@livepeer-frameworks/player-svelte 0.1.1 → 0.1.3

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.
Files changed (90) hide show
  1. package/LICENSE.md +24 -0
  2. package/README.md +6 -2
  3. package/dist/DevModePanel.svelte +304 -127
  4. package/dist/DevModePanel.svelte.d.ts +1 -1
  5. package/dist/DvdLogo.svelte +17 -21
  6. package/dist/Icons.svelte +5 -3
  7. package/dist/Icons.svelte.d.ts +6 -19
  8. package/dist/IdleScreen.svelte +300 -209
  9. package/dist/IdleScreen.svelte.d.ts +1 -1
  10. package/dist/LoadingScreen.svelte +206 -178
  11. package/dist/Player.svelte +244 -111
  12. package/dist/Player.svelte.d.ts +1 -1
  13. package/dist/PlayerControls.svelte +264 -164
  14. package/dist/PlayerControls.svelte.d.ts +1 -1
  15. package/dist/SeekBar.svelte +61 -35
  16. package/dist/SkipIndicator.svelte +4 -4
  17. package/dist/SkipIndicator.svelte.d.ts +1 -1
  18. package/dist/SpeedIndicator.svelte +1 -1
  19. package/dist/StatsPanel.svelte +76 -57
  20. package/dist/StatsPanel.svelte.d.ts +1 -1
  21. package/dist/StreamStateOverlay.svelte +159 -123
  22. package/dist/StreamStateOverlay.svelte.d.ts +1 -1
  23. package/dist/SubtitleRenderer.svelte +46 -43
  24. package/dist/ThumbnailOverlay.svelte +22 -19
  25. package/dist/TitleOverlay.svelte +6 -11
  26. package/dist/components/VolumeIcons.svelte +12 -6
  27. package/dist/global.d.ts +3 -3
  28. package/dist/icons/FullscreenExitIcon.svelte +1 -5
  29. package/dist/icons/FullscreenIcon.svelte +1 -5
  30. package/dist/icons/PauseIcon.svelte +1 -5
  31. package/dist/icons/PictureInPictureIcon.svelte +12 -6
  32. package/dist/icons/PlayIcon.svelte +1 -5
  33. package/dist/icons/SeekToLiveIcon.svelte +1 -5
  34. package/dist/icons/SettingsIcon.svelte +1 -5
  35. package/dist/icons/SkipBackIcon.svelte +1 -5
  36. package/dist/icons/SkipForwardIcon.svelte +1 -5
  37. package/dist/icons/StatsIcon.svelte +1 -5
  38. package/dist/icons/VolumeOffIcon.svelte +1 -5
  39. package/dist/icons/VolumeUpIcon.svelte +1 -5
  40. package/dist/icons/index.d.ts +12 -12
  41. package/dist/icons/index.js +12 -12
  42. package/dist/index.d.ts +24 -24
  43. package/dist/index.js +21 -21
  44. package/dist/stores/index.d.ts +6 -6
  45. package/dist/stores/index.js +6 -6
  46. package/dist/stores/playbackQuality.d.ts +2 -2
  47. package/dist/stores/playbackQuality.js +7 -7
  48. package/dist/stores/playerContext.d.ts +2 -2
  49. package/dist/stores/playerContext.js +17 -17
  50. package/dist/stores/playerController.d.ts +15 -4
  51. package/dist/stores/playerController.js +84 -56
  52. package/dist/stores/playerSelection.d.ts +2 -2
  53. package/dist/stores/playerSelection.js +7 -7
  54. package/dist/stores/streamState.d.ts +2 -2
  55. package/dist/stores/streamState.js +56 -56
  56. package/dist/stores/viewerEndpoints.d.ts +3 -3
  57. package/dist/stores/viewerEndpoints.js +21 -21
  58. package/dist/types.d.ts +1 -1
  59. package/dist/ui/Badge.svelte +9 -10
  60. package/dist/ui/Badge.svelte.d.ts +8 -29
  61. package/dist/ui/Button.svelte +16 -16
  62. package/dist/ui/Button.svelte.d.ts +8 -29
  63. package/dist/ui/Slider.svelte +21 -55
  64. package/dist/ui/badge.js +1 -1
  65. package/dist/ui/button.js +2 -2
  66. package/dist/ui/context-menu/ContextMenuCheckboxItem.svelte +5 -7
  67. package/dist/ui/context-menu/ContextMenuCheckboxItem.svelte.d.ts +6 -27
  68. package/dist/ui/context-menu/ContextMenuContent.svelte +2 -9
  69. package/dist/ui/context-menu/ContextMenuItem.svelte +1 -5
  70. package/dist/ui/context-menu/ContextMenuLabel.svelte +1 -5
  71. package/dist/ui/context-menu/ContextMenuRadioItem.svelte +5 -7
  72. package/dist/ui/context-menu/ContextMenuRadioItem.svelte.d.ts +6 -27
  73. package/dist/ui/context-menu/ContextMenuSeparator.svelte +2 -8
  74. package/dist/ui/context-menu/ContextMenuShortcut.svelte +2 -12
  75. package/dist/ui/context-menu/ContextMenuSubContent.svelte +1 -5
  76. package/package.json +22 -14
  77. package/src/DevModePanel.svelte +40 -1
  78. package/src/Icons.svelte +5 -3
  79. package/src/IdleScreen.svelte +21 -14
  80. package/src/LoadingScreen.svelte +20 -13
  81. package/src/Player.svelte +48 -2
  82. package/src/PlayerControls.svelte +37 -13
  83. package/src/SeekBar.svelte +33 -0
  84. package/src/StreamStateOverlay.svelte +2 -2
  85. package/src/stores/playerController.ts +46 -1
  86. package/src/stores/viewerEndpoints.ts +1 -1
  87. package/src/ui/Badge.svelte +7 -4
  88. package/src/ui/Button.svelte +13 -13
  89. package/src/ui/context-menu/ContextMenuCheckboxItem.svelte +4 -2
  90. package/src/ui/context-menu/ContextMenuRadioItem.svelte +4 -2
