3d-spinner 0.9.0
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/LICENSE +21 -0
- package/README.md +177 -0
- package/dist/animation.d.ts +28 -0
- package/dist/animation.js +1 -0
- package/dist/animations/object-motion.d.ts +96 -0
- package/dist/animations/object-motion.js +339 -0
- package/dist/animations/spin.d.ts +44 -0
- package/dist/animations/spin.js +108 -0
- package/dist/engines/little-3d-engine/core/camera.d.ts +26 -0
- package/dist/engines/little-3d-engine/core/camera.js +32 -0
- package/dist/engines/little-3d-engine/core/geometry.d.ts +27 -0
- package/dist/engines/little-3d-engine/core/geometry.js +87 -0
- package/dist/engines/little-3d-engine/core/light.d.ts +31 -0
- package/dist/engines/little-3d-engine/core/light.js +35 -0
- package/dist/engines/little-3d-engine/core/math.d.ts +50 -0
- package/dist/engines/little-3d-engine/core/math.js +109 -0
- package/dist/engines/little-3d-engine/core/mesh.d.ts +22 -0
- package/dist/engines/little-3d-engine/core/mesh.js +8 -0
- package/dist/engines/little-3d-engine/little-3d-engine.d.ts +75 -0
- package/dist/engines/little-3d-engine/little-3d-engine.js +167 -0
- package/dist/engines/little-3d-engine/loaders/obj.d.ts +24 -0
- package/dist/engines/little-3d-engine/loaders/obj.js +48 -0
- package/dist/engines/little-3d-engine/renderer.d.ts +43 -0
- package/dist/engines/little-3d-engine/renderer.js +16 -0
- package/dist/engines/little-3d-engine/renderers/canvas2d.d.ts +12 -0
- package/dist/engines/little-3d-engine/renderers/canvas2d.js +73 -0
- package/dist/engines/little-3d-engine/renderers/webgl.d.ts +15 -0
- package/dist/engines/little-3d-engine/renderers/webgl.js +146 -0
- package/dist/engines/little-3d-engine/renderers/webgpu.d.ts +24 -0
- package/dist/engines/little-3d-engine/renderers/webgpu.js +222 -0
- package/dist/engines/little-3d-engine/shapes/cube-sphere.d.ts +11 -0
- package/dist/engines/little-3d-engine/shapes/cube-sphere.js +50 -0
- package/dist/engines/little-3d-engine/shapes/cube.d.ts +9 -0
- package/dist/engines/little-3d-engine/shapes/cube.js +30 -0
- package/dist/engines/little-3d-engine/shapes/icosphere.d.ts +11 -0
- package/dist/engines/little-3d-engine/shapes/icosphere.js +51 -0
- package/dist/engines/little-3d-engine/shapes/octa-sphere.d.ts +10 -0
- package/dist/engines/little-3d-engine/shapes/octa-sphere.js +31 -0
- package/dist/engines/little-3d-engine/shapes/octahedron.d.ts +8 -0
- package/dist/engines/little-3d-engine/shapes/octahedron.js +38 -0
- package/dist/engines/little-3d-engine/shapes/pyramid.d.ts +9 -0
- package/dist/engines/little-3d-engine/shapes/pyramid.js +26 -0
- package/dist/engines/little-3d-engine/shapes/tetrahedron.d.ts +8 -0
- package/dist/engines/little-3d-engine/shapes/tetrahedron.js +23 -0
- package/dist/engines/little-3d-engine/shapes/uv-sphere.d.ts +10 -0
- package/dist/engines/little-3d-engine/shapes/uv-sphere.js +50 -0
- package/dist/engines/little-tween-engine/core/tweens.d.ts +39 -0
- package/dist/engines/little-tween-engine/core/tweens.js +231 -0
- package/dist/engines/little-tween-engine/little-tween-engine.d.ts +21 -0
- package/dist/engines/little-tween-engine/little-tween-engine.js +16 -0
- package/dist/index.d.ts +37 -0
- package/dist/index.js +110 -0
- package/dist/motion/circle.d.ts +17 -0
- package/dist/motion/circle.js +20 -0
- package/dist/motion/controller.d.ts +13 -0
- package/dist/motion/controller.js +1 -0
- package/dist/motion/figure-eight.d.ts +13 -0
- package/dist/motion/figure-eight.js +23 -0
- package/dist/motion/motion.d.ts +5 -0
- package/dist/motion/motion.js +4 -0
- package/dist/motion/square.d.ts +17 -0
- package/dist/motion/square.js +39 -0
- package/dist/motion/transitions.d.ts +44 -0
- package/dist/motion/transitions.js +60 -0
- package/dist/motion/wander.d.ts +22 -0
- package/dist/motion/wander.js +50 -0
- package/dist/progress-animation.d.ts +55 -0
- package/dist/progress-animation.js +128 -0
- package/package.json +74 -0
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
const DEFAULT_DISTANCE = 3.5;
|
|
2
|
+
function add(a, b) {
|
|
3
|
+
return { x: a.x + b.x, y: a.y + b.y, z: a.z + b.z };
|
|
4
|
+
}
|
|
5
|
+
function scaleVector(v, factor) {
|
|
6
|
+
return { x: v.x * factor, y: v.y * factor, z: v.z * factor };
|
|
7
|
+
}
|
|
8
|
+
function vectorLength(v) {
|
|
9
|
+
return Math.hypot(v.x, v.y, v.z);
|
|
10
|
+
}
|
|
11
|
+
function normalizeVector(v) {
|
|
12
|
+
const length = vectorLength(v);
|
|
13
|
+
if (length < 1e-6)
|
|
14
|
+
return { x: 1, y: 0, z: 0 };
|
|
15
|
+
return scaleVector(v, 1 / length);
|
|
16
|
+
}
|
|
17
|
+
function resolveDirection(input, fallback) {
|
|
18
|
+
return normalizeVector(fallback ?? input.direction ?? input.velocity ?? { x: 1, y: 0, z: 0 });
|
|
19
|
+
}
|
|
20
|
+
function easeOutBack(delta) {
|
|
21
|
+
const c = 1.70158;
|
|
22
|
+
const u = delta - 1;
|
|
23
|
+
return 1 + (c + 1) * u * u * u + c * u * u;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Constant velocity the fly-in/out travels at. When the path supplies a real
|
|
27
|
+
* velocity at the handoff (and the caller has not forced a custom `direction`),
|
|
28
|
+
* we match it exactly so the transition joins the motion with no speed jump.
|
|
29
|
+
* Only when no useful velocity is available do we fall back to covering
|
|
30
|
+
* `distance` over the duration along the resolved direction.
|
|
31
|
+
*/
|
|
32
|
+
function joinVelocity(input, options, durationMs) {
|
|
33
|
+
const inputSpeed = input.velocity ? vectorLength(input.velocity) : 0;
|
|
34
|
+
if (input.velocity && inputSpeed > 1e-6 && !options.direction) {
|
|
35
|
+
return input.velocity;
|
|
36
|
+
}
|
|
37
|
+
const distance = options.distance ?? DEFAULT_DISTANCE;
|
|
38
|
+
return scaleVector(resolveDirection(input, options.direction), distance / durationMs);
|
|
39
|
+
}
|
|
40
|
+
export function enterFromObjectDirection(options = {}) {
|
|
41
|
+
return (input) => {
|
|
42
|
+
const durationMs = Math.max(1, input.durationMs);
|
|
43
|
+
const velocity = joinVelocity(input, options, durationMs);
|
|
44
|
+
const remaining = durationMs - input.elapsedMs;
|
|
45
|
+
return { position: add(input.position, scaleVector(velocity, -remaining)) };
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
export function leaveInObjectDirection(options = {}) {
|
|
49
|
+
return (input) => {
|
|
50
|
+
const durationMs = Math.max(1, input.durationMs);
|
|
51
|
+
const velocity = joinVelocity(input, options, durationMs);
|
|
52
|
+
return { position: add(input.position, scaleVector(velocity, input.elapsedMs)) };
|
|
53
|
+
};
|
|
54
|
+
}
|
|
55
|
+
export function grow() {
|
|
56
|
+
return (input) => ({ size: (input.size ?? 1) * easeOutBack(input.delta) });
|
|
57
|
+
}
|
|
58
|
+
export function shrink() {
|
|
59
|
+
return (input) => ({ size: (input.size ?? 1) * (1 - input.delta * input.delta) });
|
|
60
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { MotionController } from "./controller.js";
|
|
2
|
+
/** Half-extents of the box the wander stays within, in scene units. */
|
|
3
|
+
export interface WanderBounds {
|
|
4
|
+
x?: number;
|
|
5
|
+
y?: number;
|
|
6
|
+
z?: number;
|
|
7
|
+
}
|
|
8
|
+
/** Options for {@link wanderMotion}. */
|
|
9
|
+
export interface WanderMotionOptions {
|
|
10
|
+
/** Half-extents of the box the object stays within. Default `{ x: 1.4, y: 1.0, z: 0.6 }`. */
|
|
11
|
+
bounds?: WanderBounds;
|
|
12
|
+
/** Base drift period in ms; larger is slower. Default `9000`. */
|
|
13
|
+
periodMs?: number;
|
|
14
|
+
/** Seed for the random direction pattern. Omit for a different wander each time. */
|
|
15
|
+
seed?: number;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Drifts smoothly in random directions, changing heading organically, while
|
|
19
|
+
* staying inside the frame. The path is bounded by construction (a weighted sum
|
|
20
|
+
* of sines), so it never wanders off-screen. Pass a `seed` for a repeatable path.
|
|
21
|
+
*/
|
|
22
|
+
export declare function wanderMotion(options?: WanderMotionOptions): MotionController;
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
function mulberry32(seed) {
|
|
2
|
+
let a = seed >>> 0;
|
|
3
|
+
return () => {
|
|
4
|
+
a = (a + 0x6d2b79f5) | 0;
|
|
5
|
+
let t = Math.imul(a ^ (a >>> 15), 1 | a);
|
|
6
|
+
t = (t + Math.imul(t ^ (t >>> 7), 61 | t)) ^ t;
|
|
7
|
+
return ((t ^ (t >>> 14)) >>> 0) / 4294967296;
|
|
8
|
+
};
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Builds a per-axis position function as a weighted sum of sines with
|
|
12
|
+
* incommensurate frequencies. The output never exceeds `bound`, so the object
|
|
13
|
+
* is guaranteed to stay inside the frame while drifting and turning smoothly.
|
|
14
|
+
*/
|
|
15
|
+
function axisDrift(rnd, omega, bound) {
|
|
16
|
+
const components = [0, 1, 2].map(() => ({
|
|
17
|
+
freq: 0.5 + rnd() * 1.4,
|
|
18
|
+
phase: rnd() * Math.PI * 2,
|
|
19
|
+
weight: 0.5 + rnd(),
|
|
20
|
+
}));
|
|
21
|
+
const total = components.reduce((sum, c) => sum + c.weight, 0);
|
|
22
|
+
return (t) => {
|
|
23
|
+
let value = 0;
|
|
24
|
+
for (const c of components)
|
|
25
|
+
value += c.weight * Math.sin(omega * c.freq * t + c.phase);
|
|
26
|
+
return (value / total) * bound;
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Drifts smoothly in random directions, changing heading organically, while
|
|
31
|
+
* staying inside the frame. The path is bounded by construction (a weighted sum
|
|
32
|
+
* of sines), so it never wanders off-screen. Pass a `seed` for a repeatable path.
|
|
33
|
+
*/
|
|
34
|
+
export function wanderMotion(options = {}) {
|
|
35
|
+
const boundX = options.bounds?.x ?? 1.4;
|
|
36
|
+
const boundY = options.bounds?.y ?? 1.0;
|
|
37
|
+
const boundZ = options.bounds?.z ?? 0.6;
|
|
38
|
+
const periodMs = options.periodMs ?? 9000;
|
|
39
|
+
const seed = options.seed ?? (Math.random() * 1e9) | 0;
|
|
40
|
+
const rnd = mulberry32(seed);
|
|
41
|
+
const omega = (2 * Math.PI) / periodMs;
|
|
42
|
+
const driftX = axisDrift(rnd, omega, boundX);
|
|
43
|
+
const driftY = axisDrift(rnd, omega, boundY);
|
|
44
|
+
const driftZ = axisDrift(rnd, omega, boundZ);
|
|
45
|
+
return {
|
|
46
|
+
positionAt(t) {
|
|
47
|
+
return { x: driftX(t), y: driftY(t), z: driftZ(t) };
|
|
48
|
+
},
|
|
49
|
+
};
|
|
50
|
+
}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
export interface ProgressAnimationOptions {
|
|
2
|
+
/** Pop-in / pop-out duration in milliseconds. Default `500`. */
|
|
3
|
+
popDurationMs?: number;
|
|
4
|
+
/** Scale overshoot fraction during pop. Default `0.2` (20%). */
|
|
5
|
+
overextend?: number;
|
|
6
|
+
/** Share of pop duration used for the fast overshoot snap. Default `0.2`. */
|
|
7
|
+
startSnapRatio?: number;
|
|
8
|
+
/** Label while loading; `false` hides it. Default `"loading"`. */
|
|
9
|
+
loadingText?: string | false;
|
|
10
|
+
/** Label when complete. Default `"done"`. */
|
|
11
|
+
doneText?: string;
|
|
12
|
+
/** Fade-out duration for the done label in milliseconds. Default `2000`. */
|
|
13
|
+
doneFadeDurationMs?: number;
|
|
14
|
+
/** Remove all overlay content after the done fade finishes. Default `false`. */
|
|
15
|
+
removeOnComplete?: boolean;
|
|
16
|
+
}
|
|
17
|
+
export interface ProgressAnimationVisual {
|
|
18
|
+
/** Uniform scale multiplier (0 = invisible). */
|
|
19
|
+
scale: number;
|
|
20
|
+
/** Overlay label, or `null` when hidden. */
|
|
21
|
+
text: string | null;
|
|
22
|
+
/** Label opacity in the range 0..1. */
|
|
23
|
+
textOpacity: number;
|
|
24
|
+
/** When true, hide the entire animation (mesh and text). */
|
|
25
|
+
hidden: boolean;
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Lifecycle visual for a progress spinner: an intro pop ({@link enter}), an
|
|
29
|
+
* active phase whose scale tracks progress, and an outro pop ({@link exit})
|
|
30
|
+
* that fades to a done label. The owner triggers `enter`/`exit`; this class
|
|
31
|
+
* does not infer them from the progress value.
|
|
32
|
+
*
|
|
33
|
+
* Lifecycle stages:
|
|
34
|
+
* - `idle`: waiting for {@link enter}; nothing is visible.
|
|
35
|
+
* - `startPop`: the object pops in and settles at the current progress scale.
|
|
36
|
+
* - `active`: the object scale tracks progress.
|
|
37
|
+
* - `endPop`: the object pops out after {@link exit}.
|
|
38
|
+
* - `done`: the object is gone while the done label fades.
|
|
39
|
+
* - `finished`: all visuals are complete and {@link isFinished} returns true.
|
|
40
|
+
*/
|
|
41
|
+
export declare class ProgressAnimation {
|
|
42
|
+
private readonly options;
|
|
43
|
+
private phase;
|
|
44
|
+
private phaseStart;
|
|
45
|
+
private activeProgress;
|
|
46
|
+
private popTarget;
|
|
47
|
+
private doneFadeStart;
|
|
48
|
+
constructor(options?: ProgressAnimationOptions);
|
|
49
|
+
/** Begin the intro pop. Ignored unless idle. */
|
|
50
|
+
enter(now: number): void;
|
|
51
|
+
/** Begin the outro pop. Ignored unless mid-intro or active. */
|
|
52
|
+
exit(now: number): void;
|
|
53
|
+
isFinished(): boolean;
|
|
54
|
+
update(now: number, progress: number, targetProgress?: number): ProgressAnimationVisual;
|
|
55
|
+
}
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
import { easeOutCubic, easeOutExpo, easeOutQuad, easeInQuad, } from "./engines/little-tween-engine/core/tweens.js";
|
|
2
|
+
function resolveOptions(options = {}) {
|
|
3
|
+
return {
|
|
4
|
+
popDurationMs: options.popDurationMs ?? 500,
|
|
5
|
+
overextend: options.overextend ?? 0.2,
|
|
6
|
+
startSnapRatio: options.startSnapRatio ?? 0.2,
|
|
7
|
+
loadingText: options.loadingText === undefined ? "loading" : options.loadingText,
|
|
8
|
+
doneText: options.doneText ?? "done",
|
|
9
|
+
doneFadeDurationMs: options.doneFadeDurationMs ?? 2000,
|
|
10
|
+
removeOnComplete: options.removeOnComplete ?? false,
|
|
11
|
+
};
|
|
12
|
+
}
|
|
13
|
+
function popPhaseT(now, phaseStart, durationMs) {
|
|
14
|
+
if (durationMs <= 0)
|
|
15
|
+
return 1;
|
|
16
|
+
return Math.min(1, Math.max(0, (now - phaseStart) / durationMs));
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Lifecycle visual for a progress spinner: an intro pop ({@link enter}), an
|
|
20
|
+
* active phase whose scale tracks progress, and an outro pop ({@link exit})
|
|
21
|
+
* that fades to a done label. The owner triggers `enter`/`exit`; this class
|
|
22
|
+
* does not infer them from the progress value.
|
|
23
|
+
*
|
|
24
|
+
* Lifecycle stages:
|
|
25
|
+
* - `idle`: waiting for {@link enter}; nothing is visible.
|
|
26
|
+
* - `startPop`: the object pops in and settles at the current progress scale.
|
|
27
|
+
* - `active`: the object scale tracks progress.
|
|
28
|
+
* - `endPop`: the object pops out after {@link exit}.
|
|
29
|
+
* - `done`: the object is gone while the done label fades.
|
|
30
|
+
* - `finished`: all visuals are complete and {@link isFinished} returns true.
|
|
31
|
+
*/
|
|
32
|
+
export class ProgressAnimation {
|
|
33
|
+
constructor(options = {}) {
|
|
34
|
+
this.phase = "idle";
|
|
35
|
+
this.phaseStart = 0;
|
|
36
|
+
this.activeProgress = 0;
|
|
37
|
+
this.popTarget = 0;
|
|
38
|
+
this.doneFadeStart = 0;
|
|
39
|
+
this.options = resolveOptions(options);
|
|
40
|
+
}
|
|
41
|
+
/** Begin the intro pop. Ignored unless idle. */
|
|
42
|
+
enter(now) {
|
|
43
|
+
if (this.phase !== "idle")
|
|
44
|
+
return;
|
|
45
|
+
this.phase = "startPop";
|
|
46
|
+
this.phaseStart = now;
|
|
47
|
+
this.activeProgress = 0;
|
|
48
|
+
this.popTarget = 0;
|
|
49
|
+
}
|
|
50
|
+
/** Begin the outro pop. Ignored unless mid-intro or active. */
|
|
51
|
+
exit(now) {
|
|
52
|
+
if (this.phase !== "startPop" && this.phase !== "active")
|
|
53
|
+
return;
|
|
54
|
+
this.phase = "endPop";
|
|
55
|
+
this.phaseStart = now;
|
|
56
|
+
}
|
|
57
|
+
isFinished() {
|
|
58
|
+
return this.phase === "finished";
|
|
59
|
+
}
|
|
60
|
+
update(now, progress, targetProgress) {
|
|
61
|
+
const { popDurationMs, overextend, startSnapRatio, loadingText, doneText, doneFadeDurationMs, removeOnComplete, } = this.options;
|
|
62
|
+
const goal = targetProgress ?? progress;
|
|
63
|
+
if (this.phase === "startPop" || this.phase === "active") {
|
|
64
|
+
this.activeProgress = progress;
|
|
65
|
+
if (this.phase === "startPop")
|
|
66
|
+
this.popTarget = Math.max(this.popTarget, goal, progress);
|
|
67
|
+
}
|
|
68
|
+
let scale = 0;
|
|
69
|
+
let text = null;
|
|
70
|
+
let textOpacity = 0;
|
|
71
|
+
let hidden = false;
|
|
72
|
+
if (this.phase === "startPop") {
|
|
73
|
+
const t = popPhaseT(now, this.phaseStart, popDurationMs);
|
|
74
|
+
const peak = this.popTarget * (1 + overextend);
|
|
75
|
+
if (t < startSnapRatio) {
|
|
76
|
+
const snapT = startSnapRatio > 0 ? t / startSnapRatio : 1;
|
|
77
|
+
scale = peak * easeOutExpo(snapT);
|
|
78
|
+
}
|
|
79
|
+
else {
|
|
80
|
+
const settleT = startSnapRatio < 1 ? (t - startSnapRatio) / (1 - startSnapRatio) : 1;
|
|
81
|
+
scale = peak + (this.activeProgress - peak) * easeOutCubic(settleT);
|
|
82
|
+
}
|
|
83
|
+
if (t >= 1)
|
|
84
|
+
this.phase = "active";
|
|
85
|
+
}
|
|
86
|
+
else if (this.phase === "active") {
|
|
87
|
+
scale = this.activeProgress;
|
|
88
|
+
}
|
|
89
|
+
else if (this.phase === "endPop") {
|
|
90
|
+
const t = popPhaseT(now, this.phaseStart, popDurationMs);
|
|
91
|
+
const peak = 1 + overextend;
|
|
92
|
+
if (t < 0.5) {
|
|
93
|
+
scale = 1 + (peak - 1) * easeOutQuad(t * 2);
|
|
94
|
+
}
|
|
95
|
+
else {
|
|
96
|
+
scale = peak * (1 - easeInQuad((t - 0.5) * 2));
|
|
97
|
+
}
|
|
98
|
+
if (t >= 1) {
|
|
99
|
+
this.phase = "done";
|
|
100
|
+
this.doneFadeStart = now;
|
|
101
|
+
scale = 0;
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
if (this.phase === "startPop" || this.phase === "active") {
|
|
105
|
+
if (loadingText !== false) {
|
|
106
|
+
text = loadingText;
|
|
107
|
+
textOpacity = 0.65;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
else if (this.phase === "endPop") {
|
|
111
|
+
text = doneText;
|
|
112
|
+
textOpacity = 0.65;
|
|
113
|
+
}
|
|
114
|
+
else if (this.phase === "done") {
|
|
115
|
+
const fadeT = popPhaseT(now, this.doneFadeStart, doneFadeDurationMs);
|
|
116
|
+
if (fadeT >= 1) {
|
|
117
|
+
if (removeOnComplete)
|
|
118
|
+
hidden = true;
|
|
119
|
+
this.phase = "finished";
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
text = doneText;
|
|
123
|
+
textOpacity = 0.65 * (1 - fadeT);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
return { scale, text, textOpacity, hidden };
|
|
127
|
+
}
|
|
128
|
+
}
|
package/package.json
ADDED
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "3d-spinner",
|
|
3
|
+
"version": "0.9.0",
|
|
4
|
+
"description": "A lightweight, zero-dependency 3D spinner, loader, and progress indicator for JavaScript.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "./dist/index.js",
|
|
7
|
+
"module": "./dist/index.js",
|
|
8
|
+
"types": "./dist/index.d.ts",
|
|
9
|
+
"exports": {
|
|
10
|
+
".": {
|
|
11
|
+
"types": "./dist/index.d.ts",
|
|
12
|
+
"import": "./dist/index.js"
|
|
13
|
+
},
|
|
14
|
+
"./animations/spin": {
|
|
15
|
+
"types": "./dist/animations/spin.d.ts",
|
|
16
|
+
"import": "./dist/animations/spin.js"
|
|
17
|
+
},
|
|
18
|
+
"./animations/object-motion": {
|
|
19
|
+
"types": "./dist/animations/object-motion.d.ts",
|
|
20
|
+
"import": "./dist/animations/object-motion.js"
|
|
21
|
+
},
|
|
22
|
+
"./motion": {
|
|
23
|
+
"types": "./dist/motion/motion.d.ts",
|
|
24
|
+
"import": "./dist/motion/motion.js"
|
|
25
|
+
},
|
|
26
|
+
"./motion/transitions": {
|
|
27
|
+
"types": "./dist/motion/transitions.d.ts",
|
|
28
|
+
"import": "./dist/motion/transitions.js"
|
|
29
|
+
},
|
|
30
|
+
"./engines/little-3d-engine": {
|
|
31
|
+
"types": "./dist/engines/little-3d-engine/little-3d-engine.d.ts",
|
|
32
|
+
"import": "./dist/engines/little-3d-engine/little-3d-engine.js"
|
|
33
|
+
},
|
|
34
|
+
"./engines/little-3d-engine/loaders/obj": {
|
|
35
|
+
"types": "./dist/engines/little-3d-engine/loaders/obj.d.ts",
|
|
36
|
+
"import": "./dist/engines/little-3d-engine/loaders/obj.js"
|
|
37
|
+
},
|
|
38
|
+
"./engines/little-tween-engine": {
|
|
39
|
+
"types": "./dist/engines/little-tween-engine/little-tween-engine.d.ts",
|
|
40
|
+
"import": "./dist/engines/little-tween-engine/little-tween-engine.js"
|
|
41
|
+
}
|
|
42
|
+
},
|
|
43
|
+
"files": [
|
|
44
|
+
"dist"
|
|
45
|
+
],
|
|
46
|
+
"scripts": {
|
|
47
|
+
"clean": "node -e \"fs.rmSync('dist', { recursive: true, force: true })\"",
|
|
48
|
+
"build": "npm run clean && tsc",
|
|
49
|
+
"dev": "npx serve .",
|
|
50
|
+
"pretest": "npm run build",
|
|
51
|
+
"test": "node --test tests/*.test.mjs",
|
|
52
|
+
"prepublishOnly": "npm run build"
|
|
53
|
+
},
|
|
54
|
+
"keywords": [
|
|
55
|
+
"spinner",
|
|
56
|
+
"loader",
|
|
57
|
+
"loading",
|
|
58
|
+
"3d",
|
|
59
|
+
"progress"
|
|
60
|
+
],
|
|
61
|
+
"author": "RuneL",
|
|
62
|
+
"license": "MIT",
|
|
63
|
+
"repository": {
|
|
64
|
+
"type": "git",
|
|
65
|
+
"url": "git+https://github.com/runelaang/3d-spinner.git"
|
|
66
|
+
},
|
|
67
|
+
"homepage": "https://github.com/runelaang/3d-spinner#readme",
|
|
68
|
+
"bugs": {
|
|
69
|
+
"url": "https://github.com/runelaang/3d-spinner/issues"
|
|
70
|
+
},
|
|
71
|
+
"devDependencies": {
|
|
72
|
+
"typescript": "^5.7.0"
|
|
73
|
+
}
|
|
74
|
+
}
|