@remotion/studio 4.0.512 → 4.0.513

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (55) hide show
  1. package/dist/components/CompositionSelectorItem.js +14 -1
  2. package/dist/components/InspectorOpenInEditor.js +24 -24
  3. package/dist/components/InspectorPanel/AlignmentControls.js +13 -2
  4. package/dist/components/InspectorPanel/CompositionInspectorHeader.js +12 -8
  5. package/dist/components/InspectorPanel/ConnectedCompositionsSection.js +12 -1
  6. package/dist/components/InspectorPanel/EasingInspector.js +11 -2
  7. package/dist/components/InspectorPanel/KeyframeInspector.js +19 -5
  8. package/dist/components/InspectorPanel/easing-inspector-selection.js +7 -2
  9. package/dist/components/InspectorPanel/inspector-section-collapse.d.ts +1 -0
  10. package/dist/components/SelectedOutlineElement.js +12 -10
  11. package/dist/components/SelectedOutlineOverlay.js +30 -8
  12. package/dist/components/Timeline/TimelineArrayField.js +1 -0
  13. package/dist/components/Timeline/TimelineEffectPropItem.js +10 -4
  14. package/dist/components/Timeline/TimelineKeyframeControls.js +25 -7
  15. package/dist/components/Timeline/TimelineKeyframedValue.js +1 -0
  16. package/dist/components/Timeline/TimelineSequencePropItem.js +11 -4
  17. package/dist/components/Timeline/TimelineSequenceRightEdgeDragHandle.d.ts +3 -0
  18. package/dist/components/Timeline/TimelineSequenceRightEdgeDragHandle.js +96 -18
  19. package/dist/components/Timeline/call-move-keyframe.d.ts +2 -1
  20. package/dist/components/Timeline/call-move-keyframe.js +70 -17
  21. package/dist/components/Timeline/delete-selected-keyframe.d.ts +0 -8
  22. package/dist/components/Timeline/delete-selected-keyframe.js +23 -44
  23. package/dist/components/Timeline/delete-selected-timeline-item.d.ts +0 -8
  24. package/dist/components/Timeline/delete-selected-timeline-item.js +16 -43
  25. package/dist/components/Timeline/get-easing-selection-after-keyframe-delete.js +8 -3
  26. package/dist/components/Timeline/get-sequence-context-menu-items.js +10 -8
  27. package/dist/components/Timeline/get-timeline-keyframes.d.ts +4 -0
  28. package/dist/components/Timeline/get-timeline-keyframes.js +16 -3
  29. package/dist/components/Timeline/keyframe-clipboard.js +9 -2
  30. package/dist/components/Timeline/use-open-sequence-in-apps.js +8 -8
  31. package/dist/components/Timeline/use-timeline-keyframe-drag.js +14 -4
  32. package/dist/components/VisualControls/ClickableFileName.js +13 -6
  33. package/dist/components/composition-menu-items.d.ts +6 -1
  34. package/dist/components/composition-menu-items.js +9 -6
  35. package/dist/components/folder-menu-items.d.ts +4 -1
  36. package/dist/components/folder-menu-items.js +4 -5
  37. package/dist/components/get-open-in-menu-items.d.ts +1 -1
  38. package/dist/components/get-open-in-menu-items.js +15 -13
  39. package/dist/components/sequence-props-api.js +44 -3
  40. package/dist/components/use-default-editor-info.d.ts +8 -0
  41. package/dist/components/use-default-editor-info.js +25 -9
  42. package/dist/error-overlay/remotion-overlay/ErrorDisplay.js +10 -3
  43. package/dist/error-overlay/remotion-overlay/OpenInEditor.d.ts +3 -1
  44. package/dist/error-overlay/remotion-overlay/OpenInEditor.js +6 -6
  45. package/dist/error-overlay/remotion-overlay/Overlay.js +14 -12
  46. package/dist/error-overlay/remotion-overlay/StackFrame.d.ts +2 -1
  47. package/dist/error-overlay/remotion-overlay/StackFrame.js +7 -4
  48. package/dist/esm/{chunk-s8gwjng0.js → chunk-tv7r0jy3.js} +1692 -1322
  49. package/dist/esm/internals.mjs +1692 -1322
  50. package/dist/esm/previewEntry.mjs +3167 -2793
  51. package/dist/esm/renderEntry.mjs +1 -1
  52. package/dist/helpers/open-in-editor.d.ts +6 -4
  53. package/dist/helpers/open-in-editor.js +4 -4
  54. package/dist/helpers/use-menu-structure.js +11 -6
  55. package/package.json +12 -12
@@ -4,14 +4,6 @@ import type { ConfirmationDialogFunction } from '../ConfirmationDialog-types';
4
4
  import type { SetPropStatuses } from './save-sequence-prop';
5
5
  import { type TimelineSelection } from './TimelineSelection';
6
6
  export declare const deleteSequencesFromSource: (nodePathInfos: SequenceNodePathInfo[], confirm: ConfirmationDialogFunction) => Promise<boolean>;
