@cntrl-site/sdk-nextjs 0.25.0 → 0.26.1

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 (32) hide show
  1. package/cntrl-site-sdk-nextjs-0.25.1.tgz +0 -0
  2. package/lib/components/Article.js +4 -4
  3. package/lib/components/ArticleWrapper.js +2 -2
  4. package/lib/components/Item.js +8 -7
  5. package/lib/components/LayoutStyle.js +2 -2
  6. package/lib/components/LinkWrapper.js +1 -1
  7. package/lib/components/Page.js +1 -1
  8. package/lib/components/ScrollPlaybackVideo.js +46 -0
  9. package/lib/components/Section.js +4 -4
  10. package/lib/components/items/CustomItem.js +2 -2
  11. package/lib/components/items/GroupItem.js +3 -3
  12. package/lib/components/items/ImageItem.js +3 -3
  13. package/lib/components/items/RectangleItem.js +3 -3
  14. package/lib/components/items/RichTextItem.js +3 -3
  15. package/lib/components/items/VideoItem.js +16 -44
  16. package/lib/components/items/VimeoEmbed.js +4 -4
  17. package/lib/components/items/YoutubeEmbed.js +3 -3
  18. package/lib/components/useItemPosition.js +5 -1
  19. package/lib/provider/CntrlProvider.js +1 -1
  20. package/lib/utils/PlaybackVideoConverter/ScrollPlaybackVideoManager.js +221 -0
  21. package/lib/utils/PlaybackVideoConverter/VideoDecoder.js +175 -0
  22. package/lib/utils/RichTextConverter/RichTextConverter.js +4 -4
  23. package/lib/utils/Youtube/YoutubeIframeApi.js +1 -1
  24. package/package.json +6 -3
  25. package/src/components/Item.tsx +6 -4
  26. package/src/components/ScrollPlaybackVideo.tsx +56 -0
  27. package/src/components/items/VideoItem.tsx +37 -55
  28. package/src/components/useItemPosition.ts +6 -2
  29. package/src/utils/PlaybackVideoConverter/ScrollPlaybackVideoManager.ts +211 -0
  30. package/src/utils/PlaybackVideoConverter/VideoDecoder.ts +174 -0
  31. package/.idea/codeStyles/codeStyleConfig.xml +0 -5
  32. package/.idea/inspectionProfiles/Project_Default.xml +0 -15
Binary file
@@ -24,14 +24,14 @@ const Article = ({ article, sectionData }) => {
24
24
  setArticleHeight(rect.height / rect.width);
25
25
  });
26
26
  }, [articleRectObserver]);
