@writepanda/mcp 1.62.0 → 1.66.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/bin/server.mjs +59 -35
  2. package/package.json +1 -1
package/bin/server.mjs CHANGED
@@ -575,7 +575,7 @@ const TOOLS = [
575
575
  command: "project.open",
576
576
  },
577
577
 
578
- // ── compose: clips, motion graphics, FX, lower-thirds ──────────
578
+ // ── compose: clips, motion graphics, FX ────────────────────────
579
579
  {
580
580
  name: "project_add_clip",
581
581
  description:
@@ -786,54 +786,71 @@ const TOOLS = [
786
786
  src: { type: "string", description: "Direct path/URL (alternative to fxId)" },
787
787
  atMs: { type: "number" },
788
788
  durationMs: { type: "number", description: "Default 2500ms for bundled FX" },
789
+ speed: {
790
+ type: "number",
791
+ description:
792
+ "Playback-speed multiplier for the looping FX (0.25-4, default 1). 2 = twice as fast, 0.5 = half. Speeds up / slows down a film burn, light leak, etc. without re-rendering.",
793
+ },
789
794
  expectedRevision: { type: "number" },
790
795
  },
791
796
  required: ["atMs"],
792
797
  },
793
798
  command: "project.add-fx",
794
799
  },
800
+ {
801
+ name: "project_add_transition",
802
+ description:
803
+ "Place a transition at a cut between two clips. Drops a bundled transition overlay (a full-frame transparent WebM that goes opaque at its midpoint) CENTERED on atMs, so the opaque peak masks the cut and reads as a scene change. No render step. Pass atMs = the cut time (a clip boundary from project_read). Ids (asset_list_transitions): fade-black, fade-white, flash, light-sweep, film-burn, glitch.",
804
+ inputSchema: {
805
+ type: "object",
806
+ properties: {
807
+ id: { type: "string" },
808
+ path: { type: "string" },
809
+ transitionId: { type: "string", description: "Bundled id, e.g. fade-black. From asset_list_transitions." },
810
+ file: { type: "string", description: "Custom transition video (path / file:// URL). Use instead of transitionId." },
811
+ atMs: { type: "number", description: "Edited-timeline CUT time to center the transition on." },
812
+ durationMs: { type: "number", description: "Total length. Default 1000 (native length of the bundled set)." },
813
+ expectedRevision: { type: "number" },
814
+ },
815
+ required: ["atMs"],
816
+ },
817
+ command: "project.add-transition",
818
+ },
795
819
  {
796
820
  name: "project_add_lower_third",
797
- description: "Drop a lower-third name plate onto the timeline.",
821
+ description:
822
+ "One-call lower third: renders an lt-* nameplate motion template (hyperframes) with your name/title and places it on the timeline as a transparent overlay at atMs. ASYNC — returns { jobId, outputPath }; call job_wait — it resolves once the region is PLACED (result: { path, revision, outputPath, durationMs }), no separate project_add_motion_graphic call needed. Designs (see motion_list, category lower-third): lt-vox-marker (default, highlighter swipe), lt-broadcast-bar (news chyron), lt-glass-card (frosted), lt-kinetic-stack (bold word-by-word), lt-minimal-line (editorial), lt-corner-plate (documentary bracket + kicker slot), lt-accent-slab (knockout name), lt-avatar-pill (creator pill), lt-typewriter-tag (mono typing), lt-gradient-sweep (gradient glow).",
798
823
  inputSchema: {
799
824
  type: "object",
800
825
  properties: {
801
826
  id: { type: "string" },
802
827
  path: { type: "string" },
803
- content: { type: "string", description: "Primary text (name)" },
804
- subtitle: { type: "string", description: "Secondary text (title)" },
805
- atMs: { type: "number" },
806
- durationMs: { type: "number", description: "Default 5000ms" },
807
- designType: {
828
+ name: { type: "string", description: "Primary text (person/brand name)" },
829
+ title: { type: "string", description: "Secondary line (role / handle / tagline)" },
830
+ templateId: {
808
831
  type: "string",
809
- description:
810
- "slash-reveal | center-stack | split-horizontal | name-bar | border-frame | minimal-underline | box-reveal | corner-brackets. Default: slash-reveal.",
832
+ description: "lt-* design id. Default lt-vox-marker.",
811
833
  },
812
- accentColor: { type: "string", description: "Hex accent/background color" },
813
- textColor: { type: "string", description: "Hex text color. Default #ffffff" },
814
- backgroundColor: {
834
+ atMs: { type: "number", description: "Edited timeline time" },
835
+ aspectRatio: {
815
836
  type: "string",
816
- description: "Hex background fill. Default matches accentColor",
837
+ description: "16:9 | 9:16 | 1:1. Default 16:9 — match the project's aspect.",
817
838
  },
818
- backgroundRadius: {
819
- type: "number",
820
- description: "Corner radius in pixels. Default 8",
839
+ slots: {
840
+ type: "object",
841
+ description:
842
+ "Optional extra slot overrides (colors like accentColor/inkColor, or kicker for lt-corner-plate). Keys from motion_list. name/title args win over same-key entries.",
821
843
  },
822
- fontSize: { type: "number", description: "Primary text font size in px. Default 28" },
823
- fontFamily: { type: "string", description: "CSS font family name. Default Inter" },
824
844
  soundUrl: {
825
845
  type: "string",
826
846
  description:
827
- 'SFX played when the lower third enters. Bundled id (bundled:sound/<id>). Default bundled:sound/mouse-click. Pass "none" for silent.',
828
- },
829
- soundVolume: {
830
- type: "number",
831
- description: "Sound volume 0–1. Default 0.8.",
847
+ 'SFX on enter. Bundled id (bundled:sound/<id>). Default bundled:sound/mouse-click. Pass "none" for silent.',
832
848
  },
849
+ soundVolume: { type: "number", description: "Sound volume 0–1. Default 1." },
833
850
  anchorSourceMs: {
834
851
  type: "number",
835
852
  description:
836
- "Anchor the lower third to a SOURCE-time moment. Pass when atMs was derived from a transcript word's startMs — the lower third re-anchors automatically on subsequent transcript edits. Without it, the lower third drifts after any trim. Omit for free-floating placement.",
853
+ "Anchor to a SOURCE-time moment. Pass when atMs comes from a transcript word's startMs so the region survives later trims.",
837
854
  },
838
855
  anchorSourceEndMs: {
839
856
  type: "number",
@@ -841,7 +858,7 @@ const TOOLS = [
841
858
  },
842
859
  expectedRevision: { type: "number" },
843
860
  },
844
- required: ["content", "atMs"],
861
+ required: ["name", "atMs"],
845
862
  },
846
863
  command: "project.add-lower-third",
847
864
  },
@@ -893,7 +910,7 @@ const TOOLS = [
893
910
  {
894
911
  name: "project_set_region_sound",
895
912
  description:
896
- 'Set or clear the sound effect on an existing region (zoom / motionGraphic / lowerThird / fx). Use to swap the default zoom swoosh, add a ding to a motion graphic, or mute a lower-third click. Pass soundUrl="none" to clear.',
913
+ 'Set or clear the sound effect on an existing region (zoom / motionGraphic / fx). Use to swap the default zoom swoosh, add a ding to a motion graphic, or mute an effect sound. Pass soundUrl="none" to clear.',
897
914
  inputSchema: {
898
915
  type: "object",
899
916
  properties: {
@@ -902,7 +919,7 @@ const TOOLS = [
902
919
  regionId: { type: "string", description: "Target region id" },
903
920
  regionType: {
904
921
  type: "string",
905
- enum: ["zoom", "motionGraphic", "lowerThird", "fx"],
922
+ enum: ["zoom", "motionGraphic", "fx"],
906
923
  description: "Region kind that owns the id",
907
924
  },
908
925
  soundUrl: {
@@ -1117,7 +1134,7 @@ const TOOLS = [
1117
1134
  {
1118
1135
  name: "project_move_clip",
1119
1136
  description:
1120
- "Reorder a clip on the main track. `clipId` identifies the clip; `toIndex` is its new 0-based position after the move. Project-level regions (zooms, trims, speeds, annotations, FX, lower-thirds, media overlays, clip transforms) automatically migrate to follow their original clips so the user-perceived edits stay attached to the same content — a zoom that was 'into the explanation in clip 2' is still pointing at the same explanation after clip 2 moves to position 0. Per-clip transcripts ride on the clips themselves and don't need separate migration.",
1137
+ "Reorder a clip on the main track. `clipId` identifies the clip; `toIndex` is its new 0-based position after the move. Project-level regions (zooms, trims, speeds, annotations, FX, media overlays, clip transforms) automatically migrate to follow their original clips so the user-perceived edits stay attached to the same content — a zoom that was 'into the explanation in clip 2' is still pointing at the same explanation after clip 2 moves to position 0. Per-clip transcripts ride on the clips themselves and don't need separate migration.",
1121
1138
  inputSchema: {
1122
1139
  type: "object",
1123
1140
  properties: {
@@ -1140,7 +1157,7 @@ const TOOLS = [
1140
1157
  {
1141
1158
  name: "project_remove_region",
1142
1159
  description:
1143
- "Delete an existing region (zoom, trim, speed, annotation, fx, lower-third, overlay, clip-transform, audio-overlay) by its id. Use project_read to find region ids — visual regions live under editor.*Regions; audio overlays live under audioOverlays[]. If the region belongs to a link group (designed-segment pair: a clip-transform parking the camera into one half + the panel motion-graphic on the other half), deleting either half also removes its peer so the pair stays coherent. Returns the updated project.",
1160
+ "Delete an existing region (zoom, trim, speed, annotation, fx, overlay, clip-transform, audio-overlay) by its id. Use project_read to find region ids — visual regions live under editor.*Regions; audio overlays live under audioOverlays[]. If the region belongs to a link group (designed-segment pair: a clip-transform parking the camera into one half + the panel motion-graphic on the other half), deleting either half also removes its peer so the pair stays coherent. Returns the updated project.",
1144
1161
  inputSchema: {
1145
1162
  type: "object",
1146
1163
  properties: {
@@ -1149,7 +1166,7 @@ const TOOLS = [
1149
1166
  regionType: {
1150
1167
  type: "string",
1151
1168
  description:
1152
- "zoom | trim | speed | annotation | fx | lower-third | overlay | clip-transform | audio-overlay",
1169
+ "zoom | trim | speed | annotation | fx | overlay | clip-transform | audio-overlay",
1153
1170
  },
1154
1171
  regionId: { type: "string", description: "id of the region to delete" },
1155
1172
  expectedRevision: { type: "number" },
@@ -1180,7 +1197,7 @@ const TOOLS = [
1180
1197
  {
1181
1198
  name: "project_update_region",
1182
1199
  description:
1183
- "Patch fields on an existing region without replacing it. Accepts any subset of the region's own properties — only the supplied fields are changed, everything else is preserved. Works on zoom (depth, focusX, focusY), trim (startMs, endMs), speed (startMs, endMs, speed), lower-third (content, subtitle, atMs, durationMs, designType, accentColor, textColor, backgroundColor, backgroundRadius, fontSize, fontFamily), fx (atMs, durationMs), annotation, overlay, clip-transform (startMs, endMs, preset, transitionMs), and audio-overlay (startMs, endMs, sourceStartMs, volume — lets you drag-trim an audio overlay without removing it). Time shifts on a link-grouped region (e.g. one half of a designed segment) propagate to every peer in the group so the pair stays coherent.",
1200
+ "Patch fields on an existing region without replacing it. Accepts any subset of the region's own properties — only the supplied fields are changed, everything else is preserved. Works on zoom (depth, focusX, focusY), trim (startMs, endMs), speed (startMs, endMs, speed), fx (atMs, durationMs, opacity, blendMode, speed), annotation, overlay, clip-transform (startMs, endMs, preset, transitionMs), and audio-overlay (startMs, endMs, sourceStartMs, volume — lets you drag-trim an audio overlay without removing it). Time shifts on a link-grouped region (e.g. one half of a designed segment) propagate to every peer in the group so the pair stays coherent.",
1184
1201
  inputSchema: {
1185
1202
  type: "object",
1186
1203
  properties: {
@@ -1189,13 +1206,13 @@ const TOOLS = [
1189
1206
  regionType: {
1190
1207
  type: "string",
1191
1208
  description:
1192
- "zoom | trim | speed | annotation | fx | lower-third | overlay | clip-transform | audio-overlay",
1209
+ "zoom | trim | speed | annotation | fx | overlay | clip-transform | audio-overlay",
1193
1210
  },
1194
1211
  regionId: { type: "string", description: "id of the region to update" },
1195
1212
  patch: {
1196
1213
  type: "object",
1197
1214
  description:
1198
- "Fields to update (partial). E.g. { depth: 4 } to change zoom depth, { content: 'New Name' } on a lower-third, or { startMs: 2000, endMs: 15000, sourceStartMs: 4000 } to shift + trim an audio overlay (play seconds 4–17 of the source from the 2s mark on the timeline).",
1215
+ "Fields to update (partial). E.g. { depth: 4 } to change zoom depth, or { startMs: 2000, endMs: 15000, sourceStartMs: 4000 } to shift + trim an audio overlay (play seconds 4–17 of the source from the 2s mark on the timeline).",
1199
1216
  },
1200
1217
  expectedRevision: { type: "number" },
1201
1218
  },
@@ -2060,6 +2077,13 @@ const TOOLS = [
2060
2077
  inputSchema: { type: "object", properties: {} },
2061
2078
  command: "asset.list-fx",
2062
2079
  },
2080
+ {
2081
+ name: "asset_list_transitions",
2082
+ description:
2083
+ "List every bundled transition (id, title, category, durationSeconds). Use the id with project_add_transition, centered on a cut.",
2084
+ inputSchema: { type: "object", properties: {} },
2085
+ command: "asset.list-transitions",
2086
+ },
2063
2087
  {
2064
2088
  name: "asset_list_music",
2065
2089
  description:
@@ -2121,7 +2145,7 @@ const TOOLS = [
2121
2145
  {
2122
2146
  name: "export_start",
2123
2147
  description:
2124
- "Render the project to MP4 via the same Tier-3 PixiJS pipeline the editor's Export Video button uses (v1.24+ — convergence release). When an editor window is already open on the target project, the agent reuses it. Otherwise the agent spawns a hidden editor window for the duration of the render and closes it after. ASYNC — returns { jobId, outputPath }; call job_wait. Honours every region/style/caption/FX/lower-third/motion-graphic in the project. Video overlays (motion graphics added via project_add_motion_graphic) — opaque MP4 and transparent WebM/VP9+alpha — composite inline in the export pipeline; no extra call needed.",
2148
+ "Render the project to MP4 via the same Tier-3 PixiJS pipeline the editor's Export Video button uses (v1.24+ — convergence release). When an editor window is already open on the target project, the agent reuses it. Otherwise the agent spawns a hidden editor window for the duration of the render and closes it after. ASYNC — returns { jobId, outputPath }; call job_wait. Honours every region/style/caption/FX/motion-graphic in the project. Video overlays (motion graphics added via project_add_motion_graphic) — opaque MP4 and transparent WebM/VP9+alpha — composite inline in the export pipeline; no extra call needed.",
2125
2149
  inputSchema: {
2126
2150
  type: "object",
2127
2151
  properties: {
@@ -2348,7 +2372,7 @@ const TOOLS = [
2348
2372
  const server = new Server(
2349
2373
  {
2350
2374
  name: "pandastudio",
2351
- version: "1.58.0",
2375
+ version: "1.66.0",
2352
2376
  },
2353
2377
  {
2354
2378
  capabilities: {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@writepanda/mcp",
3
- "version": "1.62.0",
3
+ "version": "1.66.0",
4
4
  "description": "Model Context Protocol server for PandaStudio. Exposes the desktop video editor's automation surface to Cursor, Continue, Cline, Claude Desktop, and any MCP-compliant client.",
5
5
  "keywords": [
6
6
  "pandastudio",