@px-petals/roku.motion-web 1.0.0 → 1.1.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.
Files changed (77) hide show
  1. package/bands/bands.js +3 -1
  2. package/bundle/bundle.js +56 -0
  3. package/list/list.js +12 -1
  4. package/lottie/lottie.layers.js +64 -11
  5. package/lottie/lottie.paint.js +30 -0
  6. package/lottie/lottie.paths.js +19 -4
  7. package/lottie/lottie.props.js +18 -8
  8. package/lottie/lottie.shapes.js +2 -1
  9. package/mixer/mixer.js +31 -8
  10. package/mixer/mixer.mix.js +17 -0
  11. package/motion/motion.convert.js +32 -1
  12. package/motion/motion.flow.js +20 -2
  13. package/motion/motion.machine.js +28 -13
  14. package/motion/motion.values.js +13 -9
  15. package/motion.js +196 -20
  16. package/package.json +10 -16
  17. package/player/player.js +25 -5
  18. package/readme.md +78 -3
  19. package/script/luau/lib/base/base.js +202 -0
  20. package/script/luau/lib/base/base.table.js +189 -0
  21. package/script/luau/lib/lib.args.js +152 -0
  22. package/script/luau/lib/lib.js +23 -0
  23. package/script/luau/lib/math/math.bit32.js +144 -0
  24. package/script/luau/lib/math/math.js +288 -0
  25. package/script/luau/lib/math/math.vector.js +125 -0
  26. package/script/luau/lib/string/string.format.js +143 -0
  27. package/script/luau/lib/string/string.js +160 -0
  28. package/script/luau/lib/string/string.pattern.js +505 -0
  29. package/script/luau/load/load.js +362 -0
  30. package/script/luau/load/load.ops.js +79 -0
  31. package/script/luau/luau.convert.js +259 -0
  32. package/script/luau/luau.js +132 -0
  33. package/script/luau/luau.md +111 -0
  34. package/script/luau/vm/vm.js +167 -0
  35. package/script/luau/vm/vm.meta.js +401 -0
  36. package/script/luau/vm/vm.num.js +236 -0
  37. package/script/luau/vm/vm.run.js +842 -0
  38. package/script/luau/vm/vm.value.js +406 -0
  39. package/script/play/play.js +199 -0
  40. package/script/play/play.objects.js +295 -0
  41. package/script/play/play.scope.js +91 -0
  42. package/script/rive/api/api.statics.js +31 -0
  43. package/script/rive/api/api.type.js +188 -0
  44. package/script/rive/api/artboard/artboard.js +89 -0
  45. package/script/rive/api/assets/assets.js +72 -0
  46. package/script/rive/api/data/data.value.js +99 -0
  47. package/script/rive/api/draw/draw.contours.js +163 -0
  48. package/script/rive/api/draw/draw.measure.js +196 -0
  49. package/script/rive/api/draw/draw.paint.js +235 -0
  50. package/script/rive/api/draw/draw.path.js +153 -0
  51. package/script/rive/api/draw/draw.renderer.js +117 -0
  52. package/script/rive/api/math/math.color.js +96 -0
  53. package/script/rive/api/math/math.mat2d.js +180 -0
  54. package/script/rive/api/math/math.vector.js +121 -0
  55. package/script/rive/api/media/media.audio.js +113 -0
  56. package/script/rive/api/media/media.draw.js +73 -0
  57. package/script/rive/api/media/media.image.js +61 -0
  58. package/script/rive/api/media/media.mesh.js +50 -0
  59. package/script/rive/api/pointer/pointer.event.js +64 -0
  60. package/script/rive/api/pointer/pointer.route.js +69 -0
  61. package/script/rive/api/text/text.font.js +129 -0
  62. package/script/rive/api/text/text.js +278 -0
  63. package/script/rive/api/text/text.layout.js +259 -0
  64. package/script/rive/context/context.js +76 -0
  65. package/script/rive/context/context.memory.js +196 -0
  66. package/script/rive/context/context.viewmodel.js +302 -0
  67. package/script/rive/context/lists/lists.js +160 -0
  68. package/script/rive/context/lists/lists.values.js +281 -0
  69. package/script/rive/host/host.globals.js +44 -0
  70. package/script/rive/host/host.js +533 -0
  71. package/script/rive/host/host.node.js +45 -0
  72. package/script/rive/rive.js +23 -0
  73. package/script/rive/rive.md +180 -0
  74. package/script/script.js +11 -0
  75. package/skin/skin.deform.js +514 -0
  76. package/skin/skin.ik.js +260 -0
  77. package/skin/skin.js +297 -0