@@ -3,56 +3,56 @@
3
3
  *
4
4
  * Port of useStreamState.ts React hook to Svelte 5 stores.
5
5
  */
6
- import { writable, derived } from 'svelte/store';
6
+ import { writable, derived } from "svelte/store";
7
7
  /**
8
8
  * Parse MistServer error string into StreamStatus enum
9
9
  */
10
10
  function parseErrorToStatus(error) {
11
11
  const lowerError = error.toLowerCase();
12
- if (lowerError.includes('offline'))
13
- return 'OFFLINE';
14
- if (lowerError.includes('initializing'))
15
- return 'INITIALIZING';
16
- if (lowerError.includes('booting'))
17
- return 'BOOTING';
18
- if (lowerError.includes('waiting for data'))
19
- return 'WAITING_FOR_DATA';
20
- if (lowerError.includes('shutting down'))
21
- return 'SHUTTING_DOWN';
22
- if (lowerError.includes('invalid'))
23
- return 'INVALID';
24
- return 'ERROR';
12
+ if (lowerError.includes("offline"))
13
+ return "OFFLINE";
14
+ if (lowerError.includes("initializing"))
15
+ return "INITIALIZING";
16
+ if (lowerError.includes("booting"))
17
+ return "BOOTING";
18
+ if (lowerError.includes("waiting for data"))
19
+ return "WAITING_FOR_DATA";
20
+ if (lowerError.includes("shutting down"))
21
+ return "SHUTTING_DOWN";
22
+ if (lowerError.includes("invalid"))
23
+ return "INVALID";
24
+ return "ERROR";
25
25
  }
26
26
  /**
27
27
  * Get human-readable message for stream status
28
28
  */
29
29
  function getStatusMessage(status, percentage) {
30
30
  switch (status) {
31
- case 'ONLINE':
32
- return 'Stream is online';
33
- case 'OFFLINE':
34
- return 'Stream is offline';
35
- case 'INITIALIZING':
31
+ case "ONLINE":
32
+ return "Stream is online";
33
+ case "OFFLINE":
34
+ return "Stream is offline";
35
+ case "INITIALIZING":
36
36
  return percentage !== undefined
37
37
  ? `Initializing... ${Math.round(percentage * 10) / 10}%`
38
- : 'Stream is initializing';
39
- case 'BOOTING':
40
- return 'Stream is starting up';
41
- case 'WAITING_FOR_DATA':
42
- return 'Waiting for stream data';
43
- case 'SHUTTING_DOWN':
44
- return 'Stream is shutting down';
45
- case 'INVALID':
46
- return 'Stream status is invalid';
47
- case 'ERROR':
38
+ : "Stream is initializing";
39
+ case "BOOTING":
40
+ return "Stream is starting up";
41
+ case "WAITING_FOR_DATA":
42
+ return "Waiting for stream data";
43
+ case "SHUTTING_DOWN":
44
+ return "Stream is shutting down";
45
+ case "INVALID":
46
+ return "Stream status is invalid";
47
+ case "ERROR":
48
48
  default:
49
- return 'Stream error';
49
+ return "Stream error";
50
50
  }
51
51
  }
