@vuu-ui/vuu-layout 2.1.19-beta.1 → 2.1.19-beta.2

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.
Files changed (89) hide show
  1. package/package.json +12 -13
  2. package/src/Component.js +14 -0
  3. package/src/LayoutContainer.css.js +24 -0
  4. package/src/LayoutContainer.js +26 -0
  5. package/src/debug.js +16 -0
  6. package/src/dock-layout/DockLayout.css.js +36 -0
  7. package/src/dock-layout/DockLayout.js +43 -0
  8. package/src/dock-layout/Drawer.css.js +150 -0
  9. package/src/dock-layout/Drawer.js +82 -0
  10. package/src/dock-layout/index.js +2 -0
  11. package/src/drag-drop/BoxModel.js +337 -0
  12. package/src/drag-drop/DragState.js +119 -0
  13. package/src/drag-drop/Draggable.js +140 -0
  14. package/src/drag-drop/DropTarget.js +286 -0
  15. package/src/drag-drop/DropTargetRenderer.js +275 -0
  16. package/src/drag-drop/dragDropTypes.js +0 -0
  17. package/src/drag-drop/index.js +3 -0
  18. package/src/flexbox/Flexbox.css.js +45 -0
  19. package/src/flexbox/Flexbox.js +45 -0
  20. package/src/flexbox/FlexboxLayout.js +27 -0
  21. package/src/flexbox/Splitter.css.js +57 -0
  22. package/src/flexbox/Splitter.js +112 -0
  23. package/src/flexbox/flexbox-utils.js +92 -0
  24. package/src/flexbox/flexboxTypes.js +0 -0
  25. package/src/flexbox/index.js +2 -0
  26. package/src/flexbox/useSplitterResizing.js +181 -0
  27. package/src/index.js +20 -0
  28. package/src/layout-action.js +20 -0
  29. package/src/layout-header/ActionButton.js +15 -0
  30. package/src/layout-header/Header.css.js +32 -0
  31. package/src/layout-header/Header.js +99 -0
  32. package/src/layout-header/index.js +1 -0
  33. package/src/layout-header/useHeader.js +76 -0
  34. package/src/layout-provider/LayoutProvider.js +242 -0
  35. package/src/layout-provider/LayoutProviderContext.js +13 -0
  36. package/src/layout-provider/index.js +2 -0
  37. package/src/layout-provider/useLayoutDragDrop.js +147 -0
  38. package/src/layout-reducer/flexUtils.js +186 -0
  39. package/src/layout-reducer/index.js +4 -0
  40. package/src/layout-reducer/insert-layout-element.js +179 -0
  41. package/src/layout-reducer/layout-reducer.js +121 -0
  42. package/src/layout-reducer/layoutTypes.js +34 -0
  43. package/src/layout-reducer/layoutUtils.js +178 -0
  44. package/src/layout-reducer/move-layout-element.js +18 -0
  45. package/src/layout-reducer/remove-layout-element.js +161 -0
  46. package/src/layout-reducer/replace-layout-element.js +70 -0
  47. package/src/layout-reducer/resize-flex-children.js +48 -0
  48. package/src/layout-reducer/wrap-layout-element.js +134 -0
  49. package/src/layout-view/View.css.js +76 -0
  50. package/src/layout-view/View.js +116 -0
  51. package/src/layout-view/useView.js +69 -0
  52. package/src/layout-view/useViewBroadcastChannel.js +29 -0
  53. package/src/layout-view/useViewResize.js +27 -0
  54. package/src/layout-view/viewTypes.js +0 -0
  55. package/src/layout-view-actions/ViewContext.js +11 -0
  56. package/src/layout-view-actions/useViewActionDispatcher.js +116 -0
  57. package/src/layout-view-actions/useViewContributions.js +31 -0
  58. package/src/palette/Palette.css.js +31 -0
  59. package/src/palette/Palette.js +85 -0
  60. package/src/palette/index.js +1 -0
  61. package/src/placeholder/LayoutStartPanel.css.js +35 -0
  62. package/src/placeholder/LayoutStartPanel.js +57 -0
  63. package/src/placeholder/Placeholder.css.js +20 -0
  64. package/src/placeholder/Placeholder.js +33 -0
  65. package/src/placeholder/index.js +1 -0
  66. package/src/responsive/index.js +2 -0
  67. package/src/responsive/measureMinimumNodeSize.js +24 -0
  68. package/src/responsive/useResizeObserver.js +109 -0
  69. package/src/responsive/utils.js +27 -0
  70. package/src/stack/Stack.css.js +44 -0
  71. package/src/stack/Stack.js +98 -0
  72. package/src/stack/StackLayout.js +116 -0
  73. package/src/stack/index.js +3 -0
  74. package/src/stack/stackTypes.js +0 -0
  75. package/src/tabs/TabPanel.css.js +17 -0
  76. package/src/tabs/TabPanel.js +11 -0
  77. package/src/tabs/index.js +1 -0
  78. package/src/tools/config-wrapper/ConfigWrapper.js +55 -0
  79. package/src/tools/config-wrapper/index.js +1 -0
  80. package/src/tools/devtools-box/layout-configurator.css.js +113 -0
  81. package/src/tools/devtools-tree/layout-tree-viewer.css.js +17 -0
  82. package/src/tools/index.js +3 -0
  83. package/src/use-persistent-state.js +43 -0
  84. package/src/utils/index.js +5 -0
  85. package/src/utils/pathUtils.js +212 -0
  86. package/src/utils/propUtils.js +15 -0
  87. package/src/utils/refUtils.js +5 -0
  88. package/src/utils/styleUtils.js +9 -0
  89. package/src/utils/typeOf.js +15 -0
