Compare commits
1 Commits
master
...
f7636f61a7
| Author | SHA1 | Date | |
|---|---|---|---|
|
f7636f61a7
|
@@ -6,6 +6,7 @@ const spacetimedb = schema({
|
||||
{
|
||||
id: t.u64().primaryKey(),
|
||||
url: t.string(),
|
||||
subtitleUrl: t.string(),
|
||||
timePosition: t.f64(),
|
||||
isPlaying: t.bool(),
|
||||
lastUpdatedAt: t.timestamp(),
|
||||
@@ -19,6 +20,7 @@ export const init = spacetimedb.init((ctx) => {
|
||||
ctx.db.videoState.insert({
|
||||
id: 1n,
|
||||
url: "https://cdn.cazzzer.com/LycoReco08.mkv",
|
||||
subtitleUrl: "",
|
||||
timePosition: 0.0,
|
||||
isPlaying: false,
|
||||
lastUpdatedAt: ctx.timestamp,
|
||||
@@ -34,6 +36,7 @@ export const set_url = spacetimedb.reducer({ url: t.string() }, (ctx, { url }) =
|
||||
ctx.db.videoState.id.update({
|
||||
...row,
|
||||
url,
|
||||
subtitleUrl: "", // Clear subtitle on new video
|
||||
timePosition: 0.0,
|
||||
isPlaying: false,
|
||||
lastUpdatedAt: ctx.timestamp,
|
||||
@@ -71,3 +74,13 @@ export const seek = spacetimedb.reducer({ time_position: t.f64() }, (ctx, { time
|
||||
lastUpdatedAt: ctx.timestamp,
|
||||
});
|
||||
});
|
||||
|
||||
export const set_subtitle_url = spacetimedb.reducer({ url: t.string() }, (ctx, { url }) => {
|
||||
const row = ctx.db.videoState.id.find(1n);
|
||||
if (!row) return;
|
||||
ctx.db.videoState.id.update({
|
||||
...row,
|
||||
subtitleUrl: url,
|
||||
lastUpdatedAt: ctx.timestamp,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -37,6 +37,7 @@ import {
|
||||
import PauseReducer from "./pause_reducer";
|
||||
import PlayReducer from "./play_reducer";
|
||||
import SeekReducer from "./seek_reducer";
|
||||
import SetSubtitleUrlReducer from "./set_subtitle_url_reducer";
|
||||
import SetUrlReducer from "./set_url_reducer";
|
||||
|
||||
// Import all procedure arg schemas
|
||||
@@ -66,6 +67,7 @@ const reducersSchema = __reducers(
|
||||
__reducerSchema("pause", PauseReducer),
|
||||
__reducerSchema("play", PlayReducer),
|
||||
__reducerSchema("seek", SeekReducer),
|
||||
__reducerSchema("set_subtitle_url", SetSubtitleUrlReducer),
|
||||
__reducerSchema("set_url", SetUrlReducer),
|
||||
);
|
||||
|
||||
|
||||
15
src/lib/st-bindings/set_subtitle_url_reducer.ts
Normal file
15
src/lib/st-bindings/set_subtitle_url_reducer.ts
Normal file
@@ -0,0 +1,15 @@
|
||||
// THIS FILE IS AUTOMATICALLY GENERATED BY SPACETIMEDB. EDITS TO THIS FILE
|
||||
// WILL NOT BE SAVED. MODIFY TABLES IN YOUR MODULE SOURCE CODE INSTEAD.
|
||||
|
||||
/* eslint-disable */
|
||||
/* tslint:disable */
|
||||
import {
|
||||
TypeBuilder as __TypeBuilder,
|
||||
t as __t,
|
||||
type AlgebraicTypeType as __AlgebraicTypeType,
|
||||
type Infer as __Infer,
|
||||
} from "spacetimedb";
|
||||
|
||||
export default {
|
||||
url: __t.string(),
|
||||
};
|
||||
@@ -13,6 +13,7 @@ import {
|
||||
export const VideoState = __t.object("VideoState", {
|
||||
id: __t.u64(),
|
||||
url: __t.string(),
|
||||
subtitleUrl: __t.string(),
|
||||
timePosition: __t.f64(),
|
||||
isPlaying: __t.bool(),
|
||||
lastUpdatedAt: __t.timestamp(),
|
||||
|
||||
@@ -9,10 +9,12 @@ import { type Infer as __Infer } from "spacetimedb";
|
||||
import PauseReducer from "../pause_reducer";
|
||||
import PlayReducer from "../play_reducer";
|
||||
import SeekReducer from "../seek_reducer";
|
||||
import SetSubtitleUrlReducer from "../set_subtitle_url_reducer";
|
||||
import SetUrlReducer from "../set_url_reducer";
|
||||
|
||||
export type PauseParams = __Infer<typeof PauseReducer>;
|
||||
export type PlayParams = __Infer<typeof PlayReducer>;
|
||||
export type SeekParams = __Infer<typeof SeekReducer>;
|
||||
export type SetSubtitleUrlParams = __Infer<typeof SetSubtitleUrlReducer>;
|
||||
export type SetUrlParams = __Infer<typeof SetUrlReducer>;
|
||||
|
||||
|
||||
@@ -13,6 +13,7 @@ import {
|
||||
export default __t.row({
|
||||
id: __t.u64().primaryKey(),
|
||||
url: __t.string(),
|
||||
subtitleUrl: __t.string().name("subtitle_url"),
|
||||
timePosition: __t.f64().name("time_position"),
|
||||
isPlaying: __t.bool().name("is_playing"),
|
||||
lastUpdatedAt: __t.timestamp().name("last_updated_at"),
|
||||
|
||||
@@ -8,12 +8,14 @@
|
||||
const videoState = $derived($videoStates.find((state) => state.id === 1n));
|
||||
|
||||
const setUrlReducer = useReducer(reducers.setUrl);
|
||||
const setSubtitleUrlReducer = useReducer(reducers.setSubtitleUrl);
|
||||
const playReducer = useReducer(reducers.play);
|
||||
const pauseReducer = useReducer(reducers.pause);
|
||||
const seekReducer = useReducer(reducers.seek);
|
||||
|
||||
let videoElement: HTMLVideoElement | undefined = $state();
|
||||
let newUrl = $state("");
|
||||
let newSubtitleUrl = $state("");
|
||||
|
||||
let isSyncing = false;
|
||||
let syncTimeout: ReturnType<typeof setTimeout> | undefined;
|
||||
@@ -111,6 +113,13 @@
|
||||
setUrlReducer({ url: newUrl });
|
||||
newUrl = "";
|
||||
}
|
||||
|
||||
function handleSetSubtitle(e: SubmitEvent) {
|
||||
e.preventDefault();
|
||||
if (!newSubtitleUrl.trim() || !$conn.isActive) return;
|
||||
setSubtitleUrlReducer({ url: newSubtitleUrl });
|
||||
newSubtitleUrl = "";
|
||||
}
|
||||
</script>
|
||||
|
||||
<div class="p-4">
|
||||
@@ -134,18 +143,32 @@
|
||||
<button type="submit" class="p-2" disabled={!$conn.isActive}>Set URL</button>
|
||||
</form>
|
||||
|
||||
<form onsubmit={handleSetSubtitle} class="mb-2">
|
||||
<input
|
||||
type="url"
|
||||
placeholder="Enter subtitle track URL (.vtt)"
|
||||
bind:value={newSubtitleUrl}
|
||||
class="mr-2 w-96 p-2"
|
||||
/>
|
||||
<button type="submit" class="p-2">Set Subtitles</button>
|
||||
</form>
|
||||
|
||||
<div>
|
||||
<!-- svelte-ignore a11y_media_has_caption -->
|
||||
<video
|
||||
bind:this={videoElement}
|
||||
muted
|
||||
controls
|
||||
crossorigin="anonymous"
|
||||
onplay={handlePlay}
|
||||
onpause={handlePause}
|
||||
onseeked={handleSeeked}
|
||||
ontimeupdate={handleTimeUpdate}
|
||||
class="w-full max-w-2xl bg-black"
|
||||
>
|
||||
{#if videoState?.subtitleUrl}
|
||||
<track src={videoState.subtitleUrl} kind="subtitles" srclang="en" label="English" default />
|
||||
{/if}
|
||||
Your browser does not support the video tag.
|
||||
</video>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user