52
52
  const initialState = {
53
- status: 'OFFLINE',
53
+ status: "OFFLINE",
54
54
  isOnline: false,
55
- message: 'Connecting...',
55
+ message: "Connecting...",
56
56
  lastUpdate: 0,
57
57
  };
58
58
  /**
@@ -93,7 +93,7 @@ export function createStreamStateManager(options) {
93
93
  if (data.error) {
94
94
  const status = parseErrorToStatus(data.error);
95
95
  const message = data.on_error || getStatusMessage(status, data.perc);
96
- store.update(prev => ({
96
+ store.update((prev) => ({
97
97
  status,
98
98
  isOnline: false,
99
99
  message,
@@ -105,7 +105,7 @@ export function createStreamStateManager(options) {
105
105
  }
106
106
  else {
107
107
  // Stream is online with valid metadata
108
- store.update(prev => {
108
+ store.update((prev) => {
109
109
  const mergedStreamInfo = {
110
110
  ...prev.streamInfo,
111
111
  ...data,
@@ -117,9 +117,9 @@ export function createStreamStateManager(options) {
117
117
  },
118
118
  };
119
119
  return {
120
- status: 'ONLINE',
120
+ status: "ONLINE",
121
121
  isOnline: true,
122
- message: 'Stream is online',
122
+ message: "Stream is online",
123
123
  lastUpdate: Date.now(),
124
124
  streamInfo: mergedStreamInfo,
125
125
  };
@@ -133,11 +133,11 @@ export function createStreamStateManager(options) {
133
133
  if (!mounted || !enabled)
134
134
  return;
135
135
  try {
136
- const baseUrl = `${mistBaseUrl.replace(/\/$/, '')}/json_${encodeURIComponent(streamName)}.js`;
136
+ const baseUrl = `${mistBaseUrl.replace(/\/$/, "")}/json_${encodeURIComponent(streamName)}.js`;
137
137
  const url = `${baseUrl}?metaeverywhere=1&inclzero=1`;
138
138
  const response = await fetch(url, {
139
- method: 'GET',
140
- headers: { 'Accept': 'application/json' },
139
+ method: "GET",
140
+ headers: { Accept: "application/json" },
141
141
  });
142
142
  if (!response.ok) {
143
143
  throw new Error(`HTTP ${response.status}`);
@@ -154,13 +154,13 @@ export function createStreamStateManager(options) {
154
154
  catch (error) {
155
155
  if (!mounted)
156
156
  return;
157
- store.update(prev => ({
157
+ store.update((prev) => ({
158
158
  ...prev,
159
- status: 'ERROR',
159
+ status: "ERROR",
160
160
  isOnline: false,
161
- message: error instanceof Error ? error.message : 'Connection failed',
161
+ message: error instanceof Error ? error.message : "Connection failed",
162
162
  lastUpdate: Date.now(),
163
- error: error instanceof Error ? error.message : 'Unknown error',
163
+ error: error instanceof Error ? error.message : "Unknown error",
164
164
  }));
165
165
  }
166
166
  // Schedule next poll
@@ -185,22 +185,22 @@ export function createStreamStateManager(options) {
185
185
  }
186
186
  try {
187
187
  const wsUrl = mistBaseUrl
188
- .replace(/^http:/, 'ws:')
189
- .replace(/^https:/, 'wss:')
190
- .replace(/\/$/, '');
188
+ .replace(/^http:/, "ws:")
189
+ .replace(/^https:/, "wss:")
190
+ .replace(/\/$/, "");
191
191
  const url = `${wsUrl}/json_${encodeURIComponent(streamName)}.js?metaeverywhere=1&inclzero=1`;
192
192
  const socket = new WebSocket(url);
193
193
  ws = socket;
194
194
  // Timeout: if no message within 5 seconds, fall back to HTTP
195
195
  wsTimeout = setTimeout(() => {
196
196
  if (socket.readyState <= WebSocket.OPEN) {
197
- console.debug('[streamState] WebSocket timeout (5s), falling back to HTTP');
197
+ console.debug("[streamState] WebSocket timeout (5s), falling back to HTTP");
198
198
  socket.close();
199
199
  pollHttp();
200
200
  }
201
201
  }, WS_TIMEOUT_MS);
202
202
  socket.onopen = () => {
203
- console.debug('[streamState] WebSocket connected');
203
+ console.debug("[streamState] WebSocket connected");
204
204
  socketReady.set(true);
205
205
  };
206
206
  socket.onmessage = (event) => {
@@ -213,11 +213,11 @@ export function createStreamStateManager(options) {
213
213
  processStreamInfo(data);
214
214
  }
215
215
  catch (e) {
216
- console.warn('[streamState] Failed to parse WebSocket message:', e);
216
+ console.warn("[streamState] Failed to parse WebSocket message:", e);
217
217
  }
218
218
  };
219
219
  socket.onerror = () => {
220
- console.warn('[streamState] WebSocket error, falling back to HTTP');
220
+ console.warn("[streamState] WebSocket error, falling back to HTTP");
221
221
  if (wsTimeout) {
222
222
  clearTimeout(wsTimeout);
223
223
  wsTimeout = null;
@@ -229,12 +229,12 @@ export function createStreamStateManager(options) {
229
229
  socketReady.set(false);
230
230
  if (!mounted || !enabled)
231
231
  return;
232
- console.debug('[streamState] WebSocket closed, starting HTTP polling');
232
+ console.debug("[streamState] WebSocket closed, starting HTTP polling");
233
233
  pollHttp();
234
234
  };
235
235
  }
236
236
  catch (error) {
237
- console.warn('[streamState] WebSocket connection failed:', error);
237
+ console.warn("[streamState] WebSocket connection failed:", error);
238
238
  pollHttp();
239
239
  }
240
240
  }
@@ -281,7 +281,7 @@ export function createStreamStateManager(options) {
281
281
  if (enabled && mistBaseUrl && streamName) {
282
282
  store.set({
283
283
  ...initialState,
284
- message: 'Connecting...',
284
+ message: "Connecting...",
285
285
  lastUpdate: Date.now(),
286
286
  });
287
287
  // Initial HTTP poll then WebSocket
@@ -303,12 +303,12 @@ export function createStreamStateManager(options) {
303
303
  }
304
304
  // Convenience derived stores for common values
305
305
  export function createDerivedStreamStatus(store) {
306
- return derived(store, $state => $state.status);
306
+ return derived(store, ($state) => $state.status);
307
307
  }
308
308
  export function createDerivedIsOnline(store) {
309
- return derived(store, $state => $state.isOnline);
309
+ return derived(store, ($state) => $state.isOnline);
310
310
  }
311
311
  export function createDerivedStreamInfo(store) {
312
- return derived(store, $state => $state.streamInfo);
312
+ return derived(store, ($state) => $state.streamInfo);
313
313
  }
314
314
  export default createStreamStateManager;
@@ -3,15 +3,15 @@
3
3
  *
4
4
  * Port of useViewerEndpoints.ts React hook to Svelte 5 stores.
5
5
  */
