mirror of
https://github.com/mifi/lossless-cut.git
synced 2024-11-22 10:22:31 +01:00
Implement split into fixed duration segments #469
This commit is contained in:
parent
7da209b253
commit
1cd3139ff4
@ -127,6 +127,12 @@ module.exports = (app, mainWindow, newVersion) => {
|
||||
mainWindow.webContents.send('createNumSegments');
|
||||
},
|
||||
},
|
||||
{
|
||||
label: 'Create fixed duration segments',
|
||||
click() {
|
||||
mainWindow.webContents.send('createFixedDurationSegments');
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
|
11
src/App.jsx
11
src/App.jsx
@ -48,7 +48,7 @@ import {
|
||||
getOutPath, formatDuration, toast, errorToast, showFfmpegFail, setFileNameTitle,
|
||||
promptTimeOffset, generateColor, getOutDir, withBlur, checkDirWriteAccess, dirExists, askForOutDir,
|
||||
openDirToast, askForHtml5ifySpeed, askForYouTubeInput, isMasBuild, isStoreBuild, askForFileOpenAction,
|
||||
askForImportChapters, createNumSegments,
|
||||
askForImportChapters, createNumSegments, createFixedDurationSegments,
|
||||
} from './util';
|
||||
import { openSendReportDialog } from './reporting';
|
||||
import { fallbackLng } from './i18n';
|
||||
@ -1631,6 +1631,12 @@ const App = memo(() => {
|
||||
if (segments) loadCutSegments(segments);
|
||||
}
|
||||
|
||||
async function createFixedDurationSegments2() {
|
||||
if (!checkFileOpened()) return;
|
||||
const segments = await createFixedDurationSegments(duration);
|
||||
if (segments) loadCutSegments(segments);
|
||||
}
|
||||
|
||||
electron.ipcRenderer.on('file-opened', fileOpened);
|
||||
electron.ipcRenderer.on('close-file', closeFile);
|
||||
electron.ipcRenderer.on('html5ify', html5ifyCurrentFile);
|
||||
@ -1647,6 +1653,7 @@ const App = memo(() => {
|
||||
electron.ipcRenderer.on('batchConvertFriendlyFormat', batchConvertFriendlyFormat);
|
||||
electron.ipcRenderer.on('openSendReportDialog', openSendReportDialog2);
|
||||
electron.ipcRenderer.on('createNumSegments', createNumSegments2);
|
||||
electron.ipcRenderer.on('createFixedDurationSegments', createFixedDurationSegments2);
|
||||
|
||||
return () => {
|
||||
electron.ipcRenderer.removeListener('file-opened', fileOpened);
|
||||
@ -1664,7 +1671,7 @@ const App = memo(() => {
|
||||
electron.ipcRenderer.removeListener('openAbout', openAbout);
|
||||
electron.ipcRenderer.removeListener('batchConvertFriendlyFormat', batchConvertFriendlyFormat);
|
||||
electron.ipcRenderer.removeListener('openSendReportDialog', openSendReportDialog2);
|
||||
electron.ipcRenderer.removeListener('createNumSegments', createNumSegments2);
|
||||
electron.ipcRenderer.removeListener('createFixedDurationSegments', createFixedDurationSegments2);
|
||||
};
|
||||
}, [
|
||||
mergeFiles, outputDir, filePath, isFileOpened, customOutDir, startTimeOffset, html5ifyCurrentFile,
|
||||
|
41
src/util.js
41
src/util.js
@ -263,9 +263,9 @@ export async function askForImportChapters() {
|
||||
return value;
|
||||
}
|
||||
|
||||
async function askForNumSegments() {
|
||||
const maxSegments = 1000;
|
||||
const maxSegments = 300;
|
||||
|
||||
async function askForNumSegments() {
|
||||
const { value } = await Swal.fire({
|
||||
input: 'number',
|
||||
inputAttributes: {
|
||||
@ -277,9 +277,7 @@ async function askForNumSegments() {
|
||||
text: i18n.t('Divide timeline into a number of equal length segments'),
|
||||
inputValidator: (v) => {
|
||||
const parsed = parseInt(v, 10);
|
||||
if (!Number.isNaN(parsed) && parsed >= 2 && parsed <= maxSegments) {
|
||||
return undefined;
|
||||
}
|
||||
if (!Number.isNaN(parsed) && parsed >= 2 && parsed <= maxSegments) return undefined;
|
||||
return i18n.t('Please input a valid number of segments');
|
||||
},
|
||||
});
|
||||
@ -299,3 +297,36 @@ export async function createNumSegments(fileDuration) {
|
||||
}
|
||||
return edl;
|
||||
}
|
||||
|
||||
async function askForSegmentDuration(fileDuration) {
|
||||
const example = '00:00:05.123';
|
||||
const { value } = await Swal.fire({
|
||||
input: 'text',
|
||||
showCancelButton: true,
|
||||
inputValue: '00:00:00.000',
|
||||
text: i18n.t('Divide timeline into a number of segments with the specified length'),
|
||||
inputValidator: (v) => {
|
||||
const duration = parseDuration(v);
|
||||
if (duration != null) {
|
||||
const numSegments = Math.ceil(fileDuration / duration);
|
||||
if (duration > 0 && duration < fileDuration && numSegments <= maxSegments) return undefined;
|
||||
}
|
||||
return i18n.t('Please input a valid duration. Example: {{example}}', { example });
|
||||
},
|
||||
});
|
||||
|
||||
if (value == null) return undefined;
|
||||
|
||||
return parseDuration(value);
|
||||
}
|
||||
|
||||
export async function createFixedDurationSegments(fileDuration) {
|
||||
const segmentDuration = await askForSegmentDuration(fileDuration);
|
||||
if (segmentDuration == null) return undefined;
|
||||
const edl = [];
|
||||
for (let start = 0; start < fileDuration; start += segmentDuration) {
|
||||
const end = start + segmentDuration;
|
||||
edl.push({ start, end: end >= fileDuration ? undefined : end });
|
||||
}
|
||||
return edl;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user