node-av 6.2.0-beta.31 → 6.2.0-beta.33

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 (48) hide show
  1. package/README.md +0 -10
  2. package/dist/api/data/test_av1.ivf +0 -0
  3. package/dist/api/data/test_hevc.h265 +0 -0
  4. package/dist/api/data/test_vp9.ivf +0 -0
  5. package/dist/api/decoder.d.ts +117 -2
  6. package/dist/api/decoder.js +289 -22
  7. package/dist/api/decoder.js.map +1 -1
  8. package/dist/api/encoder.d.ts +26 -3
  9. package/dist/api/encoder.js +142 -76
  10. package/dist/api/encoder.js.map +1 -1
  11. package/dist/api/filter-presets.d.ts +25 -1
  12. package/dist/api/filter-presets.js +63 -3
  13. package/dist/api/filter-presets.js.map +1 -1
  14. package/dist/api/filter.d.ts +62 -3
  15. package/dist/api/filter.js +118 -36
  16. package/dist/api/filter.js.map +1 -1
  17. package/dist/api/fmp4-stream.d.ts +1 -0
  18. package/dist/api/fmp4-stream.js +34 -49
  19. package/dist/api/fmp4-stream.js.map +1 -1
  20. package/dist/api/hardware.js +12 -9
  21. package/dist/api/hardware.js.map +1 -1
  22. package/dist/api/muxer.js +33 -24
  23. package/dist/api/muxer.js.map +1 -1
  24. package/dist/api/rtp-stream.d.ts +10 -0
  25. package/dist/api/rtp-stream.js +70 -67
  26. package/dist/api/rtp-stream.js.map +1 -1
  27. package/dist/api/scaler.d.ts +17 -1
  28. package/dist/api/scaler.js +41 -10
  29. package/dist/api/scaler.js.map +1 -1
  30. package/dist/api/utilities/live-decoding.d.ts +15 -0
  31. package/dist/api/utilities/live-decoding.js +32 -0
  32. package/dist/api/utilities/live-decoding.js.map +1 -0
  33. package/dist/api/utilities/scale-size.d.ts +22 -0
  34. package/dist/api/utilities/scale-size.js +31 -0
  35. package/dist/api/utilities/scale-size.js.map +1 -0
  36. package/dist/api/utilities/video-transcode.d.ts +183 -0
  37. package/dist/api/utilities/video-transcode.js +567 -0
  38. package/dist/api/utilities/video-transcode.js.map +1 -0
  39. package/dist/lib/binding.d.ts +1 -0
  40. package/dist/lib/binding.js.map +1 -1
  41. package/dist/lib/native-types.d.ts +2 -0
  42. package/dist/lib/output-format.d.ts +42 -0
  43. package/dist/lib/output-format.js +46 -0
  44. package/dist/lib/output-format.js.map +1 -1
  45. package/dist/lib/utilities.d.ts +26 -0
  46. package/dist/lib/utilities.js +28 -0
  47. package/dist/lib/utilities.js.map +1 -1
  48. package/package.json +7 -18