6
- import { type Readable } from 'svelte/store';
7
- import type { ContentEndpoints, ContentType } from '@livepeer-frameworks/player-core';
6
+ import { type Readable } from "svelte/store";
7
+ import type { ContentEndpoints, ContentType } from "@livepeer-frameworks/player-core";
8
8
  export interface ViewerEndpointsOptions {
9
9
  gatewayUrl: string;
10
10
  contentId: string;
11
11
  contentType?: ContentType;
12
12
  authToken?: string;
13
13
  }
14
- export type EndpointStatus = 'idle' | 'loading' | 'ready' | 'error';
14
+ export type EndpointStatus = "idle" | "loading" | "ready" | "error";
15
15
  export interface ViewerEndpointsState {
16
16
  endpoints: ContentEndpoints | null;
17
17
  status: EndpointStatus;
@@ -3,7 +3,7 @@
3
3
  *
4
4
  * Port of useViewerEndpoints.ts React hook to Svelte 5 stores.
5
5
  */
6
- import { writable, derived } from 'svelte/store';
6
+ import { writable, derived } from "svelte/store";
7
7
  const MAX_RETRIES = 3;
8
8
  const INITIAL_DELAY_MS = 500;
9
9
  /**
@@ -17,7 +17,7 @@ async function fetchWithRetry(url, options, maxRetries = MAX_RETRIES, initialDel
17
17
  return response;
18
18
  }
19
19
  catch (e) {
20
- lastError = e instanceof Error ? e : new Error('Fetch failed');
20
+ lastError = e instanceof Error ? e : new Error("Fetch failed");
21
21
  // Don't retry on abort
22
22
  if (options.signal?.aborted) {
23
23
  throw lastError;
@@ -26,15 +26,15 @@ async function fetchWithRetry(url, options, maxRetries = MAX_RETRIES, initialDel
26
26
  if (attempt < maxRetries - 1) {
27
27
  const delay = initialDelay * Math.pow(2, attempt);
28
28
  console.warn(`[viewerEndpoints] Retry ${attempt + 1}/${maxRetries - 1} after ${delay}ms`);
29
- await new Promise(resolve => setTimeout(resolve, delay));
29
+ await new Promise((resolve) => setTimeout(resolve, delay));
30
30
  }
31
31
  }
32
32
  }
33
- throw lastError ?? new Error('Gateway unreachable after retries');
33
+ throw lastError ?? new Error("Gateway unreachable after retries");
34
34
  }
35
35
  const initialState = {
36
36
  endpoints: null,
37
- status: 'idle',
37
+ status: "idle",
38
38
  error: null,
39
39
  };
40
40
  /**
@@ -70,9 +70,9 @@ export function createEndpointResolver(options) {
70
70
  // Abort previous request
71
71
  abortController?.abort();
72
72
  abortController = new AbortController();
73
- store.update(s => ({ ...s, status: 'loading', error: null }));
73
+ store.update((s) => ({ ...s, status: "loading", error: null }));
74
74
  try {
75
- const graphqlEndpoint = gatewayUrl.replace(/\/$/, '');
75
+ const graphqlEndpoint = gatewayUrl.replace(/\/$/, "");
76
76
  const query = `
77
77
  query ResolveViewer($contentId: String!) {
78
78
  resolveViewerEndpoint(contentId: $contentId) {
@@ -83,9 +83,9 @@ export function createEndpointResolver(options) {
83
83
  }
84
84
  `;
85
85
  const res = await fetchWithRetry(graphqlEndpoint, {
86
- method: 'POST',
86
+ method: "POST",
87
87
  headers: {
88
- 'Content-Type': 'application/json',
88
+ "Content-Type": "application/json",
89
89
  ...(authToken ? { Authorization: `Bearer ${authToken}` } : {}),
90
90
  },
91
91
  body: JSON.stringify({ query, variables: { contentId } }),
@@ -95,15 +95,15 @@ export function createEndpointResolver(options) {
95
95
  throw new Error(`Gateway GQL error ${res.status}`);
96
96
  const payload = await res.json();
97
97
  if (payload.errors?.length) {
98
- throw new Error(payload.errors[0]?.message || 'GraphQL error');
98
+ throw new Error(payload.errors[0]?.message || "GraphQL error");
99
99
  }
100
100
  const resp = payload.data?.resolveViewerEndpoint;
101
101
  const primary = resp?.primary;
102
102
  const fallbacks = Array.isArray(resp?.fallbacks) ? resp.fallbacks : [];
103
103
  if (!primary)
104
- throw new Error('No endpoints');
104
+ throw new Error("No endpoints");
105
105
  // Parse outputs JSON string (GraphQL returns JSON scalar as string)
106
- if (primary.outputs && typeof primary.outputs === 'string') {
106
+ if (primary.outputs && typeof primary.outputs === "string") {
107
107
  try {
108
108
  primary.outputs = JSON.parse(primary.outputs);
109
109
  }
@@ -111,7 +111,7 @@ export function createEndpointResolver(options) {
111
111
  }
112
112
  if (fallbacks) {
113
113
  fallbacks.forEach((fb) => {
114
- if (fb.outputs && typeof fb.outputs === 'string') {
114
+ if (fb.outputs && typeof fb.outputs === "string") {
115
115
  try {
116
116
  fb.outputs = JSON.parse(fb.outputs);
117
117
  }
@@ -121,18 +121,18 @@ export function createEndpointResolver(options) {
121
121
  }
122
122
  store.set({
123
123
  endpoints: { primary, fallbacks, metadata: resp?.metadata },
124
- status: 'ready',
124
+ status: "ready",
125
125
  error: null,
126
126
  });
127
127
  }
128
128
  catch (e) {
129
129
  if (abortController?.signal.aborted || !mounted)
130
130
  return;
131
- const message = e instanceof Error ? e.message : 'Unknown gateway error';
132
- console.error('[viewerEndpoints] Gateway resolution failed:', message);
131
+ const message = e instanceof Error ? e.message : "Unknown gateway error";
132
+ console.error("[viewerEndpoints] Gateway resolution failed:", message);
133
133
  store.set({
134
134
  endpoints: null,
135
- status: 'error',
135
+ status: "error",
136
136
  error: message,
137
137
  });
138
138
  }
@@ -164,15 +164,15 @@ export function createEndpointResolver(options) {
164
164
  }
165
165
  // Convenience derived stores
166
166
  export function createDerivedEndpoints(store) {
167
- return derived(store, $state => $state.endpoints);
167
+ return derived(store, ($state) => $state.endpoints);
168
168
  }
169
169
  export function createDerivedPrimaryEndpoint(store) {
170
- return derived(store, $state => $state.endpoints?.primary ?? null);
170
+ return derived(store, ($state) => $state.endpoints?.primary ?? null);
171
171
  }
172
172
  export function createDerivedMetadata(store) {
173
- return derived(store, $state => $state.endpoints?.metadata ?? null);
173
+ return derived(store, ($state) => $state.endpoints?.metadata ?? null);
174
174
  }
175
175
  export function createDerivedStatus(store) {
176
- return derived(store, $state => $state.status);
176
+ return derived(store, ($state) => $state.status);
177
177
  }
178
178
  export default createEndpointResolver;
package/dist/types.d.ts CHANGED
@@ -1,4 +1,4 @@
1
1
  /**
2
2
  * Svelte-specific type exports
3
3
  */
4
- export type SkipDirection = 'back' | 'forward' | null;
4
+ export type SkipDirection = "back" | "forward" | null;
@@ -1,21 +1,20 @@
1
1
  <script lang="ts">
2
- import { cn } from '@livepeer-frameworks/player-core';
3
- import { badgeVariants, type BadgeVariant } from './badge';
2
+ import type { Snippet } from "svelte";
3
+ import { cn } from "@livepeer-frameworks/player-core";
4
+ import { badgeVariants, type BadgeVariant } from "./badge";
4
5
 
5
- type $$Props = {
6
+ type Props = {
6
7
  variant?: BadgeVariant;
7
8
  class?: string;
8
- } & Record<string, any>;
9
+ children?: Snippet;
10
+ [key: string]: unknown;
11
+ };
9
12
 
10
- let {
11
- variant = "default",
12
- class: className = "",
13
- ...rest
14
- }: $$Props = $props();
13
+ let { variant = "default", class: className = "", children, ...rest }: Props = $props();
15
14
 
16
15
  let mergedClasses = $derived(cn(badgeVariants(variant, className)));
17
16
  </script>
18
17
 
19
18
  <div class={mergedClasses} {...rest}>
20
- <slot />
19
+ {@render children?.()}
21
20
  </div>
@@ -1,32 +1,11 @@
1
- import { type BadgeVariant } from './badge';
2
- type $$Props = {
1
+ import type { Snippet } from "svelte";
2
+ import { type BadgeVariant } from "./badge";
3
+ type Props = {
3
4
  variant?: BadgeVariant;
4
5
  class?: string;
5
- } & Record<string, any>;
6
- interface $$__sveltets_2_IsomorphicComponent<Props extends Record<string, any> = any, Events extends Record<string, any> = any, Slots extends Record<string, any> = any, Exports = {}, Bindings = string> {
7
- new (options: import('svelte').ComponentConstructorOptions<Props>): import('svelte').SvelteComponent<Props, Events, Slots> & {
8
- $$bindings?: Bindings;
9
- } & Exports;
10
- (internal: unknown, props: Props & {
11
- $$events?: Events;
12
- $$slots?: Slots;
13
- }): Exports & {
14
- $set?: any;
15
- $on?: any;
16
- };
17
- z_$$bindings?: Bindings;
18
- }
19
- type $$__sveltets_2_PropsWithChildren<Props, Slots> = Props & (Slots extends {
20
- default: any;
21
- } ? Props extends Record<string, never> ? any : {
22
- children?: any;
23
- } : {});
24
- declare const Badge: $$__sveltets_2_IsomorphicComponent<$$__sveltets_2_PropsWithChildren<$$Props, {
25
- default: {};
26
- }>, {
27
- [evt: string]: CustomEvent<any>;
28
- }, {
29
- default: {};
30
- }, {}, "">;
31
- type Badge = InstanceType<typeof Badge>;
6
+ children?: Snippet;
7
+ [key: string]: unknown;
8
+ };
9
+ declare const Badge: import("svelte").Component<Props, {}, "">;
10
+ type Badge = ReturnType<typeof Badge>;
32
11
  export default Badge;
@@ -1,15 +1,18 @@
1
1
  <script lang="ts">
2
- import { cn } from '@livepeer-frameworks/player-core';
3
- import { buttonVariants, type ButtonSize, type ButtonVariant } from './button';
4
- import { getContext, setContext } from 'svelte';
2
+ import type { Snippet } from "svelte";
3
+ import { cn } from "@livepeer-frameworks/player-core";
4
+ import { buttonVariants, type ButtonSize, type ButtonVariant } from "./button";
5
+ import { getContext } from "svelte";
5
6
 
6
- type $$Props = {
7
+ type Props = {
7
8
  variant?: ButtonVariant;
8
9
  size?: ButtonSize;
9
10
  class?: string;
10
11
  asChild?: boolean;
11
12
  type?: "button" | "submit" | "reset";
12
- } & Record<string, any>;
13
+ children?: Snippet;
14
+ [key: string]: unknown;
15
+ };
13
16
 
14
17
  let {
15
18
  variant = "default",
@@ -17,26 +20,23 @@
17
20
  class: className = "",
18
21
  asChild = false,
19
22
  type = "button",
23
+ children,
20
24
  ...rest
21
- }: $$Props = $props();
25
+ }: Props = $props();
22
26
 
