dynamic-modal 1.1.8 → 1.1.10
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/README.md +0 -1
- package/dist/components/input-upload/input-upload.js +3 -3
- package/dist/components/make-button/make-button.js +19 -10
- package/dist/components/make-description/make-description.js +2 -2
- package/dist/components/make-input/make-input.js +57 -29
- package/dist/components/make-select/make-select.js +66 -29
- package/dist/components/make-textarea/make-textarea.js +57 -29
- package/dist/components/make-toggle/make-toggle.js +57 -29
- package/dist/components/make-upload/make-upload.js +72 -18
- package/dist/components/portal/portal.js +20 -10
- package/dist/context/component/component-state.d.ts +3 -3
- package/dist/context/component/component-state.js +20 -11
- package/dist/hooks/use-enable-if.d.ts +9 -0
- package/dist/hooks/use-enable-if.js +45 -0
- package/dist/hooks/use-live-data.d.ts +14 -0
- package/dist/hooks/use-live-data.js +42 -0
- package/dist/hooks/use-render-if.d.ts +12 -0
- package/dist/hooks/use-render-if.js +51 -0
- package/dist/interfaces/component-state.d.ts +8 -8
- package/dist/interfaces/modal.d.ts +4 -2
- package/dist/modal.js +70 -58
- package/dist/util/general/general.util.d.ts +3 -0
- package/dist/util/general/general.util.js +28 -0
- package/eslint.config.mjs +72 -14
- package/examples/live-data.ts +0 -1
- package/package.json +11 -9
- package/src/components/input-upload/input-upload.tsx +40 -28
- package/src/components/make-button/make-button.tsx +11 -13
- package/src/components/make-description/make-description.tsx +14 -8
- package/src/components/make-input/make-input.tsx +94 -47
- package/src/components/make-select/make-select.tsx +118 -48
- package/src/components/make-textarea/make-textarea.tsx +94 -47
- package/src/components/make-toggle/make-toggle.tsx +94 -47
- package/src/components/make-upload/make-upload.tsx +88 -36
- package/src/components/portal/portal.tsx +27 -25
- package/src/context/component/component-state.tsx +16 -9
- package/src/hooks/modal-handler.ts +17 -14
- package/src/hooks/use-enable-if.ts +64 -0
- package/src/hooks/use-live-data.ts +45 -0
- package/src/hooks/use-render-if.ts +59 -0
- package/src/interfaces/component-state.ts +38 -23
- package/src/interfaces/field.ts +33 -27
- package/src/interfaces/input-upload.ts +17 -15
- package/src/interfaces/make-button.ts +14 -13
- package/src/interfaces/make-description.ts +9 -8
- package/src/interfaces/make-field-group.ts +9 -8
- package/src/interfaces/make-input.ts +9 -8
- package/src/interfaces/make-select.ts +9 -9
- package/src/interfaces/make-textarea.ts +5 -5
- package/src/interfaces/make-toggle.ts +3 -3
- package/src/interfaces/make-upload.ts +8 -8
- package/src/interfaces/modal.ts +57 -39
- package/src/interfaces/option.ts +3 -3
- package/src/interfaces/portal.ts +5 -5
- package/src/modal.tsx +243 -147
- package/src/util/general/general.util.ts +27 -0
- package/tsconfig.json +1 -1
- package/dist/hooks/field-render.d.ts +0 -20
- package/dist/hooks/field-render.js +0 -94
- package/dist/tools/general.d.ts +0 -1
- package/dist/tools/general.js +0 -11
- package/src/hooks/field-render.ts +0 -120
- package/src/tools/general.ts +0 -8
|
@@ -1,53 +1,100 @@
|
|
|
1
|
-
'use client'
|
|
1
|
+
'use client';
|
|
2
2
|
|
|
3
|
-
import React, { FC, useContext, useEffect,
|
|
4
|
-
import { Controller } from 'react-hook-form'
|
|
5
|
-
import { useFieldRender } from '../../hooks/field-render'
|
|
6
|
-
import { IMakeToggleProps } from '../../interfaces/make-toggle'
|
|
7
|
-
import { generateId } from '../../tools/general'
|
|
8
|
-
import { ComponentStateContext } from '../../context/component/component-state'
|
|
3
|
+
import React, { FC, useContext, useEffect, useId } from 'react';
|
|
4
|
+
import { Controller } from 'react-hook-form';
|
|
9
5
|
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
6
|
+
import { IMakeToggleProps } from '../../interfaces/make-toggle';
|
|
7
|
+
import { ComponentStateContext } from '../../context/component/component-state';
|
|
8
|
+
import useEnableIf from '../../hooks/use-enable-if';
|
|
9
|
+
import useRenderIf from '../../hooks/use-render-if';
|
|
10
|
+
|
|
11
|
+
const MakeToggle: FC<IMakeToggleProps> = ({
|
|
12
|
+
element,
|
|
13
|
+
control,
|
|
14
|
+
watch,
|
|
15
|
+
unregister,
|
|
16
|
+
}) => {
|
|
17
|
+
const { Toggle } = useContext(ComponentStateContext);
|
|
18
|
+
|
|
19
|
+
const {
|
|
20
|
+
name: elementName,
|
|
21
|
+
validation: { required, message, regex, ...otherValidation },
|
|
22
|
+
enableIf,
|
|
23
|
+
renderIf,
|
|
24
|
+
...inputProps
|
|
25
|
+
} = element;
|
|
26
|
+
|
|
27
|
+
const { checkEnable, enable, setEnable } = useEnableIf({
|
|
28
|
+
elementEnableIf: enableIf,
|
|
29
|
+
});
|
|
30
|
+
const { checkRender, render, setRender } = useRenderIf({
|
|
31
|
+
elementRenderIf: renderIf,
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
const elementId = useId();
|
|
13
35
|
|
|
14
|
-
const elementId = useMemo(() => element.id ?? generateId(), [])
|
|
15
|
-
|
|
16
36
|
useEffect(() => {
|
|
17
|
-
const
|
|
18
|
-
|
|
19
|
-
|
|
37
|
+
const { unsubscribe } = watch((formData, { name, type }) => {
|
|
38
|
+
if (!name) return;
|
|
39
|
+
|
|
40
|
+
if (enableIf) {
|
|
41
|
+
checkEnable(formData, { name, type }).then((enableStatus) => {
|
|
42
|
+
if (enableStatus === undefined || enableStatus === null) return;
|
|
43
|
+
if (enable !== enableStatus) setEnable(enableStatus);
|
|
44
|
+
});
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
if (renderIf) {
|
|
48
|
+
checkRender(formData, { name, type }).then((renderStatus) => {
|
|
49
|
+
if (renderStatus === undefined || renderStatus === null) return;
|
|
50
|
+
|
|
51
|
+
if (render !== renderStatus) {
|
|
52
|
+
if (render && !renderStatus) unregister(elementName as string);
|
|
53
|
+
setRender(!!renderStatus);
|
|
54
|
+
}
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
return () => unsubscribe();
|
|
60
|
+
}, [watch, render, enable]);
|
|
61
|
+
|
|
62
|
+
if (!render) return null;
|
|
20
63
|
|
|
21
64
|
return (
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
65
|
+
<Controller
|
|
66
|
+
control={control}
|
|
67
|
+
name={elementName}
|
|
68
|
+
rules={{
|
|
69
|
+
required: {
|
|
70
|
+
value: required,
|
|
71
|
+
message: message ?? '',
|
|
72
|
+
},
|
|
73
|
+
pattern: regex
|
|
74
|
+
? {
|
|
75
|
+
value: regex,
|
|
76
|
+
message: message ?? '',
|
|
77
|
+
}
|
|
78
|
+
: undefined,
|
|
79
|
+
...otherValidation,
|
|
80
|
+
}}
|
|
81
|
+
render={({
|
|
82
|
+
field: { onChange, value },
|
|
83
|
+
fieldState: { invalid, error },
|
|
84
|
+
}) => (
|
|
85
|
+
<Toggle
|
|
86
|
+
{...inputProps}
|
|
87
|
+
id={elementId}
|
|
88
|
+
name={elementName}
|
|
89
|
+
onChange={onChange}
|
|
90
|
+
value={value ?? ''}
|
|
91
|
+
invalid={invalid}
|
|
92
|
+
error={error}
|
|
93
|
+
disabled={element.disabled ?? !enable}
|
|
94
|
+
/>
|
|
95
|
+
)}
|
|
96
|
+
/>
|
|
97
|
+
);
|
|
98
|
+
};
|
|
99
|
+
|
|
100
|
+
export default MakeToggle;
|
|
@@ -1,40 +1,92 @@
|
|
|
1
|
-
'use client'
|
|
1
|
+
'use client';
|
|
2
2
|
|
|
3
|
-
import React,{ FC } from 'react'
|
|
4
|
-
import { Controller } from 'react-hook-form'
|
|
5
|
-
import InputUpload from '../input-upload/input-upload'
|
|
6
|
-
import { useFieldRender } from '../../hooks/field-render'
|
|
7
|
-
import { IMakeUploadProps } from '../../interfaces/make-upload'
|
|
3
|
+
import React, { FC, useEffect, useId } from 'react';
|
|
4
|
+
import { Controller } from 'react-hook-form';
|
|
8
5
|
|
|
9
|
-
|
|
10
|
-
|
|
6
|
+
import InputUpload from '../input-upload/input-upload';
|
|
7
|
+
import { IMakeUploadProps } from '../../interfaces/make-upload';
|
|
8
|
+
import useEnableIf from '../../hooks/use-enable-if';
|
|
9
|
+
import useRenderIf from '../../hooks/use-render-if';
|
|
10
|
+
|
|
11
|
+
const MakeUpload: FC<IMakeUploadProps> = ({
|
|
12
|
+
element,
|
|
13
|
+
control,
|
|
14
|
+
watch,
|
|
15
|
+
unregister,
|
|
16
|
+
}) => {
|
|
17
|
+
const {
|
|
18
|
+
name: elementName,
|
|
19
|
+
validation: { required, message, regex, ...otherValidation },
|
|
20
|
+
enableIf,
|
|
21
|
+
renderIf,
|
|
22
|
+
...inputProps
|
|
23
|
+
} = element;
|
|
24
|
+
|
|
25
|
+
const { checkEnable, enable, setEnable } = useEnableIf({
|
|
26
|
+
elementEnableIf: enableIf,
|
|
27
|
+
});
|
|
28
|
+
const { checkRender, render, setRender } = useRenderIf({
|
|
29
|
+
elementRenderIf: renderIf,
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
const elementId = useId();
|
|
33
|
+
|
|
34
|
+
useEffect(() => {
|
|
35
|
+
const { unsubscribe } = watch((formData, { name, type }) => {
|
|
36
|
+
if (!name) return;
|
|
37
|
+
|
|
38
|
+
if (enableIf) {
|
|
39
|
+
checkEnable(formData, { name, type }).then((enableStatus) => {
|
|
40
|
+
if (enableStatus === undefined || enableStatus === null) return;
|
|
41
|
+
if (enable !== enableStatus) setEnable(enableStatus);
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
if (renderIf) {
|
|
46
|
+
checkRender(formData, { name, type }).then((renderStatus) => {
|
|
47
|
+
if (renderStatus === undefined || renderStatus === null) return;
|
|
48
|
+
|
|
49
|
+
if (render !== renderStatus) {
|
|
50
|
+
if (render && !renderStatus) unregister(elementName as string);
|
|
51
|
+
setRender(!!renderStatus);
|
|
52
|
+
}
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
return () => unsubscribe();
|
|
58
|
+
}, [watch, render, enable]);
|
|
59
|
+
|
|
60
|
+
if (!render) return null;
|
|
11
61
|
|
|
12
62
|
return (
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
63
|
+
<Controller
|
|
64
|
+
control={control}
|
|
65
|
+
name={elementName}
|
|
66
|
+
rules={{
|
|
67
|
+
required: {
|
|
68
|
+
value: required,
|
|
69
|
+
message: message ?? '',
|
|
70
|
+
},
|
|
71
|
+
pattern: regex
|
|
72
|
+
? {
|
|
73
|
+
value: regex,
|
|
74
|
+
message: message ?? '',
|
|
75
|
+
}
|
|
76
|
+
: undefined,
|
|
77
|
+
...otherValidation,
|
|
78
|
+
}}
|
|
79
|
+
render={({ field: { onChange } }) => (
|
|
80
|
+
<InputUpload
|
|
81
|
+
{...inputProps}
|
|
82
|
+
id={elementId}
|
|
83
|
+
name={elementName}
|
|
84
|
+
onChange={onChange}
|
|
85
|
+
disabled={element.disabled ?? !enable}
|
|
86
|
+
/>
|
|
87
|
+
)}
|
|
88
|
+
/>
|
|
89
|
+
);
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
export default MakeUpload;
|
|
@@ -1,37 +1,39 @@
|
|
|
1
|
-
'use client'
|
|
1
|
+
'use client';
|
|
2
2
|
|
|
3
|
-
import React, { useRef, useEffect, useState, FC } from 'react'
|
|
4
|
-
import { createPortal } from 'react-dom'
|
|
5
|
-
|
|
3
|
+
import React, { useRef, useEffect, useState, FC } from 'react';
|
|
4
|
+
import { createPortal } from 'react-dom';
|
|
5
|
+
|
|
6
|
+
import { IPortal } from '../../interfaces/portal';
|
|
6
7
|
|
|
7
8
|
export const Portal: FC<IPortal> = (props) => {
|
|
8
|
-
const ref = useRef<Element | null>(null)
|
|
9
|
-
const [mounted, setMounted] = useState(false)
|
|
9
|
+
const ref = useRef<Element | null>(null);
|
|
10
|
+
const [mounted, setMounted] = useState(false);
|
|
10
11
|
|
|
11
12
|
useEffect(() => {
|
|
12
13
|
if (mounted && !props.portalOpen && props.closeTime > 0) {
|
|
13
14
|
const timeoutId = setTimeout(() => {
|
|
14
|
-
setMounted(false)
|
|
15
|
-
ref.current = null
|
|
16
|
-
}, props.closeTime)
|
|
15
|
+
setMounted(false);
|
|
16
|
+
ref.current = null;
|
|
17
|
+
}, props.closeTime);
|
|
17
18
|
|
|
18
|
-
return () => clearTimeout(timeoutId)
|
|
19
|
+
return () => clearTimeout(timeoutId);
|
|
19
20
|
} else if (mounted && !props.portalOpen) {
|
|
20
|
-
setMounted(false)
|
|
21
|
-
ref.current = null
|
|
21
|
+
setMounted(false);
|
|
22
|
+
ref.current = null;
|
|
22
23
|
} else if (!mounted && props.portalOpen) {
|
|
23
|
-
ref.current = document.querySelector<HTMLElement>(
|
|
24
|
-
|
|
24
|
+
ref.current = document.querySelector<HTMLElement>(
|
|
25
|
+
props.portalTag ?? '#portal',
|
|
26
|
+
);
|
|
27
|
+
setMounted(true);
|
|
25
28
|
}
|
|
26
|
-
}, [mounted, props.closeTime, props.portalOpen, props.portalTag])
|
|
29
|
+
}, [mounted, props.closeTime, props.portalOpen, props.portalTag]);
|
|
30
|
+
|
|
31
|
+
if (!mounted && !ref.current) return null;
|
|
27
32
|
|
|
28
|
-
return (
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
: null
|
|
36
|
-
)
|
|
37
|
-
}
|
|
33
|
+
return createPortal(
|
|
34
|
+
<div className="transition-all delay-100 fixed top-0 left-0 w-full h-full grid place-items-center bg-black bg-opacity-40 z-20">
|
|
35
|
+
{props.children}
|
|
36
|
+
</div>,
|
|
37
|
+
ref.current!,
|
|
38
|
+
);
|
|
39
|
+
};
|
|
@@ -1,18 +1,25 @@
|
|
|
1
|
-
'use client'
|
|
1
|
+
'use client';
|
|
2
2
|
|
|
3
|
-
import React, { useMemo } from
|
|
4
|
-
import { createContext } from "react"
|
|
5
|
-
import { IComponentState, IComponentStateProps } from "../../interfaces/component-state"
|
|
3
|
+
import React, { useMemo, createContext } from 'react';
|
|
6
4
|
|
|
7
|
-
|
|
5
|
+
import {
|
|
6
|
+
IComponentState,
|
|
7
|
+
IComponentStateProps,
|
|
8
|
+
} from '../../interfaces/component-state';
|
|
8
9
|
|
|
9
|
-
export const
|
|
10
|
+
export const ComponentStateContext = createContext<IComponentState>(
|
|
11
|
+
{} as IComponentState,
|
|
12
|
+
);
|
|
10
13
|
|
|
11
|
-
|
|
14
|
+
export const ComponentState = ({
|
|
15
|
+
children,
|
|
16
|
+
components,
|
|
17
|
+
}: IComponentStateProps) => {
|
|
18
|
+
const value: IComponentState = useMemo(() => components, [components]);
|
|
12
19
|
|
|
13
20
|
return (
|
|
14
21
|
<ComponentStateContext.Provider value={value}>
|
|
15
22
|
{children}
|
|
16
23
|
</ComponentStateContext.Provider>
|
|
17
|
-
)
|
|
18
|
-
}
|
|
24
|
+
);
|
|
25
|
+
};
|
|
@@ -1,14 +1,15 @@
|
|
|
1
|
-
'use client'
|
|
1
|
+
'use client';
|
|
2
2
|
|
|
3
|
-
import {
|
|
4
|
-
|
|
3
|
+
import { useState } from 'react';
|
|
4
|
+
|
|
5
|
+
import { IModal, IModalConfigProps } from '../interfaces/modal';
|
|
5
6
|
|
|
6
7
|
interface IModalHandler {
|
|
7
|
-
openModal: (config: IModalConfigProps) => void
|
|
8
|
-
modalProps: IModal
|
|
8
|
+
openModal: (config: IModalConfigProps) => void;
|
|
9
|
+
modalProps: IModal;
|
|
9
10
|
}
|
|
10
11
|
|
|
11
|
-
export function useModalHandler
|
|
12
|
+
export function useModalHandler(): IModalHandler {
|
|
12
13
|
const initialState: IModalHandler = {
|
|
13
14
|
modalProps: {
|
|
14
15
|
config: {} as IModalConfigProps,
|
|
@@ -16,23 +17,25 @@ export function useModalHandler (): IModalHandler {
|
|
|
16
17
|
open: false,
|
|
17
18
|
},
|
|
18
19
|
openModal: () => {},
|
|
19
|
-
}
|
|
20
|
+
};
|
|
20
21
|
|
|
21
|
-
const [modalConfig, setModalConfig] = useState<IModalHandler>(initialState)
|
|
22
|
+
const [modalConfig, setModalConfig] = useState<IModalHandler>(initialState);
|
|
22
23
|
|
|
23
24
|
const openModal = (config: IModalConfigProps) => {
|
|
24
25
|
if (!config) {
|
|
25
|
-
alert(
|
|
26
|
-
|
|
26
|
+
alert(
|
|
27
|
+
`¡WARNING! this modal was not returned config, please check before use`,
|
|
28
|
+
);
|
|
29
|
+
return;
|
|
27
30
|
}
|
|
28
31
|
|
|
29
|
-
setModalConfig({ openModal, modalProps: { config, open: true, close } })
|
|
30
|
-
}
|
|
32
|
+
setModalConfig({ openModal, modalProps: { config, open: true, close } });
|
|
33
|
+
};
|
|
31
34
|
|
|
32
|
-
const closeModal = () => setModalConfig(initialState)
|
|
35
|
+
const closeModal = () => setModalConfig(initialState);
|
|
33
36
|
|
|
34
37
|
return {
|
|
35
38
|
openModal,
|
|
36
39
|
modalProps: { ...modalConfig.modalProps, close: closeModal },
|
|
37
|
-
}
|
|
40
|
+
};
|
|
38
41
|
}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { useState } from 'react';
|
|
2
|
+
import {
|
|
3
|
+
IModalRenderAction,
|
|
4
|
+
IModalRenderCondition,
|
|
5
|
+
IModalRenderCriteria,
|
|
6
|
+
} from '../interfaces/modal';
|
|
7
|
+
import { liveDataHandler } from '../util/general/general.util';
|
|
8
|
+
|
|
9
|
+
export interface IRenderIfProps {
|
|
10
|
+
elementEnableIf?: IModalRenderCondition;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const useEnableIf = ({ elementEnableIf }: IRenderIfProps) => {
|
|
14
|
+
const [enable, setEnable] = useState<boolean>(() => {
|
|
15
|
+
return elementEnableIf === undefined;
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
const checkEnable = async (
|
|
19
|
+
formData: Record<string, unknown>,
|
|
20
|
+
{ name }: Record<'name', string> & Record<'type', string | undefined>,
|
|
21
|
+
) => {
|
|
22
|
+
const targetFieldData = formData[name] as string | number;
|
|
23
|
+
if (
|
|
24
|
+
targetFieldData === undefined ||
|
|
25
|
+
targetFieldData === '' ||
|
|
26
|
+
targetFieldData === null
|
|
27
|
+
)
|
|
28
|
+
return;
|
|
29
|
+
|
|
30
|
+
const enableIfConfig = elementEnableIf;
|
|
31
|
+
const isLiveEnable: boolean =
|
|
32
|
+
!!enableIfConfig?.action && !!enableIfConfig.condition;
|
|
33
|
+
|
|
34
|
+
if (isLiveEnable && enableIfConfig!.condition!.includes(name)) {
|
|
35
|
+
const enableStatus: boolean = await liveDataHandler(
|
|
36
|
+
targetFieldData,
|
|
37
|
+
formData,
|
|
38
|
+
(enableIfConfig as IModalRenderAction)!.action!,
|
|
39
|
+
);
|
|
40
|
+
|
|
41
|
+
return enableStatus;
|
|
42
|
+
} else {
|
|
43
|
+
const enableConditionList = Object.keys(
|
|
44
|
+
elementEnableIf as IModalRenderCondition,
|
|
45
|
+
);
|
|
46
|
+
if (enableConditionList.includes(name)) {
|
|
47
|
+
const enableStatus: boolean =
|
|
48
|
+
(enableIfConfig as IModalRenderCriteria)[name]!.includes(
|
|
49
|
+
targetFieldData,
|
|
50
|
+
) || (enableIfConfig as IModalRenderCriteria)[name]!.includes('*');
|
|
51
|
+
|
|
52
|
+
return enableStatus;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
enable,
|
|
59
|
+
checkEnable,
|
|
60
|
+
setEnable,
|
|
61
|
+
};
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
export default useEnableIf;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { IModalLiveDataCondition } from '../interfaces/modal';
|
|
2
|
+
import { useState } from 'react';
|
|
3
|
+
import { IOption } from '../interfaces/option';
|
|
4
|
+
import { liveDataAction } from '../util/general/general.util';
|
|
5
|
+
|
|
6
|
+
export interface ILiveDataProps {
|
|
7
|
+
elementLiveData?: IModalLiveDataCondition;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
const useLiveData = ({ elementLiveData }: ILiveDataProps) => {
|
|
11
|
+
const [liveData, setLiveData] = useState<Array<IOption> | undefined>(
|
|
12
|
+
undefined,
|
|
13
|
+
);
|
|
14
|
+
|
|
15
|
+
const checkLiveData = async (
|
|
16
|
+
formData: Record<string, unknown>,
|
|
17
|
+
{ name }: Record<'name', string> & Record<'type', string | undefined>,
|
|
18
|
+
) => {
|
|
19
|
+
const targetFieldData = formData[name] as string | number;
|
|
20
|
+
|
|
21
|
+
const liveDataConfig = elementLiveData;
|
|
22
|
+
const isLiveData: boolean =
|
|
23
|
+
!!liveDataConfig?.action && !!liveDataConfig.condition;
|
|
24
|
+
|
|
25
|
+
if (!isLiveData) return null;
|
|
26
|
+
|
|
27
|
+
if (liveDataConfig!.condition.includes(name)) {
|
|
28
|
+
return await liveDataAction(
|
|
29
|
+
targetFieldData,
|
|
30
|
+
formData,
|
|
31
|
+
liveDataConfig!.action,
|
|
32
|
+
);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
return null;
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
return {
|
|
39
|
+
liveData,
|
|
40
|
+
checkLiveData,
|
|
41
|
+
setLiveData,
|
|
42
|
+
};
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
export default useLiveData;
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { useState } from 'react';
|
|
2
|
+
import {
|
|
3
|
+
IModalRenderAction,
|
|
4
|
+
IModalRenderCondition,
|
|
5
|
+
IModalRenderCriteria,
|
|
6
|
+
} from '../interfaces/modal';
|
|
7
|
+
import { liveDataHandler } from '../util/general/general.util';
|
|
8
|
+
|
|
9
|
+
export interface IRenderIfProps {
|
|
10
|
+
elementRenderIf?: IModalRenderCondition;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const useRenderIf = ({ elementRenderIf }: IRenderIfProps) => {
|
|
14
|
+
const [render, setRender] = useState<boolean>(() => {
|
|
15
|
+
return elementRenderIf === undefined;
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
const checkRender = async (
|
|
19
|
+
formData: Record<string, unknown>,
|
|
20
|
+
{ name }: Record<'name', string> & Record<'type', string | undefined>,
|
|
21
|
+
) => {
|
|
22
|
+
const targetFieldData = formData[name] as string | number;
|
|
23
|
+
|
|
24
|
+
const renderIfConfig = elementRenderIf!;
|
|
25
|
+
const isLiveRender: boolean =
|
|
26
|
+
!!renderIfConfig?.action && !!renderIfConfig?.condition;
|
|
27
|
+
|
|
28
|
+
if (isLiveRender && renderIfConfig.condition!.includes(name)) {
|
|
29
|
+
const renderStatus: boolean = await liveDataHandler(
|
|
30
|
+
targetFieldData,
|
|
31
|
+
formData,
|
|
32
|
+
(renderIfConfig as IModalRenderAction)!.action!,
|
|
33
|
+
);
|
|
34
|
+
|
|
35
|
+
return renderStatus;
|
|
36
|
+
} else {
|
|
37
|
+
const renderConditionList = Object.keys(
|
|
38
|
+
elementRenderIf as IModalRenderCriteria,
|
|
39
|
+
);
|
|
40
|
+
|
|
41
|
+
if (renderConditionList.includes(name)) {
|
|
42
|
+
const renderStatus: boolean =
|
|
43
|
+
(renderIfConfig as IModalRenderCriteria)[name]!.includes(
|
|
44
|
+
targetFieldData,
|
|
45
|
+
) || (renderIfConfig as IModalRenderCriteria)[name]!.includes('*');
|
|
46
|
+
|
|
47
|
+
return renderStatus;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
return {
|
|
53
|
+
render,
|
|
54
|
+
checkRender,
|
|
55
|
+
setRender,
|
|
56
|
+
};
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
export default useRenderIf;
|
|
@@ -1,33 +1,48 @@
|
|
|
1
|
-
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
import { IOption } from
|
|
5
|
-
import { IMakeInput } from
|
|
6
|
-
import { IMakeButton } from
|
|
7
|
-
import { IMakeSelect } from
|
|
8
|
-
import { IMakeTextarea } from
|
|
9
|
-
import { IMakeToggle } from
|
|
1
|
+
import { FC, PropsWithChildren } from 'react';
|
|
2
|
+
import { FieldError } from 'react-hook-form';
|
|
3
|
+
|
|
4
|
+
import { IOption } from './option';
|
|
5
|
+
import { IMakeInput } from './make-input';
|
|
6
|
+
import { IMakeButton } from './make-button';
|
|
7
|
+
import { IMakeSelect } from './make-select';
|
|
8
|
+
import { IMakeTextarea } from './make-textarea';
|
|
9
|
+
import { IMakeToggle } from './make-toggle';
|
|
10
10
|
|
|
11
11
|
export interface IComponentAditionalProps {
|
|
12
|
-
onChange: (...event: any[]) => void
|
|
13
|
-
value: any
|
|
14
|
-
invalid: boolean
|
|
15
|
-
error?: FieldError
|
|
16
|
-
liveSearching?: boolean
|
|
12
|
+
onChange: (...event: any[]) => void;
|
|
13
|
+
value: any;
|
|
14
|
+
invalid: boolean;
|
|
15
|
+
error?: FieldError;
|
|
16
|
+
liveSearching?: boolean;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
19
|
export interface IComponentState {
|
|
20
|
-
ModalButtonCancel: FC<Omit<IMakeButton, 'elementType'
|
|
21
|
-
ModalButtonAction: FC<Omit<IMakeButton, 'elementType'
|
|
22
|
-
Button: FC<Omit<IMakeButton, 'elementType'
|
|
20
|
+
ModalButtonCancel: FC<Omit<IMakeButton, 'elementType'>>;
|
|
21
|
+
ModalButtonAction: FC<Omit<IMakeButton, 'elementType'>>;
|
|
22
|
+
Button: FC<Omit<IMakeButton, 'elementType'>>;
|
|
23
23
|
//Description: FC<Omit<IMakeDescription, 'elementType'>>
|
|
24
|
-
Input: FC<
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
24
|
+
Input: FC<
|
|
25
|
+
Omit<IMakeInput, 'elementType' | 'validation' | 'renderIf' | 'enableIf'> &
|
|
26
|
+
IComponentAditionalProps
|
|
27
|
+
>;
|
|
28
|
+
Select: FC<
|
|
29
|
+
Omit<IMakeSelect, 'elementType' | 'validation' | 'renderIf' | 'enableIf'> &
|
|
30
|
+
IComponentAditionalProps &
|
|
31
|
+
Record<'options', Array<IOption>>
|
|
32
|
+
>;
|
|
33
|
+
Textarea: FC<
|
|
34
|
+
Omit<
|
|
35
|
+
IMakeTextarea,
|
|
36
|
+
'elementType' | 'validation' | 'renderIf' | 'enableIf'
|
|
37
|
+
> &
|
|
38
|
+
IComponentAditionalProps
|
|
39
|
+
>;
|
|
40
|
+
Toggle: FC<
|
|
41
|
+
Omit<IMakeToggle, 'elementType' | 'validation' | 'renderIf' | 'enableIf'> &
|
|
42
|
+
IComponentAditionalProps
|
|
43
|
+
>;
|
|
28
44
|
}
|
|
29
45
|
|
|
30
46
|
export interface IComponentStateProps extends PropsWithChildren {
|
|
31
|
-
components: IComponentState
|
|
47
|
+
components: IComponentState;
|
|
32
48
|
}
|
|
33
|
-
|