@oneblink/apps-react 13.0.0-beta.2 → 13.0.0-beta.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/OneBlinkFormBase.d.ts +23 -3
- package/dist/OneBlinkFormBase.js +38 -7
- package/dist/OneBlinkFormBase.js.map +1 -1
- package/dist/OneBlinkReadOnlyForm.d.ts +17 -7
- package/dist/OneBlinkReadOnlyForm.js +24 -8
- package/dist/OneBlinkReadOnlyForm.js.map +1 -1
- package/dist/apps/services/api/submissions.d.ts +1 -1
- package/dist/apps/services/api/submissions.js +0 -5
- package/dist/apps/services/api/submissions.js.map +1 -1
- package/dist/apps/submission-service.d.ts +1 -1
- package/dist/apps/submission-service.js.map +1 -1
- package/dist/components/renderer/LookupNotification.js +8 -12
- package/dist/components/renderer/LookupNotification.js.map +1 -1
- package/dist/components/renderer/OneBlinkFormElements.d.ts +5 -7
- package/dist/components/renderer/OneBlinkFormElements.js +10 -35
- package/dist/components/renderer/OneBlinkFormElements.js.map +1 -1
- package/dist/components/renderer/ReverseGeocode.js +4 -11
- package/dist/components/renderer/ReverseGeocode.js.map +1 -1
- package/dist/form-elements/FormElementForm.d.ts +8 -9
- package/dist/form-elements/FormElementForm.js.map +1 -1
- package/dist/form-elements/FormElementRepeatableSet.d.ts +4 -4
- package/dist/form-elements/FormElementRepeatableSet.js.map +1 -1
- package/dist/form-elements/FormElementSection.d.ts +3 -3
- package/dist/form-elements/FormElementSection.js.map +1 -1
- package/dist/hooks/useAreLookupsDisallowed.d.ts +2 -0
- package/dist/hooks/useAreLookupsDisallowed.js +12 -0
- package/dist/hooks/useAreLookupsDisallowed.js.map +1 -0
- package/dist/hooks/useEditableFormElementIds.d.ts +3 -0
- package/dist/hooks/useEditableFormElementIds.js +6 -0
- package/dist/hooks/useEditableFormElementIds.js.map +1 -0
- package/dist/hooks/useFormSubmissionAttempt.d.ts +88 -0
- package/dist/hooks/useFormSubmissionAttempt.js +103 -0
- package/dist/hooks/useFormSubmissionAttempt.js.map +1 -0
- package/dist/hooks/useFormValidation.d.ts +1 -1
- package/dist/hooks/useFormValidation.js +2 -1
- package/dist/hooks/useFormValidation.js.map +1 -1
- package/dist/hooks/useIsFormElementReadOnly.d.ts +2 -0
- package/dist/hooks/useIsFormElementReadOnly.js +13 -0
- package/dist/hooks/useIsFormElementReadOnly.js.map +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/services/form-validation/extensions.d.ts +2 -1
- package/dist/services/form-validation/extensions.js +2 -1
- package/dist/services/form-validation/extensions.js.map +1 -1
- package/dist/services/form-validation/validateSubmission.d.ts +2 -1
- package/dist/services/form-validation/validateSubmission.js +14 -9
- package/dist/services/form-validation/validateSubmission.js.map +1 -1
- package/dist/utils/read-only-form-elements.d.ts +37 -0
- package/dist/utils/read-only-form-elements.js +63 -0
- package/dist/utils/read-only-form-elements.js.map +1 -0
- package/package.json +2 -1
- package/dist/services/isElementReadOnlyForAudience.d.ts +0 -20
- package/dist/services/isElementReadOnlyForAudience.js +0 -46
- package/dist/services/isElementReadOnlyForAudience.js.map +0 -1
- package/dist/services/resolveFormElementReadOnly.d.ts +0 -10
- package/dist/services/resolveFormElementReadOnly.js +0 -17
- package/dist/services/resolveFormElementReadOnly.js.map +0 -1
|
@@ -3,7 +3,7 @@ import { submissionService, attachmentsService } from './apps';
|
|
|
3
3
|
import { EnvironmentTypes, FormTypes, FormsAppsTypes, ScheduledTasksTypes, SubmissionTypes } from '@oneblink/types';
|
|
4
4
|
import { ReplaceInjectablesOverrides } from './hooks/useReplaceInjectablesOverrides';
|
|
5
5
|
import { CaptchaType, ExecutedLookups, SetFormSubmission, SectionState } from './types/form';
|
|
6
|
-
|
|
6
|
+
type OneBlinkFormDisplayProps = {
|
|
7
7
|
/**
|
|
8
8
|
* A [Google Maps API
|
|
9
9
|
* Key](https://developers.google.com/maps/documentation/javascript/get-api-key).
|
|
@@ -40,7 +40,27 @@ export type OneBlinkReadOnlyFormProps = {
|
|
|
40
40
|
*/
|
|
41
41
|
audience: FormTypes.FormElementHiddenFromAudience;
|
|
42
42
|
};
|
|
43
|
-
export type
|
|
43
|
+
export type OneBlinkReadOnlyFormProps = OneBlinkFormDisplayProps & ((OneBlinkFormControlledProps & {
|
|
44
|
+
/**
|
|
45
|
+
* Element ids that remain editable. All other elements are read-only.
|
|
46
|
+
* Requires the same controlled submission props as
|
|
47
|
+
* `OneBlinkFormControlled`.
|
|
48
|
+
*/
|
|
49
|
+
editableFormElementIds: string[];
|
|
50
|
+
form?: never;
|
|
51
|
+
initialSubmission?: never;
|
|
52
|
+
}) | (OneBlinkFormUncontrolledProps & {
|
|
53
|
+
/** Omit to render every form element as read-only. */
|
|
54
|
+
editableFormElementIds?: never;
|
|
55
|
+
definition?: never;
|
|
56
|
+
submission?: never;
|
|
57
|
+
setFormSubmission?: never;
|
|
58
|
+
lastElementUpdated?: never;
|
|
59
|
+
executedLookups?: never;
|
|
60
|
+
sectionState?: never;
|
|
61
|
+
}));
|
|
62
|
+
export type OneBlinkFormBaseProps = OneBlinkFormDisplayProps & {
|
|
63
|
+
editableFormElementIds?: string[];
|
|
44
64
|
/** The function to call when the user cancels the form */
|
|
45
65
|
onCancel: () => unknown;
|
|
46
66
|
/**
|
|
@@ -162,6 +182,6 @@ export type OneBlinkFormControlledProps = {
|
|
|
162
182
|
type Props = OneBlinkFormBaseProps & OneBlinkFormControlledProps & {
|
|
163
183
|
isReadOnly: boolean;
|
|
164
184
|
};
|
|
165
|
-
declare function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captchaSiteKey, definition, disabled, isPreview, submission, isReadOnly, onCancel, onSubmit, onSaveDraft, setFormSubmission, buttons, validationIcon, primaryColour, attachmentRetentionInDays, isPendingQueueEnabled, handleNavigateAway, isInfoPage: isInfoPageProp, lastElementUpdated, executedLookups, task, taskGroup, taskGroupInstance, onUploadAttachment, captchaType, shouldUseNavigableValidationErrorsNotification, navigableValidationErrorsNotificationSettings, replaceInjectablesOverrides, sectionState, scrollToTopOfPage, getCurrentSubmissionDuration, onBeforeUnload, audience, }: Props): import("react/jsx-runtime").JSX.Element;
|
|
185
|
+
declare function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captchaSiteKey, definition, disabled, isPreview, submission, isReadOnly, onCancel, onSubmit, onSaveDraft, setFormSubmission, buttons, validationIcon, primaryColour, attachmentRetentionInDays, isPendingQueueEnabled, handleNavigateAway, isInfoPage: isInfoPageProp, lastElementUpdated, executedLookups, task, taskGroup, taskGroupInstance, onUploadAttachment, captchaType, shouldUseNavigableValidationErrorsNotification, navigableValidationErrorsNotificationSettings, replaceInjectablesOverrides, sectionState, scrollToTopOfPage, getCurrentSubmissionDuration, onBeforeUnload, audience, editableFormElementIds, }: Props): import("react/jsx-runtime").JSX.Element;
|
|
166
186
|
declare const _default: React.MemoExoticComponent<typeof OneBlinkFormBase>;
|
|
167
187
|
export default _default;
|
package/dist/OneBlinkFormBase.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
2
|
import * as React from 'react';
|
|
3
|
+
import { flushSync } from 'react-dom';
|
|
3
4
|
import { createTheme as createMuiTheme, ThemeProvider } from '@mui/material';
|
|
4
5
|
import Tooltip from './components/renderer/Tooltip';
|
|
5
6
|
import { Prompt, useHistory } from 'react-router-dom';
|
|
@@ -44,7 +45,9 @@ import { getElementDisplayNameForAnalyticsEvent, sendGoogleAnalyticsEvent, } fro
|
|
|
44
45
|
import { useUserProfileForInjectablesOutsideContext } from './hooks/useUserProfileForInjectables';
|
|
45
46
|
import { ValidationIconConfigurationContext } from './hooks/useValidationIconConfiguration';
|
|
46
47
|
import { Clickable } from './components/Clickable';
|
|
47
|
-
|
|
48
|
+
import { EditableFormElementIdsContext } from './hooks/useEditableFormElementIds';
|
|
49
|
+
import { useRegisterFormSubmissionAttempt } from './hooks/useFormSubmissionAttempt';
|
|
50
|
+
function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captchaSiteKey, definition, disabled, isPreview, submission, isReadOnly, onCancel, onSubmit, onSaveDraft, setFormSubmission, buttons, validationIcon, primaryColour, attachmentRetentionInDays, isPendingQueueEnabled, handleNavigateAway, isInfoPage: isInfoPageProp, lastElementUpdated, executedLookups, task, taskGroup, taskGroupInstance, onUploadAttachment, captchaType, shouldUseNavigableValidationErrorsNotification = true, navigableValidationErrorsNotificationSettings, replaceInjectablesOverrides, sectionState, scrollToTopOfPage, getCurrentSubmissionDuration, onBeforeUnload, audience, editableFormElementIds, }) {
|
|
48
51
|
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r;
|
|
49
52
|
const isOffline = useIsOffline();
|
|
50
53
|
const { isUsingFormsKey } = useAuth();
|
|
@@ -225,6 +228,13 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
225
228
|
isNavigationAllowed: true,
|
|
226
229
|
}));
|
|
227
230
|
}, []);
|
|
231
|
+
const allowNavigationAfterHostAction = React.useCallback(() => {
|
|
232
|
+
// React Router DOM v5's <Prompt> has no imperative "proceed" API, so the
|
|
233
|
+
// guard must rerender as disabled before the host navigates in the same
|
|
234
|
+
// tick. Migrating to the React Router DOM v6 blocker APIs would allow the
|
|
235
|
+
// blocked transition to proceed directly without flushSync().
|
|
236
|
+
flushSync(allowNavigation);
|
|
237
|
+
}, [allowNavigation]);
|
|
228
238
|
// #endregion Unsaved Changed
|
|
229
239
|
//
|
|
230
240
|
//
|
|
@@ -246,8 +256,8 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
246
256
|
const [isShowingValidationErrorsCard, setIsShowingValidationErrorsCard] = React.useState(false);
|
|
247
257
|
const { validate } = useFormValidation(pages);
|
|
248
258
|
const recaptchaType = React.useMemo(() => captchaType !== null && captchaType !== void 0 ? captchaType : 'CHECKBOX', [captchaType]);
|
|
249
|
-
const formElementsValidation = React.useMemo(() => !isReadOnly
|
|
250
|
-
? validate(submission, formElementsConditionallyShown, executedLookups !== null && executedLookups !== void 0 ? executedLookups : {}, recaptchaType, isOffline, audience)
|
|
259
|
+
const formElementsValidation = React.useMemo(() => !isReadOnly || editableFormElementIds !== undefined
|
|
260
|
+
? validate(submission, formElementsConditionallyShown, executedLookups !== null && executedLookups !== void 0 ? executedLookups : {}, recaptchaType, isOffline, audience, editableFormElementIds)
|
|
251
261
|
: undefined, [
|
|
252
262
|
isReadOnly,
|
|
253
263
|
validate,
|
|
@@ -257,6 +267,7 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
257
267
|
recaptchaType,
|
|
258
268
|
isOffline,
|
|
259
269
|
audience,
|
|
270
|
+
editableFormElementIds,
|
|
260
271
|
]);
|
|
261
272
|
React.useEffect(() => {
|
|
262
273
|
if (!formElementsValidation) {
|
|
@@ -472,6 +483,23 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
472
483
|
setFormSubmission,
|
|
473
484
|
shouldUseNavigableValidationErrorsNotification,
|
|
474
485
|
]);
|
|
486
|
+
const attemptFormSubmission = React.useCallback(async () => {
|
|
487
|
+
setHasAttemptedSubmit(true);
|
|
488
|
+
setIsPreparingToSubmit(true);
|
|
489
|
+
try {
|
|
490
|
+
if (!(await prepareSubmission(false))) {
|
|
491
|
+
return false;
|
|
492
|
+
}
|
|
493
|
+
// The host must call this after it has persisted the edits. Calling it
|
|
494
|
+
// here would let the user cancel a later confirmation dialog and leave
|
|
495
|
+
// without being prompted.
|
|
496
|
+
return allowNavigationAfterHostAction;
|
|
497
|
+
}
|
|
498
|
+
finally {
|
|
499
|
+
setIsPreparingToSubmit(false);
|
|
500
|
+
}
|
|
501
|
+
}, [allowNavigationAfterHostAction, prepareSubmission]);
|
|
502
|
+
useRegisterFormSubmissionAttempt(editableFormElementIds === undefined ? undefined : attemptFormSubmission);
|
|
475
503
|
const handleSubmit = React.useCallback(async (event, continueWhilstAttachmentsAreUploading) => {
|
|
476
504
|
event.preventDefault();
|
|
477
505
|
// Approvers are not shown a submit button, so reaching here means the
|
|
@@ -768,9 +796,9 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
768
796
|
'is-active': isStepsHeaderActive,
|
|
769
797
|
}), onClick: toggleStepsNavigation }), _jsxs("div", { className: "steps", children: [_jsx("div", { className: clsx('steps-content', {
|
|
770
798
|
'is-single-step': !isShowingMultiplePages,
|
|
771
|
-
}), children: _jsx(InjectPagesContext.Provider, { value: handlePagesLookupResult, children: _jsx(GoogleMapsApiKeyContext.Provider, { value: googleMapsApiKey, children: _jsx(AbnLookupAuthenticationGuidContext.Provider, { value: abnLookupAuthenticationGuid, children: _jsx(ValidationIconConfigurationContext.Provider, { value: validationIcon, children: _jsx(CaptchaContext.Provider, { value: captchaContextValue, children: _jsx(AttachmentBlobsProvider, { children: _jsx(FormIsReadOnlyContext.Provider, { value: isReadOnly, children: _jsx(FormAudienceContext.Provider, { value: audience, children: _jsx(TaskContext.Provider, { value: taskContextValue, children: _jsx(OnUploadAttachmentContext.Provider, { value: onUploadAttachment, children: visiblePages.map((pageElement) => (_jsx(PageFormElements, { isActive: pageElement.id ===
|
|
772
|
-
|
|
773
|
-
|
|
799
|
+
}), children: _jsx(InjectPagesContext.Provider, { value: handlePagesLookupResult, children: _jsx(GoogleMapsApiKeyContext.Provider, { value: googleMapsApiKey, children: _jsx(AbnLookupAuthenticationGuidContext.Provider, { value: abnLookupAuthenticationGuid, children: _jsx(ValidationIconConfigurationContext.Provider, { value: validationIcon, children: _jsx(CaptchaContext.Provider, { value: captchaContextValue, children: _jsx(AttachmentBlobsProvider, { children: _jsx(FormIsReadOnlyContext.Provider, { value: isReadOnly, children: _jsx(EditableFormElementIdsContext.Provider, { value: editableFormElementIds, children: _jsx(FormAudienceContext.Provider, { value: audience, children: _jsx(TaskContext.Provider, { value: taskContextValue, children: _jsx(OnUploadAttachmentContext.Provider, { value: onUploadAttachment, children: visiblePages.map((pageElement) => (_jsx(PageFormElements, { isActive: pageElement.id ===
|
|
800
|
+
currentPage.id, formId: definition.id, formElementsConditionallyShown: formElementsConditionallyShown, formElementsValidation: formElementsValidation, displayValidationMessages: hasAttemptedSubmit ||
|
|
801
|
+
isDisplayingCurrentPageError, pageElement: pageElement, onChange: handleChange, model: submission, setFormSubmission: setFormSubmission, sectionState: sectionState }, pageElement.id))) }) }) }) }) }) }) }) }) }) }) }) }), isShowingMultiplePages && (_jsxs("div", { className: "steps-actions", children: [_jsx("div", { className: "steps-action", children: _jsxs("button", { type: "button", onClick: goToPreviousPage, disabled: isFirstVisiblePage, className: "button is-light cypress-pages-previous", children: [_jsx("span", { className: "icon", children: _jsx(MaterialIcon, { children: "keyboard_arrow_left" }) }), _jsx("span", { children: "Back" })] }) }), _jsx("div", { className: "step-progress-mobile cypress-steps-mobile", children: visiblePages.map((page, index) => (_jsx("div", { className: clsx('step-progress-mobile-dot', {
|
|
774
802
|
'is-active': currentPage.id === page.id,
|
|
775
803
|
'is-completed': currentPageIndex > index,
|
|
776
804
|
'has-background-danger': currentPage.id !== page.id &&
|
|
@@ -784,7 +812,10 @@ function OneBlinkFormBase({ googleMapsApiKey, abnLookupAuthenticationGuid, captc
|
|
|
784
812
|
isPreparingToSubmit ||
|
|
785
813
|
!submissionConditionallyEnabled, children: _jsx(CustomisableButtonInner, { label: isInfoPage
|
|
786
814
|
? 'Done'
|
|
787
|
-
: ((_e = buttons === null || buttons === void 0 ? void 0 : buttons.submit) === null || _e === void 0 ? void 0 : _e.label) || 'Submit', icon: (_f = buttons === null || buttons === void 0 ? void 0 : buttons.submit) === null || _f === void 0 ? void 0 : _f.icon }) }) }) }))] }))] }) }), !
|
|
815
|
+
: ((_e = buttons === null || buttons === void 0 ? void 0 : buttons.submit) === null || _e === void 0 ? void 0 : _e.label) || 'Submit', icon: (_f = buttons === null || buttons === void 0 ? void 0 : buttons.submit) === null || _f === void 0 ? void 0 : _f.icon }) }) }) }))] }))] }) }), !isPreview &&
|
|
816
|
+
(editableFormElementIds !== undefined || !isReadOnly) && (_jsxs(React.Fragment, { children: [_jsx(Prompt, { when: isDirty && !isNavigationAllowed, message: handleBlockedNavigation }), _jsx(Modal, { isOpen: hasConfirmedNavigation === false, title: "Unsaved Changes", cardClassName: "cypress-cancel-confirm", titleClassName: "cypress-cancel-confirm-title", bodyClassName: "cypress-cancel-confirm-body", actions: _jsxs(_Fragment, { children: [onSaveDraft && (_jsx("button", { type: "button", className: "button ob-button is-success cypress-cancel-confirm-save-draft", onClick: () => handleSaveDraft(false), children: _jsx(CustomisableButtonInner, { label: ((_g = buttons === null || buttons === void 0 ? void 0 : buttons.saveDraft) === null || _g === void 0 ? void 0 : _g.label) ||
|
|
817
|
+
'Save Draft', icon: (_h = buttons === null || buttons === void 0 ? void 0 : buttons.saveDraft) === null || _h === void 0 ? void 0 : _h.icon }) })), _jsx("span", { style: { flex: 1 } }), _jsx("button", { type: "button", className: "button ob-button is-light cypress-cancel-confirm-back", onClick: handleKeepGoing, children: _jsx(CustomisableButtonInner, { label: ((_j = buttons === null || buttons === void 0 ? void 0 : buttons.cancelPromptNo) === null || _j === void 0 ? void 0 : _j.label) || 'Back', icon: (_k = buttons === null || buttons === void 0 ? void 0 : buttons.cancelPromptNo) === null || _k === void 0 ? void 0 : _k.icon }) }), _jsx("button", { type: "button", className: "button ob-button is-primary cypress-cancel-confirm-discard", onClick: handleDiscardUnsavedChanges, autoFocus: true, children: _jsx(CustomisableButtonInner, { label: ((_l = buttons === null || buttons === void 0 ? void 0 : buttons.cancelPromptYes) === null || _l === void 0 ? void 0 : _l.label) ||
|
|
818
|
+
'Discard', icon: (_m = buttons === null || buttons === void 0 ? void 0 : buttons.cancelPromptYes) === null || _m === void 0 ? void 0 : _m.icon }) })] }), children: _jsx("p", { children: "You have unsaved changes, are you sure you want discard them?" }) })] })), !isReadOnly && !isPreview && audience !== 'APPROVER' && (_jsxs(React.Fragment, { children: [_jsx(Modal, { isOpen: promptUploadingAttachments === true, title: "Attachment upload in progress", cardClassName: "cypress-attachments-wait-continue", titleClassName: "cypress-attachments-confirm-wait-title", bodyClassName: "cypress-attachments-confirm-wait-body", actions: _jsxs(_Fragment, { children: [_jsx("span", { style: { flex: 1 } }), _jsx("button", { type: "button", className: "button ob-button is-light cypress-attachments-confirm-wait", onClick: handleWaitForAttachments, children: "Wait" }), _jsx("button", { type: "button", className: "button ob-button is-primary cypress-attachments-confirm-continue", onClick: handleContinueWithAttachments, autoFocus: true, children: "Continue" })] }), children: _jsx("p", { children: "Your attachments are still uploading, do you want to wait for the uploads to complete or continue using the app? If you click continue the attachments will upload in the background. Do not close the app until the upload has been completed." }) }), _jsxs(Modal, { isOpen: promptOfflineSubmissionAttempt, title: "It looks like you're Offline", className: "ob-modal__offline-submission-attempt", cardClassName: "cypress-submission-offline has-text-centered", titleClassName: "cypress-offline-title", bodyClassName: "cypress-offline-body", actions: _jsxs(_Fragment, { children: [onSaveDraft && (_jsx("button", { type: "button", className: "button ob-button ob-button__offline-submission-attempt-save-draft is-success", onClick: () => handleSaveDraft(false), children: _jsx(CustomisableButtonInner, { label: ((_o = buttons === null || buttons === void 0 ? void 0 : buttons.saveDraft) === null || _o === void 0 ? void 0 : _o.label) || 'Save Draft', icon: (_p = buttons === null || buttons === void 0 ? void 0 : buttons.saveDraft) === null || _p === void 0 ? void 0 : _p.icon }) })), _jsx("span", { style: { flex: 1 } }), _jsx("button", { className: "button ob-button ob-button__offline-submission-attempt-cancel is-light", onClick: () => setPromptOfflineSubmissionAttempt(false), children: "Cancel" }), _jsx("button", { className: "button ob-button ob-button__offline-submission-attempt-try-again is-primary", onClick: (e) => {
|
|
788
819
|
setPromptOfflineSubmissionAttempt(false);
|
|
789
820
|
handleSubmit(e, false);
|
|
790
821
|
}, autoFocus: true, children: "Try Again" })] }), children: [_jsxs("p", { className: "ob-modal__offline-submission-attempt-message", children: ["You cannot submit this form while offline, please try again when connectivity is restored.", onSaveDraft && (_jsxs("span", { className: "ob-modal__offline-submission-attempt-save-draft-message", children: [' ', "Alternatively, click the", ' ', _jsx("b", { children: ((_q = buttons === null || buttons === void 0 ? void 0 : buttons.saveDraft) === null || _q === void 0 ? void 0 : _q.label) || 'Save Draft' }), ' ', "button below to come back to this later."] }))] }), _jsx(MaterialIcon, { className: "has-text-warning icon-x-large ob-modal__offline-submission-attempt-icon", children: "wifi_off" })] })] })), shouldUseNavigableValidationErrorsNotification &&
|