@cyclone-ui/state 0.0.12 → 0.0.14
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/CHANGELOG.md +26 -0
- package/README.md +1 -1
- package/dist/base/atoms/atom-with-broadcast.cjs +45 -1
- package/dist/base/atoms/atom-with-broadcast.mjs +45 -1
- package/dist/base/atoms/atom-with-broadcast.mjs.map +1 -1
- package/dist/base/atoms/atom-with-compare.cjs +12 -1
- package/dist/base/atoms/atom-with-compare.mjs +12 -1
- package/dist/base/atoms/atom-with-compare.mjs.map +1 -1
- package/dist/base/atoms/atom-with-debounce.cjs +52 -1
- package/dist/base/atoms/atom-with-debounce.mjs +52 -1
- package/dist/base/atoms/atom-with-debounce.mjs.map +1 -1
- package/dist/base/atoms/atom-with-effect.cjs +123 -1
- package/dist/base/atoms/atom-with-effect.mjs +120 -1
- package/dist/base/atoms/atom-with-effect.mjs.map +1 -1
- package/dist/base/atoms/atom-with-listeners.cjs +36 -1
- package/dist/base/atoms/atom-with-listeners.mjs +36 -1
- package/dist/base/atoms/atom-with-listeners.mjs.map +1 -1
- package/dist/base/atoms/atom-with-pending.cjs +14 -1
- package/dist/base/atoms/atom-with-pending.mjs +14 -1
- package/dist/base/atoms/atom-with-pending.mjs.map +1 -1
- package/dist/base/atoms/atom-with-refresh-and-default.cjs +19 -1
- package/dist/base/atoms/atom-with-refresh-and-default.mjs +19 -1
- package/dist/base/atoms/atom-with-refresh-and-default.mjs.map +1 -1
- package/dist/base/atoms/atom-with-refresh.cjs +13 -1
- package/dist/base/atoms/atom-with-refresh.mjs +13 -1
- package/dist/base/atoms/atom-with-refresh.mjs.map +1 -1
- package/dist/base/atoms/atom-with-toggle.cjs +13 -1
- package/dist/base/atoms/atom-with-toggle.mjs +13 -1
- package/dist/base/atoms/atom-with-toggle.mjs.map +1 -1
- package/dist/base/atoms/atom-with-web-storage.cjs +48 -1
- package/dist/base/atoms/atom-with-web-storage.mjs +47 -1
- package/dist/base/atoms/atom-with-web-storage.mjs.map +1 -1
- package/dist/base/atoms/atom-with-wrapper.cjs +25 -1
- package/dist/base/atoms/atom-with-wrapper.mjs +25 -1
- package/dist/base/atoms/atom-with-wrapper.mjs.map +1 -1
- package/dist/base/atoms/base-atom.cjs +25 -1
- package/dist/base/atoms/base-atom.mjs +25 -1
- package/dist/base/atoms/base-atom.mjs.map +1 -1
- package/dist/base/atoms/index.cjs +24 -1
- package/dist/base/atoms/index.mjs +13 -1
- package/dist/base/hooks/index.cjs +9 -1
- package/dist/base/hooks/index.mjs +6 -1
- package/dist/base/hooks/use-atom-effect.cjs +17 -1
- package/dist/base/hooks/use-atom-effect.mjs +17 -1
- package/dist/base/hooks/use-atom-effect.mjs.map +1 -1
- package/dist/base/hooks/use-hydrate-molecule.cjs +17 -1
- package/dist/base/hooks/use-hydrate-molecule.mjs +17 -1
- package/dist/base/hooks/use-hydrate-molecule.mjs.map +1 -1
- package/dist/base/hooks/use-prepare-atoms.cjs +20 -1
- package/dist/base/hooks/use-prepare-atoms.mjs +20 -1
- package/dist/base/hooks/use-prepare-atoms.mjs.map +1 -1
- package/dist/base/hooks/use-sync-molecule.cjs +37 -1
- package/dist/base/hooks/use-sync-molecule.mjs +37 -1
- package/dist/base/hooks/use-sync-molecule.mjs.map +1 -1
- package/dist/base/index.cjs +47 -1
- package/dist/base/index.mjs +24 -1
- package/dist/base/utilities/create-molecule.cjs +105 -4
- package/dist/base/utilities/create-molecule.d.cts.map +1 -1
- package/dist/base/utilities/create-molecule.mjs +102 -4
- package/dist/base/utilities/create-molecule.mjs.map +1 -1
- package/dist/base/utilities/create-web-storage.cjs +55 -1
- package/dist/base/utilities/create-web-storage.mjs +55 -1
- package/dist/base/utilities/create-web-storage.mjs.map +1 -1
- package/dist/base/utilities/debounce.cjs +52 -1
- package/dist/base/utilities/debounce.mjs +52 -1
- package/dist/base/utilities/debounce.mjs.map +1 -1
- package/dist/base/utilities/index.cjs +13 -1
- package/dist/base/utilities/index.mjs +6 -1
- package/dist/base/utilities/is-atom.cjs +48 -1
- package/dist/base/utilities/is-atom.mjs +46 -1
- package/dist/base/utilities/is-atom.mjs.map +1 -1
- package/dist/base/utilities/set-atom-debug.cjs +24 -1
- package/dist/base/utilities/set-atom-debug.mjs +23 -1
- package/dist/base/utilities/set-atom-debug.mjs.map +1 -1
- package/dist/client/index.cjs +16 -1
- package/dist/client/index.mjs +8 -1
- package/dist/form/atoms/atom-with-field.cjs +23 -1
- package/dist/form/atoms/atom-with-field.mjs +23 -1
- package/dist/form/atoms/atom-with-field.mjs.map +1 -1
- package/dist/form/atoms/atom-with-messages.cjs +85 -1
- package/dist/form/atoms/atom-with-messages.mjs +78 -1
- package/dist/form/atoms/atom-with-messages.mjs.map +1 -1
- package/dist/form/hooks/index.cjs +7 -1
- package/dist/form/hooks/index.mjs +5 -1
- package/dist/form/hooks/use-field-actions.cjs +92 -1
- package/dist/form/hooks/use-field-actions.mjs +92 -1
- package/dist/form/hooks/use-field-actions.mjs.map +1 -1
- package/dist/form/hooks/use-field-ref.cjs +16 -1
- package/dist/form/hooks/use-field-ref.mjs +16 -1
- package/dist/form/hooks/use-field-ref.mjs.map +1 -1
- package/dist/form/hooks/use-form-actions.cjs +69 -1
- package/dist/form/hooks/use-form-actions.mjs +69 -1
- package/dist/form/hooks/use-form-actions.mjs.map +1 -1
- package/dist/form/index.cjs +30 -1
- package/dist/form/index.mjs +17 -1
- package/dist/form/molecules/field-molecule.cjs +154 -1
- package/dist/form/molecules/field-molecule.mjs +153 -1
- package/dist/form/molecules/field-molecule.mjs.map +1 -1
- package/dist/form/molecules/form-molecule.cjs +180 -1
- package/dist/form/molecules/form-molecule.mjs +179 -1
- package/dist/form/molecules/form-molecule.mjs.map +1 -1
- package/dist/form/molecules/index.cjs +7 -1
- package/dist/form/molecules/index.mjs +4 -1
- package/dist/form/providers/FieldProvider.cjs +103 -4
- package/dist/form/providers/FieldProvider.mjs +103 -4
- package/dist/form/providers/FieldProvider.mjs.map +1 -1
- package/dist/form/providers/FormProvider.cjs +66 -4
- package/dist/form/providers/FormProvider.d.cts.map +1 -1
- package/dist/form/providers/FormProvider.mjs +66 -4
- package/dist/form/providers/FormProvider.mjs.map +1 -1
- package/dist/form/providers/index.cjs +5 -1
- package/dist/form/providers/index.mjs +4 -1
- package/dist/form/types.cjs +13 -1
- package/dist/form/types.mjs +13 -1
- package/dist/form/types.mjs.map +1 -1
- package/dist/form/utilities/abort-error.cjs +15 -1
- package/dist/form/utilities/abort-error.mjs +15 -1
- package/dist/form/utilities/abort-error.mjs.map +1 -1
- package/dist/form/utilities/index.cjs +7 -1
- package/dist/form/utilities/index.mjs +5 -1
- package/dist/form/utilities/is-validation-results.cjs +9 -1
- package/dist/form/utilities/is-validation-results.mjs +9 -1
- package/dist/form/utilities/is-validation-results.mjs.map +1 -1
- package/dist/form/utilities/validators.cjs +8 -1
- package/dist/form/utilities/validators.mjs +8 -1
- package/dist/form/utilities/validators.mjs.map +1 -1
- package/dist/index.cjs +71 -1
- package/dist/index.mjs +34 -1
- package/dist/message/components/MessageViewport.cjs +21 -6
- package/dist/message/components/MessageViewport.mjs +21 -6
- package/dist/message/components/MessageViewport.mjs.map +1 -1
- package/dist/message/components/index.cjs +3 -1
- package/dist/message/components/index.mjs +3 -1
- package/dist/message/hooks/index.cjs +3 -1
- package/dist/message/hooks/index.mjs +3 -1
- package/dist/message/hooks/use-message-actions.cjs +63 -1
- package/dist/message/hooks/use-message-actions.mjs +63 -1
- package/dist/message/hooks/use-message-actions.mjs.map +1 -1
- package/dist/message/index.cjs +23 -1
- package/dist/message/index.mjs +8 -1
- package/dist/message/providers/MessageProvider.cjs +16 -1
- package/dist/message/providers/MessageProvider.mjs +16 -1
- package/dist/message/providers/MessageProvider.mjs.map +1 -1
- package/dist/theme/hooks/index.cjs +7 -1
- package/dist/theme/hooks/index.mjs +4 -1
- package/dist/theme/hooks/use-theme-actions.cjs +21 -1
- package/dist/theme/hooks/use-theme-actions.mjs +21 -1
- package/dist/theme/hooks/use-theme-actions.mjs.map +1 -1
- package/dist/theme/hooks/use-theme-store.cjs +61 -1
- package/dist/theme/hooks/use-theme-store.d.cts +2 -2
- package/dist/theme/hooks/use-theme-store.d.mts +2 -2
- package/dist/theme/hooks/use-theme-store.mjs +59 -1
- package/dist/theme/hooks/use-theme-store.mjs.map +1 -1
- package/dist/theme/index.cjs +17 -1
- package/dist/theme/index.mjs +9 -1
- package/dist/theme/molecules/index.cjs +3 -1
- package/dist/theme/molecules/index.mjs +3 -1
- package/dist/theme/molecules/theme-molecule.cjs +14 -1
- package/dist/theme/molecules/theme-molecule.mjs +14 -1
- package/dist/theme/molecules/theme-molecule.mjs.map +1 -1
- package/dist/theme/providers/ThemeProvider.cjs +30 -5
- package/dist/theme/providers/ThemeProvider.mjs +30 -5
- package/dist/theme/providers/ThemeProvider.mjs.map +1 -1
- package/dist/theme/utilities/theme-helpers.cjs +71 -1
- package/dist/theme/utilities/theme-helpers.mjs +70 -1
- package/dist/theme/utilities/theme-helpers.mjs.map +1 -1
- package/package.json +6 -6
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,32 @@
|
|
|
2
2
|
|
|
3
3
|
# Changelog for Cyclone UI - State
|
|
4
4
|
|
|
5
|
+
## [0.0.13](https://github.com/storm-software/cyclone-ui/releases/tag/state%400.0.13) (10/11/2026)
|
|
6
|
+
|
|
7
|
+
### Bug Fixes
|
|
8
|
+
|
|
9
|
+
- **monorepo:** Update component descriptions and added design sync with Claude Design ([35ece709](https://github.com/storm-software/cyclone-ui/commit/35ece709))
|
|
10
|
+
|
|
11
|
+
### Features
|
|
12
|
+
|
|
13
|
+
- **field:** Added the `variant` property to both field and label components ([c1e0c13c](https://github.com/storm-software/cyclone-ui/commit/c1e0c13c))
|
|
14
|
+
- **confetti-burst:** Added the Confetti Burst reusable animation ([b395a334](https://github.com/storm-software/cyclone-ui/commit/b395a334))
|
|
15
|
+
- **like-button:** Added `LikeButton` and `Feedback` components ([9814aa5b](https://github.com/storm-software/cyclone-ui/commit/9814aa5b))
|
|
16
|
+
|
|
17
|
+
### Updated Dependencies
|
|
18
|
+
|
|
19
|
+
- Updated **helpers** to **v0.3.12**
|
|
20
|
+
|
|
21
|
+
## [0.0.12](https://github.com/storm-software/cyclone-ui/releases/tag/state%400.0.12) (10/07/2026)
|
|
22
|
+
|
|
23
|
+
### Bug Fixes
|
|
24
|
+
|
|
25
|
+
- **themes:** Clean up typography tokens ([68aee6ad](https://github.com/storm-software/cyclone-ui/commit/68aee6ad))
|
|
26
|
+
|
|
27
|
+
### Updated Dependencies
|
|
28
|
+
|
|
29
|
+
- Updated **helpers** to **v0.3.11**
|
|
30
|
+
|
|
5
31
|
## [0.0.11](https://github.com/storm-software/cyclone-ui/releases/tag/state%400.0.11) (10/06/2026)
|
|
6
32
|
|
|
7
33
|
### Bug Fixes
|
package/README.md
CHANGED
|
@@ -27,7 +27,7 @@ This package is part of the <b>🌀 Cyclone UI</b> monorepo. The repository cont
|
|
|
27
27
|
<!-- markdownlint-disable -->
|
|
28
28
|
|
|
29
29
|
> [!IMPORTANT]
|
|
30
|
-
> This repository, and the apps, libraries, and tools contained within, is still in it's initial development phase. As a result, bugs and issues are expected with it's usage. When the main development phase completes, a proper release will be performed, the packages will be
|
|
30
|
+
> This repository, and the apps, libraries, and tools contained within, is still in it's initial development phase. As a result, bugs and issues are expected with it's usage. When the main development phase completes, a proper release will be performed, the packages will be available through NPM (and other distributions), and this message will be removed. However, in the meantime, please feel free to report any issues you may come across.
|
|
31
31
|
|
|
32
32
|
<!-- markdownlint-restore -->
|
|
33
33
|
<!-- prettier-ignore-end -->
|
|
@@ -1 +1,45 @@
|
|
|
1
|
-
const
|
|
1
|
+
const require_is_atom = require("../utilities/is-atom.cjs");
|
|
2
|
+
const require_base_atom = require("./base-atom.cjs");
|
|
3
|
+
let _stryke_type_checks_is_function = require("@stryke/type-checks/is-function");
|
|
4
|
+
|
|
5
|
+
//#region src/base/atoms/atom-with-broadcast.ts
|
|
6
|
+
/**
|
|
7
|
+
* Creates an atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
8
|
+
*
|
|
9
|
+
* @param key - The key to use for the BroadcastChannel
|
|
10
|
+
* @param initialValueOrAtom - The initial value of the atom
|
|
11
|
+
* @returns An atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
12
|
+
*/
|
|
13
|
+
function atomWithBroadcast(key, initialValueOrAtom) {
|
|
14
|
+
const valueAtom = require_is_atom.isAtom(initialValueOrAtom) ? initialValueOrAtom : require_base_atom.baseAtom(initialValueOrAtom);
|
|
15
|
+
const listeners = /* @__PURE__ */ new Set();
|
|
16
|
+
const channel = typeof BroadcastChannel === "undefined" ? void 0 : new BroadcastChannel(key);
|
|
17
|
+
if (channel) channel.onmessage = (message) => {
|
|
18
|
+
for (const listener of listeners) listener(message);
|
|
19
|
+
};
|
|
20
|
+
const broadcastAtom = require_base_atom.baseAtom((get) => get(valueAtom), (get, set, update) => {
|
|
21
|
+
set(valueAtom, (0, _stryke_type_checks_is_function.isFunction)(update.value) ? update.value(get(valueAtom)) : update.value);
|
|
22
|
+
if (!update.isEvent && channel) channel.postMessage(JSON.stringify(get(valueAtom)));
|
|
23
|
+
});
|
|
24
|
+
broadcastAtom.onMount = (setAtom) => {
|
|
25
|
+
const listener = (event) => {
|
|
26
|
+
setAtom({
|
|
27
|
+
isEvent: true,
|
|
28
|
+
value: JSON.parse(event.data)
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
listeners.add(listener);
|
|
32
|
+
return () => {
|
|
33
|
+
listeners.delete(listener);
|
|
34
|
+
};
|
|
35
|
+
};
|
|
36
|
+
return require_base_atom.baseAtom((get) => get(broadcastAtom), (_, set, update) => {
|
|
37
|
+
set(broadcastAtom, {
|
|
38
|
+
isEvent: false,
|
|
39
|
+
value: update
|
|
40
|
+
});
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
//#endregion
|
|
45
|
+
exports.atomWithBroadcast = atomWithBroadcast;
|
|
@@ -1,2 +1,46 @@
|
|
|
1
|
-
import{isAtom
|
|
1
|
+
import { isAtom } from "../utilities/is-atom.mjs";
|
|
2
|
+
import { baseAtom } from "./base-atom.mjs";
|
|
3
|
+
import { isFunction } from "@stryke/type-checks/is-function";
|
|
4
|
+
|
|
5
|
+
//#region src/base/atoms/atom-with-broadcast.ts
|
|
6
|
+
/**
|
|
7
|
+
* Creates an atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
8
|
+
*
|
|
9
|
+
* @param key - The key to use for the BroadcastChannel
|
|
10
|
+
* @param initialValueOrAtom - The initial value of the atom
|
|
11
|
+
* @returns An atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
12
|
+
*/
|
|
13
|
+
function atomWithBroadcast(key, initialValueOrAtom) {
|
|
14
|
+
const valueAtom = isAtom(initialValueOrAtom) ? initialValueOrAtom : baseAtom(initialValueOrAtom);
|
|
15
|
+
const listeners = /* @__PURE__ */ new Set();
|
|
16
|
+
const channel = typeof BroadcastChannel === "undefined" ? void 0 : new BroadcastChannel(key);
|
|
17
|
+
if (channel) channel.onmessage = (message) => {
|
|
18
|
+
for (const listener of listeners) listener(message);
|
|
19
|
+
};
|
|
20
|
+
const broadcastAtom = baseAtom((get) => get(valueAtom), (get, set, update) => {
|
|
21
|
+
set(valueAtom, isFunction(update.value) ? update.value(get(valueAtom)) : update.value);
|
|
22
|
+
if (!update.isEvent && channel) channel.postMessage(JSON.stringify(get(valueAtom)));
|
|
23
|
+
});
|
|
24
|
+
broadcastAtom.onMount = (setAtom) => {
|
|
25
|
+
const listener = (event) => {
|
|
26
|
+
setAtom({
|
|
27
|
+
isEvent: true,
|
|
28
|
+
value: JSON.parse(event.data)
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
listeners.add(listener);
|
|
32
|
+
return () => {
|
|
33
|
+
listeners.delete(listener);
|
|
34
|
+
};
|
|
35
|
+
};
|
|
36
|
+
return baseAtom((get) => get(broadcastAtom), (_, set, update) => {
|
|
37
|
+
set(broadcastAtom, {
|
|
38
|
+
isEvent: false,
|
|
39
|
+
value: update
|
|
40
|
+
});
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
//#endregion
|
|
45
|
+
export { atomWithBroadcast };
|
|
2
46
|
//# sourceMappingURL=atom-with-broadcast.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atom-with-broadcast.mjs","names":[
|
|
1
|
+
{"version":3,"file":"atom-with-broadcast.mjs","names":[],"sources":[],"mappings":""}
|
|
@@ -1 +1,12 @@
|
|
|
1
|
-
let
|
|
1
|
+
let jotai_utils = require("jotai/utils");
|
|
2
|
+
|
|
3
|
+
//#region src/base/atoms/atom-with-compare.ts
|
|
4
|
+
function atomWithCompare(initialValue, areEqual) {
|
|
5
|
+
return (0, jotai_utils.atomWithReducer)(initialValue, (prev, next) => {
|
|
6
|
+
if (areEqual(prev, next)) return prev;
|
|
7
|
+
return next;
|
|
8
|
+
});
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
//#endregion
|
|
12
|
+
exports.atomWithCompare = atomWithCompare;
|
|
@@ -1,2 +1,13 @@
|
|
|
1
|
-
import{atomWithReducer
|
|
1
|
+
import { atomWithReducer } from "jotai/utils";
|
|
2
|
+
|
|
3
|
+
//#region src/base/atoms/atom-with-compare.ts
|
|
4
|
+
function atomWithCompare(initialValue, areEqual) {
|
|
5
|
+
return atomWithReducer(initialValue, (prev, next) => {
|
|
6
|
+
if (areEqual(prev, next)) return prev;
|
|
7
|
+
return next;
|
|
8
|
+
});
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
//#endregion
|
|
12
|
+
export { atomWithCompare };
|
|
2
13
|
//# sourceMappingURL=atom-with-compare.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atom-with-compare.mjs","names":[
|
|
1
|
+
{"version":3,"file":"atom-with-compare.mjs","names":[],"sources":[],"mappings":""}
|
|
@@ -1 +1,52 @@
|
|
|
1
|
-
const
|
|
1
|
+
const require_is_atom = require("../utilities/is-atom.cjs");
|
|
2
|
+
const require_base_atom = require("./base-atom.cjs");
|
|
3
|
+
const require_atom_with_wrapper = require("./atom-with-wrapper.cjs");
|
|
4
|
+
let _stryke_type_checks_is_function = require("@stryke/type-checks/is-function");
|
|
5
|
+
let jotai_utils = require("jotai/utils");
|
|
6
|
+
|
|
7
|
+
//#region src/base/atoms/atom-with-debounce.ts
|
|
8
|
+
function atomWithDebounce(initialValueOrAtom, debounceMs = 500, shouldDebounceOnReset = false) {
|
|
9
|
+
const prevTimeoutAtom = require_base_atom.baseAtom(void 0);
|
|
10
|
+
const initialValueAtom = require_is_atom.isAtom(initialValueOrAtom) ? initialValueOrAtom : require_atom_with_wrapper.atomWithWrapper(initialValueOrAtom);
|
|
11
|
+
const innerValueAtom = require_base_atom.baseAtom(null);
|
|
12
|
+
const _currentValueAtom = require_base_atom.baseAtom((get) => {
|
|
13
|
+
const innerValue = get(innerValueAtom);
|
|
14
|
+
if (innerValue === null) return get(initialValueAtom);
|
|
15
|
+
return innerValue;
|
|
16
|
+
}, (get, set, update) => set(innerValueAtom, update));
|
|
17
|
+
const isDebouncingAtom = require_base_atom.baseAtom(false);
|
|
18
|
+
const debouncedValueAtom = require_base_atom.baseAtom((get) => get(innerValueAtom), (get, set, update) => {
|
|
19
|
+
clearTimeout(get(prevTimeoutAtom));
|
|
20
|
+
const prevValue = get(_currentValueAtom);
|
|
21
|
+
const nextValue = update === jotai_utils.RESET ? get(innerValueAtom) : (0, _stryke_type_checks_is_function.isFunction)(update) ? update(prevValue) : update;
|
|
22
|
+
const onDebounceStart = () => {
|
|
23
|
+
set(_currentValueAtom, nextValue);
|
|
24
|
+
set(isDebouncingAtom, true);
|
|
25
|
+
};
|
|
26
|
+
const onDebounceEnd = () => {
|
|
27
|
+
set(debouncedValueAtom, nextValue);
|
|
28
|
+
set(isDebouncingAtom, false);
|
|
29
|
+
};
|
|
30
|
+
onDebounceStart();
|
|
31
|
+
if (!shouldDebounceOnReset && nextValue === get(initialValueAtom)) {
|
|
32
|
+
onDebounceEnd();
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
const nextTimeoutId = setTimeout(() => {
|
|
36
|
+
onDebounceEnd();
|
|
37
|
+
}, debounceMs);
|
|
38
|
+
set(prevTimeoutAtom, nextTimeoutId);
|
|
39
|
+
});
|
|
40
|
+
return {
|
|
41
|
+
clearTimeoutAtom: require_base_atom.baseAtom(null, (get, set) => {
|
|
42
|
+
clearTimeout(get(prevTimeoutAtom));
|
|
43
|
+
set(isDebouncingAtom, false);
|
|
44
|
+
}),
|
|
45
|
+
currentValueAtom: require_base_atom.baseAtom((get) => get(_currentValueAtom)),
|
|
46
|
+
debouncedValueAtom,
|
|
47
|
+
isDebouncingAtom
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
//#endregion
|
|
52
|
+
exports.atomWithDebounce = atomWithDebounce;
|
|
@@ -1,2 +1,53 @@
|
|
|
1
|
-
import{isAtom
|
|
1
|
+
import { isAtom } from "../utilities/is-atom.mjs";
|
|
2
|
+
import { baseAtom } from "./base-atom.mjs";
|
|
3
|
+
import { atomWithWrapper } from "./atom-with-wrapper.mjs";
|
|
4
|
+
import { isFunction } from "@stryke/type-checks/is-function";
|
|
5
|
+
import { RESET } from "jotai/utils";
|
|
6
|
+
|
|
7
|
+
//#region src/base/atoms/atom-with-debounce.ts
|
|
8
|
+
function atomWithDebounce(initialValueOrAtom, debounceMs = 500, shouldDebounceOnReset = false) {
|
|
9
|
+
const prevTimeoutAtom = baseAtom(void 0);
|
|
10
|
+
const initialValueAtom = isAtom(initialValueOrAtom) ? initialValueOrAtom : atomWithWrapper(initialValueOrAtom);
|
|
11
|
+
const innerValueAtom = baseAtom(null);
|
|
12
|
+
const _currentValueAtom = baseAtom((get) => {
|
|
13
|
+
const innerValue = get(innerValueAtom);
|
|
14
|
+
if (innerValue === null) return get(initialValueAtom);
|
|
15
|
+
return innerValue;
|
|
16
|
+
}, (get, set, update) => set(innerValueAtom, update));
|
|
17
|
+
const isDebouncingAtom = baseAtom(false);
|
|
18
|
+
const debouncedValueAtom = baseAtom((get) => get(innerValueAtom), (get, set, update) => {
|
|
19
|
+
clearTimeout(get(prevTimeoutAtom));
|
|
20
|
+
const prevValue = get(_currentValueAtom);
|
|
21
|
+
const nextValue = update === RESET ? get(innerValueAtom) : isFunction(update) ? update(prevValue) : update;
|
|
22
|
+
const onDebounceStart = () => {
|
|
23
|
+
set(_currentValueAtom, nextValue);
|
|
24
|
+
set(isDebouncingAtom, true);
|
|
25
|
+
};
|
|
26
|
+
const onDebounceEnd = () => {
|
|
27
|
+
set(debouncedValueAtom, nextValue);
|
|
28
|
+
set(isDebouncingAtom, false);
|
|
29
|
+
};
|
|
30
|
+
onDebounceStart();
|
|
31
|
+
if (!shouldDebounceOnReset && nextValue === get(initialValueAtom)) {
|
|
32
|
+
onDebounceEnd();
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
const nextTimeoutId = setTimeout(() => {
|
|
36
|
+
onDebounceEnd();
|
|
37
|
+
}, debounceMs);
|
|
38
|
+
set(prevTimeoutAtom, nextTimeoutId);
|
|
39
|
+
});
|
|
40
|
+
return {
|
|
41
|
+
clearTimeoutAtom: baseAtom(null, (get, set) => {
|
|
42
|
+
clearTimeout(get(prevTimeoutAtom));
|
|
43
|
+
set(isDebouncingAtom, false);
|
|
44
|
+
}),
|
|
45
|
+
currentValueAtom: baseAtom((get) => get(_currentValueAtom)),
|
|
46
|
+
debouncedValueAtom,
|
|
47
|
+
isDebouncingAtom
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
//#endregion
|
|
52
|
+
export { atomWithDebounce };
|
|
2
53
|
//# sourceMappingURL=atom-with-debounce.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atom-with-debounce.mjs","names":[
|
|
1
|
+
{"version":3,"file":"atom-with-debounce.mjs","names":[],"sources":[],"mappings":""}
|
|
@@ -1 +1,123 @@
|
|
|
1
|
-
let
|
|
1
|
+
let jotai_vanilla = require("jotai/vanilla");
|
|
2
|
+
let _stryke_helpers_is_equal = require("@stryke/helpers/is-equal");
|
|
3
|
+
|
|
4
|
+
//#region src/base/atoms/atom-with-effect.ts
|
|
5
|
+
function atomWithEffect(effect) {
|
|
6
|
+
const refreshAtom = (0, jotai_vanilla.atom)(0);
|
|
7
|
+
const refAtom = (0, jotai_vanilla.atom)(() => ({
|
|
8
|
+
inProgress: 0,
|
|
9
|
+
mounted: false,
|
|
10
|
+
promise: void 0,
|
|
11
|
+
pendingError: void 0,
|
|
12
|
+
cleanup: void 0,
|
|
13
|
+
fromCleanup: false,
|
|
14
|
+
isRecursing: false,
|
|
15
|
+
isRefreshing: false,
|
|
16
|
+
get: (() => {}),
|
|
17
|
+
set: (() => {})
|
|
18
|
+
}), (get, set) => {
|
|
19
|
+
const ref = get(refAtom);
|
|
20
|
+
Object.assign(ref, {
|
|
21
|
+
mounted: true,
|
|
22
|
+
get,
|
|
23
|
+
set
|
|
24
|
+
});
|
|
25
|
+
set(refreshAtom, (c) => c + 1);
|
|
26
|
+
return () => {
|
|
27
|
+
ref.mounted = false;
|
|
28
|
+
cleanup(ref);
|
|
29
|
+
throwPendingError(ref);
|
|
30
|
+
};
|
|
31
|
+
});
|
|
32
|
+
refAtom.onMount = (mount) => mount();
|
|
33
|
+
const baseAtom = (0, jotai_vanilla.atom)(async (get) => {
|
|
34
|
+
get(refreshAtom);
|
|
35
|
+
const ref = get(refAtom);
|
|
36
|
+
if (!ref.mounted || ref.isRecursing || ref.inProgress && !ref.isRefreshing) return ref.promise;
|
|
37
|
+
throwPendingError(ref);
|
|
38
|
+
const currDeps = /* @__PURE__ */ new Map();
|
|
39
|
+
const getter = (a) => {
|
|
40
|
+
const value = get(a);
|
|
41
|
+
currDeps.set(a, value);
|
|
42
|
+
return value;
|
|
43
|
+
};
|
|
44
|
+
getter.peek = (anAtom) => ref.get(anAtom);
|
|
45
|
+
const setter = (...args) => {
|
|
46
|
+
try {
|
|
47
|
+
++ref.inProgress;
|
|
48
|
+
return ref.set(...args);
|
|
49
|
+
} finally {
|
|
50
|
+
Array.from(currDeps.keys(), get);
|
|
51
|
+
--ref.inProgress;
|
|
52
|
+
}
|
|
53
|
+
};
|
|
54
|
+
setter.recurse = (anAtom, ...args) => {
|
|
55
|
+
if (ref.fromCleanup) {
|
|
56
|
+
if (process.env.NODE_ENV !== "production") throw new Error("set.recurse is not allowed in cleanup");
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
try {
|
|
60
|
+
ref.isRecursing = true;
|
|
61
|
+
return ref.set(anAtom, ...args);
|
|
62
|
+
} finally {
|
|
63
|
+
ref.isRecursing = false;
|
|
64
|
+
if (Array.from(currDeps).some(([atom, value]) => !(0, _stryke_helpers_is_equal.isEqual)(get(atom), value))) refresh(ref);
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
++ref.inProgress;
|
|
68
|
+
function runEffect() {
|
|
69
|
+
try {
|
|
70
|
+
ref.isRefreshing = false;
|
|
71
|
+
if (!ref.mounted) return;
|
|
72
|
+
cleanup(ref);
|
|
73
|
+
ref.cleanup = effect(getter, setter);
|
|
74
|
+
} catch (error) {
|
|
75
|
+
ref.pendingError = error;
|
|
76
|
+
refresh(ref);
|
|
77
|
+
} finally {
|
|
78
|
+
ref.promise = void 0;
|
|
79
|
+
--ref.inProgress;
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
return ref.isRefreshing ? runEffect() : ref.promise = Promise.resolve().then(runEffect);
|
|
83
|
+
});
|
|
84
|
+
if (process.env.NODE_ENV !== "production") {
|
|
85
|
+
function setLabel(atom, label) {
|
|
86
|
+
Object.defineProperty(atom, "debugLabel", { get: () => `${effectAtom.debugLabel ?? "effect"}:${label}` });
|
|
87
|
+
atom.debugPrivate = true;
|
|
88
|
+
}
|
|
89
|
+
setLabel(refreshAtom, "refresh");
|
|
90
|
+
setLabel(refAtom, "ref");
|
|
91
|
+
setLabel(baseAtom, "base");
|
|
92
|
+
}
|
|
93
|
+
const effectAtom = (0, jotai_vanilla.atom)((get) => void get(baseAtom));
|
|
94
|
+
return effectAtom;
|
|
95
|
+
function refresh(ref) {
|
|
96
|
+
try {
|
|
97
|
+
ref.isRefreshing = true;
|
|
98
|
+
ref.set(refreshAtom, (c) => c + 1);
|
|
99
|
+
} finally {
|
|
100
|
+
ref.isRefreshing = false;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
function cleanup(ref) {
|
|
104
|
+
if (!ref.cleanup) return;
|
|
105
|
+
try {
|
|
106
|
+
ref.fromCleanup = true;
|
|
107
|
+
ref.cleanup();
|
|
108
|
+
} finally {
|
|
109
|
+
ref.fromCleanup = false;
|
|
110
|
+
ref.cleanup = void 0;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
function throwPendingError(ref) {
|
|
114
|
+
if ("e" in ref) {
|
|
115
|
+
const error = ref.pendingError;
|
|
116
|
+
delete ref.pendingError;
|
|
117
|
+
throw error;
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
//#endregion
|
|
123
|
+
exports.atomWithEffect = atomWithEffect;
|
|
@@ -1,2 +1,121 @@
|
|
|
1
|
-
import{atom
|
|
1
|
+
import { atom } from "jotai/vanilla";
|
|
2
|
+
import { isEqual } from "@stryke/helpers/is-equal";
|
|
3
|
+
|
|
4
|
+
//#region src/base/atoms/atom-with-effect.ts
|
|
5
|
+
function atomWithEffect(effect) {
|
|
6
|
+
const refreshAtom = atom(0);
|
|
7
|
+
const refAtom = atom(() => ({
|
|
8
|
+
inProgress: 0,
|
|
9
|
+
mounted: false,
|
|
10
|
+
promise: void 0,
|
|
11
|
+
pendingError: void 0,
|
|
12
|
+
cleanup: void 0,
|
|
13
|
+
fromCleanup: false,
|
|
14
|
+
isRecursing: false,
|
|
15
|
+
isRefreshing: false,
|
|
16
|
+
get: (() => {}),
|
|
17
|
+
set: (() => {})
|
|
18
|
+
}), (get, set) => {
|
|
19
|
+
const ref = get(refAtom);
|
|
20
|
+
Object.assign(ref, {
|
|
21
|
+
mounted: true,
|
|
22
|
+
get,
|
|
23
|
+
set
|
|
24
|
+
});
|
|
25
|
+
set(refreshAtom, (c) => c + 1);
|
|
26
|
+
return () => {
|
|
27
|
+
ref.mounted = false;
|
|
28
|
+
cleanup(ref);
|
|
29
|
+
throwPendingError(ref);
|
|
30
|
+
};
|
|
31
|
+
});
|
|
32
|
+
refAtom.onMount = (mount) => mount();
|
|
33
|
+
const baseAtom = atom(async (get) => {
|
|
34
|
+
get(refreshAtom);
|
|
35
|
+
const ref = get(refAtom);
|
|
36
|
+
if (!ref.mounted || ref.isRecursing || ref.inProgress && !ref.isRefreshing) return ref.promise;
|
|
37
|
+
throwPendingError(ref);
|
|
38
|
+
const currDeps = /* @__PURE__ */ new Map();
|
|
39
|
+
const getter = (a) => {
|
|
40
|
+
const value = get(a);
|
|
41
|
+
currDeps.set(a, value);
|
|
42
|
+
return value;
|
|
43
|
+
};
|
|
44
|
+
getter.peek = (anAtom) => ref.get(anAtom);
|
|
45
|
+
const setter = (...args) => {
|
|
46
|
+
try {
|
|
47
|
+
++ref.inProgress;
|
|
48
|
+
return ref.set(...args);
|
|
49
|
+
} finally {
|
|
50
|
+
Array.from(currDeps.keys(), get);
|
|
51
|
+
--ref.inProgress;
|
|
52
|
+
}
|
|
53
|
+
};
|
|
54
|
+
setter.recurse = (anAtom, ...args) => {
|
|
55
|
+
if (ref.fromCleanup) throw new Error("set.recurse is not allowed in cleanup");
|
|
56
|
+
try {
|
|
57
|
+
ref.isRecursing = true;
|
|
58
|
+
return ref.set(anAtom, ...args);
|
|
59
|
+
} finally {
|
|
60
|
+
ref.isRecursing = false;
|
|
61
|
+
if (Array.from(currDeps).some(([atom, value]) => !isEqual(get(atom), value))) refresh(ref);
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
++ref.inProgress;
|
|
65
|
+
function runEffect() {
|
|
66
|
+
try {
|
|
67
|
+
ref.isRefreshing = false;
|
|
68
|
+
if (!ref.mounted) return;
|
|
69
|
+
cleanup(ref);
|
|
70
|
+
ref.cleanup = effect(getter, setter);
|
|
71
|
+
} catch (error) {
|
|
72
|
+
ref.pendingError = error;
|
|
73
|
+
refresh(ref);
|
|
74
|
+
} finally {
|
|
75
|
+
ref.promise = void 0;
|
|
76
|
+
--ref.inProgress;
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
return ref.isRefreshing ? runEffect() : ref.promise = Promise.resolve().then(runEffect);
|
|
80
|
+
});
|
|
81
|
+
{
|
|
82
|
+
function setLabel(atom, label) {
|
|
83
|
+
Object.defineProperty(atom, "debugLabel", { get: () => `${effectAtom.debugLabel ?? "effect"}:${label}` });
|
|
84
|
+
atom.debugPrivate = true;
|
|
85
|
+
}
|
|
86
|
+
setLabel(refreshAtom, "refresh");
|
|
87
|
+
setLabel(refAtom, "ref");
|
|
88
|
+
setLabel(baseAtom, "base");
|
|
89
|
+
}
|
|
90
|
+
const effectAtom = atom((get) => void get(baseAtom));
|
|
91
|
+
return effectAtom;
|
|
92
|
+
function refresh(ref) {
|
|
93
|
+
try {
|
|
94
|
+
ref.isRefreshing = true;
|
|
95
|
+
ref.set(refreshAtom, (c) => c + 1);
|
|
96
|
+
} finally {
|
|
97
|
+
ref.isRefreshing = false;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
function cleanup(ref) {
|
|
101
|
+
if (!ref.cleanup) return;
|
|
102
|
+
try {
|
|
103
|
+
ref.fromCleanup = true;
|
|
104
|
+
ref.cleanup();
|
|
105
|
+
} finally {
|
|
106
|
+
ref.fromCleanup = false;
|
|
107
|
+
ref.cleanup = void 0;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
function throwPendingError(ref) {
|
|
111
|
+
if ("e" in ref) {
|
|
112
|
+
const error = ref.pendingError;
|
|
113
|
+
delete ref.pendingError;
|
|
114
|
+
throw error;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
//#endregion
|
|
120
|
+
export { atomWithEffect };
|
|
2
121
|
//# sourceMappingURL=atom-with-effect.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atom-with-effect.mjs","names":[
|
|
1
|
+
{"version":3,"file":"atom-with-effect.mjs","names":[],"sources":[],"mappings":""}
|
|
@@ -1 +1,36 @@
|
|
|
1
|
-
const
|
|
1
|
+
const require_is_atom = require("../utilities/is-atom.cjs");
|
|
2
|
+
const require_base_atom = require("./base-atom.cjs");
|
|
3
|
+
let jotai = require("jotai");
|
|
4
|
+
let react = require("react");
|
|
5
|
+
|
|
6
|
+
//#region src/base/atoms/atom-with-listeners.ts
|
|
7
|
+
/**
|
|
8
|
+
* Creates an atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
9
|
+
*
|
|
10
|
+
* @param initialValue - The initial value of the atom
|
|
11
|
+
* @returns An atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
12
|
+
*/
|
|
13
|
+
function atomWithListeners(initialValue) {
|
|
14
|
+
const rootAtom = require_is_atom.isAtom(initialValue) ? initialValue : require_base_atom.baseAtom(initialValue);
|
|
15
|
+
const listenersAtom = require_base_atom.baseAtom([]);
|
|
16
|
+
const anAtom = require_base_atom.baseAtom((get) => get(rootAtom), (get, set, arg) => {
|
|
17
|
+
const prevVal = get(rootAtom);
|
|
18
|
+
set(rootAtom, arg);
|
|
19
|
+
const newVal = get(rootAtom);
|
|
20
|
+
for (const callback of get(listenersAtom)) callback(get, set, newVal, prevVal);
|
|
21
|
+
});
|
|
22
|
+
const useListener = (callback) => {
|
|
23
|
+
const setListeners = (0, jotai.useSetAtom)(listenersAtom);
|
|
24
|
+
(0, react.useEffect)(() => {
|
|
25
|
+
setListeners((prev) => [...prev, callback]);
|
|
26
|
+
return () => setListeners((prev) => {
|
|
27
|
+
const index = prev.indexOf(callback);
|
|
28
|
+
return [...prev.slice(0, index), ...prev.slice(index + 1)];
|
|
29
|
+
});
|
|
30
|
+
}, [setListeners, callback]);
|
|
31
|
+
};
|
|
32
|
+
return [anAtom, useListener];
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
//#endregion
|
|
36
|
+
exports.atomWithListeners = atomWithListeners;
|
|
@@ -1,2 +1,37 @@
|
|
|
1
|
-
import{isAtom
|
|
1
|
+
import { isAtom } from "../utilities/is-atom.mjs";
|
|
2
|
+
import { baseAtom } from "./base-atom.mjs";
|
|
3
|
+
import { useSetAtom } from "jotai";
|
|
4
|
+
import { useEffect } from "react";
|
|
5
|
+
|
|
6
|
+
//#region src/base/atoms/atom-with-listeners.ts
|
|
7
|
+
/**
|
|
8
|
+
* Creates an atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
9
|
+
*
|
|
10
|
+
* @param initialValue - The initial value of the atom
|
|
11
|
+
* @returns An atom that broadcasts its value to other tabs/windows using the BroadcastChannel API.
|
|
12
|
+
*/
|
|
13
|
+
function atomWithListeners(initialValue) {
|
|
14
|
+
const rootAtom = isAtom(initialValue) ? initialValue : baseAtom(initialValue);
|
|
15
|
+
const listenersAtom = baseAtom([]);
|
|
16
|
+
const anAtom = baseAtom((get) => get(rootAtom), (get, set, arg) => {
|
|
17
|
+
const prevVal = get(rootAtom);
|
|
18
|
+
set(rootAtom, arg);
|
|
19
|
+
const newVal = get(rootAtom);
|
|
20
|
+
for (const callback of get(listenersAtom)) callback(get, set, newVal, prevVal);
|
|
21
|
+
});
|
|
22
|
+
const useListener = (callback) => {
|
|
23
|
+
const setListeners = useSetAtom(listenersAtom);
|
|
24
|
+
useEffect(() => {
|
|
25
|
+
setListeners((prev) => [...prev, callback]);
|
|
26
|
+
return () => setListeners((prev) => {
|
|
27
|
+
const index = prev.indexOf(callback);
|
|
28
|
+
return [...prev.slice(0, index), ...prev.slice(index + 1)];
|
|
29
|
+
});
|
|
30
|
+
}, [setListeners, callback]);
|
|
31
|
+
};
|
|
32
|
+
return [anAtom, useListener];
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
//#endregion
|
|
36
|
+
export { atomWithListeners };
|
|
2
37
|
//# sourceMappingURL=atom-with-listeners.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"atom-with-listeners.mjs","names":[
|
|
1
|
+
{"version":3,"file":"atom-with-listeners.mjs","names":[],"sources":[],"mappings":""}
|
|
@@ -1 +1,14 @@
|
|
|
1
|
-
const
|
|
1
|
+
const require_base_atom = require("./base-atom.cjs");
|
|
2
|
+
let _stryke_helpers_noop = require("@stryke/helpers/noop");
|
|
3
|
+
|
|
4
|
+
//#region src/base/atoms/atom-with-pending.ts
|
|
5
|
+
const pendingPromise = new Promise(_stryke_helpers_noop.noop);
|
|
6
|
+
/**
|
|
7
|
+
* Creates an atom that always returns a pending promise.
|
|
8
|
+
*
|
|
9
|
+
* @returns An atom that always returns a pending promise.
|
|
10
|
+
*/
|
|
11
|
+
const atomWithPending = () => require_base_atom.baseAtom(pendingPromise);
|
|
12
|
+
|
|
13
|
+
//#endregion
|
|
14
|
+
exports.atomWithPending = atomWithPending;
|