7
- export declare const deleteSelectedTimelineItem: ({ selection, sequences, overrideIdsToNodePaths, setPropStatuses, clientId, confirm, }: {
8
- selection: TimelineSelection;
9
- sequences: TSequence[];
10
- overrideIdsToNodePaths: OverrideIdToNodePaths;
11
- setPropStatuses: SetPropStatuses;
12
- clientId: string;
13
- confirm: ConfirmationDialogFunction;
14
- }) => Promise<boolean> | null;
15
7
  export declare const getTimelineSelectionAfterDeletingItems: ({ selections, sequences, overrideIdsToNodePaths, propStatuses, timelinePosition, }: {
16
8
  readonly selections: readonly TimelineSelection[];
17
9
  readonly sequences?: TSequence[] | undefined;
@@ -1,12 +1,13 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.deleteSelectedTimelineItems = exports.getTimelineSelectionAfterDeletingItems = exports.deleteSelectedTimelineItem = exports.deleteSequencesFromSource = void 0;
3
+ exports.deleteSelectedTimelineItems = exports.getTimelineSelectionAfterDeletingItems = exports.deleteSequencesFromSource = void 0;
4
4
  const remotion_1 = require("remotion");
5
5
  const call_api_1 = require("../call-api");
6
6
  const NotificationCenter_1 = require("../Notifications/NotificationCenter");
7
7
  const delete_selected_keyframe_1 = require("./delete-selected-keyframe");
8
8
  const find_track_for_node_path_info_1 = require("./find-track-for-node-path-info");
9
9
  const get_easing_selection_after_keyframe_delete_1 = require("./get-easing-selection-after-keyframe-delete");
10
+ const get_timeline_keyframes_1 = require("./get-timeline-keyframes");
10
11
  const parse_keyframe_field_from_node_path_1 = require("./parse-keyframe-field-from-node-path");
11
12
  const TimelineSelection_1 = require("./TimelineSelection");
12
13
  const update_selected_easing_1 = require("./update-selected-easing");
@@ -88,45 +89,6 @@ const deleteEffects = (effects) => {
88
89
  return false;
89
90
  });
90
91
  };
91
- const deleteSelectedTimelineItem = ({ selection, sequences, overrideIdsToNodePaths, setPropStatuses, clientId, confirm, }) => {
92
- var _a;
93
- if (selection.type === 'keyframe') {
94
- const promise = (0, delete_selected_keyframe_1.deleteSelectedKeyframe)({
95
- nodePathInfo: selection.nodePathInfo,
96
- frame: selection.frame,
97
- sequences,
98
- overrideIdsToNodePaths,
99
- setPropStatuses,
100
- clientId,
101
- });
102
- return (_a = promise === null || promise === void 0 ? void 0 : promise.then(() => true)) !== null && _a !== void 0 ? _a : null;
103
- }
104
- switch (selection.type) {
105
- case 'guide':
106
- return null;
107
- case 'sequence':
108
- return (0, exports.deleteSequencesFromSource)([selection.nodePathInfo], confirm);
109
- case 'sequence-effect':
110
- return deleteEffects([
111
- {
112
- type: 'single-effect',
113
- nodePathInfo: selection.nodePathInfo,
114
- effectIndex: selection.i,
115
- },
116
- ]);
117
- case 'sequence-prop':
118
- case 'sequence-effect-prop':
119
- case 'easing':
120
- return null;
121
- case 'sequence-all-effects':
122
- return deleteEffects([
123
- { type: 'all-effects', nodePathInfo: selection.nodePathInfo },
124
- ]);
125
- default:
126
- throw new Error(`Unexpected timeline selection type: ${selection}`);
127
- }
128
- };
129
- exports.deleteSelectedTimelineItem = deleteSelectedTimelineItem;
130
92
  const isSequenceRowSelection = (selection) => selection.type === 'sequence';
131
93
  const isSequenceEffectSelection = (selection) => selection.type === 'sequence-effect';
132
94
  const isSequenceAllEffectsSelection = (selection) => selection.type === 'sequence-all-effects';
