@finsweet/webflow-apps-utils 1.0.1 → 1.0.3
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 +162 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/providers/GlobalProvider.mdx +322 -0
- package/dist/providers/GlobalProvider.svelte +58 -0
- package/dist/providers/GlobalProvider.svelte.d.ts +4 -0
- package/dist/providers/configuratorUtils.d.ts +37 -0
- package/dist/providers/configuratorUtils.js +219 -0
- package/dist/providers/globalContext.svelte.d.ts +18 -0
- package/dist/providers/globalContext.svelte.js +439 -0
- package/dist/providers/index.d.ts +5 -0
- package/dist/providers/index.js +7 -0
- package/dist/providers/types.d.ts +103 -0
- package/dist/providers/types.js +6 -0
- package/dist/router/README.md +2 -2
- package/dist/stores/index.d.ts +0 -1
- package/dist/stores/index.js +0 -1
- package/dist/types/webflow.d.ts +31 -47
- package/dist/ui/components/LoadingScreen.svelte +2 -1
- package/dist/ui/components/button/Button.svelte +4 -1
- package/dist/ui/components/button-group/ButtonGroup.stories.js +112 -0
- package/dist/ui/components/{ButtonGroup.svelte → button-group/ButtonGroup.svelte} +20 -33
- package/dist/ui/components/button-group/ButtonGroup.svelte.d.ts +13 -0
- package/dist/ui/components/button-group/index.d.ts +2 -0
- package/dist/ui/components/button-group/index.js +1 -0
- package/dist/ui/components/button-group/types.d.ts +32 -0
- package/dist/ui/components/checkbox/Checkbox.stories.d.ts +55 -0
- package/dist/ui/components/checkbox/Checkbox.stories.js +162 -0
- package/dist/ui/components/checkbox/Checkbox.svelte +141 -0
- package/dist/ui/components/checkbox/Checkbox.svelte.d.ts +4 -0
- package/dist/ui/components/checkbox/index.d.ts +2 -0
- package/dist/ui/components/checkbox/index.js +1 -0
- package/dist/ui/components/checkbox/types.d.ts +32 -0
- package/dist/ui/components/controlled-buttons/ControlledButtons.stories.d.ts +32 -0
- package/dist/ui/components/controlled-buttons/ControlledButtons.stories.js +152 -0
- package/dist/ui/components/{buttons/FooterButton.svelte → controlled-buttons/ControlledButtons.svelte} +18 -67
- package/dist/ui/components/controlled-buttons/ControlledButtons.svelte.d.ts +4 -0
- package/dist/ui/components/controlled-buttons/index.d.ts +2 -0
- package/dist/ui/components/controlled-buttons/index.js +1 -0
- package/dist/ui/components/{buttons → controlled-buttons}/types.d.ts +11 -4
- package/dist/ui/components/divider/Divider.stories.svelte +134 -0
- package/dist/ui/components/{clickable/Clickable.stories.svelte.d.ts → divider/Divider.stories.svelte.d.ts} +4 -4
- package/dist/ui/components/divider/Divider.svelte +30 -0
- package/dist/ui/components/divider/Divider.svelte.d.ts +4 -0
- package/dist/ui/components/divider/index.d.ts +2 -0
- package/dist/ui/components/divider/index.js +1 -0
- package/dist/ui/components/divider/types.d.ts +23 -0
- package/dist/ui/components/divider/types.js +1 -0
- package/dist/ui/components/iframe/Iframe.stories.svelte +122 -0
- package/dist/ui/components/{ToggleItem.svelte.d.ts → iframe/Iframe.stories.svelte.d.ts} +7 -8
- package/dist/ui/components/iframe/Iframe.svelte +75 -0
- package/dist/ui/components/iframe/Iframe.svelte.d.ts +4 -0
- package/dist/ui/components/iframe/index.d.ts +2 -0
- package/dist/ui/components/iframe/index.js +1 -0
- package/dist/ui/components/iframe/types.d.ts +38 -0
- package/dist/ui/components/iframe/types.js +1 -0
- package/dist/ui/components/index.d.ts +12 -39
- package/dist/ui/components/index.js +12 -39
- package/dist/ui/components/input/Input.stories.d.ts +24 -0
- package/dist/ui/components/input/Input.stories.js +98 -0
- package/dist/ui/components/input/Input.svelte +321 -80
- package/dist/ui/components/input/types.d.ts +27 -1
- package/dist/ui/components/layout/Layout.stories.svelte +3 -3
- package/dist/ui/components/layout/Layout.svelte +3 -5
- package/dist/ui/components/layout/common/EditModeMessage.svelte +24 -12
- package/dist/ui/components/layout/{ExampleLayout.svelte → examples/ExampleLayout.svelte} +34 -22
- package/dist/ui/components/layout/examples/Wrapper.svelte +9 -0
- package/dist/ui/components/{NoSettingsNeeded.svelte.d.ts → layout/examples/Wrapper.svelte.d.ts} +3 -3
- package/dist/ui/components/layout/examples/index.d.ts +2 -0
- package/dist/ui/components/layout/examples/index.js +2 -0
- package/dist/ui/components/layout/index.d.ts +2 -1
- package/dist/ui/components/layout/index.js +2 -1
- package/dist/ui/components/modal/Example.svelte +320 -0
- package/dist/ui/components/modal/Example.svelte.d.ts +3 -0
- package/dist/ui/components/modal/Modal.stories.svelte +18 -0
- package/dist/ui/components/modal/Modal.stories.svelte.d.ts +26 -0
- package/dist/ui/components/modal/Modal.svelte +490 -0
- package/dist/ui/components/modal/Modal.svelte.d.ts +130 -0
- package/dist/ui/components/modal/index.d.ts +2 -0
- package/dist/ui/components/modal/index.js +1 -0
- package/dist/ui/components/modal/types.d.ts +75 -0
- package/dist/ui/components/modal/types.js +1 -0
- package/dist/ui/components/notification/Notification.stories.svelte +228 -0
- package/dist/ui/components/{ToggleList.svelte.d.ts → notification/Notification.stories.svelte.d.ts} +9 -21
- package/dist/ui/components/notification/Notification.svelte +289 -0
- package/dist/ui/components/notification/Notification.svelte.d.ts +67 -0
- package/dist/ui/components/notification/index.d.ts +2 -0
- package/dist/ui/components/notification/index.js +1 -0
- package/dist/ui/components/notification/types.d.ts +68 -0
- package/dist/ui/components/notification/types.js +1 -0
- package/dist/ui/components/section/Section.stories.svelte +263 -0
- package/dist/ui/components/section/Section.stories.svelte.d.ts +27 -0
- package/dist/ui/components/section/Section.svelte +324 -0
- package/dist/ui/components/section/Section.svelte.d.ts +5 -0
- package/dist/ui/components/section/index.d.ts +2 -0
- package/dist/ui/components/section/index.js +1 -0
- package/dist/ui/components/section/types.d.ts +106 -0
- package/dist/ui/components/section/types.js +1 -0
- package/dist/ui/components/{ImageUpload.svelte → shared/ImageUpload.svelte} +3 -3
- package/dist/ui/components/{SelectBodyOrDivBlock.svelte → shared/SelectBodyOrDivBlock.svelte} +1 -1
- package/dist/ui/components/shared/index.d.ts +2 -0
- package/dist/ui/components/shared/index.js +2 -0
- package/dist/ui/icons/LineChartIcon.svelte +8 -0
- package/dist/ui/icons/LineChartIcon.svelte.d.ts +26 -0
- package/dist/ui/icons/index.d.ts +2 -1
- package/dist/ui/icons/index.js +2 -1
- package/dist/ui/index.css +33 -5
- package/dist/utils/api/checkIfAppModeIsDesign.d.ts +1 -2
- package/dist/utils/api/checkIfAppModeIsDesign.js +1 -2
- package/dist/utils/api/clipboard/handlePaste.d.ts +6 -37
- package/dist/utils/api/clipboard/handlePaste.js +2 -6
- package/dist/utils/api/getAllAssets.d.ts +1 -2
- package/dist/utils/api/getAllAssets.js +1 -2
- package/dist/utils/api/getFinsweetComponentsEnvironment.d.ts +1 -2
- package/dist/utils/api/getFinsweetComponentsEnvironment.js +3 -6
- package/dist/utils/api/index.d.ts +0 -1
- package/dist/utils/api/index.js +0 -1
- package/dist/utils/api/insertWithXSCP.d.ts +1 -2
- package/dist/utils/api/insertWithXSCP.js +1 -2
- package/dist/utils/auth/crossWindowLogin.d.ts +3 -0
- package/dist/utils/auth/crossWindowLogin.js +3 -0
- package/dist/utils/auth/index.d.ts +9 -25
- package/dist/utils/auth/index.js +9 -25
- package/dist/utils/browser-storage/localStorage.d.ts +4 -12
- package/dist/utils/browser-storage/localStorage.js +4 -12
- package/dist/utils/browser-storage/sessionStorage.d.ts +4 -12
- package/dist/utils/browser-storage/sessionStorage.js +4 -12
- package/dist/utils/custom-code/api.d.ts +3 -7
- package/dist/utils/custom-code/api.js +3 -7
- package/dist/utils/helpers/cleanupTooltipMessage.d.ts +1 -2
- package/dist/utils/helpers/cleanupTooltipMessage.js +1 -2
- package/dist/utils/helpers/goto.d.ts +1 -4
- package/dist/utils/helpers/goto.js +2 -7
- package/dist/utils/helpers/index.d.ts +1 -0
- package/dist/utils/helpers/index.js +1 -0
- package/dist/utils/helpers/noop.d.ts +1 -1
- package/dist/utils/helpers/noop.js +1 -1
- package/dist/utils/helpers/numbers.d.ts +4 -14
- package/dist/utils/helpers/numbers.js +4 -14
- package/dist/utils/helpers/objectsToModuleExports.d.ts +1 -3
- package/dist/utils/helpers/objectsToModuleExports.js +1 -3
- package/dist/utils/helpers/trimText.d.ts +1 -8
- package/dist/utils/helpers/trimText.js +1 -8
- package/dist/utils/index.d.ts +4 -0
- package/dist/utils/index.js +4 -0
- package/dist/utils/logger/index.d.ts +0 -2
- package/dist/utils/logger/index.js +0 -2
- package/dist/utils/webflow-canvas/attributes/getAllWebflowElementAttributes.d.ts +1 -3
- package/dist/utils/webflow-canvas/attributes/getAllWebflowElementAttributes.js +1 -3
- package/dist/utils/webflow-canvas/attributes/getInstanceNamesFromObject.d.ts +1 -5
- package/dist/utils/webflow-canvas/attributes/getInstanceNamesFromObject.js +1 -5
- package/dist/utils/webflow-canvas/attributes/getWebflowElementAttribute.d.ts +1 -4
- package/dist/utils/webflow-canvas/attributes/getWebflowElementAttribute.js +1 -4
- package/dist/utils/webflow-canvas/attributes/getWebflowElementTextContent.d.ts +1 -3
- package/dist/utils/webflow-canvas/attributes/getWebflowElementTextContent.js +1 -3
- package/dist/utils/webflow-canvas/attributes/removeWebflowElementAttribute.d.ts +1 -4
- package/dist/utils/webflow-canvas/attributes/removeWebflowElementAttribute.js +1 -4
- package/dist/utils/webflow-canvas/attributes/setStyles.d.ts +1 -3
- package/dist/utils/webflow-canvas/attributes/setStyles.js +1 -3
- package/dist/utils/webflow-canvas/attributes/setWebflowElementAttribute.d.ts +1 -8
- package/dist/utils/webflow-canvas/attributes/setWebflowElementAttribute.js +1 -13
- package/dist/utils/webflow-canvas/findInstanceElement.d.ts +0 -6
- package/dist/utils/webflow-canvas/findInstanceElement.js +1 -7
- package/dist/utils/webflow-canvas/getAllPages.d.ts +3 -10
- package/dist/utils/webflow-canvas/getAllPages.js +3 -10
- package/dist/utils/webflow-canvas/getSiteStagingUrl.d.ts +1 -4
- package/dist/utils/webflow-canvas/getSiteStagingUrl.js +1 -4
- package/dist/utils/webflow-canvas/index.d.ts +1 -0
- package/dist/utils/webflow-canvas/index.js +1 -0
- package/package.json +9 -2
- package/dist/stores/globalStore.d.ts +0 -10
- package/dist/stores/globalStore.js +0 -10
- package/dist/ui/components/ButtonGroup.svelte.d.ts +0 -28
- package/dist/ui/components/Checkbox.svelte +0 -94
- package/dist/ui/components/Checkbox.svelte.d.ts +0 -36
- package/dist/ui/components/Copy.svelte +0 -329
- package/dist/ui/components/Copy.svelte.d.ts +0 -35
- package/dist/ui/components/CustomModal.svelte +0 -192
- package/dist/ui/components/CustomModal.svelte.d.ts +0 -45
- package/dist/ui/components/DisableInEditMode.svelte +0 -66
- package/dist/ui/components/DisableInEditMode.svelte.d.ts +0 -33
- package/dist/ui/components/Divider.svelte +0 -31
- package/dist/ui/components/Divider.svelte.d.ts +0 -31
- package/dist/ui/components/Header.svelte +0 -30
- package/dist/ui/components/Header.svelte.d.ts +0 -20
- package/dist/ui/components/Iframe.svelte +0 -89
- package/dist/ui/components/Iframe.svelte.d.ts +0 -40
- package/dist/ui/components/InjectComponent.svelte +0 -297
- package/dist/ui/components/InjectComponent.svelte.d.ts +0 -27
- package/dist/ui/components/Modal.svelte +0 -139
- package/dist/ui/components/Modal.svelte.d.ts +0 -42
- package/dist/ui/components/Navbar.svelte +0 -132
- package/dist/ui/components/Navbar.svelte.d.ts +0 -29
- package/dist/ui/components/NoSettingsNeeded.svelte +0 -31
- package/dist/ui/components/Notification.svelte +0 -193
- package/dist/ui/components/Notification.svelte.d.ts +0 -64
- package/dist/ui/components/PlusMinusButton.svelte +0 -91
- package/dist/ui/components/PlusMinusButton.svelte.d.ts +0 -22
- package/dist/ui/components/PreviewBar.svelte +0 -40
- package/dist/ui/components/PreviewBar.svelte.d.ts +0 -20
- package/dist/ui/components/ScrollableContent.svelte +0 -18
- package/dist/ui/components/ScrollableContent.svelte.d.ts +0 -31
- package/dist/ui/components/Section.svelte +0 -97
- package/dist/ui/components/Section.svelte.d.ts +0 -50
- package/dist/ui/components/Spacer.svelte +0 -9
- package/dist/ui/components/Spacer.svelte.d.ts +0 -22
- package/dist/ui/components/SpinnerPlusMinus.svelte +0 -75
- package/dist/ui/components/SpinnerPlusMinus.svelte.d.ts +0 -23
- package/dist/ui/components/SpinnerUpDown.svelte +0 -194
- package/dist/ui/components/SpinnerUpDown.svelte.d.ts +0 -31
- package/dist/ui/components/Tabs.svelte +0 -71
- package/dist/ui/components/Tabs.svelte.d.ts +0 -26
- package/dist/ui/components/ToggleItem.svelte +0 -29
- package/dist/ui/components/ToggleList.svelte +0 -57
- package/dist/ui/components/buttons/FooterButton.svelte.d.ts +0 -10
- package/dist/ui/components/buttons/index.d.ts +0 -5
- package/dist/ui/components/buttons/index.js +0 -5
- package/dist/ui/components/clickable/Clickable.stories.svelte +0 -213
- package/dist/ui/components/clickable/Clickable.svelte +0 -93
- package/dist/ui/components/clickable/Clickable.svelte.d.ts +0 -4
- package/dist/ui/components/clickable/index.d.ts +0 -2
- package/dist/ui/components/clickable/index.js +0 -1
- package/dist/ui/components/clickable/types.d.ts +0 -17
- package/dist/utils/api/copyPaste/index.d.ts +0 -18
- /package/dist/ui/components/{buttons → button-group}/types.js +0 -0
- /package/dist/ui/components/{clickable → checkbox}/types.js +0 -0
- /package/dist/{utils/api/copyPaste/index.js → ui/components/controlled-buttons/types.js} +0 -0
- /package/dist/ui/components/layout/{ExampleLayout.svelte.d.ts → examples/ExampleLayout.svelte.d.ts} +0 -0
- /package/dist/ui/components/{ImageUpload.svelte.d.ts → shared/ImageUpload.svelte.d.ts} +0 -0
- /package/dist/ui/components/{SelectBodyOrDivBlock.svelte.d.ts → shared/SelectBodyOrDivBlock.svelte.d.ts} +0 -0
|
@@ -0,0 +1,219 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Create default configurator state
|
|
3
|
+
*/
|
|
4
|
+
export function createDefaultConfiguratorState() {
|
|
5
|
+
return {
|
|
6
|
+
configurator: null,
|
|
7
|
+
configuratorCache: null,
|
|
8
|
+
hasChanged: false,
|
|
9
|
+
watchOptions: {
|
|
10
|
+
watchAll: true,
|
|
11
|
+
watchKeys: [],
|
|
12
|
+
debounceMs: 100
|
|
13
|
+
}
|
|
14
|
+
};
|
|
15
|
+
}
|
|
16
|
+
// Cache for deep comparison results to avoid repeated expensive operations
|
|
17
|
+
const comparisonCache = new Map();
|
|
18
|
+
const CACHE_TTL = 1000;
|
|
19
|
+
/**
|
|
20
|
+
* Optimized deep compare with caching and early returns
|
|
21
|
+
*/
|
|
22
|
+
function deepEqual(obj1, obj2, maxDepth = 10) {
|
|
23
|
+
if (obj1 === obj2)
|
|
24
|
+
return true;
|
|
25
|
+
if (maxDepth <= 0)
|
|
26
|
+
return obj1 === obj2;
|
|
27
|
+
if (obj1 == null || obj2 == null)
|
|
28
|
+
return obj1 === obj2;
|
|
29
|
+
const type1 = typeof obj1;
|
|
30
|
+
const type2 = typeof obj2;
|
|
31
|
+
if (type1 !== type2)
|
|
32
|
+
return false;
|
|
33
|
+
if (type1 !== 'object')
|
|
34
|
+
return obj1 === obj2;
|
|
35
|
+
const isArray1 = Array.isArray(obj1);
|
|
36
|
+
const isArray2 = Array.isArray(obj2);
|
|
37
|
+
if (isArray1 !== isArray2)
|
|
38
|
+
return false;
|
|
39
|
+
if (isArray1) {
|
|
40
|
+
if (obj1.length !== obj2.length)
|
|
41
|
+
return false;
|
|
42
|
+
for (let i = 0; i < obj1.length; i++) {
|
|
43
|
+
if (!deepEqual(obj1[i], obj2[i], maxDepth - 1))
|
|
44
|
+
return false;
|
|
45
|
+
}
|
|
46
|
+
return true;
|
|
47
|
+
}
|
|
48
|
+
const keys1 = Object.keys(obj1);
|
|
49
|
+
const keys2 = Object.keys(obj2);
|
|
50
|
+
if (keys1.length !== keys2.length)
|
|
51
|
+
return false;
|
|
52
|
+
keys1.sort();
|
|
53
|
+
keys2.sort();
|
|
54
|
+
for (let i = 0; i < keys1.length; i++) {
|
|
55
|
+
if (keys1[i] !== keys2[i])
|
|
56
|
+
return false;
|
|
57
|
+
}
|
|
58
|
+
for (const key of keys1) {
|
|
59
|
+
if (!deepEqual(obj1[key], obj2[key], maxDepth - 1))
|
|
60
|
+
return false;
|
|
61
|
+
}
|
|
62
|
+
return true;
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Fast shallow comparison for primitive values and first-level objects
|
|
66
|
+
*/
|
|
67
|
+
function shallowCompare(obj1, obj2) {
|
|
68
|
+
if (obj1 === obj2)
|
|
69
|
+
return true;
|
|
70
|
+
if (obj1 == null || obj2 == null)
|
|
71
|
+
return obj1 === obj2;
|
|
72
|
+
if (typeof obj1 !== 'object' || typeof obj2 !== 'object')
|
|
73
|
+
return obj1 === obj2;
|
|
74
|
+
const keys1 = Object.keys(obj1);
|
|
75
|
+
const keys2 = Object.keys(obj2);
|
|
76
|
+
if (keys1.length !== keys2.length)
|
|
77
|
+
return false;
|
|
78
|
+
for (const key of keys1) {
|
|
79
|
+
if (obj1[key] !== obj2[key])
|
|
80
|
+
return false;
|
|
81
|
+
}
|
|
82
|
+
return true;
|
|
83
|
+
}
|
|
84
|
+
/**
|
|
85
|
+
* Deep compare two objects with performance optimizations
|
|
86
|
+
*/
|
|
87
|
+
export function deepCompare(obj1, obj2) {
|
|
88
|
+
if (shallowCompare(obj1, obj2))
|
|
89
|
+
return true;
|
|
90
|
+
const cacheKey = JSON.stringify([obj1, obj2]);
|
|
91
|
+
const cached = comparisonCache.get(cacheKey);
|
|
92
|
+
if (cached && Date.now() - cached.timestamp < CACHE_TTL) {
|
|
93
|
+
return cached.result;
|
|
94
|
+
}
|
|
95
|
+
const result = deepEqual(obj1, obj2, 5);
|
|
96
|
+
comparisonCache.set(cacheKey, { result, timestamp: Date.now() });
|
|
97
|
+
// Clean old cache entries periodically
|
|
98
|
+
if (comparisonCache.size > 100) {
|
|
99
|
+
const now = Date.now();
|
|
100
|
+
for (const [key, value] of comparisonCache.entries()) {
|
|
101
|
+
if (now - value.timestamp > CACHE_TTL) {
|
|
102
|
+
comparisonCache.delete(key);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
return result;
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Compare specific keys of two objects with optimization
|
|
110
|
+
*/
|
|
111
|
+
export function compareKeys(obj1, obj2, keys) {
|
|
112
|
+
if (!obj1 && !obj2)
|
|
113
|
+
return true;
|
|
114
|
+
if (!obj1 || !obj2)
|
|
115
|
+
return false;
|
|
116
|
+
if (keys.length === 0)
|
|
117
|
+
return true;
|
|
118
|
+
if (keys.length === 1) {
|
|
119
|
+
const key = keys[0];
|
|
120
|
+
return obj1[key] === obj2[key] || deepCompare(obj1[key], obj2[key]);
|
|
121
|
+
}
|
|
122
|
+
for (const key of keys) {
|
|
123
|
+
const val1 = obj1[key];
|
|
124
|
+
const val2 = obj2[key];
|
|
125
|
+
if (val1 === val2)
|
|
126
|
+
continue;
|
|
127
|
+
if (!deepCompare(val1, val2)) {
|
|
128
|
+
return false;
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
return true;
|
|
132
|
+
}
|
|
133
|
+
// Debounce storage
|
|
134
|
+
const debounceTimers = new Map();
|
|
135
|
+
/**
|
|
136
|
+
* Determine if configurator has changed with performance optimization
|
|
137
|
+
*/
|
|
138
|
+
export function hasConfiguratorChanged(configurator, configuratorCache, watchOptions) {
|
|
139
|
+
if (!configurator && !configuratorCache)
|
|
140
|
+
return false;
|
|
141
|
+
if (!configurator || !configuratorCache)
|
|
142
|
+
return true;
|
|
143
|
+
if (watchOptions.watchAll) {
|
|
144
|
+
if (shallowCompare(configurator, configuratorCache))
|
|
145
|
+
return false;
|
|
146
|
+
return !deepCompare(configurator, configuratorCache);
|
|
147
|
+
}
|
|
148
|
+
if (watchOptions.watchKeys && watchOptions.watchKeys.length > 0) {
|
|
149
|
+
return !compareKeys(configurator, configuratorCache, watchOptions.watchKeys);
|
|
150
|
+
}
|
|
151
|
+
return !shallowCompare(configurator, configuratorCache);
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Create a debounced function for configurator updates
|
|
155
|
+
*/
|
|
156
|
+
export function createDebouncedUpdate(fn, delay) {
|
|
157
|
+
const key = fn.toString();
|
|
158
|
+
return ((...args) => {
|
|
159
|
+
const existingTimer = debounceTimers.get(key);
|
|
160
|
+
if (existingTimer) {
|
|
161
|
+
clearTimeout(existingTimer);
|
|
162
|
+
}
|
|
163
|
+
const timer = setTimeout(() => {
|
|
164
|
+
debounceTimers.delete(key);
|
|
165
|
+
fn(...args);
|
|
166
|
+
}, delay);
|
|
167
|
+
debounceTimers.set(key, timer);
|
|
168
|
+
});
|
|
169
|
+
}
|
|
170
|
+
/**
|
|
171
|
+
* Extract specific keys from an object
|
|
172
|
+
*/
|
|
173
|
+
export function extractKeys(obj, keys) {
|
|
174
|
+
if (!obj || keys.length === 0)
|
|
175
|
+
return null;
|
|
176
|
+
const result = {};
|
|
177
|
+
for (const key of keys) {
|
|
178
|
+
if (key in obj) {
|
|
179
|
+
result[key] = obj[key];
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
return result;
|
|
183
|
+
}
|
|
184
|
+
/**
|
|
185
|
+
* Get all keys from an object (for watchAll mode)
|
|
186
|
+
*/
|
|
187
|
+
export function getAllKeys(obj) {
|
|
188
|
+
if (!obj)
|
|
189
|
+
return [];
|
|
190
|
+
return Object.keys(obj);
|
|
191
|
+
}
|
|
192
|
+
/**
|
|
193
|
+
* Validate watch options
|
|
194
|
+
*/
|
|
195
|
+
export function validateWatchOptions(options) {
|
|
196
|
+
const validated = {
|
|
197
|
+
watchAll: options.watchAll ?? true,
|
|
198
|
+
watchKeys: options.watchKeys ?? [],
|
|
199
|
+
debounceMs: Math.max(options.debounceMs ?? 50, 16)
|
|
200
|
+
};
|
|
201
|
+
if (!validated.watchAll && (!validated.watchKeys || validated.watchKeys.length === 0)) {
|
|
202
|
+
validated.watchAll = true;
|
|
203
|
+
}
|
|
204
|
+
return validated;
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Create a snapshot of configurator state for comparison
|
|
208
|
+
*/
|
|
209
|
+
export function createConfiguratorSnapshot(configurator, watchOptions) {
|
|
210
|
+
if (!configurator)
|
|
211
|
+
return null;
|
|
212
|
+
if (watchOptions.watchAll) {
|
|
213
|
+
return { ...configurator };
|
|
214
|
+
}
|
|
215
|
+
if (watchOptions.watchKeys && watchOptions.watchKeys.length > 0) {
|
|
216
|
+
return extractKeys(configurator, watchOptions.watchKeys);
|
|
217
|
+
}
|
|
218
|
+
return { ...configurator };
|
|
219
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { AppContextData, ConfiguratorWatchOptions, ContextOperations, DataContextData, FormContextData, GlobalContextOperations } from './types';
|
|
2
|
+
export declare function createGlobalContext(initialContexts?: Record<string, unknown>, debug?: boolean): GlobalContextOperations;
|
|
3
|
+
export declare function setGlobalContext(context: ReturnType<typeof createGlobalContext>): GlobalContextOperations;
|
|
4
|
+
export declare function getGlobalContext(): ReturnType<typeof createGlobalContext>;
|
|
5
|
+
export declare function useContext<T = unknown>(key: string): ContextOperations<T>;
|
|
6
|
+
export declare function useFormContext(): ContextOperations<FormContextData>;
|
|
7
|
+
export declare function useAppContext<TConfigurator = Record<string, unknown>>(): ContextOperations<AppContextData<TConfigurator>>;
|
|
8
|
+
export declare function useDataContext<TData = Record<string, unknown>>(): ContextOperations<DataContextData<TData>>;
|
|
9
|
+
export declare function useConfiguratorContext<TConfigurator = Record<string, unknown>>(): {
|
|
10
|
+
readonly configurator: TConfigurator | null;
|
|
11
|
+
readonly configuratorCache: TConfigurator | null;
|
|
12
|
+
readonly hasChanged: boolean;
|
|
13
|
+
readonly watchOptions: ConfiguratorWatchOptions;
|
|
14
|
+
setConfigurator(configurator: TConfigurator | null, watchOptions?: Partial<ConfiguratorWatchOptions>): void;
|
|
15
|
+
setConfiguratorCache(configuratorCache: TConfigurator | null): void;
|
|
16
|
+
saveToCache(): void;
|
|
17
|
+
updateWatchOptions(watchOptions: Partial<ConfiguratorWatchOptions>): void;
|
|
18
|
+
};
|
|
@@ -0,0 +1,439 @@
|
|
|
1
|
+
import { getContext, setContext } from 'svelte';
|
|
2
|
+
import { createDebouncedUpdate, hasConfiguratorChanged, validateWatchOptions } from './configuratorUtils';
|
|
3
|
+
const GLOBAL_CONTEXT_KEY = Symbol('global-context');
|
|
4
|
+
export function createGlobalContext(initialContexts = {}, debug = false) {
|
|
5
|
+
// Context storage
|
|
6
|
+
const contexts = $state(new Map());
|
|
7
|
+
const activeContexts = $state(new Set());
|
|
8
|
+
const eventListeners = new Map();
|
|
9
|
+
// Performance optimization: Track last configurator state to avoid unnecessary updates
|
|
10
|
+
let lastConfiguratorState = null;
|
|
11
|
+
let lastConfiguratorHash = null;
|
|
12
|
+
// Initialize contexts
|
|
13
|
+
for (const [key, value] of Object.entries(initialContexts)) {
|
|
14
|
+
contexts.set(key, {
|
|
15
|
+
data: value,
|
|
16
|
+
updatedAt: Date.now(),
|
|
17
|
+
version: 1
|
|
18
|
+
});
|
|
19
|
+
activeContexts.add(key);
|
|
20
|
+
}
|
|
21
|
+
// Debug logging with throttling
|
|
22
|
+
let debugLogCount = 0;
|
|
23
|
+
const MAX_DEBUG_LOGS = 100;
|
|
24
|
+
function debugLog(message, data) {
|
|
25
|
+
if (debug && debugLogCount < MAX_DEBUG_LOGS) {
|
|
26
|
+
console.log(`[GlobalContext] ${message}`, data);
|
|
27
|
+
debugLogCount++;
|
|
28
|
+
if (debugLogCount >= MAX_DEBUG_LOGS) {
|
|
29
|
+
setTimeout(() => {
|
|
30
|
+
debugLogCount = 0;
|
|
31
|
+
}, 5000);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
// Event emission with batching
|
|
36
|
+
const eventQueue = [];
|
|
37
|
+
let eventBatchTimeout = null;
|
|
38
|
+
function emitEvent(event) {
|
|
39
|
+
eventQueue.push(event);
|
|
40
|
+
if (!eventBatchTimeout) {
|
|
41
|
+
eventBatchTimeout = setTimeout(() => {
|
|
42
|
+
flushEventQueue();
|
|
43
|
+
eventBatchTimeout = null;
|
|
44
|
+
}, 16);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
function flushEventQueue() {
|
|
48
|
+
const events = [...eventQueue];
|
|
49
|
+
eventQueue.length = 0;
|
|
50
|
+
for (const event of events) {
|
|
51
|
+
debugLog('Event emitted', event);
|
|
52
|
+
// Emit to specific context listeners
|
|
53
|
+
if ('contextKey' in event && event.contextKey) {
|
|
54
|
+
const listeners = eventListeners.get(event.contextKey);
|
|
55
|
+
if (listeners) {
|
|
56
|
+
for (const listener of listeners) {
|
|
57
|
+
try {
|
|
58
|
+
listener(event);
|
|
59
|
+
}
|
|
60
|
+
catch (error) {
|
|
61
|
+
console.warn('Event listener error:', error);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
// Emit to global listeners
|
|
67
|
+
const globalListeners = eventListeners.get('*');
|
|
68
|
+
if (globalListeners) {
|
|
69
|
+
for (const listener of globalListeners) {
|
|
70
|
+
try {
|
|
71
|
+
listener(event);
|
|
72
|
+
}
|
|
73
|
+
catch (error) {
|
|
74
|
+
console.warn('Global event listener error:', error);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
// Helper methods for configurator handling
|
|
81
|
+
function isConfiguratorUpdate(data) {
|
|
82
|
+
return (typeof data === 'object' &&
|
|
83
|
+
data !== null &&
|
|
84
|
+
'configurator' in data &&
|
|
85
|
+
typeof data.configurator === 'object');
|
|
86
|
+
}
|
|
87
|
+
// Fast hash function for configurator state comparison
|
|
88
|
+
function hashObject(obj) {
|
|
89
|
+
if (!obj)
|
|
90
|
+
return 'null';
|
|
91
|
+
if (typeof obj !== 'object')
|
|
92
|
+
return String(obj);
|
|
93
|
+
try {
|
|
94
|
+
const str = JSON.stringify(obj, null, 0);
|
|
95
|
+
if (str.length > 1000) {
|
|
96
|
+
return (Object.keys(obj).sort().join(',') +
|
|
97
|
+
':' +
|
|
98
|
+
Object.values(obj)
|
|
99
|
+
.filter((v) => typeof v !== 'object')
|
|
100
|
+
.join(','));
|
|
101
|
+
}
|
|
102
|
+
return str;
|
|
103
|
+
}
|
|
104
|
+
catch {
|
|
105
|
+
return Object.keys(obj).sort().join(',');
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
// Debounced configurator update handler
|
|
109
|
+
const debouncedConfiguratorUpdate = createDebouncedUpdate((appData) => {
|
|
110
|
+
if (appData.configurator) {
|
|
111
|
+
// Validate and set watch options
|
|
112
|
+
appData.configurator.watchOptions = validateWatchOptions(appData.configurator.watchOptions || { watchAll: true, debounceMs: 50 });
|
|
113
|
+
// Compute hasChanged based on configurator and cache comparison
|
|
114
|
+
const hasChanged = hasConfiguratorChanged(appData.configurator.configurator, appData.configurator.configuratorCache, appData.configurator.watchOptions);
|
|
115
|
+
// Update hasChanged only if it's actually different
|
|
116
|
+
if (appData.configurator.hasChanged !== hasChanged) {
|
|
117
|
+
appData.configurator.hasChanged = hasChanged;
|
|
118
|
+
debugLog('Configurator hasChanged updated', {
|
|
119
|
+
hasChanged,
|
|
120
|
+
configurator: appData.configurator.configurator,
|
|
121
|
+
cache: appData.configurator.configuratorCache,
|
|
122
|
+
watchOptions: appData.configurator.watchOptions
|
|
123
|
+
});
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
}, 50);
|
|
127
|
+
function handleConfiguratorUpdate(newData, previousData) {
|
|
128
|
+
const appData = newData;
|
|
129
|
+
if (appData.configurator) {
|
|
130
|
+
// Quick hash check to avoid unnecessary processing
|
|
131
|
+
const currentHash = hashObject(appData.configurator.configurator);
|
|
132
|
+
if (currentHash === lastConfiguratorHash) {
|
|
133
|
+
return;
|
|
134
|
+
}
|
|
135
|
+
lastConfiguratorHash = currentHash;
|
|
136
|
+
lastConfiguratorState = appData.configurator.configurator;
|
|
137
|
+
// Use debounced update for configurator changes
|
|
138
|
+
debouncedConfiguratorUpdate(appData);
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
// Enhanced context operations with configurator support
|
|
142
|
+
function createContextOperations(key) {
|
|
143
|
+
const operations = {
|
|
144
|
+
get() {
|
|
145
|
+
const context = contexts.get(key);
|
|
146
|
+
return context?.data;
|
|
147
|
+
},
|
|
148
|
+
set(data) {
|
|
149
|
+
const currentContext = contexts.get(key);
|
|
150
|
+
const previousData = currentContext?.data;
|
|
151
|
+
const newData = previousData ? { ...previousData, ...data } : data;
|
|
152
|
+
// Handle configurator state updates with watching
|
|
153
|
+
if (key === 'app' && isConfiguratorUpdate(data)) {
|
|
154
|
+
handleConfiguratorUpdate(newData, previousData);
|
|
155
|
+
}
|
|
156
|
+
contexts.set(key, {
|
|
157
|
+
data: newData,
|
|
158
|
+
updatedAt: Date.now(),
|
|
159
|
+
version: (currentContext?.version || 0) + 1
|
|
160
|
+
});
|
|
161
|
+
activeContexts.add(key);
|
|
162
|
+
emitEvent({
|
|
163
|
+
type: 'set',
|
|
164
|
+
contextKey: key,
|
|
165
|
+
data: newData,
|
|
166
|
+
previousData,
|
|
167
|
+
timestamp: Date.now()
|
|
168
|
+
});
|
|
169
|
+
},
|
|
170
|
+
update(updater) {
|
|
171
|
+
const currentContext = contexts.get(key);
|
|
172
|
+
const previousData = currentContext?.data;
|
|
173
|
+
const newData = updater(previousData);
|
|
174
|
+
// Handle configurator state updates with watching
|
|
175
|
+
if (key === 'app' && isConfiguratorUpdate(newData)) {
|
|
176
|
+
handleConfiguratorUpdate(newData, previousData);
|
|
177
|
+
}
|
|
178
|
+
contexts.set(key, {
|
|
179
|
+
data: newData,
|
|
180
|
+
updatedAt: Date.now(),
|
|
181
|
+
version: (currentContext?.version || 0) + 1
|
|
182
|
+
});
|
|
183
|
+
activeContexts.add(key);
|
|
184
|
+
emitEvent({
|
|
185
|
+
type: 'update',
|
|
186
|
+
contextKey: key,
|
|
187
|
+
data: newData,
|
|
188
|
+
previousData,
|
|
189
|
+
timestamp: Date.now()
|
|
190
|
+
});
|
|
191
|
+
},
|
|
192
|
+
clear() {
|
|
193
|
+
const currentContext = contexts.get(key);
|
|
194
|
+
const previousData = currentContext?.data;
|
|
195
|
+
contexts.set(key, {
|
|
196
|
+
data: null,
|
|
197
|
+
updatedAt: Date.now(),
|
|
198
|
+
version: (currentContext?.version || 0) + 1
|
|
199
|
+
});
|
|
200
|
+
emitEvent({
|
|
201
|
+
type: 'clear',
|
|
202
|
+
contextKey: key,
|
|
203
|
+
data: null,
|
|
204
|
+
previousData,
|
|
205
|
+
timestamp: Date.now()
|
|
206
|
+
});
|
|
207
|
+
},
|
|
208
|
+
reset() {
|
|
209
|
+
const currentContext = contexts.get(key);
|
|
210
|
+
const previousData = currentContext?.data;
|
|
211
|
+
contexts.delete(key);
|
|
212
|
+
activeContexts.delete(key);
|
|
213
|
+
emitEvent({
|
|
214
|
+
type: 'reset',
|
|
215
|
+
contextKey: key,
|
|
216
|
+
data: null,
|
|
217
|
+
previousData,
|
|
218
|
+
timestamp: Date.now()
|
|
219
|
+
});
|
|
220
|
+
},
|
|
221
|
+
subscribe(callback) {
|
|
222
|
+
const listeners = eventListeners.get(key) || new Set();
|
|
223
|
+
const wrappedCallback = (event) => {
|
|
224
|
+
if ('contextKey' in event && event.contextKey === key) {
|
|
225
|
+
callback(event.data);
|
|
226
|
+
}
|
|
227
|
+
};
|
|
228
|
+
listeners.add(wrappedCallback);
|
|
229
|
+
eventListeners.set(key, listeners);
|
|
230
|
+
// Return unsubscribe function
|
|
231
|
+
return () => {
|
|
232
|
+
listeners.delete(wrappedCallback);
|
|
233
|
+
if (listeners.size === 0) {
|
|
234
|
+
eventListeners.delete(key);
|
|
235
|
+
}
|
|
236
|
+
};
|
|
237
|
+
}
|
|
238
|
+
};
|
|
239
|
+
return operations;
|
|
240
|
+
}
|
|
241
|
+
// Global operations
|
|
242
|
+
const globalOperations = {
|
|
243
|
+
getContext(key) {
|
|
244
|
+
return createContextOperations(key);
|
|
245
|
+
},
|
|
246
|
+
hasContext(key) {
|
|
247
|
+
return contexts.has(key);
|
|
248
|
+
},
|
|
249
|
+
removeContext(key) {
|
|
250
|
+
const currentContext = contexts.get(key);
|
|
251
|
+
const previousData = currentContext?.data;
|
|
252
|
+
contexts.delete(key);
|
|
253
|
+
activeContexts.delete(key);
|
|
254
|
+
emitEvent({
|
|
255
|
+
type: 'remove',
|
|
256
|
+
contextKey: key,
|
|
257
|
+
data: null,
|
|
258
|
+
previousData,
|
|
259
|
+
timestamp: Date.now()
|
|
260
|
+
});
|
|
261
|
+
},
|
|
262
|
+
clearAll() {
|
|
263
|
+
const previousState = this.getAllContexts();
|
|
264
|
+
for (const key of contexts.keys()) {
|
|
265
|
+
contexts.set(key, {
|
|
266
|
+
data: null,
|
|
267
|
+
updatedAt: Date.now(),
|
|
268
|
+
version: (contexts.get(key)?.version || 0) + 1
|
|
269
|
+
});
|
|
270
|
+
}
|
|
271
|
+
emitEvent({
|
|
272
|
+
type: 'clearAll',
|
|
273
|
+
data: null,
|
|
274
|
+
previousData: previousState,
|
|
275
|
+
timestamp: Date.now()
|
|
276
|
+
});
|
|
277
|
+
},
|
|
278
|
+
resetAll() {
|
|
279
|
+
const previousState = this.getAllContexts();
|
|
280
|
+
contexts.clear();
|
|
281
|
+
activeContexts.clear();
|
|
282
|
+
emitEvent({
|
|
283
|
+
type: 'resetAll',
|
|
284
|
+
data: null,
|
|
285
|
+
previousData: previousState,
|
|
286
|
+
timestamp: Date.now()
|
|
287
|
+
});
|
|
288
|
+
},
|
|
289
|
+
resetByKey(key) {
|
|
290
|
+
const operations = this.getContext(key);
|
|
291
|
+
operations.reset();
|
|
292
|
+
},
|
|
293
|
+
getActiveContexts() {
|
|
294
|
+
return Array.from(activeContexts);
|
|
295
|
+
},
|
|
296
|
+
getAllContexts() {
|
|
297
|
+
const result = {};
|
|
298
|
+
for (const [key, context] of contexts.entries()) {
|
|
299
|
+
result[key] = context.data;
|
|
300
|
+
}
|
|
301
|
+
return result;
|
|
302
|
+
},
|
|
303
|
+
getContextMetadata(key) {
|
|
304
|
+
const context = contexts.get(key);
|
|
305
|
+
if (!context)
|
|
306
|
+
return null;
|
|
307
|
+
return {
|
|
308
|
+
updatedAt: context.updatedAt,
|
|
309
|
+
version: context.version,
|
|
310
|
+
isActive: activeContexts.has(key)
|
|
311
|
+
};
|
|
312
|
+
},
|
|
313
|
+
get state() {
|
|
314
|
+
return this.getAllContexts();
|
|
315
|
+
},
|
|
316
|
+
subscribe(callback) {
|
|
317
|
+
const listeners = eventListeners.get('*') || new Set();
|
|
318
|
+
listeners.add(callback);
|
|
319
|
+
eventListeners.set('*', listeners);
|
|
320
|
+
// Return unsubscribe function
|
|
321
|
+
return () => {
|
|
322
|
+
listeners.delete(callback);
|
|
323
|
+
if (listeners.size === 0) {
|
|
324
|
+
eventListeners.delete('*');
|
|
325
|
+
}
|
|
326
|
+
};
|
|
327
|
+
}
|
|
328
|
+
};
|
|
329
|
+
return globalOperations;
|
|
330
|
+
}
|
|
331
|
+
// Context provider functions
|
|
332
|
+
export function setGlobalContext(context) {
|
|
333
|
+
setContext(GLOBAL_CONTEXT_KEY, context);
|
|
334
|
+
return context;
|
|
335
|
+
}
|
|
336
|
+
export function getGlobalContext() {
|
|
337
|
+
const context = getContext(GLOBAL_CONTEXT_KEY);
|
|
338
|
+
if (!context) {
|
|
339
|
+
throw new Error('Global context not found. Make sure to wrap your app with GlobalProvider component.');
|
|
340
|
+
}
|
|
341
|
+
return context;
|
|
342
|
+
}
|
|
343
|
+
// Convenience hooks for specific contexts
|
|
344
|
+
export function useContext(key) {
|
|
345
|
+
const globalContext = getGlobalContext();
|
|
346
|
+
return globalContext.getContext(key);
|
|
347
|
+
}
|
|
348
|
+
export function useFormContext() {
|
|
349
|
+
return useContext('form');
|
|
350
|
+
}
|
|
351
|
+
export function useAppContext() {
|
|
352
|
+
return useContext('app');
|
|
353
|
+
}
|
|
354
|
+
export function useDataContext() {
|
|
355
|
+
return useContext('data');
|
|
356
|
+
}
|
|
357
|
+
// Enhanced configurator hooks
|
|
358
|
+
export function useConfiguratorContext() {
|
|
359
|
+
const appContext = useAppContext();
|
|
360
|
+
const configuratorOps = {
|
|
361
|
+
// Computed properties
|
|
362
|
+
get configurator() {
|
|
363
|
+
const data = appContext.get();
|
|
364
|
+
return data?.configurator?.configurator || null;
|
|
365
|
+
},
|
|
366
|
+
get configuratorCache() {
|
|
367
|
+
const data = appContext.get();
|
|
368
|
+
return data?.configurator?.configuratorCache || null;
|
|
369
|
+
},
|
|
370
|
+
get hasChanged() {
|
|
371
|
+
const data = appContext.get();
|
|
372
|
+
return data?.configurator?.hasChanged || false;
|
|
373
|
+
},
|
|
374
|
+
get watchOptions() {
|
|
375
|
+
const data = appContext.get();
|
|
376
|
+
return data?.configurator?.watchOptions || { watchAll: true, debounceMs: 50 };
|
|
377
|
+
},
|
|
378
|
+
// Optimized configurator methods
|
|
379
|
+
setConfigurator(configurator, watchOptions) {
|
|
380
|
+
const currentData = appContext.get();
|
|
381
|
+
const currentConfigurator = currentData?.configurator || {
|
|
382
|
+
configurator: null,
|
|
383
|
+
configuratorCache: null,
|
|
384
|
+
hasChanged: false,
|
|
385
|
+
watchOptions: { watchAll: true, debounceMs: 50 }
|
|
386
|
+
};
|
|
387
|
+
appContext.set({
|
|
388
|
+
configurator: {
|
|
389
|
+
...currentConfigurator,
|
|
390
|
+
configurator,
|
|
391
|
+
watchOptions: validateWatchOptions({
|
|
392
|
+
...currentConfigurator.watchOptions,
|
|
393
|
+
...watchOptions
|
|
394
|
+
})
|
|
395
|
+
}
|
|
396
|
+
});
|
|
397
|
+
},
|
|
398
|
+
setConfiguratorCache(configuratorCache) {
|
|
399
|
+
const currentData = appContext.get();
|
|
400
|
+
const currentConfigurator = currentData?.configurator || {
|
|
401
|
+
configurator: null,
|
|
402
|
+
configuratorCache: null,
|
|
403
|
+
hasChanged: false,
|
|
404
|
+
watchOptions: { watchAll: true, debounceMs: 50 }
|
|
405
|
+
};
|
|
406
|
+
appContext.set({
|
|
407
|
+
configurator: {
|
|
408
|
+
...currentConfigurator,
|
|
409
|
+
configuratorCache
|
|
410
|
+
}
|
|
411
|
+
});
|
|
412
|
+
},
|
|
413
|
+
saveToCache() {
|
|
414
|
+
const current = configuratorOps.configurator;
|
|
415
|
+
if (current) {
|
|
416
|
+
configuratorOps.setConfiguratorCache(current);
|
|
417
|
+
}
|
|
418
|
+
},
|
|
419
|
+
updateWatchOptions(watchOptions) {
|
|
420
|
+
const currentData = appContext.get();
|
|
421
|
+
const currentConfigurator = currentData?.configurator || {
|
|
422
|
+
configurator: null,
|
|
423
|
+
configuratorCache: null,
|
|
424
|
+
hasChanged: false,
|
|
425
|
+
watchOptions: { watchAll: true, debounceMs: 50 }
|
|
426
|
+
};
|
|
427
|
+
appContext.set({
|
|
428
|
+
configurator: {
|
|
429
|
+
...currentConfigurator,
|
|
430
|
+
watchOptions: validateWatchOptions({
|
|
431
|
+
...currentConfigurator.watchOptions,
|
|
432
|
+
...watchOptions
|
|
433
|
+
})
|
|
434
|
+
}
|
|
435
|
+
});
|
|
436
|
+
}
|
|
437
|
+
};
|
|
438
|
+
return configuratorOps;
|
|
439
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
export { default as GlobalProvider } from './GlobalProvider.svelte';
|
|
2
|
+
export { createGlobalContext, setGlobalContext, getGlobalContext, useContext, useFormContext, useAppContext, useDataContext, useConfiguratorContext } from './globalContext.svelte.js';
|
|
3
|
+
export type { FormContextState, AppContextState, DataContextState, ContextState, GlobalContextState, ContextOperations, GlobalContextOperations, GlobalProviderProps, ContextEvent, GlobalContextEvent, ContextKey, ContextId, ConfiguratorWatchOptions, ConfiguratorState, AppContextData, FormContextData, DataContextData } from './types.js';
|
|
4
|
+
export { CONTEXT_KEYS } from './types.js';
|
|
5
|
+
export { deepCompare, compareKeys, hasConfiguratorChanged, createDebouncedUpdate, extractKeys, getAllKeys, validateWatchOptions, createConfiguratorSnapshot, createDefaultConfiguratorState } from './configuratorUtils';
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
// Main provider component
|
|
2
|
+
export { default as GlobalProvider } from './GlobalProvider.svelte';
|
|
3
|
+
// Context functions and hooks
|
|
4
|
+
export { createGlobalContext, setGlobalContext, getGlobalContext, useContext, useFormContext, useAppContext, useDataContext, useConfiguratorContext } from './globalContext.svelte.js';
|
|
5
|
+
export { CONTEXT_KEYS } from './types.js';
|
|
6
|
+
// Configurator utilities
|
|
7
|
+
export { deepCompare, compareKeys, hasConfiguratorChanged, createDebouncedUpdate, extractKeys, getAllKeys, validateWatchOptions, createConfiguratorSnapshot, createDefaultConfiguratorState } from './configuratorUtils';
|