@mgochkov/betty-carousel 1.0.0 → 1.0.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.
@@ -0,0 +1,2 @@
1
+ ._carouselViewport_1v3r0_6{touch-action:pan-x;width:100%;margin:0 auto;position:relative;overflow:hidden}._carouselContainer_1v3r0_14{cursor:grab;scroll-behavior:smooth;scrollbar-width:none;-ms-overflow-style:none;width:100%;height:420px;display:flex;overflow:auto hidden}._carouselContainer_1v3r0_14::-webkit-scrollbar{display:none}._carouselContainer_1v3r0_14:active{cursor:grabbing}._carouselContainer_1v3r0_14:focus{outline:none}._virtualTrack_1v3r0_36{flex-shrink:0;height:100%;position:relative}._carouselItem_1v3r0_42{box-sizing:border-box;-webkit-user-select:none;user-select:none;height:100%;padding:8px;position:absolute;top:0}._imageWrapper_1v3r0_51{background-color:#f0f0f0;border-radius:8px;width:100%;height:100%;position:relative;overflow:hidden}._image_1v3r0_51{object-fit:cover;pointer-events:none;width:100%;height:100%;display:block}._authorTag_1v3r0_68{color:#fff;pointer-events:none;background:#000000a6;border-radius:4px;padding:4px 8px;font-family:sans-serif;font-size:12px;position:absolute;bottom:12px;left:12px}
2
+ /*$vite$:1*/
@@ -1,58 +1,109 @@
1
- import { useEffect as e, useRef as t, useState as n } from "react";
2
- import { jsx as r } from "react/jsx-runtime";
3
- // src/components/Carousel/Carousel.tsx
4
- var i = ({ images: i, itemWidth: a = 300, visibleCount: o = 5 }) => {
5
- let s = t(null), [c, l] = n(i.length * a), u = [
6
- ...i,
7
- ...i,
8
- ...i
9
- ], d = i.length * a;
10
- return e(() => {
11
- s.current && (s.current.scrollLeft = d);
12
- }, [d]), /* @__PURE__ */ r("div", {
13
- ref: s,
14
- onScroll: (e) => {
15
- let t = e.currentTarget.scrollLeft;
16
- t <= a ? e.currentTarget.scrollLeft = t + d : t >= d * 2 && (e.currentTarget.scrollLeft = t - d), l(e.currentTarget.scrollLeft);
17
- },
18
- style: {
19
- display: "flex",
20
- overflowX: "auto",
21
- scrollSnapType: "x mandatory",
22
- WebkitOverflowScrolling: "touch",
23
- width: "100%",
24
- cursor: "grab"
25
- },
26
- className: "carousel-container hide-scrollbar",
27
- children: u.map((e, t) => {
28
- let n = t * a, i = Math.abs(n - c) < a * (o + 1);
29
- return /* @__PURE__ */ r("div", {
30
- style: {
31
- minWidth: `${a}px`,
32
- height: "400px",
33
- scrollSnapAlign: "center",
34
- flexShrink: 0,
35
- padding: "8px",
36
- boxSizing: "border-box"
37
- },
38
- children: i ? /* @__PURE__ */ r("img", {
39
- src: e.download_url,
40
- alt: e.author,
41
- loading: "lazy",
1
+ import { useCallback as e, useEffect as t, useRef as n, useState as r } from "react";
2
+ import { jsx as i, jsxs as a } from "react/jsx-runtime";
3
+ var o = {
4
+ carouselViewport: "_carouselViewport_1v3r0_6",
5
+ carouselContainer: "_carouselContainer_1v3r0_14",
6
+ virtualTrack: "_virtualTrack_1v3r0_36",
7
+ carouselItem: "_carouselItem_1v3r0_42",
8
+ imageWrapper: "_imageWrapper_1v3r0_51",
9
+ image: "_image_1v3r0_51",
10
+ authorTag: "_authorTag_1v3r0_68"
11
+ }, s = ({ images: s, itemWidth: c = 300, visibleCount: l = 3 }) => {
12
+ let u = n(null), d = n(!1), f = n(0), p = n(0), m = s.length, h = m >= 100, g = h ? 3 : 5, _ = Array.from({ length: m * g }, (e, t) => {
13
+ let n = t % m;
14
+ return {
15
+ ...s[n],
16
+ uniqueKey: `${s[n].id}-${t}`,
17
+ originalIndex: n
18
+ };
19
+ }), v = _.length, y = v * c, b = m * c, x = h ? b : b * 2, [S, C] = r({
20
+ start: 0,
21
+ end: h ? l + 5 : v
22
+ });
23
+ t(() => {
24
+ u.current && (u.current.style.scrollBehavior = "auto", u.current.scrollLeft = x);
25
+ }, [x]);
26
+ let w = e((e) => {
27
+ let t = e.currentTarget.scrollLeft;
28
+ if (t <= b * .5) e.currentTarget.style.scrollBehavior = "auto", e.currentTarget.scrollLeft = t + b * (g - 2);
29
+ else if (t >= b * (g - 1.5)) e.currentTarget.style.scrollBehavior = "auto", e.currentTarget.scrollLeft = t - b * (g - 2);
30
+ else if (h) {
31
+ let e = Math.max(0, Math.floor(t / c) - 2), n = Math.min(v - 1, e + l + 5);
32
+ C((t) => t.start !== e || t.end !== n ? {
33
+ start: e,
34
+ end: n
35
+ } : t);
36
+ }
37
+ }, [
38
+ c,
39
+ b,
40
+ l,
41
+ v,
42
+ h,
43
+ g
44
+ ]), T = (e) => {
45
+ u.current && e.deltaY !== 0 && (e.preventDefault(), u.current.style.scrollBehavior = "auto", u.current.scrollLeft += e.deltaY);
46
+ }, E = (e) => {
47
+ [
48
+ "ArrowLeft",
49
+ "ArrowRight",
50
+ "PageUp",
51
+ "PageDown",
52
+ "Home",
53
+ "End",
54
+ " "
55
+ ].includes(e.key) && (e.preventDefault(), e.stopPropagation());
56
+ }, D = (e) => {
57
+ u.current && (d.current = !0, f.current = e.pageX - u.current.offsetLeft, p.current = u.current.scrollLeft);
58
+ }, O = () => {
59
+ d.current = !1;
60
+ };
61
+ return !s || s.length === 0 ? /* @__PURE__ */ i("div", {
62
+ className: o.carouselViewport,
63
+ children: "No images available"
64
+ }) : /* @__PURE__ */ i("div", {
65
+ className: o.carouselViewport,
66
+ style: { maxWidth: `${c * l}px` },
67
+ children: /* @__PURE__ */ i("div", {
68
+ ref: u,
69
+ className: o.carouselContainer,
70
+ onScroll: w,
71
+ onWheel: T,
72
+ onKeyDown: E,
73
+ onMouseDown: D,
74
+ onMouseLeave: O,
75
+ onMouseUp: O,
76
+ onMouseMove: (e) => {
77
+ if (!d.current || !u.current) return;
78
+ e.preventDefault();
79
+ let t = (e.pageX - u.current.offsetLeft - f.current) * 1.5;
80
+ u.current.style.scrollBehavior = "auto", u.current.scrollLeft = p.current - t;
81
+ },
82
+ tabIndex: 0,
83
+ children: /* @__PURE__ */ i("div", {
84
+ className: o.virtualTrack,
85
+ style: { width: `${y}px` },
86
+ children: _.map((e, t) => h && (t < S.start || t > S.end) ? null : /* @__PURE__ */ i("div", {
87
+ className: o.carouselItem,
42
88
  style: {
43
- width: "100%",
44
- height: "100%",
45
- objectFit: "cover",
46
- borderRadius: "8px"
47
- }
48
- }) : /* @__PURE__ */ r("div", { style: {
49
- width: "100%",
50
- height: "100%",
51
- backgroundColor: "#e0e0e0",
52
- borderRadius: "8px"
53
- } })
54
- }, `${e.id}-${t}`);
89
+ left: `${t * c}px`,
90
+ width: `${c}px`
91
+ },
92
+ children: /* @__PURE__ */ a("div", {
93
+ className: o.imageWrapper,
94
+ children: [/* @__PURE__ */ i("img", {
95
+ src: e.download_url,
96
+ alt: e.author || "Carousel Item",
97
+ loading: "lazy",
98
+ className: o.image
99
+ }), e.author && /* @__PURE__ */ i("div", {
100
+ className: o.authorTag,
101
+ children: e.author
102
+ })]
103
+ })
104
+ }, e.uniqueKey))
105
+ })
55
106
  })
56
107
  });
57
108
  };
58
- export { i as Carousel };
109
+ export { s as Carousel };
@@ -1 +1 @@
1
- (function(e,t){typeof exports==`object`&&typeof module<`u`?t(exports,require("react"),require("react/jsx-runtime")):typeof define==`function`&&define.amd?define([`exports`,`react`,`react/jsx-runtime`],t):(e=typeof globalThis<`u`?globalThis:e||self,t(e.BettyReactLibrary={},e.React,e.jsxRuntime))})(this,function(e,t,n){Object.defineProperty(e,Symbol.toStringTag,{value:`Module`});var r=Object.create,i=Object.defineProperty,a=Object.getOwnPropertyDescriptor,o=Object.getOwnPropertyNames,s=Object.getPrototypeOf,c=Object.prototype.hasOwnProperty,l=(e,t,n,r)=>{if(t&&typeof t==`object`||typeof t==`function`)for(var s=o(t),l=0,u=s.length,d;l<u;l++)d=s[l],!c.call(e,d)&&d!==n&&i(e,d,{get:(e=>t[e]).bind(null,d),enumerable:!(r=a(t,d))||r.enumerable});return e};t=((e,t,n)=>(n=e==null?{}:r(s(e)),l(i(n,`default`,{value:e,enumerable:!0}),e)))(t,1),e.Carousel=({images:e,itemWidth:r=300,visibleCount:i=5})=>{let a=(0,t.useRef)(null),[o,s]=(0,t.useState)(e.length*r),c=[...e,...e,...e],l=e.length*r;return(0,t.useEffect)(()=>{a.current&&(a.current.scrollLeft=l)},[l]),(0,n.jsx)(`div`,{ref:a,onScroll:e=>{let t=e.currentTarget.scrollLeft;t<=r?e.currentTarget.scrollLeft=t+l:t>=l*2&&(e.currentTarget.scrollLeft=t-l),s(e.currentTarget.scrollLeft)},style:{display:`flex`,overflowX:`auto`,scrollSnapType:`x mandatory`,WebkitOverflowScrolling:`touch`,width:`100%`,cursor:`grab`},className:`carousel-container hide-scrollbar`,children:c.map((e,t)=>{let a=t*r,s=Math.abs(a-o)<r*(i+1);return(0,n.jsx)(`div`,{style:{minWidth:`${r}px`,height:`400px`,scrollSnapAlign:`center`,flexShrink:0,padding:`8px`,boxSizing:`border-box`},children:s?(0,n.jsx)(`img`,{src:e.download_url,alt:e.author,loading:`lazy`,style:{width:`100%`,height:`100%`,objectFit:`cover`,borderRadius:`8px`}}):(0,n.jsx)(`div`,{style:{width:`100%`,height:`100%`,backgroundColor:`#e0e0e0`,borderRadius:`8px`}})},`${e.id}-${t}`)})})}});
1
+ (function(e,t){typeof exports==`object`&&typeof module<`u`?t(exports,require("react"),require("react/jsx-runtime")):typeof define==`function`&&define.amd?define([`exports`,`react`,`react/jsx-runtime`],t):(e=typeof globalThis<`u`?globalThis:e||self,t(e.BettyReactLibrary={},e.React,e.jsxRuntime))})(this,function(e,t,n){Object.defineProperty(e,Symbol.toStringTag,{value:`Module`});var r=Object.create,i=Object.defineProperty,a=Object.getOwnPropertyDescriptor,o=Object.getOwnPropertyNames,s=Object.getPrototypeOf,c=Object.prototype.hasOwnProperty,l=(e,t,n,r)=>{if(t&&typeof t==`object`||typeof t==`function`)for(var s=o(t),l=0,u=s.length,d;l<u;l++)d=s[l],!c.call(e,d)&&d!==n&&i(e,d,{get:(e=>t[e]).bind(null,d),enumerable:!(r=a(t,d))||r.enumerable});return e};t=((e,t,n)=>(n=e==null?{}:r(s(e)),l(i(n,`default`,{value:e,enumerable:!0}),e)))(t,1);var u={carouselViewport:`_carouselViewport_1v3r0_6`,carouselContainer:`_carouselContainer_1v3r0_14`,virtualTrack:`_virtualTrack_1v3r0_36`,carouselItem:`_carouselItem_1v3r0_42`,imageWrapper:`_imageWrapper_1v3r0_51`,image:`_image_1v3r0_51`,authorTag:`_authorTag_1v3r0_68`};e.Carousel=({images:e,itemWidth:r=300,visibleCount:i=3})=>{let a=(0,t.useRef)(null),o=(0,t.useRef)(!1),s=(0,t.useRef)(0),c=(0,t.useRef)(0),l=e.length,d=l>=100,f=d?3:5,p=Array.from({length:l*f},(t,n)=>{let r=n%l;return{...e[r],uniqueKey:`${e[r].id}-${n}`,originalIndex:r}}),m=p.length,h=m*r,g=l*r,_=d?g:g*2,[v,y]=(0,t.useState)({start:0,end:d?i+5:m});(0,t.useEffect)(()=>{a.current&&(a.current.style.scrollBehavior=`auto`,a.current.scrollLeft=_)},[_]);let b=(0,t.useCallback)(e=>{let t=e.currentTarget.scrollLeft;if(t<=g*.5)e.currentTarget.style.scrollBehavior=`auto`,e.currentTarget.scrollLeft=t+g*(f-2);else if(t>=g*(f-1.5))e.currentTarget.style.scrollBehavior=`auto`,e.currentTarget.scrollLeft=t-g*(f-2);else if(d){let e=Math.max(0,Math.floor(t/r)-2),n=Math.min(m-1,e+i+5);y(t=>t.start!==e||t.end!==n?{start:e,end:n}:t)}},[r,g,i,m,d,f]),x=e=>{a.current&&e.deltaY!==0&&(e.preventDefault(),a.current.style.scrollBehavior=`auto`,a.current.scrollLeft+=e.deltaY)},S=e=>{[`ArrowLeft`,`ArrowRight`,`PageUp`,`PageDown`,`Home`,`End`,` `].includes(e.key)&&(e.preventDefault(),e.stopPropagation())},C=e=>{a.current&&(o.current=!0,s.current=e.pageX-a.current.offsetLeft,c.current=a.current.scrollLeft)},w=()=>{o.current=!1};return!e||e.length===0?(0,n.jsx)(`div`,{className:u.carouselViewport,children:`No images available`}):(0,n.jsx)(`div`,{className:u.carouselViewport,style:{maxWidth:`${r*i}px`},children:(0,n.jsx)(`div`,{ref:a,className:u.carouselContainer,onScroll:b,onWheel:x,onKeyDown:S,onMouseDown:C,onMouseLeave:w,onMouseUp:w,onMouseMove:e=>{if(!o.current||!a.current)return;e.preventDefault();let t=(e.pageX-a.current.offsetLeft-s.current)*1.5;a.current.style.scrollBehavior=`auto`,a.current.scrollLeft=c.current-t},tabIndex:0,children:(0,n.jsx)(`div`,{className:u.virtualTrack,style:{width:`${h}px`},children:p.map((e,t)=>d&&(t<v.start||t>v.end)?null:(0,n.jsx)(`div`,{className:u.carouselItem,style:{left:`${t*r}px`,width:`${r}px`},children:(0,n.jsxs)(`div`,{className:u.imageWrapper,children:[(0,n.jsx)(`img`,{src:e.download_url,alt:e.author||`Carousel Item`,loading:`lazy`,className:u.image}),e.author&&(0,n.jsx)(`div`,{className:u.authorTag,children:e.author})]})},e.uniqueKey))})})})}});
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mgochkov/betty-carousel",
3
- "version": "1.0.0",
3
+ "version": "1.0.1",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "dist"
@@ -31,8 +31,8 @@
31
31
  "build-storybook": "storybook build"
32
32
  },
33
33
  "dependencies": {
34
- "react": "^19.3.1",
35
- "react-dom": "^19.3.1"
34
+ "react": "^18.0.0 || ^19.0.0",
35
+ "react-dom": "^18.0.0 || ^19.0.0"
36
36
  },
37
37
  "devDependencies": {
38
38
  "@chromatic-com/storybook": "latest",
@@ -58,6 +58,7 @@
58
58
  "globals": "^17.13.0",
59
59
  "jsdom": "^30.1.3",
60
60
  "playwright": "latest",
61
+ "sass-embedded": "^1.106.1",
61
62
  "storybook": "^10.6.3",
62
63
  "typescript": "~6.0.3",
63
64
  "typescript-eslint": "^8.71.2",