@@ -173,7 +135,6 @@ const getEasingSelectionAfterDeletingKeyframes = ({ selections, sequences, overr
173
135
  return null;
174
136
  }
175
137
  const nodePath = selection.nodePathInfo.sequenceSubscriptionKey;
176
- const sourceFrame = selection.frame - track.keyframeDisplayOffset;
177
138
  if (field.type === 'sequence') {
178
139
  const sequencePropStatus = (_a = remotion_1.Internals.getPropStatusesCtx(propStatuses, nodePath)) === null || _a === void 0 ? void 0 : _a[field.fieldKey];
179
140
  if ((sequencePropStatus === null || sequencePropStatus === void 0 ? void 0 : sequencePropStatus.status) !== 'keyframed' ||
@@ -181,7 +142,13 @@ const getEasingSelectionAfterDeletingKeyframes = ({ selections, sequences, overr
181
142
  return null;
182
143
  }
183
144
  return (0, get_easing_selection_after_keyframe_delete_1.getEasingSelectionAfterKeyframeDelete)({
184
- deletedSourceFrames: [sourceFrame],
145
+ deletedSourceFrames: [
146
+ selection.frame -
147
+ (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
148
+ propStatus: sequencePropStatus,
149
+ keyframeDisplayOffset: track.keyframeDisplayOffset,
150
+ }),
151
+ ],
185
152
  keyframeDisplayOffset: track.keyframeDisplayOffset,
186
153
  nodePathInfo: selection.nodePathInfo,
187
154
  propStatus: sequencePropStatus,
@@ -201,7 +168,13 @@ const getEasingSelectionAfterDeletingKeyframes = ({ selections, sequences, overr
201
168
  return null;
202
169
  }
203
170
  return (0, get_easing_selection_after_keyframe_delete_1.getEasingSelectionAfterKeyframeDelete)({
204
- deletedSourceFrames: [sourceFrame],
171
+ deletedSourceFrames: [
172
+ selection.frame -
173
+ (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
174
+ propStatus: effectPropStatus,
175
+ keyframeDisplayOffset: track.keyframeDisplayOffset,
176
+ }),
177
+ ],
205
178
  keyframeDisplayOffset: track.keyframeDisplayOffset,
206
179
  nodePathInfo: selection.nodePathInfo,
207
180
  propStatus: effectPropStatus,
@@ -1,10 +1,15 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.getEasingSelectionAfterKeyframeDelete = void 0;
4
+ const get_timeline_keyframes_1 = require("./get-timeline-keyframes");
4
5
  const getEasingSelectionAfterKeyframeDelete = ({ deletedSourceFrames, keyframeDisplayOffset, nodePathInfo, propStatus, timelinePosition, }) => {
6
+ const resolvedKeyframeDisplayOffset = (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
7
+ propStatus,
8
+ keyframeDisplayOffset,
9
+ });
5
10
  const deletedSourceFrameSet = new Set(deletedSourceFrames);
6
11
  const remainingKeyframes = propStatus.keyframes.filter((keyframe) => !deletedSourceFrameSet.has(keyframe.frame));
7
- const sourceFrame = timelinePosition - keyframeDisplayOffset;
12
+ const sourceFrame = timelinePosition - resolvedKeyframeDisplayOffset;
8
13
  for (let i = 0; i < remainingKeyframes.length - 1; i++) {
9
14
  const keyframe = remainingKeyframes[i];
10
15
  const nextKeyframe = remainingKeyframes[i + 1];
@@ -15,8 +20,8 @@ const getEasingSelectionAfterKeyframeDelete = ({ deletedSourceFrames, keyframeDi
15
20
  return {
16
21
  type: 'easing',
17
22
  nodePathInfo,
18
- fromFrame: keyframe.frame + keyframeDisplayOffset,
19
- toFrame: nextKeyframe.frame + keyframeDisplayOffset,
23
+ fromFrame: keyframe.frame + resolvedKeyframeDisplayOffset,
24
+ toFrame: nextKeyframe.frame + resolvedKeyframeDisplayOffset,
20
25
  segmentIndex: i,
21
26
  };
22
27
  }
@@ -6,6 +6,7 @@ const format_file_location_1 = require("../../helpers/format-file-location");
6
6
  const get_open_in_menu_items_1 = require("../get-open-in-menu-items");
7
7
  const NotificationCenter_1 = require("../Notifications/NotificationCenter");
8
8
  const actions_1 = require("../RenderQueue/actions");
9
+ const use_default_editor_info_1 = require("../use-default-editor-info");
9
10
  const timeline_asset_link_1 = require("./timeline-asset-link");
10
11
  const normalizeMenuDividers = (items) => {
11
12
  var _a;
@@ -26,16 +27,17 @@ const normalizeMenuDividers = (items) => {
26
27
  };
27
28
  const interactiveSvgComponentIdentity = 'dev.remotion.remotion.Interactive.Svg';
28
29
  const getSequenceContextMenuItems = ({ assetLinkInfo, canOpenInEditor, deleteDisabled, disableInteractivityDisabled, duplicateDisabled, isProgrammaticallyDuplicated, includeSourceEditItems, codingAgentInfo, editorInfo, onConfigureApps, onDeleteSequenceFromSource, onDisableSequenceInteractivity, onDuplicateSequenceFromSource, openInCodingAgent, openInEditor, originalLocation, selectAsset, sequence, sourceActions = [], }) => {
29
- var _a, _b, _c, _d;
30
- var _e, _f, _g;
31
- const editorName = window.remotion_editorName;
30
+ var _a, _b, _c;
31
+ var _d, _e, _f;
32
32
  const isInteractiveSvg = ((_a = sequence.controls) === null || _a === void 0 ? void 0 : _a.componentIdentity) === interactiveSvgComponentIdentity;
33
- const installedEditors = (_e = editorInfo === null || editorInfo === void 0 ? void 0 : editorInfo.installedEditors) !== null && _e !== void 0 ? _e : [];
34
- const defaultEditorId = (_f = (_b = installedEditors.find((editor) => editor.nameWithType === editorName)) === null || _b === void 0 ? void 0 : _b.id) !== null && _f !== void 0 ? _f : null;
33
+ const installedEditors = (_d = editorInfo === null || editorInfo === void 0 ? void 0 : editorInfo.installedEditors) !== null && _d !== void 0 ? _d : [];
34
+ const defaultEditorId = (0, use_default_editor_info_1.getPreferredEditorId)(editorInfo);
35
+ const defaultEditor = installedEditors.find((editor) => editor.id === defaultEditorId);
36
+ const editorName = (_e = defaultEditor === null || defaultEditor === void 0 ? void 0 : defaultEditor.nameWithType) !== null && _e !== void 0 ? _e : null;
35
37
  const defaultCodingAgent = codingAgentInfo === null || codingAgentInfo === void 0 ? void 0 : codingAgentInfo.installedCodingAgents.find((codingAgent) => codingAgent.id === codingAgentInfo.defaultCodingAgent);
36
38
  const contextForAgents = (0, format_file_location_1.formatContextForAgents)({
37
39
  location: originalLocation,
38
- name: sequence.displayName || ((_c = sequence.controls) === null || _c === void 0 ? void 0 : _c.componentName) || null,
40
+ name: sequence.displayName || ((_b = sequence.controls) === null || _b === void 0 ? void 0 : _b.componentName) || null,
39
41
  root: window.remotion_cwd,
40
42
  });
41
43
  const openInCodingAgentWithContext = (codingAgentId, codingAgentName) => {
@@ -46,7 +48,7 @@ const getSequenceContextMenuItems = ({ assetLinkInfo, canOpenInEditor, deleteDis
46
48
  codingAgentInfo,
47
49
  editorDisabled: !canOpenInEditor || !originalLocation,
48
50
  editorInfo,
49
- excludeCodingAgentId: (_g = defaultCodingAgent === null || defaultCodingAgent === void 0 ? void 0 : defaultCodingAgent.id) !== null && _g !== void 0 ? _g : null,
51
+ excludeCodingAgentId: (_f = defaultCodingAgent === null || defaultCodingAgent === void 0 ? void 0 : defaultCodingAgent.id) !== null && _f !== void 0 ? _f : null,
50
52
  excludeEditorId: defaultEditorId,
51
53
  fileManagerDisabled: !(originalLocation === null || originalLocation === void 0 ? void 0 : originalLocation.source),
52
54
  folder: false,
@@ -161,7 +163,7 @@ const getSequenceContextMenuItems = ({ assetLinkInfo, canOpenInEditor, deleteDis
161
163
  keyHint: null,
162
164
  label: 'Copy SVG',
163
165
  leftItem: null,
164
- disabled: !((_d = sequence.refForOutline) === null || _d === void 0 ? void 0 : _d.current),
166
+ disabled: !((_c = sequence.refForOutline) === null || _c === void 0 ? void 0 : _c.current),
165
167
  onClick: () => {
166
168
  var _a;
167
169
  const svg = (_a = sequence.refForOutline) === null || _a === void 0 ? void 0 : _a.current;
@@ -4,3 +4,7 @@ export declare const getTimelineKeyframes: (propStatus: CanUpdateSequencePropSta
4
4
  frame: number;
5
5
  value: unknown;
6
6
  }[];
7
+ export declare const getKeyframeDisplayOffset: ({ propStatus, keyframeDisplayOffset, }: {
8
+ propStatus: CanUpdateSequencePropStatus | null | undefined;
9
+ keyframeDisplayOffset: number;
10
+ }) => number;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getTimelineKeyframes = exports.getComputedStatusLabel = void 0;
3
+ exports.getKeyframeDisplayOffset = exports.getTimelineKeyframes = exports.getComputedStatusLabel = void 0;
4
4
  const getComputedStatusLabel = (propStatus) => {
5
5
  if (propStatus.status === 'computed') {
6
6
  return 'computed';
@@ -16,12 +16,25 @@ const getTimelineKeyframes = (propStatus, keyframeDisplayOffset = 0) => {
16
16
  return [];
17
17
  }
18
18
  const { keyframes } = propStatus;
19
- if (keyframeDisplayOffset === 0) {
19
+ const resolvedKeyframeDisplayOffset = (0, exports.getKeyframeDisplayOffset)({
20
+ propStatus,
21
+ keyframeDisplayOffset,
22
+ });
23
+ if (resolvedKeyframeDisplayOffset === 0) {
20
24
  return keyframes;
21
25
  }
22
26
  return keyframes.map((keyframe) => ({
23
27
  ...keyframe,
24
- frame: keyframe.frame + keyframeDisplayOffset,
28
+ frame: keyframe.frame + resolvedKeyframeDisplayOffset,
25
29
  }));
26
30
  };
27
31
  exports.getTimelineKeyframes = getTimelineKeyframes;
32
+ const getKeyframeDisplayOffset = ({ propStatus, keyframeDisplayOffset, }) => {
33
+ return (keyframeDisplayOffset +
34
+ ((propStatus === null || propStatus === void 0 ? void 0 : propStatus.status) === 'keyframed' || (propStatus === null || propStatus === void 0 ? void 0 : propStatus.status) === 'static'
35
+ ? propStatus.keyframeDisplayOffsetAdjustment === null
36
+ ? 0
37
+ : propStatus.keyframeDisplayOffsetAdjustment
38
+ : 0));
39
+ };
40
+ exports.getKeyframeDisplayOffset = getKeyframeDisplayOffset;
@@ -4,6 +4,7 @@ exports.getPasteKeyframeTarget = exports.isKeyframeValueCompatible = exports.get
4
4
  const studio_shared_1 = require("@remotion/studio-shared");
5
5
  const remotion_1 = require("remotion");
6
6
  const find_track_for_node_path_info_1 = require("./find-track-for-node-path-info");
7
+ const get_timeline_keyframes_1 = require("./get-timeline-keyframes");
7
8
  const parse_keyframe_field_from_node_path_1 = require("./parse-keyframe-field-from-node-path");
8
9
  const getKeyframeClipboardFieldType = ({ schema, fieldKey, }) => {
9
10
  const field = remotion_1.Internals.getFlatSchemaWithAllKeys(schema)[fieldKey];
@@ -68,7 +69,10 @@ const resolveKeyframeField = ({ selection, sequences, overrideIdsToNodePaths, pr
68
69
  fieldKey: identity.fieldKey,
69
70
  }),
70
71
  propStatus: sequencePropStatus,
71
- keyframeDisplayOffset: track.keyframeDisplayOffset,
72
+ keyframeDisplayOffset: (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
73
+ propStatus: sequencePropStatus,
74
+ keyframeDisplayOffset: track.keyframeDisplayOffset,
75
+ }),
72
76
  };
73
77
  }
74
78
  const effect = track.sequence.effects[identity.effectIndex];
@@ -93,7 +97,10 @@ const resolveKeyframeField = ({ selection, sequences, overrideIdsToNodePaths, pr
93
97
  fieldKey: identity.fieldKey,
94
98
  }),
95
99
  propStatus: effectPropStatus,
96
- keyframeDisplayOffset: track.keyframeDisplayOffset,
100
+ keyframeDisplayOffset: (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
101
+ propStatus: effectPropStatus,
102
+ keyframeDisplayOffset: track.keyframeDisplayOffset,
103
+ }),
97
104
  };
98
105
  };
99
106
  const areResolvedFieldsEqual = (first, second) => {
@@ -13,21 +13,21 @@ const useOpenSequenceInApps = (sequence) => {
13
13
  const { previewServerState } = (0, react_1.useContext)(client_id_1.StudioServerConnectionCtx);
14
14
  const previewConnected = previewServerState.type === 'connected';
15
15
  const { resolvedLocation: originalLocation } = (0, use_resolved_stack_react_to_change_1.useResolveStackAndReactToChange)(sequence.getStack, (_b = (_a = sequence.controls) === null || _a === void 0 ? void 0 : _a.overrideId) !== null && _b !== void 0 ? _b : sequence.id);
16
- const editorPickerAvailable = (0, use_default_editor_info_1.canUseEditorPicker)(previewConnected);
17
- const editorInfo = (0, use_default_editor_info_1.useDefaultEditorInfo)(editorPickerAvailable);
18
- const codingAgentInfo = (0, use_default_editor_info_1.useDefaultCodingAgentInfo)(editorPickerAvailable);
19
- const canOpenInEditor = (0, react_1.useMemo)(() => Boolean(window.remotion_editorName && previewConnected && originalLocation), [originalLocation, previewConnected]);
16
+ const { canConfigureApps, canOpenInEditor: editorAvailable, defaultEditorId, editorInfo, } = (0, use_default_editor_info_1.useEditorOpening)(previewConnected);
17
+ const codingAgentInfo = (0, use_default_editor_info_1.useDefaultCodingAgentInfo)(canConfigureApps);
18
+ const canOpenInEditor = (0, react_1.useMemo)(() => Boolean(editorAvailable && originalLocation), [editorAvailable, originalLocation]);
20
19
  const openInEditor = (0, react_1.useCallback)(async (editorId) => {
21
- if (!canOpenInEditor || !originalLocation) {
20
+ const resolvedEditorId = editorId !== null && editorId !== void 0 ? editorId : defaultEditorId;
21
+ if (!canOpenInEditor || !originalLocation || !resolvedEditorId) {
22
22
  return;
23
23
  }
24
24
  try {
25
- await (0, open_in_editor_1.openOriginalPositionInEditor)(originalLocation, editorId);
25
+ await (0, open_in_editor_1.openOriginalPositionInEditor)(originalLocation, resolvedEditorId);
26
26
  }
27
27
  catch (err) {
28
28
  (0, NotificationCenter_1.showNotification)(err.message, 2000);
29
29
  }
30
- }, [canOpenInEditor, originalLocation]);
30
+ }, [canOpenInEditor, defaultEditorId, originalLocation]);
31
31
  const openInCodingAgent = (0, react_1.useCallback)(async (codingAgentId, codingAgentName, contextForAgents) => {
32
32
  try {
33
33
  const response = await (0, open_in_editor_1.openInCodingAgent)(codingAgentId, contextForAgents);
@@ -41,7 +41,7 @@ const useOpenSequenceInApps = (sequence) => {
41
41
  }, []);
42
42
  return {
43
43
  canOpenInEditor,
44
- canConfigureApps: editorPickerAvailable,
44
+ canConfigureApps,
45
45
  codingAgentInfo,
46
46
  editorInfo,
47
47
  openInCodingAgent,
@@ -10,6 +10,7 @@ const timeline_layout_1 = require("../../helpers/timeline-layout");
10
10
  const call_move_keyframe_1 = require("./call-move-keyframe");
11
11
  const find_track_for_node_path_info_1 = require("./find-track-for-node-path-info");
12
12
  const get_bounded_keyframe_drag_delta_1 = require("./get-bounded-keyframe-drag-delta");
13
+ const get_timeline_keyframes_1 = require("./get-timeline-keyframes");
13
14
  const parse_keyframe_field_from_node_path_1 = require("./parse-keyframe-field-from-node-path");
14
15
  const TimelineKeyframeDragState_1 = require("./TimelineKeyframeDragState");
15
16
  const TimelineSelection_1 = require("./TimelineSelection");
@@ -101,7 +102,7 @@ const getTimelineSelectionsAfterEasingKeyframeDrag = ({ delta, selections, targe
101
102
  exports.getTimelineSelectionsAfterEasingKeyframeDrag = getTimelineSelectionsAfterEasingKeyframeDrag;
102
103
  const getCodeValueForTarget = ({ propStatuses, nodePath, }) => propStatuses[remotion_1.Internals.makeSequencePropsSubscriptionKey(nodePath)];
103
104
  const getTimelineKeyframeDragTarget = ({ propStatuses, displayFrame, nodePathInfo, overrideIdsToNodePaths, sequences, }) => {
104
- var _a, _b;
105
+ var _a, _b, _c;
105
106
  const field = (0, parse_keyframe_field_from_node_path_1.parseKeyframeFieldFromNodePath)(nodePathInfo.auxiliaryKeys);
106
107
  if (field === null) {
107
108
  return null;
@@ -115,7 +116,6 @@ const getTimelineKeyframeDragTarget = ({ propStatuses, displayFrame, nodePathInf
115
116
  if (!(sequence === null || sequence === void 0 ? void 0 : sequence.controls)) {
116
117
  return null;
117
118
  }
118
- const sourceFrame = displayFrame - ((_b = track === null || track === void 0 ? void 0 : track.keyframeDisplayOffset) !== null && _b !== void 0 ? _b : 0);
119
119
  const nodePath = nodePathInfo.sequenceSubscriptionKey;
120
120
  const fileName = nodePath.absolutePath;
121
121
  const sequenceStatus = getCodeValueForTarget({ propStatuses, nodePath });
@@ -132,7 +132,12 @@ const getTimelineKeyframeDragTarget = ({ propStatuses, displayFrame, nodePathInf
132
132
  if ((effectPropStatus === null || effectPropStatus === void 0 ? void 0 : effectPropStatus.status) !== 'keyframed') {
133
133
  return null;
134
134
  }
135
- if (!effectPropStatus.keyframes.some((keyframe) => keyframe.frame === sourceFrame)) {
135
+ const effectSourceFrame = displayFrame -
136
+ (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
137
+ propStatus: effectPropStatus,
138
+ keyframeDisplayOffset: (_b = track === null || track === void 0 ? void 0 : track.keyframeDisplayOffset) !== null && _b !== void 0 ? _b : 0,
139
+ });
140
+ if (!effectPropStatus.keyframes.some((keyframe) => keyframe.frame === effectSourceFrame)) {
136
141
  return null;
137
142
  }
138
143
  return {
@@ -145,13 +150,18 @@ const getTimelineKeyframeDragTarget = ({ propStatuses, displayFrame, nodePathInf
145
150
  nodePathInfo,
146
151
  propStatus: effectPropStatus,
147
152
  schema: effect.schema,
148
- sourceFrame,
153
+ sourceFrame: effectSourceFrame,
149
154
  };
150
155
  }
151
156
  const sequencePropStatus = sequenceStatus.props[field.fieldKey];
152
157
  if ((sequencePropStatus === null || sequencePropStatus === void 0 ? void 0 : sequencePropStatus.status) !== 'keyframed') {
153
158
  return null;
154
159
  }
160
+ const sourceFrame = displayFrame -
161
+ (0, get_timeline_keyframes_1.getKeyframeDisplayOffset)({
162
+ propStatus: sequencePropStatus,
163
+ keyframeDisplayOffset: (_c = track === null || track === void 0 ? void 0 : track.keyframeDisplayOffset) !== null && _c !== void 0 ? _c : 0,
164
+ });
155
165
  if (!sequencePropStatus.keyframes.some((keyframe) => keyframe.frame === sourceFrame)) {
156
166
  return null;
157
167
  }
@@ -3,18 +3,25 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ClickableFileName = void 0;
4
4
  const jsx_runtime_1 = require("react/jsx-runtime");
5
5
  const react_1 = require("react");
6
+ const client_id_1 = require("../../helpers/client-id");
6
7
  const colors_1 = require("../../helpers/colors");
7
8
  const open_in_editor_1 = require("../../helpers/open-in-editor");
8
9
  const NotificationCenter_1 = require("../Notifications/NotificationCenter");
9
10
  const Fieldset_1 = require("../RenderModal/SchemaEditor/Fieldset");
10
11
  const source_attribution_1 = require("../Timeline/TimelineStack/source-attribution");
12
+ const use_default_editor_info_1 = require("../use-default-editor-info");
11
13
  const container = {
12
14
  paddingLeft: (0, Fieldset_1.getSchemaEditorFieldsetPadding)(),
13
15
  paddingTop: (0, Fieldset_1.getSchemaEditorFieldsetPadding)() / 2,
14
16
  };
15
17
  const ClickableFileName = ({ originalFileName, }) => {
16
18
  const [titleHovered, setTitleHovered] = (0, react_1.useState)(false);
17
- const hoverEffect = titleHovered && originalFileName.type === 'loaded';
19
+ const { previewServerState } = (0, react_1.useContext)(client_id_1.StudioServerConnectionCtx);
20
+ const { canOpenInEditor, defaultEditorId } = (0, use_default_editor_info_1.useEditorOpening)(previewServerState.type === 'connected');
21
+ const canOpen = canOpenInEditor &&
22
+ defaultEditorId !== null &&
23
+ originalFileName.type === 'loaded';
24
+ const hoverEffect = titleHovered && canOpen;
18
25
  const onTitlePointerEnter = (0, react_1.useCallback)(() => {
19
26
  setTitleHovered(true);
20
27
  }, []);
@@ -24,19 +31,19 @@ const ClickableFileName = ({ originalFileName, }) => {
24
31
  const style = (0, react_1.useMemo)(() => {
25
32
  return {
26
33
  fontSize: 12,
27
- cursor: originalFileName.type === 'loaded' ? 'pointer' : undefined,
34
+ cursor: canOpen ? 'pointer' : undefined,
28
35
  borderBottom: hoverEffect ? colors_1.BORDER_WHITE : 'none',
29
36
  color: hoverEffect ? colors_1.WHITE_HEX : colors_1.LIGHT_COLOR,
30
37
  };
31
- }, [originalFileName, hoverEffect]);
38
+ }, [canOpen, hoverEffect]);
32
39
  const onClick = (0, react_1.useCallback)(() => {
33
- if (originalFileName.type !== 'loaded') {
40
+ if (originalFileName.type !== 'loaded' || !canOpen || !defaultEditorId) {
34
41
  return;
35
42
  }
36
- (0, open_in_editor_1.openOriginalPositionInEditor)(originalFileName.originalFileName, null).catch((err) => {
43
+ (0, open_in_editor_1.openOriginalPositionInEditor)(originalFileName.originalFileName, defaultEditorId).catch((err) => {
37
44
  (0, NotificationCenter_1.showNotification)(err.message, 2000);
38
45
  });
39
- }, [originalFileName]);
46
+ }, [canOpen, defaultEditorId, originalFileName]);
40
47
  return (jsx_runtime_1.jsx("div", { style: container, children: jsx_runtime_1.jsx("span", { style: style, onClick: onClick, onPointerEnter: onTitlePointerEnter, onPointerLeave: onTitlePointerLeave, children: originalFileName.type === 'loaded'
41
48
  ? (0, source_attribution_1.getOriginalSourceAttribution)(originalFileName.originalFileName)
42
49
  : originalFileName.type === 'loading'
@@ -1,8 +1,9 @@
1
+ import type { EditorPickerId } from '@remotion/studio-shared';
1
2
  import type { SetStateAction } from 'react';
2
3
  import type { ResolvedStackLocation } from 'remotion';
3
4
  import type { ModalState } from '../state/modals';
4
5
  import type { ComboboxValue } from './NewComposition/ComboBox';
5
- export declare const getCompositionMenuItems: ({ composition, connectionStatus, resolvedLocation, setSelectedModal, closeMenu, readOnlyStudio, includeCompositionManagementItems, }: {
6
+ export declare const getCompositionMenuItems: ({ composition, connectionStatus, resolvedLocation, setSelectedModal, closeMenu, readOnlyStudio, includeCompositionManagementItems, editorId, editorName, }: {
6
7
  composition: import("remotion").AnyComposition | null;
7
8
  connectionStatus: "connected" | "disconnected" | "init";
8
9
  resolvedLocation: ResolvedStackLocation | null;
@@ -10,6 +11,8 @@ export declare const getCompositionMenuItems: ({ composition, connectionStatus,
10
11
  closeMenu: () => void;
11
12
  readOnlyStudio: boolean;
12
13
  includeCompositionManagementItems: boolean;
14
+ editorId: EditorPickerId | null;
15
+ editorName: string | null;
13
16
  }) => ComboboxValue[];
14
17
  export declare const getCompositionContextMenuItems: (args: Omit<{
15
18
  composition: import("remotion").AnyComposition | null;
@@ -19,6 +22,8 @@ export declare const getCompositionContextMenuItems: (args: Omit<{
19
22
  closeMenu: () => void;
20
23
  readOnlyStudio: boolean;
21
24
  includeCompositionManagementItems: boolean;
25
+ editorId: EditorPickerId | null;
26
+ editorName: string | null;
22
27
  }, "includeCompositionManagementItems"> & {
23
28
  readonly includeCompositionManagementItems: boolean;
24
29
  }) => ComboboxValue[];
@@ -6,13 +6,15 @@ const format_file_location_1 = require("../helpers/format-file-location");
6
6
  const open_in_editor_1 = require("../helpers/open-in-editor");
7
7
  const NotificationCenter_1 = require("./Notifications/NotificationCenter");
8
8
  const open_in_new_window_1 = require("./open-in-new-window");
9
- const getCompositionMenuItems = ({ composition, connectionStatus, resolvedLocation, setSelectedModal, closeMenu, readOnlyStudio, includeCompositionManagementItems, }) => {
10
- const editorName = window.remotion_editorName;
9
+ const getCompositionMenuItems = ({ composition, connectionStatus, resolvedLocation, setSelectedModal, closeMenu, readOnlyStudio, includeCompositionManagementItems, editorId, editorName, }) => {
11
10
  const fileLocation = (0, format_file_location_1.formatFileLocation)({
12
11
  location: resolvedLocation,
13
12
  root: window.remotion_cwd,
14
13
  });
15
- const showInEditorDisabled = !composition || connectionStatus !== 'connected' || !resolvedLocation;
14
+ const showInEditorDisabled = !editorId ||
15
+ !composition ||
16
+ connectionStatus !== 'connected' ||
17
+ !resolvedLocation;
16
18
  const openComponentInEditorDisabled = showInEditorDisabled || !(resolvedLocation === null || resolvedLocation === void 0 ? void 0 : resolvedLocation.source);
17
19
  const copyFileLocationDisabled = !composition || !fileLocation;
18
20
  return [
@@ -24,11 +26,11 @@ const getCompositionMenuItems = ({ composition, connectionStatus, resolvedLocati
24
26
  leftItem: null,
25
27
  onClick: async () => {
26
28
  closeMenu();
27
- if (!composition || !resolvedLocation) {
29
+ if (!composition || !resolvedLocation || !editorId) {
28
30
  return;
29
31
  }
30
32
  try {
31
- await (0, open_in_editor_1.openOriginalPositionInEditor)(resolvedLocation, null);
33
+ await (0, open_in_editor_1.openOriginalPositionInEditor)(resolvedLocation, editorId);
32
34
  }
33
35
  catch (err) {
34
36
  (0, NotificationCenter_1.showNotification)(err.message, 2000);
@@ -49,13 +51,14 @@ const getCompositionMenuItems = ({ composition, connectionStatus, resolvedLocati
49
51
  leftItem: null,
50
52
  onClick: async () => {
51
53
  closeMenu();
52
- if (!composition || !(resolvedLocation === null || resolvedLocation === void 0 ? void 0 : resolvedLocation.source)) {
54
+ if (!composition || !(resolvedLocation === null || resolvedLocation === void 0 ? void 0 : resolvedLocation.source) || !editorId) {
53
55
  return;
54
56
  }
55
57
  try {
56
58
  await (0, open_in_editor_1.openCompositionComponentInEditor)({
57
59
  compositionFile: resolvedLocation.source,
58
60
  compositionId: composition.id,
61
+ editorId,
59
62
  });
60
63
  }
61
64
  catch (err) {
@@ -1,12 +1,15 @@
1
+ import type { EditorPickerId } from '@remotion/studio-shared';
1
2
  import type { SetStateAction } from 'react';
2
3
  import type { ResolvedStackLocation } from 'remotion';
3
4
  import type { ModalState } from '../state/modals';
4
5
  import type { ComboboxValue } from './NewComposition/ComboBox';
5
- export declare const getFolderMenuItems: ({ closeMenu, connectionStatus, folder, readOnlyStudio, resolvedLocation, setSelectedModal, }: {
6
+ export declare const getFolderMenuItems: ({ closeMenu, connectionStatus, folder, readOnlyStudio, resolvedLocation, setSelectedModal, editorId, editorName, }: {
6
7
  closeMenu: () => void;
7
8
  connectionStatus: "connected" | "disconnected" | "init";
8
9
  folder: import("remotion").TFolder;
9
10
  readOnlyStudio: boolean;
10
11
  resolvedLocation: ResolvedStackLocation | null;
11
12
  setSelectedModal: (value: SetStateAction<ModalState | null>) => void;
13
+ editorId: EditorPickerId | null;
14
+ editorName: string | null;
12
15
  }) => ComboboxValue[];
@@ -6,8 +6,7 @@ const format_file_location_1 = require("../helpers/format-file-location");
6
6
  const get_folder_id_1 = require("../helpers/get-folder-id");
7
7
  const open_in_editor_1 = require("../helpers/open-in-editor");
8
8
  const NotificationCenter_1 = require("./Notifications/NotificationCenter");
9
- const getFolderMenuItems = ({ closeMenu, connectionStatus, folder, readOnlyStudio, resolvedLocation, setSelectedModal, }) => {
10
- const editorName = window.remotion_editorName;
9
+ const getFolderMenuItems = ({ closeMenu, connectionStatus, folder, readOnlyStudio, resolvedLocation, setSelectedModal, editorId, editorName, }) => {
11
10
  const folderId = (0, get_folder_id_1.getFolderId)({
12
11
  folderName: folder.name,
13
12
  parentName: folder.parent,
@@ -16,7 +15,7 @@ const getFolderMenuItems = ({ closeMenu, connectionStatus, folder, readOnlyStudi
16
15
  location: resolvedLocation,
17
16
  root: window.remotion_cwd,
18
17
  });
19
- const showInEditorDisabled = connectionStatus !== 'connected' || !resolvedLocation;
18
+ const showInEditorDisabled = !editorId || connectionStatus !== 'connected' || !resolvedLocation;
20
19
  const copyFileLocationDisabled = !fileLocation;
21
20
  const codemodDisabled = readOnlyStudio || !folder.stack;
22
21
  return [
@@ -28,11 +27,11 @@ const getFolderMenuItems = ({ closeMenu, connectionStatus, folder, readOnlyStudi
28
27
  leftItem: null,
29
28
  onClick: async () => {
30
29
  closeMenu();
31
- if (!resolvedLocation) {
30
+ if (!resolvedLocation || !editorId) {
32
31
  return;
33
32
  }
34
33
  try {
35
- await (0, open_in_editor_1.openOriginalPositionInEditor)(resolvedLocation, null);
34
+ await (0, open_in_editor_1.openOriginalPositionInEditor)(resolvedLocation, editorId);
36
35
  }
37
36
  catch (err) {
38
37
  (0, NotificationCenter_1.showNotification)(err.message, 2000);
@@ -11,7 +11,7 @@ export declare const getOpenInMenuItems: ({ codingAgentInfo, editorDisabled, edi
11
11
  readonly fileManagerDisabled: boolean;
12
12
  readonly folder: boolean;
13
13
  readonly location: OriginalPosition | null;
14
- readonly onConfigureApps: () => void;
14
+ readonly onConfigureApps: (() => void) | null;
15
15
  readonly onOpenInCodingAgent: (codingAgentId: "claude-code" | "codex" | "copilot" | "cursor", codingAgentName: string) => void;
16
16
  readonly onOpenInEditor: (editorId: EditorPickerId) => void;
17
17
  readonly onOpenInFileExplorer: () => void;
@@ -174,20 +174,22 @@ const getOpenInMenuItems = ({ codingAgentInfo, editorDisabled, editorInfo, exclu
174
174
  ...systemApps,
175
175
  ]
176
176
  : []),
177
- ...(hasCategorizedApps || systemApps.length > 0
177
+ ...(onConfigureApps && (hasCategorizedApps || systemApps.length > 0)
178
178
  ? [{ type: 'divider', id: 'open-in-settings-divider' }]
179
179
  : []),
180
- {
181
- id: 'change-default-apps',
182
- keyHint: null,
183
- label: jsx_runtime_1.jsx("span", { style: menuLabel, children: "Change default apps..." }),
184
- leftItem: null,
185
- onClick: onConfigureApps,
186
- quickSwitcherLabel: null,
187
- subMenu: null,
188
- type: 'item',
189
- value: 'change-default-apps',
190
- },
191
- ];
180
+ onConfigureApps
181
+ ? {
182
+ id: 'change-default-apps',
183
+ keyHint: null,
184
+ label: jsx_runtime_1.jsx("span", { style: menuLabel, children: "Change default apps..." }),
185
+ leftItem: null,
186
+ onClick: onConfigureApps,
187
+ quickSwitcherLabel: null,
188
+ subMenu: null,
189
+ type: 'item',
190
+ value: 'change-default-apps',
191
+ }
192
+ : null,
193
+ ].filter(no_react_1.NoReactInternals.truthy);
192
194
  };
193
195
  exports.getOpenInMenuItems = getOpenInMenuItems;