27
- return ((0, jsx_runtime_1.jsxs)(ArticleRectContext_1.ArticleRectContext.Provider, Object.assign({ value: articleRectObserver }, { children: [(0, jsx_runtime_1.jsx)(ArticleWrapper_1.ArticleWrapper, { children: (0, jsx_runtime_1.jsx)("div", Object.assign({ className: "article", ref: articleRef }, { children: article.sections.map((section, i) => {
27
+ return ((0, jsx_runtime_1.jsxs)(ArticleRectContext_1.ArticleRectContext.Provider, { value: articleRectObserver, children: [(0, jsx_runtime_1.jsx)(ArticleWrapper_1.ArticleWrapper, { children: (0, jsx_runtime_1.jsx)("div", { className: "article", ref: articleRef, children: article.sections.map((section, i) => {
28
28
  const data = section.name ? sectionData[section.name] : {};
29
- return ((0, jsx_runtime_1.jsx)(Section_1.Section, Object.assign({ section: section, data: data }, { children: article.sections[i].items.map(item => ((0, jsx_runtime_1.jsx)(Item_1.Item, { item: item, sectionId: section.id, articleHeight: articleHeight }, item.id))) }), section.id));
30
- }) })) }), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
29
+ return ((0, jsx_runtime_1.jsx)(Section_1.Section, { section: section, data: data, children: article.sections[i].items.map(item => ((0, jsx_runtime_1.jsx)(Item_1.Item, { item: item, sectionId: section.id, articleHeight: articleHeight }, item.id))) }, section.id));
30
+ }) }) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
31
31
  .article {
32
32
  position: relative;
33
33
  overflow: clip;
34
34
  }
35
- ` }))] })));
35
+ ` })] }));
36
36
  };
37
37
  exports.Article = Article;
@@ -26,11 +26,11 @@ const ArticleWrapper = ({ children }) => {
26
26
  }
27
27
  }, []);
28
28
  const layoutDeviationStyle = { '--layout-deviation': layoutDeviation };
29
- return ((0, jsx_runtime_1.jsxs)(LayoutContext_1.LayoutContext.Provider, Object.assign({ value: layoutId }, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: "article-wrapper", style: Object.assign({ opacity: layoutId && isPageLoaded ? 1 : 0 }, layoutDeviationStyle) }, { children: children })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
29
+ return ((0, jsx_runtime_1.jsxs)(LayoutContext_1.LayoutContext.Provider, { value: layoutId, children: [(0, jsx_runtime_1.jsx)("div", { className: "article-wrapper", style: Object.assign({ opacity: layoutId && isPageLoaded ? 1 : 0 }, layoutDeviationStyle), children: children }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
30
30
  .article-wrapper {
31
31
  opacity: 1;
32
32
  transition: opacity 0.2s ease;
33
33
  }
34
- ` }))] })));
34
+ ` })] }));
35
35
  };
36
36
  exports.ArticleWrapper = ArticleWrapper;
@@ -42,7 +42,7 @@ const itemsMap = {
42
42
  const RichTextWrapper = ({ isRichText, children }) => {
43
43
  if (!isRichText)
44
44
  return (0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: children });
45
- return ((0, jsx_runtime_1.jsx)("div", Object.assign({ style: { transformOrigin: 'top left', transform: 'scale(var(--layout-deviation))' } }, { children: children })));
45
+ return ((0, jsx_runtime_1.jsx)("div", { style: { transformOrigin: 'top left', transform: 'scale(var(--layout-deviation))' }, children: children }));
46
46
  };
47
47
  const noop = () => null;
48
48
  const Item = ({ item, sectionId, articleHeight }) => {
@@ -55,7 +55,7 @@ const Item = ({ item, sectionId, articleHeight }) => {
55
55
  const [wrapperHeight, setWrapperHeight] = (0, react_1.useState)(undefined);
56
56
  const [itemHeight, setItemHeight] = (0, react_1.useState)(undefined);
57
57
  const { scale, scaleAnchor } = (0, useItemScale_1.useItemScale)(item, sectionId);
58
- const { top, left } = (0, useItemPosition_1.useItemPosition)(item, sectionId);
58
+ const { top, left, bottom } = (0, useItemPosition_1.useItemPosition)(item, sectionId);
59
59
  const sectionHeight = (0, useSectionHeightMap_1.useSectionHeightData)(sectionId);
60
60
  const stickyTop = (0, useStickyItemTop_1.useStickyItemTop)(item, sectionHeight, sectionId);
61
61
  const { width, height } = (0, useItemDimensions_1.useItemDimensions)(item, sectionId);
@@ -99,7 +99,7 @@ const Item = ({ item, sectionId, articleHeight }) => {
99
99
  top: `${stickyTop * 100}vw`,
100
100
  height: isRichText && itemHeight ? `${itemHeight * 100}vw` : 'unset'
101
101
  };
102
- return ((0, jsx_runtime_1.jsxs)("div", Object.assign({ className: `item-wrapper-${item.id}`, ref: itemWrapperRef, style: isInitialRef.current ? {} : Object.assign({ top, left }, (wrapperHeight !== undefined ? { height: `${wrapperHeight * 100}vw` } : {})) }, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ suppressHydrationWarning: true, className: `item-${item.id}`, style: isInitialRef.current ? {} : styles }, { children: (0, jsx_runtime_1.jsx)(RichTextWrapper, Object.assign({ isRichText: isRichText }, { children: (0, jsx_runtime_1.jsx)("div", Object.assign({ className: `item-${item.id}-inner`, style: {
102
+ return ((0, jsx_runtime_1.jsxs)("div", { className: `item-wrapper-${item.id}`, ref: itemWrapperRef, style: isInitialRef.current ? {} : Object.assign({ top, left, bottom }, (wrapperHeight !== undefined ? { height: `${wrapperHeight * 100}vw` } : {})), children: [(0, jsx_runtime_1.jsx)("div", { suppressHydrationWarning: true, className: `item-${item.id}`, style: isInitialRef.current ? {} : styles, children: (0, jsx_runtime_1.jsx)(RichTextWrapper, { isRichText: isRichText, children: (0, jsx_runtime_1.jsx)("div", { className: `item-${item.id}-inner`, style: {
103
103
  width: `${sizingAxis.x === 'manual'
104
104
  ? isRichText
105
105
  ? `${width * exemplary}px`
@@ -108,15 +108,15 @@ const Item = ({ item, sectionId, articleHeight }) => {
108
108
  height: `${sizingAxis.y === 'manual' ? `${height * 100}vw` : 'unset'}`,
109
109
  transform: `scale(${scale})`,
110
110
  transformOrigin: ScaleAnchorMap_1.ScaleAnchorMap[scaleAnchor]
111
- } }, { children: (0, jsx_runtime_1.jsx)(ItemComponent, { item: item, sectionId: sectionId, onResize: handleItemResize, articleHeight: articleHeight }) })) })) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
111
+ }, children: (0, jsx_runtime_1.jsx)(ItemComponent, { item: item, sectionId: sectionId, onResize: handleItemResize, articleHeight: articleHeight }) }) }) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
112
112
  ${(0, sdk_1.getLayoutStyles)(layouts, layoutValues, ([area, hidden, hoverParams, sticky, sectionHeight, layoutParams]) => {
113
113
  const sizingAxis = parseSizing(layoutParams.sizing);
114
+ const isScreenBasedBottom = area.positionType === sdk_1.PositionType.ScreenBased && area.anchorSide === sdk_1.AnchorSide.Bottom;
114
115
  return (`
115
116
  .item-${item.id} {
116
117
  position: ${sticky ? 'sticky' : 'absolute'};
117
118
  top: ${sticky ? `${(0, getAnchoredItemTop_1.getAnchoredItemTop)(area.top - sticky.from, sectionHeight, area.anchorSide)}` : 0};
118
119
  pointer-events: auto;
119
- cursor: ${hoverParams ? 'pointer' : 'default'};
120
120
  display: ${hidden ? 'none' : 'block'};
121
121
  height: fit-content;
122
122
  }
@@ -134,7 +134,8 @@ const Item = ({ item, sectionId, articleHeight }) => {
134
134
  -webkit-transform: translate3d(0, 0, 0);
135
135
  transform: translate3d(0, 0, 0);
136
136
  pointer-events: none;
137
- top: ${(0, getItemTopStyle_1.getItemTopStyle)(area.top, area.anchorSide)};
137
+ bottom: ${isScreenBasedBottom ? `${-area.top * 100}vw` : 'unset'};
138
+ top: ${isScreenBasedBottom ? 'unset' : (0, getItemTopStyle_1.getItemTopStyle)(area.top, area.anchorSide)};
138
139
  left: ${area.left * 100}vw;
139
140
  transition: ${(0, HoverStyles_1.getTransitions)(['left', 'top'], hoverParams)};
140
141
  }
@@ -146,7 +147,7 @@ const Item = ({ item, sectionId, articleHeight }) => {
146
147
  }
147
148
  `);
148
149
  })}
149
- ` }))] })));
150
+ ` })] }));
150
151
  };
151
152
  exports.Item = Item;
152
153
  function parseSizing(sizing = 'manual') {
@@ -9,10 +9,10 @@ const sdk_1 = require("@cntrl-site/sdk");
9
9
  const style_1 = __importDefault(require("styled-jsx/style"));
10
10
  const LayoutStyle = ({ id, layouts, layoutId, children }) => {
11
11
  const layout = layouts.find(l => l.id === layoutId);
12
- return ((0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
12
+ return ((0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
13
13
  ${(0, sdk_1.getLayoutMediaQuery)(layoutId, layouts)} {
14
14
  ${children === null || children === void 0 ? void 0 : children(layout)}
15
15
  }
16
- ` })));
16
+ ` }));
17
17
  };
18
18
  exports.LayoutStyle = LayoutStyle;
@@ -4,7 +4,7 @@ exports.LinkWrapper = void 0;
4
4
  const jsx_runtime_1 = require("react/jsx-runtime");
5
5
  const LinkWrapper = ({ url, children, target }) => {
6
6
  const validUrl = url && buildValidUrl(url);
7
- return url ? ((0, jsx_runtime_1.jsx)("a", Object.assign({ href: validUrl, target: target, rel: "noreferrer" }, { children: children }))) : ((0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: children }));
7
+ return url ? ((0, jsx_runtime_1.jsx)("a", { href: validUrl, target: target, rel: "noreferrer", children: children })) : ((0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: children }));
8
8
  };
9
9
  exports.LinkWrapper = LinkWrapper;
10
10
  function buildValidUrl(url) {
@@ -15,6 +15,6 @@ const Page = ({ article, project, meta, keyframes, sectionData }) => {
15
15
  const afterBodyOpen = (0, html_react_parser_1.default)(project.html.afterBodyOpen);
16
16
  const beforeBodyClose = (0, html_react_parser_1.default)(project.html.beforeBodyClose);
17
17
  const keyframesRepo = (0, react_1.useMemo)(() => new Keyframes_1.Keyframes(keyframes), [keyframes]);
18
- return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)(Head_1.CNTRLHead, { project: project, meta: meta }), afterBodyOpen, (0, jsx_runtime_1.jsx)(KeyframesContext_1.KeyframesContext.Provider, Object.assign({ value: keyframesRepo }, { children: (0, jsx_runtime_1.jsx)(Article_1.Article, { article: article, sectionData: sectionData }) })), beforeBodyClose] }));
18
+ return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)(Head_1.CNTRLHead, { project: project, meta: meta }), afterBodyOpen, (0, jsx_runtime_1.jsx)(KeyframesContext_1.KeyframesContext.Provider, { value: keyframesRepo, children: (0, jsx_runtime_1.jsx)(Article_1.Article, { article: article, sectionData: sectionData }) }), beforeBodyClose] }));
19
19
  };
20
20
  exports.Page = Page;
@@ -0,0 +1,46 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ScrollPlaybackVideo = void 0;
4
+ const jsx_runtime_1 = require("react/jsx-runtime");
5
+ const react_1 = require("react");
6
+ const ScrollPlaybackVideoManager_1 = require("../utils/PlaybackVideoConverter/ScrollPlaybackVideoManager");
7
+ const rangeMap_1 = require("../utils/rangeMap");
8
+ const ArticleRectContext_1 = require("../provider/ArticleRectContext");
9
+ const ScrollPlaybackVideo = ({ sectionId, src, playbackParams, style, className }) => {
10
+ const [containerElement, setContainerElement] = (0, react_1.useState)(null);
11
+ const [time, setTime] = (0, react_1.useState)(0);
12
+ const articleRectObserver = (0, react_1.useContext)(ArticleRectContext_1.ArticleRectContext);
13
+ (0, react_1.useEffect)(() => {
14
+ if (!playbackParams || !articleRectObserver)
15
+ return;
16
+ return articleRectObserver.on('scroll', () => {
17
+ const scrollPos = articleRectObserver.getSectionScroll(sectionId);
18
+ const time = (0, rangeMap_1.rangeMap)(scrollPos, playbackParams.from, playbackParams.to, 0, 1, true);
19
+ setTime(toFixed(time));
20
+ });
21
+ }, [playbackParams === null || playbackParams === void 0 ? void 0 : playbackParams.from, playbackParams === null || playbackParams === void 0 ? void 0 : playbackParams.to, time]);
22
+ const scrollVideoManager = (0, react_1.useMemo)(() => {
23
+ if (!containerElement)
24
+ return null;
25
+ const manager = new ScrollPlaybackVideoManager_1.ScrollPlaybackVideoManager({
26
+ src,
27
+ videoContainer: containerElement
28
+ });
29
+ return manager;
30
+ }, [containerElement, src]);
31
+ (0, react_1.useEffect)(() => {
32
+ return () => {
33
+ scrollVideoManager === null || scrollVideoManager === void 0 ? void 0 : scrollVideoManager.destroy();
34
+ };
35
+ }, [scrollVideoManager]);
36
+ (0, react_1.useEffect)(() => {
37
+ if (scrollVideoManager && time >= 0 && time <= 1) {
38
+ scrollVideoManager.setTargetTimePercent(time);
39
+ }
40
+ }, [time, scrollVideoManager]);
41
+ return (0, jsx_runtime_1.jsx)("div", { className: className, style: style, ref: setContainerElement });
42
+ };
43
+ exports.ScrollPlaybackVideo = ScrollPlaybackVideo;
44
+ function toFixed(num) {
45
+ return Number(num.toFixed(3));
46
+ }
@@ -33,10 +33,10 @@ const Section = ({ section, data, children }) => {
33
33
  }, '');
34
34
  };
35
35
  if (SectionComponent)
36
- return (0, jsx_runtime_1.jsx)("div", Object.assign({ ref: sectionRef }, { children: (0, jsx_runtime_1.jsx)(SectionComponent, Object.assign({ data: data }, { children: children })) }));
37
- return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `section-${section.id}`, id: section.name, style: {
36
+ return (0, jsx_runtime_1.jsx)("div", { ref: sectionRef, children: (0, jsx_runtime_1.jsx)(SectionComponent, { data: data, children: children }) });
37
+ return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `section-${section.id}`, id: section.name, style: {
38
38
  backgroundColor: backgroundColor.toCss()
39
- }, ref: sectionRef }, { children: children })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
39
+ }, ref: sectionRef, children: children }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
40
40
  ${(0, sdk_1.getLayoutStyles)(layouts, [section.height], ([height]) => (`
41
41
  .section-${section.id} {
42
42
  height: ${getSectionHeight(height)};
@@ -48,7 +48,7 @@ const Section = ({ section, data, children }) => {
48
48
  background-color: ${backgroundColor.fmt('rgba')};
49
49
  }
50
50
  }
51
- ` }))] }));
51
+ ` })] }));
52
52
  };
53
53
  exports.Section = Section;
54
54
  function getSectionHeight(heightData) {
@@ -19,7 +19,7 @@ const CustomItem = ({ item, onResize }) => {
19
19
  (0, useRegisterResize_1.useRegisterResize)(ref, onResize);
20
20
  if (!component)
21
21
  return null;
22
- return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `custom-component-${item.id}`, ref: setRef }, { children: component({}) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: item.id }, { children: `${(0, sdk_1.getLayoutStyles)(layouts, [item.state.hover], ([hoverParams]) => {
22
+ return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `custom-component-${item.id}`, ref: setRef, children: component({}) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: item.id, children: `${(0, sdk_1.getLayoutStyles)(layouts, [item.state.hover], ([hoverParams]) => {
23
23
  return (`
24
24
  .custom-component-${item.id} {
25
25
  transition: ${(0, HoverStyles_1.getTransitions)(['angle'], hoverParams)};
@@ -33,6 +33,6 @@ const CustomItem = ({ item, onResize }) => {
33
33
  ${(0, HoverStyles_1.getHoverStyles)(['angle'], hoverParams)};
34
34
  }
35
35
  `);
36
- })}` }))] }));
36
+ })}` })] }));
37
37
  };
