@nakednous/tree 0.0.3 → 0.0.4

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/README.md CHANGED
@@ -67,12 +67,28 @@ track.rotInterp = 'nlerp' // normalised lerp; cheaper, slightly non-consta
67
67
 
68
68
  Playback features: signed `rate` (negative reverses), `loop`, `pingPong`, `seek(t)` scrubbing, and lifecycle hooks (`onPlay`, `onEnd`, `onStop`). `_onActivate` / `_onDeactivate` are lib-space hooks for the host layer's draw-loop registry — not for user code.
69
69
 
70
- Keyframe `rot` input is flexible the parser normalises all forms:
71
- - raw `[x,y,z,w]` quaternion
72
- - `{ axis: [x,y,z], angle }` axis-angle
73
- - `{ dir: [x,y,z], up? }` look-direction
74
- - `{ view: mat4 }` from view matrix rotation block
75
- - `{ eye, center, up? }` lookat shorthand
70
+ `add()` accepts flexible specs. Top-level forms:
71
+
72
+ ```js
73
+ track.add({ pos, rot, scl }) // explicit TRS — rot accepts any form below
74
+ track.add({ mMatrix: mat4 }) // decompose a column-major model matrix into TRS
75
+ track.add([ spec, spec, ... ]) // bulk
76
+ ```
77
+
78
+ `rot` sub-forms — all normalised internally:
79
+
80
+ ```js
81
+ rot: [x,y,z,w] // raw quaternion
82
+ rot: { axis:[x,y,z], angle } // axis-angle
83
+ rot: { dir:[x,y,z], up?:[x,y,z] } // look direction (−Z forward)
84
+ rot: { euler:[rx,ry,rz], order?:'YXZ' } // intrinsic Euler angles (radians)
85
+ // orders: YXZ (default), XYZ, ZYX,
86
+ // ZXY, XZY, YZX
87
+ // extrinsic ABC = intrinsic CBA
88
+ rot: { from:[x,y,z], to:[x,y,z] } // shortest-arc between directions
89
+ rot: { mat3: Float32Array|Array } // column-major 3×3 rotation matrix
90
+ rot: { eMatrix: mat4 } // rotation block of an eye matrix
91
+ ```
76
92
 
77
93
  ---
78
94
 
@@ -104,12 +120,19 @@ track.eyeInterp = 'catmullrom' // default
104
120
  track.eyeInterp = 'linear'
105
121
 
106
122
  track.centerInterp = 'linear' // default — suits fixed lookat targets
107
- track.centerInterp = 'catmullrom' // smoother when center is also flying
123
+ track.centerInterp = 'catmullrom' // smoother when center is also moving freely
108
124
  ```
109
125
 
110
126
  `add()` accepts:
111
- - `{ eye, center, up? }` explicit lookat; `up` defaults to `[0,1,0]`
112
- - `{ view: mat4 }` column-major view matrix; eye and forward extracted
127
+
128
+ ```js
129
+ track.add({ eye, center, up? }) // explicit lookat; up defaults to [0,1,0]
130
+ track.add({ vMatrix: mat4 }) // view matrix (world→eye); eye reconstructed
131
+ track.add({ eMatrix: mat4 }) // eye matrix (eye→world); eye read from col3
132
+ track.add([ spec, spec, ... ]) // bulk
133
+ ```
134
+
135
+ Note: both matrix forms default `up` to `[0,1,0]`. The matrix col1 (up_ortho) is intentionally not used — it differs from the hint for upright cameras and would shift orbitControl's orbit reference. Use `capturePose()` (p5.tree bridge) when the real up hint is needed.
113
136
 
114
137
  ---
115
138
 
@@ -130,6 +153,8 @@ track.set(i, spec) // replace keyframe at index
130
153
  track.remove(i) // remove keyframe at index
131
154
 
132
155
  track.playing // boolean
156
+ track.loop // boolean
157
+ track.pingPong // boolean
133
158
  track.rate // get/set — never starts/stops playback
134
159
  track.duration // frames per segment
135
160
  track.keyframes // raw array
@@ -160,10 +185,10 @@ import { mapLocation, mapDirection, WORLD, SCREEN, WEBGL } from '@nakednous/tree
160
185
 
161
186
  const out = new Float32Array(3)
162
187
  const m = {
163
- proj: /* Float32Array(16) */,
164
- view: /* Float32Array(16) */,
165
- pv: /* proj × view */,
166
- ipv: /* inv(pv) */,
188
+ pMatrix: /* Float32Array(16) — projection */,
189
+ vMatrix: /* Float32Array(16) — view (world→eye) */,
190
+ pvMatrix: /* pMatrix × vMatrix — optional, computed if absent */,
191
+ ipvMatrix: /* inv(pvMatrix) optional, computed if absent */,
167
192
  }
168
193
  const vp = [0, height, width, -height]
169
194
 
@@ -259,14 +284,15 @@ All hot-path functions follow an **out-first, zero-allocation** contract:
259
284
 
260
285
  ```js
261
286
  // allocate once
262
- const out = new Float32Array(3)
263
- const pv = new Float32Array(16)
264
- const ipv = new Float32Array(16)
287
+ const out = new Float32Array(3)
288
+ const pvMatrix = new Float32Array(16)
289
+ const ipvMatrix= new Float32Array(16)
265
290
 
266
291
  // per frame — zero allocation
267
- mat4Mul(pv, proj, view)
268
- mat4Invert(ipv, pv)
269
- mapLocation(out, px, py, pz, WORLD, SCREEN, { proj, view, pv, ipv }, vp, WEBGL)
292
+ mat4Mul(pvMatrix, proj, view)
293
+ mat4Invert(ipvMatrix, pvMatrix)
294
+ mapLocation(out, px, py, pz, WORLD, SCREEN,
295
+ { pMatrix: proj, vMatrix: view, pvMatrix, ipvMatrix }, vp, WEBGL)
270
296
  ```
271
297
 
272
298
  ---