hyperframes 0.8.45 → 0.8.47
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/cli.js +161 -27
- package/dist/fontLocalizeCli.js +159 -25
- package/dist/hyperframe-runtime.js +5 -5
- package/dist/hyperframe.manifest.json +1 -1
- package/dist/hyperframe.runtime.iife.js +5 -5
- package/dist/hyperframes-player.global.js +3 -3
- package/dist/studio/assets/hyperframes-player-B7fsB8C2.js +464 -0
- package/dist/studio/assets/{index-BRhRJaev.js → index-B50xQfSG.js} +1 -1
- package/dist/studio/assets/{index-C_TAjvrq.js → index-j-4hCrZU.js} +130 -130
- package/dist/studio/assets/{index-DWQFIQjN.js → index-ryL7q1QG.js} +1 -1
- package/dist/studio/index.d.ts +17 -3
- package/dist/studio/index.html +1 -1
- package/dist/studio/index.js +103 -40
- package/dist/studio/index.js.map +1 -1
- package/package.json +1 -1
- package/dist/studio/assets/hyperframes-player-DMYc4Y9a.js +0 -464
package/dist/fontLocalizeCli.js
CHANGED
|
@@ -56326,37 +56326,80 @@ function finiteOr(value, fallback) {
|
|
|
56326
56326
|
}
|
|
56327
56327
|
function resolveMotionBlurPlan(options) {
|
|
56328
56328
|
if (!options) return null;
|
|
56329
|
-
const
|
|
56329
|
+
const fixedSamplesPerFrame = options.samplesPerFrame === void 0 ? null : Math.min(
|
|
56330
56330
|
MAX_SAMPLES_PER_FRAME,
|
|
56331
56331
|
Math.max(1, Math.round(finiteOr(options.samplesPerFrame, DEFAULT_SAMPLES_PER_FRAME)))
|
|
56332
56332
|
);
|
|
56333
56333
|
const shutterAngle = finiteOr(options.shutterAngle, DEFAULT_SHUTTER_ANGLE);
|
|
56334
56334
|
const shutterPhase = finiteOr(options.shutterPhase, DEFAULT_SHUTTER_PHASE);
|
|
56335
56335
|
const blend = options.blend === "linear" ? "linear" : "srgb";
|
|
56336
|
-
|
|
56337
|
-
|
|
56338
|
-
|
|
56336
|
+
return {
|
|
56337
|
+
blend,
|
|
56338
|
+
subFrameDivisions: SUB_FRAME_DIVISIONS,
|
|
56339
|
+
windowStartFrames: shutterPhase / 360,
|
|
56340
|
+
shutterFrames: shutterAngle / 360,
|
|
56341
|
+
fixedSamplesPerFrame
|
|
56342
|
+
};
|
|
56343
|
+
}
|
|
56344
|
+
function sampleTickOffsets(plan2, samplesPerFrame) {
|
|
56345
|
+
const offsets = [];
|
|
56339
56346
|
for (let k = 0; k < samplesPerFrame; k++) {
|
|
56340
|
-
const offsetFrames = windowStartFrames + (k + 0.5) / samplesPerFrame * shutterFrames;
|
|
56341
|
-
|
|
56347
|
+
const offsetFrames = plan2.windowStartFrames + (k + 0.5) / samplesPerFrame * plan2.shutterFrames;
|
|
56348
|
+
offsets.push(Math.round(offsetFrames * plan2.subFrameDivisions));
|
|
56342
56349
|
}
|
|
56343
|
-
return
|
|
56350
|
+
return offsets;
|
|
56344
56351
|
}
|
|
56345
|
-
function motionBlurSampleTimes(plan2, frameIndex, fps) {
|
|
56352
|
+
function motionBlurSampleTimes(plan2, frameIndex, fps, samplesPerFrame) {
|
|
56346
56353
|
const grid = fps * plan2.subFrameDivisions;
|
|
56347
56354
|
const frameTicks = frameIndex * plan2.subFrameDivisions;
|
|
56348
|
-
return
|
|
56355
|
+
return sampleTickOffsets(plan2, samplesPerFrame).map(
|
|
56356
|
+
(offset2) => Math.max(0, frameTicks + offset2) / grid
|
|
56357
|
+
);
|
|
56349
56358
|
}
|
|
56350
|
-
function
|
|
56351
|
-
const
|
|
56352
|
-
|
|
56359
|
+
function motionBlurProbeTimes(plan2, frameIndex, fps) {
|
|
56360
|
+
const grid = fps * plan2.subFrameDivisions;
|
|
56361
|
+
const frameTicks = frameIndex * plan2.subFrameDivisions;
|
|
56362
|
+
const startTick = Math.round(plan2.windowStartFrames * plan2.subFrameDivisions);
|
|
56363
|
+
const endTick = Math.round(
|
|
56364
|
+
(plan2.windowStartFrames + plan2.shutterFrames) * plan2.subFrameDivisions
|
|
56353
56365
|
);
|
|
56354
|
-
|
|
56366
|
+
return {
|
|
56367
|
+
windowStart: Math.max(0, frameTicks + startTick) / grid,
|
|
56368
|
+
windowEnd: Math.max(0, frameTicks + endTick) / grid
|
|
56369
|
+
};
|
|
56370
|
+
}
|
|
56371
|
+
function motionBlurWindowIsStatic(plan2, frameIndex, staticFrames) {
|
|
56372
|
+
const worstCaseSamples = plan2.fixedSamplesPerFrame ?? MAX_SAMPLES_PER_FRAME;
|
|
56373
|
+
const inset = plan2.shutterFrames / (2 * worstCaseSamples);
|
|
56374
|
+
const minOffsetFrames = plan2.windowStartFrames + inset;
|
|
56375
|
+
const maxOffsetFrames = plan2.windowStartFrames + plan2.shutterFrames - inset;
|
|
56376
|
+
const first = Math.floor(frameIndex - 1 + Math.min(0, minOffsetFrames));
|
|
56377
|
+
const last = Math.floor(frameIndex + Math.max(0, maxOffsetFrames)) + 1;
|
|
56355
56378
|
for (let frame = first; frame <= last; frame++) {
|
|
56356
56379
|
if (!staticFrames.has(frame)) return false;
|
|
56357
56380
|
}
|
|
56358
56381
|
return true;
|
|
56359
56382
|
}
|
|
56383
|
+
function adaptiveSampleCount(diff) {
|
|
56384
|
+
for (const step of ADAPTIVE_SAMPLE_STEPS) {
|
|
56385
|
+
if (diff <= step.maxDiff) return step.samples;
|
|
56386
|
+
}
|
|
56387
|
+
return MAX_SAMPLES_PER_FRAME;
|
|
56388
|
+
}
|
|
56389
|
+
function probeDiffMagnitude(a, b) {
|
|
56390
|
+
const decodedA = decodePng(a);
|
|
56391
|
+
const decodedB = decodePng(b);
|
|
56392
|
+
if (decodedA.width !== decodedB.width || decodedA.height !== decodedB.height) {
|
|
56393
|
+
throw new Error(
|
|
56394
|
+
`probeDiffMagnitude: sample geometry mismatch (${decodedA.width}x${decodedA.height} vs ${decodedB.width}x${decodedB.height})`
|
|
56395
|
+
);
|
|
56396
|
+
}
|
|
56397
|
+
let sum = 0;
|
|
56398
|
+
for (let i = 0; i < decodedA.data.length; i++) {
|
|
56399
|
+
sum += Math.abs(decodedA.data[i] - decodedB.data[i]);
|
|
56400
|
+
}
|
|
56401
|
+
return sum / decodedA.data.length;
|
|
56402
|
+
}
|
|
56360
56403
|
function linearToByte(value) {
|
|
56361
56404
|
const c = value <= 31308e-7 ? value * 12.92 : 1.055 * Math.pow(value, 1 / 2.4) - 0.055;
|
|
56362
56405
|
return clampByte(c * 255);
|
|
@@ -56364,7 +56407,7 @@ function linearToByte(value) {
|
|
|
56364
56407
|
function clampByte(value) {
|
|
56365
56408
|
return Math.min(255, Math.max(0, Math.round(value)));
|
|
56366
56409
|
}
|
|
56367
|
-
var MAX_SAMPLES_PER_FRAME, DEFAULT_SAMPLES_PER_FRAME, DEFAULT_SHUTTER_ANGLE, DEFAULT_SHUTTER_PHASE, SUB_FRAME_DIVISIONS, SRGB_TO_LINEAR, SRGB_PASSTHROUGH, MotionBlurAccumulator;
|
|
56410
|
+
var MAX_SAMPLES_PER_FRAME, DEFAULT_SAMPLES_PER_FRAME, DEFAULT_SHUTTER_ANGLE, DEFAULT_SHUTTER_PHASE, SUB_FRAME_DIVISIONS, ADAPTIVE_SAMPLE_STEPS, SPATIAL_TWEEN_PROPERTIES, SRGB_TO_LINEAR, SRGB_PASSTHROUGH, MotionBlurAccumulator;
|
|
56368
56411
|
var init_motionBlur = __esm({
|
|
56369
56412
|
"../engine/src/services/motionBlur.ts"() {
|
|
56370
56413
|
"use strict";
|
|
@@ -56374,6 +56417,42 @@ var init_motionBlur = __esm({
|
|
|
56374
56417
|
DEFAULT_SHUTTER_ANGLE = 180;
|
|
56375
56418
|
DEFAULT_SHUTTER_PHASE = -90;
|
|
56376
56419
|
SUB_FRAME_DIVISIONS = 4096;
|
|
56420
|
+
ADAPTIVE_SAMPLE_STEPS = [
|
|
56421
|
+
{ maxDiff: 3, samples: DEFAULT_SAMPLES_PER_FRAME },
|
|
56422
|
+
{ maxDiff: 6, samples: 32 },
|
|
56423
|
+
{ maxDiff: Infinity, samples: MAX_SAMPLES_PER_FRAME }
|
|
56424
|
+
];
|
|
56425
|
+
SPATIAL_TWEEN_PROPERTIES = [
|
|
56426
|
+
"x",
|
|
56427
|
+
"y",
|
|
56428
|
+
"z",
|
|
56429
|
+
"xPercent",
|
|
56430
|
+
"yPercent",
|
|
56431
|
+
"rotation",
|
|
56432
|
+
"rotate",
|
|
56433
|
+
"rotationX",
|
|
56434
|
+
"rotationY",
|
|
56435
|
+
"rotationZ",
|
|
56436
|
+
"scale",
|
|
56437
|
+
"scaleX",
|
|
56438
|
+
"scaleY",
|
|
56439
|
+
"scaleZ",
|
|
56440
|
+
"skewX",
|
|
56441
|
+
"skewY",
|
|
56442
|
+
"perspective",
|
|
56443
|
+
"transformPerspective",
|
|
56444
|
+
"top",
|
|
56445
|
+
"left",
|
|
56446
|
+
"right",
|
|
56447
|
+
"bottom",
|
|
56448
|
+
"width",
|
|
56449
|
+
"height",
|
|
56450
|
+
"translate",
|
|
56451
|
+
"translateX",
|
|
56452
|
+
"translateY",
|
|
56453
|
+
"translateZ",
|
|
56454
|
+
"transform"
|
|
56455
|
+
];
|
|
56377
56456
|
SRGB_TO_LINEAR = (() => {
|
|
56378
56457
|
const lut = new Float64Array(256);
|
|
56379
56458
|
for (let i = 0; i < 256; i++) lut[i] = srgbByteToLinear(i);
|
|
@@ -59995,7 +60074,13 @@ function isStaticDedupFrameAnalysisSafe(totalFrames) {
|
|
|
59995
60074
|
return Number.isFinite(totalFrames) && Number.isSafeInteger(totalFrames) && totalFrames > 0 && totalFrames <= MAX_STATIC_DEDUP_ANALYSIS_FRAMES;
|
|
59996
60075
|
}
|
|
59997
60076
|
async function computeStaticFrameSet(page, fps) {
|
|
59998
|
-
const result = await page.evaluate(() => {
|
|
60077
|
+
const result = await page.evaluate((spatialProps) => {
|
|
60078
|
+
const SPATIAL_PROPS = new Set(spatialProps);
|
|
60079
|
+
function isSpatial(vars) {
|
|
60080
|
+
if (!vars) return false;
|
|
60081
|
+
for (const key2 of Object.keys(vars)) if (SPATIAL_PROPS.has(key2)) return true;
|
|
60082
|
+
return false;
|
|
60083
|
+
}
|
|
59999
60084
|
const intervals2 = [];
|
|
60000
60085
|
let tweenCount2 = 0;
|
|
60001
60086
|
let hasTimelineCall2 = false;
|
|
@@ -60003,7 +60088,7 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60003
60088
|
if (typeof tl.getChildren !== "function") return;
|
|
60004
60089
|
if (typeof tl.vars?.onUpdate === "function") {
|
|
60005
60090
|
const total = typeof tl.totalDuration === "function" ? tl.totalDuration() : 0;
|
|
60006
|
-
if (total > 0) intervals2.push({ start: offset2, end: offset2 + total });
|
|
60091
|
+
if (total > 0) intervals2.push({ start: offset2, end: offset2 + total, spatial: true });
|
|
60007
60092
|
}
|
|
60008
60093
|
for (const child of tl.getChildren(false, true, true)) {
|
|
60009
60094
|
const start = offset2 + (typeof child.startTime === "function" ? child.startTime() : 0);
|
|
@@ -60011,14 +60096,14 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60011
60096
|
const total = typeof child.totalDuration === "function" ? child.totalDuration() : single;
|
|
60012
60097
|
if (typeof child.getChildren === "function") {
|
|
60013
60098
|
if (total > single + 1e-6) {
|
|
60014
|
-
intervals2.push({ start, end: start + total });
|
|
60099
|
+
intervals2.push({ start, end: start + total, spatial: true });
|
|
60015
60100
|
walk(child, start);
|
|
60016
60101
|
} else {
|
|
60017
60102
|
walk(child, start);
|
|
60018
60103
|
}
|
|
60019
60104
|
} else {
|
|
60020
60105
|
tweenCount2++;
|
|
60021
|
-
intervals2.push({ start, end: start + total });
|
|
60106
|
+
intervals2.push({ start, end: start + total, spatial: isSpatial(child.vars) });
|
|
60022
60107
|
if (total <= 1e-6 && (typeof child.vars?.onComplete === "function" || typeof child.vars?.onReverseComplete === "function")) {
|
|
60023
60108
|
hasTimelineCall2 = true;
|
|
60024
60109
|
}
|
|
@@ -60059,7 +60144,7 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60059
60144
|
hasUnresolvableClipStart: hasUnresolvableClipStart2,
|
|
60060
60145
|
hasTimelineCall: hasTimelineCall2
|
|
60061
60146
|
};
|
|
60062
|
-
});
|
|
60147
|
+
}, SPATIAL_TWEEN_PROPERTIES);
|
|
60063
60148
|
const {
|
|
60064
60149
|
intervals,
|
|
60065
60150
|
tweenCount,
|
|
@@ -60075,6 +60160,7 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60075
60160
|
return {
|
|
60076
60161
|
totalFrames,
|
|
60077
60162
|
staticFrameSet: /* @__PURE__ */ new Set(),
|
|
60163
|
+
nonSpatialOnlyFrameSet: /* @__PURE__ */ new Set(),
|
|
60078
60164
|
hasVideo,
|
|
60079
60165
|
hasCanvas,
|
|
60080
60166
|
hasNonGsapAnim,
|
|
@@ -60084,10 +60170,14 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60084
60170
|
};
|
|
60085
60171
|
}
|
|
60086
60172
|
const animated = /* @__PURE__ */ new Set();
|
|
60087
|
-
|
|
60173
|
+
const spatialFrameSet = /* @__PURE__ */ new Set();
|
|
60174
|
+
for (const { start, end, spatial } of intervals) {
|
|
60088
60175
|
const lo = Math.max(0, Math.floor(start * fps));
|
|
60089
60176
|
const hi = Math.min(totalFrames - 1, Math.ceil(end * fps));
|
|
60090
|
-
for (let f = lo; f <= hi; f++)
|
|
60177
|
+
for (let f = lo; f <= hi; f++) {
|
|
60178
|
+
animated.add(f);
|
|
60179
|
+
if (spatial) spatialFrameSet.add(f);
|
|
60180
|
+
}
|
|
60091
60181
|
}
|
|
60092
60182
|
for (const f of await computeClipBoundaryFrames(page, fps)) animated.add(f);
|
|
60093
60183
|
const reasons = [];
|
|
@@ -60105,9 +60195,14 @@ async function computeStaticFrameSet(page, fps) {
|
|
|
60105
60195
|
if (!animated.has(f) && !animated.has(f - 1)) staticFrameSet.add(f);
|
|
60106
60196
|
}
|
|
60107
60197
|
}
|
|
60198
|
+
const nonSpatialOnlyFrameSet = /* @__PURE__ */ new Set();
|
|
60199
|
+
if (eligible) {
|
|
60200
|
+
for (const f of animated) if (!spatialFrameSet.has(f)) nonSpatialOnlyFrameSet.add(f);
|
|
60201
|
+
}
|
|
60108
60202
|
return {
|
|
60109
60203
|
totalFrames,
|
|
60110
60204
|
staticFrameSet,
|
|
60205
|
+
nonSpatialOnlyFrameSet,
|
|
60111
60206
|
hasVideo,
|
|
60112
60207
|
hasCanvas,
|
|
60113
60208
|
hasNonGsapAnim,
|
|
@@ -60317,6 +60412,11 @@ async function verifyStaticFramesSafe(session, page, staticFrames, fps, sampleCo
|
|
|
60317
60412
|
}
|
|
60318
60413
|
}
|
|
60319
60414
|
async function armStaticDedup(session, page, logInitPhase) {
|
|
60415
|
+
let sharedStaticFrameStats;
|
|
60416
|
+
if (session.options.motionBlur && session.options.motionBlur.samplesPerFrame === void 0 && !session.motionBlurNonSpatialFrames) {
|
|
60417
|
+
sharedStaticFrameStats = await computeStaticFrameSet(page, fpsToNumber(session.options.fps));
|
|
60418
|
+
session.motionBlurNonSpatialFrames = sharedStaticFrameStats.nonSpatialOnlyFrameSet;
|
|
60419
|
+
}
|
|
60320
60420
|
if (session.staticFrames || session.staticDedupSkipReason) return;
|
|
60321
60421
|
session.staticDedupEnabled = session.config?.staticFrameDedup !== false;
|
|
60322
60422
|
if (!session.staticDedupEnabled) return;
|
|
@@ -60341,7 +60441,7 @@ async function armStaticDedup(session, page, logInitPhase) {
|
|
|
60341
60441
|
return;
|
|
60342
60442
|
}
|
|
60343
60443
|
const fps = fpsToNumber(session.options.fps);
|
|
60344
|
-
const stats = await computeStaticFrameSet(page, fps);
|
|
60444
|
+
const stats = sharedStaticFrameStats ?? await computeStaticFrameSet(page, fps);
|
|
60345
60445
|
if (!stats.eligible || stats.staticFrameSet.size === 0) {
|
|
60346
60446
|
session.staticDedupSkipReason = "ineligible";
|
|
60347
60447
|
logInitPhase(`static-frame dedup: disabled (${stats.reason})`);
|
|
@@ -60587,6 +60687,25 @@ function finalizeSessionInit(session) {
|
|
|
60587
60687
|
session.motionBlur = resolveSessionMotionBlur(session);
|
|
60588
60688
|
session.isInitialized = true;
|
|
60589
60689
|
}
|
|
60690
|
+
async function resolveAdaptiveSampleCount(session, frameIndex, absFrameIndex, plan2, fps, sampleSeek) {
|
|
60691
|
+
if (session.motionBlurNonSpatialFrames?.has(absFrameIndex)) {
|
|
60692
|
+
return {
|
|
60693
|
+
samplesPerFrame: DEFAULT_SAMPLES_PER_FRAME,
|
|
60694
|
+
seekMs: 0,
|
|
60695
|
+
beforeCaptureMs: 0,
|
|
60696
|
+
screenshotMs: 0
|
|
60697
|
+
};
|
|
60698
|
+
}
|
|
60699
|
+
const { windowStart, windowEnd } = motionBlurProbeTimes(plan2, absFrameIndex, fps);
|
|
60700
|
+
const probeA = await captureFrameSurface(session, frameIndex, windowStart, sampleSeek);
|
|
60701
|
+
const probeB = await captureFrameSurface(session, frameIndex, windowEnd, sampleSeek);
|
|
60702
|
+
return {
|
|
60703
|
+
samplesPerFrame: adaptiveSampleCount(probeDiffMagnitude(probeA.buffer, probeB.buffer)),
|
|
60704
|
+
seekMs: probeA.seekMs + probeB.seekMs,
|
|
60705
|
+
beforeCaptureMs: probeA.beforeCaptureMs + probeB.beforeCaptureMs,
|
|
60706
|
+
screenshotMs: probeA.screenshotMs + probeB.screenshotMs
|
|
60707
|
+
};
|
|
60708
|
+
}
|
|
60590
60709
|
async function captureAccumulatedFrame(session, frameIndex, absFrameIndex, plan2) {
|
|
60591
60710
|
const fps = fpsToNumber(session.options.fps);
|
|
60592
60711
|
const frameTime = quantizeSeekTime(absFrameIndex / fps, fps);
|
|
@@ -60597,8 +60716,23 @@ async function captureAccumulatedFrame(session, frameIndex, absFrameIndex, plan2
|
|
|
60597
60716
|
suppressEvents: true,
|
|
60598
60717
|
subFrameDivisions: plan2.subFrameDivisions
|
|
60599
60718
|
};
|
|
60719
|
+
let samplesPerFrame = plan2.fixedSamplesPerFrame;
|
|
60720
|
+
if (samplesPerFrame === null) {
|
|
60721
|
+
const chosen = await resolveAdaptiveSampleCount(
|
|
60722
|
+
session,
|
|
60723
|
+
frameIndex,
|
|
60724
|
+
absFrameIndex,
|
|
60725
|
+
plan2,
|
|
60726
|
+
fps,
|
|
60727
|
+
sampleSeek
|
|
60728
|
+
);
|
|
60729
|
+
samplesPerFrame = chosen.samplesPerFrame;
|
|
60730
|
+
totals.seekMs += chosen.seekMs;
|
|
60731
|
+
totals.beforeCaptureMs += chosen.beforeCaptureMs;
|
|
60732
|
+
totals.screenshotMs += chosen.screenshotMs;
|
|
60733
|
+
}
|
|
60600
60734
|
const accumulator = new MotionBlurAccumulator(plan2.blend);
|
|
60601
|
-
for (const sampleTime of motionBlurSampleTimes(plan2, absFrameIndex, fps)) {
|
|
60735
|
+
for (const sampleTime of motionBlurSampleTimes(plan2, absFrameIndex, fps, samplesPerFrame)) {
|
|
60602
60736
|
const sample = await captureFrameSurface(session, frameIndex, sampleTime, sampleSeek);
|
|
60603
60737
|
totals.seekMs += sample.seekMs;
|
|
60604
60738
|
totals.beforeCaptureMs += sample.beforeCaptureMs;
|
|
@@ -100520,8 +100654,8 @@ async function runFontLocalize(io, localize) {
|
|
|
100520
100654
|
}
|
|
100521
100655
|
|
|
100522
100656
|
// src/version.ts
|
|
100523
|
-
var VERSION = true ? "0.8.
|
|
100524
|
-
var PRODUCER_VERSION = true ? "0.8.
|
|
100657
|
+
var VERSION = true ? "0.8.47" : "0.0.0-dev";
|
|
100658
|
+
var PRODUCER_VERSION = true ? "0.8.47" : "0.0.0-dev";
|
|
100525
100659
|
|
|
100526
100660
|
// src/fontLocalizeCli.ts
|
|
100527
100661
|
async function readStdin() {
|