improvements and bugfixes

pull/333/head
Mikael Finstad 6 years ago
parent 5346d412b9
commit e2b0053a7a

@ -178,6 +178,8 @@ const App = memo(() => {
const durationSafe = duration || 1;
const zoomedDuration = duration != null ? duration / zoom : undefined;
const isCustomFormatSelected = fileFormat !== detectedFileFormat;
const firstUpdateRef = useRef(true);
function safeSetConfig(key, value) {
@ -946,7 +948,7 @@ const App = memo(() => {
Try one of the following before exporting again:
<ol>
{detectedFileFormat === 'mp4' && <li>Change output <b>Format</b> from <b>MP4</b> to <b>MOV</b></li>}
<li>Select a different output <b>Format</b> (<b>matroska</b> takes almost everything)</li>
<li>Select a different output <b>Format</b> (<b>matroska</b> and <b>mp4</b> support most codecs)</li>
<li>Exclude unnecessary <b>Tracks</b></li>
<li>Try both <b>Normal cut</b> and <b>Keyframe cut</b></li>
<li>Set a different <b>Working directory</b></li>
@ -956,9 +958,9 @@ const App = memo(() => {
</div>
);
const { value } = await ReactSwal.fire({ title: i18n.t('Unable to export this file'), html, timer: null, showConfirmButton: true, showCancelButton: true, confirmButtonText: i18n.t('OK'), cancelButtonText: i18n.t('Report') });
const { value } = await ReactSwal.fire({ title: i18n.t('Unable to export this file'), html, timer: null, showConfirmButton: true, showCancelButton: true, cancelButtonText: i18n.t('OK'), confirmButtonText: i18n.t('Report'), reverseButtons: true, focusCancel: true });
if (!value) {
if (value) {
openSendReportDialogWithState(err);
}
}, [openSendReportDialogWithState, detectedFileFormat]);
@ -989,7 +991,7 @@ const App = memo(() => {
customOutDir,
filePath,
outFormat: fileFormat,
isOutFormatUserSelected: fileFormat !== detectedFileFormat,
isCustomFormatSelected,
videoDuration: duration,
rotation: effectiveRotation,
copyStreamIds,
@ -1006,6 +1008,8 @@ const App = memo(() => {
await autoMergeSegments({
customOutDir,
sourceFile: filePath,
outFormat: fileFormat,
isCustomFormatSelected,
segmentPaths: outFiles,
});
}
@ -1037,9 +1041,9 @@ const App = memo(() => {
}
}, [
effectiveRotation, outSegments, handleCutFailed,
working, duration, filePath, keyframeCut, detectedFileFormat,
working, duration, filePath, keyframeCut,
autoMerge, customOutDir, fileFormat, haveInvalidSegs, copyStreamIds, numStreamsToCopy,
exportExtraStreams, nonCopiedExtraStreams, outputDir, shortestFlag,
exportExtraStreams, nonCopiedExtraStreams, outputDir, shortestFlag, isCustomFormatSelected,
]);
const capture = useCallback(async () => {

@ -152,10 +152,10 @@ const StreamsSelector = memo(({
</tbody>
</table>
{externalFilesEntries.length > 0 && !areWeCutting && (
{externalFilesEntries.length > 0 && (
<div style={{ margin: '10px 0' }}>
<div>
{t('If the streams have different length, do you want to make the combined output file as long as the longest stream or the shortest stream?')}
{t('When tracks have different lengths, do you want to make the output file as long as the longest or the shortest track?')}
</div>
<SegmentedControl
options={[{ label: t('Longest'), value: 'longest' }, { label: t('Shortest'), value: 'shortest' }]}

@ -255,9 +255,13 @@ async function cut({
await transferTimestamps(filePath, outPath);
}
function getOutFileExtension({ isCustomFormatSelected, outFormat, filePath }) {
return isCustomFormatSelected ? `.${getExtensionForFormat(outFormat)}` : extname(filePath);
}
export async function cutMultiple({
customOutDir, filePath, segments: segmentsUnsorted, videoDuration, rotation,
onProgress, keyframeCut, copyStreamIds, outFormat, isOutFormatUserSelected,
onProgress, keyframeCut, copyStreamIds, outFormat, isCustomFormatSelected,
appendFfmpegCommandLog, shortestFlag,
}) {
const segments = sortBy(segmentsUnsorted, 'cutFrom');
@ -276,7 +280,7 @@ export async function cutMultiple({
const cutToStr = formatDuration({ seconds: end, fileNameFriendly: true });
const segNamePart = name ? `-${filenamify(name)}` : '';
const cutSpecification = `${cutFromStr}-${cutToStr}${segNamePart}`.substr(0, 200);
const ext = isOutFormatUserSelected ? `.${getExtensionForFormat(outFormat)}` : extname(filePath);
const ext = getOutFileExtension({ isCustomFormatSelected, outFormat, filePath });
const fileName = `${cutSpecification}${ext}`;
const outPath = getOutPath(customOutDir, filePath, fileName);
@ -393,22 +397,27 @@ export async function html5ifyDummy(filePath, outPath) {
await transferTimestamps(filePath, outPath);
}
export async function mergeFiles({ paths, outPath, allStreams }) {
export async function mergeFiles({ paths, outPath, allStreams, outFormat }) {
console.log('Merging files', { paths }, 'to', outPath);
// https://blog.yo1.dog/fix-for-ffmpeg-protocol-not-on-whitelist-error-for-urls/
// Keep this similar to cut()
const ffmpegArgs = [
'-hide_banner',
// https://blog.yo1.dog/fix-for-ffmpeg-protocol-not-on-whitelist-error-for-urls/
'-f', 'concat', '-safe', '0', '-protocol_whitelist', 'file,pipe', '-i', '-',
'-c', 'copy',
...(allStreams ? ['-map', '0'] : []),
'-map_metadata', '0',
// https://video.stackexchange.com/questions/23741/how-to-prevent-ffmpeg-from-dropping-metadata
'-movflags', 'use_metadata_tags',
// See https://github.com/mifi/lossless-cut/issues/170
'-ignore_unknown',
...(outFormat ? ['-f', outFormat] : []),
'-y', outPath,
];
@ -428,10 +437,12 @@ export async function mergeFiles({ paths, outPath, allStreams }) {
console.log(result.stdout);
}
export async function autoMergeSegments({ customOutDir, sourceFile, segmentPaths }) {
const ext = extname(sourceFile);
const outPath = getOutPath(customOutDir, sourceFile, `cut-merged-${new Date().getTime()}${ext}`);
await mergeFiles({ paths: segmentPaths, outPath });
export async function autoMergeSegments({ customOutDir, sourceFile, isCustomFormatSelected, outFormat, segmentPaths }) {
const ext = getOutFileExtension({ isCustomFormatSelected, outFormat, filePath: sourceFile });
const fileName = `cut-merged-${new Date().getTime()}${ext}`;
const outPath = getOutPath(customOutDir, sourceFile, fileName);
await mergeFiles({ paths: segmentPaths, outPath, outFormat, allStreams: true });
await pMap(segmentPaths, path => fs.unlink(path), { concurrency: 5 });
}

Loading…
Cancel
Save