38
38
  exports.CustomItem = CustomItem;
@@ -24,10 +24,10 @@ const GroupItem = ({ item, sectionId, onResize, articleHeight }) => {
24
24
  const { opacity } = (0, useGroupItem_1.useGroupItem)(item, sectionId);
25
25
  const [ref, setRef] = (0, react_1.useState)(null);
26
26
  (0, useRegisterResize_1.useRegisterResize)(ref, onResize);
27
- return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target }, { children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `group-${item.id}`, ref: setRef, style: {
27
+ return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, { url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target, children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `group-${item.id}`, ref: setRef, style: {
28
28
  opacity,
29
29
  transform: `rotate(${angle}deg)`,
30
- } }, { children: items && items.map(item => ((0, jsx_runtime_1.jsx)(Item_1.Item, { item: item, sectionId: sectionId, articleHeight: articleHeight }, item.id))) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
30
+ }, children: items && items.map(item => ((0, jsx_runtime_1.jsx)(Item_1.Item, { item: item, sectionId: sectionId, articleHeight: articleHeight }, item.id))) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
31
31
  .group-${item.id} {
32
32
  position: absolute;
33
33
  width: 100%;
@@ -44,6 +44,6 @@ const GroupItem = ({ item, sectionId, onResize, articleHeight }) => {
44
44
  }
45
45
  `);
46
46
  })}
47
- ` }))] }) })));
47
+ ` })] }) }));
48
48
  };
49
49
  exports.GroupItem = GroupItem;
@@ -58,11 +58,11 @@ const ImageItem = ({ item, sectionId, onResize }) => {
58
58
  borderWidth: `${strokeWidth * 100}vw`,
59
59
  borderColor: `${borderColor.toCss()}`
60
60
  };
61
- return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_d = item.link) === null || _d === void 0 ? void 0 : _d.url, target: (_e = item.link) === null || _e === void 0 ? void 0 : _e.target }, { children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `image-wrapper-${item.id}`, ref: setRef, style: {
61
+ return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, { url: (_d = item.link) === null || _d === void 0 ? void 0 : _d.url, target: (_e = item.link) === null || _e === void 0 ? void 0 : _e.target, children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `image-wrapper-${item.id}`, ref: setRef, style: {
62
62
  opacity: `${opacity}`,
63
63
  transform: `rotate(${angle}deg)`,
64
64
  filter: `blur(${blur * 100}vw)`
65
- } }, { children: item.commonParams.hasGLEffect ? ((0, jsx_runtime_1.jsx)("canvas", { style: inlineStyles, ref: fxCanvas, className: "img-canvas", width: rectWidth, height: rectHeight })) : ((0, jsx_runtime_1.jsx)("img", { alt: "", className: `image image-${item.id}`, style: inlineStyles, src: item.commonParams.url })) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
65
+ }, children: item.commonParams.hasGLEffect ? ((0, jsx_runtime_1.jsx)("canvas", { style: inlineStyles, ref: fxCanvas, className: "img-canvas", width: rectWidth, height: rectHeight })) : ((0, jsx_runtime_1.jsx)("img", { alt: "", className: `image image-${item.id}`, style: inlineStyles, src: item.commonParams.url })) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
66
66
  @supports not (color: oklch(42% 0.3 90 / 1)) {
67
67
  .image-${item.id} {
68
68
  border-color: ${borderColor.fmt('rgba')};
@@ -109,6 +109,6 @@ const ImageItem = ({ item, sectionId, onResize }) => {
109
109
  }
110
110
  `);
