From b5de7826cfe299cbef16bf53f3f49700c93db5ca Mon Sep 17 00:00:00 2001 From: eirikhaugstulen Date: Tue, 19 Dec 2023 15:17:12 +0100 Subject: [PATCH] feat: implement changes from the design discussions --- i18n/en.pot | 28 ++++--------------- .../DataEntry/DataEntry.component.js | 1 - .../DataSection/DataSection.component.js | 5 ++-- .../getConvertedRelatedStageEvent.js | 5 ---- .../Validated/useBuildNewEventPayload.js | 10 ++++++- .../RelatedStagesActions.component.js | 23 +++------------ .../WidgetRelatedStages.component.js | 4 +-- .../WidgetRelatedStages.types.js | 2 +- .../WidgetRelatedStages/constants.js | 8 ++---- .../ValidationFunctions.js | 1 - .../relatedStageEventIsValid.js | 4 +++ .../relatedStageEventIsValid.types.js | 4 +-- .../WidgetRelatedStages/useRelatedStages.js | 2 +- 13 files changed, 35 insertions(+), 62 deletions(-) diff --git a/i18n/en.pot b/i18n/en.pot index 81b43b6952..d9f2290d24 100644 --- a/i18n/en.pot +++ b/i18n/en.pot @@ -5,8 +5,8 @@ msgstr "" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" -"POT-Creation-Date: 2023-12-18T20:04:11.694Z\n" -"PO-Revision-Date: 2023-12-18T20:04:11.694Z\n" +"POT-Creation-Date: 2023-12-19T14:17:13.334Z\n" +"PO-Revision-Date: 2023-12-19T14:17:13.334Z\n" msgid "Choose one or more dates..." msgstr "Choose one or more dates..." @@ -1365,9 +1365,6 @@ msgstr "Link to an existing {{linkableStageLabel}}" msgid "Choose a {{linkableStageLabel}}" msgstr "Choose a {{linkableStageLabel}}" -msgid "Related stages" -msgstr "Related stages" - msgid "Ambiguous relationships, contact system administrator" msgstr "Ambiguous relationships, contact system administrator" @@ -1378,24 +1375,11 @@ msgstr "" "Enter {{linkableStageLabel}} details in the next step after completing this " "{{currentStageLabel}}." -msgid "" -"This {{currentStageLabel}} will be created without a link to " -"{{linkableStageLabel}}" -msgstr "" -"This {{currentStageLabel}} will be created without a link to " -"{{linkableStageLabel}}" - -msgid "Schedule in {{displayName}}" -msgstr "Schedule in {{displayName}}" - -msgid "Link to an existing {{displayName}}" -msgstr "Link to an existing {{displayName}}" - -msgid "Enter {{displayName}} details now" -msgstr "Enter {{displayName}} details now" +msgid "Report now" +msgstr "Report now" -msgid "Don't link to a {{displayName}}" -msgstr "Don't link to a {{displayName}}" +msgid "Link to an existing" +msgstr "Link to an existing" msgid "Scheduled date" msgstr "Scheduled date" diff --git a/src/core_modules/capture-core/components/DataEntry/DataEntry.component.js b/src/core_modules/capture-core/components/DataEntry/DataEntry.component.js index c0c818c491..7ff1ce7056 100644 --- a/src/core_modules/capture-core/components/DataEntry/DataEntry.component.js +++ b/src/core_modules/capture-core/components/DataEntry/DataEntry.component.js @@ -44,7 +44,6 @@ const styles = theme => ({ verticalFormContainer: { flexGrow: 10, maxWidth: '100%', - marginBottom: spacers.dp12, }, verticalFormInnerContainer: { maxWidth: theme.typography.pxToRem(892), diff --git a/src/core_modules/capture-core/components/DataSection/DataSection.component.js b/src/core_modules/capture-core/components/DataSection/DataSection.component.js index f069efc794..953714939f 100644 --- a/src/core_modules/capture-core/components/DataSection/DataSection.component.js +++ b/src/core_modules/capture-core/components/DataSection/DataSection.component.js @@ -5,11 +5,12 @@ import { withStyles } from '@material-ui/core'; import type { Props } from './dataSection.type'; -const styles = { +const styles = theme => ({ sectionWrapper: { border: `1px solid ${colors.grey300}`, borderRadius: '3px', marginBottom: spacersNum.dp16, + maxWidth: theme.typography.pxToRem(892), }, sectionHeader: { color: colors.grey900, @@ -20,7 +21,7 @@ const styles = { marginBottom: '8px', width: 'fit-content', }, -}; +}); const DataSectionPlain = ({ sectionName, children, classes, dataTest }: Props) => (
, relatedStageRef) => { if ( relatedStageRef.current - && saveType === addEventSaveTypes.COMPLETE && relatedStageRef.current.eventHasLinkableStageRelationship() ) { const isValid = relatedStageRef.current.formIsValidOnSave(); @@ -54,6 +53,15 @@ export const useBuildNewEventPayload = ({ const { selectedRelationshipType, relatedStageDataValues, linkMode } = relatedStageRef.current .getLinkedStageValues(clientRequestEvent.event); + if (!linkMode) { + return { + formHasError: false, + linkedEvent: null, + relationship: null, + linkMode: null, + }; + } + const { linkedEvent, relationship } = getConvertedRelatedStageEvent({ linkMode, relatedStageDataValues, diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/RelatedStagesActions/RelatedStagesActions.component.js b/src/core_modules/capture-core/components/WidgetRelatedStages/RelatedStagesActions/RelatedStagesActions.component.js index 059ca32e73..aa39e55dda 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/RelatedStagesActions/RelatedStagesActions.component.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/RelatedStagesActions/RelatedStagesActions.component.js @@ -1,7 +1,7 @@ // @flow import React, { type ComponentType, useMemo } from 'react'; import i18n from '@dhis2/d2-i18n'; -import { Radio, colors, spacers, spacersNum, IconInfo16, IconWarning16 } from '@dhis2/ui'; +import { Radio, colors, spacers, spacersNum, IconInfo16 } from '@dhis2/ui'; import { withStyles } from '@material-ui/core'; import { actions as RelatedStagesActionTypes, mainOptionTranslatedTexts, relatedStageStatus } from '../constants'; import { DataSection } from '../../DataSection'; @@ -72,7 +72,7 @@ export const RelatedStagesActionsPlain = ({ return (
{type === relatedStageStatus.LINKABLE ? Object.keys(mainOptionTranslatedTexts).map(key => ( @@ -81,7 +81,7 @@ export const RelatedStagesActionsPlain = ({ name={`related-stage-action-${key}`} checked={key === selectedAction} disabled={key === RelatedStagesActionTypes.LINK_EXISTING_RESPONSE && !linkableEvents.length} - label={mainOptionTranslatedTexts[key](programStage.stageForm.name)} + label={mainOptionTranslatedTexts[key]} onChange={(e: Object) => updateSelectedAction(e.value)} value={key} /> @@ -122,26 +122,11 @@ export const RelatedStagesActionsPlain = ({ relatedStagesDataValues={relatedStagesDataValues} setRelatedStagesDataValues={setRelatedStagesDataValues} linkableEvents={linkableEvents} - linkedStageLabel={programStage.stageForm.name} + linkableStageLabel={programStage.stageForm.name} errorMessages={errorMessages} saveAttempted={saveAttempted} /> )} - - {selectedAction === RelatedStagesActionTypes.DO_NOT_LINK_RESPONSE && ( -
- - {i18n.t( - 'This {{currentStageLabel}} will be created without a link to {{linkableStageLabel}}', - { - linkableStageLabel: programStage.stageForm.name, - currentStageLabel, - }, - )} -
- )} ); }; diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.component.js b/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.component.js index f213a0361e..87356cf1bf 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.component.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.component.js @@ -3,7 +3,7 @@ import React, { forwardRef, useCallback, useEffect, useImperativeHandle, useStat import { useRelatedStages } from './useRelatedStages'; import type { Props, RelatedStageDataValueStates } from './WidgetRelatedStages.types'; import { RelatedStagesActions } from './RelatedStagesActions'; -import { actions as LinkModes, relatedStageStatus } from './constants'; +import { relatedStageStatus } from './constants'; import { useStageLabels } from './hooks/useStageLabels'; import type { ErrorMessagesForRelatedStages } from './RelatedStagesActions'; import { relatedStageWidgetIsValid } from './relatedStageEventIsValid/relatedStageEventIsValid'; @@ -31,7 +31,7 @@ const WidgetRelatedStagesPlain = ({ const [saveAttempted, setSaveAttempted] = useState(false); const [errorMessages, setErrorMessages] = useState({}); const [relatedStageDataValues, setRelatedStageDataValues] = useState({ - linkMode: LinkModes.SCHEDULE_IN_ORG, + linkMode: undefined, scheduledAt: '', orgUnit: undefined, linkedEventId: undefined, diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.types.js b/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.types.js index 29afdef450..3e89c82ccf 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.types.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/WidgetRelatedStages.types.js @@ -8,7 +8,7 @@ export type Props = {| currentStageLabel: string, |} export type RelatedStageDataValueStates = {| - linkMode: typeof LinkModes.SCHEDULE_IN_ORG, + linkMode: ?$Keys, scheduledAt: string, orgUnit: ?{ path: string, diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/constants.js b/src/core_modules/capture-core/components/WidgetRelatedStages/constants.js index 671b8b37ab..038d47695f 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/constants.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/constants.js @@ -10,12 +10,10 @@ export const actions = Object.freeze({ SCHEDULE_IN_ORG: 'SCHEDULE_IN_ORG', LINK_EXISTING_RESPONSE: 'LINK_EXISTING_RESPONSE', ENTER_DATA: 'ENTER_DATA', - DO_NOT_LINK_RESPONSE: 'DO_NOT_LINK_RESPONSE', }); export const mainOptionTranslatedTexts = { - [actions.SCHEDULE_IN_ORG]: (displayName?: string) => i18n.t('Schedule in {{displayName}}', { displayName }), - [actions.LINK_EXISTING_RESPONSE]: (displayName?: string) => i18n.t('Link to an existing {{displayName}}', { displayName }), - [actions.ENTER_DATA]: (displayName?: string) => i18n.t('Enter {{displayName}} details now', { displayName }), - [actions.DO_NOT_LINK_RESPONSE]: (displayName?: string) => i18n.t("Don't link to a {{displayName}}", { displayName }), + [actions.SCHEDULE_IN_ORG]: i18n.t('Schedule'), + [actions.ENTER_DATA]: i18n.t('Report now'), + [actions.LINK_EXISTING_RESPONSE]: i18n.t('Link to an existing'), }; diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/ValidationFunctions.js b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/ValidationFunctions.js index 1deb1682a3..07ad6a17a8 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/ValidationFunctions.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/ValidationFunctions.js @@ -66,6 +66,5 @@ export const ValidationFunctionsByLinkMode: { [key: string]: (props: ?Props) => [RelatedStageModes.SCHEDULE_IN_ORG]: props => scheduleInOrgUnit(props), [RelatedStageModes.ENTER_DATA]: () => true, [RelatedStageModes.LINK_EXISTING_RESPONSE]: props => linkToExistingResponse(props), - [RelatedStageModes.DO_NOT_LINK_RESPONSE]: () => true, }; diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.js b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.js index 0e09d62a6b..21e7693f2f 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.js @@ -12,6 +12,10 @@ export const relatedStageWidgetIsValid = ({ linkedEventId, setErrorMessages, }: RelatedStageIsValidProps): boolean => { + if (!linkMode) { + return true; + } + const validationFunction = ValidationFunctionsByLinkMode[linkMode]; if (!validationFunction) { diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.types.js b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.types.js index 026bf9d75e..c97648e958 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.types.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/relatedStageEventIsValid/relatedStageEventIsValid.types.js @@ -1,9 +1,9 @@ // @flow import type { ErrorMessagesForRelatedStages } from '../RelatedStagesActions'; -import { actions as RelatedStagesModes } from '../constants'; +import { actions as LinkModes } from '../constants'; export type RelatedStageIsValidProps = {| - linkMode: $Keys, + linkMode: ?$Keys, scheduledAt: ?string, orgUnit: ?{ id: string, diff --git a/src/core_modules/capture-core/components/WidgetRelatedStages/useRelatedStages.js b/src/core_modules/capture-core/components/WidgetRelatedStages/useRelatedStages.js index 93918ab259..f48ca1b5bc 100644 --- a/src/core_modules/capture-core/components/WidgetRelatedStages/useRelatedStages.js +++ b/src/core_modules/capture-core/components/WidgetRelatedStages/useRelatedStages.js @@ -18,7 +18,7 @@ type Props = {| export const useRelatedStages = ({ programStageId, programId }: Props) => { const { data: relationshipTypes } = useIndexedDBQuery( - ['RelatedStages', 'relationshipTypes'], + ['RelatedStages', 'relationshipTypes', programId, programStageId], () => getRelationshipTypeFromIndexedDB(), { select: allRelationshipTypes => allRelationshipTypes ?.filter((relationshipType) => {