remotion 4.0.295 → 4.0.296

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.
@@ -1,8 +1,10 @@
1
1
  import type React from 'react';
2
+ import type { DownloadBehavior } from './download-behavior';
2
3
  declare const ArtifactThumbnail: unique symbol;
3
4
  export declare const Artifact: React.FC<{
4
5
  readonly filename: string;
5
6
  readonly content: string | Uint8Array | typeof ArtifactThumbnail;
7
+ readonly downloadBehavior?: DownloadBehavior | null;
6
8
  }> & {
7
9
  Thumbnail: typeof ArtifactThumbnail;
8
10
  };
@@ -6,7 +6,7 @@ const RenderAssetManager_1 = require("./RenderAssetManager");
6
6
  const get_remotion_environment_1 = require("./get-remotion-environment");
7
7
  const use_current_frame_1 = require("./use-current-frame");
8
8
  const ArtifactThumbnail = Symbol('Thumbnail');
9
- const Artifact = ({ filename, content }) => {
9
+ const Artifact = ({ filename, content, downloadBehavior }) => {
10
10
  const { registerRenderAsset, unregisterRenderAsset } = (0, react_1.useContext)(RenderAssetManager_1.RenderAssetManager);
11
11
  const [env] = (0, react_1.useState)(() => (0, get_remotion_environment_1.getRemotionEnvironment)());
12
12
  const frame = (0, use_current_frame_1.useCurrentFrame)();
@@ -25,6 +25,7 @@ const Artifact = ({ filename, content }) => {
25
25
  filename,
26
26
  frame,
27
27
  contentType: 'binary',
28
+ downloadBehavior: downloadBehavior !== null && downloadBehavior !== void 0 ? downloadBehavior : null,
28
29
  });
29
30
  }
30
31
  else if (content === ArtifactThumbnail) {
@@ -34,6 +35,7 @@ const Artifact = ({ filename, content }) => {
34
35
  filename,
35
36
  frame,
36
37
  contentType: 'thumbnail',
38
+ downloadBehavior: downloadBehavior !== null && downloadBehavior !== void 0 ? downloadBehavior : null,
37
39
  });
38
40
  }
39
41
  else {
@@ -44,6 +46,7 @@ const Artifact = ({ filename, content }) => {
44
46
  filename,
45
47
  frame,
46
48
  contentType: 'text',
49
+ downloadBehavior: downloadBehavior !== null && downloadBehavior !== void 0 ? downloadBehavior : null,
47
50
  });
48
51
  }
49
52
  return () => {
@@ -57,6 +60,7 @@ const Artifact = ({ filename, content }) => {
57
60
  id,
58
61
  registerRenderAsset,
59
62
  unregisterRenderAsset,
63
+ downloadBehavior,
60
64
  ]);
61
65
  return null;
62
66
  };
@@ -3,6 +3,7 @@ import React from 'react';
3
3
  import type { AnyZodObject } from 'zod';
4
4
  import type { CalculateMetadataFunction } from './Composition.js';
5
5
  import type { BaseMetadata } from './CompositionManagerContext.js';
6
+ import type { DownloadBehavior } from './download-behavior.js';
6
7
  import type { InferProps, PropsIfHasProps } from './props-if-has-props.js';