@@ -0,0 +1,505 @@
1
+ /**
2
+ * Lua patterns: a port of the matcher in Lua 5.1's `lstrlib.c`, which Luau's
3
+ * `string.find`, `match`, `gmatch` and `gsub` use. Positions are 0-based
4
+ * indices into the byte string; `-1` means no match.
5
+ *
6
+ * Supported: `.`, character classes `%a %c %d %l %p %s %u %w %x` and their
7
+ * upper-case negations, sets `[...]` with ranges and `^`, the quantifiers
8
+ * `* + - ?`, anchors `^` and `$`, captures `(...)` and position captures
9
+ * `()`, back-references `%1`-`%9`, balanced matches `%b()` and frontiers `%f[set]`.
10
+ */
11
+
12
+ import { fail } from '../../vm/vm.value.js'
13
+
14
+ const CAP_UNFINISHED = -1
15
+ const CAP_POSITION = -2
16
+ const MAX_CAPTURES = 32
17
+ const MAX_DEPTH = 200
18
+
19
+ // Character classes
20
+ // ■■■■■■■■■■■■■■■■■
21
+
22
+ /** @param {number} c */
23
+ const isAlpha = (c) => (c >= 65 && c <= 90) || (c >= 97 && c <= 122)
24
+ /** @param {number} c */
25
+ const isDigit = (c) => c >= 48 && c <= 57
26
+ /** @param {number} c */
27
+ const isLower = (c) => c >= 97 && c <= 122
28
+ /** @param {number} c */
29
+ const isUpper = (c) => c >= 65 && c <= 90
30
+ /** @param {number} c */
31
+ const isSpace = (c) => c === 32 || (c >= 9 && c <= 13)
32
+ /** @param {number} c */
33
+ const isCntrl = (c) => c < 32 || c === 127
34
+ /** @param {number} c */
35
+ const isPunct = (c) => (c >= 33 && c <= 47) || (c >= 58 && c <= 64) || (c >= 91 && c <= 96) || (c >= 123 && c <= 126)
36
+ /** @param {number} c */
37
+ const isXDigit = (c) => isDigit(c) || (c >= 65 && c <= 70) || (c >= 97 && c <= 102)
38
+
39
+ /**
40
+ * Whether char code `c` is in the class named by the letter `cl` (`a`, `D`, ...); any other letter matches itself.
41
+ *
42
+ * @param {number} c
43
+ * @param {number} cl
44
+ * @returns {boolean}
45
+ */
46
+ function matchClass(c, cl) {
47
+ let res
48
+ switch (cl | 32) {
49
+ case 97: res = isAlpha(c); break
50
+ case 99: res = isCntrl(c); break
51
+ case 100: res = isDigit(c); break
52
+ case 108: res = isLower(c); break
53
+ case 112: res = isPunct(c); break
54
+ case 115: res = isSpace(c); break
55
+ case 117: res = isUpper(c); break
56
+ case 119: res = isAlpha(c) || isDigit(c); break
57
+ case 120: res = isXDigit(c); break
58
+ default: return cl === c
59
+ }
60
+ return isUpper(cl) ? !res : res
61
+ }
62
+
63
+ // Matcher
64
+ // ■■■■■■■
65
+
66
+ /** The state of one match attempt */
67
+ export class MatchState {
68
+ /**
69
+ * @param {string} src
70
+ * @param {string} pat
71
+ */
72
+ constructor(src, pat) {
73
+ this.src = src
74
+ this.pat = pat
75
+ this.level = 0
76
+ this.depth = 0
77
+ /** @type {number[]} */
78
+ this.capInit = []
79
+ /** @type {number[]} */
80
+ this.capLen = []
81
+ }
82
+
83
+ reset() {
84
+ this.level = 0
85
+ this.depth = 0
86
+ }
87
+
88
+ /**
89
+ * The index just past the single-character class that starts at `p`.
90
+ *
91
+ * @param {number} p
92
+ * @returns {number}
93
+ */
94
+ classEnd(p) {
95
+ const pat = this.pat
96
+ const c = pat.charCodeAt(p++)
97
+ if (c === 37) {
98
+ if (p >= pat.length) throw fail("malformed pattern (ends with '%')")
99
+ return p + 1
100
+ }
101
+ if (c === 91) {
102
+ if (pat.charCodeAt(p) === 94) p++
103
+ do {
104
+ if (p >= pat.length) throw fail("malformed pattern (missing ']')")
105
+ const d = pat.charCodeAt(p++)
106
+ if (d === 37 && p < pat.length) p++
107
+ } while (pat.charCodeAt(p) !== 93)
108
+ return p + 1
109
+ }
110
+ return p
111
+ }
112
+
113
+ /**
114
+ * @param {number} c char code
115
+ * @param {number} p index of the `[`
116
+ * @param {number} ec index of the closing `]`
117
+ * @returns {boolean}
118
+ */
119
+ matchBracketClass(c, p, ec) {
120
+ const pat = this.pat
121
+ let sig = true
122
+ if (pat.charCodeAt(p + 1) === 94) {
123
+ sig = false
124
+ p++
125
+ }
126
+ while (++p < ec) {
127
+ const pc = pat.charCodeAt(p)
128
+ if (pc === 37) {
129
+ p++
130
+ if (matchClass(c, pat.charCodeAt(p))) return sig
131
+ } else if (pat.charCodeAt(p + 1) === 45 && p + 2 < ec) {
132
+ p += 2
133
+ if (pc <= c && c <= pat.charCodeAt(p)) return sig
134
+ } else if (pc === c) return sig
135
+ }
136
+ return !sig
137
+ }
138
+
139
+ /**
140
+ * @param {number} s
141
+ * @param {number} p
142
+ * @param {number} ep the end of the class at p
143
+ * @returns {boolean}
144
+ */
145
+ singleMatch(s, p, ep) {
146
+ if (s >= this.src.length) return false
147
+ const c = this.src.charCodeAt(s)
148
+ const pc = this.pat.charCodeAt(p)
149
+ switch (pc) {
150
+ case 46: return true
151
+ case 37: return matchClass(c, this.pat.charCodeAt(p + 1))
152
+ case 91: return this.matchBracketClass(c, p, ep - 1)
153
+ default: return pc === c
154
+ }
155
+ }
156
+
157
+ /**
158
+ * @param {number} s
159
+ * @param {number} p index just past `%b`
160
+ * @returns {number}
161
+ */
162
+ matchBalance(s, p) {
163
+ if (p + 1 >= this.pat.length) throw fail("missing arguments to '%b'")
164
+ const src = this.src
165
+ if (s >= src.length || src.charCodeAt(s) !== this.pat.charCodeAt(p)) return -1
166
+ const b = this.pat.charCodeAt(p)
167
+ const e = this.pat.charCodeAt(p + 1)
168
+ let cont = 1
169
+ while (++s < src.length) {
170
+ const c = src.charCodeAt(s)
171
+ if (c === e) {
172
+ if (--cont === 0) return s + 1
173
+ } else if (c === b) cont++
174
+ }
175
+ return -1
176
+ }
177
+
178
+ /**
179
+ * @param {number} s
180
+ * @param {number} p
181
+ * @param {number} ep
182
+ * @returns {number}
183
+ */
184
+ maxExpand(s, p, ep) {
185
+ let i = 0
186
+ while (this.singleMatch(s + i, p, ep)) i++
187
+ while (i >= 0) {
188
+ const res = this.match(s + i, ep + 1)
189
+ if (res !== -1) return res
190
+ i--
191
+ }
192
+ return -1
193
+ }
194
+
195
+ /**
196
+ * @param {number} s
197
+ * @param {number} p
198
+ * @param {number} ep
199
+ * @returns {number}
200
+ */
201
+ minExpand(s, p, ep) {
202
+ for (;;) {
203
+ const res = this.match(s, ep + 1)
204
+ if (res !== -1) return res
205
+ if (this.singleMatch(s, p, ep)) s++
206
+ else return -1
207
+ }
208
+ }
209
+
210
+ /**
211
+ * @param {number} s
212
+ * @param {number} p
213
+ * @param {number} what CAP_UNFINISHED or CAP_POSITION
214
+ * @returns {number}
215
+ */
216
+ startCapture(s, p, what) {
217
+ if (this.level >= MAX_CAPTURES) throw fail('too many captures')
218
+ this.capInit[this.level] = s
219
+ this.capLen[this.level] = what
220
+ this.level++
221
+ const res = this.match(s, p)
222
+ if (res === -1) this.level--
223
+ return res
224
+ }
225
+
226
+ /**
227
+ * @param {number} s
228
+ * @param {number} p
229
+ * @returns {number}
230
+ */
231
+ endCapture(s, p) {
232
+ let l = this.level - 1
233
+ while (l >= 0 && this.capLen[l] !== CAP_UNFINISHED) l--
234
+ if (l < 0) throw fail('invalid pattern capture')
235
+ this.capLen[l] = s - this.capInit[l]
236
+ const res = this.match(s, p)
237
+ if (res === -1) this.capLen[l] = CAP_UNFINISHED
238
+ return res
239
+ }
240
+
241
+ /**
242
+ * @param {number} s
243
+ * @param {number} digit the char code of the digit after `%`
244
+ * @returns {number}
245
+ */
246
+ matchCapture(s, digit) {
247
+ const l = digit - 49
248
+ if (l < 0 || l >= this.level || this.capLen[l] === CAP_UNFINISHED) throw fail('invalid capture index %' + (l + 1))
249
+ const len = this.capLen[l]
250
+ const src = this.src
251
+ if (src.length - s >= len && src.substr(this.capInit[l], len) === src.substr(s, len)) return s + len
252
+ return -1
253
+ }
254
+
255
+ /**
256
+ * Tries to match the pattern from `p` at `s`.
257
+ *
258
+ * @param {number} s
259
+ * @param {number} p
260
+ * @returns {number} the index after the match, or -1
261
+ */
262
+ match(s, p) {
263
+ if (++this.depth > MAX_DEPTH) throw fail('pattern too complex')
264
+ try {
265
+ const pat = this.pat
266
+ for (;;) {
267
+ if (p >= pat.length) return s
268
+ const pc = pat.charCodeAt(p)
269
+ let plain = false
270
+ switch (pc) {
271
+ case 40: // (
272
+ if (pat.charCodeAt(p + 1) === 41) return this.startCapture(s, p + 2, CAP_POSITION)
273
+ return this.startCapture(s, p + 1, CAP_UNFINISHED)
274
+ case 41: // )
275
+ return this.endCapture(s, p + 1)
276
+ case 36: // $
277
+ if (p + 1 === pat.length) return s === this.src.length ? s : -1
278
+ plain = true
279
+ break
280
+ case 37: { // %
281
+ const next = pat.charCodeAt(p + 1)
282
+ if (next === 98) { // b
283
+ s = this.matchBalance(s, p + 2)
284
+ if (s !== -1) {
285
+ p += 4
286
+ continue
287
+ }
288
+ return -1
289
+ }
290
+ if (next === 102) { // f
291
+ p += 2
292
+ if (pat.charCodeAt(p) !== 91) throw fail("missing '[' after '%f' in pattern")
293
+ const ep = this.classEnd(p)
294
+ const prev = s === 0 ? 0 : this.src.charCodeAt(s - 1)
295
+ const cur = s < this.src.length ? this.src.charCodeAt(s) : 0
296
+ if (!this.matchBracketClass(prev, p, ep - 1) && this.matchBracketClass(cur, p, ep - 1)) {
297
+ p = ep
298
+ continue
299
+ }
300
+ return -1
301
+ }
302
+ if (next >= 48 && next <= 57) {
303
+ s = this.matchCapture(s, next)
304
+ if (s !== -1) {
305
+ p += 2
306
+ continue
307
+ }
308
+ return -1
309
+ }
310
+ plain = true
311
+ break
312
+ }
313
+ default:
314
+ plain = true
315
+ }
316
+ if (!plain) return -1
317
+ const ep = this.classEnd(p)
318
+ const epc = pat.charCodeAt(ep)
319
+ if (!this.singleMatch(s, p, ep)) {
320
+ if (epc === 42 || epc === 63 || epc === 45) { // * ? -
321
+ p = ep + 1
322
+ continue
323
+ }
324
+ return -1
325
+ }
326
+ if (epc === 63) { // ?
327
+ const res = this.match(s + 1, ep + 1)
328
+ if (res !== -1) return res
329
+ p = ep + 1
330
+ continue
331
+ }
332
+ if (epc === 43) return this.maxExpand(s + 1, p, ep) // +
333
+ if (epc === 42) return this.maxExpand(s, p, ep) // *
334
+ if (epc === 45) return this.minExpand(s, p, ep) // -
335
+ s++
336
+ p = ep
337
+ }
338
+ } finally {
339
+ this.depth--
340
+ }
341
+ }
342
+
343
+ /**
344
+ * Capture `i` of the last match, which spanned `s` to `e`.
345
+ *
346
+ * @param {number} i
347
+ * @param {number} s
348
+ * @param {number} e
349
+ * @returns {string | number}
350
+ */
351
+ capture(i, s, e) {
352
+ if (i >= this.level) {
353
+ if (i === 0) return this.src.substring(s, e)
354
+ throw fail('invalid capture index')
355
+ }
356
+ const l = this.capLen[i]
357
+ if (l === CAP_UNFINISHED) throw fail('unfinished capture')
358
+ if (l === CAP_POSITION) return this.capInit[i] + 1
359
+ return this.src.substr(this.capInit[i], l)
360
+ }
361
+
362
+ /**
363
+ * All the captures of the last match, or the whole match when the pattern has none.
364
+ *
365
+ * @param {number} s
366
+ * @param {number} e
367
+ * @param {boolean} wholeIfNone
368
+ * @returns {(string | number)[]}
369
+ */
370
+ captures(s, e, wholeIfNone) {
371
+ const n = this.level === 0 && wholeIfNone ? 1 : this.level
372
+ const out = []
373
+ for (let i = 0; i < n; i++) out.push(this.capture(i, s, e))
374
+ return out
375
+ }
376
+ }
377
+
378
+ // Search
379
+ // ■■■■■■
380
+
381
+ /** Pattern characters that make a pattern more than a literal */
382
+ const SPECIALS = /[\^$*+.?()[\]%-]/
383
+
384
+ /**
385
+ * `string.find` and `string.match`.
386
+ *
387
+ * @param {string} s
388
+ * @param {string} pat
389
+ * @param {number} init 1-based start, negative counts from the end
390
+ * @param {boolean} plain search for pat as text
391
+ * @param {boolean} isFind
392
+ * @returns {any[] | undefined} the results, or undefined for nil
393
+ */
394
+ export function find(s, pat, init, plain, isFind) {
395
+ const len = s.length
396
+ let start = init > 0 ? init - 1 : init === 0 ? 0 : Math.max(len + init, 0)
397
+ if (start > len) return undefined
398
+ if (isFind && (plain || !SPECIALS.test(pat))) {
399
+ const at = s.indexOf(pat, start)
400
+ return at < 0 ? undefined : [ at + 1, at + pat.length ]
401
+ }
402
+ const anchor = pat.charCodeAt(0) === 94
403
+ const ms = new MatchState(s, pat)
404
+ const p = anchor ? 1 : 0
405
+ do {
406
+ ms.reset()
407
+ const e = ms.match(start, p)
408
+ if (e !== -1) {
409
+ if (isFind) return /** @type {any[]} */ ([ start + 1, e ]).concat(ms.captures(start, e, false))
410
+ return ms.captures(start, e, true)
411
+ }
412
+ start++
413
+ } while (start <= len && !anchor)
414
+ return undefined
415
+ }
416
+
417
+ /**
418
+ * The iterator behind `string.gmatch`.
419
+ *
420
+ * @param {string} s
421
+ * @param {string} pat
422
+ * @returns {() => (string | number)[] | undefined} each call gives the next match's captures, then undefined
423
+ */
424
+ export function gmatch(s, pat) {
425
+ const ms = new MatchState(s, pat)
426
+ let pos = 0
427
+ return function () {
428
+ for (let start = pos; start <= s.length; start++) {
429
+ ms.reset()
430
+ const e = ms.match(start, 0)
431
+ if (e !== -1) {
432
+ pos = e === start ? e + 1 : e
433
+ return ms.captures(start, e, true)
434
+ }
435
+ }
436
+ pos = s.length + 1
437
+ return undefined
438
+ }
439
+ }
440
+
441
+ /**
442
+ * `string.gsub`.
443
+ *
444
+ * @param {string} s
445
+ * @param {string} pat
446
+ * @param {(captures: (string | number)[]) => string | number | boolean | undefined} replace the replacement for a match, given its captures; false or undefined keeps the match
447
+ * @param {string | null} template a replacement string with `%1` escapes, or null to use `replace`
448
+ * @param {number} max
449
+ * @returns {[string, number]}
450
+ */
451
+ export function gsub(s, pat, replace, template, max) {
452
+ const anchor = pat.charCodeAt(0) === 94
453
+ const p = anchor ? 1 : 0
454
+ const ms = new MatchState(s, pat)
455
+ let out = ''
456
+ let pos = 0
457
+ let n = 0
458
+ while (n < max) {
459
+ ms.reset()
460
+ const e = ms.match(pos, p)
461
+ if (e !== -1) {
462
+ n++
463
+ const whole = s.substring(pos, e)
464
+ if (template !== null) out += expand(ms, template, pos, e)
465
+ else {
466
+ const r = replace(ms.captures(pos, e, true))
467
+ if (r === undefined || r === false) out += whole
468
+ else out += r
469
+ }
470
+ }
471
+ if (e !== -1 && e > pos) pos = e
472
+ else if (pos < s.length) out += s.charAt(pos++)
473
+ else break
474
+ if (anchor) break
475
+ }
476
+ return [ out + s.substring(pos), n ]
477
+ }
478
+
479
+ /**
480
+ * A replacement string with its `%` escapes filled in.
481
+ *
482
+ * @param {MatchState} ms
483
+ * @param {string} template
484
+ * @param {number} s
485
+ * @param {number} e
486
+ * @returns {string}
487
+ */
488
+ function expand(ms, template, s, e) {
489
+ let out = ''
490
+ for (let i = 0; i < template.length; i++) {
491
+ const c = template.charAt(i)
492
+ if (c !== '%') {
493
+ out += c
494
+ continue
495
+ }
496
+ i++
497
+ const d = template.charAt(i)
498
+ if (d === '%') out += '%'
499
+ else if (d >= '0' && d <= '9') {
500
+ const cap = d === '0' ? ms.src.substring(s, e) : ms.capture(d.charCodeAt(0) - 49, s, e)
501
+ out += cap
502
+ } else throw fail("invalid use of '%' in replacement string")
503
+ }
504
+ return out
505
+ }