23
- let Comp: string = "button";
24
- if (asChild) {
25
- Comp = getContext('__svelte_slot_element') || 'div';
26
- }
27
-
28
- // Set context for potential nested slots (though less common for Button)
29
- setContext('__svelte_slot_element', Comp);
27
+ let Comp = $derived(
28
+ asChild ? (getContext("__svelte_slot_element") as string) || "div" : "button"
29
+ );
30
30
 
31
31
  let mergedClasses = $derived(cn(buttonVariants(variant, size, className)));
32
32
  </script>
33
33
 
34
34
  {#if asChild}
35
35
  <svelte:element this={Comp} class={mergedClasses} {...rest}>
36
- <slot />
36
+ {@render children?.()}
37
37
  </svelte:element>
38
38
  {:else}
39
- <button class={mergedClasses} type={type} {...rest}>
40
- <slot />
39
+ <button class={mergedClasses} {type} {...rest}>
40
+ {@render children?.()}
41
41
  </button>
42
42
  {/if}
@@ -1,35 +1,14 @@
1
- import { type ButtonSize, type ButtonVariant } from './button';
2
- type $$Props = {
1
+ import type { Snippet } from "svelte";
2
+ import { type ButtonSize, type ButtonVariant } from "./button";
3
+ type Props = {
3
4
  variant?: ButtonVariant;
4
5
  size?: ButtonSize;
5
6
  class?: string;
6
7
  asChild?: boolean;
7
8
  type?: "button" | "submit" | "reset";
8
- } & Record<string, any>;
9
- interface $$__sveltets_2_IsomorphicComponent<Props extends Record<string, any> = any, Events extends Record<string, any> = any, Slots extends Record<string, any> = any, Exports = {}, Bindings = string> {
10
- new (options: import('svelte').ComponentConstructorOptions<Props>): import('svelte').SvelteComponent<Props, Events, Slots> & {
11
- $$bindings?: Bindings;
12
- } & Exports;
13
- (internal: unknown, props: Props & {
14
- $$events?: Events;
15
- $$slots?: Slots;
16
- }): Exports & {
17
- $set?: any;
18
- $on?: any;
19
- };
20
- z_$$bindings?: Bindings;
21
- }
22
- type $$__sveltets_2_PropsWithChildren<Props, Slots> = Props & (Slots extends {
23
- default: any;
24
- } ? Props extends Record<string, never> ? any : {
25
- children?: any;
26
- } : {});
27
- declare const Button: $$__sveltets_2_IsomorphicComponent<$$__sveltets_2_PropsWithChildren<$$Props, {
28
- default: {};
29
- }>, {
30
- [evt: string]: CustomEvent<any>;
31
- }, {
32
- default: {};
33
- }, {}, "">;
34
- type Button = InstanceType<typeof Button>;
9
+ children?: Snippet;
10
+ [key: string]: unknown;
11
+ };
12
+ declare const Button: import("svelte").Component<Props, {}, "">;
13
+ type Button = ReturnType<typeof Button>;
35
14
  export default Button;
@@ -33,68 +33,34 @@
33
33
  ...rest
34
34
  }: $$Props = $props();
