diff --git a/android/app/build.gradle b/android/app/build.gradle
index 71a1d198f594..c4657fede5c0 100644
--- a/android/app/build.gradle
+++ b/android/app/build.gradle
@@ -96,8 +96,8 @@ android {
minSdkVersion rootProject.ext.minSdkVersion
targetSdkVersion rootProject.ext.targetSdkVersion
multiDexEnabled rootProject.ext.multiDexEnabled
- versionCode 1001041101
- versionName "1.4.11-1"
+ versionCode 1001041102
+ versionName "1.4.11-2"
}
flavorDimensions "default"
diff --git a/docs/articles/expensify-classic/account-settings/Profile-Settings.md b/docs/articles/expensify-classic/account-settings/Profile-Settings.md
deleted file mode 100644
index 3b2a0b830926..000000000000
--- a/docs/articles/expensify-classic/account-settings/Profile-Settings.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Profile Settings
-description: Profile Settings
----
-## Resource Coming Soon!
diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Cards.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Cards.md
deleted file mode 100644
index 71edcdeba00d..000000000000
--- a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Cards.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Personal Cards
-description: Connect your credit card directly to Expensify to easily track your personal finances.
----
-## Resource Coming Soon!
diff --git a/docs/articles/expensify-classic/getting-started/Mobile-App.md b/docs/articles/expensify-classic/getting-started/Mobile-App.md
deleted file mode 100644
index 7fa57abbdf61..000000000000
--- a/docs/articles/expensify-classic/getting-started/Mobile-App.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Using the App
-description: Using the App
----
-## Resource Coming Soon!
diff --git a/ios/NewExpensify/Info.plist b/ios/NewExpensify/Info.plist
index 38df19731ec6..6b56a92d222e 100644
--- a/ios/NewExpensify/Info.plist
+++ b/ios/NewExpensify/Info.plist
@@ -40,7 +40,7 @@
CFBundleVersion
- 1.4.11.1
+ 1.4.11.2
ITSAppUsesNonExemptEncryption
LSApplicationQueriesSchemes
diff --git a/ios/NewExpensifyTests/Info.plist b/ios/NewExpensifyTests/Info.plist
index e67615d9403a..16c652a16370 100644
--- a/ios/NewExpensifyTests/Info.plist
+++ b/ios/NewExpensifyTests/Info.plist
@@ -19,6 +19,6 @@
CFBundleSignature
????
CFBundleVersion
- 1.4.11.1
+ 1.4.11.2
diff --git a/package-lock.json b/package-lock.json
index 88909d7b9e97..79fa2269e1a5 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,12 +1,12 @@
{
"name": "new.expensify",
- "version": "1.4.11-1",
+ "version": "1.4.11-2",
"lockfileVersion": 2,
"requires": true,
"packages": {
"": {
"name": "new.expensify",
- "version": "1.4.11-1",
+ "version": "1.4.11-2",
"hasInstallScript": true,
"license": "MIT",
"dependencies": {
diff --git a/package.json b/package.json
index 8968ac4a520a..168e5ce04f36 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "new.expensify",
- "version": "1.4.11-1",
+ "version": "1.4.11-2",
"author": "Expensify, Inc.",
"homepage": "https://new.expensify.com",
"description": "New Expensify is the next generation of Expensify: a reimagination of payments based atop a foundation of chat.",
diff --git a/src/CONST.ts b/src/CONST.ts
index 6f1fe37f661d..4a2c21dfa1fe 100755
--- a/src/CONST.ts
+++ b/src/CONST.ts
@@ -55,6 +55,9 @@ const CONST = {
ALLOWED_RECEIPT_EXTENSIONS: ['jpg', 'jpeg', 'gif', 'png', 'pdf', 'htm', 'html', 'text', 'rtf', 'doc', 'tif', 'tiff', 'msword', 'zip', 'xml', 'message'],
},
+ // This is limit set on servers, do not update without wider internal discussion
+ API_TRANSACTION_CATEGORY_MAX_LENGTH: 255,
+
AUTO_AUTH_STATE: {
NOT_STARTED: 'not-started',
SIGNING_IN: 'signing-in',
@@ -508,6 +511,7 @@ const CONST = {
TASKREOPENED: 'TASKREOPENED',
POLICYCHANGELOG: {
ADD_APPROVER_RULE: 'POLICYCHANGELOG_ADD_APPROVER_RULE',
+ ADD_BUDGET: 'POLICYCHANGELOG_ADD_BUDGET',
ADD_CATEGORY: 'POLICYCHANGELOG_ADD_CATEGORY',
ADD_CUSTOM_UNIT: 'POLICYCHANGELOG_ADD_CUSTOM_UNIT',
ADD_CUSTOM_UNIT_RATE: 'POLICYCHANGELOG_ADD_CUSTOM_UNIT_RATE',
@@ -517,6 +521,7 @@ const CONST = {
ADD_TAG: 'POLICYCHANGELOG_ADD_TAG',
DELETE_ALL_TAGS: 'POLICYCHANGELOG_DELETE_ALL_TAGS',
DELETE_APPROVER_RULE: 'POLICYCHANGELOG_DELETE_APPROVER_RULE',
+ DELETE_BUDGET: 'POLICYCHANGELOG_DELETE_BUDGET',
DELETE_CATEGORY: 'POLICYCHANGELOG_DELETE_CATEGORY',
DELETE_CUSTOM_UNIT: 'POLICYCHANGELOG_DELETE_CUSTOM_UNIT',
DELETE_CUSTOM_UNIT_RATE: 'POLICYCHANGELOG_DELETE_CUSTOM_UNIT_RATE',
@@ -538,6 +543,7 @@ const CONST = {
UPDATE_AUTOHARVESTING: 'POLICYCHANGELOG_UPDATE_AUTOHARVESTING',
UPDATE_AUTOREIMBURSEMENT: 'POLICYCHANGELOG_UPDATE_AUTOREIMBURSEMENT',
UPDATE_AUTOREPORTING_FREQUENCY: 'POLICYCHANGELOG_UPDATE_AUTOREPORTING_FREQUENCY',
+ UPDATE_BUDGET: 'POLICYCHANGELOG_UPDATE_BUDGET',
UPDATE_CATEGORY: 'POLICYCHANGELOG_UPDATE_CATEGORY',
UPDATE_CURRENCY: 'POLICYCHANGELOG_UPDATE_CURRENCY',
UPDATE_CUSTOM_UNIT: 'POLICYCHANGELOG_UPDATE_CUSTOM_UNIT',
diff --git a/src/components/AttachmentModal.js b/src/components/AttachmentModal.js
index ef14d1bff665..68f35a828c88 100755
--- a/src/components/AttachmentModal.js
+++ b/src/components/AttachmentModal.js
@@ -2,7 +2,7 @@ import Str from 'expensify-common/lib/str';
import lodashExtend from 'lodash/extend';
import lodashGet from 'lodash/get';
import PropTypes from 'prop-types';
-import React, {useCallback, useEffect, useMemo, useRef, useState} from 'react';
+import React, {useCallback, useEffect, useMemo, useState} from 'react';
import {Animated, Keyboard, View} from 'react-native';
import {withOnyx} from 'react-native-onyx';
import _ from 'underscore';
@@ -91,6 +91,9 @@ const propTypes = {
/** Denotes whether it is a workspace avatar or not */
isWorkspaceAvatar: PropTypes.bool,
+
+ /** Whether it is a receipt attachment or not */
+ isReceiptAttachment: PropTypes.bool,
};
const defaultProps = {
@@ -108,19 +111,18 @@ const defaultProps = {
onModalHide: () => {},
onCarouselAttachmentChange: () => {},
isWorkspaceAvatar: false,
+ isReceiptAttachment: false,
};
function AttachmentModal(props) {
const theme = useTheme();
const styles = useThemeStyles();
const StyleUtils = useStyleUtils();
- const onModalHideCallbackRef = useRef(null);
const [isModalOpen, setIsModalOpen] = useState(props.defaultOpen);
const [shouldLoadAttachment, setShouldLoadAttachment] = useState(false);
const [isAttachmentInvalid, setIsAttachmentInvalid] = useState(false);
const [isDeleteReceiptConfirmModalVisible, setIsDeleteReceiptConfirmModalVisible] = useState(false);
const [isAuthTokenRequired, setIsAuthTokenRequired] = useState(props.isAuthTokenRequired);
- const [isAttachmentReceipt, setIsAttachmentReceipt] = useState(null);
const [attachmentInvalidReasonTitle, setAttachmentInvalidReasonTitle] = useState('');
const [attachmentInvalidReason, setAttachmentInvalidReason] = useState(null);
const [source, setSource] = useState(props.source);
@@ -156,7 +158,6 @@ function AttachmentModal(props) {
(attachment) => {
setSource(attachment.source);
setFile(attachment.file);
- setIsAttachmentReceipt(attachment.isReceipt);
setIsAuthTokenRequired(attachment.isAuthTokenRequired);
onCarouselAttachmentChange(attachment);
},
@@ -359,7 +360,7 @@ function AttachmentModal(props) {
const sourceForAttachmentView = props.source || source;
const threeDotsMenuItems = useMemo(() => {
- if (!isAttachmentReceipt || !props.parentReport || !props.parentReportActions) {
+ if (!props.isReceiptAttachment || !props.parentReport || !props.parentReportActions) {
return [];
}
const menuItems = [];
@@ -373,8 +374,8 @@ function AttachmentModal(props) {
icon: Expensicons.Camera,
text: props.translate('common.replace'),
onSelected: () => {
- onModalHideCallbackRef.current = () => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(props.report.reportID, CONST.EDIT_REQUEST_FIELD.RECEIPT));
closeModal();
+ Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(props.report.reportID, CONST.EDIT_REQUEST_FIELD.RECEIPT));
},
});
}
@@ -394,17 +395,17 @@ function AttachmentModal(props) {
}
return menuItems;
// eslint-disable-next-line react-hooks/exhaustive-deps
- }, [isAttachmentReceipt, props.parentReport, props.parentReportActions, props.policy, props.transaction, file]);
+ }, [props.isReceiptAttachment, props.parentReport, props.parentReportActions, props.policy, props.transaction, file]);
// There are a few things that shouldn't be set until we absolutely know if the file is a receipt or an attachment.
- // isAttachmentReceipt will be null until its certain what the file is, in which case it will then be true|false.
+ // props.isReceiptAttachment will be null until its certain what the file is, in which case it will then be true|false.
let headerTitle = props.headerTitle;
let shouldShowDownloadButton = false;
let shouldShowThreeDotsButton = false;
- if (!_.isNull(isAttachmentReceipt)) {
- headerTitle = translate(isAttachmentReceipt ? 'common.receipt' : 'common.attachment');
- shouldShowDownloadButton = props.allowDownload && isDownloadButtonReadyToBeShown && !isAttachmentReceipt && !isOffline;
- shouldShowThreeDotsButton = isAttachmentReceipt && isModalOpen;
+ if (!_.isEmpty(props.report)) {
+ headerTitle = translate(props.isReceiptAttachment ? 'common.receipt' : 'common.attachment');
+ shouldShowDownloadButton = props.allowDownload && isDownloadButtonReadyToBeShown && !props.isReceiptAttachment && !isOffline;
+ shouldShowThreeDotsButton = props.isReceiptAttachment && isModalOpen;
}
return (
@@ -421,10 +422,6 @@ function AttachmentModal(props) {
}}
onModalHide={(e) => {
props.onModalHide(e);
- if (onModalHideCallbackRef.current) {
- onModalHideCallbackRef.current();
- }
-
setShouldLoadAttachment(false);
}}
propagateSwipe
@@ -445,7 +442,7 @@ function AttachmentModal(props) {
shouldOverlay
/>
- {!_.isEmpty(props.report) ? (
+ {!_.isEmpty(props.report) && !props.isReceiptAttachment ? (
)
)}
@@ -488,7 +486,7 @@ function AttachmentModal(props) {
)}
)}
- {isAttachmentReceipt && (
+ {props.isReceiptAttachment && (
)}
- {!isAttachmentReceipt && (
+ {!props.isReceiptAttachment && (
{
- if (!ReportActionsUtils.shouldReportActionBeVisible(action, key)) {
+ if (!ReportActionsUtils.shouldReportActionBeVisible(action, key) || ReportActionsUtils.isMoneyRequestAction(action)) {
return;
}
- // We're handling receipts differently here because receipt images are not
- // part of the report action message, the images are constructed client-side
- if (ReportActionsUtils.isMoneyRequestAction(action)) {
- const transactionID = lodashGet(action, ['originalMessage', 'IOUTransactionID']);
- if (!transactionID) {
- return;
- }
-
- if (TransactionUtils.hasReceipt(transaction)) {
- const {image} = ReceiptUtils.getThumbnailAndImageURIs(transaction);
- const isLocalFile = typeof image === 'string' && _.some(CONST.ATTACHMENT_LOCAL_URL_PREFIX, (prefix) => image.startsWith(prefix));
- attachments.unshift({
- source: tryResolveUrlFromApiRoot(image),
- isAuthTokenRequired: !isLocalFile,
- file: {name: transaction.filename},
- isReceipt: true,
- transactionID,
- });
- return;
- }
- }
-
const decision = _.get(action, ['message', 0, 'moderationDecision', 'decision'], '');
const hasBeenFlagged = decision === CONST.MODERATION.MODERATOR_DECISION_PENDING_HIDE || decision === CONST.MODERATION.MODERATOR_DECISION_HIDDEN;
const html = _.get(action, ['message', 0, 'html'], '').replace('/>', `data-flagged="${hasBeenFlagged}" data-id="${action.reportActionID}"/>`);
diff --git a/src/components/Attachments/AttachmentCarousel/index.js b/src/components/Attachments/AttachmentCarousel/index.js
index 58a4b684815d..fd5879374ad4 100644
--- a/src/components/Attachments/AttachmentCarousel/index.js
+++ b/src/components/Attachments/AttachmentCarousel/index.js
@@ -1,4 +1,3 @@
-import lodashGet from 'lodash/get';
import React, {useCallback, useEffect, useRef, useState} from 'react';
import {FlatList, Keyboard, PixelRatio, View} from 'react-native';
import {withOnyx} from 'react-native-onyx';
@@ -29,7 +28,7 @@ const viewabilityConfig = {
itemVisiblePercentThreshold: 95,
};
-function AttachmentCarousel({report, reportActions, parentReportActions, source, onNavigate, setDownloadButtonVisibility, translate, transaction}) {
+function AttachmentCarousel({report, reportActions, parentReportActions, source, onNavigate, setDownloadButtonVisibility, translate}) {
const theme = useTheme();
const styles = useThemeStyles();
const scrollRef = useRef(null);
@@ -41,21 +40,12 @@ function AttachmentCarousel({report, reportActions, parentReportActions, source,
const [attachments, setAttachments] = useState([]);
const [activeSource, setActiveSource] = useState(source);
const [shouldShowArrows, setShouldShowArrows, autoHideArrows, cancelAutoHideArrows] = useCarouselArrows();
- const [isReceipt, setIsReceipt] = useState(false);
- const compareImage = useCallback(
- (attachment) => {
- if (attachment.isReceipt && isReceipt) {
- return attachment.transactionID === transaction.transactionID;
- }
- return attachment.source === source;
- },
- [source, isReceipt, transaction],
- );
+ const compareImage = useCallback((attachment) => attachment.source === source, [source]);
useEffect(() => {
const parentReportAction = parentReportActions[report.parentReportActionID];
- const attachmentsFromReport = extractAttachmentsFromReport(parentReportAction, reportActions, transaction);
+ const attachmentsFromReport = extractAttachmentsFromReport(parentReportAction, reportActions);
const initialPage = _.findIndex(attachmentsFromReport, compareImage);
@@ -90,12 +80,10 @@ function AttachmentCarousel({report, reportActions, parentReportActions, source,
// to get the index of the current page
const entry = _.first(viewableItems);
if (!entry) {
- setIsReceipt(false);
setActiveSource(null);
return;
}
- setIsReceipt(entry.item.isReceipt);
setPage(entry.index);
setActiveSource(entry.item.source);
@@ -230,7 +218,6 @@ AttachmentCarousel.defaultProps = defaultProps;
AttachmentCarousel.displayName = 'AttachmentCarousel';
export default compose(
- // eslint-disable-next-line rulesdir/no-multiple-onyx-in-file
withOnyx({
reportActions: {
key: ({report}) => `${ONYXKEYS.COLLECTION.REPORT_ACTIONS}${report.reportID}`,
@@ -244,15 +231,6 @@ export default compose(
canEvict: false,
},
}),
- // eslint-disable-next-line rulesdir/no-multiple-onyx-in-file
- withOnyx({
- transaction: {
- key: ({report, parentReportActions}) => {
- const parentReportAction = lodashGet(parentReportActions, [report.parentReportActionID]);
- return `${ONYXKEYS.COLLECTION.TRANSACTION}${lodashGet(parentReportAction, 'originalMessage.IOUTransactionID', 0)}`;
- },
- },
- }),
withLocalize,
withWindowDimensions,
)(AttachmentCarousel);
diff --git a/src/components/Attachments/AttachmentCarousel/index.native.js b/src/components/Attachments/AttachmentCarousel/index.native.js
index 6bf4e63c01e7..ea45509d6ce3 100644
--- a/src/components/Attachments/AttachmentCarousel/index.native.js
+++ b/src/components/Attachments/AttachmentCarousel/index.native.js
@@ -1,4 +1,3 @@
-import lodashGet from 'lodash/get';
import React, {useCallback, useEffect, useRef, useState} from 'react';
import {Keyboard, PixelRatio, View} from 'react-native';
import {withOnyx} from 'react-native-onyx';
@@ -18,7 +17,7 @@ import extractAttachmentsFromReport from './extractAttachmentsFromReport';
import AttachmentCarouselPager from './Pager';
import useCarouselArrows from './useCarouselArrows';
-function AttachmentCarousel({report, reportActions, parentReportActions, source, onNavigate, setDownloadButtonVisibility, translate, transaction, onClose}) {
+function AttachmentCarousel({report, reportActions, parentReportActions, source, onNavigate, setDownloadButtonVisibility, translate, onClose}) {
const styles = useThemeStyles();
const pagerRef = useRef(null);
@@ -28,21 +27,12 @@ function AttachmentCarousel({report, reportActions, parentReportActions, source,
const [activeSource, setActiveSource] = useState(source);
const [isPinchGestureRunning, setIsPinchGestureRunning] = useState(true);
const [shouldShowArrows, setShouldShowArrows, autoHideArrows, cancelAutoHideArrows] = useCarouselArrows();
- const [isReceipt, setIsReceipt] = useState(false);
- const compareImage = useCallback(
- (attachment) => {
- if (attachment.isReceipt && isReceipt) {
- return attachment.transactionID === transaction.transactionID;
- }
- return attachment.source === source;
- },
- [source, isReceipt, transaction],
- );
+ const compareImage = useCallback((attachment) => attachment.source === source, [source]);
useEffect(() => {
const parentReportAction = parentReportActions[report.parentReportActionID];
- const attachmentsFromReport = extractAttachmentsFromReport(parentReportAction, reportActions, transaction);
+ const attachmentsFromReport = extractAttachmentsFromReport(parentReportAction, reportActions);
const initialPage = _.findIndex(attachmentsFromReport, compareImage);
@@ -77,7 +67,6 @@ function AttachmentCarousel({report, reportActions, parentReportActions, source,
const item = attachments[newPageIndex];
setPage(newPageIndex);
- setIsReceipt(item.isReceipt);
setActiveSource(item.source);
onNavigate(item);
@@ -172,7 +161,6 @@ AttachmentCarousel.defaultProps = defaultProps;
AttachmentCarousel.displayName = 'AttachmentCarousel';
export default compose(
- // eslint-disable-next-line rulesdir/no-multiple-onyx-in-file
withOnyx({
reportActions: {
key: ({report}) => `${ONYXKEYS.COLLECTION.REPORT_ACTIONS}${report.reportID}`,
@@ -186,14 +174,5 @@ export default compose(
canEvict: false,
},
}),
- // eslint-disable-next-line rulesdir/no-multiple-onyx-in-file
- withOnyx({
- transaction: {
- key: ({report, parentReportActions}) => {
- const parentReportAction = lodashGet(parentReportActions, [report.parentReportActionID]);
- return `${ONYXKEYS.COLLECTION.TRANSACTION}${lodashGet(parentReportAction, 'originalMessage.IOUTransactionID', 0)}`;
- },
- },
- }),
withLocalize,
)(AttachmentCarousel);
diff --git a/src/components/CopyTextToClipboard.js b/src/components/CopyTextToClipboard.js
index acd3f08f2b22..678537c6a3d7 100644
--- a/src/components/CopyTextToClipboard.js
+++ b/src/components/CopyTextToClipboard.js
@@ -13,12 +13,14 @@ const propTypes = {
// eslint-disable-next-line react/forbid-prop-types
textStyles: PropTypes.arrayOf(PropTypes.object),
urlToCopy: PropTypes.string,
+ accessibilityRole: PropTypes.string,
...withLocalizePropTypes,
};
const defaultProps = {
textStyles: [],
urlToCopy: null,
+ accessibilityRole: undefined,
};
function CopyTextToClipboard(props) {
@@ -34,6 +36,7 @@ function CopyTextToClipboard(props) {
icon={Expensicons.Copy}
textStyles={props.textStyles}
onPress={copyToClipboard}
+ accessibilityRole={props.accessibilityRole}
/>
);
}
diff --git a/src/components/MapView/index.js b/src/components/MapView/index.js
deleted file mode 100644
index 551f57e34ed2..000000000000
--- a/src/components/MapView/index.js
+++ /dev/null
@@ -1,3 +0,0 @@
-import MapView from './MapView';
-
-export default MapView;
diff --git a/src/components/MapView/index.tsx b/src/components/MapView/index.tsx
new file mode 100644
index 000000000000..f273845fe4c0
--- /dev/null
+++ b/src/components/MapView/index.tsx
@@ -0,0 +1,10 @@
+import React from 'react';
+import MapView from './MapView';
+import {ComponentProps} from './types';
+
+function MapViewComponent(props: ComponentProps) {
+ // eslint-disable-next-line react/jsx-props-no-spreading
+ return ;
+}
+
+export default MapViewComponent;
diff --git a/src/components/MoneyRequestConfirmationList.js b/src/components/MoneyRequestConfirmationList.js
index 258a15c4c813..1bd7b71c5aa3 100755
--- a/src/components/MoneyRequestConfirmationList.js
+++ b/src/components/MoneyRequestConfirmationList.js
@@ -448,7 +448,10 @@ function MoneyRequestConfirmationList(props) {
if (_.isEmpty(selectedParticipants)) {
return;
}
-
+ if (props.iouCategory && props.iouCategory.length > CONST.API_TRANSACTION_CATEGORY_MAX_LENGTH) {
+ setFormError('iou.error.invalidCategoryLength');
+ return;
+ }
if (props.iouType === CONST.IOU.TYPE.SEND) {
if (!paymentMethod) {
return;
@@ -483,6 +486,7 @@ function MoneyRequestConfirmationList(props) {
props.isEditingSplitBill,
props.iouType,
props.isDistanceRequest,
+ props.iouCategory,
isDistanceRequestWithoutRoute,
props.iouCurrencyCode,
props.iouAmount,
diff --git a/src/components/Pressable/PressableWithDelayToggle.tsx b/src/components/Pressable/PressableWithDelayToggle.tsx
index 1601ec8d75d2..7d07831d6c3a 100644
--- a/src/components/Pressable/PressableWithDelayToggle.tsx
+++ b/src/components/Pressable/PressableWithDelayToggle.tsx
@@ -48,6 +48,7 @@ type PressableWithDelayToggleProps = PressableProps & {
* vertical text alignment of non-Text elements
*/
inline?: boolean;
+ accessibilityRole?: string;
};
function PressableWithDelayToggle(
@@ -63,6 +64,7 @@ function PressableWithDelayToggle(
textStyles,
iconStyles,
icon,
+ accessibilityRole,
}: PressableWithDelayToggleProps,
ref: PressableRef,
) {
@@ -101,6 +103,7 @@ function PressableWithDelayToggle(
onPress={updatePressState}
accessibilityLabel={tooltipTexts}
suppressHighlighting={inline ? true : undefined}
+ accessibilityRole={accessibilityRole}
>
<>
{inline && labelText}
diff --git a/src/components/ReportActionItem/ReportActionItemImage.js b/src/components/ReportActionItem/ReportActionItemImage.js
index f0eed3ac2f02..6fd322a24d3c 100644
--- a/src/components/ReportActionItem/ReportActionItemImage.js
+++ b/src/components/ReportActionItem/ReportActionItemImage.js
@@ -2,6 +2,7 @@ import PropTypes from 'prop-types';
import React from 'react';
import {View} from 'react-native';
import _ from 'underscore';
+import AttachmentModal from '@components/AttachmentModal';
import EReceiptThumbnail from '@components/EReceiptThumbnail';
import Image from '@components/Image';
import PressableWithoutFocus from '@components/Pressable/PressableWithoutFocus';
@@ -9,12 +10,10 @@ import {ShowContextMenuContext} from '@components/ShowContextMenuContext';
import ThumbnailImage from '@components/ThumbnailImage';
import transactionPropTypes from '@components/transactionPropTypes';
import useLocalize from '@hooks/useLocalize';
-import Navigation from '@libs/Navigation/Navigation';
import * as TransactionUtils from '@libs/TransactionUtils';
import tryResolveUrlFromApiRoot from '@libs/tryResolveUrlFromApiRoot';
import useThemeStyles from '@styles/useThemeStyles';
import CONST from '@src/CONST';
-import ROUTES from '@src/ROUTES';
const propTypes = {
/** thumbnail URI for the image */
@@ -83,17 +82,25 @@ function ReportActionItemImage({thumbnail, image, enablePreviewModal, transactio
return (
{({report}) => (
- {
- const route = ROUTES.REPORT_ATTACHMENTS.getRoute(report.reportID, imageSource);
- Navigation.navigate(route);
- }}
- role={CONST.ACCESSIBILITY_ROLE.IMAGEBUTTON}
- accessibilityLabel={translate('accessibilityHints.viewAttachment')}
+
- {receiptImageComponent}
-
+ {({show}) => (
+
+ {receiptImageComponent}
+
+ )}
+
)}
);
diff --git a/src/components/ReportHeaderSkeletonView.tsx b/src/components/ReportHeaderSkeletonView.tsx
index 9d8a3ee1bfd3..5ea83990431c 100644
--- a/src/components/ReportHeaderSkeletonView.tsx
+++ b/src/components/ReportHeaderSkeletonView.tsx
@@ -14,9 +14,10 @@ import SkeletonViewContentLoader from './SkeletonViewContentLoader';
type ReportHeaderSkeletonViewProps = {
shouldAnimate?: boolean;
+ onBackButtonPress?: () => void;
};
-function ReportHeaderSkeletonView({shouldAnimate = true}: ReportHeaderSkeletonViewProps) {
+function ReportHeaderSkeletonView({shouldAnimate = true, onBackButtonPress = () => {}}: ReportHeaderSkeletonViewProps) {
const theme = useTheme();
const styles = useThemeStyles();
const {translate} = useLocalize();
@@ -27,7 +28,7 @@ function ReportHeaderSkeletonView({shouldAnimate = true}: ReportHeaderSkeletonVi
{isSmallScreenWidth && (
{}}
+ onPress={onBackButtonPress}
style={[styles.LHNToggle]}
role={CONST.ACCESSIBILITY_ROLE.BUTTON}
accessibilityLabel={translate('common.back')}
diff --git a/src/languages/en.ts b/src/languages/en.ts
index c3f663eee4e0..bd2d941a7057 100755
--- a/src/languages/en.ts
+++ b/src/languages/en.ts
@@ -597,6 +597,7 @@ export default {
tagSelection: ({tagName}: TagSelectionParams) => `Select a ${tagName} to add additional organization to your money.`,
categorySelection: 'Select a category to add additional organization to your money.',
error: {
+ invalidCategoryLength: 'The length of the category chosen exceeds the maximum allowed (255). Please choose a different or shorten the category name first.',
invalidAmount: 'Please enter a valid amount before continuing.',
invalidSplit: 'Split amounts do not equal total amount',
other: 'Unexpected error, please try again later',
diff --git a/src/languages/es.ts b/src/languages/es.ts
index b4e0e37d0614..5c80ec93ac75 100644
--- a/src/languages/es.ts
+++ b/src/languages/es.ts
@@ -591,6 +591,7 @@ export default {
tagSelection: ({tagName}: TagSelectionParams) => `Seleccione una ${tagName} para organizar mejor tu dinero.`,
categorySelection: 'Seleccione una categoría para organizar mejor tu dinero.',
error: {
+ invalidCategoryLength: 'El largo de la categoría escogida excede el máximo permitido (255). Por favor escoge otra categoría o acorta la categoría primero.',
invalidAmount: 'Por favor ingresa un monto válido antes de continuar.',
invalidSplit: 'La suma de las partes no equivale al monto total',
other: 'Error inesperado, por favor inténtalo más tarde',
diff --git a/src/libs/Navigation/AppNavigator/getRootNavigatorScreenOptions.ts b/src/libs/Navigation/AppNavigator/getRootNavigatorScreenOptions.ts
index 9af92dd3e019..b294e6d7ab11 100644
--- a/src/libs/Navigation/AppNavigator/getRootNavigatorScreenOptions.ts
+++ b/src/libs/Navigation/AppNavigator/getRootNavigatorScreenOptions.ts
@@ -42,8 +42,8 @@ export default (isSmallScreenWidth: boolean, themeStyles: ThemeStyles): ScreenOp
...getNavigationModalCardStyle(),
width: isSmallScreenWidth ? '100%' : variables.sideBarWidth,
- // We need to translate the sidebar to not be covered by the StackNavigator so it can be clickable.
- transform: [{translateX: isSmallScreenWidth ? 0 : -variables.sideBarWidth}],
+ // We need to shift the sidebar to not be covered by the StackNavigator so it can be clickable.
+ marginLeft: isSmallScreenWidth ? 0 : -variables.sideBarWidth,
...(isSmallScreenWidth ? {} : themeStyles.borderRight),
},
},
diff --git a/src/pages/ReferralDetailsPage.js b/src/pages/ReferralDetailsPage.js
index 60b5d23b39da..b4d2b5e3bb9c 100644
--- a/src/pages/ReferralDetailsPage.js
+++ b/src/pages/ReferralDetailsPage.js
@@ -90,6 +90,7 @@ function ReferralDetailsPage({route, account}) {
{shouldShowClipboard && (
{isLoading ? (
-
+
) : (
<>
{isSmallScreenWidth && (
diff --git a/src/pages/iou/SplitBillDetailsPage.js b/src/pages/iou/SplitBillDetailsPage.js
index 65bf43500f88..dd9e7ce93cc6 100644
--- a/src/pages/iou/SplitBillDetailsPage.js
+++ b/src/pages/iou/SplitBillDetailsPage.js
@@ -143,7 +143,7 @@ function SplitBillDetailsPage(props) {
hasSmartScanFailed={hasSmartScanFailed}
reportID={reportID}
reportActionID={reportAction.reportActionID}
- transaction={isEditingSplitBill ? props.draftTransaction : props.transaction}
+ transaction={isEditingSplitBill ? props.draftTransaction || props.transaction : props.transaction}
onConfirm={onConfirm}
isPolicyExpenseChat={ReportUtils.isPolicyExpenseChat(props.report)}
policyID={ReportUtils.isPolicyExpenseChat(props.report) && props.report.policyID}
diff --git a/src/pages/iou/request/MoneyTemporaryForRefactorRequestParticipantsSelector.js b/src/pages/iou/request/MoneyTemporaryForRefactorRequestParticipantsSelector.js
index 165852062c54..95fa64723737 100644
--- a/src/pages/iou/request/MoneyTemporaryForRefactorRequestParticipantsSelector.js
+++ b/src/pages/iou/request/MoneyTemporaryForRefactorRequestParticipantsSelector.js
@@ -209,30 +209,8 @@ function MoneyTemporaryForRefactorRequestParticipantsSelector({
}
onParticipantsAdded(newSelectedOptions);
-
- const chatOptions = OptionsListUtils.getFilteredOptions(
- reports,
- personalDetails,
- betas,
- isOptionInList ? searchTerm : '',
- newSelectedOptions,
- CONST.EXPENSIFY_EMAILS,
-
- // If we are using this component in the "Request money" flow then we pass the includeOwnedWorkspaceChats argument so that the current user
- // sees the option to request money from their admin on their own Workspace Chat.
- iouType === CONST.IOU.TYPE.REQUEST,
-
- // We don't want to include any P2P options like personal details or reports that are not workspace chats for certain features.
- iouType !== CONST.IOU.REQUEST_TYPE.DISTANCE,
- );
-
- setNewChatOptions({
- recentReports: chatOptions.recentReports,
- personalDetails: chatOptions.personalDetails,
- userToInvite: chatOptions.userToInvite,
- });
},
- [participants, onParticipantsAdded, reports, personalDetails, betas, searchTerm, iouType],
+ [participants, onParticipantsAdded],
);
const headerMessage = OptionsListUtils.getHeaderMessage(
@@ -265,7 +243,10 @@ function MoneyTemporaryForRefactorRequestParticipantsSelector({
false,
{},
[],
- true,
+
+ // We don't want the user to be able to invite individuals when they are in the "Distance request" flow for now.
+ // This functionality is being built here: https://github.com/Expensify/App/issues/23291
+ iouRequestType !== CONST.IOU.REQUEST_TYPE.DISTANCE,
true,
);
setNewChatOptions({