hyperframes 0.8.133 → 0.8.135
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/{add-KIAMI737.js → add-7E2GRDW5.js} +16 -16
- package/dist/{animatedGifPrep-P2T6YM7Z.js → animatedGifPrep-3AKQSXPU.js} +7 -7
- package/dist/{asset-KRQ4APXQ.js → asset-43SXDTJI.js} +2 -2
- package/dist/{assetCataloger-VBLPHX24.js → assetCataloger-KBN5LNK4.js} +3 -3
- package/dist/{auth-M4XWYQDV.js → auth-BWQ4HPK7.js} +2 -2
- package/dist/{autoUpdate-J7LNL4BP.js → autoUpdate-JTHQKHG5.js} +2 -2
- package/dist/{backgroundChecks-LLNHXZPY.js → backgroundChecks-H43RKGRE.js} +3 -3
- package/dist/backgroundChecksWorker.js +3 -3
- package/dist/{batchRender-FT7AP7XH.js → batchRender-VFXGGGJG.js} +4 -4
- package/dist/{beats-NOF2NADU.js → beats-HAOQC7GJ.js} +13 -13
- package/dist/{benchmark-XVHUNNCM.js → benchmark-ANUXIEPD.js} +13 -13
- package/dist/{browser-URZ3PY73.js → browser-HEICRDNT.js} +10 -10
- package/dist/{bundleWithLocalizedFonts-5QOPOB5D.js → bundleWithLocalizedFonts-5ATL25BF.js} +2 -2
- package/dist/{capture-RLZA6EMR.js → capture-DYBK5LGE.js} +10 -10
- package/dist/{capture-SZZ4IYJK.js → capture-UEJG6BUX.js} +2 -2
- package/dist/{catalog-EJBGGESW.js → catalog-2F5L72ZT.js} +16 -16
- package/dist/{check-RXLKRRB2.js → check-WZ5QMBBF.js} +33 -33
- package/dist/{checkBrowser-DNUQDCGD.js → checkBrowser-FXVVADP6.js} +32 -32
- package/dist/{chunk-MWB3ZIFM.js → chunk-2BJCQN7K.js} +1 -1
- package/dist/{chunk-LYNI3FOL.js → chunk-32QEFPDS.js} +1 -1
- package/dist/{chunk-4NWOGZZS.js → chunk-374QQGBQ.js} +26 -3
- package/dist/{chunk-QC4FJVLM.js → chunk-37EDNWLQ.js} +1 -1
- package/dist/{chunk-KBJUXVOJ.js → chunk-3NCZ2SCH.js} +3 -3
- package/dist/{chunk-IUZFXWSV.js → chunk-4AXZWUQ6.js} +1 -1
- package/dist/{chunk-3ZP5DXE7.js → chunk-527WRFUQ.js} +1 -1
- package/dist/{chunk-ZMXUQLI2.js → chunk-5ALWCRBU.js} +47 -25
- package/dist/{chunk-JEFU7IHM.js → chunk-AV7FBRWP.js} +2 -2
- package/dist/{chunk-2YN64IN5.js → chunk-BHOKLX4F.js} +2 -2
- package/dist/{chunk-HRUGC23L.js → chunk-BSU7EOWJ.js} +1 -1
- package/dist/{chunk-FCSIGXXP.js → chunk-BWJ27MQP.js} +1 -1
- package/dist/{chunk-PDAMK4Q5.js → chunk-D2KNWIQ6.js} +1 -1
- package/dist/{chunk-RMHUQGRK.js → chunk-GK5W3SIJ.js} +4 -4
- package/dist/{chunk-GK3QVRBM.js → chunk-GN6GW6IP.js} +9 -9
- package/dist/{chunk-6CTIGJY7.js → chunk-H4UIYRZZ.js} +2 -2
- package/dist/{chunk-DIFXJN2V.js → chunk-HNUHWAHR.js} +1 -1
- package/dist/{chunk-S55PCW5S.js → chunk-I54AADBN.js} +1 -1
- package/dist/{chunk-5OZGQCAB.js → chunk-KZ7B3XK7.js} +1 -1
- package/dist/{chunk-7JZ4FXP2.js → chunk-KZJPREW7.js} +1 -1
- package/dist/{chunk-ARR5QKPH.js → chunk-LKCICE2T.js} +10 -10
- package/dist/{chunk-YQZNILVH.js → chunk-LO7L5PJ3.js} +5 -5
- package/dist/{chunk-S7NPLFWV.js → chunk-LYJNFBD6.js} +792 -671
- package/dist/{chunk-7XKF2OB5.js → chunk-N3DZEPNT.js} +1 -1
- package/dist/{chunk-K2FTXJYH.js → chunk-N3KRRPL7.js} +81 -24
- package/dist/{chunk-ETWKKKJI.js → chunk-NDKVPWBH.js} +3 -3
- package/dist/{chunk-XS4EJSKU.js → chunk-OSSVNAI5.js} +1 -1
- package/dist/{chunk-AVUUN2XD.js → chunk-OZUQF4NB.js} +5 -4
- package/dist/{chunk-Z6B37SNM.js → chunk-PGFP4FLW.js} +12 -158
- package/dist/{chunk-SF4GTH2H.js → chunk-PULS7UW7.js} +2 -2
- package/dist/{chunk-A2Z4Z4VL.js → chunk-RTURM45Q.js} +1 -1
- package/dist/{chunk-TCLGPL65.js → chunk-RVG35AL2.js} +2 -2
- package/dist/{chunk-HKGEEUZV.js → chunk-SMWYGLTD.js} +7 -7
- package/dist/chunk-SRXQEQWZ.js +3742 -0
- package/dist/{chunk-K2EQN4VU.js → chunk-T5LPCY6I.js} +1 -1
- package/dist/{chunk-MAWC5PUQ.js → chunk-TKSAWNNI.js} +3 -3
- package/dist/{chunk-Q7IU7MOR.js → chunk-V26IB6L2.js} +2 -2
- package/dist/{chunk-CWPVM2QV.js → chunk-V2J2ZWPR.js} +2 -2
- package/dist/{chunk-ZJUKFZ2P.js → chunk-VDQCNWQI.js} +2 -2
- package/dist/{chunk-CFKU7HTK.js → chunk-VNC6YQOC.js} +1 -1
- package/dist/{chunk-WPHMNO44.js → chunk-WJFCDDP7.js} +1 -1
- package/dist/{chunk-VTUOQTFU.js → chunk-WVRNPWVW.js} +1 -1
- package/dist/{chunk-7HG4BFIN.js → chunk-XE6S5CE6.js} +1 -1
- package/dist/{chunk-U7CKZ7BR.js → chunk-XFKPUKL7.js} +4 -4
- package/dist/{chunk-UEZXMWG3.js → chunk-XSWKLDVC.js} +2 -2
- package/dist/{chunk-64TQHBM7.js → chunk-XZVPQYLU.js} +5 -5
- package/dist/{chunk-LHSR3M4M.js → chunk-Z3EFUXL5.js} +2 -2
- package/dist/{chunk-MJ5XLLXY.js → chunk-Z3KAYWE5.js} +3 -3
- package/dist/{clean-XMQXSQI5.js → clean-SZMPUNNQ.js} +17 -17
- package/dist/cli.js +51 -51
- package/dist/{cloud-BAC5KWSE.js → cloud-L7RFQB5E.js} +4 -4
- package/dist/{cloudrun-AJUTHUEA.js → cloudrun-FA4XHPZS.js} +5 -5
- package/dist/{compare-QAV6WNL4.js → compare-DN5GHUAZ.js} +27 -27
- package/dist/{compiler-QO36EXLS.js → compiler-XZ654ZH2.js} +13 -11
- package/dist/{component-HAJPPCFF.js → component-RYYGPCCC.js} +3 -3
- package/dist/{compositions-A5PN3ILU.js → compositions-TF42YRGQ.js} +12 -12
- package/dist/{delete-L5LYQF6D.js → delete-KYGP772F.js} +2 -2
- package/dist/{deterministicFonts-HAEMV4TM.js → deterministicFonts-U2EXY2KQ.js} +2 -2
- package/dist/{dist-S3PJNPXQ.js → dist-HVJAGLHF.js} +5 -3
- package/dist/{dist-FNNGCKFS.js → dist-QS5WEGBE.js} +1 -1
- package/dist/{doctor-VAALU6RK.js → doctor-AWERBYTS.js} +11 -11
- package/dist/{events-53SD6Z6G.js → events-QMT3TXJ2.js} +10 -10
- package/dist/{events-FSZQPLB5.js → events-W4AILK4F.js} +9 -9
- package/dist/{feedback-HVIGQIBA.js → feedback-KNKJFGOK.js} +11 -11
- package/dist/{figma-OMHCIFA6.js → figma-D76N4WD7.js} +3 -3
- package/dist/fontLocalizeCli.js +10 -10
- package/dist/{get-VVCHOTHZ.js → get-JHNZVDVT.js} +2 -2
- package/dist/{gpuPolicy-2ZUZE5D6.js → gpuPolicy-ON3RMSWD.js} +7 -7
- package/dist/{grade-compare-VEQUV7SJ.js → grade-compare-22SRAVPO.js} +27 -27
- package/dist/{gsapParser-DIYYX6JT.js → gsapParser-2OL54XZ5.js} +61 -23
- package/dist/{gsapParserAcorn-E3GEIRZB.js → gsapParserAcorn-VXZ3ZIF2.js} +5 -3
- package/dist/{help-VWAFVPC6.js → help-CKKLDL3G.js} +1 -1
- package/dist/{history-NYADNWVR.js → history-44SS2VJQ.js} +17 -17
- package/dist/hyperframe-runtime.js +49 -49
- package/dist/hyperframe.manifest.json +1 -1
- package/dist/hyperframe.runtime.iife.js +49 -49
- package/dist/hyperframes-player.global.js +1 -1
- package/dist/{info-42A4ZXQZ.js → info-A2CXIT7G.js} +12 -12
- package/dist/{init-YUGOYCN6.js → init-6D2GNNON.js} +23 -23
- package/dist/{inspect-C66X5KGK.js → inspect-QLYCCDHV.js} +28 -28
- package/dist/{installer-K6O5WF44.js → installer-DDJVY4TO.js} +5 -5
- package/dist/{keyframes-CC4SVYGQ.js → keyframes-TBS3BUZ5.js} +13 -16
- package/dist/{lambda-D7UMN4DJ.js → lambda-LPLYOEYY.js} +6 -6
- package/dist/{layout-OBTKALAB.js → layout-YLBD2653.js} +28 -28
- package/dist/{lint-CDJ4BIB5.js → lint-6XERRN4E.js} +13 -13
- package/dist/{lintProject-OHBBM3DJ.js → lintProject-EPVG2EFE.js} +1 -1
- package/dist/{list-AMHMJLVP.js → list-DPVTICQX.js} +2 -2
- package/dist/{login-3FHM5JUX.js → login-FJJH3ZPU.js} +4 -4
- package/dist/{media-treatment-SGIJZZSW.js → media-treatment-CQWZZRHR.js} +13 -13
- package/dist/{models-C4E4IWJD.js → models-54NL5PRB.js} +8 -8
- package/dist/{motionShot-S4MIGMT5.js → motionShot-BSI4U6X7.js} +13 -13
- package/dist/{normalize-audio-U4QNHC3R.js → normalize-audio-2QQBNTAW.js} +12 -12
- package/dist/{open-DRIBRDFD.js → open-YCWBIUNN.js} +11 -11
- package/dist/{pipeline-TNGWUZQC.js → pipeline-P7QRGI5H.js} +7 -7
- package/dist/{play-NOBUJING.js → play-5OX76SR5.js} +22 -22
- package/dist/{preflight-SMNV6RW2.js → preflight-X3XFRJPQ.js} +8 -8
- package/dist/{present-Q4Q4V6JJ.js → present-UFG6NPCO.js} +18 -18
- package/dist/{preview-SEH3BNYZ.js → preview-AGS4TAWM.js} +18 -18
- package/dist/{producer-ECLEN5RP.js → producer-KQNJKM7F.js} +1 -1
- package/dist/{projectConfig-HYJMJ5BY.js → projectConfig-EAAQYRMP.js} +7 -7
- package/dist/{publication-HQ5Y3KBM.js → publication-H3G346EX.js} +3 -3
- package/dist/{publish-VHDYQASC.js → publish-NEGKIS35.js} +9 -9
- package/dist/{remove-background-W2YX2NVH.js → remove-background-HU4S4HH5.js} +8 -8
- package/dist/{render-AO5VX3YI.js → render-F3CNO2IE.js} +4 -4
- package/dist/{render-ZJYL6ZPT.js → render-KEZFDRDA.js} +22 -22
- package/dist/{render-XVKTOY2L.js → render-POQI3EKS.js} +13 -13
- package/dist/{render-batch-YH7CTWNY.js → render-batch-63CBIJYR.js} +4 -4
- package/dist/{renderCancellation-JPIHE47X.js → renderCancellation-FT3JJ7GB.js} +7 -7
- package/dist/renderSetupWorker.js +1 -1
- package/dist/{resolver-IZ647GBZ.js → resolver-YJJKOGQF.js} +5 -5
- package/dist/{sherpa-KKLNW6U2.js → sherpa-3BQDMJPJ.js} +8 -8
- package/dist/{skills-IIHWUS56.js → skills-L7SZ45NC.js} +12 -12
- package/dist/{skillsUpdateCheck-HG5HOSBY.js → skillsUpdateCheck-HP3GJFBP.js} +3 -3
- package/dist/{snapshot-SRSWE7B2.js → snapshot-CYB2PZPW.js} +28 -28
- package/dist/{src-PVYUYV3M.js → src-CUR36DBE.js} +8 -6
- package/dist/{src-6YQBJGWR.js → src-ZPAJ44CP.js} +9 -9
- package/dist/{staticProjectServer-7EU666GS.js → staticProjectServer-U5DMWKWA.js} +16 -16
- package/dist/{status-YM52BQ6S.js → status-6CGT2PJT.js} +7 -7
- package/dist/studio/assets/{hyperframes-player-Cjcwveg0.js → hyperframes-player-DFv9heE6.js} +1 -1
- package/dist/studio/assets/{index-CwgWmfgx.js → index-Buy06mZy.js} +1 -1
- package/dist/studio/assets/{index-ME-Z5jh6.js → index-CTp4loy9.js} +1 -1
- package/dist/studio/assets/{index-Dj21zXWA.js → index-N_4Ij4X6.js} +184 -183
- package/dist/studio/assets/{index-D11atkBt.css → index-syMK0_9C.css} +1 -1
- package/dist/studio/{chunk-5VSXRGIX.js → chunk-NM7BXNZ7.js} +1 -1
- package/dist/studio/chunk-NM7BXNZ7.js.map +1 -0
- package/dist/studio/{chunk-FOEID72M.js → chunk-QRLKWENQ.js} +2 -2
- package/dist/studio/index.d.ts +3 -1
- package/dist/studio/index.html +2 -2
- package/dist/studio/index.js +911 -691
- package/dist/studio/index.js.map +1 -1
- package/dist/studio/player.js +2 -2
- package/dist/studio/styles.css +1 -1
- package/dist/studio/ui.d.ts +3 -2
- package/dist/studio/ui.js +1 -1
- package/dist/{studio-api-PNQZRPX5.js → studio-api-KMBTUYG5.js} +10 -10
- package/dist/{studioServer-SKEFBCNM.js → studioServer-LOJ6IOWA.js} +42 -42
- package/dist/{system-EZYZNUFD.js → system-3BTZGJNK.js} +7 -7
- package/dist/{telemetry-TN6HXCPW.js → telemetry-MCEZ5JYB.js} +10 -10
- package/dist/{timeline-Y6RJY467.js → timeline-XWH4I5CF.js} +17 -17
- package/dist/{tokens-HWMQVD2T.js → tokens-6UTTSLVN.js} +2 -2
- package/dist/{transcribe-BNSJRR4M.js → transcribe-HC35FL6W.js} +8 -8
- package/dist/{transcribe-PZP553TY.js → transcribe-S3NI7SYU.js} +13 -13
- package/dist/{updateCheck-2HHCJUTZ.js → updateCheck-3YAKEXSX.js} +2 -2
- package/dist/{upgrade-Y55PMAGH.js → upgrade-JQPBH5RY.js} +2 -2
- package/dist/{urlDownloader-H6WRI2UE.js → urlDownloader-A5TT3AFE.js} +6 -6
- package/dist/{validate-BFYU5VTW.js → validate-BLUPV5H5.js} +17 -17
- package/dist/{video-FGSGKRSV.js → video-USXMJDEZ.js} +7 -7
- package/package.json +1 -1
- package/dist/chunk-HWKCIWQT.js +0 -3578
- package/dist/studio/chunk-5VSXRGIX.js.map +0 -1
- /package/dist/studio/{chunk-FOEID72M.js.map → chunk-QRLKWENQ.js.map} +0 -0
package/dist/studio/index.js
CHANGED
|
@@ -39,7 +39,7 @@ import {
|
|
|
39
39
|
usePreviewVariablesStore,
|
|
40
40
|
whenPreviewBooted,
|
|
41
41
|
writeStudioUiPreferences
|
|
42
|
-
} from "./chunk-
|
|
42
|
+
} from "./chunk-QRLKWENQ.js";
|
|
43
43
|
import {
|
|
44
44
|
Button,
|
|
45
45
|
ContextMenu,
|
|
@@ -71,7 +71,7 @@ import {
|
|
|
71
71
|
fieldBase,
|
|
72
72
|
fieldText,
|
|
73
73
|
popupSurface
|
|
74
|
-
} from "./chunk-
|
|
74
|
+
} from "./chunk-NM7BXNZ7.js";
|
|
75
75
|
import {
|
|
76
76
|
DOM_EDIT_LAYER_OBSERVER_INIT,
|
|
77
77
|
STUDIO_FLAT_INSPECTOR_ENABLED,
|
|
@@ -4504,6 +4504,7 @@ function timingEase(runEase) {
|
|
|
4504
4504
|
}
|
|
4505
4505
|
return timingEases.get(runEase) ?? null;
|
|
4506
4506
|
}
|
|
4507
|
+
var warpsTime = (runEase) => timingEase(runEase) !== null;
|
|
4507
4508
|
function progressAtTime(runEase, timePercentage) {
|
|
4508
4509
|
const run = timingEase(runEase);
|
|
4509
4510
|
return run ? run(timePercentage / 100) * 100 : timePercentage;
|
|
@@ -4592,7 +4593,7 @@ var PROPERTY_DEFAULTS = {
|
|
|
4592
4593
|
};
|
|
4593
4594
|
function keyframeEases(anim) {
|
|
4594
4595
|
if (!anim.keyframes) return { easeEach: anim.ease };
|
|
4595
|
-
return { ease: anim
|
|
4596
|
+
return { ease: runEaseOf(anim), easeEach: anim.keyframes.easeEach };
|
|
4596
4597
|
}
|
|
4597
4598
|
function isInstantHold(animation) {
|
|
4598
4599
|
return animation.method === "set" || (animation.method === "to" || animation.method === "fromTo") && resolveTweenDuration(animation) === 0;
|
|
@@ -9465,15 +9466,24 @@ function focusedField() {
|
|
|
9465
9466
|
function hasStudioPendingEdits() {
|
|
9466
9467
|
return pendingEdits.size > 0 || focusedField() !== null;
|
|
9467
9468
|
}
|
|
9469
|
+
var shownRestores = /* @__PURE__ */ new Set();
|
|
9470
|
+
function beginStudioShownRestore() {
|
|
9471
|
+
let end = () => {
|
|
9472
|
+
};
|
|
9473
|
+
const landed = new Promise((resolve) => end = resolve);
|
|
9474
|
+
shownRestores.add(landed);
|
|
9475
|
+
void landed.then(() => shownRestores.delete(landed));
|
|
9476
|
+
return end;
|
|
9477
|
+
}
|
|
9468
9478
|
function isStudioEditSaving() {
|
|
9469
|
-
return pendingEdits.size > 0;
|
|
9479
|
+
return pendingEdits.size > 0 || shownRestores.size > 0;
|
|
9470
9480
|
}
|
|
9471
9481
|
function afterStudioPendingEdits(run) {
|
|
9472
9482
|
let waiting = true;
|
|
9473
9483
|
const check = () => {
|
|
9474
9484
|
if (!waiting) return;
|
|
9475
9485
|
if (isStudioEditSaving()) {
|
|
9476
|
-
void Promise.allSettled([...pendingEdits.keys()]).then(check);
|
|
9486
|
+
void Promise.allSettled([...pendingEdits.keys(), ...shownRestores]).then(check);
|
|
9477
9487
|
return;
|
|
9478
9488
|
}
|
|
9479
9489
|
waiting = false;
|
|
@@ -9501,14 +9511,35 @@ function trackStudioPendingEdit(result) {
|
|
|
9501
9511
|
);
|
|
9502
9512
|
return promise;
|
|
9503
9513
|
}
|
|
9504
|
-
|
|
9514
|
+
var flushedSavesStillWriting = null;
|
|
9515
|
+
function commitOlderDebouncedEdits() {
|
|
9516
|
+
if (typeof window === "undefined" || adopting) return;
|
|
9517
|
+
const detail = { promises: [] };
|
|
9518
|
+
window.dispatchEvent(
|
|
9519
|
+
new CustomEvent(STUDIO_FLUSH_PENDING_EDITS_EVENT, { detail })
|
|
9520
|
+
);
|
|
9521
|
+
if (!detail.promises.length) return;
|
|
9522
|
+
const saves = Promise.allSettled([flushedSavesStillWriting, ...detail.promises]);
|
|
9523
|
+
flushedSavesStillWriting = saves;
|
|
9524
|
+
void saves.then(() => {
|
|
9525
|
+
if (flushedSavesStillWriting === saves) flushedSavesStillWriting = null;
|
|
9526
|
+
});
|
|
9527
|
+
}
|
|
9528
|
+
function afterOlderSaves(run) {
|
|
9529
|
+
return flushedSavesStillWriting && flushedSavesStillWriting.then(run);
|
|
9530
|
+
}
|
|
9531
|
+
function trackedStudioEdit(edit, { afterOlderSaves: waits = false } = {}) {
|
|
9505
9532
|
return (...args) => {
|
|
9533
|
+
commitOlderDebouncedEdits();
|
|
9534
|
+
const deferred = waits && !adopting ? afterOlderSaves(() => edit(...args)) : null;
|
|
9535
|
+
if (deferred) return trackStudioPendingEdit(deferred);
|
|
9506
9536
|
const result = edit(...args);
|
|
9507
9537
|
if (result instanceof Promise) trackStudioPendingEdit(result);
|
|
9508
9538
|
return result;
|
|
9509
9539
|
};
|
|
9510
9540
|
}
|
|
9511
9541
|
function beginStudioPendingEdit(revert) {
|
|
9542
|
+
commitOlderDebouncedEdits();
|
|
9512
9543
|
let settle;
|
|
9513
9544
|
const promise = trackStudioPendingEdit(new Promise((resolve) => settle = resolve));
|
|
9514
9545
|
const entry2 = pendingEdits.get(promise);
|
|
@@ -9548,7 +9579,8 @@ function beginStudioPendingEdit(revert) {
|
|
|
9548
9579
|
// Only what `start` registers synchronously is adopted; a later write joins only through `within`.
|
|
9549
9580
|
adopt(start) {
|
|
9550
9581
|
try {
|
|
9551
|
-
const
|
|
9582
|
+
const deferred = afterOlderSaves(() => inFlight.within(start));
|
|
9583
|
+
const committed = deferred ?? inFlight.within(start);
|
|
9552
9584
|
landed = Promise.resolve(committed).then(
|
|
9553
9585
|
() => true,
|
|
9554
9586
|
() => saved2
|
|
@@ -12133,7 +12165,9 @@ function trackEditCommits(actions) {
|
|
|
12133
12165
|
const tracked = { ...actions };
|
|
12134
12166
|
for (const key2 of Object.keys(SAVES_AN_EDIT)) {
|
|
12135
12167
|
if (!SAVES_AN_EDIT[key2]) continue;
|
|
12136
|
-
tracked[key2] = trackedStudioEdit(actions[key2]
|
|
12168
|
+
tracked[key2] = trackedStudioEdit(actions[key2], {
|
|
12169
|
+
afterOlderSaves: true
|
|
12170
|
+
});
|
|
12137
12171
|
}
|
|
12138
12172
|
return tracked;
|
|
12139
12173
|
}
|
|
@@ -17106,6 +17140,9 @@ function applyAuthoredInlineOpacity(style, authored) {
|
|
|
17106
17140
|
else style.setProperty("opacity", authored);
|
|
17107
17141
|
}
|
|
17108
17142
|
|
|
17143
|
+
// src/utils/softReloadTargets.ts
|
|
17144
|
+
import { parseGsapScript } from "@hyperframes/parsers/gsap-parser";
|
|
17145
|
+
|
|
17109
17146
|
// src/utils/elementGsap.ts
|
|
17110
17147
|
function gsapOf(element) {
|
|
17111
17148
|
return element.ownerDocument.defaultView?.gsap;
|
|
@@ -17122,6 +17159,12 @@ function setElementGsapScale(element, x, y) {
|
|
|
17122
17159
|
gsap3.set(element, { scaleX: x, scaleY: y });
|
|
17123
17160
|
return true;
|
|
17124
17161
|
}
|
|
17162
|
+
function setElementGsapSize(element, width, height) {
|
|
17163
|
+
const gsap3 = gsapOf(element);
|
|
17164
|
+
if (!gsap3?.set) return false;
|
|
17165
|
+
gsap3.set(element, { width, height });
|
|
17166
|
+
return true;
|
|
17167
|
+
}
|
|
17125
17168
|
function elementTargets(tween) {
|
|
17126
17169
|
return (tween.targets?.() ?? []).filter(
|
|
17127
17170
|
(t2) => Boolean(t2?.style && t2.nodeType)
|
|
@@ -17154,7 +17197,7 @@ function addTweenTargets(tween, targets) {
|
|
|
17154
17197
|
targets.set(el, seen);
|
|
17155
17198
|
}
|
|
17156
17199
|
}
|
|
17157
|
-
function collectResetTargets(win, doc, targetKeys) {
|
|
17200
|
+
function collectResetTargets(win, doc, targetKeys, outgoingScripts = []) {
|
|
17158
17201
|
const targets = /* @__PURE__ */ new Map();
|
|
17159
17202
|
const timelines = win.__timelines ?? {};
|
|
17160
17203
|
const others = new Set(
|
|
@@ -17167,6 +17210,8 @@ function collectResetTargets(win, doc, targetKeys) {
|
|
|
17167
17210
|
}
|
|
17168
17211
|
}
|
|
17169
17212
|
sweepHeldElements(doc, targetKeys, others, targets);
|
|
17213
|
+
addLiveSetTargets(doc, targetKeys, targets);
|
|
17214
|
+
for (const script of outgoingScripts) addStandaloneSetTargets(doc, script, targets);
|
|
17170
17215
|
return targets;
|
|
17171
17216
|
}
|
|
17172
17217
|
function tweenTargetsIn(timelines) {
|
|
@@ -17200,6 +17245,43 @@ function sweepHeldElements(doc, targetKeys, others, targets) {
|
|
|
17200
17245
|
}
|
|
17201
17246
|
}
|
|
17202
17247
|
}
|
|
17248
|
+
var liveSets = /* @__PURE__ */ new WeakMap();
|
|
17249
|
+
function recordLiveSet(el, vars) {
|
|
17250
|
+
const byElement = liveSets.get(el.ownerDocument) ?? /* @__PURE__ */ new Map();
|
|
17251
|
+
liveSets.set(el.ownerDocument, byElement);
|
|
17252
|
+
const props = byElement.get(el) ?? /* @__PURE__ */ new Set();
|
|
17253
|
+
for (const prop of tweenedProps(vars)) props.add(prop);
|
|
17254
|
+
byElement.set(el, props);
|
|
17255
|
+
}
|
|
17256
|
+
function addLiveSetTargets(doc, targetKeys, targets) {
|
|
17257
|
+
const roots = new Set(targetKeys.map((k) => compositionRoot(doc, k)));
|
|
17258
|
+
for (const [el, props] of liveSets.get(doc) ?? []) {
|
|
17259
|
+
if (!roots.has(el) && !roots.has(el.parentElement?.closest("[data-composition-id]"))) continue;
|
|
17260
|
+
const seen = targets.get(el) ?? /* @__PURE__ */ new Set();
|
|
17261
|
+
for (const prop of props) seen.add(prop);
|
|
17262
|
+
targets.set(el, seen);
|
|
17263
|
+
}
|
|
17264
|
+
}
|
|
17265
|
+
function forgetLiveSets(reset) {
|
|
17266
|
+
for (const el of reset.keys()) liveSets.get(el.ownerDocument)?.delete(el);
|
|
17267
|
+
}
|
|
17268
|
+
function addStandaloneSetTargets(doc, outgoingScript, targets) {
|
|
17269
|
+
if (!outgoingScript.includes("gsap.set(")) return;
|
|
17270
|
+
for (const set of parseGsapScript(outgoingScript).animations) {
|
|
17271
|
+
if (set.method !== "set" || !set.global) continue;
|
|
17272
|
+
let els;
|
|
17273
|
+
try {
|
|
17274
|
+
els = [...doc.querySelectorAll(set.targetSelector)];
|
|
17275
|
+
} catch {
|
|
17276
|
+
continue;
|
|
17277
|
+
}
|
|
17278
|
+
for (const el of els) {
|
|
17279
|
+
const seen = targets.get(el) ?? /* @__PURE__ */ new Set();
|
|
17280
|
+
for (const prop of tweenedProps(set.properties)) seen.add(prop);
|
|
17281
|
+
targets.set(el, seen);
|
|
17282
|
+
}
|
|
17283
|
+
}
|
|
17284
|
+
}
|
|
17203
17285
|
function fileDocs(ownFile, written, nestedFiles) {
|
|
17204
17286
|
const docs = /* @__PURE__ */ new Map();
|
|
17205
17287
|
return (file) => {
|
|
@@ -17363,7 +17445,12 @@ function applySoftReload(iframe, scriptText, options = {}) {
|
|
|
17363
17445
|
const readAuthoredOpacity = (el) => findAuthoredStyle(el)?.opacity ?? readStampedAuthoredOpacity(el);
|
|
17364
17446
|
const doReload = () => {
|
|
17365
17447
|
const timelines = win.__timelines;
|
|
17366
|
-
const targets = collectResetTargets(
|
|
17448
|
+
const targets = collectResetTargets(
|
|
17449
|
+
win,
|
|
17450
|
+
doc,
|
|
17451
|
+
targetKeys,
|
|
17452
|
+
staleScripts.map((script) => script.textContent ?? "")
|
|
17453
|
+
);
|
|
17367
17454
|
if (timelines) {
|
|
17368
17455
|
for (const key2 of targetKeys) {
|
|
17369
17456
|
const tl = timelines[key2];
|
|
@@ -17394,6 +17481,7 @@ function applySoftReload(iframe, scriptText, options = {}) {
|
|
|
17394
17481
|
}
|
|
17395
17482
|
}
|
|
17396
17483
|
}
|
|
17484
|
+
forgetLiveSets(targets);
|
|
17397
17485
|
for (const script of staleScripts) script.remove();
|
|
17398
17486
|
const executeScript = () => {
|
|
17399
17487
|
if (win.MotionPathPlugin && win.gsap?.registerPlugin) {
|
|
@@ -17621,25 +17709,33 @@ import { findTimelineScript } from "@hyperframes/core/gsap-parser-acorn";
|
|
|
17621
17709
|
import { walkCompositionDescendants } from "@hyperframes/parsers/hf-ids";
|
|
17622
17710
|
|
|
17623
17711
|
// src/utils/gsapLiveRetime.ts
|
|
17624
|
-
import { parseGsapScriptAcorn } from "@hyperframes/
|
|
17712
|
+
import { parseGsapScriptAcorn, scriptShape } from "@hyperframes/parsers/gsap-parser-acorn";
|
|
17625
17713
|
import { hasExplicitTime } from "@hyperframes/parsers/gsap-writer-acorn";
|
|
17626
17714
|
import { RUNTIME_FILLER } from "@hyperframes/core/runtime/protocol";
|
|
17627
17715
|
var RERUN = { kind: "rerun" };
|
|
17628
|
-
var withoutLayout = (code) => code.replace(/\s+/g, " ").replace(/ ?([^\w$ ]) ?/g, "$1").trim();
|
|
17629
17716
|
function untimedShape(animation) {
|
|
17630
17717
|
const { id: _id, position: _p, resolvedStart: _s, duration: _d, ...rest } = animation;
|
|
17631
17718
|
const provenance = rest.provenance && { ...rest.provenance, sourceRange: void 0 };
|
|
17632
17719
|
return JSON.stringify(
|
|
17633
17720
|
{ ...rest, provenance },
|
|
17634
|
-
(_key, value) => typeof value === "string" && value.startsWith("__raw:") ?
|
|
17721
|
+
(_key, value) => typeof value === "string" && value.startsWith("__raw:") ? scriptShape(`(${value.slice(6)}
|
|
17722
|
+
)`) ?? value : value
|
|
17635
17723
|
);
|
|
17636
17724
|
}
|
|
17637
17725
|
var onTimeline = (animation) => !animation.global;
|
|
17638
17726
|
var placedAlone = (animation) => hasExplicitTime(animation) && typeof animation.resolvedStart === "number";
|
|
17639
17727
|
var lengthOf = (animation) => animation.method === "set" ? 0 : animation.durationUnresolved ? void 0 : animation.duration;
|
|
17640
|
-
var
|
|
17728
|
+
var shapes = /* @__PURE__ */ new Map();
|
|
17729
|
+
function shapeOf(code) {
|
|
17730
|
+
const shape = shapes.has(code) ? shapes.get(code) : scriptShape(code, true);
|
|
17731
|
+
shapes.delete(code);
|
|
17732
|
+
shapes.set(code, shape);
|
|
17733
|
+
if (shapes.size > 2) shapes.delete(shapes.keys().next().value);
|
|
17734
|
+
return shape;
|
|
17735
|
+
}
|
|
17641
17736
|
function planLiveRetime(before, after) {
|
|
17642
|
-
|
|
17737
|
+
const shape = shapeOf(before);
|
|
17738
|
+
if (shape === null || shape !== shapeOf(after)) return RERUN;
|
|
17643
17739
|
const keys = timelineKeys(after);
|
|
17644
17740
|
if (keys.length !== 1 || timelineKeys(before).join() !== keys.join()) return RERUN;
|
|
17645
17741
|
const was = parseGsapScriptAcorn(before).animations.filter(onTimeline);
|
|
@@ -17705,15 +17801,10 @@ function sharesOneStretch(tweens) {
|
|
|
17705
17801
|
);
|
|
17706
17802
|
return stretch > 0 && fits;
|
|
17707
17803
|
}
|
|
17708
|
-
function inOrHostsSubComposition(target, ownId) {
|
|
17709
|
-
const element = target;
|
|
17710
|
-
const owner = element.closest?.("[data-composition-id]");
|
|
17711
|
-
return owner != null && owner.getAttribute("data-composition-id") !== ownId || element.querySelector?.("[data-composition-id]") != null;
|
|
17712
|
-
}
|
|
17713
17804
|
var keepsOrder = (tweens) => tweens.every(
|
|
17714
17805
|
(t2, k) => k === 0 || (tweens[k - 1].start - t2.start || tweens[k - 1].source - t2.source) < 0
|
|
17715
17806
|
);
|
|
17716
|
-
function movesKeepEachElementsHistory(timeline, plan, children) {
|
|
17807
|
+
function movesKeepEachElementsHistory(timeline, plan, children, registry3) {
|
|
17717
17808
|
const byElement = /* @__PURE__ */ new Map();
|
|
17718
17809
|
children.forEach((child, i) => {
|
|
17719
17810
|
for (const target of child.targets?.() ?? []) {
|
|
@@ -17725,16 +17816,25 @@ function movesKeepEachElementsHistory(timeline, plan, children) {
|
|
|
17725
17816
|
const moved = /* @__PURE__ */ new Set();
|
|
17726
17817
|
for (const [target, indexes] of byElement) {
|
|
17727
17818
|
if (!indexes.some((i) => plan.tweens[i].moved)) continue;
|
|
17728
|
-
if (inOrHostsSubComposition(target, plan.key)) return false;
|
|
17729
17819
|
const tweens = indexes.map((i) => plan.tweens[i]);
|
|
17730
17820
|
const shifted = tweens.every((t2) => t2.duration === t2.wasDuration);
|
|
17731
17821
|
const undelayed = indexes.every((i) => !children[i].delay() && !children[i].repeatDelay?.());
|
|
17732
17822
|
if (!keepsOrder(tweens) || !sharesOneStretch(tweens) || !(shifted || undelayed)) return false;
|
|
17733
17823
|
moved.add(target);
|
|
17734
17824
|
}
|
|
17735
|
-
return !timeline
|
|
17736
|
-
|
|
17825
|
+
return !animatedElsewhere(timeline, registry3, moved);
|
|
17826
|
+
}
|
|
17827
|
+
function animatedElsewhere(own, registry3, targets) {
|
|
17828
|
+
const seen = /* @__PURE__ */ new Set([own]);
|
|
17829
|
+
const visit = (timeline) => {
|
|
17830
|
+
if (seen.has(timeline)) return false;
|
|
17831
|
+
seen.add(timeline);
|
|
17832
|
+
return timeline.getChildren(false, true, false).some((tween) => tween.targets?.().some((target) => targets.has(target))) || timeline.getChildren(false, false, true).some(visit);
|
|
17833
|
+
};
|
|
17834
|
+
const timelines = registry3.filter(
|
|
17835
|
+
(entry2) => typeof entry2?.getChildren === "function"
|
|
17737
17836
|
);
|
|
17837
|
+
return own.getChildren(false, false, true).some(visit) || timelines.some(visit);
|
|
17738
17838
|
}
|
|
17739
17839
|
function applyLiveRetime(iframe, plan) {
|
|
17740
17840
|
const win = iframe?.contentWindow;
|
|
@@ -17743,7 +17843,8 @@ function applyLiveRetime(iframe, plan) {
|
|
|
17743
17843
|
const children = pairedLiveTweens(timeline, plan);
|
|
17744
17844
|
if (!children) return false;
|
|
17745
17845
|
if (plan.tweens.some((t2) => t2.moved)) {
|
|
17746
|
-
|
|
17846
|
+
const registry3 = Object.values(win?.__timelines ?? {});
|
|
17847
|
+
if (!movesKeepEachElementsHistory(timeline, plan, children, registry3)) return false;
|
|
17747
17848
|
const bySource = plan.tweens.map((t2, i) => ({ ...t2, tween: children[i] })).sort((a, b) => a.source - b.source);
|
|
17748
17849
|
for (const { tween } of bySource) timeline.remove(tween);
|
|
17749
17850
|
for (const { tween, start, duration } of bySource) {
|
|
@@ -21246,7 +21347,10 @@ import {
|
|
|
21246
21347
|
Scissors as PhScissors,
|
|
21247
21348
|
Link as PhLink,
|
|
21248
21349
|
Eyedropper as PhEyedropper,
|
|
21249
|
-
Trash as PhTrash
|
|
21350
|
+
Trash as PhTrash,
|
|
21351
|
+
Image as PhImage,
|
|
21352
|
+
BezierCurve,
|
|
21353
|
+
FolderSimple
|
|
21250
21354
|
} from "@phosphor-icons/react";
|
|
21251
21355
|
import { jsx as jsx40 } from "react/jsx-runtime";
|
|
21252
21356
|
var makeIcon = (Icon) => {
|
|
@@ -21291,6 +21395,9 @@ var Scissors = makeIcon(PhScissors);
|
|
|
21291
21395
|
var Link = makeIcon(PhLink);
|
|
21292
21396
|
var Eyedropper = makeIcon(PhEyedropper);
|
|
21293
21397
|
var Trash = makeIcon(PhTrash);
|
|
21398
|
+
var ImageIcon = makeIcon(PhImage);
|
|
21399
|
+
var Vector = makeIcon(BezierCurve);
|
|
21400
|
+
var Folder = makeIcon(FolderSimple);
|
|
21294
21401
|
|
|
21295
21402
|
// src/player/components/TrackClipCount.tsx
|
|
21296
21403
|
import { jsx as jsx41 } from "react/jsx-runtime";
|
|
@@ -30342,9 +30449,12 @@ var gestureSaves = /* @__PURE__ */ new WeakMap();
|
|
|
30342
30449
|
function studioManualEditSavesIn(doc) {
|
|
30343
30450
|
return gestureSaves.get(doc) ?? 0;
|
|
30344
30451
|
}
|
|
30452
|
+
function countStudioPreviewChange(doc) {
|
|
30453
|
+
gestureSaves.set(doc, studioManualEditSavesIn(doc) + 1);
|
|
30454
|
+
}
|
|
30345
30455
|
function countStudioManualEditSave(element, save) {
|
|
30346
30456
|
const doc = element.ownerDocument;
|
|
30347
|
-
const count = () =>
|
|
30457
|
+
const count = () => countStudioPreviewChange(doc);
|
|
30348
30458
|
count();
|
|
30349
30459
|
const result = save();
|
|
30350
30460
|
void Promise.resolve(result).then(count, count);
|
|
@@ -37412,22 +37522,31 @@ function readCssRotation(element, withRotate = true) {
|
|
|
37412
37522
|
return angle(transform);
|
|
37413
37523
|
}
|
|
37414
37524
|
}
|
|
37415
|
-
function
|
|
37525
|
+
function readDragStamp(element) {
|
|
37526
|
+
const read2 = (name) => Number.parseFloat(element.getAttribute(name) ?? "");
|
|
37527
|
+
return {
|
|
37528
|
+
origX: read2("data-hf-drag-initial-offset-x") || 0,
|
|
37529
|
+
origY: read2("data-hf-drag-initial-offset-y") || 0,
|
|
37530
|
+
baseX: read2("data-hf-drag-gsap-base-x"),
|
|
37531
|
+
baseY: read2("data-hf-drag-gsap-base-y")
|
|
37532
|
+
};
|
|
37533
|
+
}
|
|
37534
|
+
var freezeDragStamp = (element) => ({
|
|
37535
|
+
...readDragStamp(element),
|
|
37536
|
+
frozen: true
|
|
37537
|
+
});
|
|
37538
|
+
function computeDraggedGsapPosition(element, studioOffset, fallbackBase, stamp = readDragStamp(element)) {
|
|
37416
37539
|
const rotStyle = element.style.getPropertyValue("--hf-studio-rotation");
|
|
37417
37540
|
const rotDeg = Number.parseFloat(rotStyle) || 0;
|
|
37418
37541
|
const rad = -rotDeg * Math.PI / 180;
|
|
37419
37542
|
const cos = Math.cos(rad);
|
|
37420
37543
|
const sin = Math.sin(rad);
|
|
37421
|
-
const
|
|
37422
|
-
const
|
|
37423
|
-
const deltaX = studioOffset.x - origX;
|
|
37424
|
-
const deltaY = studioOffset.y - origY;
|
|
37544
|
+
const deltaX = studioOffset.x - stamp.origX;
|
|
37545
|
+
const deltaY = studioOffset.y - stamp.origY;
|
|
37425
37546
|
const adjX = deltaX * cos - deltaY * sin;
|
|
37426
37547
|
const adjY = deltaX * sin + deltaY * cos;
|
|
37427
|
-
const
|
|
37428
|
-
const
|
|
37429
|
-
const baseGsapX = Number.isFinite(parsedBaseX) ? parsedBaseX : fallbackBase.x;
|
|
37430
|
-
const baseGsapY = Number.isFinite(parsedBaseY) ? parsedBaseY : fallbackBase.y;
|
|
37548
|
+
const baseGsapX = Number.isFinite(stamp.baseX) ? stamp.baseX : fallbackBase.x;
|
|
37549
|
+
const baseGsapY = Number.isFinite(stamp.baseY) ? stamp.baseY : fallbackBase.y;
|
|
37431
37550
|
return {
|
|
37432
37551
|
newX: roundTo3(baseGsapX + adjX),
|
|
37433
37552
|
newY: roundTo3(baseGsapY + adjY),
|
|
@@ -37435,10 +37554,10 @@ function computeDraggedGsapPosition(element, studioOffset, fallbackBase) {
|
|
|
37435
37554
|
baseGsapY
|
|
37436
37555
|
};
|
|
37437
37556
|
}
|
|
37438
|
-
function restoreDragOffset(element) {
|
|
37439
|
-
|
|
37440
|
-
element.style.setProperty("--hf-studio-offset-x", `${
|
|
37441
|
-
element.style.setProperty("--hf-studio-offset-y", `${
|
|
37557
|
+
function restoreDragOffset(element, stamp = readDragStamp(element)) {
|
|
37558
|
+
if (stamp.frozen) return;
|
|
37559
|
+
element.style.setProperty("--hf-studio-offset-x", `${stamp.origX}px`);
|
|
37560
|
+
element.style.setProperty("--hf-studio-offset-y", `${stamp.origY}px`);
|
|
37442
37561
|
element.removeAttribute("data-hf-drag-initial-offset-x");
|
|
37443
37562
|
element.removeAttribute("data-hf-drag-initial-offset-y");
|
|
37444
37563
|
}
|
|
@@ -37512,6 +37631,12 @@ function readTranslatePx(el) {
|
|
|
37512
37631
|
y: evaluateLength(y, side("height", "top", "bottom"))
|
|
37513
37632
|
};
|
|
37514
37633
|
}
|
|
37634
|
+
function readTranslatePxLeavingPercent(el) {
|
|
37635
|
+
const value = el.ownerDocument.defaultView?.getComputedStyle(el).translate || "none";
|
|
37636
|
+
const [x = "0px", y = "0px"] = value === "none" ? [] : splitTopLevelWhitespace(value);
|
|
37637
|
+
const px = (part) => roundTo3(evaluateLength(part, 0)) || 0;
|
|
37638
|
+
return { x: px(x), y: px(y) };
|
|
37639
|
+
}
|
|
37515
37640
|
var UNREADABLE_TRANSLATE = "Studio can't read this layer's translate. Move it in the Code tab.";
|
|
37516
37641
|
function formatTranslatePx(p) {
|
|
37517
37642
|
return `${roundTo3(p.x)}px ${roundTo3(p.y)}px`;
|
|
@@ -45740,7 +45865,12 @@ function refuseStepListRewrite(anim) {
|
|
|
45740
45865
|
if (step) throw new GsapEditBlockedError("keyframes-uneditable", step);
|
|
45741
45866
|
}
|
|
45742
45867
|
async function commitStaticGsapPosition(selection, studioOffset, gsapPos, selector, existingSet, callbacks) {
|
|
45743
|
-
const { newX, newY } = computeDraggedGsapPosition(
|
|
45868
|
+
const { newX, newY } = computeDraggedGsapPosition(
|
|
45869
|
+
selection.element,
|
|
45870
|
+
studioOffset,
|
|
45871
|
+
gsapPos,
|
|
45872
|
+
callbacks.stamp
|
|
45873
|
+
);
|
|
45744
45874
|
if (existingSet) {
|
|
45745
45875
|
if (existingSet.keyframes) {
|
|
45746
45876
|
await replaceKeyframedPositionHold(
|
|
@@ -45859,21 +45989,16 @@ async function commitStaticGsapSize(selection, size, selector, existingSet, call
|
|
|
45859
45989
|
}
|
|
45860
45990
|
async function commitWholePathOffset(selection, anim, studioOffset, gsapPos, iframe, selector, callbacks) {
|
|
45861
45991
|
const el = selection.element;
|
|
45992
|
+
const stamp = callbacks.stamp ?? readDragStamp(el);
|
|
45862
45993
|
const { newX, newY, baseGsapX, baseGsapY } = computeDraggedGsapPosition(
|
|
45863
45994
|
el,
|
|
45864
45995
|
studioOffset,
|
|
45865
|
-
gsapPos
|
|
45996
|
+
gsapPos,
|
|
45997
|
+
stamp
|
|
45866
45998
|
);
|
|
45867
45999
|
const deltaX = newX - baseGsapX;
|
|
45868
46000
|
const deltaY = newY - baseGsapY;
|
|
45869
|
-
const
|
|
45870
|
-
const origY = Number.parseFloat(el.getAttribute("data-hf-drag-initial-offset-y") ?? "") || 0;
|
|
45871
|
-
const restoreOffset = () => {
|
|
45872
|
-
el.style.setProperty("--hf-studio-offset-x", `${origX}px`);
|
|
45873
|
-
el.style.setProperty("--hf-studio-offset-y", `${origY}px`);
|
|
45874
|
-
el.removeAttribute("data-hf-drag-initial-offset-x");
|
|
45875
|
-
el.removeAttribute("data-hf-drag-initial-offset-y");
|
|
45876
|
-
};
|
|
46001
|
+
const restoreOffset = () => restoreDragOffset(el, stamp);
|
|
45877
46002
|
let effectiveAnim = anim;
|
|
45878
46003
|
if (anim.keyframes) {
|
|
45879
46004
|
refuseStepListRewrite(anim);
|
|
@@ -47811,19 +47936,14 @@ function gsapPositionFromDragOutcome(selection, anim, studioOffset, gsapPos, ifr
|
|
|
47811
47936
|
}
|
|
47812
47937
|
async function commitGsapPositionFromDrag(selection, anim, studioOffset, gsapPos, iframe, callbacks) {
|
|
47813
47938
|
const el = selection.element;
|
|
47939
|
+
const stamp = callbacks.stamp ?? readDragStamp(el);
|
|
47814
47940
|
const { newX, newY, baseGsapX, baseGsapY } = computeDraggedGsapPosition(
|
|
47815
47941
|
el,
|
|
47816
47942
|
studioOffset,
|
|
47817
|
-
gsapPos
|
|
47943
|
+
gsapPos,
|
|
47944
|
+
stamp
|
|
47818
47945
|
);
|
|
47819
|
-
const
|
|
47820
|
-
const origY = Number.parseFloat(el.getAttribute("data-hf-drag-initial-offset-y") ?? "") || 0;
|
|
47821
|
-
const restoreOffset = () => {
|
|
47822
|
-
el.style.setProperty("--hf-studio-offset-x", `${origX}px`);
|
|
47823
|
-
el.style.setProperty("--hf-studio-offset-y", `${origY}px`);
|
|
47824
|
-
el.removeAttribute("data-hf-drag-initial-offset-x");
|
|
47825
|
-
el.removeAttribute("data-hf-drag-initial-offset-y");
|
|
47826
|
-
};
|
|
47946
|
+
const restoreOffset = () => restoreDragOffset(el, stamp);
|
|
47827
47947
|
if (anim.arcPath?.enabled) {
|
|
47828
47948
|
const { activeKeyframePct, currentTime, setActiveKeyframePct } = usePlayerStore.getState();
|
|
47829
47949
|
const tweenStart = resolveTweenStart(anim);
|
|
@@ -48086,7 +48206,8 @@ async function tryGsapDragIntercept(selection, offset, allAnimations, iframe, ge
|
|
|
48086
48206
|
const existingSet = posAnim && isInstantHold(posAnim) && posAnim.targetSelector === selector ? posAnim : findExistingPositionWrite(resolvedAnimations, selector, selection.element);
|
|
48087
48207
|
await commitStaticGsapPosition(selection, offset, gsapPos, selector, existingSet, {
|
|
48088
48208
|
commitMutation,
|
|
48089
|
-
fetchAnimations: fetchFallbackAnimations
|
|
48209
|
+
fetchAnimations: fetchFallbackAnimations,
|
|
48210
|
+
stamp: options?.stamp
|
|
48090
48211
|
});
|
|
48091
48212
|
return { status: "persisted" };
|
|
48092
48213
|
}
|
|
@@ -48104,7 +48225,7 @@ async function tryGsapDragIntercept(selection, offset, allAnimations, iframe, ge
|
|
|
48104
48225
|
posAnim = freshMatch;
|
|
48105
48226
|
}
|
|
48106
48227
|
}
|
|
48107
|
-
const cbs = { commitMutation, fetchAnimations: fetchFallbackAnimations };
|
|
48228
|
+
const cbs = { commitMutation, fetchAnimations: fetchFallbackAnimations, stamp: options?.stamp };
|
|
48108
48229
|
if (route === "whole-path") {
|
|
48109
48230
|
await commitWholePathOffset(selection, posAnim, offset, gsapPos, iframe, selector, cbs);
|
|
48110
48231
|
} else {
|
|
@@ -50783,7 +50904,7 @@ function revealedScroll(shape, scrollLeft) {
|
|
|
50783
50904
|
if (shape.left < scrollLeft) return shape.left;
|
|
50784
50905
|
return Math.max(scrollLeft, shape.left + shape.size + 1 - shape.width);
|
|
50785
50906
|
}
|
|
50786
|
-
function measureFill(list,
|
|
50907
|
+
function measureFill(list, shapes2) {
|
|
50787
50908
|
const fill = fillOf(list);
|
|
50788
50909
|
const tab = list.querySelector(":scope > .dv-active-tab");
|
|
50789
50910
|
const shape = {
|
|
@@ -50792,8 +50913,8 @@ function measureFill(list, shapes) {
|
|
|
50792
50913
|
left: tab?.offsetLeft ?? 0,
|
|
50793
50914
|
size: tab?.offsetWidth ?? 0
|
|
50794
50915
|
};
|
|
50795
|
-
const reveal2 = tab !== null && reshaped(
|
|
50796
|
-
if (shape.width > 0)
|
|
50916
|
+
const reveal2 = tab !== null && reshaped(shapes2.get(list), shape);
|
|
50917
|
+
if (shape.width > 0) shapes2.set(list, shape);
|
|
50797
50918
|
const scrollLeft = list.scrollLeft;
|
|
50798
50919
|
const target = reveal2 ? revealedScroll(shape, scrollLeft) : scrollLeft;
|
|
50799
50920
|
return () => {
|
|
@@ -50828,10 +50949,10 @@ function installTabFill(api, root) {
|
|
|
50828
50949
|
observed.add(element);
|
|
50829
50950
|
}
|
|
50830
50951
|
}
|
|
50831
|
-
const
|
|
50952
|
+
const shapes2 = /* @__PURE__ */ new WeakMap();
|
|
50832
50953
|
function placeAll() {
|
|
50833
50954
|
const strips2 = [...lists()];
|
|
50834
|
-
const writes = strips2.map((list) => measureFill(list,
|
|
50955
|
+
const writes = strips2.map((list) => measureFill(list, shapes2));
|
|
50835
50956
|
for (const write of writes) write();
|
|
50836
50957
|
for (const list of strips2) markClippedEdges(list);
|
|
50837
50958
|
observe(strips2.flatMap((list) => [list, ...list.querySelectorAll(":scope > .dv-tab")]));
|
|
@@ -58874,6 +58995,25 @@ function formatPropValue(prop, v) {
|
|
|
58874
58995
|
if (PERCENT_PROPS.has(prop)) return `${Math.round(Number(v) * 100)}${unit}`;
|
|
58875
58996
|
return `${v}${unit}`;
|
|
58876
58997
|
}
|
|
58998
|
+
var easeLabel = (ease) => ease.startsWith("custom(") ? "custom" : EASE_LABELS[ease] ?? ease;
|
|
58999
|
+
function uniformSegmentEase(animation) {
|
|
59000
|
+
const eases = keyframedTweenEases(animation);
|
|
59001
|
+
const steps = animation.keyframes?.keyframes ?? [];
|
|
59002
|
+
const segmentEases = new Set(steps.slice(1).map((kf) => eases.segment(kf)));
|
|
59003
|
+
if (segmentEases.size === 0) return eases.segment({});
|
|
59004
|
+
return segmentEases.size === 1 ? [...segmentEases][0] : null;
|
|
59005
|
+
}
|
|
59006
|
+
function keyframedTweenSummary(animation, pos, dur) {
|
|
59007
|
+
const steps = animation.keyframes?.keyframes ?? [];
|
|
59008
|
+
const props = [...new Set(steps.flatMap((kf) => Object.keys(kf.properties)))];
|
|
59009
|
+
const propText = props.map((p) => (PROP_LABELS[p] ?? p).toLowerCase()).join(", ");
|
|
59010
|
+
const segmentEase = uniformSegmentEase(animation);
|
|
59011
|
+
const segmentText = steps.length < 2 ? "" : segmentEase ? `, each segment eased ${easeLabel(segmentEase)}` : ", with per-keyframe easing";
|
|
59012
|
+
const run = keyframedTweenEases(animation).run;
|
|
59013
|
+
const runText = run && run !== "none" ? `, across a ${easeLabel(run)} run` : "";
|
|
59014
|
+
const count = `${steps.length} keyframe${steps.length === 1 ? "" : "s"}`;
|
|
59015
|
+
return `Starting at ${pos}s, over ${dur}s, animate ${animation.targetSelector}'s ${propText || "no properties yet"} through ${count}${segmentText}${runText}.`;
|
|
59016
|
+
}
|
|
58877
59017
|
function buildTweenSummary(animation) {
|
|
58878
59018
|
const easeName = animation.ease ?? "none";
|
|
58879
59019
|
const ease = EASE_LABELS[easeName] ?? easeName;
|
|
@@ -58882,6 +59022,7 @@ function buildTweenSummary(animation) {
|
|
|
58882
59022
|
const dur = animation.duration ?? 0;
|
|
58883
59023
|
const rawPos = animation.position;
|
|
58884
59024
|
const pos = typeof rawPos === "number" ? parseFloat(rawPos.toFixed(3)) : rawPos;
|
|
59025
|
+
if (animation.keyframes) return keyframedTweenSummary(animation, pos, dur);
|
|
58885
59026
|
const propDescs = props.map(([p, v]) => {
|
|
58886
59027
|
const label = (PROP_LABELS[p] ?? p).toLowerCase();
|
|
58887
59028
|
return `${label} to ${formatPropValue(p, v)}`;
|
|
@@ -59096,6 +59237,7 @@ var APPLY_ALL_EASES = [
|
|
|
59096
59237
|
"bounce.out",
|
|
59097
59238
|
"bounce.inOut"
|
|
59098
59239
|
];
|
|
59240
|
+
var percentLabel = (pct) => pct > 0 && pct < 1e-3 ? "<0.001" : String(roundTo3(pct));
|
|
59099
59241
|
function KeyframeEaseList({
|
|
59100
59242
|
keyframes,
|
|
59101
59243
|
globalEase,
|
|
@@ -59130,8 +59272,8 @@ function KeyframeEaseList({
|
|
|
59130
59272
|
if (i === 0) return null;
|
|
59131
59273
|
const segEase = kf.ease ?? globalEase;
|
|
59132
59274
|
const isExpanded = expandedPct === kf.percentage;
|
|
59133
|
-
const label = `${keyframes[i - 1].percentage}% \u2192 ${kf.percentage}%`;
|
|
59134
|
-
const
|
|
59275
|
+
const label = `${percentLabel(keyframes[i - 1].percentage)}% \u2192 ${percentLabel(kf.percentage)}%`;
|
|
59276
|
+
const easeLabel2 = segEase.startsWith("custom(") ? "Custom" : EASE_LABELS[segEase] ?? segEase;
|
|
59135
59277
|
return /* @__PURE__ */ jsxs105(
|
|
59136
59278
|
"div",
|
|
59137
59279
|
{
|
|
@@ -59147,7 +59289,7 @@ function KeyframeEaseList({
|
|
|
59147
59289
|
className: "flex w-full items-center gap-2 px-2 py-1.5 text-left active:scale-[0.99]",
|
|
59148
59290
|
children: [
|
|
59149
59291
|
/* @__PURE__ */ jsx140("span", { className: "text-[10px] font-medium text-neutral-400", children: label }),
|
|
59150
|
-
/* @__PURE__ */ jsx140("span", { className: "ml-auto text-[9px] text-neutral-500", children:
|
|
59292
|
+
/* @__PURE__ */ jsx140("span", { className: "ml-auto text-[9px] text-neutral-500", children: easeLabel2 }),
|
|
59151
59293
|
/* @__PURE__ */ jsx140(
|
|
59152
59294
|
"svg",
|
|
59153
59295
|
{
|
|
@@ -59360,6 +59502,7 @@ function parseNumericOrString(raw) {
|
|
|
59360
59502
|
|
|
59361
59503
|
// src/components/editor/AnimationCard.tsx
|
|
59362
59504
|
import { Fragment as Fragment40, jsx as jsx142, jsxs as jsxs107 } from "react/jsx-runtime";
|
|
59505
|
+
var easeDisplayName = (ease) => ease.startsWith("custom(") ? "Custom curve" : EASE_LABELS[ease] ?? ease;
|
|
59363
59506
|
var AnimationCard = memo37(function AnimationCard2({
|
|
59364
59507
|
animation,
|
|
59365
59508
|
defaultExpanded,
|
|
@@ -59465,7 +59608,9 @@ var AnimationCard = memo37(function AnimationCard2({
|
|
|
59465
59608
|
const [copied, setCopied] = useState75(false);
|
|
59466
59609
|
const methodLabel = METHOD_LABELS[animation.method] ?? animation.method;
|
|
59467
59610
|
const easeName = (animation.keyframes ? animation.keyframes.easeEach : void 0) ?? animation.ease ?? "none";
|
|
59468
|
-
const
|
|
59611
|
+
const headerEase = animation.keyframes ? uniformSegmentEase(animation) : easeName;
|
|
59612
|
+
const easeLabel2 = headerEase === null ? "Mixed" : easeDisplayName(headerEase);
|
|
59613
|
+
const runEase = animation.keyframes ? keyframedTweenEases(animation).run : void 0;
|
|
59469
59614
|
const endTime = typeof animation.position === "number" ? animation.position + (animation.duration ?? 0) : animation.position;
|
|
59470
59615
|
const summary = useMemo57(() => buildTweenSummary(animation), [animation]);
|
|
59471
59616
|
const setKeys = Object.keys(animation.properties);
|
|
@@ -59523,8 +59668,9 @@ var AnimationCard = memo37(function AnimationCard2({
|
|
|
59523
59668
|
"span",
|
|
59524
59669
|
{
|
|
59525
59670
|
className: `ml-auto text-[10px] ${flat ? "text-panel-text-3" : "text-neutral-500"}`,
|
|
59526
|
-
title:
|
|
59527
|
-
|
|
59671
|
+
title: headerEase ?? "Mixed",
|
|
59672
|
+
"data-card-ease": true,
|
|
59673
|
+
children: easeLabel2
|
|
59528
59674
|
}
|
|
59529
59675
|
),
|
|
59530
59676
|
/* @__PURE__ */ jsx142(
|
|
@@ -59564,6 +59710,10 @@ var AnimationCard = memo37(function AnimationCard2({
|
|
|
59564
59710
|
}
|
|
59565
59711
|
),
|
|
59566
59712
|
"Keyframed \u2014 click a segment below to edit its curve"
|
|
59713
|
+
] }),
|
|
59714
|
+
runEase && runEase !== "none" && /* @__PURE__ */ jsxs107("p", { className: "mt-1 text-[9px] text-neutral-500", "data-card-run-ease": true, children: [
|
|
59715
|
+
"Run ease: ",
|
|
59716
|
+
easeDisplayName(runEase)
|
|
59567
59717
|
] })
|
|
59568
59718
|
] }),
|
|
59569
59719
|
/* @__PURE__ */ jsx142(
|
|
@@ -59607,7 +59757,7 @@ var AnimationCard = memo37(function AnimationCard2({
|
|
|
59607
59757
|
KeyframeEaseList,
|
|
59608
59758
|
{
|
|
59609
59759
|
keyframes: animation.keyframes.keyframes,
|
|
59610
|
-
globalEase: animation.
|
|
59760
|
+
globalEase: keyframedTweenEases(animation).segment({}),
|
|
59611
59761
|
expandedPct: expandedKfPct,
|
|
59612
59762
|
collidingAnimationTargets: focusedCollidingAnimationTargets,
|
|
59613
59763
|
onToggle: (pct) => {
|
|
@@ -70768,7 +70918,7 @@ import {
|
|
|
70768
70918
|
Trash as Trash2,
|
|
70769
70919
|
FilePlus,
|
|
70770
70920
|
FolderSimplePlus,
|
|
70771
|
-
FolderSimple
|
|
70921
|
+
FolderSimple as FolderSimple2
|
|
70772
70922
|
} from "@phosphor-icons/react";
|
|
70773
70923
|
|
|
70774
70924
|
// src/components/editor/FileTreeIcons.tsx
|
|
@@ -70789,7 +70939,7 @@ import {
|
|
|
70789
70939
|
File as File2,
|
|
70790
70940
|
Waveform,
|
|
70791
70941
|
TextAa,
|
|
70792
|
-
Image as
|
|
70942
|
+
Image as PhImage2
|
|
70793
70943
|
} from "@phosphor-icons/react";
|
|
70794
70944
|
import { jsx as jsx189 } from "react/jsx-runtime";
|
|
70795
70945
|
var SZ = 14;
|
|
@@ -70812,7 +70962,7 @@ var ICONS = /* @__PURE__ */ new Map([
|
|
|
70812
70962
|
["txt", [FileTxt, GRAY]],
|
|
70813
70963
|
["png", [FilePng, GREEN]],
|
|
70814
70964
|
["jpg", [FileJpg, GREEN]],
|
|
70815
|
-
["webp", [
|
|
70965
|
+
["webp", [PhImage2, GREEN]],
|
|
70816
70966
|
["mp4", [FileVideo, "text-[light-dark(oklch(0.59_0.2_304),oklch(0.71_0.2_304))]"]],
|
|
70817
70967
|
["mp3", [Waveform, "text-[light-dark(oklch(0.53_0.159_165),#3CE6AC)]"]],
|
|
70818
70968
|
["woff", [TextAa, DIM]]
|
|
@@ -71110,7 +71260,7 @@ function InlineInput({
|
|
|
71110
71260
|
className: "flex items-center gap-2 py-0.5 min-h-7",
|
|
71111
71261
|
style: { paddingLeft: `${8 + depth * 12 + (isFolder ? 0 : 14)}px` },
|
|
71112
71262
|
children: [
|
|
71113
|
-
isFolder ? /* @__PURE__ */ jsx190(
|
|
71263
|
+
isFolder ? /* @__PURE__ */ jsx190(FolderSimple2, { size: SZ_ICON, weight: "duotone", className: `shrink-0 ${DIM}` }) : /* @__PURE__ */ jsx190(FileIcon, { path: value }),
|
|
71114
71264
|
/* @__PURE__ */ jsxs149("div", { className: "flex-1 min-w-0", children: [
|
|
71115
71265
|
/* @__PURE__ */ jsx190(
|
|
71116
71266
|
"input",
|
|
@@ -74787,7 +74937,8 @@ function showRestoreInPlace(iframe, activeCompPath, files, currentTime) {
|
|
|
74787
74937
|
const doc = iframe?.contentDocument;
|
|
74788
74938
|
const win = iframe?.contentWindow;
|
|
74789
74939
|
const plan = doc && win ? planRestoreTargets(doc, activeCompPath ?? "index.html", files) : null;
|
|
74790
|
-
if (!iframe || !win || !plan || plan.scripted) return null;
|
|
74940
|
+
if (!iframe || !doc || !win || !plan || plan.scripted) return null;
|
|
74941
|
+
countStudioPreviewChange(doc);
|
|
74791
74942
|
const before = plan.targets.map(
|
|
74792
74943
|
({ live, restored }) => [live, live.cloneNode(false), restored]
|
|
74793
74944
|
);
|
|
@@ -74821,6 +74972,7 @@ function applyUndoRestoreToPreview(iframe, activeCompPath, files, currentTime, r
|
|
|
74821
74972
|
reloadPreview();
|
|
74822
74973
|
return "full";
|
|
74823
74974
|
}
|
|
74975
|
+
countStudioPreviewChange(doc);
|
|
74824
74976
|
for (const target of plan.targets)
|
|
74825
74977
|
syncElementAttributes(target.live, target.restored, target.previous);
|
|
74826
74978
|
const active = files[activeDocPath];
|
|
@@ -78180,7 +78332,7 @@ function useTimelineMoveEditsHandler(handleTimelineGroupMove) {
|
|
|
78180
78332
|
}
|
|
78181
78333
|
|
|
78182
78334
|
// src/hooks/useDomEditSession.ts
|
|
78183
|
-
import { useCallback as
|
|
78335
|
+
import { useCallback as useCallback149 } from "react";
|
|
78184
78336
|
|
|
78185
78337
|
// src/hooks/useAskAgentModal.ts
|
|
78186
78338
|
import { useState as useState117, useCallback as useCallback125, useRef as useRef140, useEffect as useEffect115 } from "react";
|
|
@@ -80506,6 +80658,7 @@ function savePlainRotation({ commitPositionPatchToHtml, readOnlyPreview }, selec
|
|
|
80506
80658
|
}
|
|
80507
80659
|
|
|
80508
80660
|
// src/hooks/useDomGeometryCommits.ts
|
|
80661
|
+
var boxSizeCommitCounter = 0;
|
|
80509
80662
|
function useDomGeometryCommits({
|
|
80510
80663
|
showToast,
|
|
80511
80664
|
commitPositionPatchToHtml,
|
|
@@ -80535,7 +80688,10 @@ function useDomGeometryCommits({
|
|
|
80535
80688
|
if (offset) patches.push(...writePlainMove(element, offset));
|
|
80536
80689
|
return commitPositionPatchToHtml(selection, patches, {
|
|
80537
80690
|
label: "Resize layer box",
|
|
80538
|
-
...undoKey ? { coalesceKey: undoKey, coalesceMs: Number.POSITIVE_INFINITY, deferRender: true } : {
|
|
80691
|
+
...undoKey ? { coalesceKey: undoKey, coalesceMs: Number.POSITIVE_INFINITY, deferRender: true } : {
|
|
80692
|
+
coalesceKey: `box-size:${++boxSizeCommitCounter}`,
|
|
80693
|
+
coalesceMs: Number.POSITIVE_INFINITY
|
|
80694
|
+
}
|
|
80539
80695
|
}).catch((error) => {
|
|
80540
80696
|
restoreStudioBoxSize(element, beforeSize);
|
|
80541
80697
|
if (offset) restoreStudioPathOffset(element, beforeOffset);
|
|
@@ -80973,6 +81129,7 @@ function applyGlobalSet(iframe, selector, props) {
|
|
|
80973
81129
|
const numeric = finiteNumericProps(props);
|
|
80974
81130
|
if (!gsapLib?.set || !el || !numeric) return false;
|
|
80975
81131
|
gsapLib.set(el, numeric);
|
|
81132
|
+
recordLiveSet(el, numeric);
|
|
80976
81133
|
return true;
|
|
80977
81134
|
} catch {
|
|
80978
81135
|
return false;
|
|
@@ -83164,7 +83321,7 @@ function useGsapAwareGroupMove({
|
|
|
83164
83321
|
}
|
|
83165
83322
|
|
|
83166
83323
|
// src/hooks/useGsapAwareEditing.ts
|
|
83167
|
-
import { useCallback as
|
|
83324
|
+
import { useCallback as useCallback147 } from "react";
|
|
83168
83325
|
|
|
83169
83326
|
// src/hooks/gsapResizePreflight.ts
|
|
83170
83327
|
function resizeRoute(animations, fetchedAnimations) {
|
|
@@ -83196,9 +83353,339 @@ function preflightGsapResizeIntercept(selection, animations, iframe, fetchedAnim
|
|
|
83196
83353
|
return { status: "persisted" };
|
|
83197
83354
|
}
|
|
83198
83355
|
|
|
83356
|
+
// src/hooks/useEnableKeyframes.ts
|
|
83357
|
+
import { useCallback as useCallback145 } from "react";
|
|
83358
|
+
var enableKeyframesTransactionCounter = 0;
|
|
83359
|
+
function animatedProps(anim) {
|
|
83360
|
+
if (!anim) return ["x", "y"];
|
|
83361
|
+
const own = Object.keys(anim.properties ?? {});
|
|
83362
|
+
if (own.length > 0) return own;
|
|
83363
|
+
const stops = anim.keyframes?.keyframes;
|
|
83364
|
+
if (stops?.length) {
|
|
83365
|
+
const keys = /* @__PURE__ */ new Set();
|
|
83366
|
+
for (const stop2 of stops) for (const k of Object.keys(stop2.properties ?? {})) keys.add(k);
|
|
83367
|
+
if (keys.size > 0) return [...keys];
|
|
83368
|
+
}
|
|
83369
|
+
return ["x", "y"];
|
|
83370
|
+
}
|
|
83371
|
+
function isPlayheadWithinTween(anim, currentTime) {
|
|
83372
|
+
const start = resolveTweenStart(anim);
|
|
83373
|
+
if (start === null) return true;
|
|
83374
|
+
return isTimeWithinTween(currentTime, start, resolveTweenDuration(anim));
|
|
83375
|
+
}
|
|
83376
|
+
async function replaceSetWithSingleKeyframe(session, sel, setAnim, t2, iframe, selector) {
|
|
83377
|
+
const position = readElementPosition(iframe, sel, setAnim);
|
|
83378
|
+
if (Object.keys(position).length === 0) {
|
|
83379
|
+
for (const [key2, held] of Object.entries(setAnim.properties ?? {})) {
|
|
83380
|
+
if (typeof held === "number") position[key2] = held;
|
|
83381
|
+
}
|
|
83382
|
+
}
|
|
83383
|
+
if (Object.keys(position).length === 0 || !session.commitMutation) return;
|
|
83384
|
+
const range = resolveNewTweenRange(sel.dataAttributes?.start, sel.dataAttributes?.duration, t2);
|
|
83385
|
+
await session.commitMutation(
|
|
83386
|
+
{
|
|
83387
|
+
type: "replace-with-keyframes",
|
|
83388
|
+
animationId: setAnim.id,
|
|
83389
|
+
targetSelector: selector,
|
|
83390
|
+
position: roundTo3(range.start),
|
|
83391
|
+
duration: roundTo3(range.duration),
|
|
83392
|
+
keyframes: [{ percentage: 0, properties: position }],
|
|
83393
|
+
ease: setAnim.ease
|
|
83394
|
+
},
|
|
83395
|
+
{ label: "Enable keyframes", keyframeAction: "add", softReload: true }
|
|
83396
|
+
);
|
|
83397
|
+
}
|
|
83398
|
+
function readElementPosition(iframe, sel, anim) {
|
|
83399
|
+
const result = {};
|
|
83400
|
+
if (!iframe?.contentWindow) return result;
|
|
83401
|
+
let gsap3;
|
|
83402
|
+
try {
|
|
83403
|
+
gsap3 = iframe.contentWindow.gsap;
|
|
83404
|
+
} catch {
|
|
83405
|
+
return result;
|
|
83406
|
+
}
|
|
83407
|
+
const element = sel.element;
|
|
83408
|
+
if (!element?.isConnected || !gsap3?.getProperty) return result;
|
|
83409
|
+
const props = animatedProps(anim);
|
|
83410
|
+
for (const prop of props) {
|
|
83411
|
+
const val = Number(gsap3.getProperty(element, prop));
|
|
83412
|
+
if (!Number.isFinite(val)) continue;
|
|
83413
|
+
result[prop] = POSITION_PROPS.has(prop) ? Math.round(val) : roundTo3(val);
|
|
83414
|
+
}
|
|
83415
|
+
return result;
|
|
83416
|
+
}
|
|
83417
|
+
function resolveNewTweenRange(authoredStart, authoredDuration, currentTime) {
|
|
83418
|
+
const t2 = Math.max(0, roundTo3(currentTime));
|
|
83419
|
+
const start = authoredStart != null ? Number.parseFloat(authoredStart) : Number.NaN;
|
|
83420
|
+
const duration = authoredDuration != null ? Number.parseFloat(authoredDuration) : Number.NaN;
|
|
83421
|
+
if (!Number.isFinite(start) || !Number.isFinite(duration) || duration <= 0) {
|
|
83422
|
+
return { start: t2, duration: 1 };
|
|
83423
|
+
}
|
|
83424
|
+
const end = start + duration;
|
|
83425
|
+
const clampedStart = Math.min(Math.max(t2, start), end);
|
|
83426
|
+
return { start: clampedStart, duration: Math.max(0.5, roundTo3(end - clampedStart)) };
|
|
83427
|
+
}
|
|
83428
|
+
function singleKeyTweenMutation(sel, properties, currentTime) {
|
|
83429
|
+
const targetSelector = writeTargetSelector(sel);
|
|
83430
|
+
if (!targetSelector) return null;
|
|
83431
|
+
const { start, duration } = resolveNewTweenRange(
|
|
83432
|
+
sel.dataAttributes?.start,
|
|
83433
|
+
sel.dataAttributes?.duration,
|
|
83434
|
+
currentTime
|
|
83435
|
+
);
|
|
83436
|
+
return {
|
|
83437
|
+
type: "add-with-keyframes",
|
|
83438
|
+
targetSelector,
|
|
83439
|
+
position: roundTo3(start),
|
|
83440
|
+
duration: roundTo3(duration),
|
|
83441
|
+
keyframes: [{ percentage: 0, properties }]
|
|
83442
|
+
};
|
|
83443
|
+
}
|
|
83444
|
+
async function tryFetchAnimationsForElement(sel) {
|
|
83445
|
+
const projectId = window.location.hash.match(/project\/([^?/]+)/)?.[1];
|
|
83446
|
+
if (!projectId) return null;
|
|
83447
|
+
const sourceFile = sel.sourceFile || "index.html";
|
|
83448
|
+
const parsed = await fetchParsedAnimations(projectId, sourceFile);
|
|
83449
|
+
if (!parsed) return null;
|
|
83450
|
+
return getAnimationsForElement(parsed.animations, {
|
|
83451
|
+
id: sel.id,
|
|
83452
|
+
selector: sel.selector
|
|
83453
|
+
});
|
|
83454
|
+
}
|
|
83455
|
+
async function fetchAnimationsForElement(sel) {
|
|
83456
|
+
return await tryFetchAnimationsForElement(sel) ?? [];
|
|
83457
|
+
}
|
|
83458
|
+
async function extendKeyframedTweenToPlayhead(session, sel, anim, currentTime, duration, iframe, commitOverrides) {
|
|
83459
|
+
const selector = existingTweenTargetSelector(anim, sel);
|
|
83460
|
+
const position = readElementPosition(iframe, sel, anim);
|
|
83461
|
+
if (!selector || Object.keys(position).length === 0 || !session.commitMutation) return;
|
|
83462
|
+
const extended = buildExtendedKeyframes(anim, currentTime, position, duration);
|
|
83463
|
+
await session.commitMutation(
|
|
83464
|
+
{
|
|
83465
|
+
type: "replace-with-keyframes",
|
|
83466
|
+
animationId: anim.id,
|
|
83467
|
+
targetSelector: selector,
|
|
83468
|
+
position: extended.position,
|
|
83469
|
+
duration: extended.duration,
|
|
83470
|
+
keyframes: extended.keyframes,
|
|
83471
|
+
...keyframeEases(anim)
|
|
83472
|
+
},
|
|
83473
|
+
{
|
|
83474
|
+
label: "Add keyframe",
|
|
83475
|
+
keyframeAction: "add",
|
|
83476
|
+
softReload: true,
|
|
83477
|
+
...commitOverrides
|
|
83478
|
+
}
|
|
83479
|
+
);
|
|
83480
|
+
}
|
|
83481
|
+
async function applyKeyframeAtPlayhead(session, sel, kfAnim, t2, iframe, commitOverrides, liveTween) {
|
|
83482
|
+
const keepAuthoredDuration = kfAnim.durationUnresolved === true;
|
|
83483
|
+
if (keepAuthoredDuration) {
|
|
83484
|
+
kfAnim = withLiveTiming(kfAnim, liveTween ?? findParsedTween(iframe, sel.element, kfAnim));
|
|
83485
|
+
}
|
|
83486
|
+
if (keepAuthoredDuration && kfAnim.duration == null) return;
|
|
83487
|
+
const duration = resolveTweenDuration(kfAnim);
|
|
83488
|
+
const start = resolveTweenStart(kfAnim);
|
|
83489
|
+
if (start !== null && !isTimeWithinTween(t2, start, duration)) {
|
|
83490
|
+
if (keepAuthoredDuration) return;
|
|
83491
|
+
await extendKeyframedTweenToPlayhead(
|
|
83492
|
+
session,
|
|
83493
|
+
sel,
|
|
83494
|
+
kfAnim,
|
|
83495
|
+
t2,
|
|
83496
|
+
duration,
|
|
83497
|
+
iframe,
|
|
83498
|
+
commitOverrides
|
|
83499
|
+
);
|
|
83500
|
+
return;
|
|
83501
|
+
}
|
|
83502
|
+
const pct = start === null ? computeElementPercentage(t2, sel) : absoluteToPercentageForAnimation(t2, kfAnim) ?? 0;
|
|
83503
|
+
const existing = kfAnim.keyframes?.keyframes.find((k) => playsNear(kfAnim, k.percentage, pct));
|
|
83504
|
+
if (existing) {
|
|
83505
|
+
session.handleGsapRemoveKeyframe(kfAnim.id, existing.percentage);
|
|
83506
|
+
return;
|
|
83507
|
+
}
|
|
83508
|
+
if (session.handleGsapAddKeyframeBatch) {
|
|
83509
|
+
const position = readElementPosition(iframe, sel, kfAnim);
|
|
83510
|
+
if (Object.keys(position).length > 0) {
|
|
83511
|
+
await session.handleGsapAddKeyframeBatch(kfAnim.id, pct, position, commitOverrides);
|
|
83512
|
+
}
|
|
83513
|
+
}
|
|
83514
|
+
}
|
|
83515
|
+
async function promoteSetToKeyframes(session, sel, setAnim, t2, iframe) {
|
|
83516
|
+
const selector = existingTweenTargetSelector(setAnim, sel);
|
|
83517
|
+
const setStart = resolveTweenStart(setAnim) ?? 0;
|
|
83518
|
+
if (!selector || !session.commitMutation) return;
|
|
83519
|
+
if (t2 <= setStart) {
|
|
83520
|
+
await replaceSetWithSingleKeyframe(session, sel, setAnim, t2, iframe, selector);
|
|
83521
|
+
return;
|
|
83522
|
+
}
|
|
83523
|
+
const endPosition = readElementPosition(iframe, sel, setAnim);
|
|
83524
|
+
if (Object.keys(endPosition).length === 0) return;
|
|
83525
|
+
const startPosition = {};
|
|
83526
|
+
for (const key2 of Object.keys(endPosition)) {
|
|
83527
|
+
const held = setAnim.properties?.[key2];
|
|
83528
|
+
if (typeof held === "number") startPosition[key2] = held;
|
|
83529
|
+
}
|
|
83530
|
+
await session.commitMutation(
|
|
83531
|
+
{
|
|
83532
|
+
type: "replace-with-keyframes",
|
|
83533
|
+
animationId: setAnim.id,
|
|
83534
|
+
targetSelector: selector,
|
|
83535
|
+
position: roundTo3(setStart),
|
|
83536
|
+
duration: roundTo3(t2 - setStart),
|
|
83537
|
+
keyframes: [
|
|
83538
|
+
{
|
|
83539
|
+
percentage: 0,
|
|
83540
|
+
properties: Object.keys(startPosition).length > 0 ? startPosition : endPosition,
|
|
83541
|
+
auto: true
|
|
83542
|
+
},
|
|
83543
|
+
{ percentage: 100, properties: endPosition }
|
|
83544
|
+
],
|
|
83545
|
+
ease: setAnim.ease
|
|
83546
|
+
},
|
|
83547
|
+
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
83548
|
+
);
|
|
83549
|
+
}
|
|
83550
|
+
async function applyArcKeyframeAtPlayhead(session, sel, arcAnim, t2, iframe) {
|
|
83551
|
+
if (!session.commitMutation) return;
|
|
83552
|
+
const targetSelector = existingTweenTargetSelector(arcAnim, sel);
|
|
83553
|
+
if (!targetSelector) return;
|
|
83554
|
+
const start = resolveTweenStart(arcAnim) ?? 0;
|
|
83555
|
+
const duration = resolveTweenDuration(arcAnim);
|
|
83556
|
+
if (!isTimeWithinTween(t2, start, duration)) {
|
|
83557
|
+
const held = readElementPosition(iframe, sel, arcAnim);
|
|
83558
|
+
if (t2 <= start || typeof held.x !== "number" || typeof held.y !== "number") return;
|
|
83559
|
+
const extended = buildExtendedKeyframes(arcAnim, t2, { x: held.x, y: held.y }, duration, "none");
|
|
83560
|
+
await session.commitMutation(
|
|
83561
|
+
{
|
|
83562
|
+
type: "replace-with-keyframes",
|
|
83563
|
+
animationId: arcAnim.id,
|
|
83564
|
+
targetSelector,
|
|
83565
|
+
position: extended.position,
|
|
83566
|
+
duration: extended.duration,
|
|
83567
|
+
keyframes: extended.keyframes,
|
|
83568
|
+
ease: "none"
|
|
83569
|
+
},
|
|
83570
|
+
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
83571
|
+
);
|
|
83572
|
+
return;
|
|
83573
|
+
}
|
|
83574
|
+
const nodes = linearArcKeyframes(arcAnim);
|
|
83575
|
+
const playheadPercentage = absoluteToPercentage(t2, start, duration);
|
|
83576
|
+
const timedNodeIndex = nodes.findIndex(
|
|
83577
|
+
(node) => Math.abs(node.percentage - playheadPercentage) <= KEYFRAME_PCT_MATCH
|
|
83578
|
+
);
|
|
83579
|
+
if (timedNodeIndex !== -1) {
|
|
83580
|
+
if (timedNodeIndex > 0 && timedNodeIndex < nodes.length - 1) {
|
|
83581
|
+
await session.commitMutation(
|
|
83582
|
+
{
|
|
83583
|
+
type: "replace-with-keyframes",
|
|
83584
|
+
animationId: arcAnim.id,
|
|
83585
|
+
targetSelector,
|
|
83586
|
+
position: roundTo3(start),
|
|
83587
|
+
duration: roundTo3(duration),
|
|
83588
|
+
keyframes: nodes.filter((_, index) => index !== timedNodeIndex),
|
|
83589
|
+
ease: "none"
|
|
83590
|
+
},
|
|
83591
|
+
{ label: "Remove keyframe", softReload: true }
|
|
83592
|
+
);
|
|
83593
|
+
}
|
|
83594
|
+
return;
|
|
83595
|
+
}
|
|
83596
|
+
const live = readElementPosition(iframe, sel, arcAnim);
|
|
83597
|
+
if (typeof live.x !== "number" || typeof live.y !== "number") return;
|
|
83598
|
+
await session.commitMutation(
|
|
83599
|
+
{
|
|
83600
|
+
type: "replace-with-keyframes",
|
|
83601
|
+
animationId: arcAnim.id,
|
|
83602
|
+
targetSelector,
|
|
83603
|
+
position: roundTo3(start),
|
|
83604
|
+
duration: roundTo3(duration),
|
|
83605
|
+
keyframes: buildTemporalArcKeyframes(arcAnim, playheadPercentage, {
|
|
83606
|
+
x: live.x,
|
|
83607
|
+
y: live.y
|
|
83608
|
+
}),
|
|
83609
|
+
ease: "none"
|
|
83610
|
+
},
|
|
83611
|
+
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
83612
|
+
);
|
|
83613
|
+
}
|
|
83614
|
+
function useEnableKeyframes(sessionRef) {
|
|
83615
|
+
return useCallback145(async () => {
|
|
83616
|
+
const session = sessionRef.current;
|
|
83617
|
+
if (!session) return;
|
|
83618
|
+
const sel = session.domEditSelection;
|
|
83619
|
+
if (!sel) return;
|
|
83620
|
+
const t2 = usePlayerStore.getState().currentTime;
|
|
83621
|
+
const iframe = session.previewIframeRef?.current ?? null;
|
|
83622
|
+
const fetched = await tryFetchAnimationsForElement(sel);
|
|
83623
|
+
const anims = fetched ?? session.selectedGsapAnimations;
|
|
83624
|
+
const arcAnim = anims.find((a) => a.arcPath);
|
|
83625
|
+
const kfAnim = anims.find((a) => a.keyframes && !a.arcPath);
|
|
83626
|
+
const setAnim = anims.find((a) => isInstantHold(a) && !a.keyframes && !a.arcPath);
|
|
83627
|
+
const flatAnim = anims.find((a) => !a.keyframes && !a.arcPath && !isInstantHold(a));
|
|
83628
|
+
if (arcAnim) {
|
|
83629
|
+
await applyArcKeyframeAtPlayhead(session, sel, arcAnim, t2, iframe);
|
|
83630
|
+
} else if (kfAnim) {
|
|
83631
|
+
await applyKeyframeAtPlayhead(session, sel, kfAnim, t2, iframe);
|
|
83632
|
+
} else if (setAnim) {
|
|
83633
|
+
await promoteSetToKeyframes(session, sel, setAnim, t2, iframe);
|
|
83634
|
+
} else if (flatAnim) {
|
|
83635
|
+
const flatLive = flatAnim.durationUnresolved ? findParsedTween(iframe, sel.element, flatAnim) : void 0;
|
|
83636
|
+
enableKeyframesTransactionCounter += 1;
|
|
83637
|
+
const coalesceKey = `enable-keyframes:${flatAnim.id}:${enableKeyframesTransactionCounter}`;
|
|
83638
|
+
const convertCommitOverrides = {
|
|
83639
|
+
keyframeTelemetry: false,
|
|
83640
|
+
skipReload: true,
|
|
83641
|
+
coalesceKey,
|
|
83642
|
+
coalesceMs: Number.POSITIVE_INFINITY
|
|
83643
|
+
};
|
|
83644
|
+
await session.handleGsapConvertToKeyframes(
|
|
83645
|
+
flatAnim.id,
|
|
83646
|
+
void 0,
|
|
83647
|
+
void 0,
|
|
83648
|
+
convertCommitOverrides
|
|
83649
|
+
);
|
|
83650
|
+
const converted = (await fetchAnimationsForElement(sel)).find((a) => a.keyframes);
|
|
83651
|
+
if (converted) {
|
|
83652
|
+
const applyCommitOverrides = {
|
|
83653
|
+
softReload: true,
|
|
83654
|
+
coalesceKey,
|
|
83655
|
+
// Must match the convert phase's window: editHistory keys coalescing
|
|
83656
|
+
// off the incoming entry, so without Infinity here the apply (landing
|
|
83657
|
+
// after two POSTs + a fetch) falls back to the 300ms default and the
|
|
83658
|
+
// conversion splits into two undo entries under real latency.
|
|
83659
|
+
coalesceMs: Number.POSITIVE_INFINITY
|
|
83660
|
+
};
|
|
83661
|
+
await applyKeyframeAtPlayhead(
|
|
83662
|
+
session,
|
|
83663
|
+
sel,
|
|
83664
|
+
converted,
|
|
83665
|
+
t2,
|
|
83666
|
+
iframe,
|
|
83667
|
+
applyCommitOverrides,
|
|
83668
|
+
flatLive
|
|
83669
|
+
);
|
|
83670
|
+
}
|
|
83671
|
+
} else {
|
|
83672
|
+
const position = readElementPosition(iframe, sel, null);
|
|
83673
|
+
if (Object.keys(position).length === 0)
|
|
83674
|
+
Object.assign(position, readTranslatePxLeavingPercent(sel.element));
|
|
83675
|
+
const mutation = singleKeyTweenMutation(sel, position, t2);
|
|
83676
|
+
if (mutation && session.commitMutation) {
|
|
83677
|
+
await session.commitMutation(mutation, { label: "Enable keyframes", softReload: true });
|
|
83678
|
+
} else {
|
|
83679
|
+
session.handleGsapAddAnimation("to");
|
|
83680
|
+
}
|
|
83681
|
+
}
|
|
83682
|
+
}, [sessionRef]);
|
|
83683
|
+
}
|
|
83684
|
+
|
|
83199
83685
|
// src/hooks/gsapResizeIntercept.ts
|
|
83200
83686
|
var SIZE_PROPS = /* @__PURE__ */ new Set(["width", "height"]);
|
|
83201
83687
|
var POSITION_XY = /* @__PURE__ */ new Set(["x", "y"]);
|
|
83688
|
+
var MOVED_OR_SIZED = /* @__PURE__ */ new Set(["x", "y", "xPercent", "yPercent", "width", "height"]);
|
|
83202
83689
|
function originalBoxSize(el, measuredAttr, inlineProperty) {
|
|
83203
83690
|
const measured = Number.parseFloat(el?.getAttribute(measuredAttr) ?? "");
|
|
83204
83691
|
if (Number.isFinite(measured) && measured > 0) return measured;
|
|
@@ -83218,7 +83705,8 @@ async function commitSizeAtPlayhead(selection, anim, size, iframe, dragOffset, c
|
|
|
83218
83705
|
const anchor2 = moves && animationWritesAnyProperty(anim, POSITION_XY) ? computeDraggedGsapPosition(
|
|
83219
83706
|
selection.element,
|
|
83220
83707
|
dragOffset,
|
|
83221
|
-
readGsapPositionFromIframe(iframe, selector) ?? { x: 0, y: 0 }
|
|
83708
|
+
readGsapPositionFromIframe(iframe, selector) ?? { x: 0, y: 0 },
|
|
83709
|
+
callbacks.stamp
|
|
83222
83710
|
) : null;
|
|
83223
83711
|
const written = await commitValueAtPlayhead(
|
|
83224
83712
|
selection,
|
|
@@ -83232,11 +83720,28 @@ async function commitSizeAtPlayhead(selection, anim, size, iframe, dragOffset, c
|
|
|
83232
83720
|
...preGestureBoxSize(selection.element),
|
|
83233
83721
|
...anchor2 && { x: anchor2.baseGsapX, y: anchor2.baseGsapY }
|
|
83234
83722
|
},
|
|
83235
|
-
...anchor2 && { beforeReload: () => restoreDragOffset(selection.element) }
|
|
83723
|
+
...anchor2 && { beforeReload: () => restoreDragOffset(selection.element, callbacks.stamp) }
|
|
83236
83724
|
}
|
|
83237
83725
|
);
|
|
83238
83726
|
return written.status === "persisted" && anchor2 ? { ...written, ownsDragOffset: true } : written;
|
|
83239
83727
|
}
|
|
83728
|
+
function handOverDraftSize(selection, written, size, draw) {
|
|
83729
|
+
const { width, height } = size;
|
|
83730
|
+
if (written.status !== "persisted" || width == null || height == null) return written;
|
|
83731
|
+
draw(() => {
|
|
83732
|
+
clearStudioBoxSize(selection.element);
|
|
83733
|
+
setElementGsapSize(selection.element, width, height);
|
|
83734
|
+
});
|
|
83735
|
+
return written;
|
|
83736
|
+
}
|
|
83737
|
+
function firstSizeKey(selection, size, resizeGroup, animations) {
|
|
83738
|
+
const { autoKeyframeEnabled, currentTime } = usePlayerStore.getState();
|
|
83739
|
+
const keyframed = animations.some(
|
|
83740
|
+
(a) => a.keyframes && animationWritesAnyProperty(a, MOVED_OR_SIZED)
|
|
83741
|
+
);
|
|
83742
|
+
if (resizeGroup !== "size" || !autoKeyframeEnabled || !keyframed) return null;
|
|
83743
|
+
return singleKeyTweenMutation(selection, size, currentTime);
|
|
83744
|
+
}
|
|
83240
83745
|
function tweenUsesScaleLonghands(anim) {
|
|
83241
83746
|
const isLonghand = (name) => name === "scaleX" || name === "scaleY";
|
|
83242
83747
|
const inKeyframes = (anim?.keyframes?.keyframes ?? []).some(
|
|
@@ -83244,7 +83749,7 @@ function tweenUsesScaleLonghands(anim) {
|
|
|
83244
83749
|
);
|
|
83245
83750
|
return inKeyframes || Object.keys(anim?.properties ?? {}).some(isLonghand);
|
|
83246
83751
|
}
|
|
83247
|
-
async function tryGsapResizeIntercept(selection, size, animations, iframe, commitMutation, fetchFallbackAnimations, dragOffset, draw = (run) => run()) {
|
|
83752
|
+
async function tryGsapResizeIntercept(selection, size, animations, iframe, commitMutation, fetchFallbackAnimations, dragOffset, draw = (run) => run(), stamp) {
|
|
83248
83753
|
const fetchedAnimations = fetchFallbackAnimations ? await fetchFallbackAnimations() : [];
|
|
83249
83754
|
const outcome = preflightGsapResizeIntercept(selection, animations, iframe, fetchedAnimations);
|
|
83250
83755
|
if (outcome.status === "blocked") return outcome;
|
|
@@ -83269,10 +83774,16 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83269
83774
|
size
|
|
83270
83775
|
});
|
|
83271
83776
|
if (!anim || isInstantHold(anim)) {
|
|
83777
|
+
const sized = { width: roundToLayoutPx(size.width), height: roundToLayoutPx(size.height) };
|
|
83272
83778
|
const scriptWritesSize = allKnownAnimations.some(
|
|
83273
83779
|
(a) => animationWritesAnyProperty(a, SIZE_PROPS)
|
|
83274
83780
|
);
|
|
83275
|
-
if (!scriptWritesSize)
|
|
83781
|
+
if (!scriptWritesSize) {
|
|
83782
|
+
const firstKey = firstSizeKey(selection, sized, resizeGroup, workingAnimations);
|
|
83783
|
+
if (!firstKey) return { status: "element-size" };
|
|
83784
|
+
await commitMutation(selection, firstKey, { label: "Resize", softReload: true });
|
|
83785
|
+
return handOverDraftSize(selection, { status: "persisted" }, sized, draw);
|
|
83786
|
+
}
|
|
83276
83787
|
const sel = selectorFromSelection(selection) ?? writeTargetSelector(selection);
|
|
83277
83788
|
if (!sel) return { status: "blocked", reason: "no-selector" };
|
|
83278
83789
|
const sizeSet = resizeGroup === "size" ? anim ?? findSizeSetAnimation(workingAnimations, sel, selection.element) : findSizeSetAnimation(workingAnimations, sel, selection.element);
|
|
@@ -83284,11 +83795,19 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83284
83795
|
);
|
|
83285
83796
|
if (animatedTween) {
|
|
83286
83797
|
logResize("intercept-route", { route: "keyframed-size", tweenId: animatedTween.id });
|
|
83287
|
-
const
|
|
83288
|
-
|
|
83289
|
-
|
|
83290
|
-
|
|
83291
|
-
|
|
83798
|
+
const written2 = await commitSizeAtPlayhead(
|
|
83799
|
+
selection,
|
|
83800
|
+
animatedTween,
|
|
83801
|
+
sized,
|
|
83802
|
+
iframe,
|
|
83803
|
+
dragOffset,
|
|
83804
|
+
{
|
|
83805
|
+
commitMutation,
|
|
83806
|
+
fetchAnimations: fetchFallbackAnimations,
|
|
83807
|
+
stamp
|
|
83808
|
+
}
|
|
83809
|
+
);
|
|
83810
|
+
return handOverDraftSize(selection, written2, sized, draw);
|
|
83292
83811
|
}
|
|
83293
83812
|
}
|
|
83294
83813
|
logResize("intercept-route", { route: "static-size-set", hadSizeSet: !!sizeSet, resizeGroup });
|
|
@@ -83367,7 +83886,8 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83367
83886
|
const { baseGsapX, baseGsapY } = computeDraggedGsapPosition(
|
|
83368
83887
|
selection.element,
|
|
83369
83888
|
{ x: 0, y: 0 },
|
|
83370
|
-
gsapPos
|
|
83889
|
+
gsapPos,
|
|
83890
|
+
stamp
|
|
83371
83891
|
);
|
|
83372
83892
|
const base3 = { x: baseGsapX, y: baseGsapY };
|
|
83373
83893
|
setElementGsapPosition(draftEl, base3.x, base3.y);
|
|
@@ -83408,7 +83928,8 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83408
83928
|
assertGsapEditPersisted(
|
|
83409
83929
|
await commitGsapPositionFromDrag(selection, positionTween, delta, base2, iframe, {
|
|
83410
83930
|
commitMutation,
|
|
83411
|
-
fetchAnimations: fetchFallbackAnimations
|
|
83931
|
+
fetchAnimations: fetchFallbackAnimations,
|
|
83932
|
+
stamp
|
|
83412
83933
|
})
|
|
83413
83934
|
);
|
|
83414
83935
|
return true;
|
|
@@ -83416,7 +83937,8 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83416
83937
|
const existingSet = findExistingPositionWrite(currentAnimations, selector, selection.element);
|
|
83417
83938
|
await commitStaticGsapPosition(selection, delta, base2, selector, existingSet, {
|
|
83418
83939
|
commitMutation,
|
|
83419
|
-
fetchAnimations: fetchFallbackAnimations
|
|
83940
|
+
fetchAnimations: fetchFallbackAnimations,
|
|
83941
|
+
stamp
|
|
83420
83942
|
});
|
|
83421
83943
|
return true;
|
|
83422
83944
|
};
|
|
@@ -83433,9 +83955,18 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83433
83955
|
);
|
|
83434
83956
|
return { status: "persisted", ownsDragOffset: await finalizeScaleResizeCommit() };
|
|
83435
83957
|
}
|
|
83436
|
-
const callbacks = { commitMutation, fetchAnimations: fetchFallbackAnimations };
|
|
83437
|
-
if (resizeGroup === "size")
|
|
83438
|
-
|
|
83958
|
+
const callbacks = { commitMutation, fetchAnimations: fetchFallbackAnimations, stamp };
|
|
83959
|
+
if (resizeGroup === "size") {
|
|
83960
|
+
const written2 = await commitSizeAtPlayhead(
|
|
83961
|
+
selection,
|
|
83962
|
+
anim,
|
|
83963
|
+
resizeProps,
|
|
83964
|
+
iframe,
|
|
83965
|
+
dragOffset,
|
|
83966
|
+
callbacks
|
|
83967
|
+
);
|
|
83968
|
+
return handOverDraftSize(selection, written2, resizeProps, draw);
|
|
83969
|
+
}
|
|
83439
83970
|
const written = await commitValueAtPlayhead(selection, anim, resizeProps, iframe, callbacks, {
|
|
83440
83971
|
label: "Resize",
|
|
83441
83972
|
backfill: resizeBackfill
|
|
@@ -83445,7 +83976,7 @@ async function tryGsapResizeIntercept(selection, size, animations, iframe, commi
|
|
|
83445
83976
|
}
|
|
83446
83977
|
|
|
83447
83978
|
// src/hooks/useAnimatedPropertyCommit.ts
|
|
83448
|
-
import { useCallback as
|
|
83979
|
+
import { useCallback as useCallback146 } from "react";
|
|
83449
83980
|
import { classifyPropertyGroup as classifyPropertyGroup4 } from "@hyperframes/core/gsap-parser";
|
|
83450
83981
|
function pickBestAnimation(animations, selector, property) {
|
|
83451
83982
|
const targetGroup = property ? classifyPropertyGroup4(property) : void 0;
|
|
@@ -83640,7 +84171,7 @@ async function commitKeyframeProps(selection, anim, props, propEntries, primaryP
|
|
|
83640
84171
|
for (const k of Object.keys(properties)) {
|
|
83641
84172
|
if (!(k in p) && backfillDefaults[k] != null) p[k] = backfillDefaults[k];
|
|
83642
84173
|
}
|
|
83643
|
-
return { percentage: newPct, properties: p };
|
|
84174
|
+
return { percentage: newPct, properties: p, ...kf.ease ? { ease: kf.ease } : {} };
|
|
83644
84175
|
});
|
|
83645
84176
|
remapped.push({ percentage: toNewPct(ct), properties });
|
|
83646
84177
|
remapped.sort((a, b) => a.percentage - b.percentage);
|
|
@@ -83652,7 +84183,8 @@ async function commitKeyframeProps(selection, anim, props, propEntries, primaryP
|
|
|
83652
84183
|
targetSelector: anim.targetSelector,
|
|
83653
84184
|
position: roundTo3(newStart),
|
|
83654
84185
|
duration: roundTo3(newDuration),
|
|
83655
|
-
keyframes: remapped
|
|
84186
|
+
keyframes: remapped,
|
|
84187
|
+
...keyframeEases(anim)
|
|
83656
84188
|
},
|
|
83657
84189
|
{ label: `Edit ${primaryProp} (extended keyframe)`, keyframeAction: "add", softReload: true }
|
|
83658
84190
|
);
|
|
@@ -83683,7 +84215,7 @@ async function commitKeyframeProps(selection, anim, props, propEntries, primaryP
|
|
|
83683
84215
|
}
|
|
83684
84216
|
function useAnimatedPropertyCommit(deps) {
|
|
83685
84217
|
const { selectedGsapAnimations, gsapCommitMutation, previewIframeRef, bumpGsapCache } = deps;
|
|
83686
|
-
const commitAnimatedProperties =
|
|
84218
|
+
const commitAnimatedProperties = useCallback146(
|
|
83687
84219
|
// This is the single routing boundary for set, keyframe, whole-tween, and first-group writes.
|
|
83688
84220
|
// fallow-ignore-next-line complexity
|
|
83689
84221
|
async (selection, props, commit2 = gsapCommitMutation) => {
|
|
@@ -83789,7 +84321,7 @@ function useAnimatedPropertyCommit(deps) {
|
|
|
83789
84321
|
},
|
|
83790
84322
|
[selectedGsapAnimations, gsapCommitMutation, previewIframeRef, bumpGsapCache]
|
|
83791
84323
|
);
|
|
83792
|
-
const commitAnimatedProperty =
|
|
84324
|
+
const commitAnimatedProperty = useCallback146(
|
|
83793
84325
|
(selection, property, value) => commitAnimatedProperties(selection, { [property]: value }),
|
|
83794
84326
|
[commitAnimatedProperties]
|
|
83795
84327
|
);
|
|
@@ -83816,14 +84348,14 @@ function useGsapAwareEditing({
|
|
|
83816
84348
|
setArcPath,
|
|
83817
84349
|
updateArcSegment
|
|
83818
84350
|
}) {
|
|
83819
|
-
const getGsapAnimationsForSelection =
|
|
84351
|
+
const getGsapAnimationsForSelection = useCallback147(
|
|
83820
84352
|
(selection) => {
|
|
83821
84353
|
if (domEditSelection?.element === selection.element) return selectedGsapAnimations;
|
|
83822
84354
|
return makeFetchFallback(selection, { failOnFetchError: true })();
|
|
83823
84355
|
},
|
|
83824
84356
|
[domEditSelection, selectedGsapAnimations, makeFetchFallback]
|
|
83825
84357
|
);
|
|
83826
|
-
const handleGsapAwarePathOffsetCommit =
|
|
84358
|
+
const handleGsapAwarePathOffsetCommit = useCallback147(
|
|
83827
84359
|
async (selection, next, modifiers) => {
|
|
83828
84360
|
const writes = observeGsapGesture(gsapCommitMutation);
|
|
83829
84361
|
if (modifiers?.plainTranslate ?? editsPlainCss(selection.element, "move")) {
|
|
@@ -83874,8 +84406,9 @@ function useGsapAwareEditing({
|
|
|
83874
84406
|
stageElementPositionOffset,
|
|
83875
84407
|
showToast
|
|
83876
84408
|
});
|
|
83877
|
-
const handleGsapAwareBoxSizeCommit =
|
|
84409
|
+
const handleGsapAwareBoxSizeCommit = useCallback147(
|
|
83878
84410
|
async (selection, next, offset, restore2 = () => void 0, route) => {
|
|
84411
|
+
const stamp = freezeDragStamp(selection.element);
|
|
83879
84412
|
const writes = observeGsapGesture(gsapCommitMutation);
|
|
83880
84413
|
if (route?.plainTranslate ?? editsPlainCss(selection.element, "resize")) {
|
|
83881
84414
|
const result = await handleDomBoxSizeCommit(selection, next, offset, restore2);
|
|
@@ -83916,7 +84449,8 @@ function useGsapAwareEditing({
|
|
|
83916
84449
|
targetAnimations,
|
|
83917
84450
|
previewIframeRef.current,
|
|
83918
84451
|
commitMutation2,
|
|
83919
|
-
makeFetchFallback(selection)
|
|
84452
|
+
makeFetchFallback(selection),
|
|
84453
|
+
{ stamp }
|
|
83920
84454
|
);
|
|
83921
84455
|
await saveMove(dragOutcome, async () => {
|
|
83922
84456
|
const plainAfterSettle = editsPlainCss(selection.element, "move");
|
|
@@ -83937,7 +84471,12 @@ function useGsapAwareEditing({
|
|
|
83937
84471
|
x: 0,
|
|
83938
84472
|
y: 0
|
|
83939
84473
|
};
|
|
83940
|
-
const { newX, newY } = computeDraggedGsapPosition(
|
|
84474
|
+
const { newX, newY } = computeDraggedGsapPosition(
|
|
84475
|
+
selection.element,
|
|
84476
|
+
offset,
|
|
84477
|
+
gsapPos,
|
|
84478
|
+
stamp
|
|
84479
|
+
);
|
|
83941
84480
|
logResize("sync-settle", { gsapPos, offset, newX, newY });
|
|
83942
84481
|
setElementGsapPosition(selection.element, newX, newY);
|
|
83943
84482
|
});
|
|
@@ -83954,7 +84493,8 @@ function useGsapAwareEditing({
|
|
|
83954
84493
|
commitMutation2,
|
|
83955
84494
|
makeFetchFallback(selection),
|
|
83956
84495
|
offset,
|
|
83957
|
-
writes.drawKeepingUndone
|
|
84496
|
+
writes.drawKeepingUndone,
|
|
84497
|
+
stamp
|
|
83958
84498
|
);
|
|
83959
84499
|
assertGsapEditPersisted(outcome);
|
|
83960
84500
|
if (outcome.status === "element-size") {
|
|
@@ -84008,7 +84548,7 @@ function useGsapAwareEditing({
|
|
|
84008
84548
|
getGsapAnimationsForSelection
|
|
84009
84549
|
]
|
|
84010
84550
|
);
|
|
84011
|
-
const handleGsapAwareRotationCommit =
|
|
84551
|
+
const handleGsapAwareRotationCommit = useCallback147(
|
|
84012
84552
|
async (selection, next) => {
|
|
84013
84553
|
const writes = observeGsapGesture(gsapCommitMutation);
|
|
84014
84554
|
if (next.plain === void 0 ? editsPlainCss(selection.element, "rotate") : next.plain) {
|
|
@@ -84051,7 +84591,7 @@ function useGsapAwareEditing({
|
|
|
84051
84591
|
previewIframeRef,
|
|
84052
84592
|
bumpGsapCache
|
|
84053
84593
|
});
|
|
84054
|
-
const commitAnimatedProperties =
|
|
84594
|
+
const commitAnimatedProperties = useCallback147(
|
|
84055
84595
|
async (selection, properties) => {
|
|
84056
84596
|
try {
|
|
84057
84597
|
await writeSizeWithCrop(
|
|
@@ -84073,25 +84613,25 @@ function useGsapAwareEditing({
|
|
|
84073
84613
|
trackGsapInteractionFailure
|
|
84074
84614
|
]
|
|
84075
84615
|
);
|
|
84076
|
-
const commitAnimatedProperty =
|
|
84616
|
+
const commitAnimatedProperty = useCallback147(
|
|
84077
84617
|
(selection, property, value) => commitAnimatedProperties(selection, { [property]: value }),
|
|
84078
84618
|
[commitAnimatedProperties]
|
|
84079
84619
|
);
|
|
84080
|
-
const handleSetArcPath =
|
|
84620
|
+
const handleSetArcPath = useCallback147(
|
|
84081
84621
|
(animId, config) => {
|
|
84082
84622
|
if (!domEditSelection) return;
|
|
84083
84623
|
setArcPath(domEditSelection, animId, config);
|
|
84084
84624
|
},
|
|
84085
84625
|
[domEditSelection, setArcPath]
|
|
84086
84626
|
);
|
|
84087
|
-
const handleUpdateArcSegment =
|
|
84627
|
+
const handleUpdateArcSegment = useCallback147(
|
|
84088
84628
|
(animId, segmentIndex, update) => {
|
|
84089
84629
|
if (!domEditSelection) return;
|
|
84090
84630
|
updateArcSegment(domEditSelection, animId, segmentIndex, update);
|
|
84091
84631
|
},
|
|
84092
84632
|
[domEditSelection, updateArcSegment]
|
|
84093
84633
|
);
|
|
84094
|
-
const noopCommit =
|
|
84634
|
+
const noopCommit = useCallback147(async () => {
|
|
84095
84635
|
}, []);
|
|
84096
84636
|
const trackGsapSaveFailure = useGsapSaveFailureTelemetry(null);
|
|
84097
84637
|
const safeGsapCommit = useSafeGsapCommitMutation(
|
|
@@ -84099,14 +84639,14 @@ function useGsapAwareEditing({
|
|
|
84099
84639
|
trackGsapSaveFailure,
|
|
84100
84640
|
showToast
|
|
84101
84641
|
);
|
|
84102
|
-
const commitMutation =
|
|
84642
|
+
const commitMutation = useCallback147(
|
|
84103
84643
|
async (mutation, options, selection = domEditSelection) => {
|
|
84104
84644
|
if (!selection) return;
|
|
84105
84645
|
await safeGsapCommit(selection, mutation, options);
|
|
84106
84646
|
},
|
|
84107
84647
|
[domEditSelection, safeGsapCommit]
|
|
84108
84648
|
);
|
|
84109
|
-
const handleUnroll =
|
|
84649
|
+
const handleUnroll = useCallback147(() => {
|
|
84110
84650
|
void commitMutation(
|
|
84111
84651
|
{ type: "unroll-timeline" },
|
|
84112
84652
|
{ label: "Unroll to literal tweens", softReload: true }
|
|
@@ -84257,12 +84797,12 @@ function useStudioSelectionPublisher({
|
|
|
84257
84797
|
}
|
|
84258
84798
|
|
|
84259
84799
|
// src/hooks/useKeyframeEaseCommits.ts
|
|
84260
|
-
import { useCallback as
|
|
84800
|
+
import { useCallback as useCallback148 } from "react";
|
|
84261
84801
|
function useKeyframeEaseCommits({
|
|
84262
84802
|
gsapCommitMutation,
|
|
84263
84803
|
domEditSelectionRef
|
|
84264
84804
|
}) {
|
|
84265
|
-
const handleUpdateSegmentEase =
|
|
84805
|
+
const handleUpdateSegmentEase = useCallback148(
|
|
84266
84806
|
(targets, ease) => {
|
|
84267
84807
|
const selection = domEditSelectionRef.current;
|
|
84268
84808
|
if (!selection || targets.length === 0) return;
|
|
@@ -84296,11 +84836,11 @@ function useKeyframeEaseCommits({
|
|
|
84296
84836
|
},
|
|
84297
84837
|
[gsapCommitMutation, domEditSelectionRef]
|
|
84298
84838
|
);
|
|
84299
|
-
const handleUpdateKeyframeEase =
|
|
84839
|
+
const handleUpdateKeyframeEase = useCallback148(
|
|
84300
84840
|
(animationId, percentage, ease) => handleUpdateSegmentEase([{ animationId, tweenPercentage: percentage }], ease),
|
|
84301
84841
|
[handleUpdateSegmentEase]
|
|
84302
84842
|
);
|
|
84303
|
-
const handleSetAllKeyframeEases =
|
|
84843
|
+
const handleSetAllKeyframeEases = useCallback148(
|
|
84304
84844
|
(animationId, ease) => {
|
|
84305
84845
|
const sel = domEditSelectionRef.current;
|
|
84306
84846
|
if (!sel) return;
|
|
@@ -84736,7 +85276,7 @@ function useDomEditSession({
|
|
|
84736
85276
|
forceReloadSdkSession,
|
|
84737
85277
|
timelineElements
|
|
84738
85278
|
});
|
|
84739
|
-
const handleDomEditElementDelete =
|
|
85279
|
+
const handleDomEditElementDelete = useCallback149(
|
|
84740
85280
|
async (selection, options) => {
|
|
84741
85281
|
if (isRecordingRef?.current) {
|
|
84742
85282
|
showToast("Cannot edit timeline while recording", "error");
|
|
@@ -84759,7 +85299,7 @@ function useDomEditSession({
|
|
|
84759
85299
|
timelineElements
|
|
84760
85300
|
]
|
|
84761
85301
|
);
|
|
84762
|
-
const handleGroupSelection =
|
|
85302
|
+
const handleGroupSelection = useCallback149(() => {
|
|
84763
85303
|
const group = domEditGroupSelectionsRef.current;
|
|
84764
85304
|
const single = domEditSelectionRef.current;
|
|
84765
85305
|
const members = group.length > 0 ? group : single ? [single] : [];
|
|
@@ -84777,7 +85317,7 @@ function useDomEditSession({
|
|
|
84777
85317
|
trackStudioEvent("group", { action: "create", count: members.length });
|
|
84778
85318
|
void groupSelection(members);
|
|
84779
85319
|
}, [domEditGroupSelectionsRef, domEditSelectionRef, groupSelection, showToast]);
|
|
84780
|
-
const handleUngroupSelection =
|
|
85320
|
+
const handleUngroupSelection = useCallback149(() => {
|
|
84781
85321
|
const sel = domEditSelectionRef.current;
|
|
84782
85322
|
if (!sel?.element.hasAttribute("data-hf-group")) {
|
|
84783
85323
|
showToast("Select a group to ungroup", "info");
|
|
@@ -84885,7 +85425,7 @@ function useDomEditSession({
|
|
|
84885
85425
|
setArcPath,
|
|
84886
85426
|
updateArcSegment
|
|
84887
85427
|
});
|
|
84888
|
-
const handleDomGroupMoveBy =
|
|
85428
|
+
const handleDomGroupMoveBy = useCallback149(
|
|
84889
85429
|
(moves) => moveDomGroupBy(
|
|
84890
85430
|
moves,
|
|
84891
85431
|
(updates) => handleGsapAwareGroupPathOffsetCommit(updates, { refusalToast: false })
|
|
@@ -85011,7 +85551,7 @@ function useSdkSelectionSync(session, domEditSelection, domEditGroupSelections)
|
|
|
85011
85551
|
import { useEffect as useEffect126 } from "react";
|
|
85012
85552
|
|
|
85013
85553
|
// src/hooks/useSdkSession.ts
|
|
85014
|
-
import { useState as useState121, useEffect as useEffect125, useCallback as
|
|
85554
|
+
import { useState as useState121, useEffect as useEffect125, useCallback as useCallback150, useRef as useRef154 } from "react";
|
|
85015
85555
|
import { openComposition as openComposition3 } from "@hyperframes/sdk";
|
|
85016
85556
|
|
|
85017
85557
|
// src/hooks/externalFileReloadBus.ts
|
|
@@ -85225,8 +85765,8 @@ function useSdkSession(projectId, activeCompPath, fileTree = [], fileTreeLoaded
|
|
|
85225
85765
|
}
|
|
85226
85766
|
};
|
|
85227
85767
|
}, [projectId, activeCompPath, reloadToken]);
|
|
85228
|
-
const forceReload =
|
|
85229
|
-
const publish =
|
|
85768
|
+
const forceReload = useCallback150(() => setReloadToken((t2) => t2 + 1), []);
|
|
85769
|
+
const publish = useCallback150(({ candidate, expectedSession, targetPath }) => {
|
|
85230
85770
|
const expectedOwner = sessionOwnersRef.current.get(expectedSession);
|
|
85231
85771
|
const current = ownedSessionRef.current;
|
|
85232
85772
|
if (!isSessionOwnerActive(
|
|
@@ -85269,7 +85809,7 @@ function useStudioSdkSessions(projectId, activeCompPath, masterCompPath, fileTre
|
|
|
85269
85809
|
}
|
|
85270
85810
|
|
|
85271
85811
|
// src/hooks/useStudioExternalFileChanges.ts
|
|
85272
|
-
import { useCallback as
|
|
85812
|
+
import { useCallback as useCallback152 } from "react";
|
|
85273
85813
|
|
|
85274
85814
|
// src/utils/externalConflictStorage.ts
|
|
85275
85815
|
var DB_NAME = "hyperframes-studio-external-conflicts";
|
|
@@ -85370,7 +85910,7 @@ async function deleteExternalConflictSnapshot(projectId, filePath) {
|
|
|
85370
85910
|
}
|
|
85371
85911
|
|
|
85372
85912
|
// src/hooks/useExternalFileChangeCoordinator.ts
|
|
85373
|
-
import { useCallback as
|
|
85913
|
+
import { useCallback as useCallback151, useEffect as useEffect127, useRef as useRef155, useState as useState122 } from "react";
|
|
85374
85914
|
function testHotAdapter() {
|
|
85375
85915
|
const value = globalThis.__HF_STUDIO_HOT_TEST_ADAPTER__;
|
|
85376
85916
|
if (!value || typeof value !== "object") return null;
|
|
@@ -85431,7 +85971,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85431
85971
|
const drainingRef = useRef155(false);
|
|
85432
85972
|
const pendingPayloadRef = useRef155(null);
|
|
85433
85973
|
blockedRef.current = blocked;
|
|
85434
|
-
const setBlocked =
|
|
85974
|
+
const setBlocked = useCallback151((next) => {
|
|
85435
85975
|
setBlockedState(
|
|
85436
85976
|
(held) => next && held ? { ...next, payload: mergeFileChangeAffectedCompositions(held.payload, next.payload) } : next
|
|
85437
85977
|
);
|
|
@@ -85486,7 +86026,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85486
86026
|
cancelled = true;
|
|
85487
86027
|
};
|
|
85488
86028
|
}, [loadConflictSnapshot, projectId, recoveryFilePath, setBlocked]);
|
|
85489
|
-
const reloadAcceptedGeneration =
|
|
86029
|
+
const reloadAcceptedGeneration = useCallback151(
|
|
85490
86030
|
(path, affectsPreview = true) => {
|
|
85491
86031
|
logReload(affectsPreview ? "reload" : "file-tree only", {
|
|
85492
86032
|
path,
|
|
@@ -85498,7 +86038,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85498
86038
|
},
|
|
85499
86039
|
[reloadPreview, reloadSdkSession, refreshFileTree]
|
|
85500
86040
|
);
|
|
85501
|
-
const persistSnapshotInOrder =
|
|
86041
|
+
const persistSnapshotInOrder = useCallback151(async (write) => {
|
|
85502
86042
|
const next = snapshotWriteTailRef.current.catch(() => void 0).then(write);
|
|
85503
86043
|
snapshotWriteTailRef.current = next.then(
|
|
85504
86044
|
() => void 0,
|
|
@@ -85506,7 +86046,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85506
86046
|
);
|
|
85507
86047
|
await next;
|
|
85508
86048
|
}, []);
|
|
85509
|
-
const drainOnePending =
|
|
86049
|
+
const drainOnePending = useCallback151(
|
|
85510
86050
|
// fallow-ignore-next-line complexity
|
|
85511
86051
|
async (payload) => {
|
|
85512
86052
|
const path = readStudioFileChangePath(payload);
|
|
@@ -85605,7 +86145,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85605
86145
|
onAcceptedPersistedFileChange
|
|
85606
86146
|
]
|
|
85607
86147
|
);
|
|
85608
|
-
const startDrainLoop =
|
|
86148
|
+
const startDrainLoop = useCallback151(async () => {
|
|
85609
86149
|
if (drainingRef.current) return;
|
|
85610
86150
|
drainingRef.current = true;
|
|
85611
86151
|
try {
|
|
@@ -85619,7 +86159,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85619
86159
|
drainingRef.current = false;
|
|
85620
86160
|
}
|
|
85621
86161
|
}, [drainOnePending]);
|
|
85622
|
-
const processChange =
|
|
86162
|
+
const processChange = useCallback151(
|
|
85623
86163
|
// fallow-ignore-next-line complexity
|
|
85624
86164
|
(payload) => {
|
|
85625
86165
|
const path = readStudioFileChangePath(payload);
|
|
@@ -85678,14 +86218,14 @@ function useExternalFileChangeCoordinator({
|
|
|
85678
86218
|
}
|
|
85679
86219
|
return sseFileChangeChannel(handler);
|
|
85680
86220
|
}, []);
|
|
85681
|
-
const retry =
|
|
86221
|
+
const retry = useCallback151(async () => {
|
|
85682
86222
|
const current = blockedRef.current;
|
|
85683
86223
|
if (!current || current.status === "conflict" || current.recovered) return;
|
|
85684
86224
|
resetSaveQueues?.();
|
|
85685
86225
|
lastEventIdentityRef.current = null;
|
|
85686
86226
|
processChange(current.payload);
|
|
85687
86227
|
}, [processChange, resetSaveQueues]);
|
|
85688
|
-
const useExternalFile =
|
|
86228
|
+
const useExternalFile = useCallback151(
|
|
85689
86229
|
// fallow-ignore-next-line complexity
|
|
85690
86230
|
async () => {
|
|
85691
86231
|
const current = blockedRef.current;
|
|
@@ -85713,7 +86253,7 @@ function useExternalFileChangeCoordinator({
|
|
|
85713
86253
|
resetSaveQueues
|
|
85714
86254
|
]
|
|
85715
86255
|
);
|
|
85716
|
-
const keepStudioFile =
|
|
86256
|
+
const keepStudioFile = useCallback151(async () => {
|
|
85717
86257
|
const current = blockedRef.current;
|
|
85718
86258
|
if (!current || !projectId) return;
|
|
85719
86259
|
if (current.generation !== generationRef.current) return;
|
|
@@ -85784,19 +86324,19 @@ function useStudioExternalFileChanges({
|
|
|
85784
86324
|
const { flushPendingSourceSave, discardPendingSourceSave } = fileManager;
|
|
85785
86325
|
const { drainPendingDomEditSaves, resetDomEditSaveQueueBreaker } = previewPersistence;
|
|
85786
86326
|
const bumpThumbnailRevisions = usePlayerStore((state) => state.bumpThumbnailRevisions);
|
|
85787
|
-
const onAcceptedPersistedFileChange =
|
|
86327
|
+
const onAcceptedPersistedFileChange = useCallback152(
|
|
85788
86328
|
(_path, affectedCompositions) => {
|
|
85789
86329
|
onOutsideChange?.();
|
|
85790
86330
|
bumpThumbnailRevisions(affectedCompositions);
|
|
85791
86331
|
},
|
|
85792
86332
|
[bumpThumbnailRevisions, onOutsideChange]
|
|
85793
86333
|
);
|
|
85794
|
-
const drainPendingChanges =
|
|
86334
|
+
const drainPendingChanges = useCallback152(async () => {
|
|
85795
86335
|
const source = await flushPendingSourceSave();
|
|
85796
86336
|
if (source.status !== "clean") return source;
|
|
85797
86337
|
return drainPendingDomEditSaves();
|
|
85798
86338
|
}, [drainPendingDomEditSaves, flushPendingSourceSave]);
|
|
85799
|
-
const discardPendingChanges =
|
|
86339
|
+
const discardPendingChanges = useCallback152(() => {
|
|
85800
86340
|
discardPendingSourceSave();
|
|
85801
86341
|
resetDomEditSaveQueueBreaker();
|
|
85802
86342
|
}, [discardPendingSourceSave, resetDomEditSaveQueueBreaker]);
|
|
@@ -85824,7 +86364,7 @@ function useStudioExternalFileChanges({
|
|
|
85824
86364
|
}
|
|
85825
86365
|
|
|
85826
86366
|
// src/hooks/useBlockHandlers.ts
|
|
85827
|
-
import { useCallback as
|
|
86367
|
+
import { useCallback as useCallback153, useMemo as useMemo75, useRef as useRef156, useState as useState123 } from "react";
|
|
85828
86368
|
|
|
85829
86369
|
// src/utils/blockInstaller.ts
|
|
85830
86370
|
function getMaxZIndexFromIframe(iframe) {
|
|
@@ -86043,7 +86583,7 @@ function useBlockHandlers({
|
|
|
86043
86583
|
);
|
|
86044
86584
|
const installingBlockRef = useRef156(false);
|
|
86045
86585
|
const { showToast, dismissToast } = blockCtxDeps;
|
|
86046
|
-
const runBlockInstall =
|
|
86586
|
+
const runBlockInstall = useCallback153(
|
|
86047
86587
|
async (blockName, install) => {
|
|
86048
86588
|
if (installingBlockRef.current) {
|
|
86049
86589
|
showToast("A block is already installing \u2014 one moment\u2026", "info");
|
|
@@ -86060,7 +86600,7 @@ function useBlockHandlers({
|
|
|
86060
86600
|
},
|
|
86061
86601
|
[showToast, dismissToast]
|
|
86062
86602
|
);
|
|
86063
|
-
const handleAddBlock =
|
|
86603
|
+
const handleAddBlock = useCallback153(
|
|
86064
86604
|
(blockName) => {
|
|
86065
86605
|
if (!projectId) return;
|
|
86066
86606
|
void (async () => {
|
|
@@ -86090,7 +86630,7 @@ function useBlockHandlers({
|
|
|
86090
86630
|
},
|
|
86091
86631
|
[projectId, blockCtx, previewIframeRef, runBlockInstall, setRightCollapsed, setRightPanelTab]
|
|
86092
86632
|
);
|
|
86093
|
-
const handleTimelineBlockDrop =
|
|
86633
|
+
const handleTimelineBlockDrop = useCallback153(
|
|
86094
86634
|
(blockName, placement) => {
|
|
86095
86635
|
if (!projectId) return;
|
|
86096
86636
|
void runBlockInstall(
|
|
@@ -86109,7 +86649,7 @@ function useBlockHandlers({
|
|
|
86109
86649
|
},
|
|
86110
86650
|
[projectId, blockCtx, previewIframeRef, runBlockInstall]
|
|
86111
86651
|
);
|
|
86112
|
-
const handleAddMediaOverlay =
|
|
86652
|
+
const handleAddMediaOverlay = useCallback153(
|
|
86113
86653
|
async (blockName, placement) => {
|
|
86114
86654
|
if (!projectId) return;
|
|
86115
86655
|
const { compositionPath, ...timelinePlacement } = placement;
|
|
@@ -86128,7 +86668,7 @@ function useBlockHandlers({
|
|
|
86128
86668
|
},
|
|
86129
86669
|
[projectId, blockCtx, previewIframeRef, runBlockInstall]
|
|
86130
86670
|
);
|
|
86131
|
-
const handlePreviewBlockDrop =
|
|
86671
|
+
const handlePreviewBlockDrop = useCallback153(
|
|
86132
86672
|
(blockName, position) => {
|
|
86133
86673
|
if (!projectId) return;
|
|
86134
86674
|
void runBlockInstall(
|
|
@@ -86158,7 +86698,7 @@ function useBlockHandlers({
|
|
|
86158
86698
|
}
|
|
86159
86699
|
|
|
86160
86700
|
// src/hooks/useAppHotkeys.ts
|
|
86161
|
-
import { useCallback as
|
|
86701
|
+
import { useCallback as useCallback155, useEffect as useEffect128, useRef as useRef157 } from "react";
|
|
86162
86702
|
|
|
86163
86703
|
// src/hooks/appHotkeysDispatch.ts
|
|
86164
86704
|
function handleUndoRedoKey(event, onUndo, onRedo) {
|
|
@@ -86355,7 +86895,7 @@ function dispatchPlainKey(event, key2, cb) {
|
|
|
86355
86895
|
}
|
|
86356
86896
|
|
|
86357
86897
|
// src/hooks/useEditHistoryActions.ts
|
|
86358
|
-
import { useCallback as
|
|
86898
|
+
import { useCallback as useCallback154, useMemo as useMemo76 } from "react";
|
|
86359
86899
|
function useEditHistoryActions({
|
|
86360
86900
|
editHistory,
|
|
86361
86901
|
readOptionalProjectFile,
|
|
@@ -86369,20 +86909,21 @@ function useEditHistoryActions({
|
|
|
86369
86909
|
activeCompPath,
|
|
86370
86910
|
forceReloadSdkSession
|
|
86371
86911
|
}) {
|
|
86372
|
-
const readHistoryFile =
|
|
86912
|
+
const readHistoryFile = useCallback154(
|
|
86373
86913
|
(path) => path === STUDIO_MOTION_PATH ? readOptionalProjectFile(path) : readProjectFile(path),
|
|
86374
86914
|
[readOptionalProjectFile, readProjectFile]
|
|
86375
86915
|
);
|
|
86376
|
-
const serializeHistoryFiles =
|
|
86916
|
+
const serializeHistoryFiles = useCallback154(
|
|
86377
86917
|
(paths, task) => serializeStudioFileMutations(writeProjectFile, paths, task),
|
|
86378
86918
|
[writeProjectFile]
|
|
86379
86919
|
);
|
|
86380
|
-
const apply =
|
|
86920
|
+
const apply = useCallback154(
|
|
86381
86921
|
async (direction) => {
|
|
86382
86922
|
const noun = direction === "undo" ? "Undo" : "Redo";
|
|
86383
86923
|
const pendingEditShown = direction === "undo" ? paintBackNewestStudioPendingEdit() : null;
|
|
86384
86924
|
const predicted = pendingEditShown ? null : editHistory.predict?.(direction) ?? null;
|
|
86385
86925
|
const predictedShown = predicted ? showHistoryRestoreNow?.(predicted.files) ?? null : null;
|
|
86926
|
+
const shownLanded = predictedShown ? beginStudioShownRestore() : null;
|
|
86386
86927
|
const putBack = predictedShown ?? pendingEditShown?.showAgain;
|
|
86387
86928
|
const claimedAfter = pendingEditShown?.claimsAtBegin ?? (direction === "undo" && hasStudioPendingEdits() ? editHistory.claims?.() : void 0);
|
|
86388
86929
|
let result = { ok: false, reason: "failed" };
|
|
@@ -86402,6 +86943,7 @@ function useEditHistoryActions({
|
|
|
86402
86943
|
serverSteppedShown = predictedShown ? stepped && result.undoes === predicted?.id : stepped && editClaimed;
|
|
86403
86944
|
} finally {
|
|
86404
86945
|
if (putBack && !serverSteppedShown && !revertIsTheUndo) putBack();
|
|
86946
|
+
shownLanded?.();
|
|
86405
86947
|
}
|
|
86406
86948
|
if (!result.ok && result.reason === "content-mismatch") {
|
|
86407
86949
|
showToast(
|
|
@@ -86438,8 +86980,8 @@ function useEditHistoryActions({
|
|
|
86438
86980
|
forceReloadSdkSession
|
|
86439
86981
|
]
|
|
86440
86982
|
);
|
|
86441
|
-
const undo =
|
|
86442
|
-
const redo =
|
|
86983
|
+
const undo = useCallback154(() => apply("undo"), [apply]);
|
|
86984
|
+
const redo = useCallback154(() => apply("redo"), [apply]);
|
|
86443
86985
|
return useMemo76(() => ({ undo, redo }), [undo, redo]);
|
|
86444
86986
|
}
|
|
86445
86987
|
function fromShown(files, shown2) {
|
|
@@ -86528,7 +87070,7 @@ function useAppHotkeys({
|
|
|
86528
87070
|
activeCompPath,
|
|
86529
87071
|
forceReloadSdkSession
|
|
86530
87072
|
});
|
|
86531
|
-
const applyHistory =
|
|
87073
|
+
const applyHistory = useCallback155(
|
|
86532
87074
|
async (direction) => {
|
|
86533
87075
|
const captionState = useCaptionStore.getState();
|
|
86534
87076
|
if (captionState.isEditMode && isCaptionPreviewVisible()) {
|
|
@@ -86544,8 +87086,8 @@ function useAppHotkeys({
|
|
|
86544
87086
|
},
|
|
86545
87087
|
[editHistory.state, fileHistory, showToast]
|
|
86546
87088
|
);
|
|
86547
|
-
const handleUndo =
|
|
86548
|
-
const handleRedo =
|
|
87089
|
+
const handleUndo = useCallback155(() => applyHistory("undo"), [applyHistory]);
|
|
87090
|
+
const handleRedo = useCallback155(() => applyHistory("redo"), [applyHistory]);
|
|
86549
87091
|
const cbRef = useRef157(null);
|
|
86550
87092
|
cbRef.current = {
|
|
86551
87093
|
handleTimelineElementsDelete,
|
|
@@ -86568,7 +87110,7 @@ function useAppHotkeys({
|
|
|
86568
87110
|
showToast,
|
|
86569
87111
|
readOnlyPreview
|
|
86570
87112
|
};
|
|
86571
|
-
const handleAppKeyDown =
|
|
87113
|
+
const handleAppKeyDown = useCallback155((event) => {
|
|
86572
87114
|
const cb = cbRef.current;
|
|
86573
87115
|
const key2 = event.key.toLowerCase();
|
|
86574
87116
|
if (dispatchLinkShortcut(event, cb)) return;
|
|
@@ -86582,7 +87124,7 @@ function useAppHotkeys({
|
|
|
86582
87124
|
window.addEventListener("keydown", handleAppKeyDown, true);
|
|
86583
87125
|
return () => window.removeEventListener("keydown", handleAppKeyDown, true);
|
|
86584
87126
|
}, [handleAppKeyDown]);
|
|
86585
|
-
const syncPreviewHotkeys =
|
|
87127
|
+
const syncPreviewHotkeys = useCallback155(
|
|
86586
87128
|
(iframe) => {
|
|
86587
87129
|
previewHistoryCleanupRef.current?.();
|
|
86588
87130
|
previewHistoryCleanupRef.current = null;
|
|
@@ -86612,7 +87154,7 @@ function useAppHotkeys({
|
|
|
86612
87154
|
}
|
|
86613
87155
|
|
|
86614
87156
|
// src/hooks/useClipboard.ts
|
|
86615
|
-
import { useCallback as
|
|
87157
|
+
import { useCallback as useCallback156, useRef as useRef158 } from "react";
|
|
86616
87158
|
import { EXCLUDED_TAGS, mintHfId, walkCompositionDescendants as walkCompositionDescendants2 } from "@hyperframes/parsers/hf-ids";
|
|
86617
87159
|
|
|
86618
87160
|
// src/utils/clipboardPayload.ts
|
|
@@ -86892,7 +87434,7 @@ function useClipboard({
|
|
|
86892
87434
|
const clipboardRef = useRef158(null);
|
|
86893
87435
|
const projectIdRef = useRef158(projectId);
|
|
86894
87436
|
projectIdRef.current = projectId;
|
|
86895
|
-
const readSaved =
|
|
87437
|
+
const readSaved = useCallback156(
|
|
86896
87438
|
async (path) => {
|
|
86897
87439
|
const pid = projectIdRef.current;
|
|
86898
87440
|
if (!pid) throw new Error("No project is open.");
|
|
@@ -86906,7 +87448,7 @@ function useClipboard({
|
|
|
86906
87448
|
},
|
|
86907
87449
|
[waitForPendingDomEditSaves, writeProjectFile]
|
|
86908
87450
|
);
|
|
86909
|
-
const findSelectedClips =
|
|
87451
|
+
const findSelectedClips = useCallback156(() => {
|
|
86910
87452
|
const selected = getSelectedElements();
|
|
86911
87453
|
if (selected.length === 0) return null;
|
|
86912
87454
|
const lives = [];
|
|
@@ -86920,7 +87462,7 @@ function useClipboard({
|
|
|
86920
87462
|
}
|
|
86921
87463
|
return { elements: selected, lives };
|
|
86922
87464
|
}, [activeCompPath, previewIframeRef, showToast]);
|
|
86923
|
-
const readClips =
|
|
87465
|
+
const readClips = useCallback156(
|
|
86924
87466
|
async (targets) => {
|
|
86925
87467
|
const paths = targets.elements.map((el) => el.sourceFile || activeCompPath || "index.html");
|
|
86926
87468
|
const markup = await readSavedMarkup(readSaved, paths, targets.lives);
|
|
@@ -86936,7 +87478,7 @@ function useClipboard({
|
|
|
86936
87478
|
},
|
|
86937
87479
|
[activeCompPath, readSaved]
|
|
86938
87480
|
);
|
|
86939
|
-
const copyTimelineSelection =
|
|
87481
|
+
const copyTimelineSelection = useCallback156(() => {
|
|
86940
87482
|
const targets = findSelectedClips();
|
|
86941
87483
|
if (!targets) return null;
|
|
86942
87484
|
const sourceFile = targets.elements[0]?.sourceFile || activeCompPath || "index.html";
|
|
@@ -86951,7 +87493,7 @@ function useClipboard({
|
|
|
86951
87493
|
};
|
|
86952
87494
|
});
|
|
86953
87495
|
}, [activeCompPath, findSelectedClips, readClips, showToast]);
|
|
86954
|
-
const copyDomSelection =
|
|
87496
|
+
const copyDomSelection = useCallback156(
|
|
86955
87497
|
(domSelection) => {
|
|
86956
87498
|
const live = getSelectedDomElement(previewIframeRef, domSelection, activeCompPath);
|
|
86957
87499
|
if (!live) {
|
|
@@ -86973,7 +87515,7 @@ function useClipboard({
|
|
|
86973
87515
|
},
|
|
86974
87516
|
[activeCompPath, previewIframeRef, readSaved, showToast]
|
|
86975
87517
|
);
|
|
86976
|
-
const copyToClipboard =
|
|
87518
|
+
const copyToClipboard = useCallback156(() => {
|
|
86977
87519
|
const domSelection = domEditSelectionRef.current;
|
|
86978
87520
|
let pending2;
|
|
86979
87521
|
if (usePlayerStore.getState().selectedElementId) pending2 = copyTimelineSelection();
|
|
@@ -86995,8 +87537,8 @@ function useClipboard({
|
|
|
86995
87537
|
});
|
|
86996
87538
|
return own;
|
|
86997
87539
|
}, [copyDomSelection, copyTimelineSelection, domEditSelectionRef, showToast]);
|
|
86998
|
-
const handleCopy2 =
|
|
86999
|
-
const handlePaste2 =
|
|
87540
|
+
const handleCopy2 = useCallback156(() => copyToClipboard() !== null, [copyToClipboard]);
|
|
87541
|
+
const handlePaste2 = useCallback156(
|
|
87000
87542
|
async (options) => {
|
|
87001
87543
|
const payload = await clipboardRef.current;
|
|
87002
87544
|
if (!payload) {
|
|
@@ -87044,7 +87586,7 @@ function useClipboard({
|
|
|
87044
87586
|
},
|
|
87045
87587
|
[activeCompPath, recordEdit, reloadPreview, showToast, writeProjectFile]
|
|
87046
87588
|
);
|
|
87047
|
-
const handleDuplicate =
|
|
87589
|
+
const handleDuplicate = useCallback156(
|
|
87048
87590
|
async (options) => {
|
|
87049
87591
|
const targets = findSelectedClips();
|
|
87050
87592
|
if (!targets) return false;
|
|
@@ -87096,7 +87638,7 @@ function useClipboard({
|
|
|
87096
87638
|
writeProjectFile
|
|
87097
87639
|
]
|
|
87098
87640
|
);
|
|
87099
|
-
const handleCut =
|
|
87641
|
+
const handleCut = useCallback156(async () => {
|
|
87100
87642
|
const selected = getSelectedElements();
|
|
87101
87643
|
const domSelection = domEditSelectionRef.current;
|
|
87102
87644
|
const copied = copyToClipboard();
|
|
@@ -87116,7 +87658,7 @@ function useClipboard({
|
|
|
87116
87658
|
handleTimelineElementsDelete,
|
|
87117
87659
|
handleDomEditElementDelete
|
|
87118
87660
|
]);
|
|
87119
|
-
const canPaste =
|
|
87661
|
+
const canPaste = useCallback156(() => clipboardRef.current !== null, []);
|
|
87120
87662
|
return { handleCopy: handleCopy2, handlePaste: handlePaste2, handleCut, handleDuplicate, canPaste };
|
|
87121
87663
|
}
|
|
87122
87664
|
|
|
@@ -87475,11 +88017,11 @@ function useCaptionDetection({
|
|
|
87475
88017
|
}
|
|
87476
88018
|
|
|
87477
88019
|
// src/hooks/useConsoleErrorCapture.ts
|
|
87478
|
-
import { useCallback as
|
|
88020
|
+
import { useCallback as useCallback157, useEffect as useEffect130, useRef as useRef160, useState as useState124 } from "react";
|
|
87479
88021
|
function useConsoleErrorCapture(previewIframe) {
|
|
87480
88022
|
const [consoleErrors, setConsoleErrors] = useState124(null);
|
|
87481
88023
|
const consoleErrorsRef = useRef160([]);
|
|
87482
|
-
const resetErrors =
|
|
88024
|
+
const resetErrors = useCallback157(() => {
|
|
87483
88025
|
consoleErrorsRef.current = [];
|
|
87484
88026
|
setConsoleErrors(null);
|
|
87485
88027
|
}, []);
|
|
@@ -87548,7 +88090,7 @@ function useConsoleErrorCapture(previewIframe) {
|
|
|
87548
88090
|
}
|
|
87549
88091
|
|
|
87550
88092
|
// src/hooks/useFrameCapture.ts
|
|
87551
|
-
import { useMemo as useMemo77, useState as useState125, useCallback as
|
|
88093
|
+
import { useMemo as useMemo77, useState as useState125, useCallback as useCallback158, useRef as useRef161 } from "react";
|
|
87552
88094
|
function useFrameCapture({
|
|
87553
88095
|
projectId,
|
|
87554
88096
|
activeCompPath,
|
|
@@ -87566,16 +88108,16 @@ function useFrameCapture({
|
|
|
87566
88108
|
livePlayheadRef.current = time;
|
|
87567
88109
|
})
|
|
87568
88110
|
);
|
|
87569
|
-
const playheadTime =
|
|
88111
|
+
const playheadTime = useCallback158(() => {
|
|
87570
88112
|
const { isPlaying, currentTime } = usePlayerStore.getState();
|
|
87571
88113
|
return isPlaying ? livePlayheadRef.current : currentTime;
|
|
87572
88114
|
}, []);
|
|
87573
88115
|
const [captureStamp, setCaptureStamp] = useState125(Date.now);
|
|
87574
|
-
const refreshCaptureFrameTime =
|
|
88116
|
+
const refreshCaptureFrameTime = useCallback158(() => {
|
|
87575
88117
|
setCaptureFrameTime(playheadTime());
|
|
87576
88118
|
setCaptureStamp(Date.now());
|
|
87577
88119
|
}, [playheadTime]);
|
|
87578
|
-
const handleCaptureFrameClick =
|
|
88120
|
+
const handleCaptureFrameClick = useCallback158(
|
|
87579
88121
|
async (event) => {
|
|
87580
88122
|
if (!projectId) return;
|
|
87581
88123
|
event.preventDefault();
|
|
@@ -87659,7 +88201,7 @@ function useFrameCapture({
|
|
|
87659
88201
|
}
|
|
87660
88202
|
|
|
87661
88203
|
// src/hooks/useLintModal.ts
|
|
87662
|
-
import { useState as useState126, useCallback as
|
|
88204
|
+
import { useState as useState126, useCallback as useCallback159, useEffect as useEffect131, useRef as useRef162, useMemo as useMemo78 } from "react";
|
|
87663
88205
|
function parseFinding(f) {
|
|
87664
88206
|
return {
|
|
87665
88207
|
severity: f.severity === "error" ? "error" : "warning",
|
|
@@ -87679,7 +88221,7 @@ function useLintModal(projectId, refreshKey) {
|
|
|
87679
88221
|
const [linting, setLinting] = useState126(false);
|
|
87680
88222
|
const [backgroundFindings, setBackgroundFindings] = useState126([]);
|
|
87681
88223
|
const autoLintRanRef = useRef162(false);
|
|
87682
|
-
const runBackgroundLint =
|
|
88224
|
+
const runBackgroundLint = useCallback159(async () => {
|
|
87683
88225
|
if (!projectId) return;
|
|
87684
88226
|
if (!isPreviewBooted(projectId) && !await whenPreviewBooted(projectId)) return;
|
|
87685
88227
|
try {
|
|
@@ -87687,7 +88229,7 @@ function useLintModal(projectId, refreshKey) {
|
|
|
87687
88229
|
} catch {
|
|
87688
88230
|
}
|
|
87689
88231
|
}, [projectId]);
|
|
87690
|
-
const handleLint =
|
|
88232
|
+
const handleLint = useCallback159(async () => {
|
|
87691
88233
|
if (!projectId) return;
|
|
87692
88234
|
setLinting(true);
|
|
87693
88235
|
try {
|
|
@@ -87716,8 +88258,8 @@ function useLintModal(projectId, refreshKey) {
|
|
|
87716
88258
|
const timer = setTimeout(() => void runBackgroundLint(), 1e3);
|
|
87717
88259
|
return () => clearTimeout(timer);
|
|
87718
88260
|
}, [projectId, refreshKey, runBackgroundLint]);
|
|
87719
|
-
const closeLintModal =
|
|
87720
|
-
const groupFindings =
|
|
88261
|
+
const closeLintModal = useCallback159(() => setLintModal(null), []);
|
|
88262
|
+
const groupFindings = useCallback159(
|
|
87721
88263
|
(keyFn) => {
|
|
87722
88264
|
const map = /* @__PURE__ */ new Map();
|
|
87723
88265
|
for (const f of backgroundFindings) {
|
|
@@ -87754,7 +88296,7 @@ function useLintModal(projectId, refreshKey) {
|
|
|
87754
88296
|
}
|
|
87755
88297
|
|
|
87756
88298
|
// src/hooks/useToast.ts
|
|
87757
|
-
import { useState as useState127, useCallback as
|
|
88299
|
+
import { useState as useState127, useCallback as useCallback160, useRef as useRef163 } from "react";
|
|
87758
88300
|
var AUTO_DISMISS_MS2 = 4e3;
|
|
87759
88301
|
var EXIT_MS2 = 160;
|
|
87760
88302
|
var MAX_TOASTS = 3;
|
|
@@ -87762,21 +88304,21 @@ var nextToastId = 1;
|
|
|
87762
88304
|
function useToast() {
|
|
87763
88305
|
const [toasts, setToasts] = useState127([]);
|
|
87764
88306
|
const timersRef = useRef163(/* @__PURE__ */ new Map());
|
|
87765
|
-
const clearTimer =
|
|
88307
|
+
const clearTimer = useCallback160((id) => {
|
|
87766
88308
|
const timer = timersRef.current.get(id);
|
|
87767
88309
|
if (timer) {
|
|
87768
88310
|
clearTimeout(timer);
|
|
87769
88311
|
timersRef.current.delete(id);
|
|
87770
88312
|
}
|
|
87771
88313
|
}, []);
|
|
87772
|
-
const removeToast =
|
|
88314
|
+
const removeToast = useCallback160(
|
|
87773
88315
|
(id) => {
|
|
87774
88316
|
clearTimer(id);
|
|
87775
88317
|
setToasts((prev) => prev.filter((t2) => t2.id !== id));
|
|
87776
88318
|
},
|
|
87777
88319
|
[clearTimer]
|
|
87778
88320
|
);
|
|
87779
|
-
const dismissToast =
|
|
88321
|
+
const dismissToast = useCallback160(
|
|
87780
88322
|
(id) => {
|
|
87781
88323
|
clearTimer(id);
|
|
87782
88324
|
setToasts((prev) => prev.map((t2) => t2.id === id ? { ...t2, leaving: true } : t2));
|
|
@@ -87785,7 +88327,7 @@ function useToast() {
|
|
|
87785
88327
|
},
|
|
87786
88328
|
[clearTimer, removeToast]
|
|
87787
88329
|
);
|
|
87788
|
-
const showToast =
|
|
88330
|
+
const showToast = useCallback160(
|
|
87789
88331
|
(message, tone = "error") => {
|
|
87790
88332
|
const id = nextToastId++;
|
|
87791
88333
|
setToasts((prev) => {
|
|
@@ -87812,7 +88354,7 @@ function useToast() {
|
|
|
87812
88354
|
}
|
|
87813
88355
|
|
|
87814
88356
|
// src/hooks/useStudioUrlState.ts
|
|
87815
|
-
import { useCallback as
|
|
88357
|
+
import { useCallback as useCallback161, useEffect as useEffect132, useRef as useRef164, useState as useState128 } from "react";
|
|
87816
88358
|
|
|
87817
88359
|
// src/utils/studioUrlState.ts
|
|
87818
88360
|
var VALID_TABS = ["layers", "design", "renders", "slideshow", "variables"];
|
|
@@ -88051,7 +88593,7 @@ function useStudioUrlState({
|
|
|
88051
88593
|
const pendingSelectionRef = useRef164(initialState2.selection);
|
|
88052
88594
|
const stableTimeRef = useRef164(initialState2.currentTime);
|
|
88053
88595
|
const selectionApplySeqRef = useRef164(0);
|
|
88054
|
-
const buildUrlState =
|
|
88596
|
+
const buildUrlState = useCallback161(
|
|
88055
88597
|
() => ({
|
|
88056
88598
|
activeCompPath,
|
|
88057
88599
|
currentTime: stableTimeRef.current,
|
|
@@ -88062,7 +88604,7 @@ function useStudioUrlState({
|
|
|
88062
88604
|
}),
|
|
88063
88605
|
[activeCompPath, domEditGroupSelections, domEditSelection, rightCollapsed, rightPanelTab]
|
|
88064
88606
|
);
|
|
88065
|
-
const applyUrlSelection =
|
|
88607
|
+
const applyUrlSelection = useCallback161(
|
|
88066
88608
|
(selection) => {
|
|
88067
88609
|
const applySeq = ++selectionApplySeqRef.current;
|
|
88068
88610
|
if (!selection) {
|
|
@@ -88207,7 +88749,7 @@ function useEffectiveTimelineDuration(timelineDuration2, timelineElements) {
|
|
|
88207
88749
|
}
|
|
88208
88750
|
|
|
88209
88751
|
// src/hooks/useStudioContextValue.ts
|
|
88210
|
-
import { useCallback as
|
|
88752
|
+
import { useCallback as useCallback162, useMemo as useMemo80 } from "react";
|
|
88211
88753
|
function buildStudioContextValue(input) {
|
|
88212
88754
|
return {
|
|
88213
88755
|
projectId: input.projectId,
|
|
@@ -88252,11 +88794,11 @@ function useInspectorState(rightPanel, isPlaying, domEditSelection, isGestureRec
|
|
|
88252
88794
|
}, [rightPanel, isPlaying, isGestureRecording, domEditSelection]);
|
|
88253
88795
|
}
|
|
88254
88796
|
function useFileDropTarget(onImportFiles) {
|
|
88255
|
-
const onDragOver =
|
|
88797
|
+
const onDragOver = useCallback162((e) => {
|
|
88256
88798
|
if (!e.dataTransfer.types.includes("Files")) return;
|
|
88257
88799
|
e.preventDefault();
|
|
88258
88800
|
}, []);
|
|
88259
|
-
const onDrop =
|
|
88801
|
+
const onDrop = useCallback162(
|
|
88260
88802
|
(e) => {
|
|
88261
88803
|
if (e.defaultPrevented) return;
|
|
88262
88804
|
e.preventDefault();
|
|
@@ -88267,7 +88809,7 @@ function useFileDropTarget(onImportFiles) {
|
|
|
88267
88809
|
return { onDragOver, onDrop };
|
|
88268
88810
|
}
|
|
88269
88811
|
function useGlobalFileDrop(handleTimelineFileDrop) {
|
|
88270
|
-
const onDrop =
|
|
88812
|
+
const onDrop = useCallback162(
|
|
88271
88813
|
(files) => {
|
|
88272
88814
|
const start = usePlayerStore.getState().currentTime;
|
|
88273
88815
|
void handleTimelineFileDrop(Array.from(files), { start, track: 0 });
|
|
@@ -88754,10 +89296,10 @@ var StudioHeader = memo44(function StudioHeader2({
|
|
|
88754
89296
|
});
|
|
88755
89297
|
|
|
88756
89298
|
// src/hooks/useGestureCommit.ts
|
|
88757
|
-
import { useState as useState131, useCallback as
|
|
89299
|
+
import { useState as useState131, useCallback as useCallback164, useRef as useRef167, useEffect as useEffect135 } from "react";
|
|
88758
89300
|
|
|
88759
89301
|
// src/hooks/useGestureRecording.ts
|
|
88760
|
-
import { useCallback as
|
|
89302
|
+
import { useCallback as useCallback163, useEffect as useEffect134, useRef as useRef166, useState as useState130 } from "react";
|
|
88761
89303
|
function readBasePosition(element, iframeEl) {
|
|
88762
89304
|
let baseOpacity = 1;
|
|
88763
89305
|
let baseScale = 1;
|
|
@@ -88914,7 +89456,7 @@ function useGestureRecording() {
|
|
|
88914
89456
|
r.cleanup = null;
|
|
88915
89457
|
};
|
|
88916
89458
|
}, []);
|
|
88917
|
-
const startRecording =
|
|
89459
|
+
const startRecording = useCallback163(
|
|
88918
89460
|
(element, iframeEl, elementEndTime) => {
|
|
88919
89461
|
if (isRecordingRef.current) return;
|
|
88920
89462
|
isRecordingRef.current = true;
|
|
@@ -89013,7 +89555,7 @@ function useGestureRecording() {
|
|
|
89013
89555
|
[]
|
|
89014
89556
|
// No deps — uses refs only for all mutable state
|
|
89015
89557
|
);
|
|
89016
|
-
const stopRecording =
|
|
89558
|
+
const stopRecording = useCallback163(() => {
|
|
89017
89559
|
if (!isRecordingRef.current) return [];
|
|
89018
89560
|
isRecordingRef.current = false;
|
|
89019
89561
|
const r = refs.current;
|
|
@@ -89025,7 +89567,7 @@ function useGestureRecording() {
|
|
|
89025
89567
|
setIsRecording(false);
|
|
89026
89568
|
return frozen;
|
|
89027
89569
|
}, []);
|
|
89028
|
-
const clearSamples =
|
|
89570
|
+
const clearSamples = useCallback163(() => {
|
|
89029
89571
|
const r = refs.current;
|
|
89030
89572
|
r.samples = [];
|
|
89031
89573
|
r.trail = [];
|
|
@@ -89297,7 +89839,7 @@ function useGestureCommit({
|
|
|
89297
89839
|
const capturedSelectionRef = useRef167(null);
|
|
89298
89840
|
const capturedAnimationsRef = useRef167([]);
|
|
89299
89841
|
useEffect135(() => () => clearInterval(recordingAutoStopRef.current), []);
|
|
89300
|
-
const cancelRecording =
|
|
89842
|
+
const cancelRecording = useCallback164(() => {
|
|
89301
89843
|
clearInterval(recordingAutoStopRef.current);
|
|
89302
89844
|
gestureRecording.stopRecording();
|
|
89303
89845
|
gestureRecording.clearSamples();
|
|
@@ -89309,7 +89851,7 @@ function useGestureCommit({
|
|
|
89309
89851
|
useEffect135(() => {
|
|
89310
89852
|
if (readOnlyPreview && gestureStateRef.current === "recording") cancelRecording();
|
|
89311
89853
|
}, [cancelRecording, readOnlyPreview]);
|
|
89312
|
-
const stopAndCommitRecording =
|
|
89854
|
+
const stopAndCommitRecording = useCallback164(async () => {
|
|
89313
89855
|
clearInterval(recordingAutoStopRef.current);
|
|
89314
89856
|
if (commitInFlightRef.current) {
|
|
89315
89857
|
return;
|
|
@@ -89403,19 +89945,28 @@ function useGestureCommit({
|
|
|
89403
89945
|
const overlaps3 = recStart < tweenEnd + 0.05 && recEnd > tweenStart - 0.05;
|
|
89404
89946
|
if (overlaps3) {
|
|
89405
89947
|
const existingKfs = existingPositionTween.keyframes?.keyframes ?? [];
|
|
89406
|
-
const
|
|
89407
|
-
const
|
|
89408
|
-
const
|
|
89409
|
-
|
|
89410
|
-
|
|
89948
|
+
const startTimePct = tweenDur > 0 ? Math.max(0, (recStart - tweenStart) / tweenDur * 100) : 0;
|
|
89949
|
+
const endTimePct = tweenDur > 0 ? Math.min(100, (recEnd - tweenStart) / tweenDur * 100) : 100;
|
|
89950
|
+
const runEase = runEaseOf(existingPositionTween);
|
|
89951
|
+
const roundPct3 = warpsTime(runEase) ? (pct) => pct : roundTo3;
|
|
89952
|
+
const preserved = existingKfs.filter((kf) => {
|
|
89953
|
+
const playsAt = timeAtProgress(runEase, kf.percentage);
|
|
89954
|
+
return playsAt < startTimePct - 0.5 || playsAt > endTimePct + 0.5;
|
|
89955
|
+
}).map((kf) => ({
|
|
89411
89956
|
percentage: kf.percentage,
|
|
89412
89957
|
properties: kf.properties,
|
|
89413
89958
|
...kf.ease ? { ease: kf.ease } : {}
|
|
89414
89959
|
}));
|
|
89415
|
-
const
|
|
89416
|
-
|
|
89960
|
+
const constantSpeed = { ease: "none" };
|
|
89961
|
+
const mapped = keyframes.map((kf, index) => ({
|
|
89962
|
+
percentage: roundPct3(
|
|
89963
|
+
progressAtTime(
|
|
89964
|
+
runEase,
|
|
89965
|
+
startTimePct + kf.percentage / 100 * (endTimePct - startTimePct)
|
|
89966
|
+
)
|
|
89967
|
+
),
|
|
89417
89968
|
properties: kf.properties,
|
|
89418
|
-
...kf.ease ? { ease: kf.ease } : {}
|
|
89969
|
+
...kf.ease ? { ease: kf.ease } : index > 0 ? constantSpeed : {}
|
|
89419
89970
|
}));
|
|
89420
89971
|
const merged = [...preserved, ...mapped].sort((a, b) => a.percentage - b.percentage);
|
|
89421
89972
|
await commit2(
|
|
@@ -89425,7 +89976,8 @@ function useGestureCommit({
|
|
|
89425
89976
|
targetSelector: selector,
|
|
89426
89977
|
position: typeof existingPositionTween.position === "number" ? existingPositionTween.position : tweenStart,
|
|
89427
89978
|
duration: tweenDur,
|
|
89428
|
-
keyframes: merged
|
|
89979
|
+
keyframes: merged,
|
|
89980
|
+
...keyframeEases(existingPositionTween)
|
|
89429
89981
|
},
|
|
89430
89982
|
{ label: "Gesture recording (merge)", softReload: true, keyframeAction: "add" }
|
|
89431
89983
|
);
|
|
@@ -89488,7 +90040,7 @@ function useGestureCommit({
|
|
|
89488
90040
|
commitInFlightRef.current = false;
|
|
89489
90041
|
}
|
|
89490
90042
|
}, [gestureRecording, showToast, isGestureRecordingRef, domEditSessionRef]);
|
|
89491
|
-
const armAutoStop =
|
|
90043
|
+
const armAutoStop = useCallback164(
|
|
89492
90044
|
(elementEnd) => {
|
|
89493
90045
|
clearInterval(recordingAutoStopRef.current);
|
|
89494
90046
|
const autoStopAt = elementEnd ?? Infinity;
|
|
@@ -89502,7 +90054,7 @@ function useGestureCommit({
|
|
|
89502
90054
|
},
|
|
89503
90055
|
[stopAndCommitRecording]
|
|
89504
90056
|
);
|
|
89505
|
-
const startRecording =
|
|
90057
|
+
const startRecording = useCallback164(
|
|
89506
90058
|
(method) => {
|
|
89507
90059
|
if (readOnlyPreview) return;
|
|
89508
90060
|
const sel = domEditSessionRef.current.domEditSelection;
|
|
@@ -89537,7 +90089,7 @@ function useGestureCommit({
|
|
|
89537
90089
|
armAutoStop
|
|
89538
90090
|
]
|
|
89539
90091
|
);
|
|
89540
|
-
const handleToggleRecording =
|
|
90092
|
+
const handleToggleRecording = useCallback164(
|
|
89541
90093
|
(method = "button") => {
|
|
89542
90094
|
if (commitInFlightRef.current) return;
|
|
89543
90095
|
if (gestureStateRef.current === "recording") {
|
|
@@ -89699,7 +90251,7 @@ function useGestureTrailOverlay({
|
|
|
89699
90251
|
import { useMemo as useMemo88 } from "react";
|
|
89700
90252
|
|
|
89701
90253
|
// src/components/StudioLeftPanels.tsx
|
|
89702
|
-
import { memo as memo49, useCallback as
|
|
90254
|
+
import { memo as memo49, useCallback as useCallback172 } from "react";
|
|
89703
90255
|
|
|
89704
90256
|
// src/components/MediaPreview.tsx
|
|
89705
90257
|
import { useState as useState132 } from "react";
|
|
@@ -89818,7 +90370,7 @@ function MediaPreview({ projectId, filePath }) {
|
|
|
89818
90370
|
}
|
|
89819
90371
|
|
|
89820
90372
|
// src/components/sidebar/AssetsTab.tsx
|
|
89821
|
-
import { memo as memo46, useState as useState138, useCallback as
|
|
90373
|
+
import { memo as memo46, useState as useState138, useCallback as useCallback168, useRef as useRef172, useMemo as useMemo84, useEffect as useEffect141 } from "react";
|
|
89822
90374
|
|
|
89823
90375
|
// src/components/ui/SearchInput.tsx
|
|
89824
90376
|
import { jsx as jsx210, jsxs as jsxs167 } from "react/jsx-runtime";
|
|
@@ -89929,11 +90481,11 @@ var CATEGORY_LABELS = {
|
|
|
89929
90481
|
var FILTER_ORDER = ["audio", "images", "video", "fonts"];
|
|
89930
90482
|
|
|
89931
90483
|
// src/components/sidebar/AudioRow.tsx
|
|
89932
|
-
import { useState as useState134, useRef as useRef170, useEffect as useEffect137, useCallback as
|
|
90484
|
+
import { useState as useState134, useRef as useRef170, useEffect as useEffect137, useCallback as useCallback166 } from "react";
|
|
89933
90485
|
import { classifyWebAudioMediaRoute } from "@hyperframes/core/runtime/web-audio-route";
|
|
89934
90486
|
|
|
89935
90487
|
// src/components/sidebar/AssetContextMenu.tsx
|
|
89936
|
-
import { useCallback as
|
|
90488
|
+
import { useCallback as useCallback165, useEffect as useEffect136, useLayoutEffect as useLayoutEffect14, useRef as useRef169, useState as useState133 } from "react";
|
|
89937
90489
|
import { Fragment as Fragment59, jsx as jsx211, jsxs as jsxs168 } from "react/jsx-runtime";
|
|
89938
90490
|
function isValidAssetName(name) {
|
|
89939
90491
|
return name.length > 0 && !/[/\\]/.test(name) && !name.includes("..");
|
|
@@ -89993,7 +90545,7 @@ function ContextMenu3({
|
|
|
89993
90545
|
menuRef.current?.querySelector('[role="menuitem"]')?.focus();
|
|
89994
90546
|
}
|
|
89995
90547
|
}, [mode]);
|
|
89996
|
-
const commitRename =
|
|
90548
|
+
const commitRename = useCallback165(() => {
|
|
89997
90549
|
const trimmed = renameDraft.trim();
|
|
89998
90550
|
if (trimmed === filename(asset)) {
|
|
89999
90551
|
onClose();
|
|
@@ -90209,7 +90761,7 @@ function AudioRow({
|
|
|
90209
90761
|
const serveUrl = resolveMediaPreviewUrl(asset, projectId);
|
|
90210
90762
|
const isCopied = copyFeedback?.path === asset && copyFeedback.ok;
|
|
90211
90763
|
const copyFailed = copyFeedback?.path === asset && !copyFeedback.ok;
|
|
90212
|
-
const stopPlayback =
|
|
90764
|
+
const stopPlayback = useCallback166(() => {
|
|
90213
90765
|
audioRef.current?.pause();
|
|
90214
90766
|
setPlaying(false);
|
|
90215
90767
|
cancelAnimationFrame(animRef.current);
|
|
@@ -90220,7 +90772,7 @@ function AudioRow({
|
|
|
90220
90772
|
const elements = usePlayerStore((s) => s.elements);
|
|
90221
90773
|
const setPreviewAsset = useAssetPreviewStore((s) => s.setPreviewAsset);
|
|
90222
90774
|
const clearPreviewAsset = useAssetPreviewStore((s) => s.clearPreviewAsset);
|
|
90223
|
-
const activateRow =
|
|
90775
|
+
const activateRow = useCallback166(() => {
|
|
90224
90776
|
if (used) {
|
|
90225
90777
|
const clip = findClipForAsset(elements, asset);
|
|
90226
90778
|
if (clip) {
|
|
@@ -90242,10 +90794,10 @@ function AudioRow({
|
|
|
90242
90794
|
setPreviewAsset,
|
|
90243
90795
|
clearPreviewAsset
|
|
90244
90796
|
]);
|
|
90245
|
-
const handlePointerDown =
|
|
90797
|
+
const handlePointerDown = useCallback166((e) => {
|
|
90246
90798
|
pointerDownRef.current = { x: e.clientX, y: e.clientY };
|
|
90247
90799
|
}, []);
|
|
90248
|
-
const handlePointerUp =
|
|
90800
|
+
const handlePointerUp = useCallback166(
|
|
90249
90801
|
(e) => {
|
|
90250
90802
|
const origin2 = pointerDownRef.current;
|
|
90251
90803
|
pointerDownRef.current = null;
|
|
@@ -90291,7 +90843,7 @@ function AudioRow({
|
|
|
90291
90843
|
}
|
|
90292
90844
|
return () => cancelAnimationFrame(animRef.current);
|
|
90293
90845
|
}, [playing]);
|
|
90294
|
-
const togglePlay =
|
|
90846
|
+
const togglePlay = useCallback166(async () => {
|
|
90295
90847
|
if (playing) {
|
|
90296
90848
|
stopPlayback();
|
|
90297
90849
|
if (stopCurrentPreview === stopPlayback) stopCurrentPreview = null;
|
|
@@ -90489,7 +91041,7 @@ function GlobalAssetsView({ searchQuery }) {
|
|
|
90489
91041
|
}
|
|
90490
91042
|
|
|
90491
91043
|
// src/components/sidebar/AssetCard.tsx
|
|
90492
|
-
import { useState as useState137, useEffect as useEffect140, useRef as useRef171, useCallback as
|
|
91044
|
+
import { useState as useState137, useEffect as useEffect140, useRef as useRef171, useCallback as useCallback167 } from "react";
|
|
90493
91045
|
|
|
90494
91046
|
// src/components/ui/VideoFrameThumbnail.tsx
|
|
90495
91047
|
import { useState as useState136, useEffect as useEffect139 } from "react";
|
|
@@ -90636,10 +91188,10 @@ function AssetCard({
|
|
|
90636
91188
|
const elements = usePlayerStore((s) => s.elements);
|
|
90637
91189
|
const setPreviewAsset = useAssetPreviewStore((s) => s.setPreviewAsset);
|
|
90638
91190
|
const clearPreviewAsset = useAssetPreviewStore((s) => s.clearPreviewAsset);
|
|
90639
|
-
const handlePointerDown =
|
|
91191
|
+
const handlePointerDown = useCallback167((e) => {
|
|
90640
91192
|
pointerDownRef.current = { x: e.clientX, y: e.clientY };
|
|
90641
91193
|
}, []);
|
|
90642
|
-
const activateCard =
|
|
91194
|
+
const activateCard = useCallback167(() => {
|
|
90643
91195
|
if (used) {
|
|
90644
91196
|
const clip = findClipForAsset(elements, asset);
|
|
90645
91197
|
if (clip) {
|
|
@@ -90661,7 +91213,7 @@ function AssetCard({
|
|
|
90661
91213
|
setPreviewAsset,
|
|
90662
91214
|
clearPreviewAsset
|
|
90663
91215
|
]);
|
|
90664
|
-
const handlePointerUp =
|
|
91216
|
+
const handlePointerUp = useCallback167(
|
|
90665
91217
|
(e) => {
|
|
90666
91218
|
const origin2 = pointerDownRef.current;
|
|
90667
91219
|
pointerDownRef.current = null;
|
|
@@ -90993,7 +91545,7 @@ var AssetsTab = memo46(function AssetsTab2({
|
|
|
90993
91545
|
cancelled = true;
|
|
90994
91546
|
};
|
|
90995
91547
|
}, [projectId, assetsKey]);
|
|
90996
|
-
const handleImport =
|
|
91548
|
+
const handleImport = useCallback168(
|
|
90997
91549
|
async (files) => {
|
|
90998
91550
|
if (!onImport) return;
|
|
90999
91551
|
setImporting(true);
|
|
@@ -91005,7 +91557,7 @@ var AssetsTab = memo46(function AssetsTab2({
|
|
|
91005
91557
|
},
|
|
91006
91558
|
[onImport]
|
|
91007
91559
|
);
|
|
91008
|
-
const handleDrop =
|
|
91560
|
+
const handleDrop = useCallback168(
|
|
91009
91561
|
(e) => {
|
|
91010
91562
|
e.preventDefault();
|
|
91011
91563
|
setDragOver(false);
|
|
@@ -91013,7 +91565,7 @@ var AssetsTab = memo46(function AssetsTab2({
|
|
|
91013
91565
|
},
|
|
91014
91566
|
[handleImport]
|
|
91015
91567
|
);
|
|
91016
|
-
const handleCopyPath =
|
|
91568
|
+
const handleCopyPath = useCallback168(async (path) => {
|
|
91017
91569
|
const copied = await copyTextToClipboard(path);
|
|
91018
91570
|
setCopyFeedback({ path, ok: copied });
|
|
91019
91571
|
setTimeout(() => setCopyFeedback(null), copied ? 1500 : 3e3);
|
|
@@ -91223,11 +91775,11 @@ var AssetsTab = memo46(function AssetsTab2({
|
|
|
91223
91775
|
});
|
|
91224
91776
|
|
|
91225
91777
|
// src/components/sidebar/BlocksTab.tsx
|
|
91226
|
-
import { memo as memo47, useState as useState140, useCallback as
|
|
91778
|
+
import { memo as memo47, useState as useState140, useCallback as useCallback170, useRef as useRef174, useEffect as useEffect143 } from "react";
|
|
91227
91779
|
import { createPortal as createPortal13 } from "react-dom";
|
|
91228
91780
|
|
|
91229
91781
|
// src/components/sidebar/PromptPreviewModal.tsx
|
|
91230
|
-
import { useState as useState139, useCallback as
|
|
91782
|
+
import { useState as useState139, useCallback as useCallback169, useEffect as useEffect142, useRef as useRef173 } from "react";
|
|
91231
91783
|
import { jsx as jsx217, jsxs as jsxs173 } from "react/jsx-runtime";
|
|
91232
91784
|
function PromptPreviewModal({
|
|
91233
91785
|
title,
|
|
@@ -91253,7 +91805,7 @@ function PromptPreviewModal({
|
|
|
91253
91805
|
textareaRef.current?.focus();
|
|
91254
91806
|
});
|
|
91255
91807
|
}, []);
|
|
91256
|
-
const handleCopy2 =
|
|
91808
|
+
const handleCopy2 = useCallback169(async () => {
|
|
91257
91809
|
try {
|
|
91258
91810
|
await navigator.clipboard.writeText(valueRef.current);
|
|
91259
91811
|
setCopyState("copied");
|
|
@@ -91539,13 +92091,13 @@ function BlockCard({
|
|
|
91539
92091
|
const hoverTimer = useRef174(null);
|
|
91540
92092
|
const colors = getCategoryColors(category);
|
|
91541
92093
|
const needsWebGL = tags?.includes("html-in-canvas") || tags?.includes("webgl");
|
|
91542
|
-
const handleEnter =
|
|
92094
|
+
const handleEnter = useCallback170(() => {
|
|
91543
92095
|
hoverTimer.current = setTimeout(() => {
|
|
91544
92096
|
setHovered(true);
|
|
91545
92097
|
onPreview?.({ videoUrl, posterUrl, title });
|
|
91546
92098
|
}, 300);
|
|
91547
92099
|
}, [onPreview, videoUrl, posterUrl, title]);
|
|
91548
|
-
const handleLeave =
|
|
92100
|
+
const handleLeave = useCallback170(() => {
|
|
91549
92101
|
if (hoverTimer.current) {
|
|
91550
92102
|
clearTimeout(hoverTimer.current);
|
|
91551
92103
|
hoverTimer.current = null;
|
|
@@ -91558,7 +92110,7 @@ function BlockCard({
|
|
|
91558
92110
|
if (hoverTimer.current) clearTimeout(hoverTimer.current);
|
|
91559
92111
|
};
|
|
91560
92112
|
}, []);
|
|
91561
|
-
const handleAdd =
|
|
92113
|
+
const handleAdd = useCallback170(
|
|
91562
92114
|
async (e) => {
|
|
91563
92115
|
e.stopPropagation();
|
|
91564
92116
|
if (addState !== "idle" || !onAdd) return;
|
|
@@ -91574,7 +92126,7 @@ function BlockCard({
|
|
|
91574
92126
|
[onAdd, addState]
|
|
91575
92127
|
);
|
|
91576
92128
|
const { activeCompPath, compositionDimensions } = useStudioShellContext();
|
|
91577
|
-
const handleShowPrompt =
|
|
92129
|
+
const handleShowPrompt = useCallback170(
|
|
91578
92130
|
(e) => {
|
|
91579
92131
|
e.stopPropagation();
|
|
91580
92132
|
const state = usePlayerStore.getState();
|
|
@@ -91714,7 +92266,7 @@ function BlockCard({
|
|
|
91714
92266
|
}
|
|
91715
92267
|
|
|
91716
92268
|
// src/components/sidebar/CompositionsTab.tsx
|
|
91717
|
-
import { memo as memo48, useCallback as
|
|
92269
|
+
import { memo as memo48, useCallback as useCallback171, useEffect as useEffect144, useLayoutEffect as useLayoutEffect15, useMemo as useMemo85, useRef as useRef175, useState as useState141 } from "react";
|
|
91718
92270
|
import { jsx as jsx219, jsxs as jsxs175 } from "react/jsx-runtime";
|
|
91719
92271
|
var DEFAULT_PREVIEW_STAGE = { width: 1920, height: 1080 };
|
|
91720
92272
|
var CARD_W = 80;
|
|
@@ -91825,7 +92377,7 @@ function CompCard({
|
|
|
91825
92377
|
const hoverTimer = useRef175(null);
|
|
91826
92378
|
const syncTimer = useRef175(null);
|
|
91827
92379
|
const draggedRef = useRef175(false);
|
|
91828
|
-
const requestIframePlaybackSync =
|
|
92380
|
+
const requestIframePlaybackSync = useCallback171((shouldPlay) => {
|
|
91829
92381
|
if (syncTimer.current) {
|
|
91830
92382
|
clearTimeout(syncTimer.current);
|
|
91831
92383
|
syncTimer.current = null;
|
|
@@ -92205,7 +92757,7 @@ var StudioLeftPanels = memo49(function StudioLeftPanels2({
|
|
|
92205
92757
|
handleImportFiles,
|
|
92206
92758
|
handleContentChange
|
|
92207
92759
|
} = useFileManagerContext();
|
|
92208
|
-
const handleRenderComposition =
|
|
92760
|
+
const handleRenderComposition = useCallback172(
|
|
92209
92761
|
async (comp) => {
|
|
92210
92762
|
if (renderQueue.ffmpegMissing) {
|
|
92211
92763
|
useDockLayoutStore.getState().activatePanel("renders");
|
|
@@ -92315,13 +92867,28 @@ function CodeBody({
|
|
|
92315
92867
|
}
|
|
92316
92868
|
|
|
92317
92869
|
// src/components/StudioRightPanels.tsx
|
|
92318
|
-
import { memo as memo59, useCallback as
|
|
92870
|
+
import { memo as memo59, useCallback as useCallback189 } from "react";
|
|
92319
92871
|
|
|
92320
92872
|
// src/components/editor/LayersPanel.tsx
|
|
92321
|
-
import { memo as memo50, useState as useState143, useCallback as
|
|
92873
|
+
import { memo as memo50, useState as useState143, useCallback as useCallback174, useEffect as useEffect145, useRef as useRef177 } from "react";
|
|
92874
|
+
|
|
92875
|
+
// src/components/editor/layerKind.ts
|
|
92876
|
+
function isCompositionHost(el) {
|
|
92877
|
+
return el.hasAttribute("data-composition-src") || el.hasAttribute("data-composition-file");
|
|
92878
|
+
}
|
|
92879
|
+
function layerKindOf(el, hasChildren) {
|
|
92880
|
+
const tag = el.tagName.toLowerCase();
|
|
92881
|
+
if (tag === "img" || tag === "picture") return "image";
|
|
92882
|
+
if (tag === "video") return "video";
|
|
92883
|
+
if (tag === "audio") return "audio";
|
|
92884
|
+
if (tag === "svg") return "vector";
|
|
92885
|
+
if (el.hasAttribute("data-hf-group") || isCompositionHost(el)) return "group";
|
|
92886
|
+
if (hasOnlyFormattingChildren(el) && el.textContent?.trim()) return "text";
|
|
92887
|
+
return hasChildren ? "group" : "shape";
|
|
92888
|
+
}
|
|
92322
92889
|
|
|
92323
92890
|
// src/components/editor/useLayerDrag.ts
|
|
92324
|
-
import { useRef as useRef176, useState as useState142, useCallback as
|
|
92891
|
+
import { useRef as useRef176, useState as useState142, useCallback as useCallback173 } from "react";
|
|
92325
92892
|
var DRAG_THRESHOLD_PX4 = 4;
|
|
92326
92893
|
function isLayerDraggable(layer) {
|
|
92327
92894
|
if (!(layer.selector || layer.id)) return false;
|
|
@@ -92391,7 +92958,7 @@ function useLayerDrag({
|
|
|
92391
92958
|
const dragRef = useRef176(null);
|
|
92392
92959
|
const [dragKey, setDragKey] = useState142(null);
|
|
92393
92960
|
const [insertionLineY, setInsertionLineY] = useState142(null);
|
|
92394
|
-
const handleRowPointerDown =
|
|
92961
|
+
const handleRowPointerDown = useCallback173(
|
|
92395
92962
|
(layerIndex, e) => {
|
|
92396
92963
|
if (e.button !== 0) return;
|
|
92397
92964
|
const layer = visibleLayers[layerIndex];
|
|
@@ -92418,7 +92985,7 @@ function useLayerDrag({
|
|
|
92418
92985
|
},
|
|
92419
92986
|
[visibleLayers, scrollContainerRef, onSingleSibling]
|
|
92420
92987
|
);
|
|
92421
|
-
const handleContainerPointerMove =
|
|
92988
|
+
const handleContainerPointerMove = useCallback173(
|
|
92422
92989
|
(e) => {
|
|
92423
92990
|
const drag = dragRef.current;
|
|
92424
92991
|
if (!drag) return;
|
|
@@ -92444,7 +93011,7 @@ function useLayerDrag({
|
|
|
92444
93011
|
},
|
|
92445
93012
|
[visibleLayers, scrollContainerRef]
|
|
92446
93013
|
);
|
|
92447
|
-
const handleContainerPointerUp =
|
|
93014
|
+
const handleContainerPointerUp = useCallback173(() => {
|
|
92448
93015
|
const drag = dragRef.current;
|
|
92449
93016
|
dragRef.current = null;
|
|
92450
93017
|
setDragKey(null);
|
|
@@ -92531,36 +93098,17 @@ function getVisibleLayers(layers, collapsed) {
|
|
|
92531
93098
|
// src/components/editor/LayersPanel.tsx
|
|
92532
93099
|
import { jsx as jsx223, jsxs as jsxs178 } from "react/jsx-runtime";
|
|
92533
93100
|
var LAYERS_PANEL_MAX_ROWS = 80;
|
|
92534
|
-
var
|
|
92535
|
-
|
|
92536
|
-
|
|
92537
|
-
|
|
92538
|
-
|
|
92539
|
-
|
|
92540
|
-
|
|
92541
|
-
|
|
92542
|
-
|
|
92543
|
-
|
|
92544
|
-
h1: "H1",
|
|
92545
|
-
h2: "H2",
|
|
92546
|
-
h3: "H3",
|
|
92547
|
-
h4: "H4",
|
|
92548
|
-
h5: "H5",
|
|
92549
|
-
h6: "H6",
|
|
92550
|
-
a: "A",
|
|
92551
|
-
button: "Bt",
|
|
92552
|
-
ul: "Ul",
|
|
92553
|
-
ol: "Ol",
|
|
92554
|
-
li: "Li",
|
|
92555
|
-
style: "St",
|
|
92556
|
-
template: "Te"
|
|
93101
|
+
var [CARET, ICON, GAP] = [16, 20, 6];
|
|
93102
|
+
var CHILD_INDENT = CARET + GAP + ICON + GAP;
|
|
93103
|
+
var KIND_ICON = {
|
|
93104
|
+
image: ImageIcon,
|
|
93105
|
+
video: Film,
|
|
93106
|
+
audio: Music,
|
|
93107
|
+
vector: Vector,
|
|
93108
|
+
group: Folder,
|
|
93109
|
+
text: Type,
|
|
93110
|
+
shape: Square
|
|
92557
93111
|
};
|
|
92558
|
-
function getTagBadge(tagName) {
|
|
92559
|
-
return TAG_ICONS[tagName] ?? tagName.slice(0, 2).toUpperCase();
|
|
92560
|
-
}
|
|
92561
|
-
function isCompositionHost(el) {
|
|
92562
|
-
return el.hasAttribute("data-composition-src") || el.hasAttribute("data-composition-file");
|
|
92563
|
-
}
|
|
92564
93112
|
function createRafThrottle(run, throttleMs = 100) {
|
|
92565
93113
|
let rafId = null;
|
|
92566
93114
|
let lastFired = 0;
|
|
@@ -92619,7 +93167,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92619
93167
|
});
|
|
92620
93168
|
const isMasterView = !activeCompPath || activeCompPath === "index.html";
|
|
92621
93169
|
const livePreviewIframe = useLivePreviewIframe();
|
|
92622
|
-
const collectLayers =
|
|
93170
|
+
const collectLayers = useCallback174(() => {
|
|
92623
93171
|
const iframe = previewIframeRef.current;
|
|
92624
93172
|
if (!iframe) return;
|
|
92625
93173
|
let doc = null;
|
|
@@ -92667,7 +93215,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92667
93215
|
throttle.cancel();
|
|
92668
93216
|
};
|
|
92669
93217
|
}, [collectLayers]);
|
|
92670
|
-
const resolveSelection =
|
|
93218
|
+
const resolveSelection = useCallback174(
|
|
92671
93219
|
(layer) => {
|
|
92672
93220
|
const doc = previewIframeRef.current?.contentDocument;
|
|
92673
93221
|
const el = liveLayerElement(layer, doc, activeCompPath);
|
|
@@ -92680,7 +93228,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92680
93228
|
},
|
|
92681
93229
|
[activeCompPath, isMasterView, previewIframeRef, activeGroupElement]
|
|
92682
93230
|
);
|
|
92683
|
-
const seekToLayer =
|
|
93231
|
+
const seekToLayer = useCallback174(
|
|
92684
93232
|
async (layer) => {
|
|
92685
93233
|
const selection = await resolveSelection(layer);
|
|
92686
93234
|
if (!selection) return;
|
|
@@ -92709,7 +93257,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92709
93257
|
},
|
|
92710
93258
|
[currentTime, resolveSelection, timelineElements]
|
|
92711
93259
|
);
|
|
92712
|
-
const handleSelectLayer =
|
|
93260
|
+
const handleSelectLayer = useCallback174(
|
|
92713
93261
|
async (layer) => {
|
|
92714
93262
|
const selection = await resolveSelection(layer);
|
|
92715
93263
|
if (!selection) return;
|
|
@@ -92719,7 +93267,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92719
93267
|
},
|
|
92720
93268
|
[resolveSelection, applyDomSelection, seekToLayer, scheduleReveal]
|
|
92721
93269
|
);
|
|
92722
|
-
const handleLayerDoubleClick =
|
|
93270
|
+
const handleLayerDoubleClick = useCallback174(
|
|
92723
93271
|
async (layer) => {
|
|
92724
93272
|
const selection = await resolveSelection(layer);
|
|
92725
93273
|
if (selection?.element.hasAttribute("data-hf-group")) {
|
|
@@ -92730,7 +93278,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92730
93278
|
},
|
|
92731
93279
|
[resolveSelection, setActiveGroupElement, handleSelectLayer]
|
|
92732
93280
|
);
|
|
92733
|
-
const handleLayerHover =
|
|
93281
|
+
const handleLayerHover = useCallback174(
|
|
92734
93282
|
async (layer) => {
|
|
92735
93283
|
if (!layer) {
|
|
92736
93284
|
updateDomEditHoverSelection(null);
|
|
@@ -92741,11 +93289,11 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92741
93289
|
},
|
|
92742
93290
|
[resolveSelection, updateDomEditHoverSelection]
|
|
92743
93291
|
);
|
|
92744
|
-
const toggleCollapse =
|
|
93292
|
+
const toggleCollapse = useCallback174((key2, e) => {
|
|
92745
93293
|
e.stopPropagation();
|
|
92746
93294
|
setCollapsed((prev) => ({ ...prev, [key2]: !prev[key2] }));
|
|
92747
93295
|
}, []);
|
|
92748
|
-
const handleReorder =
|
|
93296
|
+
const handleReorder = useCallback174(
|
|
92749
93297
|
(event) => {
|
|
92750
93298
|
const { siblingLayers, fromIndex, toIndex } = event;
|
|
92751
93299
|
const reordered = [...siblingLayers];
|
|
@@ -92808,7 +93356,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92808
93356
|
);
|
|
92809
93357
|
const selectedKey = domEditSelection ? getDomEditLayerKey(domEditSelection) : null;
|
|
92810
93358
|
const visibleLayers = getVisibleLayers(layers, collapsed);
|
|
92811
|
-
const handleSingleSibling =
|
|
93359
|
+
const handleSingleSibling = useCallback174(() => {
|
|
92812
93360
|
showToast("Only one layer at this level", "info");
|
|
92813
93361
|
}, [showToast]);
|
|
92814
93362
|
const {
|
|
@@ -92855,7 +93403,7 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92855
93403
|
{
|
|
92856
93404
|
type: "button",
|
|
92857
93405
|
onClick: () => setActiveGroupElement(null),
|
|
92858
|
-
className: "flex w-
|
|
93406
|
+
className: "mx-1 flex w-[calc(100%-0.5rem)] items-center gap-1.5 rounded-md px-2 py-1 text-left text-[11px] text-panel-text-3 hover:bg-panel-hover/40 hover:text-panel-text-1",
|
|
92859
93407
|
children: [
|
|
92860
93408
|
/* @__PURE__ */ jsx223("span", { "aria-hidden": "true", children: "\u2190" }),
|
|
92861
93409
|
/* @__PURE__ */ jsx223("span", { className: "truncate", children: activeGroupElement.getAttribute("data-hf-group") || "Group" })
|
|
@@ -92869,6 +93417,10 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92869
93417
|
const isCollapsed = collapsed[layer.key] ?? false;
|
|
92870
93418
|
const hasChildren = layer.childCount > 0;
|
|
92871
93419
|
const isCompHost = isCompositionHost(layer.element);
|
|
93420
|
+
const kind = layerKindOf(layer.element, hasChildren);
|
|
93421
|
+
const KindIcon = KIND_ICON[kind];
|
|
93422
|
+
const kindName = kind[0].toUpperCase() + kind.slice(1);
|
|
93423
|
+
const hint = draggable ? layer.element.hasAttribute("data-hf-group") ? "Double-click to enter group" : void 0 : "This layer can't be reordered";
|
|
92872
93424
|
return /* @__PURE__ */ jsxs178(
|
|
92873
93425
|
"div",
|
|
92874
93426
|
{
|
|
@@ -92885,9 +93437,9 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92885
93437
|
handleSelectLayer(layer);
|
|
92886
93438
|
}
|
|
92887
93439
|
},
|
|
92888
|
-
className: `group flex
|
|
92889
|
-
style: { paddingLeft: 8 + layer.depth *
|
|
92890
|
-
title:
|
|
93440
|
+
className: `group mx-1 flex items-center gap-1.5 rounded-md px-2 py-1 text-left transition-colors ${isDragged ? "opacity-40" : selected ? "bg-panel-accent/14 text-accent-ink" : "text-panel-text-2 hover:bg-panel-hover/40 hover:text-panel-text-1"} ${dragKey ? "cursor-grabbing" : "cursor-pointer"}`,
|
|
93441
|
+
style: { paddingLeft: 8 + layer.depth * CHILD_INDENT },
|
|
93442
|
+
title: hint,
|
|
92891
93443
|
children: [
|
|
92892
93444
|
hasChildren ? /* @__PURE__ */ jsx223(
|
|
92893
93445
|
"button",
|
|
@@ -92909,12 +93461,14 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92909
93461
|
}
|
|
92910
93462
|
)
|
|
92911
93463
|
}
|
|
92912
|
-
) :
|
|
93464
|
+
) : null,
|
|
92913
93465
|
/* @__PURE__ */ jsx223(
|
|
92914
93466
|
"span",
|
|
92915
93467
|
{
|
|
92916
|
-
|
|
92917
|
-
|
|
93468
|
+
"data-layer-kind": kind,
|
|
93469
|
+
title: hint ? `${kindName} \xB7 ${hint}` : kindName,
|
|
93470
|
+
className: `flex h-5 w-5 shrink-0 items-center justify-center rounded ${selected ? "bg-panel-accent/18 text-accent-ink" : isCompHost ? "bg-on text-accent-ink" : "bg-panel-hover text-panel-text-4"}`,
|
|
93471
|
+
children: /* @__PURE__ */ jsx223(KindIcon, { size: 12 })
|
|
92918
93472
|
}
|
|
92919
93473
|
),
|
|
92920
93474
|
/* @__PURE__ */ jsx223("span", { className: "min-w-0 flex-1 truncate text-[11px]", children: layer.label }),
|
|
@@ -92940,10 +93494,10 @@ var LayersPanel = memo50(function LayersPanel2({ host }) {
|
|
|
92940
93494
|
});
|
|
92941
93495
|
|
|
92942
93496
|
// src/captions/components/CaptionPropertyPanel.tsx
|
|
92943
|
-
import { memo as memo52, useCallback as
|
|
93497
|
+
import { memo as memo52, useCallback as useCallback176, useState as useState145 } from "react";
|
|
92944
93498
|
|
|
92945
93499
|
// src/captions/components/CaptionAnimationPanel.tsx
|
|
92946
|
-
import { memo as memo51, useCallback as
|
|
93500
|
+
import { memo as memo51, useCallback as useCallback175 } from "react";
|
|
92947
93501
|
|
|
92948
93502
|
// src/captions/components/shared.tsx
|
|
92949
93503
|
import { useEffect as useEffect146, useRef as useRef178, useState as useState144 } from "react";
|
|
@@ -93168,25 +93722,25 @@ var CaptionAnimationPanel = memo51(function CaptionAnimationPanel2() {
|
|
|
93168
93722
|
}
|
|
93169
93723
|
const group = resolvedGroupId ? model?.groups.get(resolvedGroupId) : void 0;
|
|
93170
93724
|
const animation = group?.animation;
|
|
93171
|
-
const handleEntranceChange =
|
|
93725
|
+
const handleEntranceChange = useCallback175(
|
|
93172
93726
|
(update) => {
|
|
93173
93727
|
if (resolvedGroupId) updateGroupAnimation(resolvedGroupId, "entrance", update);
|
|
93174
93728
|
},
|
|
93175
93729
|
[resolvedGroupId, updateGroupAnimation]
|
|
93176
93730
|
);
|
|
93177
|
-
const handleHighlightChange =
|
|
93731
|
+
const handleHighlightChange = useCallback175(
|
|
93178
93732
|
(update) => {
|
|
93179
93733
|
if (resolvedGroupId) updateGroupAnimation(resolvedGroupId, "highlight", update);
|
|
93180
93734
|
},
|
|
93181
93735
|
[resolvedGroupId, updateGroupAnimation]
|
|
93182
93736
|
);
|
|
93183
|
-
const handleExitChange =
|
|
93737
|
+
const handleExitChange = useCallback175(
|
|
93184
93738
|
(update) => {
|
|
93185
93739
|
if (resolvedGroupId) updateGroupAnimation(resolvedGroupId, "exit", update);
|
|
93186
93740
|
},
|
|
93187
93741
|
[resolvedGroupId, updateGroupAnimation]
|
|
93188
93742
|
);
|
|
93189
|
-
const handleApplyToAll =
|
|
93743
|
+
const handleApplyToAll = useCallback175(() => {
|
|
93190
93744
|
if (animation) applyAnimationToAll(animation);
|
|
93191
93745
|
}, [animation, applyAnimationToAll]);
|
|
93192
93746
|
if (!group || !resolvedGroupId || !animation) {
|
|
@@ -93286,7 +93840,7 @@ var CaptionPropertyPanel = memo52(function CaptionPropertyPanel2({
|
|
|
93286
93840
|
...groupStyle,
|
|
93287
93841
|
...segmentOverrides
|
|
93288
93842
|
};
|
|
93289
|
-
const applyToIframeDom =
|
|
93843
|
+
const applyToIframeDom = useCallback176(
|
|
93290
93844
|
(updates) => {
|
|
93291
93845
|
const iframe = iframeRef.current;
|
|
93292
93846
|
if (!iframe || !model) return;
|
|
@@ -93360,7 +93914,7 @@ var CaptionPropertyPanel = memo52(function CaptionPropertyPanel2({
|
|
|
93360
93914
|
},
|
|
93361
93915
|
[iframeRef, model, selectedSegmentIds]
|
|
93362
93916
|
);
|
|
93363
|
-
const handleStyleChange =
|
|
93917
|
+
const handleStyleChange = useCallback176(
|
|
93364
93918
|
(updates) => {
|
|
93365
93919
|
if (selectedGroupId) {
|
|
93366
93920
|
updateGroupStyle(selectedGroupId, updates);
|
|
@@ -93465,7 +94019,7 @@ var CaptionPropertyPanel = memo52(function CaptionPropertyPanel2({
|
|
|
93465
94019
|
});
|
|
93466
94020
|
|
|
93467
94021
|
// src/components/editor/BlockParamsPanel.tsx
|
|
93468
|
-
import { memo as memo53, useCallback as
|
|
94022
|
+
import { memo as memo53, useCallback as useCallback177, useEffect as useEffect147, useRef as useRef179, useState as useState146 } from "react";
|
|
93469
94023
|
import { jsx as jsx227, jsxs as jsxs182 } from "react/jsx-runtime";
|
|
93470
94024
|
var BlockParamsPanel = memo53(function BlockParamsPanel2({
|
|
93471
94025
|
blockName,
|
|
@@ -93488,7 +94042,7 @@ var BlockParamsPanel = memo53(function BlockParamsPanel2({
|
|
|
93488
94042
|
);
|
|
93489
94043
|
const [commitState, setCommitState] = useState146({ tone: "idle" });
|
|
93490
94044
|
const commitTimersRef = useRef179(/* @__PURE__ */ new Map());
|
|
93491
|
-
const commitParamNow =
|
|
94045
|
+
const commitParamNow = useCallback177(
|
|
93492
94046
|
async (key2, nextValue) => {
|
|
93493
94047
|
if (!fileManager) return;
|
|
93494
94048
|
const previous = appliedRef.current[key2];
|
|
@@ -93533,7 +94087,7 @@ var BlockParamsPanel = memo53(function BlockParamsPanel2({
|
|
|
93533
94087
|
},
|
|
93534
94088
|
[fileManager, compositionPath, setRefreshKey, blockName]
|
|
93535
94089
|
);
|
|
93536
|
-
const commitParam =
|
|
94090
|
+
const commitParam = useCallback177(
|
|
93537
94091
|
(key2, nextValue) => fileManager ? serializeStudioFileMutation(
|
|
93538
94092
|
fileManager.writeProjectFile,
|
|
93539
94093
|
compositionPath,
|
|
@@ -93541,7 +94095,7 @@ var BlockParamsPanel = memo53(function BlockParamsPanel2({
|
|
|
93541
94095
|
) : Promise.resolve(),
|
|
93542
94096
|
[commitParamNow, compositionPath, fileManager]
|
|
93543
94097
|
);
|
|
93544
|
-
const handleChange =
|
|
94098
|
+
const handleChange = useCallback177(
|
|
93545
94099
|
(key2, value) => {
|
|
93546
94100
|
setValues((prev) => ({ ...prev, [key2]: value }));
|
|
93547
94101
|
const timers = commitTimersRef.current;
|
|
@@ -93704,7 +94258,7 @@ import { createPortal as createPortal14 } from "react-dom";
|
|
|
93704
94258
|
import { CANVAS_DIMENSIONS } from "@hyperframes/parsers";
|
|
93705
94259
|
|
|
93706
94260
|
// src/components/renders/RenderQueueItem.tsx
|
|
93707
|
-
import { memo as memo54, useCallback as
|
|
94261
|
+
import { memo as memo54, useCallback as useCallback178, useState as useState147 } from "react";
|
|
93708
94262
|
import { Fragment as Fragment64, jsx as jsx228, jsxs as jsxs183 } from "react/jsx-runtime";
|
|
93709
94263
|
function formatDuration2(ms) {
|
|
93710
94264
|
if (ms < 1e3) return `${ms}ms`;
|
|
@@ -93727,10 +94281,10 @@ var RenderQueueItem = memo54(function RenderQueueItem2({
|
|
|
93727
94281
|
const [videoReady, setVideoReady] = useState147(false);
|
|
93728
94282
|
const [confirmingDelete, setConfirmingDelete] = useState147(false);
|
|
93729
94283
|
const fileSrc = buildProjectApiPath(projectId, `/renders/file/${job.filename}`);
|
|
93730
|
-
const handleOpen =
|
|
94284
|
+
const handleOpen = useCallback178(() => {
|
|
93731
94285
|
window.open(fileSrc, "_blank");
|
|
93732
94286
|
}, [fileSrc]);
|
|
93733
|
-
const handleDownload =
|
|
94287
|
+
const handleDownload = useCallback178(
|
|
93734
94288
|
(e) => {
|
|
93735
94289
|
e.stopPropagation();
|
|
93736
94290
|
const a = document.createElement("a");
|
|
@@ -94478,11 +95032,11 @@ var RenderQueuePanel = memo57(function RenderQueuePanel2() {
|
|
|
94478
95032
|
});
|
|
94479
95033
|
|
|
94480
95034
|
// src/components/panels/SlideshowPanel.tsx
|
|
94481
|
-
import { useState as useState151, useEffect as useEffect150, useCallback as
|
|
95035
|
+
import { useState as useState151, useEffect as useEffect150, useCallback as useCallback180, useRef as useRef182 } from "react";
|
|
94482
95036
|
import { parseSlideshowManifest } from "@hyperframes/core/slideshow";
|
|
94483
95037
|
|
|
94484
95038
|
// src/components/panels/SlideshowSubPanels.tsx
|
|
94485
|
-
import { useState as useState150, useCallback as
|
|
95039
|
+
import { useState as useState150, useCallback as useCallback179, useId as useId6 } from "react";
|
|
94486
95040
|
import { jsx as jsx232, jsxs as jsxs186 } from "react/jsx-runtime";
|
|
94487
95041
|
function SectionHeader({
|
|
94488
95042
|
children,
|
|
@@ -94670,7 +95224,7 @@ function BranchTree({
|
|
|
94670
95224
|
}) {
|
|
94671
95225
|
const [newLabel, setNewLabel] = useState150("");
|
|
94672
95226
|
const inputId = useId6();
|
|
94673
|
-
const handleCreate =
|
|
95227
|
+
const handleCreate = useCallback179(() => {
|
|
94674
95228
|
const label = newLabel.trim();
|
|
94675
95229
|
if (!label) return;
|
|
94676
95230
|
onCreateSequence(label);
|
|
@@ -94732,7 +95286,7 @@ function BranchItem({
|
|
|
94732
95286
|
const [editing, setEditing] = useState150(false);
|
|
94733
95287
|
const [draft, setDraft] = useState150(seq.label);
|
|
94734
95288
|
const [confirmingDelete, setConfirmingDelete] = useState150(false);
|
|
94735
|
-
const commitRename =
|
|
95289
|
+
const commitRename = useCallback179(() => {
|
|
94736
95290
|
const label = draft.trim();
|
|
94737
95291
|
if (label && label !== seq.label) onRename(seq.id, label);
|
|
94738
95292
|
setEditing(false);
|
|
@@ -94865,7 +95419,7 @@ function HotspotTool({
|
|
|
94865
95419
|
const selectedElementId = domEditSelection?.element?.id ?? null;
|
|
94866
95420
|
const selectedHfId = domEditSelection?.hfId ?? null;
|
|
94867
95421
|
const elementKey3 = selectedElementId || selectedHfId;
|
|
94868
|
-
const handleMakeHotspot =
|
|
95422
|
+
const handleMakeHotspot = useCallback179(() => {
|
|
94869
95423
|
if (!selectedSceneId || !targetSequenceId || !elementKey3) return;
|
|
94870
95424
|
const id = `hotspot-${elementKey3}-${generateId()}`;
|
|
94871
95425
|
const label = hotspotLabel.trim() || elementKey3;
|
|
@@ -95190,7 +95744,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95190
95744
|
setUndoDepth(0);
|
|
95191
95745
|
setPersistError(false);
|
|
95192
95746
|
}, [compHtml]);
|
|
95193
|
-
const applyManifest =
|
|
95747
|
+
const applyManifest = useCallback180(
|
|
95194
95748
|
async (next, opts) => {
|
|
95195
95749
|
const merged = notesCtrlRef.current.mergeIntoDiscrete(next);
|
|
95196
95750
|
if (!opts?.skipUndo) {
|
|
@@ -95210,14 +95764,14 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95210
95764
|
},
|
|
95211
95765
|
[onPersist]
|
|
95212
95766
|
);
|
|
95213
|
-
const handleUndo =
|
|
95767
|
+
const handleUndo = useCallback180(() => {
|
|
95214
95768
|
const prev = undoStackRef.current.pop();
|
|
95215
95769
|
if (!prev) return;
|
|
95216
95770
|
setUndoDepth(undoStackRef.current.length);
|
|
95217
95771
|
applyManifest(prev, { skipUndo: true }).catch(() => {
|
|
95218
95772
|
});
|
|
95219
95773
|
}, [applyManifest]);
|
|
95220
|
-
const handleRetryPersist =
|
|
95774
|
+
const handleRetryPersist = useCallback180(async () => {
|
|
95221
95775
|
setRetrying(true);
|
|
95222
95776
|
try {
|
|
95223
95777
|
await onPersist(manifestRef.current);
|
|
@@ -95228,7 +95782,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95228
95782
|
setRetrying(false);
|
|
95229
95783
|
}
|
|
95230
95784
|
}, [onPersist]);
|
|
95231
|
-
const applyNotesManifest =
|
|
95785
|
+
const applyNotesManifest = useCallback180(
|
|
95232
95786
|
(next) => {
|
|
95233
95787
|
setManifest(next);
|
|
95234
95788
|
manifestRef.current = next;
|
|
@@ -95242,7 +95796,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95242
95796
|
ctrl.flush();
|
|
95243
95797
|
};
|
|
95244
95798
|
}, []);
|
|
95245
|
-
const toggleSection =
|
|
95799
|
+
const toggleSection = useCallback180((key2) => {
|
|
95246
95800
|
setExpandedSections((prev) => {
|
|
95247
95801
|
const next = new Set(prev);
|
|
95248
95802
|
if (next.has(key2)) {
|
|
@@ -95256,25 +95810,25 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95256
95810
|
const activeSlides = selectedSequenceId ? (manifest.slideSequences ?? []).find((s) => s.id === selectedSequenceId)?.slides ?? [] : manifest.slides;
|
|
95257
95811
|
const selectedSlide = activeSlides.find((s) => s.sceneId === selectedSceneId);
|
|
95258
95812
|
const sequences = manifest.slideSequences ?? [];
|
|
95259
|
-
const handleSelectBranchSlide =
|
|
95813
|
+
const handleSelectBranchSlide = useCallback180((sequenceId, sceneId) => {
|
|
95260
95814
|
setSelectedSceneId(sceneId);
|
|
95261
95815
|
setSelectedSequenceId(sequenceId);
|
|
95262
95816
|
}, []);
|
|
95263
|
-
const handleToggleSlide =
|
|
95817
|
+
const handleToggleSlide = useCallback180(
|
|
95264
95818
|
(sceneId) => {
|
|
95265
95819
|
applyManifest(toggleMainLineSlide(manifestRef.current, sceneId)).catch(() => {
|
|
95266
95820
|
});
|
|
95267
95821
|
},
|
|
95268
95822
|
[applyManifest]
|
|
95269
95823
|
);
|
|
95270
|
-
const handleReorder =
|
|
95824
|
+
const handleReorder = useCallback180(
|
|
95271
95825
|
(sceneId, dir) => {
|
|
95272
95826
|
applyManifest(reorderMainLineSlide(manifestRef.current, sceneId, dir)).catch(() => {
|
|
95273
95827
|
});
|
|
95274
95828
|
},
|
|
95275
95829
|
[applyManifest]
|
|
95276
95830
|
);
|
|
95277
|
-
const handleSetNotes =
|
|
95831
|
+
const handleSetNotes = useCallback180(
|
|
95278
95832
|
(notes) => {
|
|
95279
95833
|
if (!selectedSceneId) return;
|
|
95280
95834
|
applyNotesManifest(
|
|
@@ -95283,7 +95837,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95283
95837
|
},
|
|
95284
95838
|
[selectedSceneId, selectedSequenceId, applyNotesManifest]
|
|
95285
95839
|
);
|
|
95286
|
-
const handleMarkFragment =
|
|
95840
|
+
const handleMarkFragment = useCallback180(() => {
|
|
95287
95841
|
if (!selectedSceneId) return;
|
|
95288
95842
|
applyManifest(
|
|
95289
95843
|
addFragment(
|
|
@@ -95295,7 +95849,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95295
95849
|
).catch(() => {
|
|
95296
95850
|
});
|
|
95297
95851
|
}, [selectedSceneId, selectedSequenceId, currentTime, applyManifest]);
|
|
95298
|
-
const handleRemoveFragment =
|
|
95852
|
+
const handleRemoveFragment = useCallback180(
|
|
95299
95853
|
(time) => {
|
|
95300
95854
|
if (!selectedSceneId) return;
|
|
95301
95855
|
applyManifest(
|
|
@@ -95305,7 +95859,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95305
95859
|
},
|
|
95306
95860
|
[selectedSceneId, selectedSequenceId, applyManifest]
|
|
95307
95861
|
);
|
|
95308
|
-
const handleCreateSequence =
|
|
95862
|
+
const handleCreateSequence = useCallback180(
|
|
95309
95863
|
(label) => {
|
|
95310
95864
|
const id = `seq-${generateId()}`;
|
|
95311
95865
|
applyManifest(createSequence(manifestRef.current, id, label)).catch(() => {
|
|
@@ -95313,21 +95867,21 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95313
95867
|
},
|
|
95314
95868
|
[applyManifest]
|
|
95315
95869
|
);
|
|
95316
|
-
const handleRenameSequence =
|
|
95870
|
+
const handleRenameSequence = useCallback180(
|
|
95317
95871
|
(id, label) => {
|
|
95318
95872
|
applyManifest(renameSequence(manifestRef.current, id, label)).catch(() => {
|
|
95319
95873
|
});
|
|
95320
95874
|
},
|
|
95321
95875
|
[applyManifest]
|
|
95322
95876
|
);
|
|
95323
|
-
const handleDeleteSequence =
|
|
95877
|
+
const handleDeleteSequence = useCallback180(
|
|
95324
95878
|
(id) => {
|
|
95325
95879
|
applyManifest(deleteSequence(manifestRef.current, id)).catch(() => {
|
|
95326
95880
|
});
|
|
95327
95881
|
},
|
|
95328
95882
|
[applyManifest]
|
|
95329
95883
|
);
|
|
95330
|
-
const handleAssign =
|
|
95884
|
+
const handleAssign = useCallback180(
|
|
95331
95885
|
(sequenceId, sceneId, assign) => {
|
|
95332
95886
|
applyManifest(assignToBranch(manifestRef.current, sequenceId, sceneId, assign)).catch(
|
|
95333
95887
|
() => {
|
|
@@ -95336,7 +95890,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95336
95890
|
},
|
|
95337
95891
|
[applyManifest]
|
|
95338
95892
|
);
|
|
95339
|
-
const handleAddHotspot =
|
|
95893
|
+
const handleAddHotspot = useCallback180(
|
|
95340
95894
|
(sceneId, hotspot) => {
|
|
95341
95895
|
applyManifest(
|
|
95342
95896
|
addHotspot(manifestRef.current, sceneId, hotspot, selectedSequenceId ?? void 0)
|
|
@@ -95345,7 +95899,7 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95345
95899
|
},
|
|
95346
95900
|
[selectedSequenceId, applyManifest]
|
|
95347
95901
|
);
|
|
95348
|
-
const handleRemoveHotspot =
|
|
95902
|
+
const handleRemoveHotspot = useCallback180(
|
|
95349
95903
|
(sceneId, hotspotId) => {
|
|
95350
95904
|
applyManifest(
|
|
95351
95905
|
removeHotspot(manifestRef.current, sceneId, hotspotId, selectedSequenceId ?? void 0)
|
|
@@ -95495,10 +96049,10 @@ function SlideshowPanel({ scenes, onPersist, onPersistNotes }) {
|
|
|
95495
96049
|
}
|
|
95496
96050
|
|
|
95497
96051
|
// src/components/panels/VariablesPanel.tsx
|
|
95498
|
-
import { memo as memo58, useCallback as
|
|
96052
|
+
import { memo as memo58, useCallback as useCallback184, useEffect as useEffect152, useMemo as useMemo86, useState as useState155 } from "react";
|
|
95499
96053
|
|
|
95500
96054
|
// src/hooks/useVariablesPersist.ts
|
|
95501
|
-
import { useCallback as
|
|
96055
|
+
import { useCallback as useCallback181 } from "react";
|
|
95502
96056
|
function useVariablesPersist({
|
|
95503
96057
|
sdkSession,
|
|
95504
96058
|
activeCompPath,
|
|
@@ -95508,7 +96062,7 @@ function useVariablesPersist({
|
|
|
95508
96062
|
reloadPreview,
|
|
95509
96063
|
publishSdkSession
|
|
95510
96064
|
}) {
|
|
95511
|
-
return
|
|
96065
|
+
return useCallback181(
|
|
95512
96066
|
async (label, mutate) => {
|
|
95513
96067
|
if (!sdkSession) return false;
|
|
95514
96068
|
const path = activeCompPath ?? "index.html";
|
|
@@ -95543,10 +96097,10 @@ function useVariablesPersist({
|
|
|
95543
96097
|
}
|
|
95544
96098
|
|
|
95545
96099
|
// src/components/panels/VariablesOtherCompositions.tsx
|
|
95546
|
-
import { useCallback as
|
|
96100
|
+
import { useCallback as useCallback183, useState as useState154 } from "react";
|
|
95547
96101
|
|
|
95548
96102
|
// src/hooks/useProjectCompositionVariables.ts
|
|
95549
|
-
import { useCallback as
|
|
96103
|
+
import { useCallback as useCallback182, useEffect as useEffect151, useState as useState152 } from "react";
|
|
95550
96104
|
import { openComposition as openComposition4 } from "@hyperframes/sdk";
|
|
95551
96105
|
async function readGroup(path, readProjectFile) {
|
|
95552
96106
|
let content;
|
|
@@ -95589,7 +96143,7 @@ function useProjectCompositionVariables(compositionPaths, excludePath, readProje
|
|
|
95589
96143
|
}
|
|
95590
96144
|
function useEditVariablesInFile(deps) {
|
|
95591
96145
|
const { readProjectFile, writeProjectFile, recordEdit, reloadPreview } = deps;
|
|
95592
|
-
return
|
|
96146
|
+
return useCallback182(
|
|
95593
96147
|
async (path, label, mutate) => {
|
|
95594
96148
|
const originalContent = await readProjectFile(path);
|
|
95595
96149
|
await persistSdkSerialize(
|
|
@@ -95966,7 +96520,7 @@ function VariablesOtherCompositions({
|
|
|
95966
96520
|
reloadPreview
|
|
95967
96521
|
});
|
|
95968
96522
|
const [editingKey, setEditingKey] = useState154(null);
|
|
95969
|
-
const onSave =
|
|
96523
|
+
const onSave = useCallback183(
|
|
95970
96524
|
(path, decl) => {
|
|
95971
96525
|
setEditingKey(null);
|
|
95972
96526
|
void editInFile(
|
|
@@ -95977,7 +96531,7 @@ function VariablesOtherCompositions({
|
|
|
95977
96531
|
},
|
|
95978
96532
|
[editInFile]
|
|
95979
96533
|
);
|
|
95980
|
-
const onRemove =
|
|
96534
|
+
const onRemove = useCallback183(
|
|
95981
96535
|
(path, id) => {
|
|
95982
96536
|
void editInFile(
|
|
95983
96537
|
path,
|
|
@@ -96211,7 +96765,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96211
96765
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
96212
96766
|
[sdkSession, previewValues, refreshKey, revision]
|
|
96213
96767
|
);
|
|
96214
|
-
const copyToClipboard =
|
|
96768
|
+
const copyToClipboard = useCallback184(
|
|
96215
96769
|
(text, what) => {
|
|
96216
96770
|
void copyTextToClipboard(text).then(
|
|
96217
96771
|
(ok) => showToast(
|
|
@@ -96222,7 +96776,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96222
96776
|
},
|
|
96223
96777
|
[showToast]
|
|
96224
96778
|
);
|
|
96225
|
-
const dropPreviewOverride =
|
|
96779
|
+
const dropPreviewOverride = useCallback184(
|
|
96226
96780
|
(id) => {
|
|
96227
96781
|
if (previewValues && id in previewValues) {
|
|
96228
96782
|
const next = { ...previewValues };
|
|
@@ -96232,7 +96786,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96232
96786
|
},
|
|
96233
96787
|
[previewValues, setPreviewValues]
|
|
96234
96788
|
);
|
|
96235
|
-
const commitPreviewValue =
|
|
96789
|
+
const commitPreviewValue = useCallback184(
|
|
96236
96790
|
(id, value, declDefault) => {
|
|
96237
96791
|
const next = { ...previewValues ?? {} };
|
|
96238
96792
|
if (JSON.stringify(value) === JSON.stringify(declDefault)) {
|
|
@@ -96245,7 +96799,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96245
96799
|
},
|
|
96246
96800
|
[previewValues, setPreviewValues, reloadPreview]
|
|
96247
96801
|
);
|
|
96248
|
-
const runSchemaEdit =
|
|
96802
|
+
const runSchemaEdit = useCallback184(
|
|
96249
96803
|
async (label, mutate) => {
|
|
96250
96804
|
try {
|
|
96251
96805
|
const changed = await persistVariables(label, mutate);
|
|
@@ -96259,7 +96813,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96259
96813
|
},
|
|
96260
96814
|
[persistVariables, showToast]
|
|
96261
96815
|
);
|
|
96262
|
-
const handleAdd =
|
|
96816
|
+
const handleAdd = useCallback184(
|
|
96263
96817
|
(decl) => {
|
|
96264
96818
|
if (!sdkSession) return;
|
|
96265
96819
|
const check = sdkSession.can({ type: "declareVariable", declaration: decl });
|
|
@@ -96272,7 +96826,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96272
96826
|
},
|
|
96273
96827
|
[sdkSession, runSchemaEdit, showToast]
|
|
96274
96828
|
);
|
|
96275
|
-
const handleUpdate =
|
|
96829
|
+
const handleUpdate = useCallback184(
|
|
96276
96830
|
(decl) => {
|
|
96277
96831
|
if (!sdkSession) return;
|
|
96278
96832
|
const check = sdkSession.can({
|
|
@@ -96292,7 +96846,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96292
96846
|
},
|
|
96293
96847
|
[sdkSession, runSchemaEdit, showToast]
|
|
96294
96848
|
);
|
|
96295
|
-
const handleRemove =
|
|
96849
|
+
const handleRemove = useCallback184(
|
|
96296
96850
|
(id) => {
|
|
96297
96851
|
if (!sdkSession) return;
|
|
96298
96852
|
const check = sdkSession.can({ type: "removeVariableDeclaration", id });
|
|
@@ -96308,18 +96862,18 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96308
96862
|
},
|
|
96309
96863
|
[sdkSession, runSchemaEdit, dropPreviewOverride, showToast]
|
|
96310
96864
|
);
|
|
96311
|
-
const handleSetDefault =
|
|
96865
|
+
const handleSetDefault = useCallback184(
|
|
96312
96866
|
(id, value) => {
|
|
96313
96867
|
void runSchemaEdit(`Set default for "${id}"`, (s) => s.setVariableValue(id, value));
|
|
96314
96868
|
dropPreviewOverride(id);
|
|
96315
96869
|
},
|
|
96316
96870
|
[runSchemaEdit, dropPreviewOverride]
|
|
96317
96871
|
);
|
|
96318
|
-
const resetPreview =
|
|
96872
|
+
const resetPreview = useCallback184(() => {
|
|
96319
96873
|
setPreviewValues(null);
|
|
96320
96874
|
reloadPreview();
|
|
96321
96875
|
}, [setPreviewValues, reloadPreview]);
|
|
96322
|
-
const handleBind =
|
|
96876
|
+
const handleBind = useCallback184(
|
|
96323
96877
|
// Guard chain (session, selection, type-compat) — one branch per guard.
|
|
96324
96878
|
// fallow-ignore-next-line complexity
|
|
96325
96879
|
(action, id) => {
|
|
@@ -96431,7 +96985,7 @@ var VariablesPanel = memo58(function VariablesPanel2({
|
|
|
96431
96985
|
});
|
|
96432
96986
|
|
|
96433
96987
|
// src/hooks/useSlideshowPersist.ts
|
|
96434
|
-
import { useCallback as
|
|
96988
|
+
import { useCallback as useCallback185 } from "react";
|
|
96435
96989
|
|
|
96436
96990
|
// src/utils/setSlideshowManifest.ts
|
|
96437
96991
|
import {
|
|
@@ -96488,7 +97042,7 @@ function useSlideshowPersist({
|
|
|
96488
97042
|
publishSdkSession,
|
|
96489
97043
|
coalesceKey
|
|
96490
97044
|
}) {
|
|
96491
|
-
return
|
|
97045
|
+
return useCallback185(
|
|
96492
97046
|
async (manifest) => {
|
|
96493
97047
|
if (!sdkSession) return;
|
|
96494
97048
|
const path = activeCompPath ?? "index.html";
|
|
@@ -96546,7 +97100,7 @@ function useSlideshowTabState(params) {
|
|
|
96546
97100
|
}
|
|
96547
97101
|
|
|
96548
97102
|
// src/components/DesignPanelPromoteProvider.tsx
|
|
96549
|
-
import { useCallback as
|
|
97103
|
+
import { useCallback as useCallback186 } from "react";
|
|
96550
97104
|
import { jsx as jsx238 } from "react/jsx-runtime";
|
|
96551
97105
|
function DesignPanelPromoteProvider({
|
|
96552
97106
|
selection,
|
|
@@ -96565,7 +97119,7 @@ function DesignPanelPromoteProvider({
|
|
|
96565
97119
|
publishSdkSession: handle.publish,
|
|
96566
97120
|
activeCompPath: targetPath
|
|
96567
97121
|
});
|
|
96568
|
-
const persist2 =
|
|
97122
|
+
const persist2 = useCallback186(
|
|
96569
97123
|
async (label, mutate) => {
|
|
96570
97124
|
const committed = await rawPersist(label, mutate);
|
|
96571
97125
|
if (committed) forceReloadSharedSdkSession?.();
|
|
@@ -96573,7 +97127,7 @@ function DesignPanelPromoteProvider({
|
|
|
96573
97127
|
},
|
|
96574
97128
|
[rawPersist, forceReloadSharedSdkSession]
|
|
96575
97129
|
);
|
|
96576
|
-
const handlePersistError =
|
|
97130
|
+
const handlePersistError = useCallback186(
|
|
96577
97131
|
(error) => showToast(getStudioSaveErrorMessage(error), "error"),
|
|
96578
97132
|
[showToast]
|
|
96579
97133
|
);
|
|
@@ -96590,7 +97144,7 @@ function DesignPanelPromoteProvider({
|
|
|
96590
97144
|
}
|
|
96591
97145
|
|
|
96592
97146
|
// src/hooks/useRemoveBackground.ts
|
|
96593
|
-
import { useCallback as
|
|
97147
|
+
import { useCallback as useCallback187, useEffect as useEffect153, useRef as useRef183 } from "react";
|
|
96594
97148
|
|
|
96595
97149
|
// src/components/studioMediaJobs.ts
|
|
96596
97150
|
var MEDIA_JOB_RECONNECT_TIMEOUT_MS = 15e3;
|
|
@@ -96703,7 +97257,7 @@ function useRemoveBackground(projectId, refreshFileTree, showToast) {
|
|
|
96703
97257
|
},
|
|
96704
97258
|
[]
|
|
96705
97259
|
);
|
|
96706
|
-
return
|
|
97260
|
+
return useCallback187(
|
|
96707
97261
|
// fallow-ignore-next-line complexity
|
|
96708
97262
|
async (inputPath, options) => {
|
|
96709
97263
|
const response = await studioApiFetch(
|
|
@@ -96742,7 +97296,7 @@ function useRemoveBackground(projectId, refreshFileTree, showToast) {
|
|
|
96742
97296
|
}
|
|
96743
97297
|
|
|
96744
97298
|
// src/hooks/useApplyColorGradingScope.ts
|
|
96745
|
-
import { useCallback as
|
|
97299
|
+
import { useCallback as useCallback188 } from "react";
|
|
96746
97300
|
|
|
96747
97301
|
// src/components/editor/colorGradingScopePatch.ts
|
|
96748
97302
|
var MEDIA_TAG_RE = /<\s*(video|img)\b(?:[^>"']|"[^"]*"|'[^']*')*>/gi;
|
|
@@ -96846,7 +97400,7 @@ function useApplyColorGradingScope(recordEdit, reloadPreview) {
|
|
|
96846
97400
|
const { projectId, activeCompPath, showToast, waitForPendingDomEditSaves } = useStudioShellContext();
|
|
96847
97401
|
const { domEditSelection } = useDomEditContext();
|
|
96848
97402
|
const { readProjectFile, writeProjectFile, compositions } = useFileManagerContext();
|
|
96849
|
-
return
|
|
97403
|
+
return useCallback188(
|
|
96850
97404
|
async (scope, value) => applyColorGradingScopeUpdate({
|
|
96851
97405
|
scope,
|
|
96852
97406
|
value,
|
|
@@ -96994,11 +97548,11 @@ var StudioRightPanels = memo59(function StudioRightPanels2({
|
|
|
96994
97548
|
useCaptionDesignFocus(captionEditMode);
|
|
96995
97549
|
const handleApplyColorGradingScope = useApplyColorGradingScope(recordEdit, reloadPreview);
|
|
96996
97550
|
const handleRemoveBackground = useRemoveBackground(projectId, refreshFileTree, showToast);
|
|
96997
|
-
const setAttributeWhileDragging =
|
|
97551
|
+
const setAttributeWhileDragging = useCallback189(
|
|
96998
97552
|
(attr, value) => handleDomAttributeLiveCommit(attr, value, void 0, { previewOnly: true }),
|
|
96999
97553
|
[handleDomAttributeLiveCommit]
|
|
97000
97554
|
);
|
|
97001
|
-
const handleHideAllSelected =
|
|
97555
|
+
const handleHideAllSelected = useCallback189(() => {
|
|
97002
97556
|
if (!canHideSelections(domEditGroupSelections)) {
|
|
97003
97557
|
showToast("Audio can't be hidden \u2014 use the group's own controls", "info");
|
|
97004
97558
|
return;
|
|
@@ -97007,7 +97561,7 @@ var StudioRightPanels = memo59(function StudioRightPanels2({
|
|
|
97007
97561
|
const keys = timelineKeysForSelections(domEditGroupSelections, elements, activeCompPath);
|
|
97008
97562
|
if (keys.length > 0) void onToggleElementHidden?.(keys, true);
|
|
97009
97563
|
}, [domEditGroupSelections, showToast, activeCompPath, onToggleElementHidden]);
|
|
97010
|
-
const convertToKeyframes =
|
|
97564
|
+
const convertToKeyframes = useCallback189(
|
|
97011
97565
|
(animId, duration) => handleGsapConvertToKeyframes(animId, void 0, duration),
|
|
97012
97566
|
[handleGsapConvertToKeyframes]
|
|
97013
97567
|
);
|
|
@@ -97163,340 +97717,6 @@ import {
|
|
|
97163
97717
|
MagnifyingGlassPlus
|
|
97164
97718
|
} from "@phosphor-icons/react";
|
|
97165
97719
|
|
|
97166
|
-
// src/hooks/useEnableKeyframes.ts
|
|
97167
|
-
import { useCallback as useCallback189 } from "react";
|
|
97168
|
-
var enableKeyframesTransactionCounter = 0;
|
|
97169
|
-
function animatedProps(anim) {
|
|
97170
|
-
if (!anim) return ["x", "y"];
|
|
97171
|
-
const own = Object.keys(anim.properties ?? {});
|
|
97172
|
-
if (own.length > 0) return own;
|
|
97173
|
-
const stops = anim.keyframes?.keyframes;
|
|
97174
|
-
if (stops?.length) {
|
|
97175
|
-
const keys = /* @__PURE__ */ new Set();
|
|
97176
|
-
for (const stop2 of stops) for (const k of Object.keys(stop2.properties ?? {})) keys.add(k);
|
|
97177
|
-
if (keys.size > 0) return [...keys];
|
|
97178
|
-
}
|
|
97179
|
-
return ["x", "y"];
|
|
97180
|
-
}
|
|
97181
|
-
function isPlayheadWithinTween(anim, currentTime) {
|
|
97182
|
-
const start = resolveTweenStart(anim);
|
|
97183
|
-
if (start === null) return true;
|
|
97184
|
-
return isTimeWithinTween(currentTime, start, resolveTweenDuration(anim));
|
|
97185
|
-
}
|
|
97186
|
-
async function replaceSetWithSingleKeyframe(session, sel, setAnim, t2, iframe, selector) {
|
|
97187
|
-
const position = readElementPosition(iframe, sel, setAnim);
|
|
97188
|
-
if (Object.keys(position).length === 0) {
|
|
97189
|
-
for (const [key2, held] of Object.entries(setAnim.properties ?? {})) {
|
|
97190
|
-
if (typeof held === "number") position[key2] = held;
|
|
97191
|
-
}
|
|
97192
|
-
}
|
|
97193
|
-
if (Object.keys(position).length === 0 || !session.commitMutation) return;
|
|
97194
|
-
const range = resolveNewTweenRange(sel.dataAttributes?.start, sel.dataAttributes?.duration, t2);
|
|
97195
|
-
await session.commitMutation(
|
|
97196
|
-
{
|
|
97197
|
-
type: "replace-with-keyframes",
|
|
97198
|
-
animationId: setAnim.id,
|
|
97199
|
-
targetSelector: selector,
|
|
97200
|
-
position: roundTo3(range.start),
|
|
97201
|
-
duration: roundTo3(range.duration),
|
|
97202
|
-
keyframes: [{ percentage: 0, properties: position }],
|
|
97203
|
-
ease: setAnim.ease
|
|
97204
|
-
},
|
|
97205
|
-
{ label: "Enable keyframes", keyframeAction: "add", softReload: true }
|
|
97206
|
-
);
|
|
97207
|
-
}
|
|
97208
|
-
function readElementPosition(iframe, sel, anim) {
|
|
97209
|
-
const result = {};
|
|
97210
|
-
if (!iframe?.contentWindow) return result;
|
|
97211
|
-
let gsap3;
|
|
97212
|
-
try {
|
|
97213
|
-
gsap3 = iframe.contentWindow.gsap;
|
|
97214
|
-
} catch {
|
|
97215
|
-
return result;
|
|
97216
|
-
}
|
|
97217
|
-
const element = sel.element;
|
|
97218
|
-
if (!element?.isConnected || !gsap3?.getProperty) return result;
|
|
97219
|
-
const props = animatedProps(anim);
|
|
97220
|
-
for (const prop of props) {
|
|
97221
|
-
const val = Number(gsap3.getProperty(element, prop));
|
|
97222
|
-
if (!Number.isFinite(val)) continue;
|
|
97223
|
-
result[prop] = POSITION_PROPS.has(prop) ? Math.round(val) : roundTo3(val);
|
|
97224
|
-
}
|
|
97225
|
-
return result;
|
|
97226
|
-
}
|
|
97227
|
-
function resolveNewTweenRange(authoredStart, authoredDuration, currentTime) {
|
|
97228
|
-
const t2 = Math.max(0, roundTo3(currentTime));
|
|
97229
|
-
const start = authoredStart != null ? Number.parseFloat(authoredStart) : Number.NaN;
|
|
97230
|
-
const duration = authoredDuration != null ? Number.parseFloat(authoredDuration) : Number.NaN;
|
|
97231
|
-
if (!Number.isFinite(start) || !Number.isFinite(duration) || duration <= 0) {
|
|
97232
|
-
return { start: t2, duration: 1 };
|
|
97233
|
-
}
|
|
97234
|
-
const end = start + duration;
|
|
97235
|
-
const clampedStart = Math.min(Math.max(t2, start), end);
|
|
97236
|
-
return { start: clampedStart, duration: Math.max(0.5, roundTo3(end - clampedStart)) };
|
|
97237
|
-
}
|
|
97238
|
-
async function tryFetchAnimationsForElement(sel) {
|
|
97239
|
-
const projectId = window.location.hash.match(/project\/([^?/]+)/)?.[1];
|
|
97240
|
-
if (!projectId) return null;
|
|
97241
|
-
const sourceFile = sel.sourceFile || "index.html";
|
|
97242
|
-
const parsed = await fetchParsedAnimations(projectId, sourceFile);
|
|
97243
|
-
if (!parsed) return null;
|
|
97244
|
-
return getAnimationsForElement(parsed.animations, {
|
|
97245
|
-
id: sel.id,
|
|
97246
|
-
selector: sel.selector
|
|
97247
|
-
});
|
|
97248
|
-
}
|
|
97249
|
-
async function fetchAnimationsForElement(sel) {
|
|
97250
|
-
return await tryFetchAnimationsForElement(sel) ?? [];
|
|
97251
|
-
}
|
|
97252
|
-
async function extendKeyframedTweenToPlayhead(session, sel, anim, currentTime, duration, iframe, commitOverrides) {
|
|
97253
|
-
const selector = existingTweenTargetSelector(anim, sel);
|
|
97254
|
-
const position = readElementPosition(iframe, sel, anim);
|
|
97255
|
-
if (!selector || Object.keys(position).length === 0 || !session.commitMutation) return;
|
|
97256
|
-
const extended = buildExtendedKeyframes(anim, currentTime, position, duration);
|
|
97257
|
-
await session.commitMutation(
|
|
97258
|
-
{
|
|
97259
|
-
type: "replace-with-keyframes",
|
|
97260
|
-
animationId: anim.id,
|
|
97261
|
-
targetSelector: selector,
|
|
97262
|
-
position: extended.position,
|
|
97263
|
-
duration: extended.duration,
|
|
97264
|
-
keyframes: extended.keyframes,
|
|
97265
|
-
...keyframeEases(anim)
|
|
97266
|
-
},
|
|
97267
|
-
{
|
|
97268
|
-
label: "Add keyframe",
|
|
97269
|
-
keyframeAction: "add",
|
|
97270
|
-
softReload: true,
|
|
97271
|
-
...commitOverrides
|
|
97272
|
-
}
|
|
97273
|
-
);
|
|
97274
|
-
}
|
|
97275
|
-
async function applyKeyframeAtPlayhead(session, sel, kfAnim, t2, iframe, commitOverrides, liveTween) {
|
|
97276
|
-
const keepAuthoredDuration = kfAnim.durationUnresolved === true;
|
|
97277
|
-
if (keepAuthoredDuration) {
|
|
97278
|
-
kfAnim = withLiveTiming(kfAnim, liveTween ?? findParsedTween(iframe, sel.element, kfAnim));
|
|
97279
|
-
}
|
|
97280
|
-
if (keepAuthoredDuration && kfAnim.duration == null) return;
|
|
97281
|
-
const duration = resolveTweenDuration(kfAnim);
|
|
97282
|
-
const start = resolveTweenStart(kfAnim);
|
|
97283
|
-
if (start !== null && !isTimeWithinTween(t2, start, duration)) {
|
|
97284
|
-
if (keepAuthoredDuration) return;
|
|
97285
|
-
await extendKeyframedTweenToPlayhead(
|
|
97286
|
-
session,
|
|
97287
|
-
sel,
|
|
97288
|
-
kfAnim,
|
|
97289
|
-
t2,
|
|
97290
|
-
duration,
|
|
97291
|
-
iframe,
|
|
97292
|
-
commitOverrides
|
|
97293
|
-
);
|
|
97294
|
-
return;
|
|
97295
|
-
}
|
|
97296
|
-
const pct = start === null ? computeElementPercentage(t2, sel) : absoluteToPercentageForAnimation(t2, kfAnim) ?? 0;
|
|
97297
|
-
const existing = kfAnim.keyframes?.keyframes.find((k) => playsNear(kfAnim, k.percentage, pct));
|
|
97298
|
-
if (existing) {
|
|
97299
|
-
session.handleGsapRemoveKeyframe(kfAnim.id, existing.percentage);
|
|
97300
|
-
return;
|
|
97301
|
-
}
|
|
97302
|
-
if (session.handleGsapAddKeyframeBatch) {
|
|
97303
|
-
const position = readElementPosition(iframe, sel, kfAnim);
|
|
97304
|
-
if (Object.keys(position).length > 0) {
|
|
97305
|
-
await session.handleGsapAddKeyframeBatch(kfAnim.id, pct, position, commitOverrides);
|
|
97306
|
-
}
|
|
97307
|
-
}
|
|
97308
|
-
}
|
|
97309
|
-
async function promoteSetToKeyframes(session, sel, setAnim, t2, iframe) {
|
|
97310
|
-
const selector = existingTweenTargetSelector(setAnim, sel);
|
|
97311
|
-
const setStart = resolveTweenStart(setAnim) ?? 0;
|
|
97312
|
-
if (!selector || !session.commitMutation) return;
|
|
97313
|
-
if (t2 <= setStart) {
|
|
97314
|
-
await replaceSetWithSingleKeyframe(session, sel, setAnim, t2, iframe, selector);
|
|
97315
|
-
return;
|
|
97316
|
-
}
|
|
97317
|
-
const endPosition = readElementPosition(iframe, sel, setAnim);
|
|
97318
|
-
if (Object.keys(endPosition).length === 0) return;
|
|
97319
|
-
const startPosition = {};
|
|
97320
|
-
for (const key2 of Object.keys(endPosition)) {
|
|
97321
|
-
const held = setAnim.properties?.[key2];
|
|
97322
|
-
if (typeof held === "number") startPosition[key2] = held;
|
|
97323
|
-
}
|
|
97324
|
-
await session.commitMutation(
|
|
97325
|
-
{
|
|
97326
|
-
type: "replace-with-keyframes",
|
|
97327
|
-
animationId: setAnim.id,
|
|
97328
|
-
targetSelector: selector,
|
|
97329
|
-
position: roundTo3(setStart),
|
|
97330
|
-
duration: roundTo3(t2 - setStart),
|
|
97331
|
-
keyframes: [
|
|
97332
|
-
{
|
|
97333
|
-
percentage: 0,
|
|
97334
|
-
properties: Object.keys(startPosition).length > 0 ? startPosition : endPosition,
|
|
97335
|
-
auto: true
|
|
97336
|
-
},
|
|
97337
|
-
{ percentage: 100, properties: endPosition }
|
|
97338
|
-
],
|
|
97339
|
-
ease: setAnim.ease
|
|
97340
|
-
},
|
|
97341
|
-
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
97342
|
-
);
|
|
97343
|
-
}
|
|
97344
|
-
async function applyArcKeyframeAtPlayhead(session, sel, arcAnim, t2, iframe) {
|
|
97345
|
-
if (!session.commitMutation) return;
|
|
97346
|
-
const targetSelector = existingTweenTargetSelector(arcAnim, sel);
|
|
97347
|
-
if (!targetSelector) return;
|
|
97348
|
-
const start = resolveTweenStart(arcAnim) ?? 0;
|
|
97349
|
-
const duration = resolveTweenDuration(arcAnim);
|
|
97350
|
-
if (!isTimeWithinTween(t2, start, duration)) {
|
|
97351
|
-
const held = readElementPosition(iframe, sel, arcAnim);
|
|
97352
|
-
if (t2 <= start || typeof held.x !== "number" || typeof held.y !== "number") return;
|
|
97353
|
-
const extended = buildExtendedKeyframes(arcAnim, t2, { x: held.x, y: held.y }, duration, "none");
|
|
97354
|
-
await session.commitMutation(
|
|
97355
|
-
{
|
|
97356
|
-
type: "replace-with-keyframes",
|
|
97357
|
-
animationId: arcAnim.id,
|
|
97358
|
-
targetSelector,
|
|
97359
|
-
position: extended.position,
|
|
97360
|
-
duration: extended.duration,
|
|
97361
|
-
keyframes: extended.keyframes,
|
|
97362
|
-
ease: "none"
|
|
97363
|
-
},
|
|
97364
|
-
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
97365
|
-
);
|
|
97366
|
-
return;
|
|
97367
|
-
}
|
|
97368
|
-
const nodes = linearArcKeyframes(arcAnim);
|
|
97369
|
-
const playheadPercentage = absoluteToPercentage(t2, start, duration);
|
|
97370
|
-
const timedNodeIndex = nodes.findIndex(
|
|
97371
|
-
(node) => Math.abs(node.percentage - playheadPercentage) <= KEYFRAME_PCT_MATCH
|
|
97372
|
-
);
|
|
97373
|
-
if (timedNodeIndex !== -1) {
|
|
97374
|
-
if (timedNodeIndex > 0 && timedNodeIndex < nodes.length - 1) {
|
|
97375
|
-
await session.commitMutation(
|
|
97376
|
-
{
|
|
97377
|
-
type: "replace-with-keyframes",
|
|
97378
|
-
animationId: arcAnim.id,
|
|
97379
|
-
targetSelector,
|
|
97380
|
-
position: roundTo3(start),
|
|
97381
|
-
duration: roundTo3(duration),
|
|
97382
|
-
keyframes: nodes.filter((_, index) => index !== timedNodeIndex),
|
|
97383
|
-
ease: "none"
|
|
97384
|
-
},
|
|
97385
|
-
{ label: "Remove keyframe", softReload: true }
|
|
97386
|
-
);
|
|
97387
|
-
}
|
|
97388
|
-
return;
|
|
97389
|
-
}
|
|
97390
|
-
const live = readElementPosition(iframe, sel, arcAnim);
|
|
97391
|
-
if (typeof live.x !== "number" || typeof live.y !== "number") return;
|
|
97392
|
-
await session.commitMutation(
|
|
97393
|
-
{
|
|
97394
|
-
type: "replace-with-keyframes",
|
|
97395
|
-
animationId: arcAnim.id,
|
|
97396
|
-
targetSelector,
|
|
97397
|
-
position: roundTo3(start),
|
|
97398
|
-
duration: roundTo3(duration),
|
|
97399
|
-
keyframes: buildTemporalArcKeyframes(arcAnim, playheadPercentage, {
|
|
97400
|
-
x: live.x,
|
|
97401
|
-
y: live.y
|
|
97402
|
-
}),
|
|
97403
|
-
ease: "none"
|
|
97404
|
-
},
|
|
97405
|
-
{ label: "Add keyframe", keyframeAction: "add", softReload: true }
|
|
97406
|
-
);
|
|
97407
|
-
}
|
|
97408
|
-
function useEnableKeyframes(sessionRef) {
|
|
97409
|
-
return useCallback189(async () => {
|
|
97410
|
-
const session = sessionRef.current;
|
|
97411
|
-
if (!session) return;
|
|
97412
|
-
const sel = session.domEditSelection;
|
|
97413
|
-
if (!sel) return;
|
|
97414
|
-
const t2 = usePlayerStore.getState().currentTime;
|
|
97415
|
-
const iframe = session.previewIframeRef?.current ?? null;
|
|
97416
|
-
const fetched = await tryFetchAnimationsForElement(sel);
|
|
97417
|
-
const anims = fetched ?? session.selectedGsapAnimations;
|
|
97418
|
-
const arcAnim = anims.find((a) => a.arcPath);
|
|
97419
|
-
const kfAnim = anims.find((a) => a.keyframes && !a.arcPath);
|
|
97420
|
-
const setAnim = anims.find((a) => isInstantHold(a) && !a.keyframes && !a.arcPath);
|
|
97421
|
-
const flatAnim = anims.find((a) => !a.keyframes && !a.arcPath && !isInstantHold(a));
|
|
97422
|
-
if (arcAnim) {
|
|
97423
|
-
await applyArcKeyframeAtPlayhead(session, sel, arcAnim, t2, iframe);
|
|
97424
|
-
} else if (kfAnim) {
|
|
97425
|
-
await applyKeyframeAtPlayhead(session, sel, kfAnim, t2, iframe);
|
|
97426
|
-
} else if (setAnim) {
|
|
97427
|
-
await promoteSetToKeyframes(session, sel, setAnim, t2, iframe);
|
|
97428
|
-
} else if (flatAnim) {
|
|
97429
|
-
const flatLive = flatAnim.durationUnresolved ? findParsedTween(iframe, sel.element, flatAnim) : void 0;
|
|
97430
|
-
enableKeyframesTransactionCounter += 1;
|
|
97431
|
-
const coalesceKey = `enable-keyframes:${flatAnim.id}:${enableKeyframesTransactionCounter}`;
|
|
97432
|
-
const convertCommitOverrides = {
|
|
97433
|
-
keyframeTelemetry: false,
|
|
97434
|
-
skipReload: true,
|
|
97435
|
-
coalesceKey,
|
|
97436
|
-
coalesceMs: Number.POSITIVE_INFINITY
|
|
97437
|
-
};
|
|
97438
|
-
await session.handleGsapConvertToKeyframes(
|
|
97439
|
-
flatAnim.id,
|
|
97440
|
-
void 0,
|
|
97441
|
-
void 0,
|
|
97442
|
-
convertCommitOverrides
|
|
97443
|
-
);
|
|
97444
|
-
const converted = (await fetchAnimationsForElement(sel)).find((a) => a.keyframes);
|
|
97445
|
-
if (converted) {
|
|
97446
|
-
const applyCommitOverrides = {
|
|
97447
|
-
softReload: true,
|
|
97448
|
-
coalesceKey,
|
|
97449
|
-
// Must match the convert phase's window: editHistory keys coalescing
|
|
97450
|
-
// off the incoming entry, so without Infinity here the apply (landing
|
|
97451
|
-
// after two POSTs + a fetch) falls back to the 300ms default and the
|
|
97452
|
-
// conversion splits into two undo entries under real latency.
|
|
97453
|
-
coalesceMs: Number.POSITIVE_INFINITY
|
|
97454
|
-
};
|
|
97455
|
-
await applyKeyframeAtPlayhead(
|
|
97456
|
-
session,
|
|
97457
|
-
sel,
|
|
97458
|
-
converted,
|
|
97459
|
-
t2,
|
|
97460
|
-
iframe,
|
|
97461
|
-
applyCommitOverrides,
|
|
97462
|
-
flatLive
|
|
97463
|
-
);
|
|
97464
|
-
}
|
|
97465
|
-
} else {
|
|
97466
|
-
const position = readElementPosition(iframe, sel, null);
|
|
97467
|
-
const { start: elStart, duration: elDuration } = resolveNewTweenRange(
|
|
97468
|
-
sel.dataAttributes?.start,
|
|
97469
|
-
sel.dataAttributes?.duration,
|
|
97470
|
-
t2
|
|
97471
|
-
);
|
|
97472
|
-
const selector = writeTargetSelector(sel);
|
|
97473
|
-
if (!selector) {
|
|
97474
|
-
session.handleGsapAddAnimation("to");
|
|
97475
|
-
return;
|
|
97476
|
-
}
|
|
97477
|
-
if (Object.keys(position).length === 0) {
|
|
97478
|
-
position.x = 0;
|
|
97479
|
-
position.y = 0;
|
|
97480
|
-
}
|
|
97481
|
-
const keyframes = [{ percentage: 0, properties: { ...position } }];
|
|
97482
|
-
if (session.commitMutation) {
|
|
97483
|
-
await session.commitMutation(
|
|
97484
|
-
{
|
|
97485
|
-
type: "add-with-keyframes",
|
|
97486
|
-
targetSelector: selector,
|
|
97487
|
-
position: roundTo3(elStart),
|
|
97488
|
-
duration: roundTo3(elDuration),
|
|
97489
|
-
keyframes
|
|
97490
|
-
},
|
|
97491
|
-
{ label: "Enable keyframes", softReload: true }
|
|
97492
|
-
);
|
|
97493
|
-
} else {
|
|
97494
|
-
session.handleGsapAddAnimation("to");
|
|
97495
|
-
}
|
|
97496
|
-
}
|
|
97497
|
-
}, [sessionRef]);
|
|
97498
|
-
}
|
|
97499
|
-
|
|
97500
97720
|
// src/hooks/useKeyframeKeyboard.ts
|
|
97501
97721
|
import { useEffect as useEffect154, useCallback as useCallback190 } from "react";
|
|
97502
97722
|
function useKeyframeKeyboard({ enabled, onAddKeyframe }) {
|