From aaf87d62c9fece64070f020a978d5c47804490c2 Mon Sep 17 00:00:00 2001 From: WardPearce Date: Wed, 11 Feb 2026 06:47:21 +1300 Subject: [PATCH] Improvements to drawTimelineThumbnail --- materialious/electron/package-lock.json | 4 +- materialious/src/lib/components/Player.svelte | 1 + materialious/src/lib/timelineThumbnails.ts | 52 +++++++++++-------- 3 files changed, 32 insertions(+), 25 deletions(-) diff --git a/materialious/electron/package-lock.json b/materialious/electron/package-lock.json index fd0296f3..b1c24859 100644 --- a/materialious/electron/package-lock.json +++ b/materialious/electron/package-lock.json @@ -1,12 +1,12 @@ { "name": "Materialious", - "version": "1.13.17", + "version": "1.13.18", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "Materialious", - "version": "1.13.17", + "version": "1.13.18", "license": "MIT", "dependencies": { "@capacitor-community/electron": "^5.0.0", diff --git a/materialious/src/lib/components/Player.svelte b/materialious/src/lib/components/Player.svelte index 9e3bc7fa..a68d4a91 100644 --- a/materialious/src/lib/components/Player.svelte +++ b/materialious/src/lib/components/Player.svelte @@ -1143,6 +1143,7 @@ canvasContext, playerTimelineThumbnailsCache, playerTimelineThumbnails, + data.video, time ); } diff --git a/materialious/src/lib/timelineThumbnails.ts b/materialious/src/lib/timelineThumbnails.ts index cb6af265..b8b1c041 100644 --- a/materialious/src/lib/timelineThumbnails.ts +++ b/materialious/src/lib/timelineThumbnails.ts @@ -85,17 +85,24 @@ export async function drawTimelineThumbnail( ctx: CanvasRenderingContext2D, imageCache: ImageCache, thumbnails: TimelineThumbnail[], - time: number + video: VideoPlay, + currentTime: number ): Promise { if (!thumbnails.length) return; - const timeInMs = time * 1000; + const timeInMs = currentTime * 1000; - const closest = thumbnails.reduce((prev, curr) => - Math.abs(curr.time - timeInMs) < Math.abs(prev.time - timeInMs) ? curr : prev - ); + const closest = thumbnails.reduce((prev, curr) => { + return Math.abs(curr.time - timeInMs) < Math.abs(prev.time - timeInMs) ? curr : prev; + }); - if (!closest.url) return; + let spriteSheetEndTime: number; + const nextThumbnail = thumbnails.find((thumb) => thumb.time > closest.time); + if (nextThumbnail) { + spriteSheetEndTime = nextThumbnail.time; + } else { + spriteSheetEndTime = video.lengthSeconds * 1000; + } const img = await imageCache.load(closest.url); if (!img) { @@ -105,24 +112,23 @@ export async function drawTimelineThumbnail( const sheetWidth = img.width; const sheetHeight = img.height; - const cols = Math.floor(sheetWidth / closest.width); - const rows = Math.floor(sheetHeight / closest.height); + const thumbWidth = closest.width; + const thumbHeight = closest.height; + + const cols = Math.floor(sheetWidth / thumbWidth); + const rows = Math.floor(sheetHeight / thumbHeight); + const thumbnailsPerSheet = cols * rows; - const indexInSheet = closest.index % thumbnailsPerSheet; - const thumbX = (indexInSheet % cols) * closest.width; - const thumbY = Math.floor(indexInSheet / cols) * closest.height; + const elapsedTime = timeInMs - closest.time; + const totalDuration = spriteSheetEndTime - closest.time; + const elapsedPercentage = Math.min(Math.max(elapsedTime / totalDuration, 0), 1); - ctx.clearRect(0, 0, closest.width, closest.height); - ctx.drawImage( - img, - thumbX, - thumbY, - closest.width, - closest.height, - 0, - 0, - closest.width, - closest.height - ); + const indexInSheet = Math.floor(elapsedPercentage * thumbnailsPerSheet); + + const thumbX = (indexInSheet % cols) * thumbWidth; + const thumbY = Math.floor(indexInSheet / cols) * thumbHeight; + + ctx.clearRect(0, 0, thumbWidth, thumbHeight); + ctx.drawImage(img, thumbX, thumbY, thumbWidth, thumbHeight, 0, 0, thumbWidth, thumbHeight); }