@@ -0,0 +1,567 @@
1
+ var __addDisposableResource = (this && this.__addDisposableResource) || function (env, value, async) {
2
+ if (value !== null && value !== void 0) {
3
+ if (typeof value !== "object" && typeof value !== "function") throw new TypeError("Object expected.");
4
+ var dispose, inner;
5
+ if (async) {
6
+ if (!Symbol.asyncDispose) throw new TypeError("Symbol.asyncDispose is not defined.");
7
+ dispose = value[Symbol.asyncDispose];
8
+ }
9
+ if (dispose === void 0) {
10
+ if (!Symbol.dispose) throw new TypeError("Symbol.dispose is not defined.");
11
+ dispose = value[Symbol.dispose];
12
+ if (async) inner = dispose;
13
+ }
14
+ if (typeof dispose !== "function") throw new TypeError("Object not disposable.");
15
+ if (inner) dispose = function() { try { inner.call(this); } catch (e) { return Promise.reject(e); } };
16
+ env.stack.push({ value: value, dispose: dispose, async: async });
17
+ }
18
+ else if (async) {
19
+ env.stack.push({ async: true });
20
+ }
21
+ return value;
22
+ };
23
+ var __disposeResources = (this && this.__disposeResources) || (function (SuppressedError) {
24
+ return function (env) {
25
+ function fail(e) {
26
+ env.error = env.hasError ? new SuppressedError(e, env.error, "An error was suppressed during disposal.") : e;
27
+ env.hasError = true;
28
+ }
29
+ var r, s = 0;
30
+ function next() {
31
+ while (r = env.stack.pop()) {
32
+ try {
33
+ if (!r.async && s === 1) return s = 0, env.stack.push(r), Promise.resolve().then(next);
34
+ if (r.dispose) {
35
+ var result = r.dispose.call(r.value);
36
+ if (r.async) return s |= 2, Promise.resolve(result).then(next, function(e) { fail(e); return next(); });
37
+ }
38
+ else s |= 1;
39
+ }
40
+ catch (e) {
41
+ fail(e);
42
+ }
43
+ }
44
+ if (s === 1) return env.hasError ? Promise.reject(env.error) : Promise.resolve();
45
+ if (env.hasError) throw env.error;
46
+ }
47
+ return next();
48
+ };
49
+ })(typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
50
+ var e = new Error(message);
51
+ return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
52
+ });
53
+ import { AVCOL_RANGE_MPEG, AV_CODEC_CAP_EXPERIMENTAL, AV_CODEC_CAP_HARDWARE, AV_HWDEVICE_TYPE_CUDA, AV_HWDEVICE_TYPE_D3D11VA, AV_HWDEVICE_TYPE_DRM, AV_HWDEVICE_TYPE_DXVA2, AV_HWDEVICE_TYPE_OPENCL, AV_HWDEVICE_TYPE_VAAPI, AV_HWDEVICE_TYPE_VDPAU, AV_HWDEVICE_TYPE_VIDEOTOOLBOX, AV_LOG_WARNING, AV_PIX_FMT_NV12, AV_PIX_FMT_YUV420P, AV_PIX_FMT_YUVJ420P, } from '../../constants/constants.js';
54
+ import { Codec } from '../../lib/codec.js';
55
+ import { Filter } from '../../lib/filter.js';
56
+ import { Frame } from '../../lib/frame.js';
57
+ import { Log } from '../../lib/log.js';
58
+ import { Rational } from '../../lib/rational.js';
59
+ import { avGetPixFmtName, avIsHardwarePixelFormat } from '../../lib/utilities.js';
60
+ import { Decoder } from '../decoder.js';
61
+ import { Encoder } from '../encoder.js';
62
+ import { FilterPreset } from '../filter-presets.js';
63
+ import { FilterAPI } from '../filter.js';
64
+ import { pickSupportedPixelFormat } from './codec-format.js';
65
+ import { resolveScaleSize } from './scale-size.js';
66
+ /**
67
+ * Devices whose upload and scaler are proven together; elsewhere software frames are scaled on the CPU.
68
+ *
69
+ * @internal
70
+ */
71
+ const UPLOAD_SCALE_DEVICES = [AV_HWDEVICE_TYPE_VAAPI, AV_HWDEVICE_TYPE_CUDA, AV_HWDEVICE_TYPE_VIDEOTOOLBOX];
72
+ /**
73
+ * Devices without encoders of their own, they borrow one from a GPU vendor.
74
+ *
75
+ * @internal
76
+ */
77
+ const BORROWING_DEVICES = [
78
+ AV_HWDEVICE_TYPE_D3D11VA,
79
+ AV_HWDEVICE_TYPE_DXVA2,
80
+ AV_HWDEVICE_TYPE_OPENCL,
81
+ AV_HWDEVICE_TYPE_VDPAU,
82
+ AV_HWDEVICE_TYPE_DRM,
83
+ ];
84
+ /**
85
+ * The vendor encoders such a device borrows, in the order {@link HardwareContext.getEncoderCodec} looks for them.
86
+ *
87
+ * @internal
88
+ */
89
+ const VENDOR_ENCODERS = ['nvenc', 'qsv', 'amf'];
90
+ /**
91
+ * How long a hardware encoder that failed its test stays passed over, a busy GPU can recover.
92
+ *
93
+ * @internal
94
+ */
95
+ const FAILED_PROBE_RETRY_MS = 60_000;
96
+ /**
97
+ * Size of the test frame a hardware encoder has to encode.
98
+ *
99
+ * @internal
100
+ */
101
+ const PROBE_WIDTH = 640;
102
+ const PROBE_HEIGHT = 360;
103
+ /**
104
+ * Test encodes per device and encoder, failures with the time they failed.
105
+ *
106
+ * @internal
107
+ */
108
+ const encoderProbes = new Map();
109
+ /**
110
+ * No scaler and no upload for scaling, the graph of a device whose filters failed.
111
+ *
112
+ * @internal
113
+ */
114
+ const NO_DEVICE_FILTERS = { scaler: false, upload: false };
115
+ /**
116
+ * Filters per device type, the build decides which exist.
117
+ *
118
+ * @internal
119
+ */
120
+ const deviceFilterCache = new Map();
121
+ /**
122
+ * Build the filter graph that brings a decoded frame to the video encoder of a transcode.
123
+ *
124
+ * Frames stay on the device whenever the encoder takes them there, and scaling
125
+ * and format conversion run on the device whenever it has a scaler. Hardware
126
+ * encoders get 8-bit 4:2:0 in NV12: VAAPI decodes JPEG into planar or 4:2:2
127
+ * surfaces and 10-bit sources come as P010, which H.264 hardware encoders reject.
128
+ * Software encoders get yuv420p when the frames have to be converted anyway, it
129
+ * is the layout every browser and HomeKit decodes (unlike the 4:2:2 profile x264
130
+ * picks for a 4:2:2 JPEG camera). Packed sources such as yuyv422 are converted
131
+ * too, swscale cannot scale them in place.
132
+ *
133
+ * Decided per frame, not per stream: a hardware decoder falls back to software
134
+ * frames for input it cannot handle, e.g. 4:2:2 JPEG on NVDEC.
135
+ *
136
+ * @param input - The frame
137
+ *
138
+ * @param target - The encoder's needs
139
+ *
140
+ * @param filters - What the target's device has, see {@link findDeviceFilters}
141
+ *
142
+ * @returns The filter description, `null` when the frame can go to the encoder as it is
143
+ *
144
+ * @internal
145
+ */
146
+ export function videoTranscodeGraph(input, target, filters) {
147
+ const { encoder, hardware } = target;
148
+ const size = resolveScaleSize(input.width, input.height, target.width, target.height);
149
+ const parts = [];
150
+ let resize = size.width !== input.width || size.height !== input.height;
151
+ let format = input.format;
152
+ // a frame dropped first costs no later stage anything
153
+ if (target.fps !== undefined)
154
+ parts.push(`fps=${target.fps}`);
155
+ const takesDevice = !!hardware && encoderTakesDevice(encoder, hardware);
156
+ if (input.hw) {
157
+ if (input.onDevice && filters.scaler) {
158
+ // the scaler converts in the same pass, and a software encoder gets NV12 downloaded
159
+ if (resize || format !== AV_PIX_FMT_NV12)
160
+ parts.push(deviceScale(hardware, resize ? size : undefined));
161
+ if (takesDevice)
162
+ return finish(parts);
163
+ parts.push('hwdownload', 'format=nv12');
164
+ format = AV_PIX_FMT_NV12;
165
+ resize = false;
166
+ }
167
+ else if (input.onDevice && takesDevice && !resize && format === AV_PIX_FMT_NV12) {
168
+ return finish(parts);
169
+ }
170
+ else {
171
+ parts.push('hwdownload', `format=${pixFmtName(format)}`);
172
+ }
173
+ }
174
+ // software frames from here on
175
+ const softwareFormat = encoderSoftwareFormat(encoder);
176
+ if (hardware && (softwareFormat === null || (takesDevice && resize && filters.upload && filters.scaler))) {
177
+ // the encoder takes device frames only, or the device scales cheaper than the CPU
178
+ const scaleOnDevice = resize && filters.scaler;
179
+ if (resize && !scaleOnDevice)
180
+ parts.push(`scale=${size.width}:${size.height}`);
181
+ parts.push('format=nv12', FilterPreset.chain(hardware).hwupload().build());
182
+ if (scaleOnDevice)
183
+ parts.push(deviceScale(hardware, size));
184
+ return finish(parts);
185
+ }
186
+ if (resize)
187
+ parts.push(`scale=${size.width}:${size.height}`);
188
+ if (resize || !takesAsIs(encoder, format))
189
+ parts.push(`format=${pixFmtName(softwareFormat ?? AV_PIX_FMT_NV12)}`);
190
+ return finish(parts);
191
+ }
192
+ /**
193
+ * Describe a decoded frame for {@link videoTranscodeGraph}.
194
+ *
195
+ * @param frame - The frame
196
+ *
197
+ * @param hardware - The transcode's device, if any
198
+ *
199
+ * @returns Where the frame lives, its format and size
200
+ *
201
+ * @internal
202
+ */
203
+ export function describeVideoFrame(frame, hardware) {
204
+ const hw = frame.isHwFrame();
205
+ return {
206
+ hw,
207
+ onDevice: hw && !!hardware && frame.format === hardware.devicePixelFormat,
208
+ format: hw ? (frame.hwFramesCtx?.swFormat ?? AV_PIX_FMT_NV12) : frame.format,
209
+ width: frame.width,
210
+ height: frame.height,
211
+ };
212
+ }
213
+ /**
214
+ * Create the filter between the video decoder (or frame source) and the encoder of a transcode.
215
+ *
216
+ * The graph is built by {@link videoTranscodeGraph} from the first frame and
217
+ * again whenever the frames change, e.g. when the decoder falls back to software.
218
+ * A graph whose device filters fail to configure is replaced by one that
219
+ * converts in software.
220
+ *
221
+ * @param target - The encoder's needs
222
+ *
223
+ * @param filters - The device's filters, found by default
224
+ *
225
+ * @returns The filter
226
+ *
227
+ * @internal
228
+ */
229
+ export function createVideoTranscodeFilter(target, filters = findDeviceFilters(target.hardware)) {
230
+ return FilterAPI.create((frame, failure) => {
231
+ const input = describeVideoFrame(frame, target.hardware);
232
+ if (!failure) {
233
+ return videoTranscodeGraph(input, target, filters);
234
+ }
235
+ Log.log(AV_LOG_WARNING, `Video filters on ${target.hardware?.deviceTypeName ?? 'the CPU'} failed (${failure.message}), converting in software\n`);
236
+ return videoTranscodeGraph(input, target, NO_DEVICE_FILTERS);
237
+ }, { hardware: target.hardware });
238
+ }
239
+ /**
240
+ * Open the video decoder of a transcode, on the device unless it fails to open there.
241
+ *
242
+ * A device decoder that opens but then produces nothing moves to software on
243
+ * its own ({@link DecoderOptions.hardwareFallback}).
244
+ *
245
+ * @param stream - The video stream
246
+ *
247
+ * @param hardware - The device to decode on, if any
248
+ *
249
+ * @param options - Decoder options besides the device
250
+ *
251
+ * @returns The decoder
252
+ *
253
+ * @throws {FFmpegError} If no software decoder opens either
254
+ *
255
+ * @internal
256
+ */
257
+ export async function openTranscodeDecoder(stream, hardware, options) {
258
+ if (hardware) {
259
+ try {
260
+ return await Decoder.create(stream, { ...options, hardware, hardwareFallback: true });
261
+ }
262
+ catch (error) {
263
+ Log.log(AV_LOG_WARNING, `Video decoder failed to open on ${hardware.deviceTypeName}, decoding in software: ${error.message}\n`);
264
+ }
265
+ }
266
+ return await Decoder.create(stream, options);
267
+ }
268
+ /**
269
+ * Find the software encoder for a codec.
270
+ *
271
+ * FFmpeg picks the first encoder registered for a codec. The Linux arm64
272
+ * builds register the Rockchip MPP encoders ahead of libx264 and libx265, and
273
+ * those fail to open on every other arm64 machine, e.g. a Raspberry Pi.
274
+ *
275
+ * @param codecId - The codec to encode
276
+ *
277
+ * @returns The first encoder for the codec that is no hardware encoder, FFmpeg's pick when there is none
278
+ *
279
+ * @internal
280
+ */
281
+ export function findSoftwareEncoder(codecId) {
282
+ let opaque = null;
283
+ let result;
284
+ while ((result = Codec.iterateCodecs(opaque))) {
285
+ const { codec } = result;
286
+ if (codec.isEncoder() && codec.id === codecId && !codec.hasCapabilities(AV_CODEC_CAP_HARDWARE) && !codec.hasCapabilities(AV_CODEC_CAP_EXPERIMENTAL)) {
287
+ return codec;
288
+ }
289
+ opaque = result.opaque;
290
+ }
291
+ return Codec.findEncoder(codecId);
292
+ }
293
+ /**
294
+ * Find the device's encoder for a codec, if it works on this machine.
295
+ *
296
+ * @param hardware - The device, if any
297
+ *
298
+ * @param codec - The codec to encode
299
+ *
300
+ * @param options - Encoder options the encoder will get, some drivers need them to open (e.g. `low_power`)
301
+ *
302
+ * @returns The hardware encoder, or null to encode in software
303
+ *
304
+ * @internal
305
+ */
306
+ export async function findUsableHardwareEncoder(hardware, codec, options) {
307
+ const encoder = hardware?.getEncoderCodec(codec);
308
+ if (!encoder || !hardware) {
309
+ return null;
310
+ }
311
+ for (const candidate of encoderCandidates(encoder, hardware)) {
312
+ if (await canEncodeOnDevice(candidate, hardware, options)) {
313
+ return candidate;
314
+ }
315
+ }
316
+ return null;
317
+ }
318
+ /**
319
+ * The encoders to try for a device, the one it names first.
320
+ *
321
+ * A device without encoders of its own names the first vendor encoder the
322
+ * build has, NVENC on every Windows build. On an AMD or Intel GPU that one
323
+ * cannot work but the vendor's own can.
324
+ *
325
+ * @param encoder - The encoder the device names
326
+ *
327
+ * @param hardware - The device
328
+ *
329
+ * @returns The encoders in the order to try them
330
+ *
331
+ * @internal
332
+ */
333
+ function encoderCandidates(encoder, hardware) {
334
+ const name = encoder.name;
335
+ if (!name || !BORROWING_DEVICES.includes(hardware.deviceType)) {
336
+ return [encoder];
337
+ }
338
+ const base = name.slice(0, name.lastIndexOf('_'));
339
+ const others = VENDOR_ENCODERS.map((vendor) => Codec.findEncoderByName(`${base}_${vendor}`)).filter((candidate) => !!candidate?.isHardwareAcceleratedEncoder() && candidate.name !== name);
340
+ return [encoder, ...others];
341
+ }
342
+ /**
343
+ * Check whether a hardware encoder works on this machine, by encoding a test frame once.
344
+ *
345
+ * Finding an encoder says nothing about the driver: NVENC refuses to open
346
+ * when the driver is older than the API it was built against, many GPUs have
347
+ * no encoder at all. A failed encoder is passed over for a minute, then tried
348
+ * again. Concurrent callers share one test.
349
+ *
350
+ * @param encoder - The hardware encoder
351
+ *
352
+ * @param hardware - The device it encodes on
353
+ *
354
+ * @param options - Encoder options the encoder will get
355
+ *
356
+ * @returns Whether it encoded the frame
357
+ *
358
+ * @internal
359
+ */
360
+ export async function canEncodeOnDevice(encoder, hardware, options) {
361
+ const settings = JSON.stringify(options ?? {}, (_key, value) => (typeof value === 'bigint' ? String(value) : value));
362
+ const key = `${hardware.deviceTypeName}:${encoder.name}:${settings}`;
363
+ const known = encoderProbes.get(key);
364
+ if (known && (known.failedAt === undefined || Date.now() - known.failedAt < FAILED_PROBE_RETRY_MS)) {
365
+ return known.usable;
366
+ }
367
+ const probe = { usable: probeEncoder(encoder, hardware, options) };
368
+ encoderProbes.set(key, probe);
369
+ const usable = await probe.usable;
370
+ if (!usable) {
371
+ probe.failedAt = Date.now();
372
+ Log.log(AV_LOG_WARNING, `Hardware encoder ${encoder.name} failed to encode a test frame on ${hardware.deviceTypeName}, encoding video in software\n`);
373
+ }
374
+ return usable;
375
+ }
376
+ /**
377
+ * Encode one frame with a hardware encoder.
378
+ *
379
+ * @param codec - The hardware encoder
380
+ *
381
+ * @param hardware - The device it encodes on
382
+ *
383
+ * @param options - Encoder options
384
+ *
385
+ * @returns Whether a packet came out
386
+ *
387
+ * @internal
388
+ */
389
+ async function probeEncoder(codec, hardware, options) {
390
+ try {
391
+ const env_1 = { stack: [], error: void 0, hasError: false };
392
+ try {
393
+ const frame = __addDisposableResource(env_1, Frame.fromVideoBuffer(Buffer.alloc((PROBE_WIDTH * PROBE_HEIGHT * 3) / 2), {
394
+ width: PROBE_WIDTH,
395
+ height: PROBE_HEIGHT,
396
+ format: AV_PIX_FMT_NV12,
397
+ timeBase: { num: 1, den: 25 },
398
+ pts: 0n,
399
+ }), false);
400
+ // an unset range makes some encoders warn
401
+ frame.colorRange = AVCOL_RANGE_MPEG;
402
+ const upload = __addDisposableResource(env_1, encoderSoftwareFormat(codec) === null ? FilterAPI.create(FilterPreset.chain(hardware).hwupload().build(), { hardware }) : undefined, false);
403
+ const encoder = __addDisposableResource(env_1, await Encoder.create(codec, {
404
+ maxBFrames: 0,
405
+ options,
406
+ configure: (context) => {
407
+ context.framerate = new Rational(25, 1);
408
+ },
409
+ }), false);
410
+ const inputs = upload ? await upload.processAll(frame) : [frame];
411
+ let packets = 0;
412
+ try {
413
+ for (const input of inputs) {
414
+ for (const packet of await encoder.encodeAll(input)) {
415
+ packets++;
416
+ packet.free();
417
+ }
418
+ }
419
+ }
420
+ finally {
421
+ if (upload)
422
+ inputs.forEach((input) => input.free());
423
+ }
424
+ for await (const _packet_1 of encoder.flushPackets()) {
425
+ const env_2 = { stack: [], error: void 0, hasError: false };
426
+ try {
427
+ const _packet = __addDisposableResource(env_2, _packet_1, false);
428
+ packets++;
429
+ }
430
+ catch (e_1) {
431
+ env_2.error = e_1;
432
+ env_2.hasError = true;
433
+ }
434
+ finally {
435
+ __disposeResources(env_2);
436
+ }
437
+ }
438
+ return packets > 0;
439
+ }
440
+ catch (e_2) {
441
+ env_1.error = e_2;
442
+ env_1.hasError = true;
443
+ }
444
+ finally {
445
+ __disposeResources(env_1);
446
+ }
447
+ }
448
+ catch {
449
+ return false;
450
+ }
451
+ }
452
+ /**
453
+ * Whether an encoder takes the frames of a device as they are.
454
+ *
455
+ * @param encoder - The encoder
456
+ *
457
+ * @param hardware - The device
458
+ *
459
+ * @returns True for a hardware encoder that lists the device's pixel format
460
+ *
461
+ * @internal
462
+ */
463
+ function encoderTakesDevice(encoder, hardware) {
464
+ return encoder.isHardwareAcceleratedEncoder() && (encoder.pixelFormats?.includes(hardware.devicePixelFormat) ?? false);
465
+ }
466
+ /**
467
+ * The software format to convert frames to for an encoder.
468
+ *
469
+ * @param encoder - The encoder
470
+ *
471
+ * @returns NV12 for hardware encoders and yuv420p for software ones when listed,
472
+ * otherwise the closest listed software format; `null` if it takes device frames only
473
+ *
474
+ * @internal
475
+ */
476
+ function encoderSoftwareFormat(encoder) {
477
+ const formats = encoder.pixelFormats;
478
+ if (!formats || formats.length === 0)
479
+ return AV_PIX_FMT_YUV420P;
480
+ const preferred = encoder.isHardwareAcceleratedEncoder() ? [AV_PIX_FMT_NV12, AV_PIX_FMT_YUV420P] : [AV_PIX_FMT_YUV420P, AV_PIX_FMT_NV12];
481
+ const listed = preferred.find((format) => formats.includes(format));
482
+ if (listed !== undefined)
483
+ return listed;
484
+ const software = formats.filter((format) => !avIsHardwarePixelFormat(format));
485
+ return software.length > 0 ? pickSupportedPixelFormat(AV_PIX_FMT_YUV420P, software) : null;
486
+ }
487
+ /**
488
+ * Whether an encoder takes a software frame without conversion.
489
+ *
490
+ * @param encoder - The encoder
491
+ *
492
+ * @param format - The frame's pixel format
493
+ *
494
+ * @returns True for 8-bit 4:2:0 the encoder lists
495
+ *
496
+ * @internal
497
+ */
498
+ function takesAsIs(encoder, format) {
499
+ const is420 = format === AV_PIX_FMT_YUV420P || format === AV_PIX_FMT_YUVJ420P || format === AV_PIX_FMT_NV12;
500
+ return is420 && (encoder.pixelFormats?.includes(format) ?? true);
501
+ }
502
+ /**
503
+ * The device scaler converting to NV12, scaling too when given a size.
504
+ *
505
+ * @param hardware - The device
506
+ *
507
+ * @param size - Output size, if it changes
508
+ *
509
+ * @param size.width - Output width
510
+ *
511
+ * @param size.height - Output height
512
+ *
513
+ * @returns The filter
514
+ *
515
+ * @internal
516
+ */
517
+ function deviceScale(hardware, size) {
518
+ const chain = FilterPreset.chain(hardware);
519
+ return (size ? chain.scale(size.width, size.height, { format: 'nv12' }) : chain.scaleFormat(AV_PIX_FMT_NV12)).build();
520
+ }
521
+ /**
522
+ * Find out which transcode filters a device has in this FFmpeg build.
523
+ *
524
+ * @param hardware - The device, if any
525
+ *
526
+ * @returns Its filters, none without a device
527
+ *
528
+ * @internal
529
+ */
530
+ export function findDeviceFilters(hardware) {
531
+ if (!hardware)
532
+ return NO_DEVICE_FILTERS;
533
+ let filters = deviceFilterCache.get(hardware.deviceType);
534
+ if (!filters) {
535
+ const exists = (description) => Filter.getByName(description.split('=')[0]) !== null;
536
+ const scaler = FilterPreset.chain(hardware).supports('scale') && exists(FilterPreset.chain(hardware).scaleFormat(AV_PIX_FMT_NV12).build());
537
+ const upload = UPLOAD_SCALE_DEVICES.includes(hardware.deviceType) && exists(FilterPreset.chain(hardware).hwupload().build());
538
+ filters = { scaler, upload };
539
+ deviceFilterCache.set(hardware.deviceType, filters);
540
+ }
541
+ return filters;
542
+ }
543
+ /**
544
+ * Join the filters of a graph.
545
+ *
546
+ * @param parts - The filters
547
+ *
548
+ * @returns The description, `null` for none
549
+ *
550
+ * @internal
551
+ */
552
+ function finish(parts) {
553
+ return parts.length > 0 ? parts.join(',') : 'null';
554
+ }
555
+ /**
556
+ * Name of a pixel format for a filter description.
557
+ *
558
+ * @param format - The pixel format
559
+ *
560
+ * @returns Its name
561
+ *
562
+ * @internal
563
+ */
564
+ function pixFmtName(format) {
565
+ return avGetPixFmtName(format) ?? 'nv12';
566
+ }
567
+ //# sourceMappingURL=video-transcode.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"video-transcode.js","sourceRoot":"","sources":["../../../src/api/utilities/video-transcode.ts"],"names":[],"mappings":"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"}
@@ -185,6 +185,7 @@ export interface NativeBinding {
185
185
  avGetCodecName: (codecId: AVCodecID) => string | null;
186
186
  avGetCodecString: (codecpar: NativeCodecParameters, frameRate?: IRational) => string | null;
187
187
  avGetMimeTypeDash: (codecpar: NativeCodecParameters) => string | null;
188
+ avGuessFrameRate: (stream: NativeStream) => IRational;
188
189
  avGetPixFmtName: (pixFmt: AVPixelFormat) => string | null;
189
190
  avGetPixFmtFromName: (name: string) => AVPixelFormat;
190
191
  avIsHardwarePixelFormat: (pixFmt: AVPixelFormat) => boolean;
@@ -1 +1 @@
1
- {"version":3,"file":"binding.js","sourceRoot":"","sources":["../../src/lib/binding.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"binding.js","sourceRoot":"","sources":["../../src/lib/binding.ts"],"names":[],"mappings":"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"}
@@ -417,6 +417,8 @@ export interface NativeOutputFormat {
417
417
  readonly videoCodec: AVCodecID;
418
418
  readonly subtitleCodec: AVCodecID;
419
419
  readonly flags: AVFormatFlag;
420
+ getCodecTag(codecId: AVCodecID): number | null;
421
+ getCodecId(tag: number): AVCodecID;
420
422
  }
421
423
  /**
422
424
  * Native AVStream binding interface
@@ -169,6 +169,48 @@ export declare class OutputFormat implements NativeWrapper<NativeOutputFormat> {
169
169
  * @see {@link flags} For direct flags access
170
170
  */
171
171
  hasFlags(...flags: (AVFormatFlag | AVFormatConstants)[]): boolean;
172
+ /**
173
+ * Get the codec tag this format stores for a codec.
174
+ *
175
+ * Looks the codec up in the format's codec tag table.
176
+ *
177
+ * Direct mapping to av_codec_get_tag2() on AVOutputFormat->codec_tag.
178
+ *
179
+ * @param codecId - Codec to look up
180
+ *
181
+ * @returns The tag (FourCC), or null if the format has no tag for this codec
182
+ *
183
+ * @example
184
+ * ```typescript
185
+ * import { AV_CODEC_ID_H264 } from 'node-av/constants';
186
+ *
187
+ * const mp4 = OutputFormat.guessFormat('mp4', null, null);
188
+ * console.log(mp4?.getCodecTag(AV_CODEC_ID_H264)); // 0x31637661 ('avc1')
189
+ * ```
190
+ *
191
+ * @see {@link getCodecId} For the reverse lookup
192
+ */
193
+ getCodecTag(codecId: AVCodecID): number | null;
194
+ /**
195
+ * Get the codec a codec tag stands for in this format.
196
+ *
197
+ * Looks the tag up in the format's codec tag table.
198
+ *
199
+ * Direct mapping to av_codec_get_id() on AVOutputFormat->codec_tag.
200
+ *
201
+ * @param tag - Codec tag (FourCC)
202
+ *
203
+ * @returns The codec, or AV_CODEC_ID_NONE if the format does not know the tag
204
+ *
205
+ * @example
206
+ * ```typescript
207
+ * const mkv = OutputFormat.guessFormat('matroska', null, null);
208
+ * const id = mkv?.getCodecId(stream.codecpar.codecTag);
209
+ * ```
210
+ *
211
+ * @see {@link getCodecTag} For the reverse lookup
212
+ */
213
+ getCodecId(tag: number): AVCodecID;
172
214
  /**
173
215
  * Get the underlying native OutputFormat object.
174
216
  *