@remotion/renderer 3.2.9 → 3.2.12-crf.5
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/assets/download-and-map-assets-to-file.d.ts +2 -1
- package/dist/assets/download-and-map-assets-to-file.js +48 -5
- package/dist/assets/download-file.d.ts +1 -1
- package/dist/assets/download-file.js +3 -2
- package/dist/codec-supports-media.d.ts +1 -0
- package/dist/codec-supports-media.js +8 -1
- package/dist/combine-videos.d.ts +2 -1
- package/dist/combine-videos.js +5 -1
- package/dist/extract-frame-from-video.d.ts +0 -1
- package/dist/extract-frame-from-video.js +30 -7
- package/dist/guess-extension-for-media.js +1 -1
- package/dist/index.d.ts +7 -8
- package/dist/mime-types.d.ts +1 -0
- package/dist/mime-types.js +6 -1
- package/dist/render-media.d.ts +0 -1
- package/dist/render-media.js +6 -3
- package/dist/stitch-frames-to-video.js +1 -1
- package/package.json +3 -3
|
@@ -11,10 +11,11 @@ export declare const downloadAsset: ({ src, onDownload, downloadMap, }: {
|
|
|
11
11
|
downloadMap: DownloadMap;
|
|
12
12
|
}) => Promise<string>;
|
|
13
13
|
export declare const markAllAssetsAsDownloaded: (downloadMap: DownloadMap) => void;
|
|
14
|
-
export declare const getSanitizedFilenameForAssetUrl: ({ src, downloadDir, contentDisposition, }: {
|
|
14
|
+
export declare const getSanitizedFilenameForAssetUrl: ({ src, downloadDir, contentDisposition, contentType, }: {
|
|
15
15
|
src: string;
|
|
16
16
|
downloadDir: string;
|
|
17
17
|
contentDisposition: string | null;
|
|
18
|
+
contentType: string | null;
|
|
18
19
|
}) => string;
|
|
19
20
|
export declare const downloadAndMapAssetsToFileUrl: ({ asset, onDownload, downloadMap, }: {
|
|
20
21
|
asset: TAsset;
|
|
@@ -1,14 +1,38 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
19
|
+
if (mod && mod.__esModule) return mod;
|
|
20
|
+
var result = {};
|
|
21
|
+
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
22
|
+
__setModuleDefault(result, mod);
|
|
23
|
+
return result;
|
|
24
|
+
};
|
|
2
25
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
26
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
27
|
};
|
|
5
28
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
29
|
exports.downloadAndMapAssetsToFileUrl = exports.getSanitizedFilenameForAssetUrl = exports.markAllAssetsAsDownloaded = exports.downloadAsset = void 0;
|
|
7
30
|
const fs_1 = __importDefault(require("fs"));
|
|
8
|
-
const path_1 =
|
|
31
|
+
const path_1 = __importStar(require("path"));
|
|
9
32
|
const remotion_1 = require("remotion");
|
|
10
33
|
const compress_assets_1 = require("../compress-assets");
|
|
11
34
|
const ensure_output_directory_1 = require("../ensure-output-directory");
|
|
35
|
+
const mime_types_1 = require("../mime-types");
|
|
12
36
|
const download_file_1 = require("./download-file");
|
|
13
37
|
const sanitize_filepath_1 = require("./sanitize-filepath");
|
|
14
38
|
const waitForAssetToBeDownloaded = ({ src, downloadDir, downloadMap, }) => {
|
|
@@ -121,6 +145,7 @@ const downloadAsset = async ({ src, onDownload, downloadMap, }) => {
|
|
|
121
145
|
contentDisposition: null,
|
|
122
146
|
downloadDir,
|
|
123
147
|
src,
|
|
148
|
+
contentType: null,
|
|
124
149
|
});
|
|
125
150
|
(0, ensure_output_directory_1.ensureOutputDirectory)(output);
|
|
126
151
|
const [assetDetails, assetData] = src.substring('data:'.length).split(',');
|
|
@@ -146,7 +171,12 @@ const downloadAsset = async ({ src, onDownload, downloadMap, }) => {
|
|
|
146
171
|
onProgress: (progress) => {
|
|
147
172
|
onProgress === null || onProgress === void 0 ? void 0 : onProgress(progress);
|
|
148
173
|
},
|
|
149
|
-
to: (contentDisposition) => (0, exports.getSanitizedFilenameForAssetUrl)({
|
|
174
|
+
to: (contentDisposition, contentType) => (0, exports.getSanitizedFilenameForAssetUrl)({
|
|
175
|
+
contentDisposition,
|
|
176
|
+
downloadDir,
|
|
177
|
+
src,
|
|
178
|
+
contentType,
|
|
179
|
+
}),
|
|
150
180
|
});
|
|
151
181
|
notifyAssetIsDownloaded({ src, downloadMap, downloadDir, to });
|
|
152
182
|
return to;
|
|
@@ -161,7 +191,7 @@ const markAllAssetsAsDownloaded = (downloadMap) => {
|
|
|
161
191
|
});
|
|
162
192
|
};
|
|
163
193
|
exports.markAllAssetsAsDownloaded = markAllAssetsAsDownloaded;
|
|
164
|
-
const getFilename = ({ contentDisposition, src, }) => {
|
|
194
|
+
const getFilename = ({ contentDisposition, src, contentType, }) => {
|
|
165
195
|
const filenameProbe = 'filename=';
|
|
166
196
|
if (contentDisposition === null || contentDisposition === void 0 ? void 0 : contentDisposition.includes(filenameProbe)) {
|
|
167
197
|
const start = contentDisposition.indexOf(filenameProbe);
|
|
@@ -176,13 +206,26 @@ const getFilename = ({ contentDisposition, src, }) => {
|
|
|
176
206
|
};
|
|
177
207
|
}
|
|
178
208
|
const { pathname, search } = new URL(src);
|
|
209
|
+
const ext = (0, path_1.extname)(pathname);
|
|
210
|
+
// Has no file extension, check if we can derive it from contentType
|
|
211
|
+
if (!ext && contentType) {
|
|
212
|
+
const matchedExt = (0, mime_types_1.getExt)(contentType);
|
|
213
|
+
return {
|
|
214
|
+
pathname: `${pathname}.${matchedExt}`,
|
|
215
|
+
search,
|
|
216
|
+
};
|
|
217
|
+
}
|
|
179
218
|
return { pathname, search };
|
|
180
219
|
};
|
|
181
|
-
const getSanitizedFilenameForAssetUrl = ({ src, downloadDir, contentDisposition, }) => {
|
|
220
|
+
const getSanitizedFilenameForAssetUrl = ({ src, downloadDir, contentDisposition, contentType, }) => {
|
|
182
221
|
if ((0, compress_assets_1.isAssetCompressed)(src)) {
|
|
183
222
|
return src;
|
|
184
223
|
}
|
|
185
|
-
const { pathname, search } = getFilename({
|
|
224
|
+
const { pathname, search } = getFilename({
|
|
225
|
+
contentDisposition,
|
|
226
|
+
contentType,
|
|
227
|
+
src,
|
|
228
|
+
});
|
|
186
229
|
const split = pathname.split('.');
|
|
187
230
|
const fileExtension = split.length > 1 && split[split.length - 1]
|
|
188
231
|
? `.${split[split.length - 1]}`
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
export declare const downloadFile: ({ onProgress, url, to: toFn, }: {
|
|
2
2
|
url: string;
|
|
3
|
-
to: (contentDisposition: string | null) => string;
|
|
3
|
+
to: (contentDisposition: string | null, contentType: string | null) => string;
|
|
4
4
|
onProgress: ((progress: {
|
|
5
5
|
percent: number | null;
|
|
6
6
|
downloaded: number;
|
|
@@ -8,9 +8,10 @@ const downloadFile = ({ onProgress, url, to: toFn, }) => {
|
|
|
8
8
|
return new Promise((resolve, reject) => {
|
|
9
9
|
(0, read_file_1.readFile)(url)
|
|
10
10
|
.then((res) => {
|
|
11
|
-
var _a;
|
|
11
|
+
var _a, _b;
|
|
12
12
|
const contentDisposition = (_a = res.headers['content-disposition']) !== null && _a !== void 0 ? _a : null;
|
|
13
|
-
const
|
|
13
|
+
const contentType = (_b = res.headers['content-type']) !== null && _b !== void 0 ? _b : null;
|
|
14
|
+
const to = toFn(contentDisposition, contentType);
|
|
14
15
|
(0, ensure_output_directory_1.ensureOutputDirectory)(to);
|
|
15
16
|
const sizeHeader = res.headers['content-length'];
|
|
16
17
|
const totalSize = typeof sizeHeader === 'undefined' ? null : Number(sizeHeader);
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.codecSupportsMedia = void 0;
|
|
3
|
+
exports.codecSupportsCrf = exports.codecSupportsMedia = void 0;
|
|
4
|
+
const get_codec_name_1 = require("./get-codec-name");
|
|
4
5
|
const support = {
|
|
5
6
|
'h264-mkv': {
|
|
6
7
|
audio: true,
|
|
@@ -47,3 +48,9 @@ const codecSupportsMedia = (codec) => {
|
|
|
47
48
|
return support[codec];
|
|
48
49
|
};
|
|
49
50
|
exports.codecSupportsMedia = codecSupportsMedia;
|
|
51
|
+
const codecSupportsCrf = (codec) => {
|
|
52
|
+
const encoderName = (0, get_codec_name_1.getCodecName)(codec);
|
|
53
|
+
const supportsCrf = encoderName && codec !== 'prores';
|
|
54
|
+
return supportsCrf;
|
|
55
|
+
};
|
|
56
|
+
exports.codecSupportsCrf = codecSupportsCrf;
|
package/dist/combine-videos.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { Codec } from './codec';
|
|
2
|
-
export declare const combineVideos: ({ files, filelistDir, output, onProgress, numberOfFrames, codec, fps, numberOfGifLoops, }: {
|
|
2
|
+
export declare const combineVideos: ({ files, filelistDir, output, onProgress, numberOfFrames, codec, fps, numberOfGifLoops, crf, }: {
|
|
3
3
|
files: string[];
|
|
4
4
|
filelistDir: string;
|
|
5
5
|
output: string;
|
|
@@ -8,4 +8,5 @@ export declare const combineVideos: ({ files, filelistDir, output, onProgress, n
|
|
|
8
8
|
codec: Codec;
|
|
9
9
|
fps: number;
|
|
10
10
|
numberOfGifLoops: number | null;
|
|
11
|
+
crf: number | null;
|
|
11
12
|
}) => Promise<void>;
|
package/dist/combine-videos.js
CHANGED
|
@@ -8,15 +8,17 @@ exports.combineVideos = void 0;
|
|
|
8
8
|
const execa_1 = __importDefault(require("execa"));
|
|
9
9
|
const fs_1 = require("fs");
|
|
10
10
|
const path_1 = require("path");
|
|
11
|
+
const codec_supports_media_1 = require("./codec-supports-media");
|
|
11
12
|
const get_audio_codec_name_1 = require("./get-audio-codec-name");
|
|
12
13
|
const is_audio_codec_1 = require("./is-audio-codec");
|
|
13
14
|
const parse_ffmpeg_progress_1 = require("./parse-ffmpeg-progress");
|
|
14
15
|
const truthy_1 = require("./truthy");
|
|
15
|
-
const combineVideos = async ({ files, filelistDir, output, onProgress, numberOfFrames, codec, fps, numberOfGifLoops, }) => {
|
|
16
|
+
const combineVideos = async ({ files, filelistDir, output, onProgress, numberOfFrames, codec, fps, numberOfGifLoops, crf, }) => {
|
|
16
17
|
var _a;
|
|
17
18
|
const fileList = files.map((p) => `file '${p}'`).join('\n');
|
|
18
19
|
const fileListTxt = (0, path_1.join)(filelistDir, 'files.txt');
|
|
19
20
|
(0, fs_1.writeFileSync)(fileListTxt, fileList);
|
|
21
|
+
const supportsCrf = (0, codec_supports_media_1.codecSupportsCrf)(codec);
|
|
20
22
|
try {
|
|
21
23
|
const task = (0, execa_1.default)('ffmpeg', [
|
|
22
24
|
(0, is_audio_codec_1.isAudioCodec)(codec) ? null : '-r',
|
|
@@ -40,6 +42,8 @@ const combineVideos = async ({ files, filelistDir, output, onProgress, numberOfF
|
|
|
40
42
|
// Set max bitrate up to 1024kbps, will choose lower if that's too much
|
|
41
43
|
'-b:a',
|
|
42
44
|
'512K',
|
|
45
|
+
supportsCrf ? '-crf' : null,
|
|
46
|
+
supportsCrf ? String(crf) : null,
|
|
43
47
|
codec === 'h264' ? '-movflags' : null,
|
|
44
48
|
codec === 'h264' ? 'faststart' : null,
|
|
45
49
|
'-shortest',
|
|
@@ -32,9 +32,9 @@ const determineResizeParams = (needsResize) => {
|
|
|
32
32
|
};
|
|
33
33
|
// Uses no seeking, therefore the whole video has to be decoded. This is a last resort and should only happen
|
|
34
34
|
// if the video is corrupted
|
|
35
|
-
const getFrameOfVideoSlow = async ({ src,
|
|
36
|
-
console.warn(`\nUsing a slow method to extract the frame at ${
|
|
37
|
-
const actualOffset = `-${
|
|
35
|
+
const getFrameOfVideoSlow = async ({ src, duration, ffmpegExecutable, imageFormat, specialVCodecForTransparency, needsResize, offset, fps, }) => {
|
|
36
|
+
console.warn(`\nUsing a slow method to extract the frame at ${duration}ms of ${src}. See https://remotion.dev/docs/slow-method-to-extract-frame for advice`);
|
|
37
|
+
const actualOffset = `-${duration * 1000 - offset}ms`;
|
|
38
38
|
const command = [
|
|
39
39
|
'-itsoffset',
|
|
40
40
|
actualOffset,
|
|
@@ -72,7 +72,20 @@ const getFrameOfVideoSlow = async ({ src, timestamp, ffmpegExecutable, imageForm
|
|
|
72
72
|
const [stdErr, stdoutBuffer] = await Promise.all([stdErrString, stdoutChunk]);
|
|
73
73
|
const isEmpty = stdErr.includes('Output file is empty');
|
|
74
74
|
if (isEmpty) {
|
|
75
|
-
|
|
75
|
+
if (offset > 70) {
|
|
76
|
+
throw new Error(`Could not get last frame of ${src}. Tried to seek to the end using the command "ffmpeg ${command.join(' ')}" but got no frame. Most likely this video is corrupted.`);
|
|
77
|
+
}
|
|
78
|
+
return getFrameOfVideoSlow({
|
|
79
|
+
ffmpegExecutable,
|
|
80
|
+
duration,
|
|
81
|
+
// Decrement in 10ms increments, or 1 frame (e.g. fps = 25 --> 40ms)
|
|
82
|
+
offset: offset + (fps === null ? 10 : 1000 / fps),
|
|
83
|
+
src,
|
|
84
|
+
imageFormat,
|
|
85
|
+
specialVCodecForTransparency,
|
|
86
|
+
needsResize,
|
|
87
|
+
fps,
|
|
88
|
+
});
|
|
76
89
|
}
|
|
77
90
|
return stdoutBuffer;
|
|
78
91
|
};
|
|
@@ -88,12 +101,14 @@ const getLastFrameOfVideoFastUnlimited = async (options) => {
|
|
|
88
101
|
}
|
|
89
102
|
if (options.specialVCodecForTransparency === 'vp8' || offset > 40) {
|
|
90
103
|
const last = await getFrameOfVideoSlow({
|
|
91
|
-
|
|
104
|
+
duration,
|
|
92
105
|
ffmpegExecutable,
|
|
93
106
|
src,
|
|
94
107
|
imageFormat: options.imageFormat,
|
|
95
108
|
specialVCodecForTransparency: options.specialVCodecForTransparency,
|
|
96
109
|
needsResize: options.needsResize,
|
|
110
|
+
offset: offset - 1000 / (fps === null ? 10 : fps),
|
|
111
|
+
fps,
|
|
97
112
|
});
|
|
98
113
|
return last;
|
|
99
114
|
}
|
|
@@ -143,7 +158,7 @@ const getLastFrameOfVideoFastUnlimited = async (options) => {
|
|
|
143
158
|
const unlimited = await getLastFrameOfVideoFastUnlimited({
|
|
144
159
|
ffmpegExecutable,
|
|
145
160
|
// Decrement in 10ms increments, or 1 frame (e.g. fps = 25 --> 40ms)
|
|
146
|
-
offset: offset +
|
|
161
|
+
offset: offset + (fps === null ? 10 : 1000 / fps),
|
|
147
162
|
src,
|
|
148
163
|
ffprobeExecutable,
|
|
149
164
|
imageFormat: options.imageFormat,
|
|
@@ -167,13 +182,16 @@ const extractFrameFromVideoFn = async ({ time, ffmpegExecutable, ffprobeExecutab
|
|
|
167
182
|
const src = await (0, ensure_presentation_timestamp_1.ensurePresentationTimestamps)(downloadMap, options.src);
|
|
168
183
|
const { specialVcodec, needsResize } = await (0, get_video_info_1.getVideoInfo)(downloadMap, src, ffprobeExecutable);
|
|
169
184
|
if (specialVcodec === 'vp8') {
|
|
185
|
+
const { fps } = await (0, get_video_stream_duration_1.getVideoStreamDuration)(downloadMap, src, ffprobeExecutable);
|
|
170
186
|
return getFrameOfVideoSlow({
|
|
171
187
|
ffmpegExecutable,
|
|
172
188
|
imageFormat,
|
|
173
189
|
specialVCodecForTransparency: specialVcodec,
|
|
174
190
|
src,
|
|
175
|
-
|
|
191
|
+
duration: time,
|
|
176
192
|
needsResize,
|
|
193
|
+
offset: 0,
|
|
194
|
+
fps,
|
|
177
195
|
});
|
|
178
196
|
}
|
|
179
197
|
if ((0, is_beyond_last_frame_1.isBeyondLastFrame)(downloadMap, src, time)) {
|
|
@@ -243,6 +261,11 @@ const extractFrameFromVideoFn = async ({ time, ffmpegExecutable, ffprobeExecutab
|
|
|
243
261
|
});
|
|
244
262
|
return last;
|
|
245
263
|
}
|
|
264
|
+
if (stdOut.length === 0) {
|
|
265
|
+
console.log('FFMPEG Logs:');
|
|
266
|
+
console.log(stderrStr);
|
|
267
|
+
throw new Error("Couldn't extract frame from video - FFMPEG did not return any data. Check logs to see more information");
|
|
268
|
+
}
|
|
246
269
|
return stdOut;
|
|
247
270
|
};
|
|
248
271
|
const extractFrameFromVideo = async (options) => {
|
|
@@ -22,6 +22,6 @@ const guessExtensionForVideo = async (src) => {
|
|
|
22
22
|
if (stderr.includes('Video: h264')) {
|
|
23
23
|
return 'mp4';
|
|
24
24
|
}
|
|
25
|
-
throw new Error(`
|
|
25
|
+
throw new Error(`The media file "${src}" has no file extension and the format could not be guessed. Tips: a) Ensure this is a valid video or audio file b) Add a file extension to the URL like ".mp4" c) Set a "Content-Type" or "Content-Disposition" header if possible.`);
|
|
26
26
|
};
|
|
27
27
|
exports.guessExtensionForVideo = guessExtensionForVideo;
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
/// <reference types="node" />
|
|
2
1
|
import execa from 'execa';
|
|
3
2
|
import { SymbolicateableError } from './error-handling/symbolicateable-error';
|
|
4
3
|
import { mimeContentType, mimeLookup } from './mime-types';
|
|
@@ -68,7 +67,7 @@ export declare const RenderInternals: {
|
|
|
68
67
|
task: Promise<Buffer | null>;
|
|
69
68
|
getLogs: () => string;
|
|
70
69
|
}>;
|
|
71
|
-
getFileExtensionFromCodec: (codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif", type: "chunk" | "final") => "mp3" | "aac" | "wav" | "gif" | "
|
|
70
|
+
getFileExtensionFromCodec: (codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif", type: "chunk" | "final") => "mp3" | "aac" | "wav" | "gif" | "mp4" | "mkv" | "mov" | "webm";
|
|
72
71
|
tmpDir: (str: string) => string;
|
|
73
72
|
deleteDirectory: (directory: string) => Promise<void>;
|
|
74
73
|
isServeUrl: (potentialUrl: string) => boolean;
|
|
@@ -77,7 +76,7 @@ export declare const RenderInternals: {
|
|
|
77
76
|
validatePuppeteerTimeout: (timeoutInMilliseconds: unknown) => void;
|
|
78
77
|
downloadFile: ({ onProgress, url, to: toFn, }: {
|
|
79
78
|
url: string;
|
|
80
|
-
to: (contentDisposition: string | null) => string;
|
|
79
|
+
to: (contentDisposition: string | null, contentType: string | null) => string;
|
|
81
80
|
onProgress: ((progress: {
|
|
82
81
|
percent: number | null;
|
|
83
82
|
downloaded: number;
|
|
@@ -123,8 +122,8 @@ export declare const RenderInternals: {
|
|
|
123
122
|
validPixelFormats: readonly ["yuv420p", "yuva420p", "yuv422p", "yuv444p", "yuv420p10le", "yuv422p10le", "yuv444p10le", "yuva444p10le"];
|
|
124
123
|
DEFAULT_BROWSER: import("./browser").Browser;
|
|
125
124
|
validateFrameRange: (frameRange: import("./frame-range").FrameRange | null) => void;
|
|
126
|
-
DEFAULT_OPENGL_RENDERER: "
|
|
127
|
-
validateOpenGlRenderer: (option: "
|
|
125
|
+
DEFAULT_OPENGL_RENDERER: "swangle" | "angle" | "egl" | "swiftshader" | null;
|
|
126
|
+
validateOpenGlRenderer: (option: "swangle" | "angle" | "egl" | "swiftshader" | null) => "swangle" | "angle" | "egl" | "swiftshader" | null;
|
|
128
127
|
getDefaultCrfForCodec: (codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif") => number;
|
|
129
128
|
validateSelectedCrfAndCodecCombination: (crf: unknown, codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif") => void;
|
|
130
129
|
validImageFormats: readonly ["png", "jpeg", "none"];
|
|
@@ -136,12 +135,12 @@ export declare const RenderInternals: {
|
|
|
136
135
|
DEFAULT_TIMEOUT: number;
|
|
137
136
|
getValidCrfRanges: (codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif") => [number, number];
|
|
138
137
|
validateSelectedPixelFormatAndCodecCombination: (pixelFormat: "yuv420p" | "yuva420p" | "yuv422p" | "yuv444p" | "yuv420p10le" | "yuv422p10le" | "yuv444p10le" | "yuva444p10le", codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif") => void;
|
|
139
|
-
validateSelectedCodecAndProResCombination: (actualCodec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif", actualProResProfile: "
|
|
140
|
-
validateSelectedPixelFormatAndImageFormatCombination: (pixelFormat: "yuv420p" | "yuva420p" | "yuv422p" | "yuv444p" | "yuv420p10le" | "yuv422p10le" | "yuv444p10le" | "yuva444p10le", imageFormat: "
|
|
138
|
+
validateSelectedCodecAndProResCombination: (actualCodec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif", actualProResProfile: "4444-xq" | "4444" | "hq" | "standard" | "light" | "proxy" | undefined) => void;
|
|
139
|
+
validateSelectedPixelFormatAndImageFormatCombination: (pixelFormat: "yuv420p" | "yuva420p" | "yuv422p" | "yuv444p" | "yuv420p10le" | "yuv422p10le" | "yuv444p10le" | "yuva444p10le", imageFormat: "png" | "jpeg" | "none") => "none" | "valid";
|
|
141
140
|
DEFAULT_CODEC: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif";
|
|
142
141
|
isAudioCodec: (codec: "h264" | "h265" | "vp8" | "vp9" | "mp3" | "aac" | "wav" | "prores" | "h264-mkv" | "gif" | undefined) => boolean;
|
|
143
142
|
logLevels: readonly ["verbose", "info", "warn", "error"];
|
|
144
|
-
isEqualOrBelowLogLevel: (currentLevel: "
|
|
143
|
+
isEqualOrBelowLogLevel: (currentLevel: "verbose" | "error" | "info" | "warn", level: "verbose" | "error" | "info" | "warn") => boolean;
|
|
145
144
|
isValidLogLevel: (level: string) => boolean;
|
|
146
145
|
validateEveryNthFrame: (everyNthFrame: unknown) => void;
|
|
147
146
|
perf: typeof perf;
|
package/dist/mime-types.d.ts
CHANGED
package/dist/mime-types.js
CHANGED
|
@@ -1,12 +1,17 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.mimeContentType = exports.mimeLookup = void 0;
|
|
3
|
+
exports.mimeContentType = exports.mimeLookup = exports.getExt = void 0;
|
|
4
4
|
const path_1 = require("path");
|
|
5
5
|
const mime_db_1 = require("./mime-db");
|
|
6
6
|
const extensions = {};
|
|
7
7
|
const types = {};
|
|
8
8
|
// Populate the extensions/types maps
|
|
9
9
|
populateMaps(extensions, {});
|
|
10
|
+
const getExt = (contentType) => {
|
|
11
|
+
var _a, _b, _c;
|
|
12
|
+
return (_c = (_b = (_a = mime_db_1.mimeDb[contentType.toLowerCase()]) === null || _a === void 0 ? void 0 : _a.extensions) === null || _b === void 0 ? void 0 : _b[0]) !== null && _c !== void 0 ? _c : null;
|
|
13
|
+
};
|
|
14
|
+
exports.getExt = getExt;
|
|
10
15
|
function mimeLookup(path) {
|
|
11
16
|
if (!path || typeof path !== 'string') {
|
|
12
17
|
return false;
|
package/dist/render-media.d.ts
CHANGED
package/dist/render-media.js
CHANGED
|
@@ -46,6 +46,9 @@ const renderMedia = ({ parallelism, proResProfile, crf, composition, ffmpegExecu
|
|
|
46
46
|
if (outputLocation) {
|
|
47
47
|
(0, validate_output_filename_1.validateOutputFilename)(codec, (0, get_extension_of_filename_1.getExtensionOfFilename)(outputLocation));
|
|
48
48
|
}
|
|
49
|
+
const absoluteOutputLocation = outputLocation
|
|
50
|
+
? path_1.default.resolve(process.cwd(), outputLocation)
|
|
51
|
+
: null;
|
|
49
52
|
(0, validate_scale_1.validateScale)(scale);
|
|
50
53
|
const everyNthFrame = (_a = options.everyNthFrame) !== null && _a !== void 0 ? _a : 1;
|
|
51
54
|
const numberOfGifLoops = (_b = options.numberOfGifLoops) !== null && _b !== void 0 ? _b : null;
|
|
@@ -207,8 +210,8 @@ const renderMedia = ({ parallelism, proResProfile, crf, composition, ffmpegExecu
|
|
|
207
210
|
.then(([{ assetsInfo }]) => {
|
|
208
211
|
renderedDoneIn = Date.now() - renderStart;
|
|
209
212
|
callUpdate();
|
|
210
|
-
if (
|
|
211
|
-
(0, ensure_output_directory_1.ensureOutputDirectory)(
|
|
213
|
+
if (absoluteOutputLocation) {
|
|
214
|
+
(0, ensure_output_directory_1.ensureOutputDirectory)(absoluteOutputLocation);
|
|
212
215
|
}
|
|
213
216
|
const stitchStart = Date.now();
|
|
214
217
|
return Promise.all([
|
|
@@ -216,7 +219,7 @@ const renderMedia = ({ parallelism, proResProfile, crf, composition, ffmpegExecu
|
|
|
216
219
|
width: composition.width * (scale !== null && scale !== void 0 ? scale : 1),
|
|
217
220
|
height: composition.height * (scale !== null && scale !== void 0 ? scale : 1),
|
|
218
221
|
fps,
|
|
219
|
-
outputLocation,
|
|
222
|
+
outputLocation: absoluteOutputLocation,
|
|
220
223
|
internalOptions: {
|
|
221
224
|
preEncodedFileLocation,
|
|
222
225
|
imageFormat,
|
|
@@ -96,7 +96,7 @@ const spawnFfmpeg = async (options) => {
|
|
|
96
96
|
const audioCodecName = (0, get_audio_codec_name_1.getAudioCodecName)(codec);
|
|
97
97
|
const proResProfileName = (0, get_prores_profile_name_1.getProResProfileName)(codec, options.proResProfile);
|
|
98
98
|
const mediaSupport = (0, codec_supports_media_1.codecSupportsMedia)(codec);
|
|
99
|
-
const supportsCrf =
|
|
99
|
+
const supportsCrf = (0, codec_supports_media_1.codecSupportsCrf)(codec);
|
|
100
100
|
const tempFile = options.outputLocation
|
|
101
101
|
? null
|
|
102
102
|
: path_1.default.join(options.assetsInfo.downloadMap.stitchFrames, `out.${(0, get_extension_from_codec_1.getFileExtensionFromCodec)(codec, 'final')}`);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@remotion/renderer",
|
|
3
|
-
"version": "3.2.
|
|
3
|
+
"version": "3.2.12-crf.5+14dc380ad",
|
|
4
4
|
"description": "Renderer for Remotion",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -22,7 +22,7 @@
|
|
|
22
22
|
"dependencies": {
|
|
23
23
|
"execa": "5.1.1",
|
|
24
24
|
"extract-zip": "2.0.1",
|
|
25
|
-
"remotion": "3.2.
|
|
25
|
+
"remotion": "3.2.12-crf.5+14dc380ad",
|
|
26
26
|
"source-map": "^0.8.0-beta.0",
|
|
27
27
|
"ws": "8.7.0"
|
|
28
28
|
},
|
|
@@ -57,5 +57,5 @@
|
|
|
57
57
|
"publishConfig": {
|
|
58
58
|
"access": "public"
|
|
59
59
|
},
|
|
60
|
-
"gitHead": "
|
|
60
|
+
"gitHead": "14dc380ad148868c35c5612f48eaf8e78ab42d9c"
|
|
61
61
|
}
|