diff --git a/app/actions/actionsTypes.js b/app/actions/actionsTypes.js index 7c191903..74780887 100644 --- a/app/actions/actionsTypes.js +++ b/app/actions/actionsTypes.js @@ -47,7 +47,7 @@ export const ROOM = createRequestTypes('ROOM', [ 'MESSAGE_RECEIVED', 'SET_LAST_OPEN' ]); -export const APP = createRequestTypes('APP', ['START', 'READY', 'INIT']); +export const APP = createRequestTypes('APP', ['START', 'READY', 'INIT', 'SET_STACK_ROOT']); export const MESSAGES = createRequestTypes('MESSAGES', [ ...defaultTypes, 'ACTIONS_SHOW', diff --git a/app/actions/index.js b/app/actions/index.js index 634d049c..01366e55 100644 --- a/app/actions/index.js +++ b/app/actions/index.js @@ -20,6 +20,13 @@ export function appInit() { }; } +export function setStackRoot(stackRoot) { + return { + type: APP.SET_STACK_ROOT, + stackRoot + }; +} + export function setCurrentServer(server) { return { type: types.SET_CURRENT_SERVER, diff --git a/app/containers/Sidebar.js b/app/containers/Sidebar.js index 975606dc..4dce2487 100644 --- a/app/containers/Sidebar.js +++ b/app/containers/Sidebar.js @@ -7,7 +7,7 @@ import { connect } from 'react-redux'; import Icon from 'react-native-vector-icons/MaterialIcons'; import { Navigation } from 'react-native-navigation'; -import { appStart as appStartAction } from '../actions'; +import { appStart as appStartAction, setStackRoot as setStackRootAction } from '../actions'; import { logout as logoutAction } from '../actions/login'; import Avatar from './Avatar'; import Status from './status'; @@ -19,7 +19,6 @@ import I18n from '../i18n'; import scrollPersistTaps from '../utils/scrollPersistTaps'; import DeviceInfo from '../utils/deviceInfo'; import Drawer from '../Drawer'; -import EventEmitter from '../utils/events'; const styles = StyleSheet.create({ container: { @@ -86,6 +85,7 @@ const keyExtractor = item => item.id; @connect(state => ({ Site_Name: state.settings.Site_Name, + stackRoot: state.app.stackRoot, user: { id: state.login.user && state.login.user.id, language: state.login.user && state.login.user.language, @@ -95,30 +95,31 @@ const keyExtractor = item => item.id; baseUrl: state.settings.Site_Url || state.server ? state.server.server : '' }), dispatch => ({ logout: () => dispatch(logoutAction()), - appStart: () => dispatch(appStartAction('outside')) + appStart: () => dispatch(appStartAction('outside')), + setStackRoot: stackRoot => dispatch(setStackRootAction(stackRoot)) })) export default class Sidebar extends Component { static propTypes = { baseUrl: PropTypes.string, componentId: PropTypes.string, Site_Name: PropTypes.string.isRequired, + stackRoot: PropTypes.string.isRequired, user: PropTypes.object, logout: PropTypes.func.isRequired, - appStart: PropTypes.func + appStart: PropTypes.func, + setStackRoot: PropTypes.func } constructor(props) { super(props); this.state = { - showStatus: false, - currentStack: 'RoomsListView' + showStatus: false }; Navigation.events().bindComponent(this); } componentDidMount() { this.setStatus(); - EventEmitter.addEventListener('ChangeStack', this.handleChangeStack); } componentWillReceiveProps(nextProps) { @@ -128,10 +129,6 @@ export default class Sidebar extends Component { } } - componentWillUnmount() { - EventEmitter.removeListener('ChangeStack', this.handleChangeStack); - } - handleChangeStack = (event) => { const { stack } = event; this.setStack(stack); @@ -164,16 +161,16 @@ export default class Sidebar extends Component { }); } - setStack = (stack) => { - const { currentStack } = this.state; - if (currentStack !== stack) { - Navigation.setStackRoot('AppRoot', { + setStack = async(stack) => { + const { stackRoot, setStackRoot } = this.props; + if (stackRoot !== stack) { + await Navigation.setStackRoot('AppRoot', { component: { id: stack, name: stack } }); - this.setState({ currentStack: stack }); + setStackRoot(stack); } } @@ -237,7 +234,7 @@ export default class Sidebar extends Component { } renderNavigation = () => { - const { currentStack } = this.state; + const { stackRoot } = this.props; const { logout } = this.props; return ( [ @@ -246,21 +243,21 @@ export default class Sidebar extends Component { left: , onPress: () => this.sidebarNavigate('RoomsListView'), testID: 'sidebar-chats', - current: currentStack === 'RoomsListView' + current: stackRoot === 'RoomsListView' }), this.renderItem({ text: I18n.t('Profile'), left: , onPress: () => this.sidebarNavigate('ProfileView'), testID: 'sidebar-profile', - current: currentStack === 'ProfileView' + current: stackRoot === 'ProfileView' }), this.renderItem({ text: I18n.t('Settings'), left: , onPress: () => this.sidebarNavigate('SettingsView'), testID: 'sidebar-settings', - current: currentStack === 'SettingsView' + current: stackRoot === 'SettingsView' }), this.renderSeparator('separator-logout'), this.renderItem({ diff --git a/app/reducers/app.js b/app/reducers/app.js index 53d978e3..7e0dec2a 100644 --- a/app/reducers/app.js +++ b/app/reducers/app.js @@ -3,6 +3,7 @@ import { APP } from '../actions/actionsTypes'; const initialState = { root: null, + stackRoot: 'RoomsListView', starting: true, ready: false, inactive: false, @@ -37,6 +38,11 @@ export default function app(state = initialState, action) { ...state, root: action.root }; + case APP.SET_STACK_ROOT: + return { + ...state, + stackRoot: action.stackRoot + }; case APP.INIT: return { ...state, diff --git a/app/sagas/deepLinking.js b/app/sagas/deepLinking.js index 83247379..c4479e06 100644 --- a/app/sagas/deepLinking.js +++ b/app/sagas/deepLinking.js @@ -6,23 +6,38 @@ import { import { Navigation } from 'react-native-navigation'; import * as types from '../actions/actionsTypes'; -import { appStart } from '../actions'; +import { appStart, setStackRoot } from '../actions'; import { selectServerRequest } from '../actions/server'; import database from '../lib/realm'; import RocketChat from '../lib/rocketchat'; import EventEmitter from '../utils/events'; -const navigate = function* go({ params, sameServer = true }) { +const navigate = function* navigate({ params, sameServer = true }) { if (!sameServer) { yield put(appStart('inside')); } if (params.rid) { const canOpenRoom = yield RocketChat.canOpenRoom(params); if (canOpenRoom) { + const stack = 'RoomsListView'; + const stackRoot = yield select(state => state.app.stackRoot); + // Make sure current stack is RoomsListView before navigate to RoomView - EventEmitter.emit('ChangeStack', { stack: 'RoomsListView' }); - yield Navigation.popToRoot('RoomsListView'); - Navigation.push('RoomsListView', { + if (stackRoot !== stack) { + yield Navigation.setStackRoot('AppRoot', { + component: { + id: stack, + name: stack + } + }); + yield put(setStackRoot(stack)); + } + try { + yield Navigation.popToRoot(stack); + } catch (error) { + console.log(error); + } + Navigation.push(stack, { component: { name: 'RoomView', passProps: {