refactor(SVGPanZoom): Fix memory leaking - consolidate zoom lifecycle into PanzoomContainer (#23236)
* refactor(SVGPanZoom): attach panzoom via use: action and remove unused parent bind:this * refactor: centralize panzoom in createPanzoomAction and align ImagePreview cleanup * refactor(panzoom): consolidate zoom lifecycle into PanzoomContainer and remove action-based wiring
This commit is contained in:
@@ -293,7 +293,6 @@
|
||||
// ── File preview management ──────────────────────────────────────────
|
||||
const clearFilePreview = () => {
|
||||
fileContent = null;
|
||||
filePreviewRef?.disposePanzoom();
|
||||
if (fileImageUrl) {
|
||||
URL.revokeObjectURL(fileImageUrl);
|
||||
fileImageUrl = null;
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
<script lang="ts">
|
||||
import { getContext, onDestroy, tick } from 'svelte';
|
||||
import panzoom, { type PanZoom } from 'panzoom';
|
||||
import { getContext, tick } from 'svelte';
|
||||
import { marked } from 'marked';
|
||||
import DOMPurify from 'dompurify';
|
||||
import { settings } from '$lib/stores';
|
||||
@@ -8,6 +7,7 @@
|
||||
import { initMermaid, renderMermaidDiagram } from '$lib/utils';
|
||||
import Spinner from '../../common/Spinner.svelte';
|
||||
import PDFViewer from '../../common/PDFViewer.svelte';
|
||||
import PanzoomContainer from '../../common/PanzoomContainer.svelte';
|
||||
import JsonTreeView from './JsonTreeView.svelte';
|
||||
import NotebookView from './NotebookView.svelte';
|
||||
import SqliteView from './SqliteView.svelte';
|
||||
@@ -250,38 +250,14 @@
|
||||
showRaw = true;
|
||||
}
|
||||
|
||||
let pzInstance: PanZoom | null = null;
|
||||
|
||||
const initImagePanzoom = (node: HTMLElement) => {
|
||||
pzInstance = panzoom(node, {
|
||||
bounds: true,
|
||||
boundsPadding: 0.1,
|
||||
zoomSpeed: 0.065,
|
||||
zoomDoubleClickSpeed: 1
|
||||
});
|
||||
};
|
||||
|
||||
let panzoomRef: PanzoomContainer;
|
||||
export const resetImageView = () => {
|
||||
if (pzInstance) {
|
||||
pzInstance.moveTo(0, 0);
|
||||
pzInstance.zoomAbs(0, 0, 1);
|
||||
}
|
||||
};
|
||||
|
||||
export const disposePanzoom = () => {
|
||||
if (pzInstance) {
|
||||
pzInstance.dispose();
|
||||
pzInstance = null;
|
||||
}
|
||||
panzoomRef?.reset();
|
||||
};
|
||||
|
||||
export const resetPdfView = () => {
|
||||
pdfViewerRef?.resetView();
|
||||
};
|
||||
|
||||
onDestroy(() => {
|
||||
disposePanzoom();
|
||||
});
|
||||
</script>
|
||||
|
||||
<div
|
||||
@@ -293,14 +269,18 @@
|
||||
{#if fileLoading}
|
||||
<div class="flex items-center justify-center h-full"><Spinner className="size-4" /></div>
|
||||
{:else if fileImageUrl !== null}
|
||||
<div class="w-full h-full flex items-center justify-center" use:initImagePanzoom>
|
||||
<PanzoomContainer
|
||||
bind:this={panzoomRef}
|
||||
className="w-full h-full flex items-center justify-center"
|
||||
options={{ zoomDoubleClickSpeed: 1 }}
|
||||
>
|
||||
<img
|
||||
src={fileImageUrl}
|
||||
alt={selectedFile?.split('/').pop()}
|
||||
class="max-w-full max-h-full object-contain p-3"
|
||||
draggable="false"
|
||||
/>
|
||||
</div>
|
||||
</PanzoomContainer>
|
||||
{:else if fileVideoUrl !== null}
|
||||
<div class="w-full h-full flex items-center justify-center bg-black">
|
||||
<!-- svelte-ignore a11y-media-has-caption -->
|
||||
@@ -343,9 +323,10 @@
|
||||
</div>
|
||||
{:else if fileOfficeSlides !== null && fileOfficeSlides.length > 0}
|
||||
<div class="flex flex-col h-full">
|
||||
<div
|
||||
class="w-full flex-1 min-h-0 flex items-center justify-center overflow-hidden"
|
||||
use:initImagePanzoom
|
||||
<PanzoomContainer
|
||||
bind:this={panzoomRef}
|
||||
className="w-full flex-1 min-h-0 flex items-center justify-center overflow-hidden"
|
||||
options={{ zoomDoubleClickSpeed: 1 }}
|
||||
>
|
||||
<img
|
||||
src={fileOfficeSlides[currentSlide]}
|
||||
@@ -353,7 +334,7 @@
|
||||
class="max-w-full max-h-full object-contain p-3"
|
||||
draggable="false"
|
||||
/>
|
||||
</div>
|
||||
</PanzoomContainer>
|
||||
{#if fileOfficeSlides.length > 1}
|
||||
<div
|
||||
class="flex items-center justify-center gap-3 py-2 px-3 border-t border-gray-100 dark:border-gray-800 text-xs text-gray-500"
|
||||
|
||||
Reference in New Issue
Block a user