From b28da2d69cd4a8538cd1621fc59342142351e3a9 Mon Sep 17 00:00:00 2001 From: allgandalf Date: Tue, 21 Jan 2025 16:31:50 +0530 Subject: [PATCH 1/5] add skeleton states to animate button --- src/components/ReportActionItem/ReportPreview.tsx | 11 +++++++++-- .../SettlementButton/AnimatedSettlementButton.tsx | 7 +++++-- 2 files changed, 14 insertions(+), 4 deletions(-) diff --git a/src/components/ReportActionItem/ReportPreview.tsx b/src/components/ReportActionItem/ReportPreview.tsx index 47520c6b77c8..fc38ae60fcc5 100644 --- a/src/components/ReportActionItem/ReportPreview.tsx +++ b/src/components/ReportActionItem/ReportPreview.tsx @@ -173,6 +173,7 @@ function ReportPreview({ const [isPaidAnimationRunning, setIsPaidAnimationRunning] = useState(false); const [isApprovedAnimationRunning, setIsApprovedAnimationRunning] = useState(false); + const [isSubmitAnimationRunning, setIsSubmitAnimationRunning] = useState(false); const [isHoldMenuVisible, setIsHoldMenuVisible] = useState(false); const [requestType, setRequestType] = useState(); const [paymentType, setPaymentType] = useState(); @@ -246,7 +247,7 @@ function ReportPreview({ const isArchived = isArchivedReport(iouReport); const isAdmin = policy?.role === CONST.POLICY.ROLE.ADMIN; - const shouldShowSubmitButton = canSubmitReport(iouReport, policy, transactionIDList, transactionViolations); + const shouldShowSubmitButton = canSubmitReport(iouReport, policy, transactionIDList, transactionViolations) || isSubmitAnimationRunning; const shouldDisableSubmitButton = shouldShowSubmitButton && !isAllowedToSubmitDraftExpenseReport(iouReport); @@ -262,6 +263,7 @@ function ReportPreview({ const stopAnimation = useCallback(() => { setIsPaidAnimationRunning(false); setIsApprovedAnimationRunning(false); + setIsSubmitAnimationRunning(false); }, []); const startAnimation = useCallback(() => { setIsPaidAnimationRunning(true); @@ -271,6 +273,10 @@ function ReportPreview({ setIsApprovedAnimationRunning(true); HapticFeedback.longPress(); }, []); + const startSubmitAnimation = useCallback(() => { + setIsSubmitAnimationRunning(true); + HapticFeedback.longPress(); + }, []); const confirmPayment = useCallback( (type: PaymentMethodType | undefined, payAsBusiness?: boolean) => { @@ -404,7 +410,7 @@ function ReportPreview({ const bankAccountRoute = getBankAccountRoute(chatReport); - const shouldShowSettlementButton = (shouldShowPayButton || shouldShowApproveButton) && !showRTERViolationMessage && !shouldShowBrokenConnectionViolation; + const shouldShowSettlementButton = (shouldShowPayButton || shouldShowApproveButton) && !showRTERViolationMessage && !shouldShowBrokenConnectionViolation && !isSubmitAnimationRunning; const shouldPromptUserToAddBankAccount = (hasMissingPaymentMethod(userWallet, iouReportID) || hasMissingInvoiceBankAccount(iouReportID)) && !isSettled(iouReportID); const shouldShowRBR = hasErrors && !iouSettled; @@ -622,6 +628,7 @@ function ReportPreview({ onlyShowPayElsewhere={onlyShowPayElsewhere} isPaidAnimationRunning={isPaidAnimationRunning} isApprovedAnimationRunning={isApprovedAnimationRunning} + isSubmitAnimationRunning={isSubmitAnimationRunning} canIOUBePaid={canIOUBePaidAndApproved || isPaidAnimationRunning} onAnimationFinish={stopAnimation} formattedAmount={getSettlementAmount() ?? ''} diff --git a/src/components/SettlementButton/AnimatedSettlementButton.tsx b/src/components/SettlementButton/AnimatedSettlementButton.tsx index 9a9e6f8de01c..028ba8a022f9 100644 --- a/src/components/SettlementButton/AnimatedSettlementButton.tsx +++ b/src/components/SettlementButton/AnimatedSettlementButton.tsx @@ -12,6 +12,7 @@ type AnimatedSettlementButtonProps = SettlementButtonProps & { isPaidAnimationRunning: boolean; onAnimationFinish: () => void; isApprovedAnimationRunning: boolean; + isSubmitAnimationRunning: boolean; canIOUBePaid: boolean; }; @@ -21,6 +22,7 @@ function AnimatedSettlementButton({ isApprovedAnimationRunning, isDisabled, canIOUBePaid, + isSubmitAnimationRunning, ...settlementButtonProps }: AnimatedSettlementButtonProps) { const styles = useThemeStyles(); @@ -48,7 +50,7 @@ function AnimatedSettlementButton({ marginTop: buttonMarginTop.get(), })); const buttonDisabledStyle = - isPaidAnimationRunning || isApprovedAnimationRunning + isPaidAnimationRunning || isApprovedAnimationRunning || isSubmitAnimationRunning ? { opacity: 1, ...styles.cursorDefault, @@ -65,7 +67,7 @@ function AnimatedSettlementButton({ }, [buttonScale, buttonOpacity, paymentCompleteTextScale, paymentCompleteTextOpacity, height, buttonMarginTop, styles.expenseAndReportPreviewTextButtonContainer.gap]); useEffect(() => { - if (!isApprovedAnimationRunning && !isPaidAnimationRunning) { + if (!isApprovedAnimationRunning && !isPaidAnimationRunning && !isSubmitAnimationRunning) { resetAnimation(); return; } @@ -88,6 +90,7 @@ function AnimatedSettlementButton({ }, [ isPaidAnimationRunning, isApprovedAnimationRunning, + isSubmitAnimationRunning, onAnimationFinish, buttonOpacity, buttonScale, From 7dc48fae60642270eafa896eb4d07d9f3710df2f Mon Sep 17 00:00:00 2001 From: allgandalf Date: Tue, 25 Feb 2025 17:04:40 +0530 Subject: [PATCH 2/5] animate the submit button --- src/CONST.ts | 3 + .../ReportActionItem/ReportPreview.tsx | 34 ++++---- src/components/SubmitButtonWithAnimation.tsx | 83 +++++++++++++++++++ src/languages/en.ts | 1 + src/languages/es.ts | 1 + 5 files changed, 106 insertions(+), 16 deletions(-) create mode 100644 src/components/SubmitButtonWithAnimation.tsx diff --git a/src/CONST.ts b/src/CONST.ts index 4cec868320a7..4c90e3e9de38 100755 --- a/src/CONST.ts +++ b/src/CONST.ts @@ -387,6 +387,9 @@ const CONST = { ANIMATION_THUMBSUP_DURATION: 250, ANIMATION_THUMBSUP_DELAY: 200, ANIMATION_PAID_BUTTON_HIDE_DELAY: 1000, + ANIMATION_SUBMITTED_TEXT_DELAY: 500, + ANIMATION_SUBMITTED_HEIGHT_DURATION: 1000, + ANIMATION_SUBMITTED_TEXT_DURATION: 2000, BACKGROUND_IMAGE_TRANSITION_DURATION: 1000, SCREEN_TRANSITION_END_TIMEOUT: 1000, ARROW_HIDE_DELAY: 3000, diff --git a/src/components/ReportActionItem/ReportPreview.tsx b/src/components/ReportActionItem/ReportPreview.tsx index 30790139b353..67e85bbf7ff1 100644 --- a/src/components/ReportActionItem/ReportPreview.tsx +++ b/src/components/ReportActionItem/ReportPreview.tsx @@ -84,6 +84,7 @@ import type {ContextMenuAnchor} from '@pages/home/report/ContextMenu/ReportActio import variables from '@styles/variables'; import {approveMoneyRequest, canApproveIOU, canIOUBePaid as canIOUBePaidIOUActions, canSubmitReport, payInvoice, payMoneyRequest, submitReport} from '@userActions/IOU'; import Timing from '@userActions/Timing'; +import SubmitButtonWithAnimation from '@src/components/SubmitButtonWithAnimation'; import CONST from '@src/CONST'; import type {TranslationPaths} from '@src/languages/types'; import ONYXKEYS from '@src/ONYXKEYS'; @@ -174,7 +175,6 @@ function ReportPreview({ const [isPaidAnimationRunning, setIsPaidAnimationRunning] = useState(false); const [isApprovedAnimationRunning, setIsApprovedAnimationRunning] = useState(false); - const [isSubmitAnimationRunning, setIsSubmitAnimationRunning] = useState(false); const [isHoldMenuVisible, setIsHoldMenuVisible] = useState(false); const [requestType, setRequestType] = useState(); const [paymentType, setPaymentType] = useState(); @@ -246,12 +246,17 @@ function ReportPreview({ formattedMerchant = null; } + const [isSubmitAnimationRunning, setIsSubmitAnimationRunning] = useState(false); + + const startSubmitAnimation = useCallback(() => { + setIsSubmitAnimationRunning(true); + HapticFeedback.longPress(); + }, []); + const isArchived = isArchivedReportWithID(iouReport?.reportID); const isAdmin = policy?.role === CONST.POLICY.ROLE.ADMIN; - - const shouldShowSubmitButton = canSubmitReport(iouReport, policy, transactionIDList, transactionViolations) || isSubmitAnimationRunning; const filteredTransactions = transactions?.filter((transaction) => transaction) ?? []; - const shouldShowSubmitButton = canSubmitReport(iouReport, policy, filteredTransactions, violations); + const shouldShowSubmitButton = canSubmitReport(iouReport, policy, filteredTransactions, violations) || isSubmitAnimationRunning; const shouldDisableSubmitButton = shouldShowSubmitButton && !isAllowedToSubmitDraftExpenseReport(iouReport); // The submit button should be success green colour only if the user is submitter and the policy does not have Scheduled Submit turned on @@ -276,11 +281,6 @@ function ReportPreview({ setIsApprovedAnimationRunning(true); HapticFeedback.longPress(); }, []); - const startSubmitAnimation = useCallback(() => { - setIsSubmitAnimationRunning(true); - HapticFeedback.longPress(); - }, []); - const confirmPayment = useCallback( (type: PaymentMethodType | undefined, payAsBusiness?: boolean) => { if (!type) { @@ -424,8 +424,8 @@ function ReportPreview({ const bankAccountRoute = getBankAccountRoute(chatReport); - const shouldShowSettlementButton = !shouldShowSubmitButton && (shouldShowPayButton || shouldShowApproveButton) && !showRTERViolationMessage && !shouldShowBrokenConnectionViolation && !isSubmitAnimationRunning; - + const shouldShowSettlementButton = + !shouldShowSubmitButton && (shouldShowPayButton || shouldShowApproveButton) && !showRTERViolationMessage && !shouldShowBrokenConnectionViolation && !isSubmitAnimationRunning; const shouldPromptUserToAddBankAccount = (hasMissingPaymentMethod(userWallet, iouReportID) || hasMissingInvoiceBankAccount(iouReportID)) && !isSettled(iouReportID); const shouldShowRBR = hasErrors && !iouSettled; @@ -674,11 +674,13 @@ function ReportPreview({ /> )} {shouldShowSubmitButton && ( -