111
111
  })}
112
- ` }))] }) })));
112
+ ` })] }) }));
113
113
  };
114
114
  exports.ImageItem = ImageItem;
@@ -26,7 +26,7 @@ const RectangleItem = ({ item, sectionId, onResize }) => {
26
26
  const [ref, setRef] = (0, react_1.useState)(null);
27
27
  (0, useRegisterResize_1.useRegisterResize)(ref, onResize);
28
28
  const backdropFilterValue = backdropBlur !== 0 ? `blur(${backdropBlur * 100}vw)` : 'unset';
29
- return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target }, { children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `rectangle-${item.id}`, ref: setRef, style: {
29
+ return ((0, jsx_runtime_1.jsx)(LinkWrapper_1.LinkWrapper, { url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target, children: (0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { className: `rectangle-${item.id}`, ref: setRef, style: {
30
30
  backgroundColor: `${backgroundColor.toCss()}`,
31
31
  borderRadius: `${radius * 100}vw`,
32
32
  borderWidth: `${strokeWidth * 100}vw`,
@@ -35,7 +35,7 @@ const RectangleItem = ({ item, sectionId, onResize }) => {
35
35
  filter: blur !== 0 ? `blur(${blur * 100}vw)` : 'unset',
36
36
  backdropFilter: backdropFilterValue,
37
37
  WebkitBackdropFilter: backdropFilterValue,
38
- } }), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
38
+ } }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
39
39
  @supports not (color: oklch(42% 0.3 90 / 1)) {
40
40
  .rectangle-${item.id} {
41
41
  background-color: ${backgroundColor.fmt('rgba')};
@@ -59,6 +59,6 @@ const RectangleItem = ({ item, sectionId, onResize }) => {
59
59
  }
60
60
  `);
61
61
  })}
62
- ` }))] }) })));
62
+ ` })] }) }));
63
63
  };
64
64
  exports.RectangleItem = RectangleItem;
@@ -25,13 +25,13 @@ const RichTextItem = ({ item, sectionId, onResize }) => {
25
25
  const textColor = (0, react_1.useMemo)(() => color_1.CntrlColor.parse(color), [color]);
26
26
  const exemplary = (0, useExemplary_1.useExemplary)();
27
27
  (0, useRegisterResize_1.useRegisterResize)(ref, onResize);
28
- return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ ref: setRef, className: `rich-text-wrapper-${item.id}`, style: {
28
+ return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)("div", { ref: setRef, className: `rich-text-wrapper-${item.id}`, style: {
29
29
  transform: `rotate(${angle}deg)`,
30
30
  filter: `blur(${blur * exemplary}px)`,
31
31
  letterSpacing: `${letterSpacing * exemplary}px`,
32
32
  wordSpacing: `${wordSpacing * exemplary}px`,
33
33
  color: `${textColor.toCss()}`
34
- } }, { children: content })), (0, jsx_runtime_1.jsxs)(style_1.default, Object.assign({ id: id }, { children: [styles, `${(0, sdk_1.getLayoutStyles)(layouts, [item.state.hover], ([hoverParams]) => {
34
+ }, children: content }), (0, jsx_runtime_1.jsxs)(style_1.default, { id: id, children: [styles, `${(0, sdk_1.getLayoutStyles)(layouts, [item.state.hover], ([hoverParams]) => {
35
35
  return (`
36
36
  .rich-text-wrapper-${item.id} {
37
37
  transition: ${(0, HoverStyles_1.getTransitions)(['angle', 'blur', 'letterSpacing', 'wordSpacing', 'color'], hoverParams)};
@@ -62,6 +62,6 @@ const RichTextItem = ({ item, sectionId, onResize }) => {
62
62
  }
63
63
  }
64
64
  `);
65
- })}`] }))] }));
65
+ })}`] })] }));
66
66
  };
67
67
  exports.RichTextItem = RichTextItem;
@@ -15,12 +15,8 @@ const useItemAngle_1 = require("../useItemAngle");
15
15
  const useCntrlContext_1 = require("../../provider/useCntrlContext");
16
16
  const HoverStyles_1 = require("../../utils/HoverStyles/HoverStyles");
17
17
  const useRegisterResize_1 = require("../../common/useRegisterResize");
18
- const rangeMap_1 = require("../../utils/rangeMap");
19
- const ArticleRectContext_1 = require("../../provider/ArticleRectContext");
20
18
  const useLayoutContext_1 = require("../useLayoutContext");
21
- // To prevent video behaviour that drops to the first frame
22
- // when close to the end
23
- const SCROLL_TIME_SHIFT = 0.1;
19
+ const ScrollPlaybackVideo_1 = require("../ScrollPlaybackVideo");
24
20
  const VideoItem = ({ item, sectionId, onResize }) => {
25
21
  var _a, _b;
26
22
  const id = (0, react_1.useId)();
@@ -30,49 +26,24 @@ const VideoItem = ({ item, sectionId, onResize }) => {
30
26
  const borderColor = (0, react_1.useMemo)(() => color_1.CntrlColor.parse(strokeColor), [strokeColor]);
31
27
  const [ref, setRef] = (0, react_1.useState)(null);
32
28
  const videoRef = (0, react_1.useRef)(null);
33
- const articleRectObserver = (0, react_1.useContext)(ArticleRectContext_1.ArticleRectContext);
34
- const rafId = (0, react_1.useRef)();
35
29
  const layoutId = (0, useLayoutContext_1.useLayoutContext)();
36
30
  const scrollPlayback = item.layoutParams[layoutId].scrollPlayback;
37
- (0, react_1.useEffect)(() => {
38
- const video = videoRef.current;
39
- if (!video || !scrollPlayback) {
40
- video === null || video === void 0 ? void 0 : video.play();
41
- return;
42
- }
43
- video === null || video === void 0 ? void 0 : video.pause();
44
- const scrollVideo = () => {
45
- rafId.current = window.requestAnimationFrame(scrollVideo);
46
- if (!articleRectObserver)
47
- return;
48
- const scrollPos = articleRectObserver.getSectionScroll(sectionId);
49
- if (!video.duration)
50
- return;
51
- const time = (0, rangeMap_1.rangeMap)(scrollPos, scrollPlayback.from, scrollPlayback.to, 0, video.duration, true);
52
- if (scrollPos > scrollPlayback.from && scrollPos < scrollPlayback.to) {
53
- if (toFixed(video.currentTime) === toFixed(time - SCROLL_TIME_SHIFT))
54
- return;
55
- video.currentTime = Math.max(0, time - SCROLL_TIME_SHIFT);
56
- }
57
- };
58
- rafId.current = window.requestAnimationFrame(scrollVideo);
59
- return () => {
60
- if (rafId.current) {
61
- window.cancelAnimationFrame(rafId.current);
62
- rafId.current = undefined;
63
- }
64
- };
65
- }, [scrollPlayback]);
31
+ const hasScrollPlayback = scrollPlayback !== null;
66
32
  (0, useRegisterResize_1.useRegisterResize)(ref, onResize);
67
- return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target }, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `video-wrapper-${item.id}`, ref: setRef, style: {
33
+ return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, { url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target, children: [(0, jsx_runtime_1.jsx)("div", { className: `video-wrapper-${item.id}`, ref: setRef, style: {
68
34
  opacity: `${opacity}`,
69
35
  transform: `rotate(${angle}deg)`,
70
- filter: `blur(${blur * 100}vw)`
71
- } }, { children: (0, jsx_runtime_1.jsx)("video", Object.assign({ ref: videoRef, autoPlay: true, muted: true, loop: true, playsInline: true, className: `video video-${item.id}`, style: {
36
+ filter: `blur(${blur * 100}vw)`,
37
+ overflow: hasScrollPlayback ? 'hidden' : 'auto'
38
+ }, children: hasScrollPlayback ? ((0, jsx_runtime_1.jsx)(ScrollPlaybackVideo_1.ScrollPlaybackVideo, { sectionId: sectionId, src: item.commonParams.url, playbackParams: scrollPlayback, style: {
72
39
  borderRadius: `${radius * 100}vw`,
73
40
  borderWidth: `${strokeWidth * 100}vw`,
74
41
  borderColor: `${borderColor.toCss()}`
75
- } }, { children: (0, jsx_runtime_1.jsx)("source", { src: item.commonParams.url }) })) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
42
+ }, className: `video video-playback-wrapper video-${item.id}` })) : ((0, jsx_runtime_1.jsx)("video", { ref: videoRef, autoPlay: true, muted: true, loop: true, playsInline: true, className: `video video-${item.id}`, style: {
43
+ borderRadius: `${radius * 100}vw`,
44
+ borderWidth: `${strokeWidth * 100}vw`,
45
+ borderColor: `${borderColor.toCss()}`
46
+ }, children: (0, jsx_runtime_1.jsx)("source", { src: item.commonParams.url }) })) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
76
47
  @supports not (color: oklch(42% 0.3 90 / 1)) {
77
48
  .video-${item.id} {
78
49
  border-color: ${borderColor.fmt('rgba')};
@@ -97,6 +68,10 @@ const VideoItem = ({ item, sectionId, onResize }) => {
97
68
  .video-${item.id} {
98
69
  border-color: ${strokeColor};
99
70
  }
71
+ .video-playback-wrapper {
72
+ display: flex;
73
+ justify-content: center;
74
+ }
100
75
  ${(0, sdk_1.getLayoutStyles)(layouts, [item.state.hover], ([hoverParams]) => {
101
76
  return (`
