animation variety: per-scene motion signatures (occlusion-safe scenes only) - aperitif tumble, Course IV curved-arc trajectories, Course V spiral orbit-in; achieved via manual per-frame transform math, no plugin/dependency added; bite-carrying scenes keep clean translate
This commit is contained in:
+18
-1
@@ -943,13 +943,30 @@ body:not(.fx) .slab{display:none}
|
||||
u.flat.style.visibility = "hidden";
|
||||
const lis = u.legend ? [...u.legend.children] : [];
|
||||
const n = lis.length;
|
||||
// per-scene motion signature (occlusion-safe scenes only; default is straight translate).
|
||||
// "away" is 0 at the hero layout, 1 at collapsed/flown - every signature returns to identity
|
||||
// at the hero so the assembled slices always match the source image exactly.
|
||||
const M = u.man.motion, RAD = Math.PI / 180;
|
||||
u.apply = t => {
|
||||
const sg = u.man.stagger || 0, k = u.man.parts.length;
|
||||
u.man.parts.forEach((p, i) => {
|
||||
const pt = sg ? Math.min(1, Math.max(0, t * (1 + sg * (k - 1)) - sg * i)) : t;
|
||||
const e = u.man.reverse ? (1 - pt) : pt;
|
||||
const away = 1 - e;
|
||||
let ox = p.dx * away, oy = p.dy * away, extra = "";
|
||||
if (M === "tumble") { // aperitif: fragments spin as they fly out
|
||||
const spin = (p.spin != null ? p.spin : (i % 2 ? 20 : -20)) * away;
|
||||
extra = " rotate(" + spin.toFixed(2) + "deg)";
|
||||
} else if (M === "arc") { // traffic: slices travel a bowed (curved) path
|
||||
const len = Math.hypot(p.dx, p.dy) || 1;
|
||||
const bow = (u.man.bow || 9) * 4 * away * (1 - away);
|
||||
ox += (-p.dy / len) * bow; oy += (p.dx / len) * bow;
|
||||
} else if (M === "orbit") { // OpenShift: satellites spiral in around the core
|
||||
const a = (u.man.orbit || 55) * away * RAD, c = Math.cos(a), sn = Math.sin(a);
|
||||
ox = (p.dx * c - p.dy * sn) * away; oy = (p.dx * sn + p.dy * c) * away;
|
||||
}
|
||||
u.slabs[i].style.transform =
|
||||
"translate3d(" + (p.dx * (1 - e)).toFixed(3) + "%," + (p.dy * (1 - e)).toFixed(3) + "%,0)";
|
||||
"translate3d(" + ox.toFixed(3) + "%," + oy.toFixed(3) + "%,0)" + extra;
|
||||
});
|
||||
u.scene.style.transform = "scale(" + (0.95 + 0.05 * t).toFixed(4) + ")";
|
||||
if (n) lis.forEach((li, i) => li.classList.toggle("lit", t >= 0.9 * ((i + 0.5) / n)));
|
||||
|
||||
Reference in New Issue
Block a user