fix(web): viewport reactivity, off-screen thumbhashes being rendered (#15435)

* viewport optimizations

* fade in

* async bitmap

* fast path for smaller date groups

---------

Co-authored-by: Alex <alex.tran1502@gmail.com>
This commit is contained in:
Mert 2025-02-21 07:38:12 +03:00 committed by GitHub
parent ac36effb45
commit 52f21fb331
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 183 additions and 52 deletions

View file

@ -39,6 +39,7 @@
thumbnailSize?: number | undefined;
thumbnailWidth?: number | undefined;
thumbnailHeight?: number | undefined;
eagerThumbhash?: boolean;
selected?: boolean;
selectionCandidate?: boolean;
disabled?: boolean;
@ -71,6 +72,7 @@
thumbnailSize = undefined,
thumbnailWidth = undefined,
thumbnailHeight = undefined,
eagerThumbhash = true,
selected = false,
selectionCandidate = false,
disabled = false,
@ -113,7 +115,6 @@
let width = $derived(thumbnailSize || thumbnailWidth || 235);
let height = $derived(thumbnailSize || thumbnailHeight || 235);
let display = $derived(intersecting);
const onIconClickedHandler = (e?: MouseEvent) => {
e?.stopPropagation();
@ -207,7 +208,11 @@
? 'bg-gray-300'
: 'bg-immich-primary/20 dark:bg-immich-dark-primary/20'}"
>
{#if !loaded && asset.thumbhash}
<!-- TODO: Rendering thumbhashes for offscreen assets is a ton of overhead.
This is here to ensure thumbhashes appear on the first
frame instead of a gray box for smaller date groups,
where the overhead (while wasteful) does not cause major issues. -->
{#if eagerThumbhash && !loaded && asset.thumbhash}
<canvas
use:thumbhash={{ base64ThumbHash: asset.thumbhash }}
class="absolute object-cover z-10"
@ -217,7 +222,17 @@
></canvas>
{/if}
{#if display}
{#if intersecting}
{#if !eagerThumbhash && !loaded && asset.thumbhash}
<canvas
use:thumbhash={{ base64ThumbHash: asset.thumbhash }}
class="absolute object-cover z-10"
style:width="{width}px"
style:height="{height}px"
out:fade={{ duration: THUMBHASH_FADE_DURATION }}
></canvas>
{/if}
<!-- svelte queries for all links on afterNavigate, leading to performance problems in asset-grid which updates
the navigation url on scroll. Replace this with button for now. -->
<div