Files
gnommoplayer/slide-preview-integration.md
2026-04-11 09:21:22 +02:00

6.8 KiB
Raw Permalink Blame History

Slide Preview Integration Guide

This guide is for integrating an authoritative slide preview into another React + Vite UI, using the real GlitchPlayer runtime rather than a custom thumbnail or placeholder renderer.

Goal

When the editor user selects a slide, the preview should be:

  • the real GlitchPlayer
  • moved to the selected slide
  • paused on that slide
  • rendered with the same layout, video, timing, and slide runtime as the final presentation

This is the correct preview surface when fidelity matters more than efficiency.

Use This, Not A Custom Thumbnail

For the main preview panel:

  • use GlitchPlayer
  • with mode="slide-preview"
  • and targetSlideId

Do not use:

  • GlitchSlideThumbnail
  • GlitchSlideRenderer
  • a hand-built editor preview

Those are useful for slide lists and lightweight surfaces, but not for the authoritative preview.

Built Files To Consume

If the integration agent is only allowed to fetch built artifacts from this repo, use:

Build them with:

npm run build

That command now produces both the demo app build and the vendor bundle.

What To Import

From gnommoplayer.js, the preview integration should import:

  • GlitchPlayer
  • defaultSlideRegistry

From gnommoplayer.css, import the player stylesheet once near the app root.

Example:

import "../vendor/gnommoplayer/gnommoplayer.css";
import {
  GlitchPlayer,
  defaultSlideRegistry,
} from "../vendor/gnommoplayer/gnommoplayer.js";

Required Data

The preview must receive a full presentation object, not just one slide.

That presentation should include:

  • id
  • title
  • version
  • durationSec
  • segments
  • slides

Why:

  • the player needs the full timeline
  • the player needs the talking-head video segments
  • the player derives the active slide from presentation timing
  • the player must match the final runtime, not a simplified editor view

Preview Contract

The preview panel should render the player like this:

<GlitchPlayer
  presentation={presentation}
  slideRegistry={defaultSlideRegistry}
  mode="slide-preview"
  targetSlideId={selectedSlideId}
  initialSessionId={`editor-preview-${presentation.id}`}
/>

Behavior of this mode:

  • the player jumps to the targeted slides startTimeSec
  • playback starts paused
  • the real player UI and layout are used
  • the talking-head video is still part of the runtime surface

The host app should wrap this in a dedicated preview component.

Example:

import { useEffect, useState } from "react";
import "../vendor/gnommoplayer/gnommoplayer.css";
import {
  GlitchPlayer,
  defaultSlideRegistry,
} from "../vendor/gnommoplayer/gnommoplayer.js";

export function SlidePreviewPanel({
  presentationId,
  selectedSlideId,
}: {
  presentationId: string;
  selectedSlideId: string | null;
}) {
  const [presentation, setPresentation] = useState(null);
  const [error, setError] = useState(null);

  useEffect(() => {
    let cancelled = false;

    fetch(`/api/videos/${presentationId}/export`)
      .then((response) => {
        if (!response.ok) {
          throw new Error(`Preview fetch failed: ${response.status}`);
        }

        return response.json();
      })
      .then((data) => {
        if (!cancelled) {
          setPresentation(data);
          setError(null);
        }
      })
      .catch((caughtError) => {
        if (!cancelled) {
          setError(String(caughtError));
        }
      });

    return () => {
      cancelled = true;
    };
  }, [presentationId]);

  if (error) {
    return <div>Preview error: {error}</div>;
  }

  if (!presentation || !selectedSlideId) {
    return <div>Select a slide to preview.</div>;
  }

  return (
    <div style={{ width: "100%", height: "100%" }}>
      <GlitchPlayer
        presentation={presentation}
        slideRegistry={defaultSlideRegistry}
        mode="slide-preview"
        targetSlideId={selectedSlideId}
        initialSessionId={`editor-preview-${presentation.id}`}
      />
    </div>
  );
}

How The Editor Should Drive It

The editor should keep one piece of selection state:

  • selectedSlideId

When the user clicks a slide in the editor:

  1. update selectedSlideId
  2. keep the same presentation
  3. re-render GlitchPlayer with the new targetSlideId

That is enough for the player to move to the correct slide.

Important Implementation Notes

1. Use The Full Presentation

Do not try to construct a fake one-slide presentation for preview.

That creates drift in:

  • timing
  • fullscreen transitions
  • video positioning
  • segment masking
  • variant behavior

The preview should be the real timeline.

2. It Is Fine If The Video Loads Again

That is an acceptable tradeoff for now.

The goal of the editor preview is correctness:

  • same player
  • same slide runtime
  • same layout

Not maximum efficiency.

3. Keep Thumbnails Separate

This preview guide is only for the main preview panel.

For slide list cards:

  • GlitchSlideThumbnail is still appropriate

For the large “truth” preview:

  • use GlitchPlayer

4. Prefer Stable Slide Ids

The editor should pass a stable selectedSlideId, ideally the same id used in the exported presentation payload.

The preview mechanism depends on exact id matching:

targetSlideId={selectedSlideId}

5. Do Not Replace The Players Internal Registry Logic

Use:

slideRegistry={defaultSlideRegistry}

unless the host intentionally provides a superset registry.

The preview should not invent its own runtime component resolution.

When To Use GlitchSlideThumbnail Instead

Use GlitchSlideThumbnail only for:

  • slide list rows
  • compact cards
  • mini previews in inspector sidebars

Do not use it as a substitute for the main preview panel.

If the current editor preview is “kind of not working,” replace it with this sequence:

  1. Keep the slide list as-is for now
  2. Remove the custom preview widget
  3. Add a dedicated preview panel component
  4. Fetch the full exported presentation JSON
  5. Render:
<GlitchPlayer
  presentation={presentation}
  slideRegistry={defaultSlideRegistry}
  mode="slide-preview"
  targetSlideId={selectedSlideId}
/>

That gives you a preview surface that is as close to final runtime as possible.

Short Handoff Note

If you need the shortest possible instruction for the other agent, use this:

Use the real player for slide preview, not the thumbnail renderer. Import GlitchPlayer and defaultSlideRegistry from dist/vendor/gnommoplayer.js, import dist/vendor/gnommoplayer.css, fetch the full presentation JSON, and render GlitchPlayer with mode="slide-preview" and targetSlideId={selectedSlideId}.