@@ -0,0 +1,44 @@
1
+ const css = `
2
+ .vuuTabs {
3
+ box-sizing: border-box;
4
+ flex-direction: column;
5
+ display: flex;
6
+ }
7
+
8
+ .vuuTabs-horizontal {
9
+ --vuu-tabs-border-style: none solid none none;
10
+ flex-direction: row;
11
+ }
12
+
13
+ .vuuTabs .Toolbar:before {
14
+ content: "";
15
+ background: var(--grey60);
16
+ width: 100%;
17
+ height: 1px;
18
+ position: absolute;
19
+ bottom: 0;
20
+ left: 0;
21
+ }
22
+
23
+ .vuuTabs-tabPanel {
24
+ flex-direction: column;
25
+ flex: 1;
26
+ display: flex;
27
+ }
28
+
29
+ .vuuTabs-tabPanel > * {
30
+ flex: auto;
31
+ }
32
+
33
+ .vuuTabHeader + .vuuView > .vuuHeader {
34
+ height: 0;
35
+ overflow: hidden;
36
+ }
37
+
38
+ .Layout-svg-button {
39
+ --spacing-medium: 5px;
40
+ }
41
+
42
+
43
+ `;
44
+ export default css;
@@ -0,0 +1,98 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { Tab, Tabstrip } from "@vuu-ui/vuu-ui-controls";
3
+ import { useId } from "@vuu-ui/vuu-utils";
4
+ import clsx from "clsx";
5
+ import { useComponentCssInjection } from "@salt-ds/styles";
6
+ import { useWindow } from "@salt-ds/window";
7
+ import react, { forwardRef, useCallback, useRef } from "react";
8
+ import { getDefaultTabLabel } from "../layout-reducer/index.js";
9
+ import Stack_0 from "./Stack.css";
10
+ const classBase = "vuuTabs";
11
+ const getDefaultTabIcon = ()=>void 0;
12
+ const getChildElements = (children)=>{
13
+ const elements = [];
14
+ react.Children.forEach(children, (child)=>{
15
+ if (/*#__PURE__*/ react.isValidElement(child)) elements.push(child);
16
+ else console.warn("Stack has unexpected child element type");
17
+ });
18
+ return elements;
19
+ };
20
+ const DefaultTabstripProps = {
21
+ allowAddTab: false,
22
+ allowCloseTab: false,
23
+ allowRenameTab: false
24
+ };
25
+ const Stack_Stack = /*#__PURE__*/ forwardRef(function({ TabstripProps = DefaultTabstripProps, active = 0, children, className: classNameProp, getTabIcon = getDefaultTabIcon, getTabLabel = getDefaultTabLabel, id: idProp, keyBoardActivation = "manual", onAddTab, onMoveTab, onTabClose, onTabEdit, onTabSelectionChanged, showTabs = "top", style }, ref) {
26
+ const targetWindow = useWindow();
27
+ useComponentCssInjection({
28
+ testId: "vuu-stack",
29
+ css: Stack_0,
30
+ window: targetWindow
31
+ });
32
+ const id = useId(idProp);
33
+ const tabLabelsRef = useRef([]);
34
+ const { allowCloseTab, allowRenameTab, className: tabstripClassName } = TabstripProps;
35
+ const handleExitEditMode = useCallback((_oldText, newText, _allowDeactivation, tabIndex)=>{
36
+ onTabEdit?.(tabIndex, newText);
37
+ }, [
38
+ onTabEdit
39
+ ]);
40
+ const activeChild = ()=>{
41
+ if (/*#__PURE__*/ react.isValidElement(children)) return children;
42
+ if (Array.isArray(children)) return children[active] ?? null;
43
+ return null;
44
+ };
45
+ tabLabelsRef.current.length = 0;
46
+ const renderTabs = ()=>getChildElements(children).map((child, idx)=>{
47
+ const { closeable = allowCloseTab, id: childId = `${id}-${idx}`, "data-tab-location": tabLocation } = child.props;
48
+ const label = getTabLabel(child, idx, tabLabelsRef.current);
49
+ tabLabelsRef.current.push(label);
50
+ return /*#__PURE__*/ jsx(Tab, {
51
+ ariaControls: childId,
52
+ "data-icon": getTabIcon(child, idx),
53
+ id: `${childId}-tab`,
54
+ index: idx,
55
+ label: label,
56
+ location: tabLocation,
57
+ closeable: closeable,
58
+ editable: allowRenameTab
59
+ }, childId);
60
+ });
61
+ const child = activeChild();
62
+ const isHorizontal = "left" === showTabs || "right" === showTabs;
63
+ const tabstripOrientation = isHorizontal ? "vertical" : "horizontal";
64
+ return /*#__PURE__*/ jsxs("div", {
65
+ className: clsx(classBase, classNameProp, {
66
+ [`${classBase}-horizontal`]: isHorizontal
67
+ }),
68
+ style: style,
69
+ id: id,
70
+ ref: ref,
71
+ children: [
72
+ showTabs ? /*#__PURE__*/ jsx(Tabstrip, {
73
+ "aria-label": "data tabs",
74
+ ...TabstripProps,
75
+ activeTabIndex: TabstripProps?.activeTabIndex ?? (null === child ? -1 : active),
76
+ allowDragDrop: false !== TabstripProps.allowDragDrop,
77
+ animateSelectionThumb: true,
78
+ className: clsx("vuuTabHeader", tabstripClassName),
79
+ keyBoardActivation: keyBoardActivation,
80
+ onActiveChange: onTabSelectionChanged,
81
+ onAddTab: onAddTab,
82
+ onCloseTab: onTabClose,
83
+ onExitEditMode: handleExitEditMode,
84
+ onMoveTab: onMoveTab,
85
+ orientation: tabstripOrientation,
86
+ children: renderTabs()
87
+ }) : null,
88
+ /*#__PURE__*/ jsx("div", {
89
+ "aria-labelledby": `${id}-${active}`,
90
+ className: `${classBase}-tabPanel`,
91
+ role: "tabpanel",
92
+ children: child
93
+ })
94
+ ]
95
+ });
96
+ });
97
+ Stack_Stack.displayName = "Stack";
98
+ export { Stack_Stack as Stack };
@@ -0,0 +1,116 @@
1
+ import { jsx } from "react/jsx-runtime";
2
+ import { registerComponent, useId } from "@vuu-ui/vuu-utils";
3
+ import react, { useCallback, useRef } from "react";
4
+ import { useLayoutCreateNewChild, useLayoutProviderDispatch } from "../layout-provider/index.js";
5
+ import { getDefaultTabLabel } from "../layout-reducer/index.js";
6
+ import { useViewActionDispatcher } from "../layout-view-actions/useViewActionDispatcher.js";
7
+ import { useViewBroadcastChannel } from "../layout-view/useViewBroadcastChannel.js";
8
+ import { usePersistentState } from "../use-persistent-state.js";
9
+ import { Stack } from "./Stack.js";
10
+ const StackLayout = (props)=>{
11
+ const rootRef = useRef(null);
12
+ const dispatch = useLayoutProviderDispatch();
13
+ const { loadState } = usePersistentState();
14
+ const { createNewChild: createNewChildProp, id: idProp, onTabSelectionChanged, path, ...restProps } = props;
15
+ const { children } = props;
16
+ const id = useId(idProp);
17
+ const sendMessage = useViewBroadcastChannel();
18
+ const [dispatchViewAction] = useViewActionDispatcher(id, rootRef, path);
19
+ const createNewChildFromContext = useLayoutCreateNewChild();
20
+ const createNewChild = createNewChildProp ?? createNewChildFromContext;
21
+ const handleTabSelection = (nextIdx)=>{
22
+ if (path) {
23
+ dispatch({
24
+ type: "switch-tab",
25
+ id,
26
+ path,
27
+ nextIdx
28
+ });
29
+ onTabSelectionChanged?.(nextIdx);
30
+ }
31
+ };
32
+ const handleTabClose = useCallback((tabIndex)=>{
33
+ if (Array.isArray(children)) {
34
+ const { props: { "data-path": dataPath, path = dataPath } } = children[tabIndex];
35
+ sendMessage({
36
+ type: "layout-closed",
37
+ path
38
+ });
39
+ setTimeout(()=>{
40
+ dispatch({
41
+ type: "remove",
42
+ path
43
+ });
44
+ }, 100);
45
+ }
46
+ }, [
47
+ children,
48
+ dispatch,
49
+ sendMessage
50
+ ]);
51
+ const handleTabAdd = useCallback(()=>{
52
+ if (path) {
53
+ const tabIndex = react.Children.count(children);
54
+ dispatch({
55
+ type: "add",
56
+ path,
57
+ component: createNewChild(tabIndex)
58
+ });
59
+ }
60
+ }, [
61
+ children,
62
+ createNewChild,
63
+ dispatch,
64
+ path
65
+ ]);
66
+ const handleMoveTab = useCallback((fromIndex, toIndex)=>{
67
+ if (path) dispatch({
68
+ fromIndex,
69
+ toIndex,
70
+ path,
71
+ type: "move-child"
72
+ });
73
+ }, [
74
+ dispatch,
75
+ path
76
+ ]);
77
+ const handleMouseDown = async (e, index)=>{
78
+ let readyToDrag;
79
+ const preDragActivity = async ()=>new Promise((resolve)=>{
80
+ console.log("preDragActivity: Ok, gonna release the drag");
81
+ readyToDrag = resolve;
82
+ });
83
+ const dragging = await dispatchViewAction({
84
+ type: "mousedown",
85
+ index,
86
+ preDragActivity
87
+ }, e);
88
+ if (dragging) readyToDrag?.(void 0);
89
+ };
90
+ const handleTabEdit = (tabIndex, text)=>{
91
+ dispatch({
92
+ type: "set-title",
93
+ path: `${path}.${tabIndex}`,
94
+ title: text
95
+ });
96
+ };
97
+ const getTabLabel = (component, idx, existingLabels)=>{
98
+ const { id, title } = component.props;
99
+ return loadState(id, "view-title") || title || getDefaultTabLabel(component, idx, existingLabels);
100
+ };
101
+ return /*#__PURE__*/ jsx(Stack, {
102
+ ...restProps,
103
+ id: id,
104
+ getTabLabel: getTabLabel,
105
+ onMouseDown: handleMouseDown,
106
+ onMoveTab: handleMoveTab,
107
+ onAddTab: handleTabAdd,
108
+ onTabClose: handleTabClose,
109
+ onTabEdit: handleTabEdit,
110
+ onTabSelectionChanged: handleTabSelection,
111
+ ref: rootRef
112
+ });
113
+ };
114
+ StackLayout.displayName = "Stack";
115
+ registerComponent("Stack", StackLayout, "container");
116
+ export { StackLayout };
@@ -0,0 +1,3 @@
1
+ export * from "./Stack.js";
2
+ export * from "./StackLayout.js";
3
+ export * from "./stackTypes.js";
File without changes
@@ -0,0 +1,17 @@
1
+ const css = `
2
+ .TabPanel {
3
+ flex: 1;
4
+ display: flex;
5
+ }
6
+
7
+ .TabPanel > * {
8
+ height: 100%;
9
+ }
10
+
11
+ .TabPanel > .View > .Header {
12
+ display: none;
13
+ }
14
+
15
+
16
+ `;
17
+ export default css;
@@ -0,0 +1,11 @@
1
+ import { jsx } from "react/jsx-runtime";
2
+ import "./TabPanel.css";
3
+ const TabPanel = ({ ariaLabelledBy, children, id })=>/*#__PURE__*/ jsx("div", {
4
+ className: "TabPanel",
5
+ id: id,
6
+ role: "tabpanel",
7
+ "aria-labelledby": ariaLabelledBy,
8
+ children: children
9
+ });
10
+ var tabs_TabPanel = TabPanel;
11
+ export default tabs_TabPanel;
@@ -0,0 +1 @@
1
+ export { default as TabPanel } from "./TabPanel.js";
@@ -0,0 +1,55 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import react, { useState } from "react";
3
+ import { LayoutConfigurator, LayoutTreeViewer } from "../index.js";
4
+ import { followPathToComponent } from "../../index.js";
5
+ const ConfigWrapper = ({ children })=>{
6
+ const designMode = false;
7
+ const [layout, setLayout] = useState(children);
8
+ const [selectedComponent, setSelectedComponent] = useState(children);
9
+ const handleSelection = (selectedPath)=>{
10
+ const targetComponent = followPathToComponent(layout, selectedPath);
11
+ setSelectedComponent(targetComponent);
12
+ };
13
+ const handleChange = (property, value)=>{
14
+ console.log(`change ${property} -> ${value}`);
15
+ const newComponent = /*#__PURE__*/ react.cloneElement(selectedComponent, {
16
+ style: {
17
+ ...selectedComponent.props.style,
18
+ [property]: value
19
+ }
20
+ });
21
+ setSelectedComponent(newComponent);
22
+ setLayout(/*#__PURE__*/ react.cloneElement(layout, {}, newComponent));
23
+ };
24
+ return /*#__PURE__*/ jsxs("div", {
25
+ "data-design-mode": `${designMode}`,
26
+ children: [
27
+ layout,
28
+ /*#__PURE__*/ jsx("br", {}),
29
+ /*#__PURE__*/ jsxs("div", {
30
+ style: {
31
+ display: "flex"
32
+ },
33
+ children: [
34
+ /*#__PURE__*/ jsx(LayoutConfigurator, {
35
+ height: 300,
36
+ managedStyle: selectedComponent.props.style,
37
+ width: 300,
38
+ onChange: handleChange,
39
+ style: void 0
40
+ }),
41
+ /*#__PURE__*/ jsx(LayoutTreeViewer, {
42
+ layout: layout,
43
+ onSelect: handleSelection,
44
+ style: {
45
+ width: 300,
46
+ height: 300,
47
+ backgroundColor: "#ccc"
48
+ }
49
+ })
50
+ ]
51
+ })
52
+ ]
53
+ });
54
+ };
55
+ export { ConfigWrapper };
@@ -0,0 +1 @@
1
+ export * from "./ConfigWrapper.js";
@@ -0,0 +1,113 @@
1
+ const css = `
2
+ [data-design-mode="true"] .Component {
3
+ filter: grayscale();
4
+ opacity: .4;
5
+ }
6
+
7
+ [data-design-mode="true"] .Component:after {
8
+ color: #000;
9
+ content: "Component";
10
+ background-color: #ff0;
11
+ height: 12px;
12
+ }
13
+
14
+ .LayoutConfigurator {
15
+ --margin-color: #f3cea5;
16
+ --border-color: #fddda0;
17
+ --padding-color: #c6d092;
18
+ --content-color: #8cb6c0;
19
+ background-color: var(--margin-color);
20
+ flex-direction: column;
21
+ align-items: stretch;
22
+ display: flex;
23
+ }
24
+
25
+ .LayoutConfigurator .layout-outer {
26
+ flex-direction: column;
27
+ flex: auto;
28
+ align-items: stretch;
29
+ display: flex;
30
+ }
31
+
32
+ .LayoutBox {
33
+ --hw-control-font-size: 13px;
34
+ --hw-text-input-bg: #ffffff4d;
35
+ --hwTextInput-padding: 3px;
36
+ --hw-text-input-position: absolute;
37
+ --hwTextInput-width: 30px;
38
+ flex: auto;
39
+ }
40
+
41
+ .LayoutBox > .layout-top {
42
+ flex-direction: row;
43
+ flex: 0 0 40px;
44
+ align-items: center;
45
+ padding-left: 12px;
46
+ display: flex;
47
+ position: relative;
48
+ }
49
+
50
+ .LayoutBox > .layout-bottom {
51
+ flex-direction: row;
52
+ flex: 0 0 40px;
53
+ align-items: center;
54
+ display: flex;
55
+ position: relative;
56
+ }
57
+
58
+ .LayoutBox > .layout-inner > .layout-right, .LayoutBox > .layout-inner > .layout-left {
59
+ flex-direction: column;
60
+ flex: 0 0 40px;
61
+ justify-content: center;
62
+ align-items: center;
63
+ display: flex;
64
+ }
65
+
66
+ .layout-top, .layout-bottom {
67
+ --hw-text-input-margin: 0 0 0 -15px;
68
+ }
69
+
70
+ .layout-top > .layout-input, .layout-bottom > .layout-input {
71
+ left: 50%;
72
+ }
73
+
74
+ .LayoutBox > .layout-inner {
75
+ flex-direction: row;
76
+ flex: auto;
77
+ align-items: stretch;
78
+ display: flex;
79
+ }
80
+
81
+ .LayoutBox.layout-margin {
82
+ background-color: var(--margin-color);
83
+ border: 2px dashed #000;
84
+ }
85
+
86
+ .LayoutBox.layout-border {
87
+ background-color: var(--border-color);
88
+ border: 2px solid #000;
89
+ }
90
+
91
+ .LayoutBox.layout-padding {
92
+ background-color: var(--padding-color);
93
+ border: 2px dashed #000;
94
+ }
95
+
96
+ .LayoutBox .layout-content {
97
+ background-color: var(--content-color);
98
+ border: 2px solid gray;
99
+ flex: auto;
100
+ }
101
+
102
+ .LayoutBox .layout-title {
103
+ color: #161616;
104
+ font-size: 11px;
105
+ line-height: 15px;
106
+ position: absolute;
107
+ top: 1px;
108
+ left: 4px;
109
+ }
110
+
111
+
112
+ `;
113
+ export default css;
@@ -0,0 +1,17 @@
1
+ const css = `
2
+ .hwLayoutTreeNode {
3
+ cursor: default;
4
+ }
5
+
6
+ .hwLayoutTreeNode:hover {
7
+ background-color: #fff3;
8
+ }
9
+
10
+ .hwLayoutTreeNode[aria-selected="true"] {
11
+ color: #fff;
12
+ background-color: #6495ed;
13
+ }
14
+
15
+
16
+ `;
17
+ export default css;
@@ -0,0 +1,3 @@
1
+ export * from "./config-wrapper/index.js";
2
+ export * from "./devtools-box/layout-configurator.js";
3
+ export * from "./devtools-tree/layout-tree-viewer.js";
@@ -0,0 +1,43 @@
1
+ import { useCallback } from "react";
2
+ const persistentState = new Map();
3
+ const getPersistentState = (id)=>persistentState.get(id);
4
+ const hasPersistentState = (id)=>persistentState.has(id);
5
+ const setPersistentState = (id, value)=>persistentState.set(id, value);
6
+ const usePersistentState = ()=>{
7
+ const loadState = useCallback((id, key)=>{
8
+ const state = persistentState.get(id);
9
+ if (state) {
10
+ if (void 0 !== key) return state[key];
11
+ return state;
12
+ }
13
+ }, []);
14
+ const saveState = useCallback((id, key, data)=>{
15
+ if (void 0 === key) persistentState.set(id, data);
16
+ else if (persistentState.has(id)) {
17
+ const state = persistentState.get(id);
18
+ persistentState.set(id, {
19
+ ...state,
20
+ [key]: data
21
+ });
22
+ } else persistentState.set(id, {
23
+ [key]: data
24
+ });
25
+ }, []);
26
+ const purgeState = useCallback((id, key)=>{
27
+ if (persistentState.has(id)) if (void 0 === key) persistentState.delete(id);
28
+ else {
29
+ const state = persistentState.get(id);
30
+ if (state[key]) {
31
+ const { [key]: _doomedState, ...rest } = persistentState.get(id);
32
+ if (Object.keys(rest).length > 0) persistentState.set(id, rest);
33
+ else persistentState.delete(id);
34
+ }
35
+ }
36
+ }, []);
37
+ return {
38
+ loadState,
39
+ saveState,
40
+ purgeState
41
+ };
42
+ };
43
+ export { getPersistentState, hasPersistentState, setPersistentState, usePersistentState };
@@ -0,0 +1,5 @@
1
+ export * from "./pathUtils.js";
2
+ export * from "./propUtils.js";
3
+ export * from "./refUtils.js";
4
+ export * from "./styleUtils.js";
5
+ export * from "./typeOf.js";