@gem-sdk/pages 1.23.0-staging.29 → 1.23.0-staging.322
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/dist/cjs/components/builder/Toolbar.js +345 -156
- package/dist/cjs/components/builder/Toolbox.js +94 -53
- package/dist/cjs/components/builder/toolbar/Onboarding.js +110 -0
- package/dist/cjs/components/image-to-layout/AddSectionImageToLayout.js +1 -7
- package/dist/cjs/libs/api/get-home-page-props-v2.js +3 -1
- package/dist/cjs/libs/api/get-static-page-props-preview.js +3 -1
- package/dist/cjs/libs/google-fonts.js +6 -1
- package/dist/cjs/libs/helpers/gen-fonts.js +15 -4
- package/dist/cjs/pages/builder.js +43 -41
- package/dist/cjs/pages/collection-detail.js +12 -10
- package/dist/cjs/pages/product-detail.js +18 -16
- package/dist/cjs/pages/static-v2.js +14 -12
- package/dist/cjs/pages/static.js +13 -11
- package/dist/esm/components/builder/Toolbar.js +346 -157
- package/dist/esm/components/builder/Toolbox.js +95 -54
- package/dist/esm/components/builder/toolbar/Onboarding.js +106 -0
- package/dist/esm/components/image-to-layout/AddSectionImageToLayout.js +1 -7
- package/dist/esm/libs/api/get-home-page-props-v2.js +4 -2
- package/dist/esm/libs/api/get-static-page-props-preview.js +4 -2
- package/dist/esm/libs/google-fonts.js +6 -1
- package/dist/esm/libs/helpers/gen-fonts.js +15 -4
- package/dist/esm/pages/builder.js +44 -42
- package/dist/esm/pages/collection-detail.js +13 -11
- package/dist/esm/pages/product-detail.js +19 -17
- package/dist/esm/pages/static-v2.js +15 -13
- package/dist/esm/pages/static.js +14 -12
- package/dist/types/index.d.ts +1 -0
- package/package.json +2 -2
|
@@ -2,131 +2,69 @@
|
|
|
2
2
|
|
|
3
3
|
Object.defineProperty(exports, '__esModule', { value: true });
|
|
4
4
|
|
|
5
|
+
var jsxRuntime = require('react/jsx-runtime');
|
|
5
6
|
var react = require('react');
|
|
7
|
+
var Onboarding = require('./toolbar/Onboarding.js');
|
|
6
8
|
|
|
7
9
|
const TOOLBAR_HOVER_HEIGHT = 24;
|
|
8
10
|
const TOOLBAR_ACTIVE_HEIGHT = 32;
|
|
9
|
-
const
|
|
10
|
-
// Set up a parent array
|
|
11
|
-
const parents = [];
|
|
12
|
-
// Push each parent $elms to the array
|
|
13
|
-
while($el){
|
|
14
|
-
$el = $el.parentElement ?? undefined;
|
|
15
|
-
if ($el) {
|
|
16
|
-
if ($el.tagName === 'BODY' || $el.getAttribute('data-uid') === 'ROOT') {
|
|
17
|
-
break;
|
|
18
|
-
}
|
|
19
|
-
if (selector) {
|
|
20
|
-
if ($el.matches(selector)) {
|
|
21
|
-
parents.push($el);
|
|
22
|
-
if (limit && parents.length == limit) {
|
|
23
|
-
return parents;
|
|
24
|
-
}
|
|
25
|
-
}
|
|
26
|
-
continue;
|
|
27
|
-
}
|
|
28
|
-
parents.push($el);
|
|
29
|
-
if (limit && parents.length == limit) {
|
|
30
|
-
return parents;
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
// Return our parent array
|
|
35
|
-
return parents;
|
|
36
|
-
};
|
|
37
|
-
const getChildrenByAttrSelector = ($el, attrSelector)=>{
|
|
38
|
-
const childLen = $el.children.length;
|
|
39
|
-
if (childLen) {
|
|
40
|
-
for(let i = 0; i < childLen; i++){
|
|
41
|
-
const children = $el.children[i];
|
|
42
|
-
if (children) {
|
|
43
|
-
const is = children.getAttribute(attrSelector);
|
|
44
|
-
if (is) {
|
|
45
|
-
return children;
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
}
|
|
50
|
-
};
|
|
51
|
-
const isOverParent = ({ current, parent, index, revert })=>{
|
|
52
|
-
for(let i = 0; i < index; i++){
|
|
53
|
-
let is = current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent.top && current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent.top + parent.height || current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent.top + parent.height && current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent.top;
|
|
54
|
-
if (revert) {
|
|
55
|
-
is = current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent.bottom && current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent.bottom - parent.height || current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent.bottom - parent.height && current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent.bottom;
|
|
56
|
-
}
|
|
57
|
-
if (is) return true;
|
|
58
|
-
}
|
|
59
|
-
return false;
|
|
60
|
-
};
|
|
61
|
-
const waitForElementToExist = (selector, timeout = 200)=>{
|
|
62
|
-
return new Promise((resolve)=>{
|
|
63
|
-
const intervalID = setInterval(()=>{
|
|
64
|
-
const el = document.querySelector(selector);
|
|
65
|
-
if (el) {
|
|
66
|
-
clearInterval(intervalID);
|
|
67
|
-
clearTimeout(timeoutID);
|
|
68
|
-
resolve(el);
|
|
69
|
-
}
|
|
70
|
-
}, 50);
|
|
71
|
-
const timeoutID = setTimeout(()=>{
|
|
72
|
-
clearInterval(intervalID);
|
|
73
|
-
clearTimeout(timeoutID);
|
|
74
|
-
resolve(null);
|
|
75
|
-
}, timeout);
|
|
76
|
-
});
|
|
77
|
-
};
|
|
78
|
-
const notVisible = (el)=>{
|
|
79
|
-
const overflow = getComputedStyle(el).overflow;
|
|
80
|
-
return overflow !== 'visible';
|
|
81
|
-
};
|
|
82
|
-
const isSection = (el)=>{
|
|
11
|
+
const isPopup = (el)=>{
|
|
83
12
|
const tag = el.getAttribute('data-component-tag');
|
|
84
|
-
return tag === '
|
|
13
|
+
return tag === 'Dialog';
|
|
85
14
|
};
|
|
86
|
-
const
|
|
87
|
-
const
|
|
88
|
-
|
|
89
|
-
// 32px = toolbar active height
|
|
90
|
-
return rect.top - rectP.top < TOOLBAR_ACTIVE_HEIGHT + 1;
|
|
91
|
-
};
|
|
92
|
-
const findOverflowParent = (element, initEl)=>{
|
|
93
|
-
const thisEl = element;
|
|
94
|
-
const origEl = initEl || thisEl;
|
|
95
|
-
if (!thisEl) return;
|
|
96
|
-
if (isSection(thisEl)) return;
|
|
97
|
-
if (notVisible(thisEl) && isOverToolbarPosition(initEl, thisEl)) return thisEl;
|
|
98
|
-
if (thisEl.parentElement) {
|
|
99
|
-
return findOverflowParent(thisEl.parentElement, origEl);
|
|
100
|
-
} else {
|
|
101
|
-
return;
|
|
102
|
-
}
|
|
15
|
+
const isSticky = (el)=>{
|
|
16
|
+
const tag = el.getAttribute('data-component-tag');
|
|
17
|
+
return tag === 'Sticky';
|
|
103
18
|
};
|
|
104
19
|
const Toolbar = ()=>{
|
|
105
20
|
const currentComponentActive = react.useRef(null);
|
|
106
21
|
const isDragging = react.useRef(false);
|
|
107
|
-
const
|
|
22
|
+
const stopWatchReRenderComponent = react.useRef();
|
|
108
23
|
const isResizeSpacing = react.useRef(false);
|
|
24
|
+
const [isOnboarding, setIsOnboarding] = react.useState(false);
|
|
25
|
+
const [countShowOnboarding, setCountShowOnboarding] = react.useState(0);
|
|
26
|
+
const [onboardingPosition, setOnboardingPosition] = react.useState('bottom');
|
|
27
|
+
const timeoutRef = react.useRef(null);
|
|
28
|
+
const timeoutOnboarding = 5000;
|
|
109
29
|
/* Functions */ const changePositionToolbar = ({ state, $toolbar, $component })=>{
|
|
110
30
|
const $parentOverflow = findOverflowParent($component, $toolbar);
|
|
31
|
+
const rect = $toolbar.getBoundingClientRect();
|
|
32
|
+
const rectComponent = $component.getBoundingClientRect();
|
|
33
|
+
const windowWidth = window.innerWidth;
|
|
111
34
|
if ($parentOverflow) {
|
|
112
|
-
|
|
113
|
-
if (rect?.height >= 60) {
|
|
114
|
-
$toolbar.setAttribute(`data-toolbar-${state}-inside`, 'true');
|
|
115
|
-
} else {
|
|
35
|
+
if (rectComponent?.height <= 60) {
|
|
116
36
|
$toolbar.setAttribute(`data-toolbar-${state}-revert`, 'true');
|
|
37
|
+
} else {
|
|
38
|
+
$toolbar.setAttribute(`data-toolbar-${state}-inside`, 'true');
|
|
39
|
+
}
|
|
40
|
+
// fix toolbar overflow right side
|
|
41
|
+
if (rectComponent.left + rect.width > windowWidth) {
|
|
42
|
+
$toolbar.setAttribute(`data-toolbar-${state}-overflow`, 'true');
|
|
117
43
|
}
|
|
118
44
|
} else {
|
|
119
|
-
const rect = $toolbar.getBoundingClientRect();
|
|
120
45
|
if (rect.top < TOOLBAR_ACTIVE_HEIGHT + 1) {
|
|
121
|
-
if (
|
|
122
|
-
$toolbar.setAttribute(`data-toolbar-${state}-inside`, 'true');
|
|
123
|
-
} else {
|
|
46
|
+
if (rectComponent?.height <= 60) {
|
|
124
47
|
$toolbar.setAttribute(`data-toolbar-${state}-revert`, 'true');
|
|
48
|
+
} else {
|
|
49
|
+
$toolbar.setAttribute(`data-toolbar-${state}-inside`, 'true');
|
|
125
50
|
}
|
|
126
51
|
}
|
|
52
|
+
// fix toolbar overflow right side
|
|
53
|
+
if (rectComponent.left + rect.width > windowWidth) {
|
|
54
|
+
$toolbar.setAttribute(`data-toolbar-${state}-overflow`, 'true');
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
// fix Popup overflow right position
|
|
58
|
+
const popupEl = $component?.closest('[aria-label="Dialog body"]');
|
|
59
|
+
if (popupEl) {
|
|
60
|
+
const rectPopupEl = popupEl.getBoundingClientRect();
|
|
61
|
+
const popupElRightPosition = rectPopupEl.left + rectPopupEl.width - 20;
|
|
62
|
+
if (rectComponent.left + rect.width > popupElRightPosition) {
|
|
63
|
+
$toolbar.setAttribute(`data-toolbar-${state}-overflow`, 'true');
|
|
64
|
+
}
|
|
127
65
|
}
|
|
128
66
|
};
|
|
129
|
-
const setHoverComponent = react.useCallback(({ $component, componentUid, focus, isThemeSection })=>{
|
|
67
|
+
const setHoverComponent = react.useCallback(({ $component, componentUid, focus, isThemeSection, isParent })=>{
|
|
130
68
|
if (!$component && !componentUid) return;
|
|
131
69
|
if (!$component) {
|
|
132
70
|
const $c = document.querySelector(`[data-uid="${componentUid}"]`);
|
|
@@ -148,7 +86,9 @@ const Toolbar = ()=>{
|
|
|
148
86
|
}
|
|
149
87
|
if ($toolbar) {
|
|
150
88
|
$toolbar.removeAttribute('style');
|
|
151
|
-
|
|
89
|
+
if (!isParent) {
|
|
90
|
+
$toolbar.setAttribute('data-toolbar-hover', 'true');
|
|
91
|
+
}
|
|
152
92
|
if (focus) {
|
|
153
93
|
$toolbar.setAttribute('data-toolbar-hover-focus', 'true');
|
|
154
94
|
}
|
|
@@ -160,6 +100,9 @@ const Toolbar = ()=>{
|
|
|
160
100
|
}
|
|
161
101
|
if ($outline) {
|
|
162
102
|
$outline.setAttribute('data-outline-hover', 'true');
|
|
103
|
+
if (isParent) {
|
|
104
|
+
$outline.setAttribute('data-outline-parent-hover', 'true');
|
|
105
|
+
}
|
|
163
106
|
if (isThemeSection) {
|
|
164
107
|
$outline.setAttribute('data-outline-overlay-theme-section', 'true');
|
|
165
108
|
}
|
|
@@ -168,10 +111,14 @@ const Toolbar = ()=>{
|
|
|
168
111
|
}
|
|
169
112
|
}
|
|
170
113
|
if ($btnAddTop) {
|
|
171
|
-
|
|
114
|
+
if (!isParent) {
|
|
115
|
+
$btnAddTop.setAttribute('data-toolbar-add-hover', 'true');
|
|
116
|
+
}
|
|
172
117
|
}
|
|
173
118
|
if ($btnAddBottom) {
|
|
174
|
-
|
|
119
|
+
if (!isParent) {
|
|
120
|
+
$btnAddBottom.setAttribute('data-toolbar-add-hover', 'true');
|
|
121
|
+
}
|
|
175
122
|
}
|
|
176
123
|
}, []);
|
|
177
124
|
const setHoverComponentParents = react.useCallback(({ $component, componentUid })=>{
|
|
@@ -180,12 +127,13 @@ const Toolbar = ()=>{
|
|
|
180
127
|
if (!$c) return;
|
|
181
128
|
$component = $c;
|
|
182
129
|
}
|
|
183
|
-
const $parents = getDOMElementParents($component, '[data-uid][data-component-type="component"]:not([data-component-no-setting])');
|
|
130
|
+
const $parents = getDOMElementParents($component, '[data-uid][data-component-type="component"]:not([data-component-no-setting])', 1);
|
|
184
131
|
if ($parents.length) {
|
|
185
132
|
for (const $parent of $parents){
|
|
186
133
|
if ($parent) {
|
|
187
134
|
setHoverComponent({
|
|
188
|
-
$component: $parent
|
|
135
|
+
$component: $parent,
|
|
136
|
+
isParent: true
|
|
189
137
|
});
|
|
190
138
|
}
|
|
191
139
|
}
|
|
@@ -260,8 +208,11 @@ const Toolbar = ()=>{
|
|
|
260
208
|
'data-toolbar-hover',
|
|
261
209
|
'data-outline-hover-focus',
|
|
262
210
|
'data-toolbar-hover-revert',
|
|
211
|
+
'data-toolbar-hover-inside',
|
|
263
212
|
'data-outline-hover',
|
|
264
|
-
'data-toolbar-add-hover'
|
|
213
|
+
'data-toolbar-add-hover',
|
|
214
|
+
'data-outline-parent-hover',
|
|
215
|
+
'data-toolbar-hover-overflow'
|
|
265
216
|
];
|
|
266
217
|
const $elms = document.querySelectorAll(clearAttrs.map((attr)=>`[${attr}]`).join(','));
|
|
267
218
|
if ($elms) {
|
|
@@ -273,6 +224,21 @@ const Toolbar = ()=>{
|
|
|
273
224
|
}, [
|
|
274
225
|
removeHoverOverlayComponent
|
|
275
226
|
]);
|
|
227
|
+
const onCloseOnboarding = react.useCallback(()=>{
|
|
228
|
+
timeoutRef.current && clearTimeout(timeoutRef.current);
|
|
229
|
+
if (countShowOnboarding > 0) {
|
|
230
|
+
const eventCreate = new CustomEvent('editor:toolbar:close-onboarding', {
|
|
231
|
+
bubbles: true,
|
|
232
|
+
detail: {
|
|
233
|
+
close: 'close Onboarding'
|
|
234
|
+
}
|
|
235
|
+
});
|
|
236
|
+
window.dispatchEvent(eventCreate);
|
|
237
|
+
setIsOnboarding(false);
|
|
238
|
+
}
|
|
239
|
+
}, [
|
|
240
|
+
countShowOnboarding
|
|
241
|
+
]);
|
|
276
242
|
const removeActiveComponent = react.useCallback(()=>{
|
|
277
243
|
currentComponentActive.current = null;
|
|
278
244
|
const clearAttrs = [
|
|
@@ -280,9 +246,11 @@ const Toolbar = ()=>{
|
|
|
280
246
|
'data-outline-active',
|
|
281
247
|
'data-toolbar-add-active',
|
|
282
248
|
'data-toolbar-active-revert',
|
|
249
|
+
'data-toolbar-active-inside',
|
|
283
250
|
'data-spacing-margin-bottom-active',
|
|
284
251
|
'data-toolbar-force-hover',
|
|
285
|
-
'data-outline-force-hover'
|
|
252
|
+
'data-outline-force-hover',
|
|
253
|
+
'data-toolbar-active-overflow'
|
|
286
254
|
];
|
|
287
255
|
const $elms = document.querySelectorAll(clearAttrs.map((attr)=>`[${attr}]`).join(','));
|
|
288
256
|
if ($elms) {
|
|
@@ -291,25 +259,32 @@ const Toolbar = ()=>{
|
|
|
291
259
|
});
|
|
292
260
|
}
|
|
293
261
|
setFocusTextEditor(false);
|
|
294
|
-
if (
|
|
295
|
-
|
|
262
|
+
if (stopWatchReRenderComponent.current) stopWatchReRenderComponent.current();
|
|
263
|
+
onCloseOnboarding();
|
|
264
|
+
}, [
|
|
265
|
+
onCloseOnboarding
|
|
266
|
+
]);
|
|
296
267
|
const watchComponentReRender = ($el, callback)=>{
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
mutation.removedNodes.forEach((el)=>{
|
|
303
|
-
if (el === $el) {
|
|
304
|
-
if (obsActiveComponent.current) obsActiveComponent.current.disconnect();
|
|
305
|
-
callback();
|
|
306
|
-
}
|
|
307
|
-
});
|
|
268
|
+
// editor:component:render
|
|
269
|
+
const onComponentReRender = (e)=>{
|
|
270
|
+
const detail = e.detail;
|
|
271
|
+
if (detail?.componentUid == currentComponentActive.current?.componentUid) {
|
|
272
|
+
callback();
|
|
308
273
|
}
|
|
309
|
-
}
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
274
|
+
};
|
|
275
|
+
window.removeEventListener('editor:component:render', onComponentReRender);
|
|
276
|
+
window.addEventListener('editor:component:render', onComponentReRender);
|
|
277
|
+
const $images = $el.querySelectorAll('img');
|
|
278
|
+
if ($images?.length) {
|
|
279
|
+
$images.forEach(($img)=>{
|
|
280
|
+
$img.addEventListener('load', ()=>{
|
|
281
|
+
callback();
|
|
282
|
+
});
|
|
283
|
+
});
|
|
284
|
+
}
|
|
285
|
+
stopWatchReRenderComponent.current = ()=>{
|
|
286
|
+
window.removeEventListener('editor:component:render', onComponentReRender);
|
|
287
|
+
};
|
|
313
288
|
};
|
|
314
289
|
const setActiveComponentSpacing = react.useCallback(({ $component })=>{
|
|
315
290
|
if (!$component) return;
|
|
@@ -320,43 +295,96 @@ const Toolbar = ()=>{
|
|
|
320
295
|
const $bg = $marginBottom.querySelector('[data-spacing-margin-bottom-bg]') || null;
|
|
321
296
|
const $drag = $marginBottom.querySelector('[data-spacing-margin-bottom-drag]') || null;
|
|
322
297
|
if ($bg && $drag) {
|
|
323
|
-
|
|
298
|
+
let value = style.marginBottom;
|
|
299
|
+
if (parseFloat(value) < 0) {
|
|
300
|
+
value = '0';
|
|
301
|
+
}
|
|
324
302
|
$bg.style.height = value;
|
|
325
303
|
$drag.style.top = value;
|
|
326
304
|
$marginBottom.setAttribute('data-spacing-margin-bottom-active', 'true');
|
|
305
|
+
if (isLayoutElement($component)) {
|
|
306
|
+
$bg.style.left = '0';
|
|
307
|
+
} else {
|
|
308
|
+
const paddingLeft = style.paddingLeft;
|
|
309
|
+
const leftValue = `-${paddingLeft}`;
|
|
310
|
+
const translateCss = `translate(${leftValue}, -100%)`;
|
|
311
|
+
$bg.style.left = leftValue;
|
|
312
|
+
$drag.style.transform = translateCss;
|
|
313
|
+
}
|
|
327
314
|
}
|
|
328
315
|
}
|
|
329
316
|
}, []);
|
|
330
|
-
const
|
|
331
|
-
const
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
const
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
317
|
+
const calculateOnboardingPosition = ()=>{
|
|
318
|
+
const toolbar = document.querySelector('[data-toolbar-active]');
|
|
319
|
+
const toolbarOnboading = document.querySelector('[data-toolbar-onboarding]');
|
|
320
|
+
if (toolbar && toolbarOnboading) {
|
|
321
|
+
toolbarOnboading?.removeAttribute('data-onboarding-active');
|
|
322
|
+
setTimeout(()=>{
|
|
323
|
+
const rect = toolbar.getBoundingClientRect();
|
|
324
|
+
const rectTop = rect.top || 0;
|
|
325
|
+
const rectOnboading = toolbarOnboading?.getBoundingClientRect();
|
|
326
|
+
const onboardingHeight = rectOnboading?.height || 0;
|
|
327
|
+
const $iframe = parent.document.querySelector('.iframe');
|
|
328
|
+
const $iframeWin = $iframe?.contentWindow;
|
|
329
|
+
const iframeWinScrollY = $iframeWin?.scrollY || 0;
|
|
330
|
+
const iframeHeight = $iframe?.clientHeight || 0;
|
|
331
|
+
if (rectTop + onboardingHeight > iframeHeight) {
|
|
332
|
+
const oboardingTop = rect.top + iframeWinScrollY - onboardingHeight - 8;
|
|
333
|
+
toolbarOnboading?.setAttribute('style', `top: ${oboardingTop}px;left: ${rect.left}px;`);
|
|
334
|
+
setOnboardingPosition('top');
|
|
335
|
+
if ($iframeWin && oboardingTop < rect.top + iframeWinScrollY) {
|
|
336
|
+
setTimeout(()=>{
|
|
337
|
+
const toTop = oboardingTop - 20;
|
|
338
|
+
$iframeWin.scrollTo({
|
|
339
|
+
top: toTop,
|
|
340
|
+
behavior: 'smooth'
|
|
341
|
+
});
|
|
342
|
+
}, 200);
|
|
343
|
+
}
|
|
344
|
+
} else {
|
|
345
|
+
const oboardingTop = rect.top + iframeWinScrollY + rect.height + 8;
|
|
346
|
+
toolbarOnboading?.setAttribute('style', `top: ${oboardingTop}px;left: ${rect.left}px;`);
|
|
347
|
+
setOnboardingPosition('bottom');
|
|
350
348
|
}
|
|
351
|
-
|
|
349
|
+
setCountShowOnboarding((countShowOnboarding)=>countShowOnboarding + 1);
|
|
350
|
+
toolbarOnboading?.setAttribute('data-onboarding-active', 'true');
|
|
351
|
+
}, 100);
|
|
352
352
|
}
|
|
353
353
|
};
|
|
354
|
+
const setToolbarOnboarding = react.useCallback(({ $component })=>{
|
|
355
|
+
if (!$component) return;
|
|
356
|
+
if (isSection($component) || isPopup($component) || isSticky($component)) return;
|
|
357
|
+
const toolbarOnboading = document.querySelector('[data-toolbar-onboarding]');
|
|
358
|
+
// only show one time
|
|
359
|
+
if (countShowOnboarding == 0) {
|
|
360
|
+
calculateOnboardingPosition();
|
|
361
|
+
} else {
|
|
362
|
+
onCloseOnboarding();
|
|
363
|
+
toolbarOnboading?.removeAttribute('data-onboarding-active');
|
|
364
|
+
}
|
|
365
|
+
}, [
|
|
366
|
+
countShowOnboarding,
|
|
367
|
+
onCloseOnboarding
|
|
368
|
+
]);
|
|
354
369
|
const setActiveComponent = react.useCallback(async ({ componentUid, productId, timeAwait = 500, forceReActive })=>{
|
|
355
370
|
if (!componentUid) return;
|
|
356
|
-
|
|
357
|
-
|
|
371
|
+
let $component = await waitForElementToExist(`${productId ? `[data-product-id="${productId}"] ` : ''}[data-uid="${componentUid}"]`, timeAwait);
|
|
372
|
+
// check element fetch data: product, product list
|
|
373
|
+
if (!$component) {
|
|
374
|
+
const isLoading = document.querySelector(`.gp-loading-placeholder`);
|
|
375
|
+
if (!isLoading) {
|
|
376
|
+
return;
|
|
377
|
+
}
|
|
378
|
+
if (isLoading) {
|
|
379
|
+
// await element onload
|
|
380
|
+
$component = await waitForElementToExist(`${productId ? `[data-product-id="${productId}"] ` : ''}[data-uid="${componentUid}"]`, 15000);
|
|
381
|
+
}
|
|
382
|
+
}
|
|
383
|
+
if (!$component) {
|
|
384
|
+
return;
|
|
385
|
+
}
|
|
358
386
|
if (!forceReActive && componentUid == currentComponentActive.current?.componentUid && productId == currentComponentActive.current?.productId) return;
|
|
359
|
-
if (
|
|
387
|
+
if (componentUid !== currentComponentActive.current?.componentUid || productId !== currentComponentActive.current?.productId || forceReActive) removeActiveComponent();
|
|
360
388
|
const $toolbar = getChildrenByAttrSelector($component, 'data-toolbar');
|
|
361
389
|
const $outline = getChildrenByAttrSelector($component, 'data-outline');
|
|
362
390
|
const $btnAddTop = getChildrenByAttrSelector($component, 'data-toolbar-add-top');
|
|
@@ -398,7 +426,14 @@ const Toolbar = ()=>{
|
|
|
398
426
|
setActiveComponentSpacing({
|
|
399
427
|
$component
|
|
400
428
|
});
|
|
401
|
-
|
|
429
|
+
timeoutRef.current && clearTimeout(timeoutRef.current);
|
|
430
|
+
timeoutRef.current = setTimeout(()=>{
|
|
431
|
+
if ($component) {
|
|
432
|
+
setToolbarOnboarding({
|
|
433
|
+
$component
|
|
434
|
+
});
|
|
435
|
+
}
|
|
436
|
+
}, timeoutOnboarding);
|
|
402
437
|
removeHoverComponent();
|
|
403
438
|
// Reactive when component re-render
|
|
404
439
|
watchComponentReRender($component, ()=>{
|
|
@@ -412,7 +447,8 @@ const Toolbar = ()=>{
|
|
|
412
447
|
}, [
|
|
413
448
|
removeActiveComponent,
|
|
414
449
|
removeHoverComponent,
|
|
415
|
-
setActiveComponentSpacing
|
|
450
|
+
setActiveComponentSpacing,
|
|
451
|
+
setToolbarOnboarding
|
|
416
452
|
]);
|
|
417
453
|
const setFocusTextEditor = async (value)=>{
|
|
418
454
|
if (!value) {
|
|
@@ -535,7 +571,7 @@ const Toolbar = ()=>{
|
|
|
535
571
|
if (isDragging.current) return;
|
|
536
572
|
if (isResizeSpacing.current) return;
|
|
537
573
|
const $target = e.target;
|
|
538
|
-
if (!$target) {
|
|
574
|
+
if (!$target || typeof $target.closest !== 'function') {
|
|
539
575
|
removeHoverOverlayComponent();
|
|
540
576
|
return;
|
|
541
577
|
}
|
|
@@ -578,6 +614,7 @@ const Toolbar = ()=>{
|
|
|
578
614
|
if ($product) {
|
|
579
615
|
const productId = $product.getAttribute('data-product-id');
|
|
580
616
|
if (productId == currentComponentActive.current.productId) {
|
|
617
|
+
removeHoverComponent();
|
|
581
618
|
return;
|
|
582
619
|
}
|
|
583
620
|
}
|
|
@@ -677,6 +714,46 @@ const Toolbar = ()=>{
|
|
|
677
714
|
}, [
|
|
678
715
|
removeHoverComponent
|
|
679
716
|
]);
|
|
717
|
+
const setHoverParentComponent = (uid, type)=>{
|
|
718
|
+
if (!uid) return;
|
|
719
|
+
const $parentComponents = document.querySelectorAll(`[data-uid="${uid}"]`);
|
|
720
|
+
if ($parentComponents.length) {
|
|
721
|
+
$parentComponents.forEach(($parentComponent)=>{
|
|
722
|
+
const $outline = getChildrenByAttrSelector($parentComponent, 'data-outline');
|
|
723
|
+
if ($outline) {
|
|
724
|
+
if (type === 'in') {
|
|
725
|
+
$outline.setAttribute('data-outline-force-hover', 'true');
|
|
726
|
+
$outline.setAttribute('data-outline-force-overlay', 'true');
|
|
727
|
+
} else {
|
|
728
|
+
$outline.removeAttribute('data-outline-force-hover');
|
|
729
|
+
$outline.removeAttribute('data-outline-force-overlay');
|
|
730
|
+
}
|
|
731
|
+
}
|
|
732
|
+
});
|
|
733
|
+
}
|
|
734
|
+
};
|
|
735
|
+
const onHoverComponent = react.useCallback((e)=>{
|
|
736
|
+
if (isDragging.current) return;
|
|
737
|
+
const detail = e.detail;
|
|
738
|
+
if (detail?.componentUid) {
|
|
739
|
+
setHoverParentComponent(detail?.componentUid, detail?.type);
|
|
740
|
+
}
|
|
741
|
+
}, [
|
|
742
|
+
isDragging
|
|
743
|
+
]);
|
|
744
|
+
const onToolbarOnboarding = react.useCallback((e)=>{
|
|
745
|
+
const detail = e.detail;
|
|
746
|
+
if (detail?.isNewUser) {
|
|
747
|
+
setIsOnboarding(true);
|
|
748
|
+
}
|
|
749
|
+
}, []);
|
|
750
|
+
const onWindowResize = react.useCallback(()=>{
|
|
751
|
+
if (isOnboarding) {
|
|
752
|
+
calculateOnboardingPosition();
|
|
753
|
+
}
|
|
754
|
+
}, [
|
|
755
|
+
isOnboarding
|
|
756
|
+
]);
|
|
680
757
|
/* Register event */ react.useEffect(()=>{
|
|
681
758
|
document.addEventListener('mousemove', onMouseMove);
|
|
682
759
|
window.addEventListener('editor:active-component', onActiveComponent);
|
|
@@ -685,6 +762,9 @@ const Toolbar = ()=>{
|
|
|
685
762
|
window.addEventListener('editor:is-editing-text-editor', onIsEditingTextEditor);
|
|
686
763
|
window.addEventListener('editor:toolbar:show-parents', onShowParents);
|
|
687
764
|
window.addEventListener('editor:toolbar:resize-spacing', onResizeSpacing);
|
|
765
|
+
window.addEventListener('editor:hover-component', onHoverComponent);
|
|
766
|
+
window.addEventListener('editor:toolbar-onboarding', onToolbarOnboarding);
|
|
767
|
+
window.addEventListener('resize', onWindowResize);
|
|
688
768
|
return ()=>{
|
|
689
769
|
document.removeEventListener('mousemove', onMouseMove);
|
|
690
770
|
window.removeEventListener('editor:active-component', onActiveComponent);
|
|
@@ -693,6 +773,9 @@ const Toolbar = ()=>{
|
|
|
693
773
|
window.removeEventListener('editor:is-editing-text-editor', onIsEditingTextEditor);
|
|
694
774
|
window.removeEventListener('editor:toolbar:show-parents', onShowParents);
|
|
695
775
|
window.removeEventListener('editor:toolbar:resize-spacing', onResizeSpacing);
|
|
776
|
+
window.removeEventListener('editor:hover-component', onHoverComponent);
|
|
777
|
+
window.removeEventListener('editor:toolbar-onboarding', onToolbarOnboarding);
|
|
778
|
+
window.removeEventListener('resize', onWindowResize);
|
|
696
779
|
};
|
|
697
780
|
}, [
|
|
698
781
|
onMouseMove,
|
|
@@ -701,9 +784,115 @@ const Toolbar = ()=>{
|
|
|
701
784
|
onIsDragging,
|
|
702
785
|
onIsEditingTextEditor,
|
|
703
786
|
onShowParents,
|
|
704
|
-
onResizeSpacing
|
|
787
|
+
onResizeSpacing,
|
|
788
|
+
onHoverComponent,
|
|
789
|
+
onToolbarOnboarding,
|
|
790
|
+
onWindowResize
|
|
705
791
|
]);
|
|
706
|
-
return
|
|
792
|
+
return isOnboarding && /*#__PURE__*/ jsxRuntime.jsx(Onboarding.default, {
|
|
793
|
+
enable: true,
|
|
794
|
+
position: onboardingPosition,
|
|
795
|
+
onCloseOnboarding: onCloseOnboarding
|
|
796
|
+
});
|
|
797
|
+
};
|
|
798
|
+
const getDOMElementParents = ($el, selector, limit)=>{
|
|
799
|
+
// Set up a parent array
|
|
800
|
+
const parents = [];
|
|
801
|
+
// Push each parent $elms to the array
|
|
802
|
+
while($el){
|
|
803
|
+
$el = $el.parentElement ?? undefined;
|
|
804
|
+
if ($el) {
|
|
805
|
+
if ($el.tagName === 'BODY' || $el.getAttribute('data-uid') === 'ROOT') {
|
|
806
|
+
break;
|
|
807
|
+
}
|
|
808
|
+
if (selector) {
|
|
809
|
+
if ($el.matches(selector)) {
|
|
810
|
+
parents.push($el);
|
|
811
|
+
if (limit && parents.length == limit) {
|
|
812
|
+
return parents;
|
|
813
|
+
}
|
|
814
|
+
}
|
|
815
|
+
continue;
|
|
816
|
+
}
|
|
817
|
+
parents.push($el);
|
|
818
|
+
if (limit && parents.length == limit) {
|
|
819
|
+
return parents;
|
|
820
|
+
}
|
|
821
|
+
}
|
|
822
|
+
}
|
|
823
|
+
// Return our parent array
|
|
824
|
+
return parents;
|
|
825
|
+
};
|
|
826
|
+
const getChildrenByAttrSelector = ($el, attrSelector)=>{
|
|
827
|
+
const childLen = $el.children.length;
|
|
828
|
+
if (childLen) {
|
|
829
|
+
for(let i = 0; i < childLen; i++){
|
|
830
|
+
const children = $el.children[i];
|
|
831
|
+
if (children) {
|
|
832
|
+
const is = children.getAttribute(attrSelector);
|
|
833
|
+
if (is) {
|
|
834
|
+
return children;
|
|
835
|
+
}
|
|
836
|
+
}
|
|
837
|
+
}
|
|
838
|
+
}
|
|
839
|
+
};
|
|
840
|
+
const isOverParent = ({ current, parent: parent1, index, revert })=>{
|
|
841
|
+
for(let i = 0; i < index; i++){
|
|
842
|
+
let is = current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent1.top && current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent1.top + parent1.height || current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent1.top + parent1.height && current.top - (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent1.top;
|
|
843
|
+
if (revert) {
|
|
844
|
+
is = current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent1.bottom && current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent1.bottom - parent1.height || current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i >= parent1.bottom - parent1.height && current.bottom + (TOOLBAR_HOVER_HEIGHT - 1) * i <= parent1.bottom;
|
|
845
|
+
}
|
|
846
|
+
if (is) return true;
|
|
847
|
+
}
|
|
848
|
+
return false;
|
|
849
|
+
};
|
|
850
|
+
const waitForElementToExist = (selector, timeout = 200)=>{
|
|
851
|
+
return new Promise((resolve)=>{
|
|
852
|
+
const intervalID = setInterval(()=>{
|
|
853
|
+
const el = document.querySelector(selector);
|
|
854
|
+
if (el) {
|
|
855
|
+
clearInterval(intervalID);
|
|
856
|
+
clearTimeout(timeoutID);
|
|
857
|
+
resolve(el);
|
|
858
|
+
}
|
|
859
|
+
}, 50);
|
|
860
|
+
const timeoutID = setTimeout(()=>{
|
|
861
|
+
clearInterval(intervalID);
|
|
862
|
+
clearTimeout(timeoutID);
|
|
863
|
+
resolve(null);
|
|
864
|
+
}, timeout);
|
|
865
|
+
});
|
|
866
|
+
};
|
|
867
|
+
const notVisible = (el)=>{
|
|
868
|
+
const overflow = getComputedStyle(el).overflow;
|
|
869
|
+
return overflow !== 'visible';
|
|
870
|
+
};
|
|
871
|
+
const isSection = (el)=>{
|
|
872
|
+
const tag = el.getAttribute('data-component-tag');
|
|
873
|
+
return tag === 'Section';
|
|
874
|
+
};
|
|
875
|
+
const isLayoutElement = (el)=>{
|
|
876
|
+
const tag = el.getAttribute('data-component-tag');
|
|
877
|
+
return tag === 'Row' || tag === 'Product';
|
|
878
|
+
};
|
|
879
|
+
const isOverToolbarPosition = (el, parent1)=>{
|
|
880
|
+
const rect = el.getBoundingClientRect();
|
|
881
|
+
const rectP = parent1.getBoundingClientRect();
|
|
882
|
+
// 32px = toolbar active height
|
|
883
|
+
return rect.top - rectP.top < TOOLBAR_ACTIVE_HEIGHT + 1;
|
|
884
|
+
};
|
|
885
|
+
const findOverflowParent = (element, initEl)=>{
|
|
886
|
+
const thisEl = element;
|
|
887
|
+
const origEl = initEl || thisEl;
|
|
888
|
+
if (!thisEl) return;
|
|
889
|
+
if (isSection(thisEl)) return;
|
|
890
|
+
if (notVisible(thisEl) && isOverToolbarPosition(initEl, thisEl)) return thisEl;
|
|
891
|
+
if (thisEl.parentElement) {
|
|
892
|
+
return findOverflowParent(thisEl.parentElement, origEl);
|
|
893
|
+
} else {
|
|
894
|
+
return;
|
|
895
|
+
}
|
|
707
896
|
};
|
|
708
897
|
var Toolbar$1 = /*#__PURE__*/ react.memo(Toolbar);
|
|
709
898
|
|