Files
clawbot/skills/remotion-prompt-video/node_modules/@remotion/media-parser/dist/get-duration.js
T

158 lines
6.3 KiB
JavaScript

"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.hasSlowDuration = exports.hasDuration = exports.getDuration = exports.isMatroska = void 0;
const get_duration_from_flac_1 = require("./containers/flac/get-duration-from-flac");
const are_samples_complete_1 = require("./containers/iso-base-media/are-samples-complete");
const get_sample_positions_from_track_1 = require("./containers/iso-base-media/get-sample-positions-from-track");
const traversal_1 = require("./containers/iso-base-media/traversal");
const get_duration_from_m3u_1 = require("./containers/m3u/get-duration-from-m3u");
const get_duration_1 = require("./containers/mp3/get-duration");
const get_duration_2 = require("./containers/riff/get-duration");
const get_duration_from_wav_1 = require("./containers/wav/get-duration-from-wav");
const get_tracks_1 = require("./get-tracks");
const precomputed_tfra_1 = require("./state/iso-base-media/precomputed-tfra");
const getDurationFromMatroska = (segments) => {
const mainSegment = segments.find((s) => s.type === 'Segment');
if (!mainSegment || mainSegment.type !== 'Segment') {
return null;
}
const { value: children } = mainSegment;
if (!children) {
return null;
}
const infoSegment = children.find((s) => s.type === 'Info');
const relevantBoxes = [
...mainSegment.value,
...(infoSegment && infoSegment.type === 'Info' ? infoSegment.value : []),
];
const timestampScale = relevantBoxes.find((s) => s.type === 'TimestampScale');
if (!timestampScale || timestampScale.type !== 'TimestampScale') {
return null;
}
const duration = relevantBoxes.find((s) => s.type === 'Duration');
if (!duration || duration.type !== 'Duration') {
return null;
}
return (duration.value.value / timestampScale.value.value) * 1000;
};
const isMatroska = (boxes) => {
const matroskaBox = boxes.find((b) => b.type === 'Segment');
return matroskaBox;
};
exports.isMatroska = isMatroska;
const getDurationFromIsoBaseMedia = (parserState) => {
var _a, _b;
const structure = parserState.structure.getIsoStructure();
const moovBox = (0, traversal_1.getMoovBoxFromState)({
structureState: parserState.structure,
isoState: parserState.iso,
mp4HeaderSegment: (_b = (_a = parserState.m3uPlaylistContext) === null || _a === void 0 ? void 0 : _a.mp4HeaderSegment) !== null && _b !== void 0 ? _b : null,
mayUsePrecomputed: true,
});
if (!moovBox) {
return null;
}
const moofBoxes = (0, traversal_1.getMoofBoxes)(structure.boxes);
const mfra = parserState.iso.mfra.getIfAlreadyLoaded();
const tfraBoxes = (0, precomputed_tfra_1.deduplicateTfraBoxesByOffset)([
...(mfra ? (0, traversal_1.getTfraBoxesFromMfraBoxChildren)(mfra) : []),
...(0, traversal_1.getTfraBoxes)(structure.boxes),
]);
if (!(0, are_samples_complete_1.areSamplesComplete)({ moofBoxes, tfraBoxes })) {
return null;
}
const mvhdBox = (0, traversal_1.getMvhdBox)(moovBox);
if (!mvhdBox) {
return null;
}
if (mvhdBox.type !== 'mvhd-box') {
throw new Error('Expected mvhd-box');
}
if (mvhdBox.durationInSeconds > 0) {
return mvhdBox.durationInSeconds;
}
const tracks = (0, get_tracks_1.getTracks)(parserState, true);
const allSamples = tracks.map((t) => {
const { originalTimescale: ts } = t;
const trakBox = (0, traversal_1.getTrakBoxByTrackId)(moovBox, t.trackId);
if (!trakBox) {
return null;
}
const { samplePositions, isComplete } = (0, get_sample_positions_from_track_1.getSamplePositionsFromTrack)({
trakBox,
moofBoxes,
moofComplete: (0, are_samples_complete_1.areSamplesComplete)({ moofBoxes, tfraBoxes }),
trexBoxes: (0, traversal_1.getTrexBoxes)(moovBox),
});
if (!isComplete) {
return null;
}
if (samplePositions.length === 0) {
return null;
}
const highest = samplePositions === null || samplePositions === void 0 ? void 0 : samplePositions.map((sp) => (sp.timestamp + sp.duration) / ts).reduce((a, b) => Math.max(a, b), 0);
return highest !== null && highest !== void 0 ? highest : 0;
});
if (allSamples.every((s) => s === null)) {
return null;
}
const highestTimestamp = Math.max(...allSamples.filter((s) => s !== null));
return highestTimestamp;
};
const getDuration = (parserState) => {
const structure = parserState.structure.getStructure();
if (structure.type === 'matroska') {
return getDurationFromMatroska(structure.boxes);
}
if (structure.type === 'iso-base-media') {
return getDurationFromIsoBaseMedia(parserState);
}
if (structure.type === 'riff') {
return (0, get_duration_2.getDurationFromAvi)(structure);
}
if (structure.type === 'transport-stream') {
return null;
}
if (structure.type === 'mp3') {
return (0, get_duration_1.getDurationFromMp3)(parserState);
}
if (structure.type === 'wav') {
return (0, get_duration_from_wav_1.getDurationFromWav)(parserState);
}
if (structure.type === 'aac') {
return null;
}
if (structure.type === 'flac') {
return (0, get_duration_from_flac_1.getDurationFromFlac)(parserState);
}
if (structure.type === 'm3u') {
return (0, get_duration_from_m3u_1.getDurationFromM3u)(parserState);
}
throw new Error('Has no duration ' + structure);
};
exports.getDuration = getDuration;
// `duration` just grabs from metadata, and otherwise returns null
// Therefore just checking if we have tracks
const hasDuration = (parserState) => {
const structure = parserState.structure.getStructureOrNull();
if (structure === null) {
return false;
}
return (0, get_tracks_1.getHasTracks)(parserState, true);
};
exports.hasDuration = hasDuration;
// `slowDuration` goes through everything, and therefore is false
// Unless it it somewhere in the metadata and is non-null
const hasSlowDuration = (parserState) => {
try {
if (!(0, exports.hasDuration)(parserState)) {
return false;
}
return (0, exports.getDuration)(parserState) !== null;
}
catch (_a) {
return false;
}
};
exports.hasSlowDuration = hasSlowDuration;