From ede8ea51d3d92fb81d71309864e757539f49ccb8 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Thu, 29 Dec 2022 17:32:54 -0800 Subject: [PATCH 01/20] Initial quintuple tap gesture on header view --- src/libs/actions/App.js | 6 ++ src/pages/home/HeaderView.js | 175 ++++++++++++++++++----------------- 2 files changed, 97 insertions(+), 84 deletions(-) diff --git a/src/libs/actions/App.js b/src/libs/actions/App.js index 874b45f1fc57..de9378b53664 100644 --- a/src/libs/actions/App.js +++ b/src/libs/actions/App.js @@ -270,6 +270,11 @@ function openProfile() { Navigation.navigate(ROUTES.SETTINGS_PROFILE); } +function openTestToolModal() { + Log.info('Neil gesture'); + console.log('Recognized gesture'); +} + export { setLocale, setSidebarLoaded, @@ -277,4 +282,5 @@ export { openProfile, openApp, reconnectApp, + openTestToolModal, }; diff --git a/src/pages/home/HeaderView.js b/src/pages/home/HeaderView.js index 2e048ad18bd8..c824a6c4af83 100644 --- a/src/pages/home/HeaderView.js +++ b/src/pages/home/HeaderView.js @@ -25,6 +25,8 @@ import Tooltip from '../../components/Tooltip'; import variables from '../../styles/variables'; import colors from '../../styles/colors'; import reportPropTypes from '../reportPropTypes'; +import { GestureDetector, Gesture } from 'react-native-gesture-handler'; +import * as App from '../../libs/actions/App'; const propTypes = { /** Toggles the navigationMenu open and closed */ @@ -74,98 +76,103 @@ const HeaderView = (props) => { const shouldShowSubscript = isPolicyExpenseChat && !props.report.isOwnPolicyExpenseChat && !ReportUtils.isArchivedRoom(props.report); const icons = ReportUtils.getIcons(props.report, props.personalDetails, props.policies); const brickRoadIndicator = ReportUtils.hasReportNameError(props.report) ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''; + const quintupleTap = Gesture.Tap() + .numberOfTaps(5) + .onEnd(App.openTestToolModal) return ( - - - {props.isSmallScreenWidth && ( - - + + + {props.isSmallScreenWidth && ( + + + + + + )} + {Boolean(props.report && title) && ( + - - - - )} - {Boolean(props.report && title) && ( - - ReportUtils.navigateToDetailsPage(props.report)} - style={[styles.flexRow, styles.alignItemsCenter, styles.flex1]} - > - {shouldShowSubscript ? ( - - ) : ( - - )} - - - {(isChatRoom || isPolicyExpenseChat) && ( - - {subtitle} - + ReportUtils.navigateToDetailsPage(props.report)} + style={[styles.flexRow, styles.alignItemsCenter, styles.flex1]} + > + {shouldShowSubscript ? ( + + ) : ( + )} - - {brickRoadIndicator === CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR && ( - - + + {(isChatRoom || isPolicyExpenseChat) && ( + + {subtitle} + + )} - )} - - - {props.report.hasOutstandingIOU && ( - - )} + {brickRoadIndicator === CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR && ( + + + + )} + + + {props.report.hasOutstandingIOU && ( + + )} - {shouldShowCallButton && } - - Report.togglePinnedState(props.report)} - style={[styles.touchableButtonImage, styles.mr0]} - > - - - + {shouldShowCallButton && } + + Report.togglePinnedState(props.report)} + style={[styles.touchableButtonImage, styles.mr0]} + > + + + + - - )} + )} + - + ); }; HeaderView.propTypes = propTypes; From 83f8d9a9ae74792d87fdf6e94b49c2fea5e8bf63 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Thu, 29 Dec 2022 17:46:18 -0800 Subject: [PATCH 02/20] Move quintuple tap gesture into the screen wrapper --- src/components/ScreenWrapper/index.js | 51 ++++---- src/pages/home/HeaderView.js | 175 +++++++++++++------------- 2 files changed, 113 insertions(+), 113 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 52d9aa5e6b62..168697e18796 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -18,6 +18,8 @@ import withWindowDimensions from '../withWindowDimensions'; import ONYXKEYS from '../../ONYXKEYS'; import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; +import {GestureDetector, Gesture} from 'react-native-gesture-handler'; +import * as App from '../../libs/actions/App'; class ScreenWrapper extends React.Component { constructor(props) { @@ -66,6 +68,9 @@ class ScreenWrapper extends React.Component { } render() { + const quintupleTap = Gesture.Tap() + .numberOfTaps(5) + .onEnd(App.openTestToolModal) return ( {(insets) => { @@ -82,28 +87,30 @@ class ScreenWrapper extends React.Component { } return ( - - - - {// If props.children is a function, call it to provide the insets to the children. - _.isFunction(this.props.children) - ? this.props.children({ - insets, - didScreenTransitionEnd: this.state.didScreenTransitionEnd, - }) - : this.props.children - } - {this.props.isSmallScreenWidth && ( - - )} - - + + + + + {// If props.children is a function, call it to provide the insets to the children. + _.isFunction(this.props.children) + ? this.props.children({ + insets, + didScreenTransitionEnd: this.state.didScreenTransitionEnd, + }) + : this.props.children + } + {this.props.isSmallScreenWidth && ( + + )} + + + ); }} diff --git a/src/pages/home/HeaderView.js b/src/pages/home/HeaderView.js index c824a6c4af83..2e048ad18bd8 100644 --- a/src/pages/home/HeaderView.js +++ b/src/pages/home/HeaderView.js @@ -25,8 +25,6 @@ import Tooltip from '../../components/Tooltip'; import variables from '../../styles/variables'; import colors from '../../styles/colors'; import reportPropTypes from '../reportPropTypes'; -import { GestureDetector, Gesture } from 'react-native-gesture-handler'; -import * as App from '../../libs/actions/App'; const propTypes = { /** Toggles the navigationMenu open and closed */ @@ -76,103 +74,98 @@ const HeaderView = (props) => { const shouldShowSubscript = isPolicyExpenseChat && !props.report.isOwnPolicyExpenseChat && !ReportUtils.isArchivedRoom(props.report); const icons = ReportUtils.getIcons(props.report, props.personalDetails, props.policies); const brickRoadIndicator = ReportUtils.hasReportNameError(props.report) ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''; - const quintupleTap = Gesture.Tap() - .numberOfTaps(5) - .onEnd(App.openTestToolModal) return ( - - - - {props.isSmallScreenWidth && ( - - - - - - )} - {Boolean(props.report && title) && ( - + + {props.isSmallScreenWidth && ( + + - ReportUtils.navigateToDetailsPage(props.report)} - style={[styles.flexRow, styles.alignItemsCenter, styles.flex1]} - > - {shouldShowSubscript ? ( - - ) : ( - - )} - - + + + )} + {Boolean(props.report && title) && ( + + ReportUtils.navigateToDetailsPage(props.report)} + style={[styles.flexRow, styles.alignItemsCenter, styles.flex1]} + > + {shouldShowSubscript ? ( + + ) : ( + + )} + + + {(isChatRoom || isPolicyExpenseChat) && ( + + {subtitle} + + )} + + {brickRoadIndicator === CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR && ( + + - {(isChatRoom || isPolicyExpenseChat) && ( - - {subtitle} - - )} - {brickRoadIndicator === CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR && ( - - - - )} - - - {props.report.hasOutstandingIOU && ( - - )} + )} + + + {props.report.hasOutstandingIOU && ( + + )} - {shouldShowCallButton && } - - Report.togglePinnedState(props.report)} - style={[styles.touchableButtonImage, styles.mr0]} - > - - - - + {shouldShowCallButton && } + + Report.togglePinnedState(props.report)} + style={[styles.touchableButtonImage, styles.mr0]} + > + + + - )} - + + )} - + ); }; HeaderView.propTypes = propTypes; From a6d758666916712f63ffaf2636adc8f97ba516fa Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 13:48:42 -0800 Subject: [PATCH 03/20] Add a small centered modal type --- src/CONST.js | 1 + .../getModalStyles/getBaseModalStyles.js | 32 +++++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/src/CONST.js b/src/CONST.js index ef02585f6aed..9b0d57424007 100755 --- a/src/CONST.js +++ b/src/CONST.js @@ -338,6 +338,7 @@ const CONST = { CONFIRM: 'confirm', CENTERED: 'centered', CENTERED_UNSWIPEABLE: 'centered_unswipeable', + CENTERED_SMALL: 'centered_small', BOTTOM_DOCKED: 'bottom_docked', POPOVER: 'popover', RIGHT_DOCKED: 'right_docked', diff --git a/src/styles/getModalStyles/getBaseModalStyles.js b/src/styles/getModalStyles/getBaseModalStyles.js index aea136f6818a..a0a707870d4d 100644 --- a/src/styles/getModalStyles/getBaseModalStyles.js +++ b/src/styles/getModalStyles/getBaseModalStyles.js @@ -123,6 +123,38 @@ export default (type, windowDimensions, popoverAnchorPosition = {}, containerSty shouldAddTopSafeAreaPadding = isSmallScreenWidth; shouldAddBottomSafeAreaPadding = false; break; + case CONST.MODAL.MODAL_TYPE.CENTERED_SMALL: + // A centered modal that takes up the minimum possible screen space on all devices + modalStyle = { + ...modalStyle, + ...{ + alignItems: 'center', + }, + }; + modalContainerStyle = { + // Shadow Styles + shadowColor: themeColors.shadow, + shadowOffset: { + width: 0, + height: 0, + }, + shadowOpacity: 0.1, + shadowRadius: 5, + + flex: 1, + borderRadius: 12, + borderWidth: 0, + }; + + // Allow this modal to be dismissed with a swipe down or swipe right + swipeDirection = ['down', 'right']; + animationIn = 'fadeIn'; + animationOut = 'fadeOut'; + shouldAddTopSafeAreaMargin = !isSmallScreenWidth; + shouldAddBottomSafeAreaMargin = !isSmallScreenWidth; + shouldAddTopSafeAreaPadding = isSmallScreenWidth; + shouldAddBottomSafeAreaPadding = false; + break; case CONST.MODAL.MODAL_TYPE.BOTTOM_DOCKED: modalStyle = { ...modalStyle, From e5c41413076637810e651d29f6dd9fc253e12af2 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 14:13:26 -0800 Subject: [PATCH 04/20] Use Onyx to open and close the test tools modal --- src/ONYXKEYS.js | 3 +++ src/libs/actions/App.js | 8 ++++++-- 2 files changed, 9 insertions(+), 2 deletions(-) diff --git a/src/ONYXKEYS.js b/src/ONYXKEYS.js index 5f338cf5c6cf..1931ecb99a14 100755 --- a/src/ONYXKEYS.js +++ b/src/ONYXKEYS.js @@ -157,6 +157,9 @@ export default { // Is Keyboard shortcuts modal open? IS_SHORTCUTS_MODAL_OPEN: 'isShortcutsModalOpen', + // Is the test tools modal open? + IS_TEST_TOOLS_MODAL_OPEN: 'isTestToolsModalOpen', + // Stores information about active wallet transfer amount, selectedAccountID, status, etc WALLET_TRANSFER: 'walletTransfer', diff --git a/src/libs/actions/App.js b/src/libs/actions/App.js index de9378b53664..56f3f2cc83d8 100644 --- a/src/libs/actions/App.js +++ b/src/libs/actions/App.js @@ -271,8 +271,11 @@ function openProfile() { } function openTestToolModal() { - Log.info('Neil gesture'); - console.log('Recognized gesture'); + Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, true); +} + +function closeTestToolModal() { + Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, false); } export { @@ -283,4 +286,5 @@ export { openApp, reconnectApp, openTestToolModal, + closeTestToolModal, }; From 3065c6c3a61b7d48b98e80171130b4e424366670 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 14:14:48 -0800 Subject: [PATCH 05/20] Blank test tools modal in the screen wrapper --- src/components/ScreenWrapper/index.js | 14 ++++++++++++-- src/components/ScreenWrapper/propTypes.js | 4 ++++ 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 168697e18796..5bf7eb0b3aaf 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -1,5 +1,6 @@ import {View} from 'react-native'; import React from 'react'; +import {GestureDetector, Gesture} from 'react-native-gesture-handler'; import {SafeAreaInsetsContext} from 'react-native-safe-area-context'; import _ from 'underscore'; import {withOnyx} from 'react-native-onyx'; @@ -18,8 +19,8 @@ import withWindowDimensions from '../withWindowDimensions'; import ONYXKEYS from '../../ONYXKEYS'; import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; -import {GestureDetector, Gesture} from 'react-native-gesture-handler'; import * as App from '../../libs/actions/App'; +import Modal from '../Modal'; class ScreenWrapper extends React.Component { constructor(props) { @@ -70,7 +71,7 @@ class ScreenWrapper extends React.Component { render() { const quintupleTap = Gesture.Tap() .numberOfTaps(5) - .onEnd(App.openTestToolModal) + .onEnd(App.openTestToolModal); return ( {(insets) => { @@ -97,6 +98,12 @@ class ScreenWrapper extends React.Component { > + {// If props.children is a function, call it to provide the insets to the children. _.isFunction(this.props.children) ? this.props.children({ @@ -128,6 +135,9 @@ export default compose( modal: { key: ONYXKEYS.MODAL, }, + isTestToolsModalOpen: { + key: ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, + }, }), withNetwork(), )(ScreenWrapper); diff --git a/src/components/ScreenWrapper/propTypes.js b/src/components/ScreenWrapper/propTypes.js index ce1858ef20bd..191cc318c66d 100644 --- a/src/components/ScreenWrapper/propTypes.js +++ b/src/components/ScreenWrapper/propTypes.js @@ -28,6 +28,9 @@ const propTypes = { /** Indicates when an Alert modal is about to be visible */ willAlertModalBecomeVisible: PropTypes.bool, }), + + /** Whether the test tools modal is open */ + isTestToolsModalOpen: PropTypes.bool, }; const defaultProps = { @@ -36,6 +39,7 @@ const defaultProps = { includePaddingTop: true, onTransitionEnd: () => {}, modal: {}, + isTestToolsModalOpen: false, keyboardAvoidingViewBehavior: 'padding', }; From eb2573ca5dd51655899e4574427158ac59a9b992 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 14:42:25 -0800 Subject: [PATCH 06/20] Create a test tools modal --- src/components/ScreenWrapper/index.js | 9 +--- src/components/ScreenWrapper/propTypes.js | 3 -- src/components/TestToolsModal.js | 46 +++++++++++++++++++ .../getModalStyles/getBaseModalStyles.js | 1 - 4 files changed, 48 insertions(+), 11 deletions(-) create mode 100644 src/components/TestToolsModal.js diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 5bf7eb0b3aaf..88793543b587 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -20,7 +20,7 @@ import ONYXKEYS from '../../ONYXKEYS'; import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; import * as App from '../../libs/actions/App'; -import Modal from '../Modal'; +import TestToolsModal from '../TestToolsModal'; class ScreenWrapper extends React.Component { constructor(props) { @@ -98,12 +98,7 @@ class ScreenWrapper extends React.Component { > - + {// If props.children is a function, call it to provide the insets to the children. _.isFunction(this.props.children) ? this.props.children({ diff --git a/src/components/ScreenWrapper/propTypes.js b/src/components/ScreenWrapper/propTypes.js index 191cc318c66d..671689d5612b 100644 --- a/src/components/ScreenWrapper/propTypes.js +++ b/src/components/ScreenWrapper/propTypes.js @@ -28,9 +28,6 @@ const propTypes = { /** Indicates when an Alert modal is about to be visible */ willAlertModalBecomeVisible: PropTypes.bool, }), - - /** Whether the test tools modal is open */ - isTestToolsModalOpen: PropTypes.bool, }; const defaultProps = { diff --git a/src/components/TestToolsModal.js b/src/components/TestToolsModal.js new file mode 100644 index 000000000000..a22dcc153d9b --- /dev/null +++ b/src/components/TestToolsModal.js @@ -0,0 +1,46 @@ +import React from 'react'; +import PropTypes from 'prop-types'; +import {withOnyx} from 'react-native-onyx'; +import {View, ScrollView} from 'react-native'; +import ONYXKEYS from '../ONYXKEYS'; +import Modal from './Modal'; +import CONST from '../CONST'; +import * as App from '../libs/actions/App'; +import TestToolMenu from './TestToolMenu'; +import styles from '../styles/styles'; + +const propTypes = { + /** Whether the test tools modal is open */ + isTestToolsModalOpen: PropTypes.bool, +}; + +const defaultProps = { + isTestToolsModalOpen: false, +}; + +const TestToolsModal = props => ( + + + + + + + +); + +TestToolsModal.propTypes = propTypes; +TestToolsModal.defaultProps = defaultProps; +TestToolsModal.displayName = 'TestToolsModal'; + +export default withOnyx({ + modal: { + key: ONYXKEYS.MODAL, + }, + isTestToolsModalOpen: { + key: ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, + }, +})(TestToolsModal); diff --git a/src/styles/getModalStyles/getBaseModalStyles.js b/src/styles/getModalStyles/getBaseModalStyles.js index a0a707870d4d..31a5757e1db1 100644 --- a/src/styles/getModalStyles/getBaseModalStyles.js +++ b/src/styles/getModalStyles/getBaseModalStyles.js @@ -141,7 +141,6 @@ export default (type, windowDimensions, popoverAnchorPosition = {}, containerSty shadowOpacity: 0.1, shadowRadius: 5, - flex: 1, borderRadius: 12, borderWidth: 0, }; From 3d6fbc7193c13f2b3ffb923e9aad51976f950d42 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 15:11:04 -0800 Subject: [PATCH 07/20] Open the test tools menu on 5 taps in dev only --- src/components/ScreenWrapper/index.js | 10 +++++++++- src/components/ScreenWrapper/propTypes.js | 3 +++ 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 88793543b587..b76af7f7900a 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -16,6 +16,7 @@ import OfflineIndicator from '../OfflineIndicator'; import compose from '../../libs/compose'; import withNavigation from '../withNavigation'; import withWindowDimensions from '../withWindowDimensions'; +import withEnvironment from '../withEnvironment'; import ONYXKEYS from '../../ONYXKEYS'; import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; @@ -69,9 +70,15 @@ class ScreenWrapper extends React.Component { } render() { + // Open the test tools menu on 5 taps in dev only const quintupleTap = Gesture.Tap() .numberOfTaps(5) - .onEnd(App.openTestToolModal); + .onEnd(() => { + if (this.props.environment !== CONST.ENVIRONMENT.DEV) { + return; + } + App.openTestToolModal(); + }); return ( {(insets) => { @@ -135,4 +142,5 @@ export default compose( }, }), withNetwork(), + withEnvironment, )(ScreenWrapper); diff --git a/src/components/ScreenWrapper/propTypes.js b/src/components/ScreenWrapper/propTypes.js index 671689d5612b..56f3e3feb672 100644 --- a/src/components/ScreenWrapper/propTypes.js +++ b/src/components/ScreenWrapper/propTypes.js @@ -1,4 +1,5 @@ import PropTypes from 'prop-types'; +import {environmentPropTypes} from '../withEnvironment'; const propTypes = { /** Array of additional styles to add */ @@ -28,6 +29,8 @@ const propTypes = { /** Indicates when an Alert modal is about to be visible */ willAlertModalBecomeVisible: PropTypes.bool, }), + + ...environmentPropTypes, }; const defaultProps = { From 933d99427b786638afda07267ac630ab0a4999b3 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 15:13:29 -0800 Subject: [PATCH 08/20] Only render the test tools modal on dev --- src/components/ScreenWrapper/index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index b76af7f7900a..b181270883ce 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -105,7 +105,7 @@ class ScreenWrapper extends React.Component { > - + {(this.props.environment === CONST.ENVIRONMENT.DEV) && } {// If props.children is a function, call it to provide the insets to the children. _.isFunction(this.props.children) ? this.props.children({ From bea47c8217fb578733b71bce69bf8b0a87c77c3b Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 15:18:46 -0800 Subject: [PATCH 09/20] Fix the gesture onEnd callback --- src/components/ScreenWrapper/index.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index b181270883ce..f207dd93592a 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -71,10 +71,11 @@ class ScreenWrapper extends React.Component { render() { // Open the test tools menu on 5 taps in dev only + const isDevEnvironment = this.props.environment === CONST.ENVIRONMENT.DEV; const quintupleTap = Gesture.Tap() .numberOfTaps(5) .onEnd(() => { - if (this.props.environment !== CONST.ENVIRONMENT.DEV) { + if (!isDevEnvironment) { return; } App.openTestToolModal(); From c762879a9f3027840d1b9554d1cf66f926a641be Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 15:36:08 -0800 Subject: [PATCH 10/20] Fix iOS by running callbacks on the JS thread --- src/components/ScreenWrapper/index.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index f207dd93592a..57a35de1c59f 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -74,6 +74,9 @@ class ScreenWrapper extends React.Component { const isDevEnvironment = this.props.environment === CONST.ENVIRONMENT.DEV; const quintupleTap = Gesture.Tap() .numberOfTaps(5) + + // Run the callbacks on the JS thread otherwise there's an error on iOS + .runOnJS(true) .onEnd(() => { if (!isDevEnvironment) { return; From 73c635cc1bb00e37739d2f96aa9637790997ee75 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 6 Jan 2023 16:17:08 -0800 Subject: [PATCH 11/20] Somewhat fix the iOS modal --- src/components/TestToolsModal.js | 8 +++----- src/styles/getModalStyles/getBaseModalStyles.js | 6 +++--- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/src/components/TestToolsModal.js b/src/components/TestToolsModal.js index a22dcc153d9b..b79842b3d834 100644 --- a/src/components/TestToolsModal.js +++ b/src/components/TestToolsModal.js @@ -24,11 +24,9 @@ const TestToolsModal = props => ( type={CONST.MODAL.MODAL_TYPE.CENTERED_SMALL} onClose={App.closeTestToolModal} > - - - - - + + + ); diff --git a/src/styles/getModalStyles/getBaseModalStyles.js b/src/styles/getModalStyles/getBaseModalStyles.js index 31a5757e1db1..b23f7e6516f2 100644 --- a/src/styles/getModalStyles/getBaseModalStyles.js +++ b/src/styles/getModalStyles/getBaseModalStyles.js @@ -149,9 +149,9 @@ export default (type, windowDimensions, popoverAnchorPosition = {}, containerSty swipeDirection = ['down', 'right']; animationIn = 'fadeIn'; animationOut = 'fadeOut'; - shouldAddTopSafeAreaMargin = !isSmallScreenWidth; - shouldAddBottomSafeAreaMargin = !isSmallScreenWidth; - shouldAddTopSafeAreaPadding = isSmallScreenWidth; + shouldAddTopSafeAreaMargin = false; + shouldAddBottomSafeAreaMargin = false; + shouldAddTopSafeAreaPadding = false; shouldAddBottomSafeAreaPadding = false; break; case CONST.MODAL.MODAL_TYPE.BOTTOM_DOCKED: From 75d30f794808c49cad05866a0baedabb93db20c5 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 16:27:14 -0800 Subject: [PATCH 12/20] Min width for mobile test tool modal --- src/components/TestToolRow.js | 2 +- src/styles/utilities/sizing.js | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/components/TestToolRow.js b/src/components/TestToolRow.js index 5364f44537b0..deefaaf3adc0 100644 --- a/src/components/TestToolRow.js +++ b/src/components/TestToolRow.js @@ -13,7 +13,7 @@ const propTypes = { }; const TestToolRow = props => ( - + {props.title} diff --git a/src/styles/utilities/sizing.js b/src/styles/utilities/sizing.js index 70826444f72d..6267f9b098da 100644 --- a/src/styles/utilities/sizing.js +++ b/src/styles/utilities/sizing.js @@ -24,6 +24,10 @@ export default { minWidth: '25%', }, + mnw120: { + minWidth: 120, + }, + w50: { width: '50%', }, From b9a901b13fb88756eedc865258d464a1ce0836aa Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 16:35:57 -0800 Subject: [PATCH 13/20] lint --- src/components/ScreenWrapper/index.js | 1 - src/components/TestToolsModal.js | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 64daf18a9e4b..352ad91f85cb 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -18,7 +18,6 @@ import ONYXKEYS from '../../ONYXKEYS'; import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; import * as App from '../../libs/actions/App'; -import TestToolsModal from '../TestToolsModal'; import SafeAreaConsumer from '../SafeAreaConsumer'; class ScreenWrapper extends React.Component { diff --git a/src/components/TestToolsModal.js b/src/components/TestToolsModal.js index b79842b3d834..8c846e4ced32 100644 --- a/src/components/TestToolsModal.js +++ b/src/components/TestToolsModal.js @@ -1,7 +1,7 @@ import React from 'react'; import PropTypes from 'prop-types'; import {withOnyx} from 'react-native-onyx'; -import {View, ScrollView} from 'react-native'; +import {View} from 'react-native'; import ONYXKEYS from '../ONYXKEYS'; import Modal from './Modal'; import CONST from '../CONST'; From ffd628805e933d8123880550c39e4d57855b372d Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 16:41:39 -0800 Subject: [PATCH 14/20] Clean up --- src/components/ScreenWrapper/index.js | 21 ++++++++++----------- 1 file changed, 10 insertions(+), 11 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 352ad91f85cb..b12b5ffbc1a3 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -76,14 +76,13 @@ class ScreenWrapper extends React.Component { render() { // Open the test tools menu on 5 taps in dev only - const isDevEnvironment = this.props.environment === CONST.ENVIRONMENT.DEV; const quintupleTap = Gesture.Tap() .numberOfTaps(5) // Run the callbacks on the JS thread otherwise there's an error on iOS .runOnJS(true) .onEnd(() => { - if (!isDevEnvironment) { + if (this.props.environment !== CONST.ENVIRONMENT.DEV) { return; } App.openTestToolModal(); @@ -116,16 +115,16 @@ class ScreenWrapper extends React.Component { {// If props.children is a function, call it to provide the insets to the children. - _.isFunction(this.props.children) - ? this.props.children({ - insets, - safeAreaPaddingBottomStyle, - didScreenTransitionEnd: this.state.didScreenTransitionEnd, - }) - : this.props.children - } + _.isFunction(this.props.children) + ? this.props.children({ + insets, + safeAreaPaddingBottomStyle, + didScreenTransitionEnd: this.state.didScreenTransitionEnd, + }) + : this.props.children + } {this.props.isSmallScreenWidth && ( - + )} From 257e1b245300413c2d8a93f2c75435a1fd8a92d6 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 16:44:33 -0800 Subject: [PATCH 15/20] Add missing prop type --- src/components/ScreenWrapper/propTypes.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/components/ScreenWrapper/propTypes.js b/src/components/ScreenWrapper/propTypes.js index 3a9a2e994d04..54ba0feb1b28 100644 --- a/src/components/ScreenWrapper/propTypes.js +++ b/src/components/ScreenWrapper/propTypes.js @@ -20,6 +20,9 @@ const propTypes = { // Called when navigated Screen's transition is finished. onTransitionEnd: PropTypes.func, + // Is the test tools modal open? + isTestToolsModalOpen: PropTypes.bool, + /** The behavior to pass to the KeyboardAvoidingView, requires some trial and error depending on the layout/devices used. * Search 'switch(behavior)' in ./node_modules/react-native/Libraries/Components/Keyboard/KeyboardAvoidingView.js for more context */ keyboardAvoidingViewBehavior: PropTypes.oneOf(['padding', 'height', 'position']), From 40105a47e197860f95a3bb7e4f94354639e8bf1a Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 16:48:34 -0800 Subject: [PATCH 16/20] Standardize on TestToolsModal name --- src/components/ScreenWrapper/index.js | 2 +- src/components/TestToolsModal.js | 2 +- src/libs/actions/App.js | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index b12b5ffbc1a3..a10a3ca2767c 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -85,7 +85,7 @@ class ScreenWrapper extends React.Component { if (this.props.environment !== CONST.ENVIRONMENT.DEV) { return; } - App.openTestToolModal(); + App.openTestToolsModal(); }); return ( diff --git a/src/components/TestToolsModal.js b/src/components/TestToolsModal.js index 8c846e4ced32..e0085fe7fd0b 100644 --- a/src/components/TestToolsModal.js +++ b/src/components/TestToolsModal.js @@ -22,7 +22,7 @@ const TestToolsModal = props => ( diff --git a/src/libs/actions/App.js b/src/libs/actions/App.js index 8ae2926bad2f..19c6fbac2e95 100644 --- a/src/libs/actions/App.js +++ b/src/libs/actions/App.js @@ -268,11 +268,11 @@ function openProfile() { Navigation.navigate(ROUTES.SETTINGS_PROFILE); } -function openTestToolModal() { +function openTestToolsModal() { Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, true); } -function closeTestToolModal() { +function closeTestToolsModal() { Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, false); } @@ -283,6 +283,6 @@ export { openProfile, openApp, reconnectApp, - openTestToolModal, - closeTestToolModal, + openTestToolsModal, + closeTestToolsModal, }; From 0d3c1c6d6365c9efc4796acba41f91bfa9e9fd47 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 17:05:52 -0800 Subject: [PATCH 17/20] Fix test tools modal after merge --- src/components/ScreenWrapper/index.js | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index a10a3ca2767c..5bd8e5a9cc6b 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -19,6 +19,7 @@ import {withNetwork} from '../OnyxProvider'; import {propTypes, defaultProps} from './propTypes'; import * as App from '../../libs/actions/App'; import SafeAreaConsumer from '../SafeAreaConsumer'; +import TestToolsModal from '../TestToolsModal'; class ScreenWrapper extends React.Component { constructor(props) { @@ -76,13 +77,14 @@ class ScreenWrapper extends React.Component { render() { // Open the test tools menu on 5 taps in dev only + const isDevEnvironment = this.props.environment === CONST.ENVIRONMENT.DEV; const quintupleTap = Gesture.Tap() .numberOfTaps(5) // Run the callbacks on the JS thread otherwise there's an error on iOS .runOnJS(true) .onEnd(() => { - if (this.props.environment !== CONST.ENVIRONMENT.DEV) { + if (!isDevEnvironment) { return; } App.openTestToolsModal(); @@ -114,6 +116,7 @@ class ScreenWrapper extends React.Component { > + {(this.props.environment === CONST.ENVIRONMENT.DEV) && } {// If props.children is a function, call it to provide the insets to the children. _.isFunction(this.props.children) ? this.props.children({ From f5982640ae9b9be0a242cd51f3df17e200008639 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Tue, 7 Feb 2023 17:11:55 -0800 Subject: [PATCH 18/20] Remove extra top margin --- src/components/TestToolMenu.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/TestToolMenu.js b/src/components/TestToolMenu.js index a5e61942f240..ec99689a05f6 100644 --- a/src/components/TestToolMenu.js +++ b/src/components/TestToolMenu.js @@ -37,7 +37,7 @@ const defaultProps = { const TestToolMenu = props => ( <> - + Test Preferences From f3fb8abbe5313de7240095badb412145a90267ce Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 17 Feb 2023 16:46:50 -0800 Subject: [PATCH 19/20] Throttle toggling test tools modal for mWeb Chrome --- src/components/ScreenWrapper/index.js | 2 +- src/components/TestToolsModal.js | 2 +- src/libs/actions/App.js | 21 ++++++++++++++------- 3 files changed, 16 insertions(+), 9 deletions(-) diff --git a/src/components/ScreenWrapper/index.js b/src/components/ScreenWrapper/index.js index 5bd8e5a9cc6b..3b4dec0f9561 100644 --- a/src/components/ScreenWrapper/index.js +++ b/src/components/ScreenWrapper/index.js @@ -87,7 +87,7 @@ class ScreenWrapper extends React.Component { if (!isDevEnvironment) { return; } - App.openTestToolsModal(); + App.toggleTestToolsModal(); }); return ( diff --git a/src/components/TestToolsModal.js b/src/components/TestToolsModal.js index e0085fe7fd0b..92aae8e3c810 100644 --- a/src/components/TestToolsModal.js +++ b/src/components/TestToolsModal.js @@ -22,7 +22,7 @@ const TestToolsModal = props => ( diff --git a/src/libs/actions/App.js b/src/libs/actions/App.js index 19c6fbac2e95..642f7d265a2c 100644 --- a/src/libs/actions/App.js +++ b/src/libs/actions/App.js @@ -268,12 +268,20 @@ function openProfile() { Navigation.navigate(ROUTES.SETTINGS_PROFILE); } -function openTestToolsModal() { - Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, true); -} +let isTestToolsModalOpen = false; +Onyx.connect({ + key: ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, + callback: val => isTestToolsModalOpen = val || false, +}); -function closeTestToolsModal() { - Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, false); +/** + * Toggle the test tools modal open or closed. Throttle the toggle to fix Android Chrome where there seems to be an extra tap which closes the modal. + * Throttling also makes the modal stay open if you accidentally tap an extra time, which is easy to do. + */ +function toggleTestToolsModal() { + const toggle = () => Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, !isTestToolsModalOpen); + const throttledToggle = _.throttle(toggle, 800, true); + throttledToggle(); } export { @@ -283,6 +291,5 @@ export { openProfile, openApp, reconnectApp, - openTestToolsModal, - closeTestToolsModal, + toggleTestToolsModal, }; From eca2c73d20f78cace6fe54e5df0ce822bdf8bf73 Mon Sep 17 00:00:00 2001 From: neil-marcellini Date: Fri, 17 Feb 2023 16:49:34 -0800 Subject: [PATCH 20/20] Use constant for test tools modal throttle time --- src/CONST.js | 1 + src/libs/actions/App.js | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/CONST.js b/src/CONST.js index f65e353ee98e..118162c41b82 100755 --- a/src/CONST.js +++ b/src/CONST.js @@ -395,6 +395,7 @@ const CONST = { WARM: 'warm', REPORT_ACTION_ITEM_LAYOUT_DEBOUNCE_TIME: 1500, SHOW_LOADING_SPINNER_DEBOUNCE_TIME: 250, + TEST_TOOLS_MODAL_THROTTLE_TIME: 800, TOOLTIP_SENSE: 1000, TRIE_INITIALIZATION: 'trie_initialization', }, diff --git a/src/libs/actions/App.js b/src/libs/actions/App.js index 642f7d265a2c..e44db00feec1 100644 --- a/src/libs/actions/App.js +++ b/src/libs/actions/App.js @@ -280,7 +280,7 @@ Onyx.connect({ */ function toggleTestToolsModal() { const toggle = () => Onyx.set(ONYXKEYS.IS_TEST_TOOLS_MODAL_OPEN, !isTestToolsModalOpen); - const throttledToggle = _.throttle(toggle, 800, true); + const throttledToggle = _.throttle(toggle, CONST.TIMING.TEST_TOOLS_MODAL_THROTTLE_TIME); throttledToggle(); }