Skip to content

Commit d2c9a35

Browse files
authored
Merge pull request #56865 from nkdengineer/fix/56796
[CP Staging] fix: FAB is not responsive after exiting create expense flow
2 parents c6aa8bd + 45c347a commit d2c9a35

File tree

3 files changed

+105
-73
lines changed

3 files changed

+105
-73
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
import {InteractionManager} from 'react-native';
2+
import Navigation from '@libs/Navigation/Navigation';
3+
4+
/**
5+
* On iOS, the navigation transition can sometimes break other animations, such as the closing modal.
6+
* In this case we need to wait for the animation to be complete before executing the navigation
7+
*/
8+
function navigateAfterInteraction(callback: () => void) {
9+
InteractionManager.runAfterInteractions(() => {
10+
Navigation.setNavigationActionToMicrotaskQueue(callback);
11+
});
12+
}
13+
14+
export default navigateAfterInteraction;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
function navigateAfterInteraction(callback: () => void) {
2+
callback();
3+
}
4+
5+
export default navigateAfterInteraction;

src/pages/home/sidebar/FloatingActionButtonAndPopover.tsx

+86-73
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ import {canActionTask as canActionTaskUtils, canModifyTask as canModifyTaskUtils
3131
import {setSelfTourViewed} from '@libs/actions/Welcome';
3232
import getIconForAction from '@libs/getIconForAction';
3333
import interceptAnonymousUser from '@libs/interceptAnonymousUser';
34+
import navigateAfterInteraction from '@libs/Navigation/navigateAfterInteraction';
3435
import Navigation from '@libs/Navigation/Navigation';
3536
import {hasSeenTourSelector} from '@libs/onboardingSelectors';
3637
import {areAllGroupPoliciesExpenseChatDisabled, canSendInvoice as canSendInvoicePolicyUtils, shouldShowPolicy} from '@libs/PolicyUtils';
@@ -454,6 +455,80 @@ function FloatingActionButtonAndPopover({onHideCreateMenu, onShowCreateMenu, isT
454455
const canModifyTask = canModifyTaskUtils(viewTourTaskReport, currentUserPersonalDetails.accountID);
455456
const canActionTask = canActionTaskUtils(viewTourTaskReport, currentUserPersonalDetails.accountID);
456457

458+
const menuItems = [
459+
...expenseMenuItems,
460+
{
461+
icon: Expensicons.ChatBubble,
462+
text: translate('sidebarScreen.fabNewChat'),
463+
onSelected: () => interceptAnonymousUser(startNewChat),
464+
},
465+
...(canSendInvoice
466+
? [
467+
{
468+
icon: Expensicons.InvoiceGeneric,
469+
text: translate('workspace.invoices.sendInvoice'),
470+
shouldCallAfterModalHide: shouldRedirectToExpensifyClassic,
471+
onSelected: () =>
472+
interceptAnonymousUser(() => {
473+
if (shouldRedirectToExpensifyClassic) {
474+
setModalVisible(true);
475+
return;
476+
}
477+
478+
startMoneyRequest(
479+
CONST.IOU.TYPE.INVOICE,
480+
// When starting to create an invoice from the global FAB, there is not an existing report yet. A random optimistic reportID is generated and used
481+
// for all of the routes in the creation flow.
482+
generateReportID(),
483+
);
484+
}),
485+
},
486+
]
487+
: []),
488+
...(canUseSpotnanaTravel
489+
? [
490+
{
491+
icon: Expensicons.Suitcase,
492+
text: translate('travel.bookTravel'),
493+
onSelected: () => interceptAnonymousUser(() => Navigation.navigate(ROUTES.TRAVEL_MY_TRIPS)),
494+
},
495+
]
496+
: []),
497+
...(!hasSeenTour
498+
? [
499+
{
500+
icon: Expensicons.Binoculars,
501+
iconStyles: styles.popoverIconCircle,
502+
iconFill: theme.icon,
503+
text: translate('tour.takeATwoMinuteTour'),
504+
description: translate('tour.exploreExpensify'),
505+
onSelected: () => {
506+
openExternalLink(navatticURL);
507+
setSelfTourViewed(isAnonymousUser());
508+
if (viewTourTaskReport && canModifyTask && canActionTask) {
509+
completeTask(viewTourTaskReport);
510+
}
511+
},
512+
},
513+
]
514+
: []),
515+
...(!isLoading && shouldShowNewWorkspaceButton
516+
? [
517+
{
518+
displayInDefaultIconColor: true,
519+
contentFit: 'contain' as ImageContentFit,
520+
icon: Expensicons.NewWorkspace,
521+
iconWidth: variables.w46,
522+
iconHeight: variables.h40,
523+
text: translate('workspace.new.newWorkspace'),
524+
description: translate('workspace.new.getTheExpensifyCardAndMore'),
525+
onSelected: () => interceptAnonymousUser(() => Navigation.navigate(ROUTES.WORKSPACE_CONFIRMATION.getRoute(Navigation.getActiveRoute()))),
526+
},
527+
]
528+
: []),
529+
...quickActionMenuItems,
530+
];
531+
457532
return (
458533
<View style={styles.flexGrow1}>
459534
<PopoverMenu
@@ -462,79 +537,17 @@ function FloatingActionButtonAndPopover({onHideCreateMenu, onShowCreateMenu, isT
462537
anchorPosition={styles.createMenuPositionSidebar(windowHeight)}
463538
onItemSelected={hideCreateMenu}
464539
fromSidebarMediumScreen={!shouldUseNarrowLayout}
465-
menuItems={[
466-
...expenseMenuItems,
467-
{
468-
icon: Expensicons.ChatBubble,
469-
text: translate('sidebarScreen.fabNewChat'),
470-
onSelected: () => interceptAnonymousUser(startNewChat),
471-
},
472-
...(canSendInvoice
473-
? [
474-
{
475-
icon: Expensicons.InvoiceGeneric,
476-
text: translate('workspace.invoices.sendInvoice'),
477-
shouldCallAfterModalHide: shouldRedirectToExpensifyClassic,
478-
onSelected: () =>
479-
interceptAnonymousUser(() => {
480-
if (shouldRedirectToExpensifyClassic) {
481-
setModalVisible(true);
482-
return;
483-
}
484-
485-
startMoneyRequest(
486-
CONST.IOU.TYPE.INVOICE,
487-
// When starting to create an invoice from the global FAB, there is not an existing report yet. A random optimistic reportID is generated and used
488-
// for all of the routes in the creation flow.
489-
generateReportID(),
490-
);
491-
}),
492-
},
493-
]
494-
: []),
495-
...(canUseSpotnanaTravel
496-
? [
497-
{
498-
icon: Expensicons.Suitcase,
499-
text: translate('travel.bookTravel'),
500-
onSelected: () => interceptAnonymousUser(() => Navigation.navigate(ROUTES.TRAVEL_MY_TRIPS)),
501-
},
502-
]
503-
: []),
504-
...(!hasSeenTour
505-
? [
506-
{
507-
icon: Expensicons.Binoculars,
508-
iconStyles: styles.popoverIconCircle,
509-
iconFill: theme.icon,
510-
text: translate('tour.takeATwoMinuteTour'),
511-
description: translate('tour.exploreExpensify'),
512-
onSelected: () => {
513-
openExternalLink(navatticURL);
514-
setSelfTourViewed(isAnonymousUser());
515-
if (viewTourTaskReport && canModifyTask && canActionTask) {
516-
completeTask(viewTourTaskReport);
517-
}
518-
},
519-
},
520-
]
521-
: []),
522-
...(!isLoading && shouldShowNewWorkspaceButton
523-
? [
524-
{
525-
displayInDefaultIconColor: true,
526-
contentFit: 'contain' as ImageContentFit,
527-
icon: Expensicons.NewWorkspace,
528-
iconWidth: variables.w46,
529-
iconHeight: variables.h40,
530-
text: translate('workspace.new.newWorkspace'),
531-
description: translate('workspace.new.getTheExpensifyCardAndMore'),
532-
onSelected: () => interceptAnonymousUser(() => Navigation.navigate(ROUTES.WORKSPACE_CONFIRMATION.getRoute(Navigation.getActiveRoute()))),
533-
},
534-
]
535-
: []),
536-
...quickActionMenuItems,
537-
]}
540+
menuItems={menuItems.map((item) => {
541+
return {
542+
...item,
543+
onSelected: () => {
544+
if (!item.onSelected) {
545+
return;
546+
}
547+
navigateAfterInteraction(item.onSelected);
548+
},
549+
};
550+
})}
538551
withoutOverlay
539552
anchorRef={fabRef}
540553
/>

0 commit comments

Comments
 (0)