Add video viewer modal for gallery videos
All checks were successful
Build and Push Frontend Docker Image / build (push) Successful in 30s

- Click on video thumbnail to open in large viewer
- Video plays on hover, pauses when mouse leaves
- Close viewer by clicking X or clicking outside video

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Debian
2026-01-08 01:08:13 +00:00
parent ad4114ab82
commit 52dd0d8766
3 changed files with 88 additions and 1 deletions

View File

@@ -427,7 +427,7 @@ function renderGallery(container, items) {
<div class="gallery-item">
<div class="gallery-item-media">
${item.status === 'completed'
? `<video src="/api/content/${item.id}/stream" muted loop onmouseenter="this.play()" onmouseleave="this.pause()"></video>`
? `<video src="/api/content/${item.id}/stream" muted loop data-content-id="${item.id}"></video>`
: '<div style="display:flex;align-items:center;justify-content:center;height:100%;color:var(--gray-500)">' + item.status + '</div>'
}
<span class="gallery-item-status ${item.status}">${item.status}</span>
@@ -445,6 +445,19 @@ function renderGallery(container, items) {
</div>
`).join('');
// Video hover play/pause and click to view
container.querySelectorAll('.gallery-item-media video').forEach(video => {
video.addEventListener('mouseenter', () => video.play());
video.addEventListener('mouseleave', () => {
video.pause();
video.currentTime = 0;
});
video.addEventListener('click', () => {
const contentId = video.dataset.contentId;
openVideoViewer(`/api/content/${contentId}/stream`);
});
});
container.querySelectorAll('.delete-content-btn').forEach(btn => {
btn.addEventListener('click', async function() {
const contentId = parseInt(this.dataset.contentId, 10);
@@ -673,6 +686,28 @@ document.getElementById('modal-overlay').addEventListener('click', (e) => {
if (e.target === e.currentTarget) hideModal();
});
// Video Viewer
const videoViewer = document.getElementById('video-viewer');
const videoViewerPlayer = document.getElementById('video-viewer-player');
const videoViewerClose = document.getElementById('video-viewer-close');
function openVideoViewer(src) {
videoViewerPlayer.src = src;
videoViewer.classList.remove('hidden');
videoViewerPlayer.play();
}
function closeVideoViewer() {
videoViewerPlayer.pause();
videoViewerPlayer.src = '';
videoViewer.classList.add('hidden');
}
videoViewerClose.addEventListener('click', closeVideoViewer);
videoViewer.addEventListener('click', (e) => {
if (e.target === videoViewer) closeVideoViewer();
});
// Pagination
function renderPagination(container, pagination, loadFn) {
const { page, totalPages } = pagination;