promptslide 0.3.17 → 0.3.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,19 @@
1
1
  # Changelog
2
2
 
3
+ ## [0.3.19](https://github.com/prompticeu/promptslide/compare/promptslide-v0.3.18...promptslide-v0.3.19) (2026-10-23)
4
+
5
+
6
+ ### Features
7
+
8
+ * add timed autoplay loops and shared slide inspector ([#109](https://github.com/prompticeu/promptslide/issues/109)) ([6393775](https://github.com/prompticeu/promptslide/commit/63937759fd86b996fe69b0a76dd3e18adf0a8a86))
9
+
10
+ ## [0.3.18](https://github.com/prompticeu/promptslide/compare/promptslide-v0.3.17...promptslide-v0.3.18) (2026-10-23)
11
+
12
+
13
+ ### Features
14
+
15
+ * add visual slide editing in studio ([#107](https://github.com/prompticeu/promptslide/issues/107)) ([4dd6651](https://github.com/prompticeu/promptslide/commit/4dd6651269687c6a0d219c8e3b261a9ac11b7876))
16
+
3
17
  ## [0.3.17](https://github.com/prompticeu/promptslide/compare/promptslide-v0.3.16...promptslide-v0.3.17) (2026-09-26)
4
18
 
5
19
 
package/README.md CHANGED
@@ -38,6 +38,82 @@ All commands are run via `npx promptslide <command>`.
38
38
 
39
39
  Use optional, unique slide IDs in `src/deck-config.ts` for stable URL links and annotations. Existing numbered slide links and decks without IDs continue to work.
40
40
 
41
+ ## Auto-loop presentations
42
+
43
+ Open **Slide settings** in the toolbar, or choose **Present** → **Configure loop…**.
44
+ The shared right inspector has **Slide**, **Elements** (local Studio only), and **Comments**
45
+ tabs. Use the existing thumbnail rail to select a slide; its settings follow the selection.
46
+ Each slide has an initial view plus its numbered click steps. Select a timing row to preview
47
+ that exact state on the main canvas, then edit its duration in seconds. The normal navigation
48
+ arrows update the highlighted row too. Unconfigured states use the deck default (5 seconds).
49
+
50
+ **Include in loop** excludes a slide from autoplay while keeping it available for manual
51
+ presentations. Excluded slides show **Skip in loop** on their thumbnails. **Loop defaults**
52
+ contains the default duration and estimated total time. Edits remain buffered when switching
53
+ slides, tabs, or closing the inspector. **Revert** restores the last saved loop settings.
54
+
55
+ **Save settings** in local Studio writes `loop-config.json` in the project folder.
56
+ The CLI embeds it in production builds and preserves it through publish, clone, create,
57
+ and pull. Static presentations save changes in that browser; use **Download settings**
58
+ and put the file in the project folder to include them in later builds or publications.
59
+ Use stable slide IDs so timings survive reordering. Adding steps uses the default duration;
60
+ changing a configured slide's step count flags its timings for review.
61
+
62
+ ```json
63
+ {
64
+ "version": 1,
65
+ "defaultDuration": 5,
66
+ "slides": {
67
+ "intro": { "steps": 0, "dwell": [6] },
68
+ "agents": { "steps": 5, "dwell": [3, 2, 2, 2, 3, 12] },
69
+ "notification": { "excluded": true }
70
+ }
71
+ }
72
+ ```
73
+
74
+ `dwell[0]` is the initial state. Later entries correspond to click steps; missing or
75
+ `null` entries inherit the default. Durations are between 0.1 and 3600 seconds.
76
+ Timing begins after an incoming slide transition; each state duration includes its
77
+ reveal animation. The estimated total excludes slide transitions. Videos and custom
78
+ animations need enough explicit time; their completion is not detected automatically.
79
+
80
+ Choose **Auto-loop** to start in full screen from the first included slide, step zero.
81
+ **Space** pauses or resumes progression, **Left/Right** navigate within the loop and
82
+ restart the state's timer, and **Escape** stops and exits. Timers pause in hidden tabs
83
+ without catching up afterward. Pausing progression does not pause custom animations or
84
+ videos. Slide components remount each cycle so mount-driven animations replay.
85
+
86
+ For unattended use, run `npm run build && npm run preview` and open
87
+ `http://localhost:4173/?loop`. Click once to start. Full screen requires a real user
88
+ interaction; a rejected request shows a retryable error. Keep the computer awake and
89
+ self-host fonts, images, video, and other assets needed offline.
90
+
91
+ Custom SDK hosts can pass `loopConfig` and `onLoopConfigChange` to `SlideDeck` to provide
92
+ settings and their own persistence adapter. CLI Studio's file save endpoint accepts
93
+ validated, same-origin requests on loopback interfaces only.
94
+
95
+ ```tsx
96
+ import { SlideDeck, type LoopConfig } from "promptslide"
97
+
98
+ const loopConfig: LoopConfig = {
99
+ version: 1,
100
+ defaultDuration: 5,
101
+ slides: {
102
+ intro: { dwell: [6] },
103
+ agents: { steps: 2, dwell: [3, 2, 12] },
104
+ notification: { excluded: true }
105
+ }
106
+ }
107
+
108
+ // `slides` is your existing SlideConfig[] in deck order.
109
+ <SlideDeck slides={slides} loopConfig={loopConfig} />
110
+ ```
111
+
112
+ The prop overrides CLI/provider defaults; saved browser settings may override the same
113
+ base configuration locally. CLI publishing reads `loop-config.json`, so keep shared
114
+ timings there rather than only in a React prop. Included slides follow deck order;
115
+ there is no separate playlist order.
116
+
41
117
  ## How It Works
42
118
 
43
119
  1. **You describe** what you want in natural language
package/dist/index.d.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  import { Variants, Transition } from 'framer-motion';
2
2
  import * as react_jsx_runtime from 'react/jsx-runtime';
3
- import React$1 from 'react';
3
+ import React$1, { ReactNode } from 'react';
4
4
  import { ClassValue } from 'clsx';
5
5
 
6
6
  /**
@@ -195,6 +195,18 @@ interface ThemeConfig {
195
195
  /** Typography preferences */
196
196
  fonts?: ThemeFonts;
197
197
  }
198
+ /** Durations in seconds, including the initial state at dwell[0]. */
199
+ interface LoopSlideConfig {
200
+ excluded?: boolean;
201
+ /** Step count when these timings were edited; used to flag changes. */
202
+ steps?: number;
203
+ dwell?: (number | null)[];
204
+ }
205
+ interface LoopConfig {
206
+ version: 1;
207
+ defaultDuration: number;
208
+ slides: Record<string, LoopSlideConfig>;
209
+ }
198
210
 
199
211
  interface AnimationContextValue {
200
212
  /** Current animation step (0 = no animations shown yet) */
@@ -322,6 +334,8 @@ interface UseSlideNavigationReturn {
322
334
  advance: () => void;
323
335
  goBack: () => void;
324
336
  goToSlide: (index: number) => void;
337
+ goToStep: (step: number) => void;
338
+ restartAtSlide: (index: number) => void;
325
339
  onTransitionComplete: () => void;
326
340
  }
327
341
  declare function useSlideNavigation({ slides, initialSlide, onSlideChange }: UseSlideNavigationOptions): UseSlideNavigationReturn;
@@ -341,6 +355,7 @@ interface SlideThemeProviderProps {
341
355
  declare function SlideThemeProvider({ theme, children }: SlideThemeProviderProps): react_jsx_runtime.JSX.Element;
342
356
 
343
357
  interface SlideRendererProps {
358
+ playbackKey?: number;
344
359
  slides: SlideConfig[];
345
360
  currentSlide: number;
346
361
  animationStep: number;
@@ -355,7 +370,7 @@ interface SlideRendererProps {
355
370
  * Renders a single slide with animated transitions.
356
371
  * Extracted from SlideDeck so it can be reused in SlideEmbed and other contexts.
357
372
  */
358
- declare function SlideRenderer({ slides, currentSlide, animationStep, totalSteps, direction, showAllAnimations, transition, directionalTransition, onTransitionComplete }: SlideRendererProps): react_jsx_runtime.JSX.Element;
373
+ declare function SlideRenderer({ playbackKey, slides, currentSlide, animationStep, totalSteps, direction, showAllAnimations, transition, directionalTransition, onTransitionComplete }: SlideRendererProps): react_jsx_runtime.JSX.Element;
359
374
 
360
375
  interface SlideEmbedProps {
361
376
  slides: SlideConfig[];
@@ -461,6 +476,10 @@ interface SlideDeckProps {
461
476
  slides: SlideConfig[];
462
477
  transition?: SlideTransitionType;
463
478
  directionalTransition?: boolean;
479
+ /** Overrides the CLI-provided loop settings. */
480
+ loopConfig?: LoopConfig;
481
+ /** Persist settings in a custom host. CLI Studio saves loop-config.json automatically. */
482
+ onLoopConfigChange?: (config: LoopConfig) => void | Promise<void>;
464
483
  /** Annotation data to display. When provided (even empty array), annotation UI is enabled. When undefined, annotation UI is hidden. */
465
484
  annotations?: Annotation[];
466
485
  /** Called when the user creates an annotation */
@@ -469,7 +488,7 @@ interface SlideDeckProps {
469
488
  onAnnotationDelete?: (id: string) => void;
470
489
  onAnnotationUpdate?: (id: string, patch: Partial<Pick<Annotation, "body" | "status">>) => void;
471
490
  }
472
- declare function SlideDeck({ slides, transition, directionalTransition, annotations, onAnnotationAdd, onAnnotationDelete, onAnnotationUpdate }: SlideDeckProps): react_jsx_runtime.JSX.Element;
491
+ declare function SlideDeck({ slides, transition, directionalTransition, loopConfig: suppliedLoopConfig, onLoopConfigChange, annotations, onAnnotationAdd, onAnnotationDelete, onAnnotationUpdate }: SlideDeckProps): react_jsx_runtime.JSX.Element;
473
492
 
474
493
  interface SlideErrorBoundaryProps {
475
494
  slideIndex: number;
@@ -492,4 +511,10 @@ declare class SlideErrorBoundary extends React$1.Component<SlideErrorBoundaryPro
492
511
 
493
512
  declare function cn(...inputs: ClassValue[]): string;
494
513
 
495
- export { Animated, AnimatedGroup, AnimationProvider, type AnimationType, type Annotation, AnnotationOverlay, type AnnotationStorageAdapter, type AnnotationTarget, type AnnotationsFile, DEFAULT_SLIDE_TRANSITION, EASE_DEFAULT, EASE_IN, EASE_MORPH, EASE_OUT, ELEMENT_SLIDE_DISTANCE, MORPH_DURATION, MORPH_TRANSITION, Morph, MorphGroup, MorphItem, MorphText, type NavigationDirection, SLIDE_DIMENSIONS, SLIDE_DISTANCE, SLIDE_TRANSITION, SLIDE_TRANSITION_DURATION, SLIDE_VARIANTS, SPRING_BOUNCY, SPRING_SMOOTH, SPRING_SNAPPY, STAGGER_DELAY, STEP_ANIMATION_DURATION, STEP_TRANSITION, type SlideComponent, type SlideConfig, SlideDeck, SlideEmbed, SlideErrorBoundary, type SlideProps, SlideRenderer, type SlideRendererProps, SlideThemeProvider, type SlideTransitionConfig, type SlideTransitionType, type ThemeConfig, type UseSlideNavigationOptions, type UseSlideNavigationReturn, cn, createDirectionalVariants, createHttpAdapter, directionalSlideX, directionalSlideY, getSlideTransition, getSlideVariants, useAnimationContext, useAnnotations, useSlideNavigation, useTheme };
514
+ /** The CLI supplies the deck's loop-config.json in development and production. */
515
+ declare function LoopConfigProvider({ config, children }: {
516
+ config: LoopConfig;
517
+ children: ReactNode;
518
+ }): react_jsx_runtime.JSX.Element;
519
+
520
+ export { Animated, AnimatedGroup, AnimationProvider, type AnimationType, type Annotation, AnnotationOverlay, type AnnotationStorageAdapter, type AnnotationTarget, type AnnotationsFile, DEFAULT_SLIDE_TRANSITION, EASE_DEFAULT, EASE_IN, EASE_MORPH, EASE_OUT, ELEMENT_SLIDE_DISTANCE, type LoopConfig, LoopConfigProvider, type LoopSlideConfig, MORPH_DURATION, MORPH_TRANSITION, Morph, MorphGroup, MorphItem, MorphText, type NavigationDirection, SLIDE_DIMENSIONS, SLIDE_DISTANCE, SLIDE_TRANSITION, SLIDE_TRANSITION_DURATION, SLIDE_VARIANTS, SPRING_BOUNCY, SPRING_SMOOTH, SPRING_SNAPPY, STAGGER_DELAY, STEP_ANIMATION_DURATION, STEP_TRANSITION, type SlideComponent, type SlideConfig, SlideDeck, SlideEmbed, SlideErrorBoundary, type SlideProps, SlideRenderer, type SlideRendererProps, SlideThemeProvider, type SlideTransitionConfig, type SlideTransitionType, type ThemeConfig, type UseSlideNavigationOptions, type UseSlideNavigationReturn, cn, createDirectionalVariants, createHttpAdapter, directionalSlideX, directionalSlideY, getSlideTransition, getSlideVariants, useAnimationContext, useAnnotations, useSlideNavigation, useTheme };