35
35
 
36
- // Colors based on accentColor prop
37
- const rangeColorClass = $derived(accentColor ? "bg-[hsl(var(--tn-cyan,195_100%_50%))]" : "bg-white/90");
38
- const thumbColorClass = $derived(accentColor ? "bg-[hsl(var(--tn-cyan,195_100%_50%))]" : "bg-white");
39
-
40
36
  function handleValueChange(newValue: number) {
41
37
  value = newValue;
42
38
  if (oninput) {
43
- // Defensive: ensure we pass a valid finite number (prevents NaN propagation)
44
- if (typeof newValue === 'number' && Number.isFinite(newValue)) {
39
+ if (typeof newValue === "number" && Number.isFinite(newValue)) {
45
40
  oninput(newValue);
46
41
  }
47
42
  }
48
43
  }
49
44
  </script>
50
45
 
51
- <div
52
- class={cn(
53
- "group relative flex touch-none select-none items-center cursor-pointer",
54
- orientation === "horizontal" ? "w-full h-5" : "h-full flex-col w-5",
55
- className
56
- )}
46
+ <BitsSlider.Root
47
+ type="single"
48
+ {min}
49
+ {max}
50
+ {step}
51
+ {value}
52
+ onValueChange={handleValueChange}
53
+ {orientation}
54
+ class={cn("fw-slider", orientation === "vertical" && "fw-slider--vertical", className)}
55
+ {...rest}
57
56
  >
58
- <BitsSlider.Root
59
- type="single"
60
- {min}
61
- {max}
62
- {step}
63
- {value}
64
- onValueChange={handleValueChange}
65
- {orientation}
66
- class="w-full h-full relative flex items-center"
67
- {...rest}
68
- >
69
- {#if showTrack}
70
- <div
71
- class={cn(
72
- "absolute rounded-full bg-white/30 transition-all duration-150",
73
- orientation === "horizontal"
74
- ? "inset-x-0 h-1 group-hover:h-1.5"
75
- : "inset-y-0 w-1 group-hover:w-1.5",
76
- trackClassName
77
- )}
78
- >
79
- <BitsSlider.Range
80
- class={cn(
81
- "absolute rounded-full transition-all duration-150",
82
- orientation === "horizontal" ? "h-full" : "w-full bottom-0",
83
- rangeColorClass
84
- )}
85
- />
86
- </div>
87
- {/if}
88
- <BitsSlider.Thumb
89
- index={0}
90
- class={cn(
91
- "block rounded-full border-0 cursor-pointer shadow-md transition-all duration-150",
92
- "w-2.5 h-2.5 group-hover:w-3.5 group-hover:h-3.5",
93
- "focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-white/50",
94
- "disabled:pointer-events-none disabled:opacity-50",
95
- thumbColorClass,
96
- thumbClassName
97
- )}
98
- />
99
- </BitsSlider.Root>
100
- </div>
57
+ {#if showTrack}
58
+ <div class={cn("fw-slider-track", trackClassName)}>
59
+ <BitsSlider.Range class={cn("fw-slider-range", accentColor && "fw-slider-range--accent")} />
60
+ </div>
61
+ {/if}
62
+ <BitsSlider.Thumb
63
+ index={0}
64
+ class={cn("fw-slider-thumb", accentColor && "fw-slider-thumb--accent", thumbClassName)}
65
+ />
66
+ </BitsSlider.Root>