diff --git a/package-lock.json b/package-lock.json index d35fb70..b73faef 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11239,6 +11239,14 @@ "shallowequal": "^1.0.2" } }, + "react-infinite-scroller": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.2.tgz", + "integrity": "sha512-YshEvalWsC/vTWwA2t5rc+ku8JSXTIe/gzNuyA7rkdJZfs+7LfOz/HpOI3g/VqPCZIxikXBJDlSWltVZN4KyVQ==", + "requires": { + "prop-types": "^15.5.8" + } + }, "react-is": { "version": "16.4.2", "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.4.2.tgz", diff --git a/package.json b/package.json index ac49e3b..52939cd 100644 --- a/package.json +++ b/package.json @@ -78,6 +78,7 @@ "react": "^16.3.2", "react-dom": "^16.3.2", "react-hot-loader": "^4.1.1", + "react-infinite-scroller": "^1.2.2", "react-redux": "^5.0.7", "react-router": "^4.3.1", "react-scrollbar": "^0.5.4", diff --git a/src/components/dialogs/MapListMoreDialog.jsx b/src/components/dialogs/MapListMoreDialog.jsx new file mode 100644 index 0000000..82fbafa --- /dev/null +++ b/src/components/dialogs/MapListMoreDialog.jsx @@ -0,0 +1,128 @@ +// @flow +import React from 'react'; +import { bindActionCreators } from 'redux'; +import { connect } from 'react-redux'; +import { RouteRow } from '$components/maps/RouteRow'; +import { Scroll } from '$components/Scroll'; +import { + searchSetAuthor, + searchSetDistance, + searchSetTitle, +} from '$redux/user/actions'; + +type Props = { + routes: { + limit: Number, + loading: Boolean, // <-- maybe delete this + list: Array, + filter: { + title: String, + author: String, + distance: Array, + tab: Array, + } + }, + editing: Boolean, + routes_sorted: Array, + + searchSetAuthor: Function, + searchSetDistance: Function, + searchSetTitle: Function, +}; + +class Component extends React.Component { + setTitle = ({ target: { value } }) => { + this.props.searchSetTitle(value); + }; + + setDistanceMin = ({ target: { value } }) => { + console.log('A'); + const parsed = parseInt(value > 0 ? value : 0, 10); + const { distance } = this.props.routes.filter; + + this.props.searchSetDistance([parsed, distance[1] > parsed ? distance[1] : parsed]); + }; + + setDistanceMax = ({ target: { value } }) => { + console.log('B'); + const parsed = parseInt(value > 0 ? value : 0, 10); + const { distance } = this.props.routes.filter; + + this.props.searchSetDistance([distance[0], parsed > distance[0] ? parsed : distance[0]]); + }; + + render() { + const { + routes: { + list, + filter: { + title, + distance, + tab, + } + }, + editing, + } = this.props; + + return ( +
+
+
+ маршруты +
+
+ + +
+ + + + +
+
+ +
+ { + list.map((route, index) => ( + + )) + } +
+
+
+ ); + } +} + +const mapStateToProps = ({ user: { editing, routes } }) => ({ + routes, + editing, + // routes_sorted: Object.keys(routes).sort((a, b) => (Date.parse(routes[b].updated_at) - Date.parse(routes[a].updated_at))), +}); + +const mapDispatchToProps = dispatch => bindActionCreators({ + searchSetAuthor, + searchSetDistance, + searchSetTitle, +}, dispatch); + +export const MapListMoreDialog = connect(mapStateToProps, mapDispatchToProps)(Component); diff --git a/src/containers/LeftDialog.jsx b/src/containers/LeftDialog.jsx index c59a05d..3e664f9 100644 --- a/src/containers/LeftDialog.jsx +++ b/src/containers/LeftDialog.jsx @@ -5,6 +5,7 @@ import { MapListDialog } from '$components/dialogs/MapListDialog'; import classnames from 'classnames'; import { AppInfoDialog } from '$components/dialogs/AppInfoDialog'; import { Icon } from '$components/panels/Icon'; +import { MapListMoreDialog } from '$components/dialogs/MapListMoreDialog'; type Props = { dialog: String, @@ -14,7 +15,7 @@ type Props = { } const LEFT_DIALOGS = { - [DIALOGS.MAP_LIST]: MapListDialog, + [DIALOGS.MAP_LIST]: MapListMoreDialog, [DIALOGS.APP_INFO]: AppInfoDialog, }; diff --git a/src/index.js b/src/index.js index 837d1be..4dcae9a 100644 --- a/src/index.js +++ b/src/index.js @@ -1,6 +1,6 @@ /* - todo add ability to copy-paste address after saving + done add ability to copy-paste address after saving todo save progress done hide sticker dialog on sticker selection diff --git a/src/redux/user/actions.js b/src/redux/user/actions.js index 2a9e102..27906fd 100644 --- a/src/redux/user/actions.js +++ b/src/redux/user/actions.js @@ -32,7 +32,6 @@ export const setSaveSuccess = payload => ({ type: ACTIONS.SET_SAVE_SUCCESS, ...p export const setSaveError = save_error => ({ type: ACTIONS.SET_SAVE_ERROR, save_error }); export const setSaveOverwrite = () => ({ type: ACTIONS.SET_SAVE_OVERWRITE }); -export const showRenderer = () => ({ type: ACTIONS.SHOW_RENDERER }); export const hideRenderer = () => ({ type: ACTIONS.HIDE_RENDERER }); export const setRenderer = payload => ({ type: ACTIONS.SET_RENDERER, payload }); export const takeAShot = () => ({ type: ACTIONS.TAKE_A_SHOT }); @@ -49,4 +48,6 @@ export const setReady = ready => ({ type: ACTIONS.SET_READY, ready }); export const gotVkUser = user => ({ type: ACTIONS.GOT_VK_USER, user }); export const keyPressed = ({ key }) => ({ type: ACTIONS.KEY_PRESSED, key }); -export const iframeLoginVk = payload => ({ type: ACTIONS.IFRAME_LOGIN_VK, ...payload }); +export const searchSetTitle = title => ({ type: ACTIONS.SEARCH_SET_TITLE, title }); +export const searchSetDistance = distance => ({ type: ACTIONS.SEARCH_SET_DISTANCE, distance }); +export const searchSetTab = tab => ({ type: ACTIONS.SEARCH_SET_TAB, tab }); diff --git a/src/redux/user/constants.js b/src/redux/user/constants.js index 4a60ebf..e41beb9 100644 --- a/src/redux/user/constants.js +++ b/src/redux/user/constants.js @@ -50,4 +50,9 @@ export const ACTIONS = ({ KEY_PRESSED: 'KEY_PRESSED', IFRAME_LOGIN_VK: 'IFRAME_LOGIN_VK', + + SEARCH_SET_TITLE: 'SEARCH_SET_TITLE', + SEARCH_SET_DISTANCE: 'SEARCH_SET_DISTANCE', + + SEARCH_SET_TAB: 'SEARCH_SET_TAB', }: { [key: String]: String }); diff --git a/src/redux/user/reducer.js b/src/redux/user/reducer.js index 11b38ff..071d21f 100644 --- a/src/redux/user/reducer.js +++ b/src/redux/user/reducer.js @@ -95,6 +95,39 @@ const setReady = (state, { ready = true }) => ({ ready, }); +const searchSetTitle = (state, { title = '' }) => ({ + ...state, + routes: { + ...state.routes, + filter: { + ...state.routes.filter, + title, + } + } +}); + +const searchSetDistance = (state, { distance = [0, 9999] }) => ({ + ...state, + routes: { + ...state.routes, + filter: { + ...state.routes.filter, + distance, + } + } +}); + +const searchSetTab = (state, { tab = 'mine' }) => ({ + ...state, + routes: { + ...state.routes, + filter: { + ...state.routes.filter, + tab: ['mine', 'all', 'star'].indexOf(tab) >= 0 ? tab : 'mine', + } + } +}); + const HANDLERS = ({ [ACTIONS.SET_USER]: setUser, [ACTIONS.SET_EDITING]: setEditing, @@ -122,6 +155,10 @@ const HANDLERS = ({ [ACTIONS.SET_DIALOG]: setDialog, [ACTIONS.SET_DIALOG_ACTIVE]: setDialogActive, [ACTIONS.SET_READY]: setReady, + + [ACTIONS.SEARCH_SET_TITLE]: searchSetTitle, + [ACTIONS.SEARCH_SET_DISTANCE]: searchSetDistance, + [ACTIONS.SEARCH_SET_TAB]: searchSetTab, }: { [key: String]: Function }); export const INITIAL_STATE = { @@ -145,8 +182,8 @@ export const INITIAL_STATE = { save_overwriting: false, save_processing: false, - dialog: DIALOGS.NONE, - dialog_active: false, + dialog: DIALOGS.MAP_LIST, + dialog_active: true, renderer: { data: '', @@ -155,7 +192,21 @@ export const INITIAL_STATE = { renderer_active: false, info: '', progress: 0, - } + }, + + routes: { + limit: 0, + loading: false, // <-- maybe delete this + list: [], + filter: { + title: '', + starred: false, + distance: [0, 300], + + author: '', + tab: 'mine', + } + }, }; export const userReducer = createReducer(INITIAL_STATE, HANDLERS); diff --git a/src/redux/user/sagas.js b/src/redux/user/sagas.js index e31473d..0b27f7a 100644 --- a/src/redux/user/sagas.js +++ b/src/redux/user/sagas.js @@ -435,6 +435,13 @@ function* keyPressedSaga({ key }): void { return; } +function* searchSetSaga() { + yield delay(500); + const { routes: { filter: { title, distance, tab }}} = yield select(getState); + + console.log({ title, distance, tab }); +} + export function* userSaga() { yield takeLatest(REHYDRATE, authCheckSaga); yield takeEvery(ACTIONS.SET_MODE, setModeSaga); @@ -467,4 +474,9 @@ export function* userSaga() { yield takeLatest(ACTIONS.KEY_PRESSED, keyPressedSaga); yield takeLatest(ACTIONS.IFRAME_LOGIN_VK, iframeLoginVkSaga); + + yield takeLatest([ + ACTIONS.SEARCH_SET_TITLE, + ACTIONS.SEARCH_SET_DISTANCE, + ], searchSetSaga) }