@remotion/media 4.0.490 → 4.0.491

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.
@@ -1122,6 +1122,7 @@ var makeStableFramePool = () => {
1122
1122
  if (!context) {
1123
1123
  throw new Error("Could not create canvas context");
1124
1124
  }
1125
+ context.clearRect(0, 0, stableCanvas.width, stableCanvas.height);
1125
1126
  context.drawImage(canvas, 0, 0);
1126
1127
  let released = false;
1127
1128
  const stableFrame = {
@@ -1815,6 +1816,9 @@ class MediaPlayer {
1815
1816
  }
1816
1817
  const canDecode = await videoTrack.canDecode();
1817
1818
  if (!canDecode) {
1819
+ if (videoTrack.codec === "prores") {
1820
+ return { type: "cannot-decode-prores" };
1821
+ }
1818
1822
  return { type: "cannot-decode" };
1819
1823
  }
1820
1824
  if (this.isDisposalError()) {
@@ -2533,6 +2537,9 @@ var AudioForPreviewAssertedShowing = ({
2533
2537
  handleError(new Error(`No video or audio tracks found for ${preloadedSrc}.`), `No video or audio tracks found for ${preloadedSrc}, falling back to <Html5Audio>`);
2534
2538
  return;
2535
2539
  }
2540
+ if (result.type === "cannot-decode-prores") {
2541
+ throw new Error(`Encountered ProRes media for ${preloadedSrc}. But this should never happen, since you used the <Audio> tag. Please report this as a bug.`);
2542
+ }
2536
2543
  if (result.type === "success") {
2537
2544
  setMediaPlayerReady(true);
2538
2545
  setMediaDurationInSeconds(result.durationInSeconds);
@@ -3916,6 +3923,9 @@ var getSinks = async (src, logLevel, credentials, requestInit) => {
3916
3923
  }
3917
3924
  const canDecode = await videoTrack.canDecode();
3918
3925
  if (!canDecode) {
3926
+ if (videoTrack.codec === "prores") {
3927
+ return "cannot-decode-prores";
3928
+ }
3919
3929
  return "cannot-decode";
3920
3930
  }
3921
3931
  const sampleSink = new VideoSampleSink(videoTrack);
@@ -4174,6 +4184,12 @@ var extractFrameInternal = async ({
4174
4184
  if (video === "cannot-decode") {
4175
4185
  return { type: "cannot-decode", durationInSeconds: mediaDurationInSeconds };
4176
4186
  }
4187
+ if (video === "cannot-decode-prores") {
4188
+ return {
4189
+ type: "cannot-decode-prores",
4190
+ durationInSeconds: mediaDurationInSeconds
4191
+ };
4192
+ }
4177
4193
  if (video === "unknown-container-format") {
4178
4194
  return { type: "unknown-container-format" };
4179
4195
  }
@@ -4329,6 +4345,12 @@ var extractFrameAndAudio = async ({
4329
4345
  durationInSeconds: video.durationInSeconds
4330
4346
  };
4331
4347
  }
4348
+ if (video?.type === "cannot-decode-prores") {
4349
+ return {
4350
+ type: "cannot-decode-prores",
4351
+ durationInSeconds: video.durationInSeconds
4352
+ };
4353
+ }
4332
4354
  if (video?.type === "unknown-container-format") {
4333
4355
  return { type: "unknown-container-format" };
4334
4356
  }
@@ -4416,6 +4438,15 @@ var addBroadcastChannelListener = () => {
4416
4438
  window.remotion_broadcastChannel.postMessage(cannotDecodeResponse);
4417
4439
  return;
4418
4440
  }
4441
+ if (result.type === "cannot-decode-prores") {
4442
+ const cannotDecodeProresResponse = {
4443
+ type: "response-cannot-decode-prores",
4444
+ id: data.id,
4445
+ durationInSeconds: result.durationInSeconds
4446
+ };
4447
+ window.remotion_broadcastChannel.postMessage(cannotDecodeProresResponse);
4448
+ return;
4449
+ }
4419
4450
  if (result.type === "cannot-decode-alpha") {
4420
4451
  const cannotDecodeAlphaResponse = {
4421
4452
  type: "response-cannot-decode-alpha",
@@ -4562,6 +4593,14 @@ var extractFrameViaBroadcastChannel = async ({
4562
4593
  window.remotion_broadcastChannel.removeEventListener("message", onMessage);
4563
4594
  return;
4564
4595
  }
4596
+ if (data.type === "response-cannot-decode-prores") {
4597
+ resolve({
4598
+ type: "cannot-decode-prores",
4599
+ durationInSeconds: data.durationInSeconds
4600
+ });
4601
+ window.remotion_broadcastChannel.removeEventListener("message", onMessage);
4602
+ return;
4603
+ }
4565
4604
  if (data.type === "response-network-error") {
4566
4605
  resolve({ type: "network-error" });
4567
4606
  window.remotion_broadcastChannel.removeEventListener("message", onMessage);
@@ -4735,6 +4774,9 @@ var AudioForRendering = ({
4735
4774
  if (result.type === "cannot-decode-alpha") {
4736
4775
  throw new Error(`Cannot decode alpha component for ${src}, and 'disallowFallbackToHtml5Audio' was set. But this should never happen, since you used the <Audio> tag. Please report this as a bug.`);
4737
4776
  }
4777
+ if (result.type === "cannot-decode-prores") {
4778
+ throw new Error(`Encountered ProRes media for ${src}. But this should never happen, since you used the <Audio> tag. Please report this as a bug.`);
4779
+ }
4738
4780
  if (result.type === "network-error") {
4739
4781
  handleError(new Error(`Network error fetching ${src}.`), new Error(`Cannot render audio "${src}": Network error while fetching the audio (possibly CORS).`), `Network error fetching ${src}, falling back to <Html5Audio>`);
4740
4782
  return;
@@ -4973,6 +5015,19 @@ import {
4973
5015
  useVideoConfig as useVideoConfig3
4974
5016
  } from "remotion";
4975
5017
 
5018
+ // src/prores-error.ts
5019
+ var PRORES_DOCS_URL = "https://www.remotion.dev/docs/videos/prores";
5020
+ var proresDecoderNotEnabledMessage = (src) => {
5021
+ return `Cannot decode "${src}": it is encoded with Apple ProRes, which WebCodecs does not support natively. ` + `ProRes decoding is not enabled by default. Register the ProRes decoder by calling ` + `registerProresDecoder() from "@mediabunny/prores" in your entry point, before registerRoot(). ` + `See ${PRORES_DOCS_URL}. ` + `(This is required to decode a ProRes source for both preview and rendering — it is unrelated to exporting a video as ProRes.)`;
5022
+ };
5023
+
5024
+ class ProResDecoderNotEnabledError extends Error {
5025
+ constructor(src) {
5026
+ super(proresDecoderNotEnabledMessage(src));
5027
+ this.name = "ProResDecoderNotEnabledError";
5028
+ }
5029
+ }
5030
+
4976
5031
  // src/video/video-frame-cache.ts
4977
5032
  var cache = new Map;
4978
5033
  var cacheVideoFrame = (src, sourceCanvas) => {
@@ -5228,6 +5283,9 @@ var VideoForPreviewAssertedShowing = ({
5228
5283
  handleError(new Error(`Cannot decode ${preloadedSrc}.`), `Cannot decode ${preloadedSrc}, falling back to <OffthreadVideo>`);
5229
5284
  return;
5230
5285
  }
5286
+ if (result.type === "cannot-decode-prores") {
5287
+ throw new ProResDecoderNotEnabledError(preloadedSrc);
5288
+ }
5231
5289
  if (result.type === "no-tracks") {
5232
5290
  handleError(new Error(`No video or audio tracks found for ${preloadedSrc}.`), `No video or audio tracks found for ${preloadedSrc}, falling back to <OffthreadVideo>`);
5233
5291
  return;
@@ -5238,6 +5296,10 @@ var VideoForPreviewAssertedShowing = ({
5238
5296
  hasDrawnRealFrameRef.current = true;
5239
5297
  }
5240
5298
  }).catch((error) => {
5299
+ if (error instanceof ProResDecoderNotEnabledError) {
5300
+ onErrorRef.current?.(error);
5301
+ throw error;
5302
+ }
5241
5303
  const [action, errorToUse] = callOnErrorAndResolve({
5242
5304
  onError: onErrorRef.current,
5243
5305
  error,
@@ -5554,6 +5616,12 @@ var VideoForRendering = ({
5554
5616
  handleError(new Error(`Cannot decode ${src}.`), new Error(`Cannot render video "${src}": The video could not be decoded by the browser.`), `Cannot decode ${src}, falling back to <OffthreadVideo>`, result.durationInSeconds);
5555
5617
  return;
5556
5618
  }
5619
+ if (result.type === "cannot-decode-prores") {
5620
+ const proresError = new ProResDecoderNotEnabledError(src);
5621
+ onError?.(proresError);
5622
+ cancelRender3(proresError);
5623
+ return;
5624
+ }
5557
5625
  if (result.type === "cannot-decode-alpha") {
5558
5626
  handleError(new Error(`Cannot decode alpha component for ${src}.`), new Error(`Cannot render video "${src}": The alpha channel could not be decoded by the browser.`), `Cannot decode alpha component for ${src}, falling back to <OffthreadVideo>`, result.durationInSeconds);
5559
5627
  return;
@@ -10,6 +10,8 @@ export type MediaPlayerInitResult = {
10
10
  type: 'unknown-container-format';
11
11
  } | {
12
12
  type: 'cannot-decode';
13
+ } | {
14
+ type: 'cannot-decode-prores';
13
15
  } | {
14
16
  type: 'network-error';
15
17
  } | {
@@ -0,0 +1,4 @@
1
+ export declare const proresDecoderNotEnabledMessage: (src: string) => string;
2
+ export declare class ProResDecoderNotEnabledError extends Error {
3
+ constructor(src: string);
4
+ }
@@ -15,6 +15,10 @@ export type MessageFromMainTab = {
15
15
  type: 'response-cannot-decode';
16
16
  id: string;
17
17
  durationInSeconds: number | null;
18
+ } | {
19
+ type: 'response-cannot-decode-prores';
20
+ id: string;
21
+ durationInSeconds: number | null;
18
22
  } | {
19
23
  type: 'response-cannot-decode-alpha';
20
24
  id: string;
@@ -8,6 +8,9 @@ export type ExtractFrameViaBroadcastChannelResult = {
8
8
  } | {
9
9
  type: 'cannot-decode';
10
10
  durationInSeconds: number | null;
11
+ } | {
12
+ type: 'cannot-decode-prores';
13
+ durationInSeconds: number | null;
11
14
  } | {
12
15
  type: 'cannot-decode-alpha';
13
16
  durationInSeconds: number | null;
@@ -8,6 +8,9 @@ type ExtractFrameResult = {
8
8
  } | {
9
9
  type: 'cannot-decode';
10
10
  durationInSeconds: number | null;
11
+ } | {
12
+ type: 'cannot-decode-prores';
13
+ durationInSeconds: number | null;
11
14
  } | {
12
15
  type: 'cannot-decode-alpha';
13
16
  durationInSeconds: number | null;
@@ -7,7 +7,7 @@ type AudioSinks = {
7
7
  sampleSink: AudioSampleSink;
8
8
  };
9
9
  export type AudioSinkResult = AudioSinks | 'no-audio-track' | 'cannot-decode-audio' | 'unknown-container-format' | 'network-error';
10
- export type VideoSinkResult = VideoSinks | 'no-video-track' | 'cannot-decode' | 'cannot-decode-alpha' | 'unknown-container-format' | 'network-error';
10
+ export type VideoSinkResult = VideoSinks | 'no-video-track' | 'cannot-decode' | 'cannot-decode-prores' | 'cannot-decode-alpha' | 'unknown-container-format' | 'network-error';
11
11
  export declare const getSinks: (src: string, logLevel: "error" | "info" | "trace" | "verbose" | "warn", credentials: RequestCredentials | undefined, requestInit?: MediaRequestInit | undefined) => Promise<{
12
12
  getVideo: () => Promise<VideoSinkResult>;
13
13
  getAudio: (index: number | null) => Promise<AudioSinkResult>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@remotion/media",
3
- "version": "4.0.490",
3
+ "version": "4.0.491",
4
4
  "main": "dist/index.js",
5
5
  "types": "dist/index.d.ts",
6
6
  "module": "dist/esm/index.mjs",
@@ -23,7 +23,7 @@
23
23
  },
24
24
  "dependencies": {
25
25
  "mediabunny": "1.50.8",
26
- "remotion": "4.0.490",
26
+ "remotion": "4.0.491",
27
27
  "zod": "4.3.6"
28
28
  },
29
29
  "peerDependencies": {
@@ -31,8 +31,8 @@
31
31
  "react-dom": ">=16.8.0"
32
32
  },
33
33
  "devDependencies": {
34
- "@remotion/eslint-config-internal": "4.0.490",
35
- "@remotion/player": "4.0.490",
34
+ "@remotion/eslint-config-internal": "4.0.491",
35
+ "@remotion/player": "4.0.491",
36
36
  "@vitest/browser-webdriverio": "4.0.9",
37
37
  "eslint": "9.19.0",
38
38
  "react": "19.2.3",