1
+ import type { ReactNode } from 'react' ;
1
2
import React , { useCallback , useEffect , useState } from 'react' ;
2
3
import { View } from 'react-native' ;
3
4
import { withOnyx } from 'react-native-onyx' ;
4
- import type { OnyxEntry } from 'react-native-onyx' ;
5
+ import type { OnyxCollection , OnyxEntry } from 'react-native-onyx' ;
5
6
import useLocalize from '@hooks/useLocalize' ;
6
7
import useTheme from '@hooks/useTheme' ;
7
8
import useThemeStyles from '@hooks/useThemeStyles' ;
@@ -16,12 +17,14 @@ import * as IOU from '@userActions/IOU';
16
17
import CONST from '@src/CONST' ;
17
18
import ONYXKEYS from '@src/ONYXKEYS' ;
18
19
import ROUTES from '@src/ROUTES' ;
19
- import type { Policy , Report , ReportAction , ReportActions , Session , Transaction } from '@src/types/onyx' ;
20
+ import type { Policy , Report , ReportAction , ReportActions , Session , Transaction , TransactionViolations } from '@src/types/onyx' ;
20
21
import type { OriginalMessageIOU } from '@src/types/onyx/OriginalMessage' ;
22
+ import type IconAsset from '@src/types/utils/IconAsset' ;
21
23
import ConfirmModal from './ConfirmModal' ;
22
24
import HeaderWithBackButton from './HeaderWithBackButton' ;
23
25
import Icon from './Icon' ;
24
26
import * as Expensicons from './Icon/Expensicons' ;
27
+ import type { MoneyRequestHeaderStatusBarProps } from './MoneyRequestHeaderStatusBar' ;
25
28
import MoneyRequestHeaderStatusBar from './MoneyRequestHeaderStatusBar' ;
26
29
import ProcessMoneyRequestHoldMenu from './ProcessMoneyRequestHoldMenu' ;
27
30
@@ -35,6 +38,9 @@ type MoneyRequestHeaderOnyxProps = {
35
38
/** All the data for the transaction */
36
39
transaction : OnyxEntry < Transaction > ;
37
40
41
+ /** The violations of the transaction */
42
+ transactionViolations : OnyxCollection < TransactionViolations > ;
43
+
38
44
/** All report actions */
39
45
// eslint-disable-next-line react/no-unused-prop-types
40
46
parentReportActions : OnyxEntry < ReportActions > ;
@@ -65,6 +71,7 @@ function MoneyRequestHeader({
65
71
parentReport,
66
72
report,
67
73
parentReportAction,
74
+ transactionViolations,
68
75
transaction,
69
76
shownHoldUseExplanation = false ,
70
77
policy,
@@ -101,7 +108,6 @@ function MoneyRequestHeader({
101
108
} , [ parentReport ?. reportID , parentReportAction , setIsDeleteModalVisible ] ) ;
102
109
103
110
const isScanning = TransactionUtils . hasReceipt ( transaction ) && TransactionUtils . isReceiptBeingScanned ( transaction ) ;
104
- const isPending = TransactionUtils . isExpensifyCardTransaction ( transaction ) && TransactionUtils . isPending ( transaction ) ;
105
111
106
112
const isDeletedParentAction = ReportActionsUtils . isDeletedAction ( parentReportAction ) ;
107
113
const canHoldOrUnholdRequest = ! isSettled && ! isApproved && ! isDeletedParentAction ;
@@ -120,6 +126,33 @@ function MoneyRequestHeader({
120
126
}
121
127
} ;
122
128
129
+ const getStatusIcon : ( src : IconAsset ) => ReactNode = ( src ) => (
130
+ < Icon
131
+ src = { src }
132
+ height = { variables . iconSizeSmall }
133
+ width = { variables . iconSizeSmall }
134
+ fill = { theme . icon }
135
+ />
136
+ ) ;
137
+
138
+ const getStatusBarProps : ( ) => MoneyRequestHeaderStatusBarProps | undefined = ( ) => {
139
+ if ( isOnHold ) {
140
+ return { title : translate ( 'iou.hold' ) , description : translate ( 'iou.expenseOnHold' ) , danger : true , shouldShowBorderBottom : true } ;
141
+ }
142
+
143
+ if ( TransactionUtils . isExpensifyCardTransaction ( transaction ) && TransactionUtils . isPending ( transaction ) ) {
144
+ return { title : getStatusIcon ( Expensicons . CreditCardHourglass ) , description : translate ( 'iou.transactionPendingDescription' ) , shouldShowBorderBottom : true } ;
145
+ }
146
+ if ( isScanning ) {
147
+ return { title : getStatusIcon ( Expensicons . ReceiptScan ) , description : translate ( 'iou.receiptScanInProgressDescription' ) , shouldShowBorderBottom : true } ;
148
+ }
149
+ if ( TransactionUtils . hasPendingRTERViolation ( TransactionUtils . getTransactionViolations ( transaction ?. transactionID ?? '' , transactionViolations ) ) ) {
150
+ return { title : getStatusIcon ( Expensicons . Hourglass ) , description : translate ( 'iou.pendingMatchWithCreditCardDescription' ) , shouldShowBorderBottom : true } ;
151
+ }
152
+ } ;
153
+
154
+ const statusBarProps = getStatusBarProps ( ) ;
155
+
123
156
useEffect ( ( ) => {
124
157
if ( canDeleteRequest ) {
125
158
return ;
@@ -184,7 +217,7 @@ function MoneyRequestHeader({
184
217
< >
185
218
< View style = { [ styles . pl0 ] } >
186
219
< HeaderWithBackButton
187
- shouldShowBorderBottom = { ! isScanning && ! isPending && ! isOnHold }
220
+ shouldShowBorderBottom = { ! statusBarProps && ! isOnHold }
188
221
shouldShowReportAvatarWithDisplay
189
222
shouldEnableDetailPageNavigation
190
223
shouldShowPinButton = { false }
@@ -199,40 +232,12 @@ function MoneyRequestHeader({
199
232
shouldShowBackButton = { shouldUseNarrowLayout }
200
233
onBackButtonPress = { onBackButtonPress }
201
234
/>
202
- { isPending && (
203
- < MoneyRequestHeaderStatusBar
204
- title = {
205
- < Icon
206
- src = { Expensicons . CreditCardHourglass }
207
- height = { variables . iconSizeSmall }
208
- width = { variables . iconSizeSmall }
209
- fill = { theme . icon }
210
- />
211
- }
212
- description = { translate ( 'iou.transactionPendingDescription' ) }
213
- shouldShowBorderBottom = { ! isScanning }
214
- />
215
- ) }
216
- { isScanning && (
235
+ { statusBarProps && (
217
236
< MoneyRequestHeaderStatusBar
218
- title = {
219
- < Icon
220
- src = { Expensicons . ReceiptScan }
221
- height = { variables . iconSizeSmall }
222
- width = { variables . iconSizeSmall }
223
- fill = { theme . icon }
224
- />
225
- }
226
- description = { translate ( 'iou.receiptScanInProgressDescription' ) }
227
- shouldShowBorderBottom
228
- />
229
- ) }
230
- { isOnHold && (
231
- < MoneyRequestHeaderStatusBar
232
- title = { translate ( 'iou.hold' ) }
233
- description = { translate ( 'iou.expenseOnHold' ) }
234
- shouldShowBorderBottom
235
- danger
237
+ title = { statusBarProps . title }
238
+ description = { statusBarProps . description }
239
+ danger = { statusBarProps . danger }
240
+ shouldShowBorderBottom = { statusBarProps . shouldShowBorderBottom }
236
241
/>
237
242
) }
238
243
</ View >
@@ -259,7 +264,7 @@ function MoneyRequestHeader({
259
264
260
265
MoneyRequestHeader . displayName = 'MoneyRequestHeader' ;
261
266
262
- const MoneyRequestHeaderWithTransaction = withOnyx < MoneyRequestHeaderProps , Pick < MoneyRequestHeaderOnyxProps , 'transaction' | 'shownHoldUseExplanation' > > ( {
267
+ const MoneyRequestHeaderWithTransaction = withOnyx < MoneyRequestHeaderProps , Pick < MoneyRequestHeaderOnyxProps , 'transactionViolations' | ' transaction' | 'shownHoldUseExplanation' > > ( {
263
268
transaction : {
264
269
key : ( { report, parentReportActions} ) => {
265
270
const parentReportAction = ( report . parentReportActionID && parentReportActions ? parentReportActions [ report . parentReportActionID ] : { } ) as ReportAction & OriginalMessageIOU ;
@@ -270,9 +275,15 @@ const MoneyRequestHeaderWithTransaction = withOnyx<MoneyRequestHeaderProps, Pick
270
275
key : ONYXKEYS . NVP_HOLD_USE_EXPLAINED ,
271
276
initWithStoredValues : true ,
272
277
} ,
278
+ transactionViolations : {
279
+ key : ONYXKEYS . COLLECTION . TRANSACTION_VIOLATIONS ,
280
+ } ,
273
281
} ) ( MoneyRequestHeader ) ;
274
282
275
- export default withOnyx < Omit < MoneyRequestHeaderProps , 'transaction' | 'shownHoldUseExplanation' > , Omit < MoneyRequestHeaderOnyxProps , 'transaction' | 'shownHoldUseExplanation' > > ( {
283
+ export default withOnyx <
284
+ Omit < MoneyRequestHeaderProps , 'transactionViolations' | 'transaction' | 'shownHoldUseExplanation' > ,
285
+ Omit < MoneyRequestHeaderOnyxProps , 'transactionViolations' | 'transaction' | 'shownHoldUseExplanation' >
286
+ > ( {
276
287
session : {
277
288
key : ONYXKEYS . SESSION ,
278
289
} ,
0 commit comments