From 996de26e07b80e5a5faee6fd0a64b7f96c441d0b Mon Sep 17 00:00:00 2001 From: Chris Bobbe Date: Thu, 24 Sep 2020 22:24:50 -0700 Subject: [PATCH] nav: Tell all screens on AppNavigator that they get the `navigation` prop. This has been done on an as-needed basis in the past, but in a few different ways, and it would be good to be consistent. With #3804 approaching, it makes sense to proactively furnish all these components with the knowledge that they have the `navigation` prop if they ever need it. In doing so, we're making an unchecked assumption: that the components will in fact be passed the `navigation` prop, in the shape we say it will take. It's unchecked because of the `$FlowFixMe` from aaaf847fe on the route config passed to `createStackNavigator` [0]. ----- There is a doc for doing this in TypeScript [1], but it's clearly wrong about how to handle it in Flow (and I believe it's also wrong about TypeScript in ways that would matter to us if we were using TypeScript). In particular, `NavigationStackScreenProps` is marketed (under "Type checking all props for a screen") as something you can spread in your `Props` type to get `theme` and `screenProps` along with `navigation`. Sounds great. But it doesn't exist in the libdef, and I haven't found a clear alternative. In #4127, a demo PR branch that informed 17f73d88d -- in particular, f48282752 [FOR DISCUSSION] One way to get `sharedData` into ShareToStream, ShareToPm -- I seemed [2] to have favored something called `NavigationNavigatorProps` for this purpose. But it has at least two points against it: 1. I don't see documentation that we're supposed to use it, or how. 2. It's not tailored (or conveniently tailorable) to screens that get put on a particular type of navigator (stack, drawer, tabs, etc.) So, take a conservative approach and just type the `navigation` prop, and in a way that says we know it comes from a stack navigator. The main example in the TypeScript doc is the following: ``` type Props = { navigation: NavigationStackProp<{ userId: string }>; }; ``` We find `NavigationStackProp` is a good thing to use, but `{ userId: string }` is bad for a couple of reasons: - It's off by a level of nesting; surely they mean to describe `navigation.state.params`. To do that, the type needs to look something like `{ params: { userId: string } }`. - It leaves out all the other things on `navigation.state` including `key` and `routeName`, which might be nice to have someday. Experimentally, these are conveniently filled in by saying `NavigationStackProp` [3]. So, account for those deficiencies straightforwardly. [0] Initial thoughts on this were written in a36814e80, but see https://github.com/zulip/zulip-mobile/pull/4114#issuecomment-634255590 for more recent concerns about typing our component classes with a static `navigationOptions` property. I'm inclined to not revisit these suppressions until we're on React Navigation v5, which has quite a different, component-based API, and a particular guide for type-checking the route config and the screen components in a unified way; that's at https://reactnavigation.org/docs/typescript/. [1] https://reactnavigation.org/docs/4.x/typescript/ [2] Possibly following a train of thought from https://chat.zulip.org/#narrow/stream/243-mobile-team/topic/react-navigation.20types/near/878262. [3] Like at https://github.com/react-navigation/react-navigation/issues/3643#issuecomment-370044086, but with `NavigationStackProp` instead of `NavigationScreenProp`. --- src/account-info/AccountDetailsScreen.js | 6 ++++-- src/account/AccountPickScreen.js | 5 +++++ src/chat/ChatScreen.js | 6 ++++-- src/chat/GroupDetailsScreen.js | 10 ++++++++-- src/common/SmartUrlInput.js | 8 ++++++-- src/diagnostics/DiagnosticsScreen.js | 6 +++++- src/diagnostics/StorageScreen.js | 5 +++++ src/diagnostics/TimingScreen.js | 9 ++++++++- src/diagnostics/VariablesScreen.js | 9 ++++++++- src/emoji/EmojiPickerScreen.js | 7 +++++-- src/lightbox/LightboxScreen.js | 9 +++++++-- src/main/MainScreenWithTabs.js | 6 ++++-- src/reactions/MessageReactionList.js | 9 +++++++-- src/search/SearchMessagesScreen.js | 5 +++++ src/settings/DebugScreen.js | 5 +++++ src/settings/LanguageScreen.js | 5 +++++ src/settings/LegalScreen.js | 5 +++++ src/settings/NotificationsScreen.js | 5 +++++ src/sharing/SharingScreen.js | 11 +++++++++-- src/start/AuthScreen.js | 10 ++++++++-- src/start/DevAuthScreen.js | 5 +++++ src/start/LoadingScreen.js | 9 ++++++++- src/start/PasswordAuthScreen.js | 10 ++++++++-- src/start/RealmScreen.js | 9 ++++++--- src/streams/CreateStreamScreen.js | 5 +++++ src/streams/EditStreamScreen.js | 9 +++++++-- src/streams/InviteUsersScreen.js | 9 +++++++-- src/streams/StreamScreen.js | 9 +++++++-- src/topics/TopicListScreen.js | 9 +++++++-- src/user-groups/CreateGroupScreen.js | 5 +++++ src/user-status/UserStatusScreen.js | 5 +++++ src/users/UsersScreen.js | 7 ++++++- 32 files changed, 194 insertions(+), 38 deletions(-) diff --git a/src/account-info/AccountDetailsScreen.js b/src/account-info/AccountDetailsScreen.js index c969c8028e3..261173912bc 100644 --- a/src/account-info/AccountDetailsScreen.js +++ b/src/account-info/AccountDetailsScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; -import type { NavigationScreenProp } from 'react-navigation'; import type { Dispatch, UserOrBot } from '../types'; import { createStyleSheet } from '../styles'; import { connect } from '../react-redux'; @@ -30,7 +30,9 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| userId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| ...NavigationStateRoute, params: {| userId: number |} |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/account/AccountPickScreen.js b/src/account/AccountPickScreen.js index 148e9daf166..2d0cf6232e1 100644 --- a/src/account/AccountPickScreen.js +++ b/src/account/AccountPickScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -11,6 +12,10 @@ import AccountList from './AccountList'; import { navigateToRealmScreen, accountSwitch, removeAccount } from '../actions'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + accounts: AccountStatus[], dispatch: Dispatch, hasAuth: boolean, diff --git a/src/chat/ChatScreen.js b/src/chat/ChatScreen.js index 5b683228417..0f86b6a1c50 100644 --- a/src/chat/ChatScreen.js +++ b/src/chat/ChatScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { withNavigationFocus } from 'react-navigation'; import { ActionSheetProvider } from '@expo/react-native-action-sheet'; import { compose } from 'redux'; @@ -34,7 +34,9 @@ type SelectorProps = {| |}; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| narrow: Narrow |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| ...NavigationStateRoute, params: {| narrow: Narrow |} |}>, dispatch: Dispatch, // From React Navigation's `withNavigationFocus` HOC. Type copied diff --git a/src/chat/GroupDetailsScreen.js b/src/chat/GroupDetailsScreen.js index f087aa336b8..7f39a1b1d0e 100644 --- a/src/chat/GroupDetailsScreen.js +++ b/src/chat/GroupDetailsScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { FlatList } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch, UserOrBot } from '../types'; import { connect } from '../react-redux'; @@ -10,7 +10,13 @@ import UserItem from '../users/UserItem'; import { navigateToAccountDetails } from '../actions'; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| recipients: UserOrBot[] |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| recipients: UserOrBot[] |}, + |}>, + dispatch: Dispatch, |}>; diff --git a/src/common/SmartUrlInput.js b/src/common/SmartUrlInput.js index 95650656da2..1408734782a 100644 --- a/src/common/SmartUrlInput.js +++ b/src/common/SmartUrlInput.js @@ -2,7 +2,11 @@ import React, { PureComponent } from 'react'; import { TextInput, TouchableWithoutFeedback, View } from 'react-native'; import type { ViewStyleProp } from 'react-native/Libraries/StyleSheet/StyleSheet'; -import type { NavigationEventSubscription, NavigationScreenProp } from 'react-navigation'; +import type { + NavigationEventSubscription, + NavigationScreenProp, + NavigationState, +} from 'react-navigation'; import type { ThemeData } from '../styles'; import { ThemeContext, createStyleSheet } from '../styles'; @@ -45,7 +49,7 @@ type Props = $ReadOnly<{| * it appears not to contain an explicit domain. */ defaultDomain: string, - navigation: NavigationScreenProp, + navigation: NavigationScreenProp, style?: ViewStyleProp, onChangeText: (value: string) => void, onSubmitEditing: () => Promise, diff --git a/src/diagnostics/DiagnosticsScreen.js b/src/diagnostics/DiagnosticsScreen.js index f29cbbed1d8..dc71dcb9b27 100644 --- a/src/diagnostics/DiagnosticsScreen.js +++ b/src/diagnostics/DiagnosticsScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; - +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { nativeApplicationVersion } from 'expo-application'; import type { Dispatch } from '../types'; @@ -23,6 +23,10 @@ const styles = createStyleSheet({ }); type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, |}>; diff --git a/src/diagnostics/StorageScreen.js b/src/diagnostics/StorageScreen.js index 6a330aec39d..e64b8a1adb7 100644 --- a/src/diagnostics/StorageScreen.js +++ b/src/diagnostics/StorageScreen.js @@ -2,6 +2,7 @@ import React, { PureComponent } from 'react'; import { FlatList } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { GlobalState, Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -17,6 +18,10 @@ const calculateKeyStorageSizes = obj => .sort((a, b) => b.size - a.size); type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, state: GlobalState, |}>; diff --git a/src/diagnostics/TimingScreen.js b/src/diagnostics/TimingScreen.js index d57188e21f9..42a565a558f 100644 --- a/src/diagnostics/TimingScreen.js +++ b/src/diagnostics/TimingScreen.js @@ -1,12 +1,19 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { FlatList } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { Screen } from '../common'; import TimeItem from './TimeItem'; import timing from '../utils/timing'; -export default class TimingScreen extends PureComponent<{||}> { +type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, +|}>; + +export default class TimingScreen extends PureComponent { render() { return ( diff --git a/src/diagnostics/VariablesScreen.js b/src/diagnostics/VariablesScreen.js index ddcf5eec749..5b4a21c5f69 100644 --- a/src/diagnostics/VariablesScreen.js +++ b/src/diagnostics/VariablesScreen.js @@ -1,12 +1,19 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { FlatList } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import config from '../config'; import { Screen } from '../common'; import InfoItem from './InfoItem'; -export default class VariablesScreen extends PureComponent<{||}> { +type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, +|}>; + +export default class VariablesScreen extends PureComponent { render() { const variables = { enableReduxLogging: config.enableReduxLogging, diff --git a/src/emoji/EmojiPickerScreen.js b/src/emoji/EmojiPickerScreen.js index e27826a932e..bb6f2ea32e9 100644 --- a/src/emoji/EmojiPickerScreen.js +++ b/src/emoji/EmojiPickerScreen.js @@ -2,7 +2,7 @@ import React, { PureComponent } from 'react'; import { FlatList } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import * as api from '../api'; import { unicodeCodeByName } from './codePointMap'; @@ -16,10 +16,13 @@ import { navigateBack } from '../nav/navActions'; import zulipExtraEmojiMap from './zulipExtraEmojiMap'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| ...NavigationStateRoute, params: {| messageId: number |} |}>, + activeImageEmojiByName: RealmEmojiById, auth: Auth, dispatch: Dispatch, - navigation: NavigationScreenProp<{ params: {| messageId: number |} }>, |}>; type State = {| diff --git a/src/lightbox/LightboxScreen.js b/src/lightbox/LightboxScreen.js index bfe25e8636c..13380467da8 100644 --- a/src/lightbox/LightboxScreen.js +++ b/src/lightbox/LightboxScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { ActionSheetProvider } from '@expo/react-native-action-sheet'; import { ZulipStatusBar } from '../common'; @@ -19,7 +19,12 @@ const styles = createStyleSheet({ }); type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| src: string, message: Message |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| src: string, message: Message |}, + |}>, |}>; export default class LightboxScreen extends PureComponent { diff --git a/src/main/MainScreenWithTabs.js b/src/main/MainScreenWithTabs.js index e44598888f6..070f3d46a51 100644 --- a/src/main/MainScreenWithTabs.js +++ b/src/main/MainScreenWithTabs.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { ThemeData } from '../styles'; import styles, { ThemeContext } from '../styles'; @@ -9,7 +9,9 @@ import { OfflineNotice, ZulipStatusBar } from '../common'; import MainTabs from './MainTabs'; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, |}>; export default class MainScreenWithTabs extends PureComponent { diff --git a/src/reactions/MessageReactionList.js b/src/reactions/MessageReactionList.js index 04cfba68218..3c8e2cd906c 100644 --- a/src/reactions/MessageReactionList.js +++ b/src/reactions/MessageReactionList.js @@ -2,7 +2,7 @@ import React, { PureComponent } from 'react'; import { View } from 'react-native'; import { createAppContainer } from 'react-navigation'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { createMaterialTopTabNavigator } from 'react-navigation-tabs'; import * as logging from '../utils/logging'; @@ -111,7 +111,12 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| reactionName?: string, messageId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| reactionName?: string, messageId: number |}, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/search/SearchMessagesScreen.js b/src/search/SearchMessagesScreen.js index 164c5fa2dad..e6cacc702dc 100644 --- a/src/search/SearchMessagesScreen.js +++ b/src/search/SearchMessagesScreen.js @@ -1,5 +1,6 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Auth, Dispatch, Message } from '../types'; import { Screen } from '../common'; @@ -12,6 +13,10 @@ import { getAuth } from '../account/accountsSelectors'; import { fetchMessages } from '../message/fetchActions'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + auth: Auth, dispatch: Dispatch, // Warning: do not add new props without considering their effect on the diff --git a/src/settings/DebugScreen.js b/src/settings/DebugScreen.js index 27f03728f7c..65a22f3ea08 100644 --- a/src/settings/DebugScreen.js +++ b/src/settings/DebugScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Debug, Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -9,6 +10,10 @@ import { OptionRow, Screen } from '../common'; import { debugFlagToggle } from '../actions'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + debug: Debug, dispatch: Dispatch, |}>; diff --git a/src/settings/LanguageScreen.js b/src/settings/LanguageScreen.js index a72c721076a..013d8582a94 100644 --- a/src/settings/LanguageScreen.js +++ b/src/settings/LanguageScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -10,6 +11,10 @@ import { getSettings } from '../selectors'; import { settingsChange } from '../actions'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, locale: string, |}>; diff --git a/src/settings/LegalScreen.js b/src/settings/LegalScreen.js index b0a49a65131..aed8733e423 100644 --- a/src/settings/LegalScreen.js +++ b/src/settings/LegalScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -9,6 +10,10 @@ import openLink from '../utils/openLink'; import { getCurrentRealm } from '../selectors'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, realm: URL, |}>; diff --git a/src/settings/NotificationsScreen.js b/src/settings/NotificationsScreen.js index 8261c377f82..21d34ccbbce 100644 --- a/src/settings/NotificationsScreen.js +++ b/src/settings/NotificationsScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Auth, Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -10,6 +11,10 @@ import * as api from '../api'; import { settingsChange } from '../actions'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + auth: Auth, dispatch: Dispatch, offlineNotification: boolean, diff --git a/src/sharing/SharingScreen.js b/src/sharing/SharingScreen.js index d57745ebc77..038b1d79a3f 100644 --- a/src/sharing/SharingScreen.js +++ b/src/sharing/SharingScreen.js @@ -1,9 +1,10 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { Text } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { createMaterialTopTabNavigator } from 'react-navigation-tabs'; import { FormattedMessage } from 'react-intl'; + import type { Dispatch, SharedData, Auth, TabNavigationOptionsPropsType } from '../types'; import { createStyleSheet } from '../styles'; import tabsOptions from '../styles/tabs'; @@ -15,7 +16,13 @@ import ShareToStream from './ShareToStream'; import ShareToPm from './ShareToPm'; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| sharedData: SharedData |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| sharedData: SharedData |}, + |}>, + auth: Auth | void, dispatch: Dispatch, |}>; diff --git a/src/start/AuthScreen.js b/src/start/AuthScreen.js index 8774e49ce79..bf67fd43758 100644 --- a/src/start/AuthScreen.js +++ b/src/start/AuthScreen.js @@ -2,7 +2,7 @@ import React, { PureComponent } from 'react'; import { Linking, Platform } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { AppleAuthenticationCredential } from 'expo-apple-authentication'; import * as AppleAuthentication from 'expo-apple-authentication'; @@ -167,9 +167,15 @@ export const activeAuthentications = ( }; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| serverSettings: ApiResponseServerSettings |}, + |}>, + dispatch: Dispatch, realm: URL, - navigation: NavigationScreenProp<{ params: {| serverSettings: ApiResponseServerSettings |} }>, |}>; let otp = ''; diff --git a/src/start/DevAuthScreen.js b/src/start/DevAuthScreen.js index 10259c570a8..3b52e54f563 100644 --- a/src/start/DevAuthScreen.js +++ b/src/start/DevAuthScreen.js @@ -2,6 +2,7 @@ import React, { PureComponent } from 'react'; import { ActivityIndicator, View, FlatList } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Auth, DevUser, Dispatch } from '../types'; import styles, { createStyleSheet } from '../styles'; @@ -27,6 +28,10 @@ const componentStyles = createStyleSheet({ }); type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + partialAuth: Auth, dispatch: Dispatch, |}>; diff --git a/src/start/LoadingScreen.js b/src/start/LoadingScreen.js index 4aa560c9417..1f5eba6efb8 100644 --- a/src/start/LoadingScreen.js +++ b/src/start/LoadingScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { BRAND_COLOR, createStyleSheet } from '../styles'; import { LoadingIndicator, ZulipStatusBar } from '../common'; @@ -14,7 +15,13 @@ const styles = createStyleSheet({ }, }); -export default class LoadingScreen extends PureComponent<{||}> { +type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, +|}>; + +export default class LoadingScreen extends PureComponent { render() { return ( diff --git a/src/start/PasswordAuthScreen.js b/src/start/PasswordAuthScreen.js index 21a4c7d4b52..4d471378f1d 100644 --- a/src/start/PasswordAuthScreen.js +++ b/src/start/PasswordAuthScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Auth, Dispatch } from '../types'; import { createStyleSheet } from '../styles'; @@ -27,9 +27,15 @@ const styles = createStyleSheet({ }); type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| requireEmailFormat: boolean |}, + |}>, + partialAuth: Auth, dispatch: Dispatch, - navigation: NavigationScreenProp<{ params: {| requireEmailFormat: boolean |} }>, |}>; type State = {| diff --git a/src/start/RealmScreen.js b/src/start/RealmScreen.js index 7cf6bfdb9ea..c82927c3f3d 100644 --- a/src/start/RealmScreen.js +++ b/src/start/RealmScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { ScrollView, Keyboard } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { ZulipVersion } from '../utils/zulipVersion'; import type { ApiResponseServerSettings, Dispatch } from '../types'; @@ -16,12 +16,15 @@ type SelectorProps = {| |}; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, params: {| realm: URL | void, initial?: boolean, |}, - }>, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/streams/CreateStreamScreen.js b/src/streams/CreateStreamScreen.js index fdc559afabf..c6808086b54 100644 --- a/src/streams/CreateStreamScreen.js +++ b/src/streams/CreateStreamScreen.js @@ -1,5 +1,6 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch } from '../types'; import { connect } from '../react-redux'; @@ -9,6 +10,10 @@ import { Screen } from '../common'; import EditStreamCard from './EditStreamCard'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, ownEmail: string, |}>; diff --git a/src/streams/EditStreamScreen.js b/src/streams/EditStreamScreen.js index 0b03d60811c..cc307a7ee1e 100644 --- a/src/streams/EditStreamScreen.js +++ b/src/streams/EditStreamScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; -import type { NavigationScreenProp } from 'react-navigation'; import type { Dispatch, Stream } from '../types'; import { connect } from '../react-redux'; import { updateExistingStream, navigateBack } from '../actions'; @@ -14,7 +14,12 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| streamId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| streamId: number |}, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/streams/InviteUsersScreen.js b/src/streams/InviteUsersScreen.js index 645c1c5e1f1..6bb84d10cdc 100644 --- a/src/streams/InviteUsersScreen.js +++ b/src/streams/InviteUsersScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; -import type { NavigationScreenProp } from 'react-navigation'; import type { Auth, Dispatch, Stream, User } from '../types'; import { connect } from '../react-redux'; import { Screen } from '../common'; @@ -16,7 +16,12 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| streamId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| streamId: number |}, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/streams/StreamScreen.js b/src/streams/StreamScreen.js index 9e60cf4aa70..d7ea48a10ab 100644 --- a/src/streams/StreamScreen.js +++ b/src/streams/StreamScreen.js @@ -1,7 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { View } from 'react-native'; -import type { NavigationScreenProp } from 'react-navigation'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch, Stream, Subscription } from '../types'; import { connect } from '../react-redux'; @@ -30,7 +30,12 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| streamId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| streamId: number |}, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/topics/TopicListScreen.js b/src/topics/TopicListScreen.js index e6de39f29a6..d067b3fef65 100644 --- a/src/topics/TopicListScreen.js +++ b/src/topics/TopicListScreen.js @@ -1,8 +1,8 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; -import type { NavigationScreenProp } from 'react-navigation'; import type { Dispatch, Stream, TopicExtended } from '../types'; import { connect } from '../react-redux'; import { Screen } from '../common'; @@ -18,7 +18,12 @@ type SelectorProps = $ReadOnly<{| |}>; type Props = $ReadOnly<{| - navigation: NavigationScreenProp<{ params: {| streamId: number |} }>, + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp<{| + ...NavigationStateRoute, + params: {| streamId: number |}, + |}>, dispatch: Dispatch, ...SelectorProps, diff --git a/src/user-groups/CreateGroupScreen.js b/src/user-groups/CreateGroupScreen.js index 64c6cbd8560..541f37fd592 100644 --- a/src/user-groups/CreateGroupScreen.js +++ b/src/user-groups/CreateGroupScreen.js @@ -1,5 +1,6 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import type { Dispatch, User } from '../types'; import { connect } from '../react-redux'; @@ -9,6 +10,10 @@ import { groupNarrow } from '../utils/narrow'; import UserPickerCard from '../user-picker/UserPickerCard'; type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, |}>; diff --git a/src/user-status/UserStatusScreen.js b/src/user-status/UserStatusScreen.js index a139a1206dc..df9a9d3fb06 100644 --- a/src/user-status/UserStatusScreen.js +++ b/src/user-status/UserStatusScreen.js @@ -1,6 +1,7 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; import { FlatList, View } from 'react-native'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { TranslationContext } from '../boot/TranslationProvider'; import { createStyleSheet } from '../styles'; @@ -27,6 +28,10 @@ const styles = createStyleSheet({ }); type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, + dispatch: Dispatch, userStatusText: string, |}>; diff --git a/src/users/UsersScreen.js b/src/users/UsersScreen.js index b7031295ee3..3f49b520cea 100644 --- a/src/users/UsersScreen.js +++ b/src/users/UsersScreen.js @@ -1,10 +1,15 @@ /* @flow strict-local */ import React, { PureComponent } from 'react'; +import type { NavigationStackProp, NavigationStateRoute } from 'react-navigation-stack'; import { Screen } from '../common'; import UsersCard from './UsersCard'; -type Props = $ReadOnly<{||}>; +type Props = $ReadOnly<{| + // Since we've put this screen in a stack-nav route config, it gets the + // `navigation` prop for free. + navigation: NavigationStackProp, +|}>; type State = {| filter: string,