Add fullscreen toggle to large images

This commit is contained in:
carlobortolan 2025-01-13 18:10:44 +01:00
parent b74f83694b
commit 416a45bd2f
No known key found for this signature in database
GPG Key ID: 574D9F10F0EED1BE
3 changed files with 60 additions and 1 deletions

View File

@ -0,0 +1,54 @@
'use client';
import { useEffect, RefObject } from 'react';
import { MdFullscreen, MdFullscreenExit } from 'react-icons/md';
import { clsx } from 'clsx/lite';
import { useAppState } from '@/state/AppState';
import LoaderButton from './primitives/LoaderButton';
export default function FullscreenButton({
className,
imageRef,
}: {
className?: string;
imageRef: RefObject<HTMLImageElement | null>;
}) {
const { isFullscreen, setIsFullscreen } = useAppState();
const toggleFullscreen = async () => {
if (!document.fullscreenElement) {
await imageRef.current?.requestFullscreen();
setIsFullscreen && setIsFullscreen(true);
} else {
await document.exitFullscreen();
setIsFullscreen && setIsFullscreen(false);
}
};
useEffect(() => {
const handleKeyDown = (event: KeyboardEvent) => {
if (event.key === 'f' || event.key === 'F') {
toggleFullscreen();
}
};
document.addEventListener('keydown', handleKeyDown);
return () => {
document.removeEventListener('keydown', handleKeyDown);
};
}, [toggleFullscreen]);
return (
<LoaderButton
title="Toggle Fullscreen"
className={clsx(
className,
'text-medium absolute bottom-2 right-2 bg-white p-2 rounded'
)}
icon={isFullscreen ? <MdFullscreenExit size={18} /> : <MdFullscreen size={18} />}
spinnerColor='light-gray'
styleAs='link'
onClick={toggleFullscreen}
/>
);
}

View File

@ -13,6 +13,7 @@ export default function ImageLarge(props: ImageProps) {
blurCompatibilityLevel: blurCompatibilityMode ? 'high' : 'none',
width: IMAGE_WIDTH_LARGE,
height: Math.round(IMAGE_WIDTH_LARGE / aspectRatio),
allowFullscreen: true,
}} />
);
};

View File

@ -6,10 +6,12 @@ import { useAppState } from '@/state/AppState';
import { clsx} from 'clsx/lite';
import Image, { ImageProps } from 'next/image';
import { useCallback, useEffect, useRef, useState } from 'react';
import FullscreenButton from '../FullscreenButton';
export default function ImageWithFallback(props: ImageProps & {
blurCompatibilityLevel?: 'none' | 'low' | 'high'
imgClassName?: string
allowFullscreen?: boolean
}) {
const {
className,
@ -17,6 +19,7 @@ export default function ImageWithFallback(props: ImageProps & {
blurDataURL,
blurCompatibilityLevel = 'low',
imgClassName = 'object-cover h-full',
allowFullscreen,
...rest
} = props;
@ -104,6 +107,7 @@ export default function ImageWithFallback(props: ImageProps & {
onLoad,
onError,
}} />
</div>
{allowFullscreen && <FullscreenButton imageRef={imgRef} />}
</div>
);
}