102
77
  .video-wrapper-${item.id} {
@@ -113,9 +88,6 @@ const VideoItem = ({ item, sectionId, onResize }) => {
113
88
  }
114
89
  `);
115
90
  })}
116
- ` }))] })));
91
+ ` })] }));
117
92
  };
118
93
  exports.VideoItem = VideoItem;
119
- function toFixed(num) {
120
- return Number(num.toFixed(5));
121
- }
@@ -40,7 +40,7 @@ const VimeoEmbedItem = ({ item, sectionId, onResize }) => {
40
40
  return validURL.href;
41
41
  };
42
42
  const validUrl = getValidVimeoUrl(url);
43
- return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target }, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `embed-video-wrapper-${item.id}`, ref: setRef, style: {
43
+ return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, { url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target, children: [(0, jsx_runtime_1.jsx)("div", { className: `embed-video-wrapper-${item.id}`, ref: setRef, style: {
44
44
  transform: `rotate(${angle}deg)`,
45
45
  filter: `blur(${blur * 100}vw)`
46
46
  }, onMouseEnter: () => {
@@ -51,9 +51,9 @@ const VimeoEmbedItem = ({ item, sectionId, onResize }) => {
51
51
  if (!vimeoPlayer || play !== 'on-hover')
52
52
  return;
53
53
  vimeoPlayer.pause();
54
- } }, { children: (0, jsx_runtime_1.jsx)("iframe", { ref: setIframeRef, className: "embedVideo", src: validUrl || '', allow: "autoplay; fullscreen; picture-in-picture;", allowFullScreen: true, style: {
54
+ }, children: (0, jsx_runtime_1.jsx)("iframe", { ref: setIframeRef, className: "embedVideo", src: validUrl || '', allow: "autoplay; fullscreen; picture-in-picture;", allowFullScreen: true, style: {
55
55
  borderRadius: `${radius * 100}vw`
56
- } }) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
56
+ } }) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
57
57
  .embed-video-wrapper-${item.id} {
58
58
  position: absolute;
59
59
  width: 100%;
@@ -82,6 +82,6 @@ const VimeoEmbedItem = ({ item, sectionId, onResize }) => {
82
82
  }
83
83
  `);
