react-flow-modal 0.4.1 → 0.5.0
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 +36 -49
- package/dist/index.cjs +12 -16
- package/dist/index.d.cts +6 -10
- package/dist/index.d.ts +6 -10
- package/dist/index.js +11 -14
- package/package.json +1 -1
- package/src/ModalHost.tsx +6 -10
- package/src/index.ts +1 -2
- package/src/useModal.tsx +1 -1
- package/src/useModalContext.ts +0 -8
package/README.md
CHANGED
|
@@ -22,7 +22,9 @@ yarn add react-flow-modal
|
|
|
22
22
|
## Basic Usage
|
|
23
23
|
|
|
24
24
|
```tsx
|
|
25
|
-
import {
|
|
25
|
+
import { StrictMode } from 'react';
|
|
26
|
+
import { createRoot } from 'react-dom/client';
|
|
27
|
+
import { ModalProvider, useModal, ModalHost } from "react-flow-modal";
|
|
26
28
|
|
|
27
29
|
function ConfirmModal({
|
|
28
30
|
onConfirm,
|
|
@@ -66,6 +68,7 @@ function App() {
|
|
|
66
68
|
const modal = useModal();
|
|
67
69
|
|
|
68
70
|
const onClick = async () => {
|
|
71
|
+
// render modal and await resolve
|
|
69
72
|
const result = await modal.open("confirm", (resolve) => (
|
|
70
73
|
<ConfirmModal
|
|
71
74
|
onConfirm={() => resolve(true)}
|
|
@@ -73,24 +76,22 @@ function App() {
|
|
|
73
76
|
/>
|
|
74
77
|
));
|
|
75
78
|
|
|
79
|
+
// flow resumed
|
|
76
80
|
console.log("Result:", result);
|
|
77
81
|
};
|
|
78
82
|
|
|
79
83
|
return <button onClick={onClick}>Open Confirm Modal</button>;
|
|
80
84
|
}
|
|
81
85
|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
export default function Root() {
|
|
87
|
-
return (
|
|
86
|
+
createRoot(document.getElementById('root')!).render(
|
|
87
|
+
<StrictMode>
|
|
88
88
|
<ModalProvider>
|
|
89
89
|
<App />
|
|
90
|
-
<
|
|
90
|
+
<ModalHost />
|
|
91
91
|
</ModalProvider>
|
|
92
|
-
|
|
93
|
-
|
|
92
|
+
</StrictMode>,
|
|
93
|
+
)
|
|
94
|
+
|
|
94
95
|
```
|
|
95
96
|
|
|
96
97
|
---
|
|
@@ -101,8 +102,10 @@ To support exit animations, modals must be rendered inside the same
|
|
|
101
102
|
React tree as `AnimatePresence`.
|
|
102
103
|
|
|
103
104
|
```tsx
|
|
104
|
-
import {
|
|
105
|
-
import {
|
|
105
|
+
import { StrictMode } from 'react';
|
|
106
|
+
import { createRoot } from 'react-dom/client';
|
|
107
|
+
import { ModalHost, ModalProvider } from 'react-flow-modal';
|
|
108
|
+
import { AnimatePresence, motion } from 'motion/react';
|
|
106
109
|
|
|
107
110
|
function ConfirmModal({
|
|
108
111
|
onConfirm,
|
|
@@ -113,7 +116,7 @@ function ConfirmModal({
|
|
|
113
116
|
}) {
|
|
114
117
|
return (
|
|
115
118
|
<motion.div
|
|
116
|
-
key="modal"
|
|
119
|
+
key="confirm-modal-container"
|
|
117
120
|
initial={{ opacity: 0 }}
|
|
118
121
|
animate={{ opacity: 1 }}
|
|
119
122
|
exit={{ opacity: 0 }}
|
|
@@ -127,7 +130,6 @@ function ConfirmModal({
|
|
|
127
130
|
}}
|
|
128
131
|
>
|
|
129
132
|
<motion.div
|
|
130
|
-
key="modal-content"
|
|
131
133
|
initial={{ scale: 0.9, opacity: 0 }}
|
|
132
134
|
animate={{ scale: 1, opacity: 1 }}
|
|
133
135
|
exit={{ scale: 0.95, opacity: 0 }}
|
|
@@ -137,6 +139,7 @@ function ConfirmModal({
|
|
|
137
139
|
padding: 24,
|
|
138
140
|
borderRadius: 8,
|
|
139
141
|
minWidth: 300,
|
|
142
|
+
color: "black",
|
|
140
143
|
}}
|
|
141
144
|
>
|
|
142
145
|
<h3>Are you sure?</h3>
|
|
@@ -151,39 +154,24 @@ function ConfirmModal({
|
|
|
151
154
|
);
|
|
152
155
|
}
|
|
153
156
|
|
|
154
|
-
|
|
155
|
-
const modal = useModal();
|
|
156
|
-
|
|
157
|
-
const onClick = async () => {
|
|
158
|
-
const result = await modal.open("confirm", (resolve) => (
|
|
159
|
-
<ConfirmModal
|
|
160
|
-
onConfirm={() => resolve(true)}
|
|
161
|
-
onCancel={() => resolve(false)}
|
|
162
|
-
/>
|
|
163
|
-
));
|
|
164
|
-
|
|
165
|
-
console.log("Result:", result);
|
|
166
|
-
};
|
|
167
|
-
|
|
168
|
-
return <button onClick={onClick}>Open Confirm Modal</button>;
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
function ModalRenderer() {
|
|
172
|
-
return (
|
|
173
|
-
<AnimatePresence>
|
|
174
|
-
{renderModals()}
|
|
175
|
-
</AnimatePresence>
|
|
176
|
-
);
|
|
177
|
-
}
|
|
157
|
+
...
|
|
178
158
|
|
|
179
|
-
|
|
180
|
-
|
|
159
|
+
createRoot(document.getElementById('root')!).render(
|
|
160
|
+
<StrictMode>
|
|
181
161
|
<ModalProvider>
|
|
182
162
|
<App />
|
|
183
|
-
<
|
|
163
|
+
<ModalHost>
|
|
164
|
+
{(modals) => (
|
|
165
|
+
<AnimatePresence>
|
|
166
|
+
{modals}
|
|
167
|
+
</AnimatePresence>
|
|
168
|
+
)}
|
|
169
|
+
</ModalHost>
|
|
184
170
|
</ModalProvider>
|
|
185
|
-
|
|
186
|
-
|
|
171
|
+
</StrictMode>,
|
|
172
|
+
)
|
|
173
|
+
|
|
174
|
+
|
|
187
175
|
```
|
|
188
176
|
|
|
189
177
|
---
|
|
@@ -210,11 +198,13 @@ Returns an object that controls the modal flow.
|
|
|
210
198
|
}
|
|
211
199
|
```
|
|
212
200
|
|
|
213
|
-
###
|
|
201
|
+
### ModalHost
|
|
214
202
|
```ts
|
|
215
|
-
|
|
203
|
+
const ModalHost: FC<{
|
|
204
|
+
children?: (modals: ReactElement[]) => React.ReactNode;
|
|
205
|
+
}>;
|
|
216
206
|
```
|
|
217
|
-
Renders the entire modal stack. This
|
|
207
|
+
Renders the entire modal stack. This component should be rendered **once** in your React tree.
|
|
218
208
|
|
|
219
209
|
---
|
|
220
210
|
|
|
@@ -223,9 +213,6 @@ Renders the entire modal stack. This function should be rendered **once** in you
|
|
|
223
213
|
> ⚠️ Always resolve or reject the promise.
|
|
224
214
|
> Leaving it pending will block the async flow.
|
|
225
215
|
|
|
226
|
-
> ⚠️ `renderModals()` should be rendered once.
|
|
227
|
-
> Rendering it multiple times may result in duplicated modals.
|
|
228
|
-
|
|
229
216
|
---
|
|
230
217
|
|
|
231
218
|
## Why react-flow-modal?
|
package/dist/index.cjs
CHANGED
|
@@ -22,8 +22,7 @@ var index_exports = {};
|
|
|
22
22
|
__export(index_exports, {
|
|
23
23
|
ModalHost: () => ModalHost,
|
|
24
24
|
ModalProvider: () => ModalProvider,
|
|
25
|
-
useModal: () => useModal
|
|
26
|
-
useModalHost: () => useModalHost
|
|
25
|
+
useModal: () => useModal
|
|
27
26
|
});
|
|
28
27
|
module.exports = __toCommonJS(index_exports);
|
|
29
28
|
|
|
@@ -44,6 +43,9 @@ var ModalProvider = ({ children }) => {
|
|
|
44
43
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(ModalContext.Provider, { value: { stack, setStack }, children });
|
|
45
44
|
};
|
|
46
45
|
|
|
46
|
+
// src/useModal.tsx
|
|
47
|
+
var import_react4 = require("react");
|
|
48
|
+
|
|
47
49
|
// src/useModalContext.ts
|
|
48
50
|
var import_react3 = require("react");
|
|
49
51
|
var useModalContext = () => {
|
|
@@ -53,14 +55,9 @@ var useModalContext = () => {
|
|
|
53
55
|
}
|
|
54
56
|
return context;
|
|
55
57
|
};
|
|
56
|
-
var useModalHost = () => {
|
|
57
|
-
const { stack } = useModalContext();
|
|
58
|
-
return {
|
|
59
|
-
render: () => stack.map((item) => item)
|
|
60
|
-
};
|
|
61
|
-
};
|
|
62
58
|
|
|
63
59
|
// src/useModal.tsx
|
|
60
|
+
var import_jsx_runtime2 = require("react/jsx-runtime");
|
|
64
61
|
var useModal = () => {
|
|
65
62
|
const { setStack } = useModalContext();
|
|
66
63
|
const pop = () => {
|
|
@@ -78,23 +75,22 @@ var useModal = () => {
|
|
|
78
75
|
reject(reason);
|
|
79
76
|
pop();
|
|
80
77
|
});
|
|
81
|
-
push(element);
|
|
78
|
+
push(/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react4.Fragment, { children: element }, `modal-${key}`));
|
|
82
79
|
});
|
|
83
80
|
};
|
|
84
81
|
return { open };
|
|
85
82
|
};
|
|
86
83
|
|
|
87
84
|
// src/ModalHost.tsx
|
|
88
|
-
var
|
|
89
|
-
var
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
return
|
|
85
|
+
var import_react5 = require("react");
|
|
86
|
+
var ModalHost = ({ children }) => {
|
|
87
|
+
const { stack } = useModalContext();
|
|
88
|
+
if (!children) return stack.filter(import_react5.isValidElement);
|
|
89
|
+
return children(stack.filter(import_react5.isValidElement));
|
|
93
90
|
};
|
|
94
91
|
// Annotate the CommonJS export names for ESM import in node:
|
|
95
92
|
0 && (module.exports = {
|
|
96
93
|
ModalHost,
|
|
97
94
|
ModalProvider,
|
|
98
|
-
useModal
|
|
99
|
-
useModalHost
|
|
95
|
+
useModal
|
|
100
96
|
});
|
package/dist/index.d.cts
CHANGED
|
@@ -1,17 +1,13 @@
|
|
|
1
|
-
import
|
|
2
|
-
import react__default, { FC, PropsWithChildren } from 'react';
|
|
1
|
+
import React$1, { FC, PropsWithChildren, ReactElement } from 'react';
|
|
3
2
|
|
|
4
3
|
declare const ModalProvider: FC<PropsWithChildren>;
|
|
5
4
|
|
|
6
5
|
declare const useModal: () => {
|
|
7
|
-
open: <T>(key: string, render: (resolve: (value: T) => void, reject: (reason?: unknown) => void) =>
|
|
6
|
+
open: <T>(key: string, render: (resolve: (value: T) => void, reject: (reason?: unknown) => void) => React$1.ReactNode) => Promise<T>;
|
|
8
7
|
};
|
|
9
8
|
|
|
10
|
-
|
|
11
|
-
|
|
9
|
+
declare const ModalHost: FC<{
|
|
10
|
+
children?: (modals: ReactElement[]) => React.ReactNode;
|
|
11
|
+
}>;
|
|
12
12
|
|
|
13
|
-
|
|
14
|
-
render: () => react.ReactNode[];
|
|
15
|
-
};
|
|
16
|
-
|
|
17
|
-
export { ModalHost, ModalProvider, useModal, useModalHost };
|
|
13
|
+
export { ModalHost, ModalProvider, useModal };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,17 +1,13 @@
|
|
|
1
|
-
import
|
|
2
|
-
import react__default, { FC, PropsWithChildren } from 'react';
|
|
1
|
+
import React$1, { FC, PropsWithChildren, ReactElement } from 'react';
|
|
3
2
|
|
|
4
3
|
declare const ModalProvider: FC<PropsWithChildren>;
|
|
5
4
|
|
|
6
5
|
declare const useModal: () => {
|
|
7
|
-
open: <T>(key: string, render: (resolve: (value: T) => void, reject: (reason?: unknown) => void) =>
|
|
6
|
+
open: <T>(key: string, render: (resolve: (value: T) => void, reject: (reason?: unknown) => void) => React$1.ReactNode) => Promise<T>;
|
|
8
7
|
};
|
|
9
8
|
|
|
10
|
-
|
|
11
|
-
|
|
9
|
+
declare const ModalHost: FC<{
|
|
10
|
+
children?: (modals: ReactElement[]) => React.ReactNode;
|
|
11
|
+
}>;
|
|
12
12
|
|
|
13
|
-
|
|
14
|
-
render: () => react.ReactNode[];
|
|
15
|
-
};
|
|
16
|
-
|
|
17
|
-
export { ModalHost, ModalProvider, useModal, useModalHost };
|
|
13
|
+
export { ModalHost, ModalProvider, useModal };
|
package/dist/index.js
CHANGED
|
@@ -15,6 +15,9 @@ var ModalProvider = ({ children }) => {
|
|
|
15
15
|
return /* @__PURE__ */ jsx(ModalContext.Provider, { value: { stack, setStack }, children });
|
|
16
16
|
};
|
|
17
17
|
|
|
18
|
+
// src/useModal.tsx
|
|
19
|
+
import { Fragment } from "react";
|
|
20
|
+
|
|
18
21
|
// src/useModalContext.ts
|
|
19
22
|
import { useContext } from "react";
|
|
20
23
|
var useModalContext = () => {
|
|
@@ -24,14 +27,9 @@ var useModalContext = () => {
|
|
|
24
27
|
}
|
|
25
28
|
return context;
|
|
26
29
|
};
|
|
27
|
-
var useModalHost = () => {
|
|
28
|
-
const { stack } = useModalContext();
|
|
29
|
-
return {
|
|
30
|
-
render: () => stack.map((item) => item)
|
|
31
|
-
};
|
|
32
|
-
};
|
|
33
30
|
|
|
34
31
|
// src/useModal.tsx
|
|
32
|
+
import { jsx as jsx2 } from "react/jsx-runtime";
|
|
35
33
|
var useModal = () => {
|
|
36
34
|
const { setStack } = useModalContext();
|
|
37
35
|
const pop = () => {
|
|
@@ -49,22 +47,21 @@ var useModal = () => {
|
|
|
49
47
|
reject(reason);
|
|
50
48
|
pop();
|
|
51
49
|
});
|
|
52
|
-
push(element);
|
|
50
|
+
push(/* @__PURE__ */ jsx2(Fragment, { children: element }, `modal-${key}`));
|
|
53
51
|
});
|
|
54
52
|
};
|
|
55
53
|
return { open };
|
|
56
54
|
};
|
|
57
55
|
|
|
58
56
|
// src/ModalHost.tsx
|
|
59
|
-
import {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
return
|
|
57
|
+
import { isValidElement } from "react";
|
|
58
|
+
var ModalHost = ({ children }) => {
|
|
59
|
+
const { stack } = useModalContext();
|
|
60
|
+
if (!children) return stack.filter(isValidElement);
|
|
61
|
+
return children(stack.filter(isValidElement));
|
|
64
62
|
};
|
|
65
63
|
export {
|
|
66
64
|
ModalHost,
|
|
67
65
|
ModalProvider,
|
|
68
|
-
useModal
|
|
69
|
-
useModalHost
|
|
66
|
+
useModal
|
|
70
67
|
};
|
package/package.json
CHANGED
package/src/ModalHost.tsx
CHANGED
|
@@ -1,13 +1,9 @@
|
|
|
1
|
-
import { FC,
|
|
2
|
-
import {
|
|
1
|
+
import { FC, isValidElement, ReactElement } from 'react';
|
|
2
|
+
import { useModalContext } from './useModalContext';
|
|
3
3
|
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
const { render } = useModalHost();
|
|
4
|
+
export const ModalHost: FC<{ children?: (modals: ReactElement[]) => React.ReactNode }> = ({ children }) => {
|
|
5
|
+
const { stack } = useModalContext();
|
|
7
6
|
|
|
8
|
-
return (
|
|
9
|
-
|
|
10
|
-
{render()}
|
|
11
|
-
</Fragment>
|
|
12
|
-
);
|
|
7
|
+
if (!children) return stack.filter(isValidElement);
|
|
8
|
+
return children(stack.filter(isValidElement));
|
|
13
9
|
};
|
package/src/index.ts
CHANGED
package/src/useModal.tsx
CHANGED
package/src/useModalContext.ts
CHANGED