7
8
  export type TComposition<Schema extends AnyZodObject, Props extends Record<string, unknown>> = {
8
9
  width: number | undefined;
@@ -81,6 +82,7 @@ export type ArtifactAsset = {
81
82
  id: string;
82
83
  filename: string;
83
84
  frame: number;
85
+ downloadBehavior: DownloadBehavior | null;
84
86
  } & DiscriminatedArtifact;
85
87
  export type TRenderAsset = AudioOrVideoAsset | ArtifactAsset;
86
88
  export declare const compositionsRef: React.RefObject<{
@@ -8,6 +8,11 @@ const isSafariWebkit = () => {
8
8
  const isSafari = /^((?!chrome|android).)*safari/i.test(window.navigator.userAgent);
9
9
  return isSafari;
10
10
  };
11
+ const isDesktopChrome = () => {
12
+ const isChrome = /chrome/i.test(window.navigator.userAgent);
13
+ const isDesktop = !/mobile/i.test(window.navigator.userAgent);
14
+ return isChrome && isDesktop;
15
+ };
11
16
  const useBufferUntilFirstFrame = ({ mediaRef, mediaType, onVariableFpsVideoDetected, pauseWhenBuffering, logLevel, mountTime, }) => {
12
17
  const bufferingRef = (0, react_1.useRef)(false);
13
18
  const { delayPlayback } = (0, use_buffer_state_1.useBufferState)();
@@ -23,10 +28,16 @@ const useBufferUntilFirstFrame = ({ mediaRef, mediaType, onVariableFpsVideoDetec
23
28
  if (!current) {
24
29
  return;
25
30
  }
26
- if (current.readyState >= current.HAVE_ENOUGH_DATA && !isSafariWebkit()) {
31
+ if (current.readyState >= current.HAVE_ENOUGH_DATA &&
32
+ !isSafariWebkit() &&
33
+ // In Desktop Chrome, the video might switch to playing
34
+ // but does not play due to Bluetooth headphones
35
+ // Enabling back this flag for Chrome without extensive testing
36
+ // because we never had big problems on Chrome
37
+ !isDesktopChrome()) {
27
38
  (0, playback_logging_1.playbackLogging)({
28
39
  logLevel,
29
- message: `Not using buffer until first frame, because readyState is ${current.readyState} and is not Safari`,
40
+ message: `Not using buffer until first frame, because readyState is ${current.readyState} and is not Safari or Desktop Chrome`,
30
41
  mountTime,
31
42
  tag: 'buffer',
32
43
  });
@@ -0,0 +1,6 @@
1
+ export type DownloadBehavior = {
2
+ type: 'play-in-browser';
3
+ } | {
4
+ type: 'download';
5
+ fileName: string | null;
6
+ };
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -83,6 +83,7 @@ export { CalculateMetadataFunction, Composition, CompositionProps, CompProps, St
83
83
  export type { CanvasContent } from './CompositionManagerContext.js';
84
84
  export { getInputProps } from './config/input-props.js';
85
85
  export { continueRender, delayRender } from './delay-render.js';
86
+ export { DownloadBehavior } from './download-behavior.js';
86
87
  export * from './easing.js';
87
88
  export * from './Folder.js';
88
89
  export * from './freeze.js';
@@ -1,4 +1,5 @@
1
1
  export type { ArtifactAsset, AudioOrVideoAsset, TRenderAsset, } from './CompositionManager';
2
+ export { DownloadBehavior } from './download-behavior';
2
3
  export { EasingFunction, ExtrapolateType, interpolate, InterpolateOptions, } from './interpolate';
3
4
  export { random, RandomSeed } from './random.js';
4
5
  export type { VideoConfig } from './video-config';
@@ -1,9 +1,10 @@
1
1
  import type React from 'react';
2
2
  import type { LogLevel } from './log';
3
- export declare const useMediaBuffering: ({ element, shouldBuffer, isPremounting, logLevel, mountTime, }: {
3
+ export declare const useMediaBuffering: ({ element, shouldBuffer, isPremounting, logLevel, mountTime, src, }: {
4
4
  element: React.RefObject<HTMLVideoElement | HTMLAudioElement | null>;
5
5
  shouldBuffer: boolean;
6
6
  isPremounting: boolean;
7
7
  logLevel: LogLevel;
8
8
  mountTime: number;
9
+ src: string | null;
9
10
  }) => boolean;
@@ -4,7 +4,7 @@ exports.useMediaBuffering = void 0;
4
4
  const react_1 = require("react");
5
5
  const playback_logging_1 = require("./playback-logging");
6
6
  const use_buffer_state_1 = require("./use-buffer-state");
7
- const useMediaBuffering = ({ element, shouldBuffer, isPremounting, logLevel, mountTime, }) => {
7
+ const useMediaBuffering = ({ element, shouldBuffer, isPremounting, logLevel, mountTime, src, }) => {
8
8
  const buffer = (0, use_buffer_state_1.useBufferState)();
9
9
  const [isBuffering, setIsBuffering] = (0, react_1.useState)(false);
10
10
  // Buffer state based on `waiting` and `canplay`
@@ -114,7 +114,7 @@ const useMediaBuffering = ({ element, shouldBuffer, isPremounting, logLevel, mou
114
114
  if (!navigator.userAgent.includes('Firefox/')) {
115
115
  (0, playback_logging_1.playbackLogging)({
116
116
  logLevel,
117
- message: `Calling .load() on ${current.src} because readyState is ${current.readyState} and it is not Firefox.`,
117
+ message: `Calling .load() on ${src} because readyState is ${current.readyState} and it is not Firefox.`,
118
118
  tag: 'load',
119
119
  mountTime,
120
120
  });
@@ -135,7 +135,11 @@ const useMediaBuffering = ({ element, shouldBuffer, isPremounting, logLevel, mou
135
135
  return () => {
136
136
  cleanup('element was unmounted or prop changed');
137
137
  };
138
- }, [buffer, element, isPremounting, logLevel, shouldBuffer, mountTime]);
138
+ // dependencies array:
139
+ // `src` should be in it, because if changing the source and pausing at the same time,
140
+ // it gives the chance to load the new source.
141
+ // https://github.com/remotion-dev/remotion/issues/5218
142
+ }, [buffer, src, element, isPremounting, logLevel, shouldBuffer, mountTime]);
139
143
  return isBuffering;
140
144
  };
141
145
  exports.useMediaBuffering = useMediaBuffering;
@@ -59,6 +59,7 @@ const useMediaPlayback = ({ mediaRef, src, mediaType, playbackRate: localPlaybac
59
59
  isPremounting,
60
60
  logLevel,
61
61
  mountTime,
62
+ src: src !== null && src !== void 0 ? src : null,
62
63
  });
63
64
  const { bufferUntilFirstFrame, isBuffering } = (0, buffer_until_first_frame_js_1.useBufferUntilFirstFrame)({
64
65
  mediaRef,
@@ -3,4 +3,4 @@
3
3
  * @see [Documentation](https://remotion.dev/docs/version)
4
4
  * @returns {string} The current version of the remotion package
5
5
  */
6
- export declare const VERSION = "4.0.295";
6
+ export declare const VERSION = "4.0.296";
@@ -7,4 +7,4 @@ exports.VERSION = void 0;
7
7
  * @see [Documentation](https://remotion.dev/docs/version)
8
8
  * @returns {string} The current version of the remotion package
9
9
  */
10
- exports.VERSION = '4.0.295';
10
+ exports.VERSION = '4.0.296';
@@ -104,7 +104,7 @@ function truthy(value) {
104
104
  }
105
105
 
106
106
  // src/version.ts
107
- var VERSION = "4.0.295";
107
+ var VERSION = "4.0.296";
108
108
 
109
109
  // src/multiple-versions-warning.ts
110
110
  var checkMultipleRemotionVersions = () => {
@@ -2072,7 +2072,7 @@ var RenderAssetManagerProvider = ({ children }) => {
2072
2072
 
2073
2073
  // src/Artifact.tsx
2074
2074
  var ArtifactThumbnail = Symbol("Thumbnail");
2075
- var Artifact = ({ filename, content }) => {
2075
+ var Artifact = ({ filename, content, downloadBehavior }) => {
2076
2076
  const { registerRenderAsset, unregisterRenderAsset } = useContext11(RenderAssetManager);
2077
2077
  const [env] = useState7(() => getRemotionEnvironment());
2078
2078
  const frame = useCurrentFrame();
@@ -2090,7 +2090,8 @@ var Artifact = ({ filename, content }) => {
2090
2090
  content: btoa(new TextDecoder("utf8").decode(content)),
2091
2091
  filename,
2092
2092
  frame,
2093
- contentType: "binary"
2093
+ contentType: "binary",
2094
+ downloadBehavior: downloadBehavior ?? null
2094
2095
  });
2095
2096
  } else if (content === ArtifactThumbnail) {
2096
2097
  registerRenderAsset({
@@ -2098,7 +2099,8 @@ var Artifact = ({ filename, content }) => {
2098
2099
  id,
2099
2100
  filename,
2100
2101
  frame,
2101
- contentType: "thumbnail"
2102
+ contentType: "thumbnail",
2103
+ downloadBehavior: downloadBehavior ?? null
2102
2104
  });
2103
2105
  } else {
2104
2106
  registerRenderAsset({
@@ -2107,7 +2109,8 @@ var Artifact = ({ filename, content }) => {
2107
2109
  content,
2108
2110
  filename,
2109
2111
  frame,
2110
- contentType: "text"
2112
+ contentType: "text",
2113
+ downloadBehavior: downloadBehavior ?? null
2111
2114
  });
2112
2115
  }
2113
2116
  return () => {
@@ -2120,7 +2123,8 @@ var Artifact = ({ filename, content }) => {
2120
2123
  frame,
2121
2124
  id,
2122
2125
  registerRenderAsset,
2123
- unregisterRenderAsset
2126
+ unregisterRenderAsset,
2127
+ downloadBehavior
2124
2128
  ]);
2125
2129
  return null;
2126
2130
  };
@@ -3052,6 +3056,11 @@ var isSafariWebkit = () => {
3052
3056
  const isSafari = /^((?!chrome|android).)*safari/i.test(window.navigator.userAgent);
3053
3057
  return isSafari;
3054
3058
  };
3059
+ var isDesktopChrome = () => {
3060
+ const isChrome = /chrome/i.test(window.navigator.userAgent);
3061
+ const isDesktop = !/mobile/i.test(window.navigator.userAgent);
3062
+ return isChrome && isDesktop;
3063
+ };
3055
3064
  var useBufferUntilFirstFrame = ({
3056
3065
  mediaRef,
3057
3066
  mediaType,
@@ -3073,10 +3082,10 @@ var useBufferUntilFirstFrame = ({
3073
3082
  if (!current) {
3074
3083
  return;
3075
3084
  }
3076
- if (current.readyState >= current.HAVE_ENOUGH_DATA && !isSafariWebkit()) {
3085
+ if (current.readyState >= current.HAVE_ENOUGH_DATA && !isSafariWebkit() && !isDesktopChrome()) {
3077
3086
  playbackLogging({
3078
3087
  logLevel,
3079
- message: `Not using buffer until first frame, because readyState is ${current.readyState} and is not Safari`,
3088
+ message: `Not using buffer until first frame, because readyState is ${current.readyState} and is not Safari or Desktop Chrome`,
3080
3089
  mountTime,
3081
3090
  tag: "buffer"
3082
3091
  });
@@ -3268,7 +3277,8 @@ var useMediaBuffering = ({
3268
3277
  shouldBuffer,
3269
3278
  isPremounting,
3270
3279
  logLevel,
3271
- mountTime
3280
+ mountTime,
3281
+ src
3272
3282
  }) => {
3273
3283
  const buffer = useBufferState();
3274
3284
  const [isBuffering, setIsBuffering] = useState11(false);
@@ -3362,7 +3372,7 @@ var useMediaBuffering = ({
3362
3372
  if (!navigator.userAgent.includes("Firefox/")) {
3363
3373
  playbackLogging({
3364
3374
  logLevel,
3365
- message: `Calling .load() on ${current.src} because readyState is ${current.readyState} and it is not Firefox.`,
3375
+ message: `Calling .load() on ${src} because readyState is ${current.readyState} and it is not Firefox.`,
3366
3376
  tag: "load",
3367
3377
  mountTime
3368
3378
  });
@@ -3382,7 +3392,7 @@ var useMediaBuffering = ({
3382
3392
  return () => {
3383
3393
  cleanup("element was unmounted or prop changed");
3384
3394
  };
3385
- }, [buffer, element, isPremounting, logLevel, shouldBuffer, mountTime]);
3395
+ }, [buffer, src, element, isPremounting, logLevel, shouldBuffer, mountTime]);
3386
3396
  return isBuffering;
3387
3397
  };
3388
3398
 
@@ -3656,7 +3666,8 @@ var useMediaPlayback = ({
3656
3666
  shouldBuffer: pauseWhenBuffering,
3657
3667
  isPremounting,
3658
3668
  logLevel,
3659
- mountTime
3669
+ mountTime,
3670
+ src: src ?? null
3660
3671
  });
3661
3672
  const { bufferUntilFirstFrame, isBuffering } = useBufferUntilFirstFrame({
3662
3673
  mediaRef,
@@ -1,5 +1,5 @@
1
1
  // src/version.ts
2
- var VERSION = "4.0.295";
2
+ var VERSION = "4.0.296";
3
3
  export {
4
4
  VERSION
5
5
  };
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "url": "https://github.com/remotion-dev/remotion/tree/main/packages/core"
4
4
  },
5
5
  "name": "remotion",
6
- "version": "4.0.295",
6
+ "version": "4.0.296",
7
7
  "description": "Make videos programmatically",
8
8
  "main": "dist/cjs/index.js",
9
9
  "types": "dist/cjs/index.d.ts",
@@ -28,7 +28,7 @@
28
28
  "webpack": "5.96.1",
29
29
  "zod": "3.22.3",
30
30
  "eslint": "9.19.0",
31
- "@remotion/eslint-config-internal": "4.0.295"
31
+ "@remotion/eslint-config-internal": "4.0.296"
32
32
  },
33
33
  "keywords": [
34
34
  "remotion",