84
84
  })}
85
- ` }))] })));
85
+ ` })] }));
86
86
  };
87
87
  exports.VimeoEmbedItem = VimeoEmbedItem;
@@ -56,7 +56,7 @@ const YoutubeEmbedItem = ({ item, sectionId, onResize }) => {
56
56
  (_a = placeholder.parentElement) === null || _a === void 0 ? void 0 : _a.removeChild(placeholder);
57
57
  };
58
58
  }, [YT, div]);
59
- return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, Object.assign({ url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target }, { children: [(0, jsx_runtime_1.jsx)("div", Object.assign({ className: `embed-youtube-video-wrapper-${item.id}`, onMouseEnter: () => {
59
+ return ((0, jsx_runtime_1.jsxs)(LinkWrapper_1.LinkWrapper, { url: (_a = item.link) === null || _a === void 0 ? void 0 : _a.url, target: (_b = item.link) === null || _b === void 0 ? void 0 : _b.target, children: [(0, jsx_runtime_1.jsx)("div", { className: `embed-youtube-video-wrapper-${item.id}`, onMouseEnter: () => {
60
60
  if (!player || play !== 'on-hover')
61
61
  return;
62
62
  player.playVideo();
@@ -67,7 +67,7 @@ const YoutubeEmbedItem = ({ item, sectionId, onResize }) => {
67
67
  }, style: {
68
68
  transform: `rotate(${angle}deg)`,
69
69
  filter: `blur(${blur * 100}vw)`
70
- } }, { children: (0, jsx_runtime_1.jsx)("div", { className: `embed-${item.id}`, ref: setDiv, style: { borderRadius: `${radius * 100}vw` } }) })), (0, jsx_runtime_1.jsx)(style_1.default, Object.assign({ id: id }, { children: `
70
+ }, children: (0, jsx_runtime_1.jsx)("div", { className: `embed-${item.id}`, ref: setDiv, style: { borderRadius: `${radius * 100}vw` } }) }), (0, jsx_runtime_1.jsx)(style_1.default, { id: id, children: `
71
71
  .embed-youtube-video-wrapper-${item.id},
72
72
  .embed-${item.id} {
73
73
  position: absolute;
@@ -99,6 +99,6 @@ const YoutubeEmbedItem = ({ item, sectionId, onResize }) => {
99
99
  }
100
100
  `);
101
101
  })}
102
- ` }))] })));
102
+ ` })] }));
103
103
  };
104
104
  exports.YoutubeEmbedItem = YoutubeEmbedItem;
@@ -13,8 +13,12 @@ const useItemPosition = (item, sectionId) => {
13
13
  return item.area[layoutId];
14
14
  }, (animator, scroll, value) => animator.getPositions(value, scroll), sectionId, [layoutId]);
15
15
  const anchorSide = layoutId ? item.area[layoutId].anchorSide : sdk_1.AnchorSide.Top;
16
+ const positionType = layoutId ? item.area[layoutId].positionType : sdk_1.PositionType.ScreenBased;
17
+ // tp prevent fixed item (with anchor point bottom) to jump when scroll in safari on mobile
18
+ const isScreenBasedBottom = positionType === sdk_1.PositionType.ScreenBased && anchorSide === sdk_1.AnchorSide.Bottom;
16
19
  return {
17
- top: (0, getItemTopStyle_1.getItemTopStyle)(top, anchorSide),
20
+ bottom: isScreenBasedBottom ? `${-top * 100}vw` : 'unset',
21
+ top: isScreenBasedBottom ? 'unset' : (0, getItemTopStyle_1.getItemTopStyle)(top, anchorSide),
18
22
  left: `${left * 100}vw`
19
23
  };
20
24
  };
@@ -5,6 +5,6 @@ const jsx_runtime_1 = require("react/jsx-runtime");
5
5
  const CntrlContext_1 = require("./CntrlContext");
6
6
  const defaultContext_1 = require("./defaultContext");
7
7
  const CntrlProvider = ({ children }) => {
8
- return ((0, jsx_runtime_1.jsx)(CntrlContext_1.CntrlContext.Provider, Object.assign({ value: defaultContext_1.cntrlSdkContext }, { children: children })));
8
+ return ((0, jsx_runtime_1.jsx)(CntrlContext_1.CntrlContext.Provider, { value: defaultContext_1.cntrlSdkContext, children: children }));
9
9
  };
10
10
  exports.CntrlProvider = CntrlProvider;