-
Notifications
You must be signed in to change notification settings - Fork 10
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
42e77fb
commit bd0a25c
Showing
29 changed files
with
2,093 additions
and
1,725 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
114 changes: 114 additions & 0 deletions
114
...omponents/LogicalOperator/components/CriteriaRightPanel/CriteriaForm/components/index.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,114 @@ | ||
import { FormLabel, Tooltip } from '@mui/material' | ||
import React, { PropsWithChildren } from 'react' | ||
import { | ||
CriteriaDataType, | ||
CriteriaFormItemView, | ||
CriteriaFormItemViewProps, | ||
CriteriaItem, | ||
CriteriaItemType, | ||
CriteriaSection, | ||
DataTypeMapping | ||
} from '../types' | ||
import useStyles from '../style' | ||
import { BlockWrapper } from 'components/ui/Layout' | ||
import Collapse from 'components/ui/Collapse' | ||
import { CriteriaLabel } from 'components/ui/CriteriaLabel' | ||
import InfoIcon from '@mui/icons-material/Info' | ||
import { isFunction, isString } from 'lodash' | ||
|
||
type CriteriaItemRuntimeProps<T extends CriteriaDataType> = { | ||
setError: (error?: string) => void | ||
updateData: (data: T) => void | ||
data: T | ||
getValueSetOptions: CriteriaFormItemViewProps<never>['getValueSetOptions'] | ||
searchCode: CriteriaFormItemViewProps<never>['searchCode'] | ||
viewRenderers: { [key in CriteriaItemType]: CriteriaFormItemView<key> } | ||
} | ||
|
||
type CritieraItemProps<T extends CriteriaDataType, U extends CriteriaItem<T>> = CriteriaItemRuntimeProps<T> & U | ||
|
||
export const CFLabel = (props: { label: string; tooltip?: string; altStyle?: boolean }) => { | ||
const { label, tooltip, altStyle } = props | ||
if (altStyle) { | ||
return ( | ||
<FormLabel | ||
style={{ padding: '0 0 1em', fontWeight: 600, fontSize: 12, display: 'flex', alignItems: 'center' }} | ||
component="legend" | ||
> | ||
Fin de prise en charge | ||
{tooltip && ( | ||
<Tooltip title={tooltip}> | ||
<InfoIcon fontSize="small" color="primary" style={{ marginLeft: 4 }} /> | ||
</Tooltip> | ||
)} | ||
</FormLabel> | ||
) | ||
} | ||
return label | ||
} | ||
|
||
export const CFItem = <T extends CriteriaDataType, U extends CriteriaItem<T>>(props: CritieraItemProps<T, U>) => { | ||
const { valueKey, updateData, data, setError, getValueSetOptions, searchCode, viewRenderers } = props | ||
const View = viewRenderers[props.type] as CriteriaFormItemView<U['type']> | ||
const fieldValue = data[valueKey] as DataTypeMapping[U['type']]['dataType'] | ||
const displayCondition = props.displayCondition | ||
if ( | ||
displayCondition && | ||
((isFunction(displayCondition) && !displayCondition(data)) || | ||
(isString(displayCondition) && !eval(displayCondition))) | ||
) { | ||
return null | ||
} | ||
const disableCondition = props.disableCondition | ||
const disabled = | ||
disableCondition && | ||
((isFunction(disableCondition) && disableCondition(data)) || (isString(disableCondition) && eval(disableCondition))) | ||
return ( | ||
<View | ||
value={fieldValue} | ||
disabled={disabled} | ||
definition={props} | ||
updateData={(value) => updateData({ ...data, [valueKey]: value })} | ||
getValueSetOptions={getValueSetOptions} | ||
searchCode={searchCode} | ||
setError={setError} | ||
/> | ||
) | ||
} | ||
|
||
export const CFSection = <T extends CriteriaDataType>( | ||
props: PropsWithChildren<Omit<CriteriaSection<T>, 'items'> & { collapsed?: boolean }> | ||
) => { | ||
const { classes } = useStyles() | ||
return props.title ? ( | ||
<BlockWrapper className={classes.inputItem}> | ||
<Collapse title={props.title} value={!props.defaulCollapsed || !props.collapsed} margin="0"> | ||
{props.children} | ||
</Collapse> | ||
</BlockWrapper> | ||
) : ( | ||
<>{props.children}</> | ||
) | ||
} | ||
|
||
export const CFItemWrapper = (props: PropsWithChildren<{ label?: string; info?: string }>) => { | ||
const { classes } = useStyles() | ||
return ( | ||
<BlockWrapper className={classes.inputItem}> | ||
{props.label ? ( | ||
<CriteriaLabel label={props.label} style={{ padding: 0, marginTop: '1em' }}> | ||
{props.info && ( | ||
<Tooltip title={props.info}> | ||
<InfoIcon fontSize="small" color="primary" style={{ marginLeft: 4 }} /> | ||
</Tooltip> | ||
)} | ||
</CriteriaLabel> | ||
) : ( | ||
'' | ||
)} | ||
{props.children} | ||
</BlockWrapper> | ||
) | ||
} | ||
|
||
export default { CFItemWrapper, CFSection, CFLabel, CFItem } |
95 changes: 95 additions & 0 deletions
95
...agramView/components/LogicalOperator/components/CriteriaRightPanel/CriteriaForm/index.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,95 @@ | ||
import React, { useEffect, useState } from 'react' | ||
import CriteriaLayout from 'components/ui/CriteriaLayout' | ||
import { | ||
CriteriaData, | ||
CriteriaForm as CriteriaFormDefinition, | ||
CriteriaDataType, | ||
CriteriaFormItemViewProps, | ||
NumberAndComparatorDataType, | ||
NewDurationRangeType | ||
} from './types' | ||
import { CFItem, CFItemWrapper, CFSection } from './components' | ||
import FORM_ITEM_RENDERER from './renderers' | ||
import { useAppSelector } from 'state' | ||
import { LabelObject } from 'types/searchCriterias' | ||
|
||
export type CriteriaFormRuntimeProps<T extends CriteriaDataType> = { | ||
goBack: () => void | ||
data?: CriteriaData<T> | ||
updateData: (data: CriteriaData<T>) => void | ||
searchCode: CriteriaFormItemViewProps<never>['searchCode'] | ||
} | ||
|
||
type CriteriaFormProps<T extends CriteriaDataType> = CriteriaFormDefinition<T> & CriteriaFormRuntimeProps<T> | ||
|
||
export default function CriteriaForm<T extends CriteriaDataType>(props: CriteriaFormProps<T>) { | ||
const [criteriaData, setCriteriaData] = useState<CriteriaData<T>>(props.data || props.initialData) | ||
const valueSets = useAppSelector((state) => state.valueSets) | ||
const { goBack, updateData, label, warningAlert, itemSections, errorMessages, onDataChange } = props | ||
const isEdition = !!props.data | ||
const [error, setError] = useState<string>() | ||
|
||
useEffect(() => { | ||
onDataChange?.(criteriaData) | ||
}, [criteriaData, onDataChange]) | ||
|
||
console.log('rendering form') | ||
|
||
return ( | ||
<CriteriaLayout | ||
criteriaLabel={`${label}`} | ||
title={criteriaData.title} | ||
onChangeTitle={(title) => setCriteriaData({ ...criteriaData, title })} | ||
isEdition={isEdition} | ||
goBack={goBack} | ||
onSubmit={() => updateData(criteriaData)} | ||
disabled={error !== undefined} | ||
isInclusive={criteriaData.isInclusive} | ||
onChangeIsInclusive={(isInclusive) => setCriteriaData({ ...criteriaData, isInclusive: isInclusive })} | ||
infoAlert={['Tous les éléments des champs multiples sont liés par une contrainte OU']} | ||
warningAlert={warningAlert} | ||
errorAlert={error ? [errorMessages[error]] : undefined} | ||
> | ||
{itemSections.map((section, index) => ( | ||
<CFSection | ||
key={index} | ||
title={section.title} | ||
defaulCollapsed={section.defaulCollapsed} | ||
collapsed={section.items.every((item) => { | ||
const value = criteriaData[item.valueKey] | ||
let isNull = !value || (Array.isArray(value) && value.length === 0) | ||
if (item.type === 'numberAndComparator') { | ||
isNull = isNull || !(value as NumberAndComparatorDataType).value | ||
} else if (item.type === 'duration') { | ||
const duration = value as NewDurationRangeType | ||
isNull = isNull || (duration.start === null && duration.end === null) | ||
} | ||
if (!isNull) console.log(isNull, item.valueKey, value) | ||
|
||
return isNull | ||
})} | ||
> | ||
{section.items.map((item, index) => ( | ||
<CFItemWrapper key={index} label={item.extraLabel} info={item.extraInfo}> | ||
<CFItem | ||
{...{ | ||
viewRenderers: FORM_ITEM_RENDERER, | ||
...item, | ||
data: criteriaData, | ||
getValueSetOptions: (valueSetId) => { | ||
return (valueSets.entities[valueSetId]?.options || []) as LabelObject[] | ||
}, | ||
searchCode: props.searchCode, | ||
updateData: (newData: T) => { | ||
setCriteriaData({ ...criteriaData, ...newData }) | ||
}, | ||
setError | ||
}} | ||
/> | ||
</CFItemWrapper> | ||
))} | ||
</CFSection> | ||
))} | ||
</CriteriaLayout> | ||
) | ||
} |
49 changes: 49 additions & 0 deletions
49
...mponents/LogicalOperator/components/CriteriaRightPanel/CriteriaForm/legacyFormAdapter.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
import React from 'react' | ||
import { CriteriaDrawerComponentProps, CriteriaItemDataCache } from 'types' | ||
import { CriteriaData, CriteriaDataType } from './types' | ||
import CriteriaForm from '.' | ||
import { CriteriaForm as CriteriaFormDefinition } from './types' | ||
import { SelectedCriteriaType } from 'types/requestCriterias' | ||
import { fetchValueSet } from 'services/aphp/callApi' | ||
|
||
export type LegacyAdapterProps<T extends CriteriaDataType, U extends SelectedCriteriaType> = { | ||
form: () => CriteriaFormDefinition<T> | ||
adapter: { | ||
mapFromLegacyDataType: (legacyData: U, criteriaData: CriteriaItemDataCache) => CriteriaData<T> | ||
mapToLegacyDataType: (data: CriteriaData<T>) => Omit<U, 'id'> | ||
} | ||
} | ||
|
||
/** | ||
* Enable the use of the new CriteriaForm component with the legacy data format | ||
* @param props contains the form definition and the adapter to convert the legacy data to the new data format | ||
* @returns the legacy Drawer component with the new CriteriaForm component | ||
*/ | ||
export default function withLegacyAdapter<T extends CriteriaDataType, U extends SelectedCriteriaType>( | ||
props: LegacyAdapterProps<T, U> | ||
) { | ||
return (legacyProps: CriteriaDrawerComponentProps) => { | ||
const { criteriaData, goBack, selectedCriteria, onChangeSelectedCriteria } = legacyProps | ||
const formDefinition = props.form() | ||
const runtimeProps = { | ||
data: selectedCriteria | ||
? props.adapter.mapFromLegacyDataType(selectedCriteria as U, criteriaData) | ||
: formDefinition.initialData, | ||
updateData: (data: CriteriaData<T>) => onChangeSelectedCriteria(props.adapter.mapToLegacyDataType(data) as U), | ||
goBack | ||
} | ||
return ( | ||
<CriteriaForm | ||
{...formDefinition} | ||
{...runtimeProps} | ||
searchCode={(code: string, codeSystemUrl: string, abortSignal: AbortSignal) => | ||
fetchValueSet( | ||
codeSystemUrl, | ||
{ valueSetTitle: 'Toute la hiérarchie', search: code, noStar: false }, | ||
abortSignal | ||
) | ||
} | ||
/> | ||
) | ||
} | ||
} |
Oops, something went wrong.