@akinon/pz-theme 2.0.58-rc.0 → 2.0.58

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.
@@ -0,0 +1,68 @@
1
+ 'use client';
2
+
3
+ import { useEffect, useState } from 'react';
4
+
5
+ import { parseEditorMessage } from '../editor-bridge';
6
+ import { breakpointForWidth } from '../utils/breakpoints';
7
+
8
+ /**
9
+ * Which breakpoint the surrounding page is at.
10
+ *
11
+ * `ThemePlaceholderWrapper` already tracks this for the sections it renders,
12
+ * but a modal host is not inside a placeholder — it is mounted once in the
13
+ * brand's layout — so it cannot read that state and needs its own copy of the
14
+ * same rule.
15
+ *
16
+ * Two sources, exactly as the wrapper has: the viewport on a live storefront,
17
+ * and the editor's forced breakpoint in the canvas. Inside the iframe the
18
+ * viewport is the iframe's, not the device the designer picked, so the message
19
+ * wins there and the resize listener is not installed at all.
20
+ */
21
+ export const useOverlayBreakpoint = (): string => {
22
+ const [breakpoint, setBreakpoint] = useState<string>('desktop');
23
+
24
+ useEffect(() => {
25
+ if (typeof window === 'undefined') return undefined;
26
+
27
+ const inIframe = (() => {
28
+ try {
29
+ return window.self !== window.top;
30
+ } catch {
31
+ // Cross-origin parent: the access threw, which itself means embedded.
32
+ return true;
33
+ }
34
+ })();
35
+
36
+ if (inIframe) {
37
+ const handleMessage = (event: MessageEvent) => {
38
+ const message = parseEditorMessage(event);
39
+ if (message?.type !== 'CHANGE_BREAKPOINT') return;
40
+
41
+ const next = (message.data as { breakpoint?: string })?.breakpoint;
42
+ if (next) setBreakpoint(next);
43
+ };
44
+
45
+ window.addEventListener('message', handleMessage);
46
+
47
+ return () => window.removeEventListener('message', handleMessage);
48
+ }
49
+
50
+ const read = () => setBreakpoint(breakpointForWidth(window.innerWidth));
51
+
52
+ let timeoutId: ReturnType<typeof setTimeout>;
53
+ const handleResize = () => {
54
+ clearTimeout(timeoutId);
55
+ timeoutId = setTimeout(read, 200);
56
+ };
57
+
58
+ read();
59
+ window.addEventListener('resize', handleResize);
60
+
61
+ return () => {
62
+ window.removeEventListener('resize', handleResize);
63
+ clearTimeout(timeoutId);
64
+ };
65
+ }, []);
66
+
67
+ return breakpoint;
68
+ };