feat(project): optimize image imports and converter
- Optimize imported scene preview images (smart WebP/JPEG/PNG, preserve alpha, keep pixel size) - Update converter to re-encode existing image assets with same algorithm - Improve import/export progress overlay and reduce presentation slide stutter Made-with: Cursor
This commit is contained in:
+36
-2
@@ -27,6 +27,20 @@ import {
|
||||
waitForEditorWindowReady,
|
||||
} from './windows/createWindows';
|
||||
|
||||
function emitZipProgress(evt: {
|
||||
kind: 'import' | 'export';
|
||||
stage: string;
|
||||
percent: number;
|
||||
detail?: string;
|
||||
}): void {
|
||||
for (const win of BrowserWindow.getAllWindows()) {
|
||||
win.webContents.send(
|
||||
evt.kind === 'import' ? ipcChannels.project.importZipProgress : ipcChannels.project.exportZipProgress,
|
||||
evt,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Отключение GPU ломает скорость вторичных окон (презентация/пульт — WebGL). По умолчанию не трогаем.
|
||||
* При чёрном экране в упакованной сборке: `DND_DISABLE_GPU=1`.
|
||||
@@ -403,7 +417,18 @@ async function main() {
|
||||
if (canceled || !filePaths[0]) {
|
||||
return { canceled: true as const };
|
||||
}
|
||||
const project = await projectStore.importProjectFromExternalZip(filePaths[0]);
|
||||
const srcPath = filePaths[0];
|
||||
emitZipProgress({ kind: 'import', stage: 'copy', percent: 0, detail: 'Копирование…' });
|
||||
// Let store import; progress for unzip is emitted from unzipToDir wrapper in store.
|
||||
const project = await projectStore.importProjectFromExternalZip(srcPath, (p) => {
|
||||
emitZipProgress({
|
||||
kind: 'import',
|
||||
stage: p.stage,
|
||||
percent: p.percent,
|
||||
...(p.detail ? { detail: p.detail } : null),
|
||||
});
|
||||
});
|
||||
emitZipProgress({ kind: 'import', stage: 'done', percent: 100, detail: 'Готово' });
|
||||
emitSessionState();
|
||||
return { canceled: false as const, project };
|
||||
});
|
||||
@@ -428,7 +453,16 @@ async function main() {
|
||||
if (!lower.endsWith('.dnd.zip')) {
|
||||
dest = lower.endsWith('.zip') ? dest.replace(/\.zip$/iu, '.dnd.zip') : `${dest}.dnd.zip`;
|
||||
}
|
||||
await projectStore.exportProjectZipToPath(projectId, dest);
|
||||
emitZipProgress({ kind: 'export', stage: 'copy', percent: 0, detail: 'Экспорт…' });
|
||||
await projectStore.exportProjectZipToPath(projectId, dest, (p) => {
|
||||
emitZipProgress({
|
||||
kind: 'export',
|
||||
stage: p.stage,
|
||||
percent: p.percent,
|
||||
...(p.detail ? { detail: p.detail } : null),
|
||||
});
|
||||
});
|
||||
emitZipProgress({ kind: 'export', stage: 'done', percent: 100, detail: 'Готово' });
|
||||
return { canceled: false as const };
|
||||
});
|
||||
registerHandler(ipcChannels.project.deleteProject, async ({ projectId }) => {
|
||||
|
||||
Reference in New Issue
Block a user