anim-3d-obj 2.0.6 → 2.0.8

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/index.cjs CHANGED
@@ -229,6 +229,7 @@ var Obj = React__namespace.memo(
229
229
  transitionDuration = 1,
230
230
  oneAtATime = false,
231
231
  remainJoined = false,
232
+ ytilt = false,
232
233
  className,
233
234
  style
234
235
  }) => {
@@ -239,6 +240,32 @@ var Obj = React__namespace.memo(
239
240
  const animation2 = toAnimationShorthand(anim2) ?? void 0;
240
241
  const faceList = faces && faces.length > 0 ? faces : DEFAULT_FACE_NAMES.map((name) => ({ name }));
241
242
  const transitionCss = (delay = 0) => `transform ${transitionDuration}s ease-in-out ${delay}s`;
243
+ const tiltCount = React__namespace.useRef(0);
244
+ const prevFlat = React__namespace.useRef(flat);
245
+ const [tiltAnim, setTiltAnim] = React__namespace.useState(void 0);
246
+ React__namespace.useEffect(() => {
247
+ if (flat !== prevFlat.current) {
248
+ prevFlat.current = flat;
249
+ if (ytilt) {
250
+ tiltCount.current += 1;
251
+ const sideCount = faceList.filter(
252
+ (f) => ["front", "right", "back", "left"].includes(
253
+ f.name
254
+ )
255
+ ).length;
256
+ const totalDur = oneAtATime ? transitionDuration * sideCount : transitionDuration;
257
+ const name = tiltCount.current % 2 === 0 ? "anim3d-ytilt-a" : "anim3d-ytilt-b";
258
+ setTiltAnim(
259
+ `${name} ${totalDur}s ease-in-out 1 forwards`
260
+ );
261
+ const timer = setTimeout(
262
+ () => setTiltAnim(void 0),
263
+ totalDur * 1e3 + 50
264
+ );
265
+ return () => clearTimeout(timer);
266
+ }
267
+ }
268
+ }, [flat, ytilt, transitionDuration, oneAtATime, faceList]);
242
269
  const renderStandard = () => faceList.map((face, i) => {
243
270
  const dims = faceDimensions(face.name, w, h, d);
244
271
  const transform = flat ? faceTransformFlat(face.name, w, h, d) : faceTransform3D(face.name, w, h, d);
@@ -452,27 +479,36 @@ var Obj = React__namespace.memo(
452
479
  children: /* @__PURE__ */ jsxRuntime.jsx(
453
480
  "div",
454
481
  {
455
- className: "anim3d-wrapper",
456
482
  style: {
457
- ...cssVars,
458
- animation: flat ? "none" : animation1,
459
483
  transformStyle: "preserve-3d",
460
- transition: transitionCss()
484
+ animation: tiltAnim
461
485
  },
462
- children: /* @__PURE__ */ jsxRuntime.jsxs(
486
+ children: /* @__PURE__ */ jsxRuntime.jsx(
463
487
  "div",
464
488
  {
465
489
  className: "anim3d-wrapper",
466
490
  style: {
467
491
  ...cssVars,
468
- animation: flat ? "none" : animation2,
492
+ animation: flat ? "none" : animation1,
469
493
  transformStyle: "preserve-3d",
470
494
  transition: transitionCss()
471
495
  },
472
- children: [
473
- showCenterDiv && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "anim3d-center" }),
474
- remainJoined ? renderJoined() : renderStandard()
475
- ]
496
+ children: /* @__PURE__ */ jsxRuntime.jsxs(
497
+ "div",
498
+ {
499
+ className: "anim3d-wrapper",
500
+ style: {
501
+ ...cssVars,
502
+ animation: flat ? "none" : animation2,
503
+ transformStyle: "preserve-3d",
504
+ transition: transitionCss()
505
+ },
506
+ children: [
507
+ showCenterDiv && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "anim3d-center" }),
508
+ remainJoined ? renderJoined() : renderStandard()
509
+ ]
510
+ }
511
+ )
476
512
  }
477
513
  )
478
514
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/keyframes.ts","../src/components/Obj.tsx"],"names":["React","jsx","jsxs","Fragment"],"mappings":"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","file":"index.cjs","sourcesContent":["import type { AnimationConfig } from \"./types\";\n\n/** Create (or reuse) a <style> tag for dynamic keyframes */\nfunction ensureStyleTag(): HTMLStyleElement {\n let tag = document.getElementById(\n \"anim3d-keyframes\"\n ) as HTMLStyleElement | null;\n if (!tag) {\n tag = document.createElement(\"style\");\n tag.id = \"anim3d-keyframes\";\n document.head.appendChild(tag);\n }\n return tag;\n}\n\nfunction inject(css: string) {\n if (typeof document === \"undefined\") return; // SSR\n const tag = ensureStyleTag();\n tag.appendChild(document.createTextNode(css));\n}\n\n/** Keyframes text for built-ins */\nfunction builtInKeyframes(name: string, cfg: AnimationConfig) {\n const hi = cfg.degreesHi ?? 15;\n const lo = cfg.degreesLow ?? -15;\n switch (name) {\n case \"Y360\":\n return `@keyframes Y360 { from { transform: rotateY(0deg) } to { transform: rotateY(360deg) } }`;\n case \"X360\":\n return `@keyframes X360 { from { transform: rotateX(0deg) } to { transform: rotateX(360deg) } }`;\n case \"Z360\":\n return `@keyframes Z360 { from { transform: rotateZ(0deg) } to { transform: rotateZ(360deg) } }`;\n case \"rockY\":\n return `@keyframes rockY { 0%{ transform: rotateY(${lo}deg) } 50%{ transform: rotateY(${hi}deg) } 100%{ transform: rotateY(${lo}deg) } }`;\n case \"rockX\":\n return `@keyframes rockX { 0%{ transform: rotateX(${lo}deg) } 50%{ transform: rotateX(${hi}deg) } 100%{ transform: rotateX(${lo}deg) } }`;\n default:\n // Custom names: let authors supply their own @keyframes in global CSS with that name.\n return \"\";\n }\n}\n\n/** Returns a concrete animation-name and ensures keyframes exist (for built-ins) */\nexport function resolveAnimation(cfg?: AnimationConfig): string | null {\n if (!cfg) return null;\n const name = cfg.name;\n const builtIn = builtInKeyframes(name, cfg);\n if (builtIn) {\n // Ensure single injection per built-in name\n const marker = `/*kf-${name}*/`;\n if (typeof document !== \"undefined\") {\n const tag = ensureStyleTag();\n if (!tag.innerHTML.includes(marker)) {\n inject(`${builtIn}\\n${marker}`);\n }\n }\n return name; // use built-in name as animation-name\n }\n // custom: use author-provided @keyframes by name\n return name;\n}\n\n/** Build the full CSS animation shorthand from a config and resolved name */\nexport function toAnimationShorthand(cfg?: AnimationConfig): string | null {\n const name = resolveAnimation(cfg);\n if (!cfg || !name) return null;\n const dur = (cfg.duration ?? 10) + \"s\";\n const delay = (cfg.delay ?? 0) + \"s\";\n const iter = cfg.iterationCount ?? \"infinite\";\n const dir = cfg.direction ?? \"normal\";\n const timing = cfg.timing ?? \"linear\";\n const fill = cfg.fillMode ?? \"forwards\";\n const play = cfg.animationPlayState ?? \"running\";\n // name duration timing delay iteration-count direction fill-mode play-state\n return `${name} ${dur} ${timing} ${delay} ${iter} ${dir} ${fill} ${play}`;\n}\n","import * as React from \"react\";\nimport type {\n ObjProps,\n FaceDef,\n FaceName,\n GlobalDef,\n} from \"../types\";\nimport { toAnimationShorthand } from \"../keyframes\";\nimport \"../styles/obj.css\";\n\n// Re-export the canonical ObjProps from types.ts\nexport type { ObjProps } from \"../types\";\n\n/* ------------------------------------------------------------------ */\n/* Face transform — 3D cuboid positions */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransform3D(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const hw = w / 2;\n const hh = h / 2;\n const hd = d / 2;\n\n switch (name as FaceName) {\n case \"front\":\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n case \"back\":\n return `translate(-50%, -50%) rotateY(180deg) translateZ(${hd}px)`;\n case \"left\":\n return `translate(-50%, -50%) rotateY(-90deg) translateZ(${hw}px)`;\n case \"right\":\n return `translate(-50%, -50%) rotateY(90deg) translateZ(${hw}px)`;\n case \"top\":\n return `translate(-50%, -50%) rotateX(90deg) translateZ(${hh}px)`;\n case \"bottom\":\n return `translate(-50%, -50%) rotateX(-90deg) translateZ(${hh}px)`;\n case \"top_front\":\n return `translate(-50%, -50%) rotateX(45deg) translateZ(${hh}px)`;\n case \"top_rear\":\n return `translate(-50%, -50%) rotateX(135deg) translateZ(${hh}px)`;\n case \"bottom_front\":\n return `translate(-50%, -50%) rotateX(-45deg) translateZ(${hh}px)`;\n case \"bottom_rear\":\n return `translate(-50%, -50%) rotateX(-135deg) translateZ(${hh}px)`;\n default:\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Face transform — flat (unfolded) positions */\n/* */\n/* Flat order: front | right | back | left */\n/* Centred on the midpoint of the full row. */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransformFlat(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n // Row layout (left to right): front(w) | right(d) | back(w) | left(d)\n // Total width = 2w + 2d. Centre of row at (w + d).\n const total = 2 * w + 2 * d;\n const half = total / 2;\n\n let cx: number;\n\n switch (name as FaceName) {\n case \"front\":\n cx = w / 2;\n break;\n case \"right\":\n cx = w + d / 2;\n break;\n case \"back\":\n cx = w + d + w / 2;\n break;\n case \"left\":\n cx = w + d + w + d / 2;\n break;\n case \"top\":\n case \"top_front\":\n case \"top_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(-${h}px)`;\n case \"bottom\":\n case \"bottom_front\":\n case \"bottom_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(${h}px)`;\n default:\n cx = w / 2;\n break;\n }\n\n return `translate(-50%, -50%) translateX(${cx - half}px)`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Parse a legacy CSS text string into a CSSProperties object */\n/* ------------------------------------------------------------------ */\n\nfunction parseCssText(css?: string): React.CSSProperties {\n if (!css) return {};\n const style: Record<string, string> = {};\n css.split(\";\").forEach((rule) => {\n const [prop, ...rest] = rule.split(\":\");\n if (!prop || rest.length === 0) return;\n const key = prop\n .trim()\n .replace(/-([a-z])/g, (_, c) => c.toUpperCase());\n style[key] = rest.join(\":\").trim();\n });\n return style as React.CSSProperties;\n}\n\n/* ------------------------------------------------------------------ */\n/* Resolve face dimensions for non-standard faces */\n/* ------------------------------------------------------------------ */\n\nfunction faceDimensions(\n name: string,\n w: number,\n h: number,\n d: number\n): { width: number; height: number } {\n switch (name as FaceName) {\n case \"left\":\n case \"right\":\n return { width: d, height: h };\n case \"top\":\n case \"bottom\":\n case \"top_front\":\n case \"top_rear\":\n case \"bottom_front\":\n case \"bottom_rear\":\n return { width: w, height: d };\n default:\n return { width: w, height: h };\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Build appearance style for a face (colours, borders, etc.) */\n/* Does NOT include position / transform / size. */\n/* ------------------------------------------------------------------ */\n\nfunction faceAppearance(\n face: FaceDef,\n globalDef?: GlobalDef\n): {\n style: React.CSSProperties;\n className: string;\n body: React.ReactNode;\n} {\n const globalStyle = parseCssText(globalDef?.css);\n const faceInlineStyle = parseCssText(face.css);\n\n const style: React.CSSProperties = {\n ...globalStyle,\n ...(globalDef?.style ?? {}),\n ...faceInlineStyle,\n ...(face.style ?? {}),\n };\n\n const className = [\"anim3d-face\", face.className]\n .filter(Boolean)\n .join(\" \");\n\n const body = face.body ?? globalDef?.body ?? null;\n\n return { style, className, body };\n}\n\n/* ------------------------------------------------------------------ */\n/* Default 6-sided cube when no faces are provided */\n/* ------------------------------------------------------------------ */\n\nconst DEFAULT_FACE_NAMES: FaceName[] = [\n \"front\",\n \"back\",\n \"left\",\n \"right\",\n \"top\",\n \"bottom\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Stagger order for oneAtATime (standard mode) */\n/* ------------------------------------------------------------------ */\n\nconst STAGGER_ORDER: string[] = [\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n \"top\",\n \"bottom\",\n \"top_front\",\n \"top_rear\",\n \"bottom_front\",\n \"bottom_rear\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Component */\n/* ------------------------------------------------------------------ */\n\nexport const Obj: React.FC<ObjProps> = React.memo(\n ({\n width = 160,\n height = 160,\n depth = 150,\n perspective = 600,\n perspectiveOrigin = \"50% 50%\",\n faces,\n global: globalDef,\n anim1,\n anim2,\n showCenterDiv = false,\n flat = false,\n transitionDuration = 1,\n oneAtATime = false,\n remainJoined = false,\n className,\n style,\n }) => {\n const w =\n typeof width === \"number\" ? width : parseFloat(String(width));\n const h =\n typeof height === \"number\" ? height : parseFloat(String(height));\n const d =\n typeof depth === \"number\" ? depth : parseFloat(String(depth));\n\n // Resolve animation shorthands\n const animation1 = toAnimationShorthand(anim1) ?? undefined;\n const animation2 = toAnimationShorthand(anim2) ?? undefined;\n\n // Determine which faces to render\n const faceList: FaceDef[] =\n faces && faces.length > 0\n ? faces\n : DEFAULT_FACE_NAMES.map((name) => ({ name }));\n\n const transitionCss = (delay = 0) =>\n `transform ${transitionDuration}s ease-in-out ${delay}s`;\n\n /* ============================================================ */\n /* Standard rendering (no remainJoined) */\n /* ============================================================ */\n\n const renderStandard = () =>\n faceList.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const transform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n\n const idx = STAGGER_ORDER.indexOf(face.name);\n const delay = oneAtATime\n ? (idx >= 0 ? idx : i) * transitionDuration\n : 0;\n\n return (\n <div\n key={face.name + \"-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform,\n transition: transitionCss(delay),\n }}\n >\n {body}\n </div>\n );\n });\n\n /* ============================================================ */\n /* Joined rendering — nested hinge structure */\n /* */\n /* Chain: front → right → back (hinged at shared edges) */\n /* Left is independent (the break‑point). */\n /* */\n /* Flat order: front | right | back | left (left on far right) */\n /* ============================================================ */\n\n const renderJoined = () => {\n const findFace = (n: string) =>\n faceList.find((f) => f.name === n);\n\n const frontFace = findFace(\"front\");\n const rightFace = findFace(\"right\");\n const backFace = findFace(\"back\");\n const leftFace = findFace(\"left\");\n\n const sideNames = new Set([\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n ]);\n const otherFaces = faceList.filter(\n (f) => !sideNames.has(f.name)\n );\n\n const step = oneAtATime ? transitionDuration : 0;\n\n /* Helper: render a single face element with merged styles */\n const renderFaceEl = (\n face: FaceDef | undefined,\n dims: { width: number; height: number },\n extra: React.CSSProperties,\n key: string\n ) => {\n if (!face) return null;\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={key}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n boxSizing: \"border-box\",\n ...extra,\n }}\n >\n {body}\n </div>\n );\n };\n\n return (\n <>\n {/* ---- Front face (anchor) ---- */}\n {renderFaceEl(\n frontFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: \"50%\",\n top: \"50%\",\n transform: flat\n ? \"translate(-50%, -50%)\"\n : `translate(-50%, -50%) translateZ(${d / 2}px)`,\n transition: transitionCss(0),\n },\n \"front-j\"\n )}\n\n {/* ---- Right hinge (pivots at front's right edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: `calc(50% + ${w / 2}px)`,\n top: \"50%\",\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : `translateZ(${d / 2}px) rotateY(90deg)`,\n transition: transitionCss(step),\n }}\n >\n {/* Right face */}\n {renderFaceEl(\n rightFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"right-j\"\n )}\n\n {/* ---- Back hinge (pivots at right's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: d,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 2),\n }}\n >\n {/* Back face */}\n {renderFaceEl(\n backFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"back-j\"\n )}\n\n {/* ---- Left hinge (pivots at back's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: w,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 3),\n }}\n >\n {/* Left face */}\n {renderFaceEl(\n leftFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"left-j\"\n )}\n </div>\n </div>\n </div>\n\n {/* ---- Non-side faces (top, bottom, etc.) ---- */}\n {otherFaces.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const xform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={face.name + \"-o-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform: xform,\n transition: transitionCss(0),\n }}\n >\n {body}\n </div>\n );\n })}\n </>\n );\n };\n\n /* ============================================================ */\n /* Render tree */\n /* ============================================================ */\n\n const cssVars = {\n \"--obj-w\": w + \"px\",\n \"--obj-h\": h + \"px\",\n \"--obj-d\": d + \"px\",\n } as React.CSSProperties;\n\n return (\n <div\n className={[\"anim3d-stage\", className]\n .filter(Boolean)\n .join(\" \")}\n style={{\n perspective,\n perspectiveOrigin,\n ...cssVars,\n ...style,\n }}\n data-anim-3d-obj\n role=\"img\"\n aria-label=\"3D object\"\n >\n {/* Outer animation wrapper (anim1) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation1,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {/* Inner animation wrapper (anim2) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation2,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {showCenterDiv && (\n <div className=\"anim3d-center\" />\n )}\n {remainJoined\n ? renderJoined()\n : renderStandard()}\n </div>\n </div>\n </div>\n );\n }\n);\n\nObj.displayName = \"Obj\";\n"]}
1
+ {"version":3,"sources":["../src/keyframes.ts","../src/components/Obj.tsx"],"names":["React","jsx","jsxs","Fragment"],"mappings":"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","file":"index.cjs","sourcesContent":["import type { AnimationConfig } from \"./types\";\n\n/** Create (or reuse) a <style> tag for dynamic keyframes */\nfunction ensureStyleTag(): HTMLStyleElement {\n let tag = document.getElementById(\n \"anim3d-keyframes\"\n ) as HTMLStyleElement | null;\n if (!tag) {\n tag = document.createElement(\"style\");\n tag.id = \"anim3d-keyframes\";\n document.head.appendChild(tag);\n }\n return tag;\n}\n\nfunction inject(css: string) {\n if (typeof document === \"undefined\") return; // SSR\n const tag = ensureStyleTag();\n tag.appendChild(document.createTextNode(css));\n}\n\n/** Keyframes text for built-ins */\nfunction builtInKeyframes(name: string, cfg: AnimationConfig) {\n const hi = cfg.degreesHi ?? 15;\n const lo = cfg.degreesLow ?? -15;\n switch (name) {\n case \"Y360\":\n return `@keyframes Y360 { from { transform: rotateY(0deg) } to { transform: rotateY(360deg) } }`;\n case \"X360\":\n return `@keyframes X360 { from { transform: rotateX(0deg) } to { transform: rotateX(360deg) } }`;\n case \"Z360\":\n return `@keyframes Z360 { from { transform: rotateZ(0deg) } to { transform: rotateZ(360deg) } }`;\n case \"rockY\":\n return `@keyframes rockY { 0%{ transform: rotateY(${lo}deg) } 50%{ transform: rotateY(${hi}deg) } 100%{ transform: rotateY(${lo}deg) } }`;\n case \"rockX\":\n return `@keyframes rockX { 0%{ transform: rotateX(${lo}deg) } 50%{ transform: rotateX(${hi}deg) } 100%{ transform: rotateX(${lo}deg) } }`;\n default:\n // Custom names: let authors supply their own @keyframes in global CSS with that name.\n return \"\";\n }\n}\n\n/** Returns a concrete animation-name and ensures keyframes exist (for built-ins) */\nexport function resolveAnimation(cfg?: AnimationConfig): string | null {\n if (!cfg) return null;\n const name = cfg.name;\n const builtIn = builtInKeyframes(name, cfg);\n if (builtIn) {\n // Ensure single injection per built-in name\n const marker = `/*kf-${name}*/`;\n if (typeof document !== \"undefined\") {\n const tag = ensureStyleTag();\n if (!tag.innerHTML.includes(marker)) {\n inject(`${builtIn}\\n${marker}`);\n }\n }\n return name; // use built-in name as animation-name\n }\n // custom: use author-provided @keyframes by name\n return name;\n}\n\n/** Build the full CSS animation shorthand from a config and resolved name */\nexport function toAnimationShorthand(cfg?: AnimationConfig): string | null {\n const name = resolveAnimation(cfg);\n if (!cfg || !name) return null;\n const dur = (cfg.duration ?? 10) + \"s\";\n const delay = (cfg.delay ?? 0) + \"s\";\n const iter = cfg.iterationCount ?? \"infinite\";\n const dir = cfg.direction ?? \"normal\";\n const timing = cfg.timing ?? \"linear\";\n const fill = cfg.fillMode ?? \"forwards\";\n const play = cfg.animationPlayState ?? \"running\";\n // name duration timing delay iteration-count direction fill-mode play-state\n return `${name} ${dur} ${timing} ${delay} ${iter} ${dir} ${fill} ${play}`;\n}\n","import * as React from \"react\";\nimport type {\n ObjProps,\n FaceDef,\n FaceName,\n GlobalDef,\n} from \"../types\";\nimport { toAnimationShorthand } from \"../keyframes\";\nimport \"../styles/obj.css\";\n\n// Re-export the canonical ObjProps from types.ts\nexport type { ObjProps } from \"../types\";\n\n/* ------------------------------------------------------------------ */\n/* Face transform — 3D cuboid positions */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransform3D(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const hw = w / 2;\n const hh = h / 2;\n const hd = d / 2;\n\n switch (name as FaceName) {\n case \"front\":\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n case \"back\":\n return `translate(-50%, -50%) rotateY(180deg) translateZ(${hd}px)`;\n case \"left\":\n return `translate(-50%, -50%) rotateY(-90deg) translateZ(${hw}px)`;\n case \"right\":\n return `translate(-50%, -50%) rotateY(90deg) translateZ(${hw}px)`;\n case \"top\":\n return `translate(-50%, -50%) rotateX(90deg) translateZ(${hh}px)`;\n case \"bottom\":\n return `translate(-50%, -50%) rotateX(-90deg) translateZ(${hh}px)`;\n case \"top_front\":\n return `translate(-50%, -50%) rotateX(45deg) translateZ(${hh}px)`;\n case \"top_rear\":\n return `translate(-50%, -50%) rotateX(135deg) translateZ(${hh}px)`;\n case \"bottom_front\":\n return `translate(-50%, -50%) rotateX(-45deg) translateZ(${hh}px)`;\n case \"bottom_rear\":\n return `translate(-50%, -50%) rotateX(-135deg) translateZ(${hh}px)`;\n default:\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Face transform — flat (unfolded) positions */\n/* */\n/* Flat order: front | right | back | left */\n/* Centred on the midpoint of the full row. */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransformFlat(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const total = 2 * w + 2 * d;\n const half = total / 2;\n\n let cx: number;\n\n switch (name as FaceName) {\n case \"front\":\n cx = w / 2;\n break;\n case \"right\":\n cx = w + d / 2;\n break;\n case \"back\":\n cx = w + d + w / 2;\n break;\n case \"left\":\n cx = w + d + w + d / 2;\n break;\n case \"top\":\n case \"top_front\":\n case \"top_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(-${h}px)`;\n case \"bottom\":\n case \"bottom_front\":\n case \"bottom_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(${h}px)`;\n default:\n cx = w / 2;\n break;\n }\n\n return `translate(-50%, -50%) translateX(${cx - half}px)`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Parse a legacy CSS text string into a CSSProperties object */\n/* ------------------------------------------------------------------ */\n\nfunction parseCssText(css?: string): React.CSSProperties {\n if (!css) return {};\n const style: Record<string, string> = {};\n css.split(\";\").forEach((rule) => {\n const [prop, ...rest] = rule.split(\":\");\n if (!prop || rest.length === 0) return;\n const key = prop\n .trim()\n .replace(/-([a-z])/g, (_, c) => c.toUpperCase());\n style[key] = rest.join(\":\").trim();\n });\n return style as React.CSSProperties;\n}\n\n/* ------------------------------------------------------------------ */\n/* Resolve face dimensions for non-standard faces */\n/* ------------------------------------------------------------------ */\n\nfunction faceDimensions(\n name: string,\n w: number,\n h: number,\n d: number\n): { width: number; height: number } {\n switch (name as FaceName) {\n case \"left\":\n case \"right\":\n return { width: d, height: h };\n case \"top\":\n case \"bottom\":\n case \"top_front\":\n case \"top_rear\":\n case \"bottom_front\":\n case \"bottom_rear\":\n return { width: w, height: d };\n default:\n return { width: w, height: h };\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Build appearance style for a face (colours, borders, etc.) */\n/* Does NOT include position / transform / size. */\n/* ------------------------------------------------------------------ */\n\nfunction faceAppearance(\n face: FaceDef,\n globalDef?: GlobalDef\n): {\n style: React.CSSProperties;\n className: string;\n body: React.ReactNode;\n} {\n const globalStyle = parseCssText(globalDef?.css);\n const faceInlineStyle = parseCssText(face.css);\n\n const style: React.CSSProperties = {\n ...globalStyle,\n ...(globalDef?.style ?? {}),\n ...faceInlineStyle,\n ...(face.style ?? {}),\n };\n\n const className = [\"anim3d-face\", face.className]\n .filter(Boolean)\n .join(\" \");\n\n const body = face.body ?? globalDef?.body ?? null;\n\n return { style, className, body };\n}\n\n/* ------------------------------------------------------------------ */\n/* Default 6-sided cube when no faces are provided */\n/* ------------------------------------------------------------------ */\n\nconst DEFAULT_FACE_NAMES: FaceName[] = [\n \"front\",\n \"back\",\n \"left\",\n \"right\",\n \"top\",\n \"bottom\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Stagger order for oneAtATime (standard mode) */\n/* ------------------------------------------------------------------ */\n\nconst STAGGER_ORDER: string[] = [\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n \"top\",\n \"bottom\",\n \"top_front\",\n \"top_rear\",\n \"bottom_front\",\n \"bottom_rear\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Component */\n/* ------------------------------------------------------------------ */\n\nexport const Obj: React.FC<ObjProps> = React.memo(\n ({\n width = 160,\n height = 160,\n depth = 150,\n perspective = 600,\n perspectiveOrigin = \"50% 50%\",\n faces,\n global: globalDef,\n anim1,\n anim2,\n showCenterDiv = false,\n flat = false,\n transitionDuration = 1,\n oneAtATime = false,\n remainJoined = false,\n ytilt = false,\n className,\n style,\n }) => {\n const w =\n typeof width === \"number\" ? width : parseFloat(String(width));\n const h =\n typeof height === \"number\" ? height : parseFloat(String(height));\n const d =\n typeof depth === \"number\" ? depth : parseFloat(String(depth));\n\n // Resolve animation shorthands\n const animation1 = toAnimationShorthand(anim1) ?? undefined;\n const animation2 = toAnimationShorthand(anim2) ?? undefined;\n\n // Determine which faces to render\n const faceList: FaceDef[] =\n faces && faces.length > 0\n ? faces\n : DEFAULT_FACE_NAMES.map((name) => ({ name }));\n\n const transitionCss = (delay = 0) =>\n `transform ${transitionDuration}s ease-in-out ${delay}s`;\n\n /* ============================================================ */\n /* Y-tilt — fire a one-shot rotateX(0→45→0) each time */\n /* flat changes. We alternate between two identical keyframe */\n /* names (a/b) so the browser re-triggers the animation. */\n /* ============================================================ */\n\n const tiltCount = React.useRef(0);\n const prevFlat = React.useRef(flat);\n const [tiltAnim, setTiltAnim] = React.useState<\n string | undefined\n >(undefined);\n\n React.useEffect(() => {\n if (flat !== prevFlat.current) {\n prevFlat.current = flat;\n if (ytilt) {\n tiltCount.current += 1;\n const sideCount = faceList.filter((f) =>\n [\"front\", \"right\", \"back\", \"left\"].includes(\n f.name\n )\n ).length;\n const totalDur = oneAtATime\n ? transitionDuration * sideCount\n : transitionDuration;\n const name =\n tiltCount.current % 2 === 0\n ? \"anim3d-ytilt-a\"\n : \"anim3d-ytilt-b\";\n setTiltAnim(\n `${name} ${totalDur}s ease-in-out 1 forwards`\n );\n // Clear animation after it completes so it can re-trigger\n const timer = setTimeout(\n () => setTiltAnim(undefined),\n totalDur * 1000 + 50\n );\n return () => clearTimeout(timer);\n }\n }\n }, [flat, ytilt, transitionDuration, oneAtATime, faceList]);\n\n /* ============================================================ */\n /* Standard rendering (no remainJoined) */\n /* ============================================================ */\n\n const renderStandard = () =>\n faceList.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const transform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n\n const idx = STAGGER_ORDER.indexOf(face.name);\n const delay = oneAtATime\n ? (idx >= 0 ? idx : i) * transitionDuration\n : 0;\n\n return (\n <div\n key={face.name + \"-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform,\n transition: transitionCss(delay),\n }}\n >\n {body}\n </div>\n );\n });\n\n /* ============================================================ */\n /* Joined rendering — nested hinge structure */\n /* */\n /* Chain: front → right → back → left (hinged at shared edges) */\n /* The left–front edge is the break‑point. */\n /* */\n /* Flat order: front | right | back | left (left on far right) */\n /* ============================================================ */\n\n const renderJoined = () => {\n const findFace = (n: string) =>\n faceList.find((f) => f.name === n);\n\n const frontFace = findFace(\"front\");\n const rightFace = findFace(\"right\");\n const backFace = findFace(\"back\");\n const leftFace = findFace(\"left\");\n\n const sideNames = new Set([\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n ]);\n const otherFaces = faceList.filter(\n (f) => !sideNames.has(f.name)\n );\n\n const step = oneAtATime ? transitionDuration : 0;\n\n /* Helper: render a single face element with merged styles */\n const renderFaceEl = (\n face: FaceDef | undefined,\n dims: { width: number; height: number },\n extra: React.CSSProperties,\n key: string\n ) => {\n if (!face) return null;\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={key}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n boxSizing: \"border-box\",\n ...extra,\n }}\n >\n {body}\n </div>\n );\n };\n\n return (\n <>\n {/* ---- Front face (anchor) ---- */}\n {renderFaceEl(\n frontFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: \"50%\",\n top: \"50%\",\n transform: flat\n ? \"translate(-50%, -50%)\"\n : `translate(-50%, -50%) translateZ(${d / 2}px)`,\n transition: transitionCss(0),\n },\n \"front-j\"\n )}\n\n {/* ---- Right hinge (pivots at front's right edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: `calc(50% + ${w / 2}px)`,\n top: \"50%\",\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : `translateZ(${d / 2}px) rotateY(90deg)`,\n transition: transitionCss(step),\n }}\n >\n {/* Right face */}\n {renderFaceEl(\n rightFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"right-j\"\n )}\n\n {/* ---- Back hinge (pivots at right's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: d,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 2),\n }}\n >\n {/* Back face */}\n {renderFaceEl(\n backFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"back-j\"\n )}\n\n {/* ---- Left hinge (pivots at back's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: w,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 3),\n }}\n >\n {/* Left face */}\n {renderFaceEl(\n leftFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"left-j\"\n )}\n </div>\n </div>\n </div>\n\n {/* ---- Non-side faces (top, bottom, etc.) ---- */}\n {otherFaces.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const xform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={face.name + \"-o-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform: xform,\n transition: transitionCss(0),\n }}\n >\n {body}\n </div>\n );\n })}\n </>\n );\n };\n\n /* ============================================================ */\n /* Render tree */\n /* ============================================================ */\n\n const cssVars = {\n \"--obj-w\": w + \"px\",\n \"--obj-h\": h + \"px\",\n \"--obj-d\": d + \"px\",\n } as React.CSSProperties;\n\n return (\n <div\n className={[\"anim3d-stage\", className]\n .filter(Boolean)\n .join(\" \")}\n style={{\n perspective,\n perspectiveOrigin,\n ...cssVars,\n ...style,\n }}\n data-anim-3d-obj\n role=\"img\"\n aria-label=\"3D object\"\n >\n {/* Y-tilt wrapper — sits between stage and anim wrappers */}\n <div\n style={{\n transformStyle: \"preserve-3d\",\n animation: tiltAnim,\n }}\n >\n {/* Outer animation wrapper (anim1) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation1,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {/* Inner animation wrapper (anim2) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation2,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {showCenterDiv && (\n <div className=\"anim3d-center\" />\n )}\n {remainJoined\n ? renderJoined()\n : renderStandard()}\n </div>\n </div>\n </div>\n </div>\n );\n }\n);\n\nObj.displayName = \"Obj\";\n"]}
package/dist/index.css CHANGED
@@ -32,4 +32,26 @@
32
32
  backface-visibility: visible;
33
33
  box-sizing: border-box;
34
34
  }
35
+ @keyframes anim3d-ytilt-a {
36
+ 0% {
37
+ transform: rotateX(0deg);
38
+ }
39
+ 50% {
40
+ transform: rotateX(45deg);
41
+ }
42
+ 100% {
43
+ transform: rotateX(0deg);
44
+ }
45
+ }
46
+ @keyframes anim3d-ytilt-b {
47
+ 0% {
48
+ transform: rotateX(0deg);
49
+ }
50
+ 50% {
51
+ transform: rotateX(45deg);
52
+ }
53
+ 100% {
54
+ transform: rotateX(0deg);
55
+ }
56
+ }
35
57
  /*# sourceMappingURL=index.css.map */
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/styles/obj.css"],"sourcesContent":[".anim3d-stage {\n position: relative;\n width: max-content;\n height: max-content;\n /* perspective is set inline via props */\n}\n\n.anim3d-wrapper {\n position: relative;\n transform-style: preserve-3d;\n width: var(--obj-w, 160px);\n height: var(--obj-h, 160px);\n}\n\n.anim3d-center {\n position: absolute;\n left: 50%;\n top: 50%;\n width: 2px;\n height: 2px;\n background: #f00;\n transform: translate(-50%, -50%);\n z-index: 10;\n pointer-events: none;\n}\n\n.anim3d-face {\n position: absolute;\n left: 50%;\n top: 50%;\n transform-style: preserve-3d;\n display: flex;\n align-items: center;\n justify-content: center;\n backface-visibility: visible;\n box-sizing: border-box;\n /* width/height/transform set inline per face */\n}\n"],"mappings":";AAAA,CAAC;AACE,YAAU;AACV,SAAO;AACP,UAAQ;AAEX;AAEA,CAAC;AACE,YAAU;AACV,mBAAiB;AACjB,SAAO,IAAI,OAAO,EAAE;AACpB,UAAQ,IAAI,OAAO,EAAE;AACxB;AAEA,CAAC;AACE,YAAU;AACV,QAAM;AACN,OAAK;AACL,SAAO;AACP,UAAQ;AACR,cAAY;AACZ,aAAW,UAAU,IAAI,EAAE;AAC3B,WAAS;AACT,kBAAgB;AACnB;AAEA,CAAC;AACE,YAAU;AACV,QAAM;AACN,OAAK;AACL,mBAAiB;AACjB,WAAS;AACT,eAAa;AACb,mBAAiB;AACjB,uBAAqB;AACrB,cAAY;AAEf;","names":[]}
1
+ {"version":3,"sources":["../src/styles/obj.css"],"sourcesContent":[".anim3d-stage {\n position: relative;\n width: max-content;\n height: max-content;\n /* perspective is set inline via props */\n}\n\n.anim3d-wrapper {\n position: relative;\n transform-style: preserve-3d;\n width: var(--obj-w, 160px);\n height: var(--obj-h, 160px);\n}\n\n.anim3d-center {\n position: absolute;\n left: 50%;\n top: 50%;\n width: 2px;\n height: 2px;\n background: #f00;\n transform: translate(-50%, -50%);\n z-index: 10;\n pointer-events: none;\n}\n\n.anim3d-face {\n position: absolute;\n left: 50%;\n top: 50%;\n transform-style: preserve-3d;\n display: flex;\n align-items: center;\n justify-content: center;\n backface-visibility: visible;\n box-sizing: border-box;\n /* width/height/transform set inline per face */\n}\n\n/* ---- Y-tilt: tips forward 45° during fold/unfold, then returns ---- */\n\n@keyframes anim3d-ytilt-a {\n 0% {\n transform: rotateX(0deg);\n }\n 50% {\n transform: rotateX(45deg);\n }\n 100% {\n transform: rotateX(0deg);\n }\n}\n\n@keyframes anim3d-ytilt-b {\n 0% {\n transform: rotateX(0deg);\n }\n 50% {\n transform: rotateX(45deg);\n }\n 100% {\n transform: rotateX(0deg);\n }\n}\n"],"mappings":";AAAA,CAAC;AACE,YAAU;AACV,SAAO;AACP,UAAQ;AAEX;AAEA,CAAC;AACE,YAAU;AACV,mBAAiB;AACjB,SAAO,IAAI,OAAO,EAAE;AACpB,UAAQ,IAAI,OAAO,EAAE;AACxB;AAEA,CAAC;AACE,YAAU;AACV,QAAM;AACN,OAAK;AACL,SAAO;AACP,UAAQ;AACR,cAAY;AACZ,aAAW,UAAU,IAAI,EAAE;AAC3B,WAAS;AACT,kBAAgB;AACnB;AAEA,CAAC;AACE,YAAU;AACV,QAAM;AACN,OAAK;AACL,mBAAiB;AACjB,WAAS;AACT,eAAa;AACb,mBAAiB;AACjB,uBAAqB;AACrB,cAAY;AAEf;AAIA,WAAW;AACR;AACG,eAAW,QAAQ;AACtB;AACA;AACG,eAAW,QAAQ;AACtB;AACA;AACG,eAAW,QAAQ;AACtB;AACH;AAEA,WAAW;AACR;AACG,eAAW,QAAQ;AACtB;AACA;AACG,eAAW,QAAQ;AACtB;AACA;AACG,eAAW,QAAQ;AACtB;AACH;","names":[]}
package/dist/index.d.mts CHANGED
@@ -51,6 +51,10 @@ type ObjProps = {
51
51
  /** When true, connected edges stay joined during unfold (front→right→back chain).
52
52
  * The left–front edge is the break point. */
53
53
  remainJoined?: boolean;
54
+ /** When true, the object tilts 45° on the X-axis (tips forward) during
55
+ * a fold/unfold transition, then returns to 0° when the transition
56
+ * completes. Only active while flat is changing. */
57
+ ytilt?: boolean;
54
58
  className?: string;
55
59
  style?: CSSProperties;
56
60
  };
package/dist/index.d.ts CHANGED
@@ -51,6 +51,10 @@ type ObjProps = {
51
51
  /** When true, connected edges stay joined during unfold (front→right→back chain).
52
52
  * The left–front edge is the break point. */
53
53
  remainJoined?: boolean;
54
+ /** When true, the object tilts 45° on the X-axis (tips forward) during
55
+ * a fold/unfold transition, then returns to 0° when the transition
56
+ * completes. Only active while flat is changing. */
57
+ ytilt?: boolean;
54
58
  className?: string;
55
59
  style?: CSSProperties;
56
60
  };
package/dist/index.js CHANGED
@@ -205,6 +205,7 @@ var Obj = React.memo(
205
205
  transitionDuration = 1,
206
206
  oneAtATime = false,
207
207
  remainJoined = false,
208
+ ytilt = false,
208
209
  className,
209
210
  style
210
211
  }) => {
@@ -215,6 +216,32 @@ var Obj = React.memo(
215
216
  const animation2 = toAnimationShorthand(anim2) ?? void 0;
216
217
  const faceList = faces && faces.length > 0 ? faces : DEFAULT_FACE_NAMES.map((name) => ({ name }));
217
218
  const transitionCss = (delay = 0) => `transform ${transitionDuration}s ease-in-out ${delay}s`;
219
+ const tiltCount = React.useRef(0);
220
+ const prevFlat = React.useRef(flat);
221
+ const [tiltAnim, setTiltAnim] = React.useState(void 0);
222
+ React.useEffect(() => {
223
+ if (flat !== prevFlat.current) {
224
+ prevFlat.current = flat;
225
+ if (ytilt) {
226
+ tiltCount.current += 1;
227
+ const sideCount = faceList.filter(
228
+ (f) => ["front", "right", "back", "left"].includes(
229
+ f.name
230
+ )
231
+ ).length;
232
+ const totalDur = oneAtATime ? transitionDuration * sideCount : transitionDuration;
233
+ const name = tiltCount.current % 2 === 0 ? "anim3d-ytilt-a" : "anim3d-ytilt-b";
234
+ setTiltAnim(
235
+ `${name} ${totalDur}s ease-in-out 1 forwards`
236
+ );
237
+ const timer = setTimeout(
238
+ () => setTiltAnim(void 0),
239
+ totalDur * 1e3 + 50
240
+ );
241
+ return () => clearTimeout(timer);
242
+ }
243
+ }
244
+ }, [flat, ytilt, transitionDuration, oneAtATime, faceList]);
218
245
  const renderStandard = () => faceList.map((face, i) => {
219
246
  const dims = faceDimensions(face.name, w, h, d);
220
247
  const transform = flat ? faceTransformFlat(face.name, w, h, d) : faceTransform3D(face.name, w, h, d);
@@ -428,27 +455,36 @@ var Obj = React.memo(
428
455
  children: /* @__PURE__ */ jsx(
429
456
  "div",
430
457
  {
431
- className: "anim3d-wrapper",
432
458
  style: {
433
- ...cssVars,
434
- animation: flat ? "none" : animation1,
435
459
  transformStyle: "preserve-3d",
436
- transition: transitionCss()
460
+ animation: tiltAnim
437
461
  },
438
- children: /* @__PURE__ */ jsxs(
462
+ children: /* @__PURE__ */ jsx(
439
463
  "div",
440
464
  {
441
465
  className: "anim3d-wrapper",
442
466
  style: {
443
467
  ...cssVars,
444
- animation: flat ? "none" : animation2,
468
+ animation: flat ? "none" : animation1,
445
469
  transformStyle: "preserve-3d",
446
470
  transition: transitionCss()
447
471
  },
448
- children: [
449
- showCenterDiv && /* @__PURE__ */ jsx("div", { className: "anim3d-center" }),
450
- remainJoined ? renderJoined() : renderStandard()
451
- ]
472
+ children: /* @__PURE__ */ jsxs(
473
+ "div",
474
+ {
475
+ className: "anim3d-wrapper",
476
+ style: {
477
+ ...cssVars,
478
+ animation: flat ? "none" : animation2,
479
+ transformStyle: "preserve-3d",
480
+ transition: transitionCss()
481
+ },
482
+ children: [
483
+ showCenterDiv && /* @__PURE__ */ jsx("div", { className: "anim3d-center" }),
484
+ remainJoined ? renderJoined() : renderStandard()
485
+ ]
486
+ }
487
+ )
452
488
  }
453
489
  )
454
490
  }
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/keyframes.ts","../src/components/Obj.tsx"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["import type { AnimationConfig } from \"./types\";\n\n/** Create (or reuse) a <style> tag for dynamic keyframes */\nfunction ensureStyleTag(): HTMLStyleElement {\n let tag = document.getElementById(\n \"anim3d-keyframes\"\n ) as HTMLStyleElement | null;\n if (!tag) {\n tag = document.createElement(\"style\");\n tag.id = \"anim3d-keyframes\";\n document.head.appendChild(tag);\n }\n return tag;\n}\n\nfunction inject(css: string) {\n if (typeof document === \"undefined\") return; // SSR\n const tag = ensureStyleTag();\n tag.appendChild(document.createTextNode(css));\n}\n\n/** Keyframes text for built-ins */\nfunction builtInKeyframes(name: string, cfg: AnimationConfig) {\n const hi = cfg.degreesHi ?? 15;\n const lo = cfg.degreesLow ?? -15;\n switch (name) {\n case \"Y360\":\n return `@keyframes Y360 { from { transform: rotateY(0deg) } to { transform: rotateY(360deg) } }`;\n case \"X360\":\n return `@keyframes X360 { from { transform: rotateX(0deg) } to { transform: rotateX(360deg) } }`;\n case \"Z360\":\n return `@keyframes Z360 { from { transform: rotateZ(0deg) } to { transform: rotateZ(360deg) } }`;\n case \"rockY\":\n return `@keyframes rockY { 0%{ transform: rotateY(${lo}deg) } 50%{ transform: rotateY(${hi}deg) } 100%{ transform: rotateY(${lo}deg) } }`;\n case \"rockX\":\n return `@keyframes rockX { 0%{ transform: rotateX(${lo}deg) } 50%{ transform: rotateX(${hi}deg) } 100%{ transform: rotateX(${lo}deg) } }`;\n default:\n // Custom names: let authors supply their own @keyframes in global CSS with that name.\n return \"\";\n }\n}\n\n/** Returns a concrete animation-name and ensures keyframes exist (for built-ins) */\nexport function resolveAnimation(cfg?: AnimationConfig): string | null {\n if (!cfg) return null;\n const name = cfg.name;\n const builtIn = builtInKeyframes(name, cfg);\n if (builtIn) {\n // Ensure single injection per built-in name\n const marker = `/*kf-${name}*/`;\n if (typeof document !== \"undefined\") {\n const tag = ensureStyleTag();\n if (!tag.innerHTML.includes(marker)) {\n inject(`${builtIn}\\n${marker}`);\n }\n }\n return name; // use built-in name as animation-name\n }\n // custom: use author-provided @keyframes by name\n return name;\n}\n\n/** Build the full CSS animation shorthand from a config and resolved name */\nexport function toAnimationShorthand(cfg?: AnimationConfig): string | null {\n const name = resolveAnimation(cfg);\n if (!cfg || !name) return null;\n const dur = (cfg.duration ?? 10) + \"s\";\n const delay = (cfg.delay ?? 0) + \"s\";\n const iter = cfg.iterationCount ?? \"infinite\";\n const dir = cfg.direction ?? \"normal\";\n const timing = cfg.timing ?? \"linear\";\n const fill = cfg.fillMode ?? \"forwards\";\n const play = cfg.animationPlayState ?? \"running\";\n // name duration timing delay iteration-count direction fill-mode play-state\n return `${name} ${dur} ${timing} ${delay} ${iter} ${dir} ${fill} ${play}`;\n}\n","import * as React from \"react\";\nimport type {\n ObjProps,\n FaceDef,\n FaceName,\n GlobalDef,\n} from \"../types\";\nimport { toAnimationShorthand } from \"../keyframes\";\nimport \"../styles/obj.css\";\n\n// Re-export the canonical ObjProps from types.ts\nexport type { ObjProps } from \"../types\";\n\n/* ------------------------------------------------------------------ */\n/* Face transform — 3D cuboid positions */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransform3D(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const hw = w / 2;\n const hh = h / 2;\n const hd = d / 2;\n\n switch (name as FaceName) {\n case \"front\":\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n case \"back\":\n return `translate(-50%, -50%) rotateY(180deg) translateZ(${hd}px)`;\n case \"left\":\n return `translate(-50%, -50%) rotateY(-90deg) translateZ(${hw}px)`;\n case \"right\":\n return `translate(-50%, -50%) rotateY(90deg) translateZ(${hw}px)`;\n case \"top\":\n return `translate(-50%, -50%) rotateX(90deg) translateZ(${hh}px)`;\n case \"bottom\":\n return `translate(-50%, -50%) rotateX(-90deg) translateZ(${hh}px)`;\n case \"top_front\":\n return `translate(-50%, -50%) rotateX(45deg) translateZ(${hh}px)`;\n case \"top_rear\":\n return `translate(-50%, -50%) rotateX(135deg) translateZ(${hh}px)`;\n case \"bottom_front\":\n return `translate(-50%, -50%) rotateX(-45deg) translateZ(${hh}px)`;\n case \"bottom_rear\":\n return `translate(-50%, -50%) rotateX(-135deg) translateZ(${hh}px)`;\n default:\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Face transform — flat (unfolded) positions */\n/* */\n/* Flat order: front | right | back | left */\n/* Centred on the midpoint of the full row. */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransformFlat(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n // Row layout (left to right): front(w) | right(d) | back(w) | left(d)\n // Total width = 2w + 2d. Centre of row at (w + d).\n const total = 2 * w + 2 * d;\n const half = total / 2;\n\n let cx: number;\n\n switch (name as FaceName) {\n case \"front\":\n cx = w / 2;\n break;\n case \"right\":\n cx = w + d / 2;\n break;\n case \"back\":\n cx = w + d + w / 2;\n break;\n case \"left\":\n cx = w + d + w + d / 2;\n break;\n case \"top\":\n case \"top_front\":\n case \"top_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(-${h}px)`;\n case \"bottom\":\n case \"bottom_front\":\n case \"bottom_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(${h}px)`;\n default:\n cx = w / 2;\n break;\n }\n\n return `translate(-50%, -50%) translateX(${cx - half}px)`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Parse a legacy CSS text string into a CSSProperties object */\n/* ------------------------------------------------------------------ */\n\nfunction parseCssText(css?: string): React.CSSProperties {\n if (!css) return {};\n const style: Record<string, string> = {};\n css.split(\";\").forEach((rule) => {\n const [prop, ...rest] = rule.split(\":\");\n if (!prop || rest.length === 0) return;\n const key = prop\n .trim()\n .replace(/-([a-z])/g, (_, c) => c.toUpperCase());\n style[key] = rest.join(\":\").trim();\n });\n return style as React.CSSProperties;\n}\n\n/* ------------------------------------------------------------------ */\n/* Resolve face dimensions for non-standard faces */\n/* ------------------------------------------------------------------ */\n\nfunction faceDimensions(\n name: string,\n w: number,\n h: number,\n d: number\n): { width: number; height: number } {\n switch (name as FaceName) {\n case \"left\":\n case \"right\":\n return { width: d, height: h };\n case \"top\":\n case \"bottom\":\n case \"top_front\":\n case \"top_rear\":\n case \"bottom_front\":\n case \"bottom_rear\":\n return { width: w, height: d };\n default:\n return { width: w, height: h };\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Build appearance style for a face (colours, borders, etc.) */\n/* Does NOT include position / transform / size. */\n/* ------------------------------------------------------------------ */\n\nfunction faceAppearance(\n face: FaceDef,\n globalDef?: GlobalDef\n): {\n style: React.CSSProperties;\n className: string;\n body: React.ReactNode;\n} {\n const globalStyle = parseCssText(globalDef?.css);\n const faceInlineStyle = parseCssText(face.css);\n\n const style: React.CSSProperties = {\n ...globalStyle,\n ...(globalDef?.style ?? {}),\n ...faceInlineStyle,\n ...(face.style ?? {}),\n };\n\n const className = [\"anim3d-face\", face.className]\n .filter(Boolean)\n .join(\" \");\n\n const body = face.body ?? globalDef?.body ?? null;\n\n return { style, className, body };\n}\n\n/* ------------------------------------------------------------------ */\n/* Default 6-sided cube when no faces are provided */\n/* ------------------------------------------------------------------ */\n\nconst DEFAULT_FACE_NAMES: FaceName[] = [\n \"front\",\n \"back\",\n \"left\",\n \"right\",\n \"top\",\n \"bottom\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Stagger order for oneAtATime (standard mode) */\n/* ------------------------------------------------------------------ */\n\nconst STAGGER_ORDER: string[] = [\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n \"top\",\n \"bottom\",\n \"top_front\",\n \"top_rear\",\n \"bottom_front\",\n \"bottom_rear\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Component */\n/* ------------------------------------------------------------------ */\n\nexport const Obj: React.FC<ObjProps> = React.memo(\n ({\n width = 160,\n height = 160,\n depth = 150,\n perspective = 600,\n perspectiveOrigin = \"50% 50%\",\n faces,\n global: globalDef,\n anim1,\n anim2,\n showCenterDiv = false,\n flat = false,\n transitionDuration = 1,\n oneAtATime = false,\n remainJoined = false,\n className,\n style,\n }) => {\n const w =\n typeof width === \"number\" ? width : parseFloat(String(width));\n const h =\n typeof height === \"number\" ? height : parseFloat(String(height));\n const d =\n typeof depth === \"number\" ? depth : parseFloat(String(depth));\n\n // Resolve animation shorthands\n const animation1 = toAnimationShorthand(anim1) ?? undefined;\n const animation2 = toAnimationShorthand(anim2) ?? undefined;\n\n // Determine which faces to render\n const faceList: FaceDef[] =\n faces && faces.length > 0\n ? faces\n : DEFAULT_FACE_NAMES.map((name) => ({ name }));\n\n const transitionCss = (delay = 0) =>\n `transform ${transitionDuration}s ease-in-out ${delay}s`;\n\n /* ============================================================ */\n /* Standard rendering (no remainJoined) */\n /* ============================================================ */\n\n const renderStandard = () =>\n faceList.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const transform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n\n const idx = STAGGER_ORDER.indexOf(face.name);\n const delay = oneAtATime\n ? (idx >= 0 ? idx : i) * transitionDuration\n : 0;\n\n return (\n <div\n key={face.name + \"-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform,\n transition: transitionCss(delay),\n }}\n >\n {body}\n </div>\n );\n });\n\n /* ============================================================ */\n /* Joined rendering — nested hinge structure */\n /* */\n /* Chain: front → right → back (hinged at shared edges) */\n /* Left is independent (the break‑point). */\n /* */\n /* Flat order: front | right | back | left (left on far right) */\n /* ============================================================ */\n\n const renderJoined = () => {\n const findFace = (n: string) =>\n faceList.find((f) => f.name === n);\n\n const frontFace = findFace(\"front\");\n const rightFace = findFace(\"right\");\n const backFace = findFace(\"back\");\n const leftFace = findFace(\"left\");\n\n const sideNames = new Set([\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n ]);\n const otherFaces = faceList.filter(\n (f) => !sideNames.has(f.name)\n );\n\n const step = oneAtATime ? transitionDuration : 0;\n\n /* Helper: render a single face element with merged styles */\n const renderFaceEl = (\n face: FaceDef | undefined,\n dims: { width: number; height: number },\n extra: React.CSSProperties,\n key: string\n ) => {\n if (!face) return null;\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={key}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n boxSizing: \"border-box\",\n ...extra,\n }}\n >\n {body}\n </div>\n );\n };\n\n return (\n <>\n {/* ---- Front face (anchor) ---- */}\n {renderFaceEl(\n frontFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: \"50%\",\n top: \"50%\",\n transform: flat\n ? \"translate(-50%, -50%)\"\n : `translate(-50%, -50%) translateZ(${d / 2}px)`,\n transition: transitionCss(0),\n },\n \"front-j\"\n )}\n\n {/* ---- Right hinge (pivots at front's right edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: `calc(50% + ${w / 2}px)`,\n top: \"50%\",\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : `translateZ(${d / 2}px) rotateY(90deg)`,\n transition: transitionCss(step),\n }}\n >\n {/* Right face */}\n {renderFaceEl(\n rightFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"right-j\"\n )}\n\n {/* ---- Back hinge (pivots at right's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: d,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 2),\n }}\n >\n {/* Back face */}\n {renderFaceEl(\n backFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"back-j\"\n )}\n\n {/* ---- Left hinge (pivots at back's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: w,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 3),\n }}\n >\n {/* Left face */}\n {renderFaceEl(\n leftFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"left-j\"\n )}\n </div>\n </div>\n </div>\n\n {/* ---- Non-side faces (top, bottom, etc.) ---- */}\n {otherFaces.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const xform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={face.name + \"-o-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform: xform,\n transition: transitionCss(0),\n }}\n >\n {body}\n </div>\n );\n })}\n </>\n );\n };\n\n /* ============================================================ */\n /* Render tree */\n /* ============================================================ */\n\n const cssVars = {\n \"--obj-w\": w + \"px\",\n \"--obj-h\": h + \"px\",\n \"--obj-d\": d + \"px\",\n } as React.CSSProperties;\n\n return (\n <div\n className={[\"anim3d-stage\", className]\n .filter(Boolean)\n .join(\" \")}\n style={{\n perspective,\n perspectiveOrigin,\n ...cssVars,\n ...style,\n }}\n data-anim-3d-obj\n role=\"img\"\n aria-label=\"3D object\"\n >\n {/* Outer animation wrapper (anim1) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation1,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {/* Inner animation wrapper (anim2) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation2,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {showCenterDiv && (\n <div className=\"anim3d-center\" />\n )}\n {remainJoined\n ? renderJoined()\n : renderStandard()}\n </div>\n </div>\n </div>\n );\n }\n);\n\nObj.displayName = \"Obj\";\n"]}
1
+ {"version":3,"sources":["../src/keyframes.ts","../src/components/Obj.tsx"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["import type { AnimationConfig } from \"./types\";\n\n/** Create (or reuse) a <style> tag for dynamic keyframes */\nfunction ensureStyleTag(): HTMLStyleElement {\n let tag = document.getElementById(\n \"anim3d-keyframes\"\n ) as HTMLStyleElement | null;\n if (!tag) {\n tag = document.createElement(\"style\");\n tag.id = \"anim3d-keyframes\";\n document.head.appendChild(tag);\n }\n return tag;\n}\n\nfunction inject(css: string) {\n if (typeof document === \"undefined\") return; // SSR\n const tag = ensureStyleTag();\n tag.appendChild(document.createTextNode(css));\n}\n\n/** Keyframes text for built-ins */\nfunction builtInKeyframes(name: string, cfg: AnimationConfig) {\n const hi = cfg.degreesHi ?? 15;\n const lo = cfg.degreesLow ?? -15;\n switch (name) {\n case \"Y360\":\n return `@keyframes Y360 { from { transform: rotateY(0deg) } to { transform: rotateY(360deg) } }`;\n case \"X360\":\n return `@keyframes X360 { from { transform: rotateX(0deg) } to { transform: rotateX(360deg) } }`;\n case \"Z360\":\n return `@keyframes Z360 { from { transform: rotateZ(0deg) } to { transform: rotateZ(360deg) } }`;\n case \"rockY\":\n return `@keyframes rockY { 0%{ transform: rotateY(${lo}deg) } 50%{ transform: rotateY(${hi}deg) } 100%{ transform: rotateY(${lo}deg) } }`;\n case \"rockX\":\n return `@keyframes rockX { 0%{ transform: rotateX(${lo}deg) } 50%{ transform: rotateX(${hi}deg) } 100%{ transform: rotateX(${lo}deg) } }`;\n default:\n // Custom names: let authors supply their own @keyframes in global CSS with that name.\n return \"\";\n }\n}\n\n/** Returns a concrete animation-name and ensures keyframes exist (for built-ins) */\nexport function resolveAnimation(cfg?: AnimationConfig): string | null {\n if (!cfg) return null;\n const name = cfg.name;\n const builtIn = builtInKeyframes(name, cfg);\n if (builtIn) {\n // Ensure single injection per built-in name\n const marker = `/*kf-${name}*/`;\n if (typeof document !== \"undefined\") {\n const tag = ensureStyleTag();\n if (!tag.innerHTML.includes(marker)) {\n inject(`${builtIn}\\n${marker}`);\n }\n }\n return name; // use built-in name as animation-name\n }\n // custom: use author-provided @keyframes by name\n return name;\n}\n\n/** Build the full CSS animation shorthand from a config and resolved name */\nexport function toAnimationShorthand(cfg?: AnimationConfig): string | null {\n const name = resolveAnimation(cfg);\n if (!cfg || !name) return null;\n const dur = (cfg.duration ?? 10) + \"s\";\n const delay = (cfg.delay ?? 0) + \"s\";\n const iter = cfg.iterationCount ?? \"infinite\";\n const dir = cfg.direction ?? \"normal\";\n const timing = cfg.timing ?? \"linear\";\n const fill = cfg.fillMode ?? \"forwards\";\n const play = cfg.animationPlayState ?? \"running\";\n // name duration timing delay iteration-count direction fill-mode play-state\n return `${name} ${dur} ${timing} ${delay} ${iter} ${dir} ${fill} ${play}`;\n}\n","import * as React from \"react\";\nimport type {\n ObjProps,\n FaceDef,\n FaceName,\n GlobalDef,\n} from \"../types\";\nimport { toAnimationShorthand } from \"../keyframes\";\nimport \"../styles/obj.css\";\n\n// Re-export the canonical ObjProps from types.ts\nexport type { ObjProps } from \"../types\";\n\n/* ------------------------------------------------------------------ */\n/* Face transform — 3D cuboid positions */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransform3D(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const hw = w / 2;\n const hh = h / 2;\n const hd = d / 2;\n\n switch (name as FaceName) {\n case \"front\":\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n case \"back\":\n return `translate(-50%, -50%) rotateY(180deg) translateZ(${hd}px)`;\n case \"left\":\n return `translate(-50%, -50%) rotateY(-90deg) translateZ(${hw}px)`;\n case \"right\":\n return `translate(-50%, -50%) rotateY(90deg) translateZ(${hw}px)`;\n case \"top\":\n return `translate(-50%, -50%) rotateX(90deg) translateZ(${hh}px)`;\n case \"bottom\":\n return `translate(-50%, -50%) rotateX(-90deg) translateZ(${hh}px)`;\n case \"top_front\":\n return `translate(-50%, -50%) rotateX(45deg) translateZ(${hh}px)`;\n case \"top_rear\":\n return `translate(-50%, -50%) rotateX(135deg) translateZ(${hh}px)`;\n case \"bottom_front\":\n return `translate(-50%, -50%) rotateX(-45deg) translateZ(${hh}px)`;\n case \"bottom_rear\":\n return `translate(-50%, -50%) rotateX(-135deg) translateZ(${hh}px)`;\n default:\n return `translate(-50%, -50%) translateZ(${hd}px)`;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Face transform — flat (unfolded) positions */\n/* */\n/* Flat order: front | right | back | left */\n/* Centred on the midpoint of the full row. */\n/* ------------------------------------------------------------------ */\n\nfunction faceTransformFlat(\n name: string,\n w: number,\n h: number,\n d: number\n): string {\n const total = 2 * w + 2 * d;\n const half = total / 2;\n\n let cx: number;\n\n switch (name as FaceName) {\n case \"front\":\n cx = w / 2;\n break;\n case \"right\":\n cx = w + d / 2;\n break;\n case \"back\":\n cx = w + d + w / 2;\n break;\n case \"left\":\n cx = w + d + w + d / 2;\n break;\n case \"top\":\n case \"top_front\":\n case \"top_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(-${h}px)`;\n case \"bottom\":\n case \"bottom_front\":\n case \"bottom_rear\":\n cx = w / 2;\n return `translate(-50%, -50%) translateX(${cx - half}px) translateY(${h}px)`;\n default:\n cx = w / 2;\n break;\n }\n\n return `translate(-50%, -50%) translateX(${cx - half}px)`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Parse a legacy CSS text string into a CSSProperties object */\n/* ------------------------------------------------------------------ */\n\nfunction parseCssText(css?: string): React.CSSProperties {\n if (!css) return {};\n const style: Record<string, string> = {};\n css.split(\";\").forEach((rule) => {\n const [prop, ...rest] = rule.split(\":\");\n if (!prop || rest.length === 0) return;\n const key = prop\n .trim()\n .replace(/-([a-z])/g, (_, c) => c.toUpperCase());\n style[key] = rest.join(\":\").trim();\n });\n return style as React.CSSProperties;\n}\n\n/* ------------------------------------------------------------------ */\n/* Resolve face dimensions for non-standard faces */\n/* ------------------------------------------------------------------ */\n\nfunction faceDimensions(\n name: string,\n w: number,\n h: number,\n d: number\n): { width: number; height: number } {\n switch (name as FaceName) {\n case \"left\":\n case \"right\":\n return { width: d, height: h };\n case \"top\":\n case \"bottom\":\n case \"top_front\":\n case \"top_rear\":\n case \"bottom_front\":\n case \"bottom_rear\":\n return { width: w, height: d };\n default:\n return { width: w, height: h };\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Build appearance style for a face (colours, borders, etc.) */\n/* Does NOT include position / transform / size. */\n/* ------------------------------------------------------------------ */\n\nfunction faceAppearance(\n face: FaceDef,\n globalDef?: GlobalDef\n): {\n style: React.CSSProperties;\n className: string;\n body: React.ReactNode;\n} {\n const globalStyle = parseCssText(globalDef?.css);\n const faceInlineStyle = parseCssText(face.css);\n\n const style: React.CSSProperties = {\n ...globalStyle,\n ...(globalDef?.style ?? {}),\n ...faceInlineStyle,\n ...(face.style ?? {}),\n };\n\n const className = [\"anim3d-face\", face.className]\n .filter(Boolean)\n .join(\" \");\n\n const body = face.body ?? globalDef?.body ?? null;\n\n return { style, className, body };\n}\n\n/* ------------------------------------------------------------------ */\n/* Default 6-sided cube when no faces are provided */\n/* ------------------------------------------------------------------ */\n\nconst DEFAULT_FACE_NAMES: FaceName[] = [\n \"front\",\n \"back\",\n \"left\",\n \"right\",\n \"top\",\n \"bottom\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Stagger order for oneAtATime (standard mode) */\n/* ------------------------------------------------------------------ */\n\nconst STAGGER_ORDER: string[] = [\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n \"top\",\n \"bottom\",\n \"top_front\",\n \"top_rear\",\n \"bottom_front\",\n \"bottom_rear\",\n];\n\n/* ------------------------------------------------------------------ */\n/* Component */\n/* ------------------------------------------------------------------ */\n\nexport const Obj: React.FC<ObjProps> = React.memo(\n ({\n width = 160,\n height = 160,\n depth = 150,\n perspective = 600,\n perspectiveOrigin = \"50% 50%\",\n faces,\n global: globalDef,\n anim1,\n anim2,\n showCenterDiv = false,\n flat = false,\n transitionDuration = 1,\n oneAtATime = false,\n remainJoined = false,\n ytilt = false,\n className,\n style,\n }) => {\n const w =\n typeof width === \"number\" ? width : parseFloat(String(width));\n const h =\n typeof height === \"number\" ? height : parseFloat(String(height));\n const d =\n typeof depth === \"number\" ? depth : parseFloat(String(depth));\n\n // Resolve animation shorthands\n const animation1 = toAnimationShorthand(anim1) ?? undefined;\n const animation2 = toAnimationShorthand(anim2) ?? undefined;\n\n // Determine which faces to render\n const faceList: FaceDef[] =\n faces && faces.length > 0\n ? faces\n : DEFAULT_FACE_NAMES.map((name) => ({ name }));\n\n const transitionCss = (delay = 0) =>\n `transform ${transitionDuration}s ease-in-out ${delay}s`;\n\n /* ============================================================ */\n /* Y-tilt — fire a one-shot rotateX(0→45→0) each time */\n /* flat changes. We alternate between two identical keyframe */\n /* names (a/b) so the browser re-triggers the animation. */\n /* ============================================================ */\n\n const tiltCount = React.useRef(0);\n const prevFlat = React.useRef(flat);\n const [tiltAnim, setTiltAnim] = React.useState<\n string | undefined\n >(undefined);\n\n React.useEffect(() => {\n if (flat !== prevFlat.current) {\n prevFlat.current = flat;\n if (ytilt) {\n tiltCount.current += 1;\n const sideCount = faceList.filter((f) =>\n [\"front\", \"right\", \"back\", \"left\"].includes(\n f.name\n )\n ).length;\n const totalDur = oneAtATime\n ? transitionDuration * sideCount\n : transitionDuration;\n const name =\n tiltCount.current % 2 === 0\n ? \"anim3d-ytilt-a\"\n : \"anim3d-ytilt-b\";\n setTiltAnim(\n `${name} ${totalDur}s ease-in-out 1 forwards`\n );\n // Clear animation after it completes so it can re-trigger\n const timer = setTimeout(\n () => setTiltAnim(undefined),\n totalDur * 1000 + 50\n );\n return () => clearTimeout(timer);\n }\n }\n }, [flat, ytilt, transitionDuration, oneAtATime, faceList]);\n\n /* ============================================================ */\n /* Standard rendering (no remainJoined) */\n /* ============================================================ */\n\n const renderStandard = () =>\n faceList.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const transform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n\n const idx = STAGGER_ORDER.indexOf(face.name);\n const delay = oneAtATime\n ? (idx >= 0 ? idx : i) * transitionDuration\n : 0;\n\n return (\n <div\n key={face.name + \"-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform,\n transition: transitionCss(delay),\n }}\n >\n {body}\n </div>\n );\n });\n\n /* ============================================================ */\n /* Joined rendering — nested hinge structure */\n /* */\n /* Chain: front → right → back → left (hinged at shared edges) */\n /* The left–front edge is the break‑point. */\n /* */\n /* Flat order: front | right | back | left (left on far right) */\n /* ============================================================ */\n\n const renderJoined = () => {\n const findFace = (n: string) =>\n faceList.find((f) => f.name === n);\n\n const frontFace = findFace(\"front\");\n const rightFace = findFace(\"right\");\n const backFace = findFace(\"back\");\n const leftFace = findFace(\"left\");\n\n const sideNames = new Set([\n \"front\",\n \"right\",\n \"back\",\n \"left\",\n ]);\n const otherFaces = faceList.filter(\n (f) => !sideNames.has(f.name)\n );\n\n const step = oneAtATime ? transitionDuration : 0;\n\n /* Helper: render a single face element with merged styles */\n const renderFaceEl = (\n face: FaceDef | undefined,\n dims: { width: number; height: number },\n extra: React.CSSProperties,\n key: string\n ) => {\n if (!face) return null;\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={key}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n boxSizing: \"border-box\",\n ...extra,\n }}\n >\n {body}\n </div>\n );\n };\n\n return (\n <>\n {/* ---- Front face (anchor) ---- */}\n {renderFaceEl(\n frontFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: \"50%\",\n top: \"50%\",\n transform: flat\n ? \"translate(-50%, -50%)\"\n : `translate(-50%, -50%) translateZ(${d / 2}px)`,\n transition: transitionCss(0),\n },\n \"front-j\"\n )}\n\n {/* ---- Right hinge (pivots at front's right edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: `calc(50% + ${w / 2}px)`,\n top: \"50%\",\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : `translateZ(${d / 2}px) rotateY(90deg)`,\n transition: transitionCss(step),\n }}\n >\n {/* Right face */}\n {renderFaceEl(\n rightFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"right-j\"\n )}\n\n {/* ---- Back hinge (pivots at right's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: d,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 2),\n }}\n >\n {/* Back face */}\n {renderFaceEl(\n backFace,\n { width: w, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"back-j\"\n )}\n\n {/* ---- Left hinge (pivots at back's far edge) ---- */}\n <div\n style={{\n position: \"absolute\",\n left: w,\n top: 0,\n width: 0,\n height: 0,\n transformOrigin: \"0 0\",\n transformStyle: \"preserve-3d\",\n transform: flat\n ? \"none\"\n : \"rotateY(90deg)\",\n transition: transitionCss(step * 3),\n }}\n >\n {/* Left face */}\n {renderFaceEl(\n leftFace,\n { width: d, height: h },\n {\n position: \"absolute\",\n left: 0,\n top: 0,\n transform: \"translateY(-50%)\",\n },\n \"left-j\"\n )}\n </div>\n </div>\n </div>\n\n {/* ---- Non-side faces (top, bottom, etc.) ---- */}\n {otherFaces.map((face, i) => {\n const dims = faceDimensions(face.name, w, h, d);\n const xform = flat\n ? faceTransformFlat(face.name, w, h, d)\n : faceTransform3D(face.name, w, h, d);\n const {\n style: fStyle,\n className: fCls,\n body,\n } = faceAppearance(face, globalDef);\n return (\n <div\n key={face.name + \"-o-\" + i}\n className={fCls}\n style={{\n ...fStyle,\n width: dims.width,\n height: dims.height,\n transform: xform,\n transition: transitionCss(0),\n }}\n >\n {body}\n </div>\n );\n })}\n </>\n );\n };\n\n /* ============================================================ */\n /* Render tree */\n /* ============================================================ */\n\n const cssVars = {\n \"--obj-w\": w + \"px\",\n \"--obj-h\": h + \"px\",\n \"--obj-d\": d + \"px\",\n } as React.CSSProperties;\n\n return (\n <div\n className={[\"anim3d-stage\", className]\n .filter(Boolean)\n .join(\" \")}\n style={{\n perspective,\n perspectiveOrigin,\n ...cssVars,\n ...style,\n }}\n data-anim-3d-obj\n role=\"img\"\n aria-label=\"3D object\"\n >\n {/* Y-tilt wrapper — sits between stage and anim wrappers */}\n <div\n style={{\n transformStyle: \"preserve-3d\",\n animation: tiltAnim,\n }}\n >\n {/* Outer animation wrapper (anim1) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation1,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {/* Inner animation wrapper (anim2) */}\n <div\n className=\"anim3d-wrapper\"\n style={{\n ...cssVars,\n animation: flat ? \"none\" : animation2,\n transformStyle: \"preserve-3d\",\n transition: transitionCss(),\n }}\n >\n {showCenterDiv && (\n <div className=\"anim3d-center\" />\n )}\n {remainJoined\n ? renderJoined()\n : renderStandard()}\n </div>\n </div>\n </div>\n </div>\n );\n }\n);\n\nObj.displayName = \"Obj\";\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "anim-3d-obj",
3
- "version": "2.0.6",
3
+ "version": "2.0.8",
4
4
  "description": "Configurable 3D object with animated rotations and face content",
5
5
  "license": "MIT",
6
6
  "author": "mdnelles",