diff --git a/packages/studio-server/src/helpers/sourceMutation.ts b/packages/studio-server/src/helpers/sourceMutation.ts
index a60a7fd4fa..9caa160937 100644
--- a/packages/studio-server/src/helpers/sourceMutation.ts
+++ b/packages/studio-server/src/helpers/sourceMutation.ts
@@ -367,14 +367,18 @@ export function splitElementInHtml(
// Keep the "clip" class — the runtime uses it to control visibility
// based on data-start/data-duration timing.
- // Adjust media trim offset for the second half
+ // A split creates two views over the same media source. Even an untrimmed
+ // audio/video element needs an explicit zero in-point stamped on the first
+ // half so the second half can advance from it instead of restarting at zero.
const playbackStartAttr = el.hasAttribute("data-playback-start")
? "data-playback-start"
: el.hasAttribute("data-media-start")
? "data-media-start"
: fallbackTiming?.stampPlaybackStart
? "data-playback-start"
- : null;
+ : el.matches("audio, video")
+ ? "data-media-start"
+ : null;
if (playbackStartAttr) {
const currentTrim =
parseFloat(el.getAttribute(playbackStartAttr) ?? "") || fallbackTiming?.playbackStart || 0;
diff --git a/packages/studio-server/src/helpers/sourceMutationSplitAndGroup.test.ts b/packages/studio-server/src/helpers/sourceMutationSplitAndGroup.test.ts
index a405cdb633..48a175feb6 100644
--- a/packages/studio-server/src/helpers/sourceMutationSplitAndGroup.test.ts
+++ b/packages/studio-server/src/helpers/sourceMutationSplitAndGroup.test.ts
@@ -123,6 +123,36 @@ describe("splitElementInHtml", () => {
expect(result.html).toMatch(/id="box-split"[^>]*data-playback-start="2"/);
});
+ it.each(["audio", "video"])(
+ "seeds the second %s half with a media in-point when the source starts at zero",
+ (tag) => {
+ const mediaSource = `