agentroam-runtime-darwin-arm64 0.2.0-preview.68 → 0.2.0-preview.69

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 (896) hide show
  1. package/manifest.json +2 -2
  2. package/package.json +1 -1
  3. package/runtime/.next/BUILD_ID +1 -1
  4. package/runtime/.next/app-build-manifest.json +8 -8
  5. package/runtime/.next/app-path-routes-manifest.json +1 -1
  6. package/runtime/.next/build-manifest.json +3 -3
  7. package/runtime/.next/prerender-manifest.json +1 -1
  8. package/runtime/.next/required-server-files.json +1 -1
  9. package/runtime/.next/server/app/_not-found/page.js +1 -1
  10. package/runtime/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  11. package/runtime/.next/server/app/_not-found.html +1 -1
  12. package/runtime/.next/server/app/_not-found.rsc +1 -1
  13. package/runtime/.next/server/app/api/agent/abort/route.js +1 -1
  14. package/runtime/.next/server/app/api/agent/answer/route.js +1 -1
  15. package/runtime/.next/server/app/api/agent/codex-sharing/route.js +1 -1
  16. package/runtime/.next/server/app/api/agent/harness/status/route.js +1 -1
  17. package/runtime/.next/server/app/api/agent/model/route.js +1 -1
  18. package/runtime/.next/server/app/api/agent/models/route.js +1 -1
  19. package/runtime/.next/server/app/api/agent/run/route.js +1 -1
  20. package/runtime/.next/server/app/api/agent/runtime-health/route.js +1 -1
  21. package/runtime/.next/server/app/api/agent/steer/route.js +1 -1
  22. package/runtime/.next/server/app/api/agent/stream/route.js +2 -2
  23. package/runtime/.next/server/app/api/agent-workspaces/[workspaceId]/sessions/route.js +1 -1
  24. package/runtime/.next/server/app/api/agent-workspaces/route.js +1 -1
  25. package/runtime/.next/server/app/api/auth/verify/route.js +1 -1
  26. package/runtime/.next/server/app/api/business/route.js +1 -1
  27. package/runtime/.next/server/app/api/client-logs/route.js +1 -1
  28. package/runtime/.next/server/app/api/collaboration/route.js +4 -4
  29. package/runtime/.next/server/app/api/flow/v1/catalog/route.js +1 -1
  30. package/runtime/.next/server/app/api/flow/v1/runs/[runId]/cancel/route.js +1 -1
  31. package/runtime/.next/server/app/api/flow/v1/runs/[runId]/events/route.js +4 -4
  32. package/runtime/.next/server/app/api/flow/v1/runs/route.js +1 -1
  33. package/runtime/.next/server/app/api/flow-studio/config/route.js +1 -1
  34. package/runtime/.next/server/app/api/mcp/connect/route.js +1 -1
  35. package/runtime/.next/server/app/api/mcp/disconnect/route.js +1 -1
  36. package/runtime/.next/server/app/api/mcp/servers/route.js +1 -1
  37. package/runtime/.next/server/app/api/memory/[key]/route.js +1 -1
  38. package/runtime/.next/server/app/api/memory/route.js +1 -1
  39. package/runtime/.next/server/app/api/plugins/load/route.js +1 -1
  40. package/runtime/.next/server/app/api/projects/[id]/route.js +1 -1
  41. package/runtime/.next/server/app/api/projects/check/route.js +1 -1
  42. package/runtime/.next/server/app/api/projects/directories/route.js +1 -1
  43. package/runtime/.next/server/app/api/projects/roots/route.js +1 -1
  44. package/runtime/.next/server/app/api/projects/route.js +1 -1
  45. package/runtime/.next/server/app/api/push/subscribe/route.js +2 -2
  46. package/runtime/.next/server/app/api/push/unsubscribe/route.js +3 -3
  47. package/runtime/.next/server/app/api/push/vapid/route.js +2 -2
  48. package/runtime/.next/server/app/api/push/vapid.body +1 -1
  49. package/runtime/.next/server/app/api/remote-tools/register/route.js +1 -1
  50. package/runtime/.next/server/app/api/sessions/[id]/background-jobs/[jobId]/route.js +1 -1
  51. package/runtime/.next/server/app/api/sessions/[id]/background-jobs/[jobId]/stop/route.js +1 -1
  52. package/runtime/.next/server/app/api/sessions/[id]/background-jobs/route.js +1 -1
  53. package/runtime/.next/server/app/api/sessions/[id]/changes/route.js +2 -2
  54. package/runtime/.next/server/app/api/sessions/[id]/fork/route.js +1 -1
  55. package/runtime/.next/server/app/api/sessions/[id]/fork-at/route.js +1 -1
  56. package/runtime/.next/server/app/api/sessions/[id]/goals/route.js +1 -1
  57. package/runtime/.next/server/app/api/sessions/[id]/handoff/route.js +1 -1
  58. package/runtime/.next/server/app/api/sessions/[id]/native-goal/route.js +1 -1
  59. package/runtime/.next/server/app/api/sessions/[id]/query-index/route.js +1 -1
  60. package/runtime/.next/server/app/api/sessions/[id]/release/route.js +1 -1
  61. package/runtime/.next/server/app/api/sessions/[id]/route.js +1 -1
  62. package/runtime/.next/server/app/api/sessions/[id]/thread-goal/route.js +1 -1
  63. package/runtime/.next/server/app/api/sessions/[id]/tool-result/route.js +1 -1
  64. package/runtime/.next/server/app/api/sessions/route.js +1 -1
  65. package/runtime/.next/server/app/api/settings/route.js +1 -1
  66. package/runtime/.next/server/app/api/skills/route.js +1 -1
  67. package/runtime/.next/server/app/api/tool-policies/[policyId]/route.js +1 -1
  68. package/runtime/.next/server/app/api/tool-policies/route.js +1 -1
  69. package/runtime/.next/server/app/api/tools/route.js +1 -1
  70. package/runtime/.next/server/app/api/update/check/route.js +1 -1
  71. package/runtime/.next/server/app/api/update/install/route.js +1 -1
  72. package/runtime/.next/server/app/api/update/status/route.js +1 -1
  73. package/runtime/.next/server/app/api/web-auth/login/route.js +1 -1
  74. package/runtime/.next/server/app/api/web-auth/logout/route.js +1 -1
  75. package/runtime/.next/server/app/api/web-auth/revoke-all/route.js +1 -1
  76. package/runtime/.next/server/app/api/web-auth/setup/route.js +1 -1
  77. package/runtime/.next/server/app/api/web-auth/status/route.js +1 -1
  78. package/runtime/.next/server/app/api/web-console/bootstrap/route.js +1 -1
  79. package/runtime/.next/server/app/api/web-console/computer-settings/route.js +1 -1
  80. package/runtime/.next/server/app/api/web-console/computers/route.js +1 -1
  81. package/runtime/.next/server/app/api/web-console/device-state/route.js +1 -1
  82. package/runtime/.next/server/app/api/web-console/history/route.js +1 -1
  83. package/runtime/.next/server/app/api/web-console/preferences/route.js +1 -1
  84. package/runtime/.next/server/app/web/page.js +4 -4
  85. package/runtime/.next/server/app/web/page_client-reference-manifest.js +1 -1
  86. package/runtime/.next/server/app-paths-manifest.json +30 -30
  87. package/runtime/.next/server/chunks/5303.js +2 -2
  88. package/runtime/.next/server/middleware-build-manifest.js +1 -1
  89. package/runtime/.next/server/pages/404.html +1 -1
  90. package/runtime/.next/server/pages/500.html +1 -1
  91. package/runtime/.next/server/server-reference-manifest.json +1 -1
  92. package/runtime/.next/static/chunks/app/web/{error-b5d1875531d2eeb6.js → error-c3847c5e65100576.js} +1 -1
  93. package/runtime/.next/static/chunks/app/web/layout-579afeab60c11faf.js +1 -0
  94. package/runtime/.next/static/chunks/app/web/page-1586e76a5cff32d5.js +1 -0
  95. package/runtime/.next/static/chunks/{main-app-3734d90a62991817.js → main-app-c797e818a3f2a09f.js} +1 -1
  96. package/runtime/native/Support.noindex/AgentRoam Remote Desktop.app/Contents/MacOS/agentroam-remote-desktop +0 -0
  97. package/runtime/native/Support.noindex/AgentRoam Remote Desktop.app/Contents/Resources/agentroam-component.json +1 -1
  98. package/runtime/native/Support.noindex/AgentRoam Remote Desktop.app/Contents/_CodeSignature/CodeResources +2 -2
  99. package/runtime/node_modules/.package-lock.json +128 -128
  100. package/runtime/node_modules/@agent/native-runtime/dist/index.js +442 -69
  101. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/README.md +1 -1
  102. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/bridge.mjs +75 -82
  103. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/browser-sdk.js +28 -37
  104. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-a9vq6p1m.mjs +31 -0
  105. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-bb8r6h44.mjs +17 -0
  106. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-kzw924e6.mjs +18 -0
  107. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-t4mxrz5y.mjs +43 -0
  108. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core.mjs +12 -21
  109. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/manifest.json +19 -20
  110. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/manifest.zst.json +23 -24
  111. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/package.json +14 -14
  112. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/sdk.mjs +73 -82
  113. package/runtime/node_modules/caniuse-lite/data/agents.js +1 -1
  114. package/runtime/node_modules/caniuse-lite/data/browserVersions.js +1 -1
  115. package/runtime/node_modules/caniuse-lite/data/features/aac.js +1 -1
  116. package/runtime/node_modules/caniuse-lite/data/features/abortcontroller.js +1 -1
  117. package/runtime/node_modules/caniuse-lite/data/features/ac3-ec3.js +1 -1
  118. package/runtime/node_modules/caniuse-lite/data/features/accelerometer.js +1 -1
  119. package/runtime/node_modules/caniuse-lite/data/features/addeventlistener.js +1 -1
  120. package/runtime/node_modules/caniuse-lite/data/features/alternate-stylesheet.js +1 -1
  121. package/runtime/node_modules/caniuse-lite/data/features/ambient-light.js +1 -1
  122. package/runtime/node_modules/caniuse-lite/data/features/apng.js +1 -1
  123. package/runtime/node_modules/caniuse-lite/data/features/array-find-index.js +1 -1
  124. package/runtime/node_modules/caniuse-lite/data/features/array-find.js +1 -1
  125. package/runtime/node_modules/caniuse-lite/data/features/array-flat.js +1 -1
  126. package/runtime/node_modules/caniuse-lite/data/features/array-includes.js +1 -1
  127. package/runtime/node_modules/caniuse-lite/data/features/arrow-functions.js +1 -1
  128. package/runtime/node_modules/caniuse-lite/data/features/asmjs.js +1 -1
  129. package/runtime/node_modules/caniuse-lite/data/features/async-clipboard.js +1 -1
  130. package/runtime/node_modules/caniuse-lite/data/features/async-functions.js +1 -1
  131. package/runtime/node_modules/caniuse-lite/data/features/atob-btoa.js +1 -1
  132. package/runtime/node_modules/caniuse-lite/data/features/audio-api.js +1 -1
  133. package/runtime/node_modules/caniuse-lite/data/features/audio.js +1 -1
  134. package/runtime/node_modules/caniuse-lite/data/features/audiotracks.js +1 -1
  135. package/runtime/node_modules/caniuse-lite/data/features/autofocus.js +1 -1
  136. package/runtime/node_modules/caniuse-lite/data/features/auxclick.js +1 -1
  137. package/runtime/node_modules/caniuse-lite/data/features/av1.js +1 -1
  138. package/runtime/node_modules/caniuse-lite/data/features/avif.js +1 -1
  139. package/runtime/node_modules/caniuse-lite/data/features/background-attachment.js +1 -1
  140. package/runtime/node_modules/caniuse-lite/data/features/background-clip-text.js +1 -1
  141. package/runtime/node_modules/caniuse-lite/data/features/background-img-opts.js +1 -1
  142. package/runtime/node_modules/caniuse-lite/data/features/background-position-x-y.js +1 -1
  143. package/runtime/node_modules/caniuse-lite/data/features/background-repeat-round-space.js +1 -1
  144. package/runtime/node_modules/caniuse-lite/data/features/background-sync.js +1 -1
  145. package/runtime/node_modules/caniuse-lite/data/features/battery-status.js +1 -1
  146. package/runtime/node_modules/caniuse-lite/data/features/beacon.js +1 -1
  147. package/runtime/node_modules/caniuse-lite/data/features/beforeafterprint.js +1 -1
  148. package/runtime/node_modules/caniuse-lite/data/features/bigint.js +1 -1
  149. package/runtime/node_modules/caniuse-lite/data/features/blobbuilder.js +1 -1
  150. package/runtime/node_modules/caniuse-lite/data/features/bloburls.js +1 -1
  151. package/runtime/node_modules/caniuse-lite/data/features/border-image.js +1 -1
  152. package/runtime/node_modules/caniuse-lite/data/features/border-radius.js +1 -1
  153. package/runtime/node_modules/caniuse-lite/data/features/broadcastchannel.js +1 -1
  154. package/runtime/node_modules/caniuse-lite/data/features/brotli.js +1 -1
  155. package/runtime/node_modules/caniuse-lite/data/features/calc.js +1 -1
  156. package/runtime/node_modules/caniuse-lite/data/features/canvas-blending.js +1 -1
  157. package/runtime/node_modules/caniuse-lite/data/features/canvas-text.js +1 -1
  158. package/runtime/node_modules/caniuse-lite/data/features/canvas.js +1 -1
  159. package/runtime/node_modules/caniuse-lite/data/features/ch-unit.js +1 -1
  160. package/runtime/node_modules/caniuse-lite/data/features/chacha20-poly1305.js +1 -1
  161. package/runtime/node_modules/caniuse-lite/data/features/channel-messaging.js +1 -1
  162. package/runtime/node_modules/caniuse-lite/data/features/childnode-remove.js +1 -1
  163. package/runtime/node_modules/caniuse-lite/data/features/classlist.js +1 -1
  164. package/runtime/node_modules/caniuse-lite/data/features/client-hints-dpr-width-viewport.js +1 -1
  165. package/runtime/node_modules/caniuse-lite/data/features/clipboard.js +1 -1
  166. package/runtime/node_modules/caniuse-lite/data/features/colr-v1.js +1 -1
  167. package/runtime/node_modules/caniuse-lite/data/features/colr.js +1 -1
  168. package/runtime/node_modules/caniuse-lite/data/features/comparedocumentposition.js +1 -1
  169. package/runtime/node_modules/caniuse-lite/data/features/console-basic.js +1 -1
  170. package/runtime/node_modules/caniuse-lite/data/features/console-time.js +1 -1
  171. package/runtime/node_modules/caniuse-lite/data/features/const.js +1 -1
  172. package/runtime/node_modules/caniuse-lite/data/features/constraint-validation.js +1 -1
  173. package/runtime/node_modules/caniuse-lite/data/features/contenteditable.js +1 -1
  174. package/runtime/node_modules/caniuse-lite/data/features/contentsecuritypolicy.js +1 -1
  175. package/runtime/node_modules/caniuse-lite/data/features/contentsecuritypolicy2.js +1 -1
  176. package/runtime/node_modules/caniuse-lite/data/features/cookie-store-api.js +1 -1
  177. package/runtime/node_modules/caniuse-lite/data/features/cors.js +1 -1
  178. package/runtime/node_modules/caniuse-lite/data/features/createimagebitmap.js +1 -1
  179. package/runtime/node_modules/caniuse-lite/data/features/credential-management.js +1 -1
  180. package/runtime/node_modules/caniuse-lite/data/features/cross-document-view-transitions.js +1 -1
  181. package/runtime/node_modules/caniuse-lite/data/features/cryptography.js +1 -1
  182. package/runtime/node_modules/caniuse-lite/data/features/css-all.js +1 -1
  183. package/runtime/node_modules/caniuse-lite/data/features/css-anchor-positioning.js +1 -1
  184. package/runtime/node_modules/caniuse-lite/data/features/css-animation.js +1 -1
  185. package/runtime/node_modules/caniuse-lite/data/features/css-any-link.js +1 -1
  186. package/runtime/node_modules/caniuse-lite/data/features/css-appearance.js +1 -1
  187. package/runtime/node_modules/caniuse-lite/data/features/css-at-counter-style.js +1 -1
  188. package/runtime/node_modules/caniuse-lite/data/features/css-autofill.js +1 -1
  189. package/runtime/node_modules/caniuse-lite/data/features/css-backdrop-filter.js +1 -1
  190. package/runtime/node_modules/caniuse-lite/data/features/css-background-offsets.js +1 -1
  191. package/runtime/node_modules/caniuse-lite/data/features/css-backgroundblendmode.js +1 -1
  192. package/runtime/node_modules/caniuse-lite/data/features/css-boxdecorationbreak.js +1 -1
  193. package/runtime/node_modules/caniuse-lite/data/features/css-boxshadow.js +1 -1
  194. package/runtime/node_modules/caniuse-lite/data/features/css-canvas.js +1 -1
  195. package/runtime/node_modules/caniuse-lite/data/features/css-caret-color.js +1 -1
  196. package/runtime/node_modules/caniuse-lite/data/features/css-cascade-layers.js +1 -1
  197. package/runtime/node_modules/caniuse-lite/data/features/css-cascade-scope.js +1 -1
  198. package/runtime/node_modules/caniuse-lite/data/features/css-case-insensitive.js +1 -1
  199. package/runtime/node_modules/caniuse-lite/data/features/css-clip-path.js +1 -1
  200. package/runtime/node_modules/caniuse-lite/data/features/css-color-adjust.js +1 -1
  201. package/runtime/node_modules/caniuse-lite/data/features/css-color-function.js +1 -1
  202. package/runtime/node_modules/caniuse-lite/data/features/css-conic-gradients.js +1 -1
  203. package/runtime/node_modules/caniuse-lite/data/features/css-container-queries-style.js +1 -1
  204. package/runtime/node_modules/caniuse-lite/data/features/css-container-queries.js +1 -1
  205. package/runtime/node_modules/caniuse-lite/data/features/css-container-query-units.js +1 -1
  206. package/runtime/node_modules/caniuse-lite/data/features/css-containment.js +1 -1
  207. package/runtime/node_modules/caniuse-lite/data/features/css-content-visibility.js +1 -1
  208. package/runtime/node_modules/caniuse-lite/data/features/css-counters.js +1 -1
  209. package/runtime/node_modules/caniuse-lite/data/features/css-crisp-edges.js +1 -1
  210. package/runtime/node_modules/caniuse-lite/data/features/css-cross-fade.js +1 -1
  211. package/runtime/node_modules/caniuse-lite/data/features/css-default-pseudo.js +1 -1
  212. package/runtime/node_modules/caniuse-lite/data/features/css-descendant-gtgt.js +1 -1
  213. package/runtime/node_modules/caniuse-lite/data/features/css-deviceadaptation.js +1 -1
  214. package/runtime/node_modules/caniuse-lite/data/features/css-dir-pseudo.js +1 -1
  215. package/runtime/node_modules/caniuse-lite/data/features/css-display-contents.js +1 -1
  216. package/runtime/node_modules/caniuse-lite/data/features/css-element-function.js +1 -1
  217. package/runtime/node_modules/caniuse-lite/data/features/css-env-function.js +1 -1
  218. package/runtime/node_modules/caniuse-lite/data/features/css-exclusions.js +1 -1
  219. package/runtime/node_modules/caniuse-lite/data/features/css-featurequeries.js +1 -1
  220. package/runtime/node_modules/caniuse-lite/data/features/css-file-selector-button.js +1 -1
  221. package/runtime/node_modules/caniuse-lite/data/features/css-filter-function.js +1 -1
  222. package/runtime/node_modules/caniuse-lite/data/features/css-filters.js +1 -1
  223. package/runtime/node_modules/caniuse-lite/data/features/css-first-letter.js +1 -1
  224. package/runtime/node_modules/caniuse-lite/data/features/css-first-line.js +1 -1
  225. package/runtime/node_modules/caniuse-lite/data/features/css-fixed.js +1 -1
  226. package/runtime/node_modules/caniuse-lite/data/features/css-focus-visible.js +1 -1
  227. package/runtime/node_modules/caniuse-lite/data/features/css-focus-within.js +1 -1
  228. package/runtime/node_modules/caniuse-lite/data/features/css-font-palette.js +1 -1
  229. package/runtime/node_modules/caniuse-lite/data/features/css-font-rendering-controls.js +1 -1
  230. package/runtime/node_modules/caniuse-lite/data/features/css-font-stretch.js +1 -1
  231. package/runtime/node_modules/caniuse-lite/data/features/css-gencontent.js +1 -1
  232. package/runtime/node_modules/caniuse-lite/data/features/css-gradients.js +1 -1
  233. package/runtime/node_modules/caniuse-lite/data/features/css-grid-animation.js +1 -1
  234. package/runtime/node_modules/caniuse-lite/data/features/css-grid-lanes.js +1 -1
  235. package/runtime/node_modules/caniuse-lite/data/features/css-grid.js +1 -1
  236. package/runtime/node_modules/caniuse-lite/data/features/css-hanging-punctuation.js +1 -1
  237. package/runtime/node_modules/caniuse-lite/data/features/css-has.js +1 -1
  238. package/runtime/node_modules/caniuse-lite/data/features/css-hyphens.js +1 -1
  239. package/runtime/node_modules/caniuse-lite/data/features/css-if.js +1 -1
  240. package/runtime/node_modules/caniuse-lite/data/features/css-image-orientation.js +1 -1
  241. package/runtime/node_modules/caniuse-lite/data/features/css-image-set.js +1 -1
  242. package/runtime/node_modules/caniuse-lite/data/features/css-in-out-of-range.js +1 -1
  243. package/runtime/node_modules/caniuse-lite/data/features/css-indeterminate-pseudo.js +1 -1
  244. package/runtime/node_modules/caniuse-lite/data/features/css-initial-letter.js +1 -1
  245. package/runtime/node_modules/caniuse-lite/data/features/css-initial-value.js +1 -1
  246. package/runtime/node_modules/caniuse-lite/data/features/css-lch-lab.js +1 -1
  247. package/runtime/node_modules/caniuse-lite/data/features/css-letter-spacing.js +1 -1
  248. package/runtime/node_modules/caniuse-lite/data/features/css-line-clamp.js +1 -1
  249. package/runtime/node_modules/caniuse-lite/data/features/css-logical-props.js +1 -1
  250. package/runtime/node_modules/caniuse-lite/data/features/css-marker-pseudo.js +1 -1
  251. package/runtime/node_modules/caniuse-lite/data/features/css-masks.js +1 -1
  252. package/runtime/node_modules/caniuse-lite/data/features/css-matches-pseudo.js +1 -1
  253. package/runtime/node_modules/caniuse-lite/data/features/css-math-functions.js +1 -1
  254. package/runtime/node_modules/caniuse-lite/data/features/css-media-interaction.js +1 -1
  255. package/runtime/node_modules/caniuse-lite/data/features/css-media-range-syntax.js +1 -1
  256. package/runtime/node_modules/caniuse-lite/data/features/css-media-resolution.js +1 -1
  257. package/runtime/node_modules/caniuse-lite/data/features/css-media-scripting.js +1 -1
  258. package/runtime/node_modules/caniuse-lite/data/features/css-mediaqueries.js +1 -1
  259. package/runtime/node_modules/caniuse-lite/data/features/css-mixblendmode.js +1 -1
  260. package/runtime/node_modules/caniuse-lite/data/features/css-module-scripts.js +1 -1
  261. package/runtime/node_modules/caniuse-lite/data/features/css-motion-paths.js +1 -1
  262. package/runtime/node_modules/caniuse-lite/data/features/css-namespaces.js +1 -1
  263. package/runtime/node_modules/caniuse-lite/data/features/css-nesting.js +1 -1
  264. package/runtime/node_modules/caniuse-lite/data/features/css-not-sel-list.js +1 -1
  265. package/runtime/node_modules/caniuse-lite/data/features/css-nth-child-of.js +1 -1
  266. package/runtime/node_modules/caniuse-lite/data/features/css-opacity.js +1 -1
  267. package/runtime/node_modules/caniuse-lite/data/features/css-optional-pseudo.js +1 -1
  268. package/runtime/node_modules/caniuse-lite/data/features/css-overflow-anchor.js +1 -1
  269. package/runtime/node_modules/caniuse-lite/data/features/css-overflow-overlay.js +1 -1
  270. package/runtime/node_modules/caniuse-lite/data/features/css-overflow.js +1 -1
  271. package/runtime/node_modules/caniuse-lite/data/features/css-overscroll-behavior.js +1 -1
  272. package/runtime/node_modules/caniuse-lite/data/features/css-page-break.js +1 -1
  273. package/runtime/node_modules/caniuse-lite/data/features/css-paged-media.js +1 -1
  274. package/runtime/node_modules/caniuse-lite/data/features/css-paint-api.js +1 -1
  275. package/runtime/node_modules/caniuse-lite/data/features/css-placeholder-shown.js +1 -1
  276. package/runtime/node_modules/caniuse-lite/data/features/css-placeholder.js +1 -1
  277. package/runtime/node_modules/caniuse-lite/data/features/css-print-color-adjust.js +1 -1
  278. package/runtime/node_modules/caniuse-lite/data/features/css-read-only-write.js +1 -1
  279. package/runtime/node_modules/caniuse-lite/data/features/css-rebeccapurple.js +1 -1
  280. package/runtime/node_modules/caniuse-lite/data/features/css-reflections.js +1 -1
  281. package/runtime/node_modules/caniuse-lite/data/features/css-regions.js +1 -1
  282. package/runtime/node_modules/caniuse-lite/data/features/css-relative-colors.js +1 -1
  283. package/runtime/node_modules/caniuse-lite/data/features/css-repeating-gradients.js +1 -1
  284. package/runtime/node_modules/caniuse-lite/data/features/css-resize.js +1 -1
  285. package/runtime/node_modules/caniuse-lite/data/features/css-revert-value.js +1 -1
  286. package/runtime/node_modules/caniuse-lite/data/features/css-rrggbbaa.js +1 -1
  287. package/runtime/node_modules/caniuse-lite/data/features/css-scroll-behavior.js +1 -1
  288. package/runtime/node_modules/caniuse-lite/data/features/css-scrollbar.js +1 -1
  289. package/runtime/node_modules/caniuse-lite/data/features/css-sel2.js +1 -1
  290. package/runtime/node_modules/caniuse-lite/data/features/css-sel3.js +1 -1
  291. package/runtime/node_modules/caniuse-lite/data/features/css-selection.js +1 -1
  292. package/runtime/node_modules/caniuse-lite/data/features/css-shapes.js +1 -1
  293. package/runtime/node_modules/caniuse-lite/data/features/css-snappoints.js +1 -1
  294. package/runtime/node_modules/caniuse-lite/data/features/css-sticky.js +1 -1
  295. package/runtime/node_modules/caniuse-lite/data/features/css-subgrid.js +1 -1
  296. package/runtime/node_modules/caniuse-lite/data/features/css-supports-api.js +1 -1
  297. package/runtime/node_modules/caniuse-lite/data/features/css-table.js +1 -1
  298. package/runtime/node_modules/caniuse-lite/data/features/css-text-align-last.js +1 -1
  299. package/runtime/node_modules/caniuse-lite/data/features/css-text-box-trim.js +1 -1
  300. package/runtime/node_modules/caniuse-lite/data/features/css-text-indent.js +1 -1
  301. package/runtime/node_modules/caniuse-lite/data/features/css-text-justify.js +1 -1
  302. package/runtime/node_modules/caniuse-lite/data/features/css-text-orientation.js +1 -1
  303. package/runtime/node_modules/caniuse-lite/data/features/css-text-spacing.js +1 -1
  304. package/runtime/node_modules/caniuse-lite/data/features/css-text-wrap-balance.js +1 -1
  305. package/runtime/node_modules/caniuse-lite/data/features/css-textshadow.js +1 -1
  306. package/runtime/node_modules/caniuse-lite/data/features/css-touch-action.js +1 -1
  307. package/runtime/node_modules/caniuse-lite/data/features/css-transitions.js +1 -1
  308. package/runtime/node_modules/caniuse-lite/data/features/css-unicode-bidi.js +1 -1
  309. package/runtime/node_modules/caniuse-lite/data/features/css-unset-value.js +1 -1
  310. package/runtime/node_modules/caniuse-lite/data/features/css-variables.js +1 -1
  311. package/runtime/node_modules/caniuse-lite/data/features/css-when-else.js +1 -1
  312. package/runtime/node_modules/caniuse-lite/data/features/css-widows-orphans.js +1 -1
  313. package/runtime/node_modules/caniuse-lite/data/features/css-width-stretch.js +1 -1
  314. package/runtime/node_modules/caniuse-lite/data/features/css-writing-mode.js +1 -1
  315. package/runtime/node_modules/caniuse-lite/data/features/css-zoom.js +1 -1
  316. package/runtime/node_modules/caniuse-lite/data/features/css3-attr.js +1 -1
  317. package/runtime/node_modules/caniuse-lite/data/features/css3-boxsizing.js +1 -1
  318. package/runtime/node_modules/caniuse-lite/data/features/css3-colors.js +1 -1
  319. package/runtime/node_modules/caniuse-lite/data/features/css3-cursors-grab.js +1 -1
  320. package/runtime/node_modules/caniuse-lite/data/features/css3-cursors-newer.js +1 -1
  321. package/runtime/node_modules/caniuse-lite/data/features/css3-cursors.js +1 -1
  322. package/runtime/node_modules/caniuse-lite/data/features/css3-tabsize.js +1 -1
  323. package/runtime/node_modules/caniuse-lite/data/features/currentcolor.js +1 -1
  324. package/runtime/node_modules/caniuse-lite/data/features/custom-elements.js +1 -1
  325. package/runtime/node_modules/caniuse-lite/data/features/custom-elementsv1.js +1 -1
  326. package/runtime/node_modules/caniuse-lite/data/features/customevent.js +1 -1
  327. package/runtime/node_modules/caniuse-lite/data/features/customizable-select.js +1 -1
  328. package/runtime/node_modules/caniuse-lite/data/features/datalist.js +1 -1
  329. package/runtime/node_modules/caniuse-lite/data/features/dataset.js +1 -1
  330. package/runtime/node_modules/caniuse-lite/data/features/datauri.js +1 -1
  331. package/runtime/node_modules/caniuse-lite/data/features/date-tolocaledatestring.js +1 -1
  332. package/runtime/node_modules/caniuse-lite/data/features/declarative-shadow-dom.js +1 -1
  333. package/runtime/node_modules/caniuse-lite/data/features/decorators.js +1 -1
  334. package/runtime/node_modules/caniuse-lite/data/features/details.js +1 -1
  335. package/runtime/node_modules/caniuse-lite/data/features/deviceorientation.js +1 -1
  336. package/runtime/node_modules/caniuse-lite/data/features/devicepixelratio.js +1 -1
  337. package/runtime/node_modules/caniuse-lite/data/features/dialog.js +1 -1
  338. package/runtime/node_modules/caniuse-lite/data/features/dispatchevent.js +1 -1
  339. package/runtime/node_modules/caniuse-lite/data/features/dnssec.js +1 -1
  340. package/runtime/node_modules/caniuse-lite/data/features/do-not-track.js +1 -1
  341. package/runtime/node_modules/caniuse-lite/data/features/document-currentscript.js +1 -1
  342. package/runtime/node_modules/caniuse-lite/data/features/document-evaluate-xpath.js +1 -1
  343. package/runtime/node_modules/caniuse-lite/data/features/document-execcommand.js +1 -1
  344. package/runtime/node_modules/caniuse-lite/data/features/document-policy.js +1 -1
  345. package/runtime/node_modules/caniuse-lite/data/features/document-scrollingelement.js +1 -1
  346. package/runtime/node_modules/caniuse-lite/data/features/documenthead.js +1 -1
  347. package/runtime/node_modules/caniuse-lite/data/features/dom-manip-convenience.js +1 -1
  348. package/runtime/node_modules/caniuse-lite/data/features/dom-range.js +1 -1
  349. package/runtime/node_modules/caniuse-lite/data/features/domcontentloaded.js +1 -1
  350. package/runtime/node_modules/caniuse-lite/data/features/dommatrix.js +1 -1
  351. package/runtime/node_modules/caniuse-lite/data/features/download.js +1 -1
  352. package/runtime/node_modules/caniuse-lite/data/features/dragndrop.js +1 -1
  353. package/runtime/node_modules/caniuse-lite/data/features/element-closest.js +1 -1
  354. package/runtime/node_modules/caniuse-lite/data/features/element-from-point.js +1 -1
  355. package/runtime/node_modules/caniuse-lite/data/features/element-scroll-methods.js +1 -1
  356. package/runtime/node_modules/caniuse-lite/data/features/eme.js +1 -1
  357. package/runtime/node_modules/caniuse-lite/data/features/eot.js +1 -1
  358. package/runtime/node_modules/caniuse-lite/data/features/es5.js +1 -1
  359. package/runtime/node_modules/caniuse-lite/data/features/es6-class.js +1 -1
  360. package/runtime/node_modules/caniuse-lite/data/features/es6-generators.js +1 -1
  361. package/runtime/node_modules/caniuse-lite/data/features/es6-module-dynamic-import.js +1 -1
  362. package/runtime/node_modules/caniuse-lite/data/features/es6-module.js +1 -1
  363. package/runtime/node_modules/caniuse-lite/data/features/es6-number.js +1 -1
  364. package/runtime/node_modules/caniuse-lite/data/features/es6-string-includes.js +1 -1
  365. package/runtime/node_modules/caniuse-lite/data/features/es6.js +1 -1
  366. package/runtime/node_modules/caniuse-lite/data/features/eventsource.js +1 -1
  367. package/runtime/node_modules/caniuse-lite/data/features/extended-system-fonts.js +1 -1
  368. package/runtime/node_modules/caniuse-lite/data/features/feature-policy.js +1 -1
  369. package/runtime/node_modules/caniuse-lite/data/features/fetch.js +1 -1
  370. package/runtime/node_modules/caniuse-lite/data/features/fieldset-disabled.js +1 -1
  371. package/runtime/node_modules/caniuse-lite/data/features/fileapi.js +1 -1
  372. package/runtime/node_modules/caniuse-lite/data/features/filereader.js +1 -1
  373. package/runtime/node_modules/caniuse-lite/data/features/filereadersync.js +1 -1
  374. package/runtime/node_modules/caniuse-lite/data/features/filesystem.js +1 -1
  375. package/runtime/node_modules/caniuse-lite/data/features/flac.js +1 -1
  376. package/runtime/node_modules/caniuse-lite/data/features/flexbox-gap.js +1 -1
  377. package/runtime/node_modules/caniuse-lite/data/features/flexbox.js +1 -1
  378. package/runtime/node_modules/caniuse-lite/data/features/flow-root.js +1 -1
  379. package/runtime/node_modules/caniuse-lite/data/features/focusin-focusout-events.js +1 -1
  380. package/runtime/node_modules/caniuse-lite/data/features/font-family-system-ui.js +1 -1
  381. package/runtime/node_modules/caniuse-lite/data/features/font-feature.js +1 -1
  382. package/runtime/node_modules/caniuse-lite/data/features/font-kerning.js +1 -1
  383. package/runtime/node_modules/caniuse-lite/data/features/font-loading.js +1 -1
  384. package/runtime/node_modules/caniuse-lite/data/features/font-size-adjust.js +1 -1
  385. package/runtime/node_modules/caniuse-lite/data/features/font-smooth.js +1 -1
  386. package/runtime/node_modules/caniuse-lite/data/features/font-unicode-range.js +1 -1
  387. package/runtime/node_modules/caniuse-lite/data/features/font-variant-alternates.js +1 -1
  388. package/runtime/node_modules/caniuse-lite/data/features/font-variant-numeric.js +1 -1
  389. package/runtime/node_modules/caniuse-lite/data/features/fontface.js +1 -1
  390. package/runtime/node_modules/caniuse-lite/data/features/form-attribute.js +1 -1
  391. package/runtime/node_modules/caniuse-lite/data/features/form-submit-attributes.js +1 -1
  392. package/runtime/node_modules/caniuse-lite/data/features/form-validation.js +1 -1
  393. package/runtime/node_modules/caniuse-lite/data/features/forms.js +1 -1
  394. package/runtime/node_modules/caniuse-lite/data/features/fullscreen.js +1 -1
  395. package/runtime/node_modules/caniuse-lite/data/features/gamepad.js +1 -1
  396. package/runtime/node_modules/caniuse-lite/data/features/geolocation.js +1 -1
  397. package/runtime/node_modules/caniuse-lite/data/features/getboundingclientrect.js +1 -1
  398. package/runtime/node_modules/caniuse-lite/data/features/getcomputedstyle.js +1 -1
  399. package/runtime/node_modules/caniuse-lite/data/features/getelementsbyclassname.js +1 -1
  400. package/runtime/node_modules/caniuse-lite/data/features/getrandomvalues.js +1 -1
  401. package/runtime/node_modules/caniuse-lite/data/features/gyroscope.js +1 -1
  402. package/runtime/node_modules/caniuse-lite/data/features/hardwareconcurrency.js +1 -1
  403. package/runtime/node_modules/caniuse-lite/data/features/hashchange.js +1 -1
  404. package/runtime/node_modules/caniuse-lite/data/features/heif.js +1 -1
  405. package/runtime/node_modules/caniuse-lite/data/features/hevc.js +1 -1
  406. package/runtime/node_modules/caniuse-lite/data/features/hidden.js +1 -1
  407. package/runtime/node_modules/caniuse-lite/data/features/high-resolution-time.js +1 -1
  408. package/runtime/node_modules/caniuse-lite/data/features/history.js +1 -1
  409. package/runtime/node_modules/caniuse-lite/data/features/html-media-capture.js +1 -1
  410. package/runtime/node_modules/caniuse-lite/data/features/html5semantic.js +1 -1
  411. package/runtime/node_modules/caniuse-lite/data/features/http-live-streaming.js +1 -1
  412. package/runtime/node_modules/caniuse-lite/data/features/http2.js +1 -1
  413. package/runtime/node_modules/caniuse-lite/data/features/http3.js +1 -1
  414. package/runtime/node_modules/caniuse-lite/data/features/iframe-sandbox.js +1 -1
  415. package/runtime/node_modules/caniuse-lite/data/features/iframe-seamless.js +1 -1
  416. package/runtime/node_modules/caniuse-lite/data/features/iframe-srcdoc.js +1 -1
  417. package/runtime/node_modules/caniuse-lite/data/features/imagecapture.js +1 -1
  418. package/runtime/node_modules/caniuse-lite/data/features/ime.js +1 -1
  419. package/runtime/node_modules/caniuse-lite/data/features/img-naturalwidth-naturalheight.js +1 -1
  420. package/runtime/node_modules/caniuse-lite/data/features/import-maps.js +1 -1
  421. package/runtime/node_modules/caniuse-lite/data/features/imports.js +1 -1
  422. package/runtime/node_modules/caniuse-lite/data/features/indeterminate-checkbox.js +1 -1
  423. package/runtime/node_modules/caniuse-lite/data/features/indexeddb.js +1 -1
  424. package/runtime/node_modules/caniuse-lite/data/features/indexeddb2.js +1 -1
  425. package/runtime/node_modules/caniuse-lite/data/features/inline-block.js +1 -1
  426. package/runtime/node_modules/caniuse-lite/data/features/innertext.js +1 -1
  427. package/runtime/node_modules/caniuse-lite/data/features/input-autocomplete-onoff.js +1 -1
  428. package/runtime/node_modules/caniuse-lite/data/features/input-color.js +1 -1
  429. package/runtime/node_modules/caniuse-lite/data/features/input-datetime.js +1 -1
  430. package/runtime/node_modules/caniuse-lite/data/features/input-email-tel-url.js +1 -1
  431. package/runtime/node_modules/caniuse-lite/data/features/input-event.js +1 -1
  432. package/runtime/node_modules/caniuse-lite/data/features/input-file-accept.js +1 -1
  433. package/runtime/node_modules/caniuse-lite/data/features/input-file-directory.js +1 -1
  434. package/runtime/node_modules/caniuse-lite/data/features/input-file-multiple.js +1 -1
  435. package/runtime/node_modules/caniuse-lite/data/features/input-inputmode.js +1 -1
  436. package/runtime/node_modules/caniuse-lite/data/features/input-minlength.js +1 -1
  437. package/runtime/node_modules/caniuse-lite/data/features/input-number.js +1 -1
  438. package/runtime/node_modules/caniuse-lite/data/features/input-pattern.js +1 -1
  439. package/runtime/node_modules/caniuse-lite/data/features/input-placeholder.js +1 -1
  440. package/runtime/node_modules/caniuse-lite/data/features/input-range.js +1 -1
  441. package/runtime/node_modules/caniuse-lite/data/features/input-search.js +1 -1
  442. package/runtime/node_modules/caniuse-lite/data/features/input-selection.js +1 -1
  443. package/runtime/node_modules/caniuse-lite/data/features/insert-adjacent.js +1 -1
  444. package/runtime/node_modules/caniuse-lite/data/features/insertadjacenthtml.js +1 -1
  445. package/runtime/node_modules/caniuse-lite/data/features/internationalization.js +1 -1
  446. package/runtime/node_modules/caniuse-lite/data/features/intersectionobserver-v2.js +1 -1
  447. package/runtime/node_modules/caniuse-lite/data/features/intersectionobserver.js +1 -1
  448. package/runtime/node_modules/caniuse-lite/data/features/intl-pluralrules.js +1 -1
  449. package/runtime/node_modules/caniuse-lite/data/features/intrinsic-width.js +1 -1
  450. package/runtime/node_modules/caniuse-lite/data/features/jpeg2000.js +1 -1
  451. package/runtime/node_modules/caniuse-lite/data/features/jpegxl.js +1 -1
  452. package/runtime/node_modules/caniuse-lite/data/features/jpegxr.js +1 -1
  453. package/runtime/node_modules/caniuse-lite/data/features/js-regexp-lookbehind.js +1 -1
  454. package/runtime/node_modules/caniuse-lite/data/features/json.js +1 -1
  455. package/runtime/node_modules/caniuse-lite/data/features/justify-content-space-evenly.js +1 -1
  456. package/runtime/node_modules/caniuse-lite/data/features/kerning-pairs-ligatures.js +1 -1
  457. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-charcode.js +1 -1
  458. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-code.js +1 -1
  459. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-getmodifierstate.js +1 -1
  460. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-key.js +1 -1
  461. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-location.js +1 -1
  462. package/runtime/node_modules/caniuse-lite/data/features/keyboardevent-which.js +1 -1
  463. package/runtime/node_modules/caniuse-lite/data/features/lazyload.js +1 -1
  464. package/runtime/node_modules/caniuse-lite/data/features/let.js +1 -1
  465. package/runtime/node_modules/caniuse-lite/data/features/link-icon-png.js +1 -1
  466. package/runtime/node_modules/caniuse-lite/data/features/link-icon-svg.js +1 -1
  467. package/runtime/node_modules/caniuse-lite/data/features/link-rel-dns-prefetch.js +1 -1
  468. package/runtime/node_modules/caniuse-lite/data/features/link-rel-modulepreload.js +1 -1
  469. package/runtime/node_modules/caniuse-lite/data/features/link-rel-preconnect.js +1 -1
  470. package/runtime/node_modules/caniuse-lite/data/features/link-rel-prefetch.js +1 -1
  471. package/runtime/node_modules/caniuse-lite/data/features/link-rel-preload.js +1 -1
  472. package/runtime/node_modules/caniuse-lite/data/features/link-rel-prerender.js +1 -1
  473. package/runtime/node_modules/caniuse-lite/data/features/loading-lazy-attr.js +1 -1
  474. package/runtime/node_modules/caniuse-lite/data/features/loading-lazy-media.js +1 -1
  475. package/runtime/node_modules/caniuse-lite/data/features/localecompare.js +1 -1
  476. package/runtime/node_modules/caniuse-lite/data/features/magnetometer.js +1 -1
  477. package/runtime/node_modules/caniuse-lite/data/features/matchesselector.js +1 -1
  478. package/runtime/node_modules/caniuse-lite/data/features/matchmedia.js +1 -1
  479. package/runtime/node_modules/caniuse-lite/data/features/mathml.js +1 -1
  480. package/runtime/node_modules/caniuse-lite/data/features/maxlength.js +1 -1
  481. package/runtime/node_modules/caniuse-lite/data/features/mdn-css-backdrop-pseudo-element.js +1 -1
  482. package/runtime/node_modules/caniuse-lite/data/features/mdn-css-unicode-bidi-isolate-override.js +1 -1
  483. package/runtime/node_modules/caniuse-lite/data/features/mdn-css-unicode-bidi-isolate.js +1 -1
  484. package/runtime/node_modules/caniuse-lite/data/features/mdn-css-unicode-bidi-plaintext.js +1 -1
  485. package/runtime/node_modules/caniuse-lite/data/features/mdn-text-decoration-color.js +1 -1
  486. package/runtime/node_modules/caniuse-lite/data/features/mdn-text-decoration-line.js +1 -1
  487. package/runtime/node_modules/caniuse-lite/data/features/mdn-text-decoration-shorthand.js +1 -1
  488. package/runtime/node_modules/caniuse-lite/data/features/mdn-text-decoration-style.js +1 -1
  489. package/runtime/node_modules/caniuse-lite/data/features/media-fragments.js +1 -1
  490. package/runtime/node_modules/caniuse-lite/data/features/mediacapture-fromelement.js +1 -1
  491. package/runtime/node_modules/caniuse-lite/data/features/mediarecorder.js +1 -1
  492. package/runtime/node_modules/caniuse-lite/data/features/mediasource.js +1 -1
  493. package/runtime/node_modules/caniuse-lite/data/features/menu.js +1 -1
  494. package/runtime/node_modules/caniuse-lite/data/features/meta-theme-color.js +1 -1
  495. package/runtime/node_modules/caniuse-lite/data/features/meter.js +1 -1
  496. package/runtime/node_modules/caniuse-lite/data/features/midi.js +1 -1
  497. package/runtime/node_modules/caniuse-lite/data/features/minmaxwh.js +1 -1
  498. package/runtime/node_modules/caniuse-lite/data/features/mp3.js +1 -1
  499. package/runtime/node_modules/caniuse-lite/data/features/mpeg-dash.js +1 -1
  500. package/runtime/node_modules/caniuse-lite/data/features/mpeg4.js +1 -1
  501. package/runtime/node_modules/caniuse-lite/data/features/multibackgrounds.js +1 -1
  502. package/runtime/node_modules/caniuse-lite/data/features/multicolumn.js +1 -1
  503. package/runtime/node_modules/caniuse-lite/data/features/mutation-events.js +1 -1
  504. package/runtime/node_modules/caniuse-lite/data/features/mutationobserver.js +1 -1
  505. package/runtime/node_modules/caniuse-lite/data/features/namevalue-storage.js +1 -1
  506. package/runtime/node_modules/caniuse-lite/data/features/native-filesystem-api.js +1 -1
  507. package/runtime/node_modules/caniuse-lite/data/features/nav-timing.js +1 -1
  508. package/runtime/node_modules/caniuse-lite/data/features/netinfo.js +1 -1
  509. package/runtime/node_modules/caniuse-lite/data/features/notifications.js +1 -1
  510. package/runtime/node_modules/caniuse-lite/data/features/object-entries.js +1 -1
  511. package/runtime/node_modules/caniuse-lite/data/features/object-fit.js +1 -1
  512. package/runtime/node_modules/caniuse-lite/data/features/object-observe.js +1 -1
  513. package/runtime/node_modules/caniuse-lite/data/features/object-values.js +1 -1
  514. package/runtime/node_modules/caniuse-lite/data/features/objectrtc.js +1 -1
  515. package/runtime/node_modules/caniuse-lite/data/features/offline-apps.js +1 -1
  516. package/runtime/node_modules/caniuse-lite/data/features/offscreencanvas.js +1 -1
  517. package/runtime/node_modules/caniuse-lite/data/features/ogg-vorbis.js +1 -1
  518. package/runtime/node_modules/caniuse-lite/data/features/ogv.js +1 -1
  519. package/runtime/node_modules/caniuse-lite/data/features/ol-reversed.js +1 -1
  520. package/runtime/node_modules/caniuse-lite/data/features/once-event-listener.js +1 -1
  521. package/runtime/node_modules/caniuse-lite/data/features/online-status.js +1 -1
  522. package/runtime/node_modules/caniuse-lite/data/features/opus.js +1 -1
  523. package/runtime/node_modules/caniuse-lite/data/features/orientation-sensor.js +1 -1
  524. package/runtime/node_modules/caniuse-lite/data/features/outline.js +1 -1
  525. package/runtime/node_modules/caniuse-lite/data/features/pad-start-end.js +1 -1
  526. package/runtime/node_modules/caniuse-lite/data/features/page-transition-events.js +1 -1
  527. package/runtime/node_modules/caniuse-lite/data/features/pagevisibility.js +1 -1
  528. package/runtime/node_modules/caniuse-lite/data/features/passive-event-listener.js +1 -1
  529. package/runtime/node_modules/caniuse-lite/data/features/passkeys.js +1 -1
  530. package/runtime/node_modules/caniuse-lite/data/features/passwordrules.js +1 -1
  531. package/runtime/node_modules/caniuse-lite/data/features/path2d.js +1 -1
  532. package/runtime/node_modules/caniuse-lite/data/features/payment-request.js +1 -1
  533. package/runtime/node_modules/caniuse-lite/data/features/pdf-viewer.js +1 -1
  534. package/runtime/node_modules/caniuse-lite/data/features/permissions-api.js +1 -1
  535. package/runtime/node_modules/caniuse-lite/data/features/permissions-policy.js +1 -1
  536. package/runtime/node_modules/caniuse-lite/data/features/picture-in-picture.js +1 -1
  537. package/runtime/node_modules/caniuse-lite/data/features/picture.js +1 -1
  538. package/runtime/node_modules/caniuse-lite/data/features/ping.js +1 -1
  539. package/runtime/node_modules/caniuse-lite/data/features/png-alpha.js +1 -1
  540. package/runtime/node_modules/caniuse-lite/data/features/pointer-events.js +1 -1
  541. package/runtime/node_modules/caniuse-lite/data/features/pointer.js +1 -1
  542. package/runtime/node_modules/caniuse-lite/data/features/pointerlock.js +1 -1
  543. package/runtime/node_modules/caniuse-lite/data/features/portals.js +1 -1
  544. package/runtime/node_modules/caniuse-lite/data/features/prefers-color-scheme.js +1 -1
  545. package/runtime/node_modules/caniuse-lite/data/features/prefers-reduced-motion.js +1 -1
  546. package/runtime/node_modules/caniuse-lite/data/features/progress.js +1 -1
  547. package/runtime/node_modules/caniuse-lite/data/features/promise-finally.js +1 -1
  548. package/runtime/node_modules/caniuse-lite/data/features/promises.js +1 -1
  549. package/runtime/node_modules/caniuse-lite/data/features/proximity.js +1 -1
  550. package/runtime/node_modules/caniuse-lite/data/features/proxy.js +1 -1
  551. package/runtime/node_modules/caniuse-lite/data/features/publickeypinning.js +1 -1
  552. package/runtime/node_modules/caniuse-lite/data/features/push-api.js +1 -1
  553. package/runtime/node_modules/caniuse-lite/data/features/queryselector.js +1 -1
  554. package/runtime/node_modules/caniuse-lite/data/features/readonly-attr.js +1 -1
  555. package/runtime/node_modules/caniuse-lite/data/features/referrer-policy.js +1 -1
  556. package/runtime/node_modules/caniuse-lite/data/features/registerprotocolhandler.js +1 -1
  557. package/runtime/node_modules/caniuse-lite/data/features/rel-noopener.js +1 -1
  558. package/runtime/node_modules/caniuse-lite/data/features/rel-noreferrer.js +1 -1
  559. package/runtime/node_modules/caniuse-lite/data/features/rellist.js +1 -1
  560. package/runtime/node_modules/caniuse-lite/data/features/rem.js +1 -1
  561. package/runtime/node_modules/caniuse-lite/data/features/requestanimationframe.js +1 -1
  562. package/runtime/node_modules/caniuse-lite/data/features/requestidlecallback.js +1 -1
  563. package/runtime/node_modules/caniuse-lite/data/features/resizeobserver.js +1 -1
  564. package/runtime/node_modules/caniuse-lite/data/features/resource-timing.js +1 -1
  565. package/runtime/node_modules/caniuse-lite/data/features/rest-parameters.js +1 -1
  566. package/runtime/node_modules/caniuse-lite/data/features/rtcpeerconnection.js +1 -1
  567. package/runtime/node_modules/caniuse-lite/data/features/ruby.js +1 -1
  568. package/runtime/node_modules/caniuse-lite/data/features/run-in.js +1 -1
  569. package/runtime/node_modules/caniuse-lite/data/features/same-site-cookie-attribute.js +1 -1
  570. package/runtime/node_modules/caniuse-lite/data/features/screen-orientation.js +1 -1
  571. package/runtime/node_modules/caniuse-lite/data/features/script-async.js +1 -1
  572. package/runtime/node_modules/caniuse-lite/data/features/script-defer.js +1 -1
  573. package/runtime/node_modules/caniuse-lite/data/features/scrollintoview.js +1 -1
  574. package/runtime/node_modules/caniuse-lite/data/features/scrollintoviewifneeded.js +1 -1
  575. package/runtime/node_modules/caniuse-lite/data/features/sdch.js +1 -1
  576. package/runtime/node_modules/caniuse-lite/data/features/selection-api.js +1 -1
  577. package/runtime/node_modules/caniuse-lite/data/features/server-timing.js +1 -1
  578. package/runtime/node_modules/caniuse-lite/data/features/serviceworkers.js +1 -1
  579. package/runtime/node_modules/caniuse-lite/data/features/setimmediate.js +1 -1
  580. package/runtime/node_modules/caniuse-lite/data/features/shadowdom.js +1 -1
  581. package/runtime/node_modules/caniuse-lite/data/features/shadowdomv1.js +1 -1
  582. package/runtime/node_modules/caniuse-lite/data/features/sharedarraybuffer.js +1 -1
  583. package/runtime/node_modules/caniuse-lite/data/features/sharedworkers.js +1 -1
  584. package/runtime/node_modules/caniuse-lite/data/features/sni.js +1 -1
  585. package/runtime/node_modules/caniuse-lite/data/features/spdy.js +1 -1
  586. package/runtime/node_modules/caniuse-lite/data/features/speech-recognition.js +1 -1
  587. package/runtime/node_modules/caniuse-lite/data/features/speech-synthesis.js +1 -1
  588. package/runtime/node_modules/caniuse-lite/data/features/spellcheck-attribute.js +1 -1
  589. package/runtime/node_modules/caniuse-lite/data/features/sql-storage.js +1 -1
  590. package/runtime/node_modules/caniuse-lite/data/features/srcset.js +1 -1
  591. package/runtime/node_modules/caniuse-lite/data/features/stream.js +1 -1
  592. package/runtime/node_modules/caniuse-lite/data/features/streams.js +1 -1
  593. package/runtime/node_modules/caniuse-lite/data/features/stricttransportsecurity.js +1 -1
  594. package/runtime/node_modules/caniuse-lite/data/features/style-scoped.js +1 -1
  595. package/runtime/node_modules/caniuse-lite/data/features/subresource-bundling.js +1 -1
  596. package/runtime/node_modules/caniuse-lite/data/features/subresource-integrity.js +1 -1
  597. package/runtime/node_modules/caniuse-lite/data/features/svg-css.js +1 -1
  598. package/runtime/node_modules/caniuse-lite/data/features/svg-filters.js +1 -1
  599. package/runtime/node_modules/caniuse-lite/data/features/svg-fonts.js +1 -1
  600. package/runtime/node_modules/caniuse-lite/data/features/svg-fragment.js +1 -1
  601. package/runtime/node_modules/caniuse-lite/data/features/svg-html.js +1 -1
  602. package/runtime/node_modules/caniuse-lite/data/features/svg-html5.js +1 -1
  603. package/runtime/node_modules/caniuse-lite/data/features/svg-img.js +1 -1
  604. package/runtime/node_modules/caniuse-lite/data/features/svg-smil.js +1 -1
  605. package/runtime/node_modules/caniuse-lite/data/features/svg.js +1 -1
  606. package/runtime/node_modules/caniuse-lite/data/features/sxg.js +1 -1
  607. package/runtime/node_modules/caniuse-lite/data/features/tabindex-attr.js +1 -1
  608. package/runtime/node_modules/caniuse-lite/data/features/template-literals.js +1 -1
  609. package/runtime/node_modules/caniuse-lite/data/features/template.js +1 -1
  610. package/runtime/node_modules/caniuse-lite/data/features/temporal.js +1 -1
  611. package/runtime/node_modules/caniuse-lite/data/features/testfeat.js +1 -1
  612. package/runtime/node_modules/caniuse-lite/data/features/text-decoration.js +1 -1
  613. package/runtime/node_modules/caniuse-lite/data/features/text-emphasis.js +1 -1
  614. package/runtime/node_modules/caniuse-lite/data/features/text-overflow.js +1 -1
  615. package/runtime/node_modules/caniuse-lite/data/features/text-size-adjust.js +1 -1
  616. package/runtime/node_modules/caniuse-lite/data/features/text-stroke.js +1 -1
  617. package/runtime/node_modules/caniuse-lite/data/features/textcontent.js +1 -1
  618. package/runtime/node_modules/caniuse-lite/data/features/textencoder.js +1 -1
  619. package/runtime/node_modules/caniuse-lite/data/features/tls1-1.js +1 -1
  620. package/runtime/node_modules/caniuse-lite/data/features/tls1-2.js +1 -1
  621. package/runtime/node_modules/caniuse-lite/data/features/tls1-3.js +1 -1
  622. package/runtime/node_modules/caniuse-lite/data/features/touch.js +1 -1
  623. package/runtime/node_modules/caniuse-lite/data/features/transforms2d.js +1 -1
  624. package/runtime/node_modules/caniuse-lite/data/features/transforms3d.js +1 -1
  625. package/runtime/node_modules/caniuse-lite/data/features/trusted-types.js +1 -1
  626. package/runtime/node_modules/caniuse-lite/data/features/ttf.js +1 -1
  627. package/runtime/node_modules/caniuse-lite/data/features/typedarrays.js +1 -1
  628. package/runtime/node_modules/caniuse-lite/data/features/u2f.js +1 -1
  629. package/runtime/node_modules/caniuse-lite/data/features/unhandledrejection.js +1 -1
  630. package/runtime/node_modules/caniuse-lite/data/features/upgradeinsecurerequests.js +1 -1
  631. package/runtime/node_modules/caniuse-lite/data/features/url-scroll-to-text-fragment.js +1 -1
  632. package/runtime/node_modules/caniuse-lite/data/features/url.js +1 -1
  633. package/runtime/node_modules/caniuse-lite/data/features/urlsearchparams.js +1 -1
  634. package/runtime/node_modules/caniuse-lite/data/features/use-strict.js +1 -1
  635. package/runtime/node_modules/caniuse-lite/data/features/user-select-none.js +1 -1
  636. package/runtime/node_modules/caniuse-lite/data/features/user-timing.js +1 -1
  637. package/runtime/node_modules/caniuse-lite/data/features/variable-fonts.js +1 -1
  638. package/runtime/node_modules/caniuse-lite/data/features/vector-effect.js +1 -1
  639. package/runtime/node_modules/caniuse-lite/data/features/vibration.js +1 -1
  640. package/runtime/node_modules/caniuse-lite/data/features/video.js +1 -1
  641. package/runtime/node_modules/caniuse-lite/data/features/videotracks.js +1 -1
  642. package/runtime/node_modules/caniuse-lite/data/features/view-transitions.js +1 -1
  643. package/runtime/node_modules/caniuse-lite/data/features/viewport-unit-variants.js +1 -1
  644. package/runtime/node_modules/caniuse-lite/data/features/viewport-units.js +1 -1
  645. package/runtime/node_modules/caniuse-lite/data/features/wai-aria.js +1 -1
  646. package/runtime/node_modules/caniuse-lite/data/features/wake-lock.js +1 -1
  647. package/runtime/node_modules/caniuse-lite/data/features/wasm-bigint.js +1 -1
  648. package/runtime/node_modules/caniuse-lite/data/features/wasm-bulk-memory.js +1 -1
  649. package/runtime/node_modules/caniuse-lite/data/features/wasm-extended-const.js +1 -1
  650. package/runtime/node_modules/caniuse-lite/data/features/wasm-gc.js +1 -1
  651. package/runtime/node_modules/caniuse-lite/data/features/wasm-multi-memory.js +1 -1
  652. package/runtime/node_modules/caniuse-lite/data/features/wasm-multi-value.js +1 -1
  653. package/runtime/node_modules/caniuse-lite/data/features/wasm-mutable-globals.js +1 -1
  654. package/runtime/node_modules/caniuse-lite/data/features/wasm-nontrapping-fptoint.js +1 -1
  655. package/runtime/node_modules/caniuse-lite/data/features/wasm-reference-types.js +1 -1
  656. package/runtime/node_modules/caniuse-lite/data/features/wasm-relaxed-simd.js +1 -1
  657. package/runtime/node_modules/caniuse-lite/data/features/wasm-signext.js +1 -1
  658. package/runtime/node_modules/caniuse-lite/data/features/wasm-simd.js +1 -1
  659. package/runtime/node_modules/caniuse-lite/data/features/wasm-tail-calls.js +1 -1
  660. package/runtime/node_modules/caniuse-lite/data/features/wasm-threads.js +1 -1
  661. package/runtime/node_modules/caniuse-lite/data/features/wasm.js +1 -1
  662. package/runtime/node_modules/caniuse-lite/data/features/wav.js +1 -1
  663. package/runtime/node_modules/caniuse-lite/data/features/wbr-element.js +1 -1
  664. package/runtime/node_modules/caniuse-lite/data/features/web-animation.js +1 -1
  665. package/runtime/node_modules/caniuse-lite/data/features/web-app-manifest.js +1 -1
  666. package/runtime/node_modules/caniuse-lite/data/features/web-bluetooth.js +1 -1
  667. package/runtime/node_modules/caniuse-lite/data/features/web-serial.js +1 -1
  668. package/runtime/node_modules/caniuse-lite/data/features/web-share.js +1 -1
  669. package/runtime/node_modules/caniuse-lite/data/features/webauthn.js +1 -1
  670. package/runtime/node_modules/caniuse-lite/data/features/webcodecs.js +1 -1
  671. package/runtime/node_modules/caniuse-lite/data/features/webgl.js +1 -1
  672. package/runtime/node_modules/caniuse-lite/data/features/webgl2.js +1 -1
  673. package/runtime/node_modules/caniuse-lite/data/features/webgpu.js +1 -1
  674. package/runtime/node_modules/caniuse-lite/data/features/webhid.js +1 -1
  675. package/runtime/node_modules/caniuse-lite/data/features/webkit-user-drag.js +1 -1
  676. package/runtime/node_modules/caniuse-lite/data/features/webm.js +1 -1
  677. package/runtime/node_modules/caniuse-lite/data/features/webnfc.js +1 -1
  678. package/runtime/node_modules/caniuse-lite/data/features/webp.js +1 -1
  679. package/runtime/node_modules/caniuse-lite/data/features/websockets.js +1 -1
  680. package/runtime/node_modules/caniuse-lite/data/features/webtransport.js +1 -1
  681. package/runtime/node_modules/caniuse-lite/data/features/webusb.js +1 -1
  682. package/runtime/node_modules/caniuse-lite/data/features/webvr.js +1 -1
  683. package/runtime/node_modules/caniuse-lite/data/features/webvtt.js +1 -1
  684. package/runtime/node_modules/caniuse-lite/data/features/webworkers.js +1 -1
  685. package/runtime/node_modules/caniuse-lite/data/features/webxr.js +1 -1
  686. package/runtime/node_modules/caniuse-lite/data/features/will-change.js +1 -1
  687. package/runtime/node_modules/caniuse-lite/data/features/woff.js +1 -1
  688. package/runtime/node_modules/caniuse-lite/data/features/woff2.js +1 -1
  689. package/runtime/node_modules/caniuse-lite/data/features/word-break.js +1 -1
  690. package/runtime/node_modules/caniuse-lite/data/features/wordwrap.js +1 -1
  691. package/runtime/node_modules/caniuse-lite/data/features/x-doc-messaging.js +1 -1
  692. package/runtime/node_modules/caniuse-lite/data/features/x-frame-options.js +1 -1
  693. package/runtime/node_modules/caniuse-lite/data/features/xhr2.js +1 -1
  694. package/runtime/node_modules/caniuse-lite/data/features/xhtml.js +1 -1
  695. package/runtime/node_modules/caniuse-lite/data/features/xhtmlsmil.js +1 -1
  696. package/runtime/node_modules/caniuse-lite/data/features/xml-serializer.js +1 -1
  697. package/runtime/node_modules/caniuse-lite/data/features/zstd.js +1 -1
  698. package/runtime/node_modules/caniuse-lite/data/versionGroups.js +1 -1
  699. package/runtime/node_modules/caniuse-lite/package.json +1 -1
  700. package/runtime/node_modules/mediabunny/README.md +8 -0
  701. package/runtime/node_modules/mediabunny/dist/bundles/mediabunny.cjs +1438 -659
  702. package/runtime/node_modules/mediabunny/dist/bundles/mediabunny.min.cjs +20 -20
  703. package/runtime/node_modules/mediabunny/dist/bundles/mediabunny.min.mjs +20 -20
  704. package/runtime/node_modules/mediabunny/dist/bundles/mediabunny.mjs +1438 -659
  705. package/runtime/node_modules/mediabunny/dist/bundles/mediabunny.node.cjs +1438 -659
  706. package/runtime/node_modules/mediabunny/dist/modules/shared/aac-misc.js +9 -1
  707. package/runtime/node_modules/mediabunny/dist/modules/shared/mp3-misc.js +2 -0
  708. package/runtime/node_modules/mediabunny/dist/modules/shared/truehd-misc.js +10 -0
  709. package/runtime/node_modules/mediabunny/dist/modules/src/adts/adts-demuxer.js +1 -2
  710. package/runtime/node_modules/mediabunny/dist/modules/src/codec-data.js +11 -0
  711. package/runtime/node_modules/mediabunny/dist/modules/src/codec.js +111 -4
  712. package/runtime/node_modules/mediabunny/dist/modules/src/conversion.js +10 -13
  713. package/runtime/node_modules/mediabunny/dist/modules/src/encode.js +4 -2
  714. package/runtime/node_modules/mediabunny/dist/modules/src/flac/flac-demuxer.js +1 -1
  715. package/runtime/node_modules/mediabunny/dist/modules/src/hls/hls-demuxer.js +48 -1
  716. package/runtime/node_modules/mediabunny/dist/modules/src/hls/hls-misc.js +4 -0
  717. package/runtime/node_modules/mediabunny/dist/modules/src/hls/hls-muxer.js +32 -4
  718. package/runtime/node_modules/mediabunny/dist/modules/src/hls/hls-segmented-input.js +102 -17
  719. package/runtime/node_modules/mediabunny/dist/modules/src/id3.js +26 -8
  720. package/runtime/node_modules/mediabunny/dist/modules/src/input-track.js +25 -5
  721. package/runtime/node_modules/mediabunny/dist/modules/src/isobmff/isobmff-boxes.js +76 -7
  722. package/runtime/node_modules/mediabunny/dist/modules/src/isobmff/isobmff-demuxer.js +31 -0
  723. package/runtime/node_modules/mediabunny/dist/modules/src/isobmff/isobmff-muxer.js +79 -59
  724. package/runtime/node_modules/mediabunny/dist/modules/src/matroska/ebml.js +2 -0
  725. package/runtime/node_modules/mediabunny/dist/modules/src/matroska/matroska-demuxer.js +28 -9
  726. package/runtime/node_modules/mediabunny/dist/modules/src/matroska/matroska-muxer.js +114 -105
  727. package/runtime/node_modules/mediabunny/dist/modules/src/media-sink.js +138 -48
  728. package/runtime/node_modules/mediabunny/dist/modules/src/media-source.js +165 -31
  729. package/runtime/node_modules/mediabunny/dist/modules/src/metadata.js +3 -2
  730. package/runtime/node_modules/mediabunny/dist/modules/src/misc.js +9 -2
  731. package/runtime/node_modules/mediabunny/dist/modules/src/mp3/mp3-demuxer.js +28 -13
  732. package/runtime/node_modules/mediabunny/dist/modules/src/mp3/mp3-muxer.js +53 -28
  733. package/runtime/node_modules/mediabunny/dist/modules/src/mp3/mp3-writer.js +30 -8
  734. package/runtime/node_modules/mediabunny/dist/modules/src/mpeg-ts/mpeg-ts-demuxer.js +21 -28
  735. package/runtime/node_modules/mediabunny/dist/modules/src/mpeg-ts/mpeg-ts-misc.js +24 -1
  736. package/runtime/node_modules/mediabunny/dist/modules/src/mpeg-ts/mpeg-ts-muxer.js +5 -8
  737. package/runtime/node_modules/mediabunny/dist/modules/src/ogg/ogg-demuxer.js +15 -10
  738. package/runtime/node_modules/mediabunny/dist/modules/src/ogg/ogg-misc.js +4 -5
  739. package/runtime/node_modules/mediabunny/dist/modules/src/ogg/ogg-muxer.js +14 -11
  740. package/runtime/node_modules/mediabunny/dist/modules/src/output-format.js +11 -1
  741. package/runtime/node_modules/mediabunny/dist/modules/src/resample.js +6 -7
  742. package/runtime/node_modules/mediabunny/dist/modules/src/segmented-input.js +56 -17
  743. package/runtime/node_modules/mediabunny/dist/modules/src/source.js +16 -0
  744. package/runtime/node_modules/mediabunny/dist/modules/src/target.js +16 -1
  745. package/runtime/node_modules/mediabunny/dist/modules/src/tsconfig.tsbuildinfo +1 -1
  746. package/runtime/node_modules/mediabunny/dist/modules/src/version.js +1 -1
  747. package/runtime/node_modules/mediabunny/package.json +3 -3
  748. package/runtime/node_modules/mediabunny/src/adts/adts-demuxer.ts +1 -2
  749. package/runtime/node_modules/mediabunny/src/codec-data.ts +13 -2
  750. package/runtime/node_modules/mediabunny/src/codec.ts +128 -3
  751. package/runtime/node_modules/mediabunny/src/conversion.ts +16 -17
  752. package/runtime/node_modules/mediabunny/src/encode.ts +6 -2
  753. package/runtime/node_modules/mediabunny/src/flac/flac-demuxer.ts +1 -1
  754. package/runtime/node_modules/mediabunny/src/hls/hls-demuxer.ts +62 -1
  755. package/runtime/node_modules/mediabunny/src/hls/hls-misc.ts +5 -0
  756. package/runtime/node_modules/mediabunny/src/hls/hls-muxer.ts +39 -3
  757. package/runtime/node_modules/mediabunny/src/hls/hls-segmented-input.ts +139 -17
  758. package/runtime/node_modules/mediabunny/src/id3.ts +25 -8
  759. package/runtime/node_modules/mediabunny/src/input-track.ts +35 -5
  760. package/runtime/node_modules/mediabunny/src/input.ts +4 -1
  761. package/runtime/node_modules/mediabunny/src/isobmff/isobmff-boxes.ts +89 -5
  762. package/runtime/node_modules/mediabunny/src/isobmff/isobmff-demuxer.ts +35 -0
  763. package/runtime/node_modules/mediabunny/src/isobmff/isobmff-muxer.ts +100 -54
  764. package/runtime/node_modules/mediabunny/src/matroska/ebml.ts +2 -0
  765. package/runtime/node_modules/mediabunny/src/matroska/matroska-demuxer.ts +31 -8
  766. package/runtime/node_modules/mediabunny/src/matroska/matroska-muxer.ts +148 -118
  767. package/runtime/node_modules/mediabunny/src/media-sink.ts +165 -47
  768. package/runtime/node_modules/mediabunny/src/media-source.ts +211 -37
  769. package/runtime/node_modules/mediabunny/src/metadata.ts +9 -4
  770. package/runtime/node_modules/mediabunny/src/misc.ts +11 -2
  771. package/runtime/node_modules/mediabunny/src/mp3/mp3-demuxer.ts +33 -12
  772. package/runtime/node_modules/mediabunny/src/mp3/mp3-muxer.ts +63 -30
  773. package/runtime/node_modules/mediabunny/src/mp3/mp3-writer.ts +36 -11
  774. package/runtime/node_modules/mediabunny/src/mpeg-ts/mpeg-ts-demuxer.ts +28 -38
  775. package/runtime/node_modules/mediabunny/src/mpeg-ts/mpeg-ts-misc.ts +36 -1
  776. package/runtime/node_modules/mediabunny/src/mpeg-ts/mpeg-ts-muxer.ts +6 -9
  777. package/runtime/node_modules/mediabunny/src/ogg/ogg-demuxer.ts +17 -13
  778. package/runtime/node_modules/mediabunny/src/ogg/ogg-misc.ts +4 -5
  779. package/runtime/node_modules/mediabunny/src/ogg/ogg-muxer.ts +20 -17
  780. package/runtime/node_modules/mediabunny/src/output-format.ts +32 -0
  781. package/runtime/node_modules/mediabunny/src/resample.ts +8 -7
  782. package/runtime/node_modules/mediabunny/src/segmented-input.ts +67 -18
  783. package/runtime/node_modules/mediabunny/src/source.ts +21 -0
  784. package/runtime/node_modules/mediabunny/src/target.ts +21 -6
  785. package/runtime/node_modules/mediabunny/src/version.ts +1 -1
  786. package/runtime/package-lock.json +161 -161
  787. package/runtime/server.js +1 -1
  788. package/runtime/webapp/dist/assets/{AiHubPane-DIk3VHVD.js → AiHubPane-BQ8CJAQL.js} +1 -1
  789. package/runtime/webapp/dist/assets/App-GXFFBAhW.js +174 -0
  790. package/runtime/webapp/dist/assets/{BrowserLivePanel-C2eapgzC.js → BrowserLivePanel-DxhSUu4j.js} +1 -1
  791. package/runtime/webapp/dist/assets/{CollaborationDashboard-CmbzUAIn.js → CollaborationDashboard-c_iNusPf.js} +1 -1
  792. package/runtime/webapp/dist/assets/{CollaborationPage-DdGiWsrN.js → CollaborationPage-DRBPK_iH.js} +1 -1
  793. package/runtime/webapp/dist/assets/{FilePreview-C35N6c_1.js → FilePreview-DScFSi_K.js} +3 -3
  794. package/runtime/webapp/dist/assets/{FileTree-DHyts8Fp.js → FileTree-BB5xTMg6.js} +1 -1
  795. package/runtime/webapp/dist/assets/{FlowStudioPane-v-fObPNM.js → FlowStudioPane-BBf0zyw1.js} +1 -1
  796. package/runtime/webapp/dist/assets/{RemoteDesktopPage-D7mgoU7b.js → RemoteDesktopPage-CWW4T1QF.js} +1 -1
  797. package/runtime/webapp/dist/assets/SessionDashboard-BdGlakPd.js +26 -0
  798. package/runtime/webapp/dist/assets/SessionDashboard-CUCEDkCI.css +1 -0
  799. package/runtime/webapp/dist/assets/SessionDashboardBridge-8zrk0Bub.js +1 -0
  800. package/runtime/webapp/dist/assets/{TerminalPane-BPk3av7L.js → TerminalPane-DkEyD1ge.js} +1 -1
  801. package/runtime/webapp/dist/assets/{abnfDiagram-VCTEODGH-pOFLDnXP.js → abnfDiagram-VCTEODGH-Dlsyu96y.js} +1 -1
  802. package/runtime/webapp/dist/assets/{arc-Dtxck3vK.js → arc-D0AvBRtK.js} +1 -1
  803. package/runtime/webapp/dist/assets/{architectureDiagram-5GKGNRK7-BvgB-eqr.js → architectureDiagram-5GKGNRK7-BLAHjBcI.js} +1 -1
  804. package/runtime/webapp/dist/assets/{arrow-right-C4BiGWqO.js → arrow-right-B15rGLIR.js} +1 -1
  805. package/runtime/webapp/dist/assets/{artifact-links-oA81jfGt.js → artifact-links-BkoUldDR.js} +1 -1
  806. package/runtime/webapp/dist/assets/{blockDiagram-I7D4REHJ-BsbUYhsJ.js → blockDiagram-I7D4REHJ-CqIb0xz-.js} +1 -1
  807. package/runtime/webapp/dist/assets/{c4Diagram-7LVT6UL2-CWyR12wW.js → c4Diagram-7LVT6UL2-CG98ZTHr.js} +1 -1
  808. package/runtime/webapp/dist/assets/channel-Bw3F6pJc.js +1 -0
  809. package/runtime/webapp/dist/assets/{chunk-2Q5K7J3B-C7QXnn8h.js → chunk-2Q5K7J3B-DQh8kgcp.js} +1 -1
  810. package/runtime/webapp/dist/assets/{chunk-5VM5RSS4-CWJADtCm.js → chunk-5VM5RSS4-BesfCxeX.js} +1 -1
  811. package/runtime/webapp/dist/assets/{chunk-F27PBJKO-Cweh6MCq.js → chunk-F27PBJKO-BCXEjgx-.js} +1 -1
  812. package/runtime/webapp/dist/assets/{chunk-IMKFNOWR-DF-E9vxt.js → chunk-IMKFNOWR-ydMd7mT-.js} +1 -1
  813. package/runtime/webapp/dist/assets/{chunk-JWPE2WC7-Bt0XKJGJ.js → chunk-JWPE2WC7-K3_myO-F.js} +1 -1
  814. package/runtime/webapp/dist/assets/{chunk-POPQ4Y6H-Wv9f4r1o.js → chunk-POPQ4Y6H-BtqLafwd.js} +1 -1
  815. package/runtime/webapp/dist/assets/{chunk-SVP7TREG-CyaFVrLD.js → chunk-SVP7TREG-mKZUbHcv.js} +1 -1
  816. package/runtime/webapp/dist/assets/{chunk-TICWLB2K-DOIbwoJY.js → chunk-TICWLB2K-hDH9_eNh.js} +1 -1
  817. package/runtime/webapp/dist/assets/{chunk-XXDRQBXY-CAwhKZv-.js → chunk-XXDRQBXY-B6wXA24N.js} +1 -1
  818. package/runtime/webapp/dist/assets/classDiagram-ZZMXUADV-By2XJYuW.js +1 -0
  819. package/runtime/webapp/dist/assets/classDiagram-v2-VYDZK3BY-By2XJYuW.js +1 -0
  820. package/runtime/webapp/dist/assets/{clipboard-Ct7ZTYsT.js → clipboard-CrmYgzo8.js} +1 -1
  821. package/runtime/webapp/dist/assets/{codeSyntax-KLkJvvR9.js → codeSyntax-KyRYSqw_.js} +1 -1
  822. package/runtime/webapp/dist/assets/{collaboration-CiUq-T01.js → collaboration-B7rPFZje.js} +1 -1
  823. package/runtime/webapp/dist/assets/{cose-bilkent-JH36ORCC-gN410IPt.js → cose-bilkent-JH36ORCC-MoeyZZ6x.js} +1 -1
  824. package/runtime/webapp/dist/assets/{crown-o7sh7UXl.js → crown-BKylWZLt.js} +1 -1
  825. package/runtime/webapp/dist/assets/{cynefin-OW5HDTMX-5wFL_0bx.js → cynefin-OW5HDTMX-BWYtTqVq.js} +1 -1
  826. package/runtime/webapp/dist/assets/{cynefinDiagram-5FMLGOSQ-CS8w0Cb8.js → cynefinDiagram-5FMLGOSQ-CoqnJ7eo.js} +1 -1
  827. package/runtime/webapp/dist/assets/{dagre-GXQ25YYZ-Bbk8onQY.js → dagre-GXQ25YYZ-DMwZ_7F7.js} +1 -1
  828. package/runtime/webapp/dist/assets/{diagram-S7CK7UJ4-BHFR1JYZ.js → diagram-S7CK7UJ4-DJ2BAyzP.js} +1 -1
  829. package/runtime/webapp/dist/assets/{diagram-UQ7AKVKN-DYuD9-hs.js → diagram-UQ7AKVKN-ChujnpjG.js} +1 -1
  830. package/runtime/webapp/dist/assets/{diagram-VSXAHHWV-B8ZYNIIS.js → diagram-VSXAHHWV-CDSAKYID.js} +1 -1
  831. package/runtime/webapp/dist/assets/{diagram-VX7I27RA-CNIniP-o.js → diagram-VX7I27RA-DXvCy8w-.js} +1 -1
  832. package/runtime/webapp/dist/assets/{diagram-Z3DM3KII-BRIldGhQ.js → diagram-Z3DM3KII-BWrKegI9.js} +1 -1
  833. package/runtime/webapp/dist/assets/{ebnfDiagram-PWID7BFC-BeZcHuYS.js → ebnfDiagram-PWID7BFC-CqDhPmpp.js} +1 -1
  834. package/runtime/webapp/dist/assets/{erDiagram-RLTQ6QDP-DHwEwxeO.js → erDiagram-RLTQ6QDP-D5HR9ddP.js} +1 -1
  835. package/runtime/webapp/dist/assets/{file-types-CALnsqxP.js → file-types-D_egQYAD.js} +1 -1
  836. package/runtime/webapp/dist/assets/{flowDiagram-HODETNUW-DIN9fq8w.js → flowDiagram-HODETNUW-Bz89eEJ2.js} +1 -1
  837. package/runtime/webapp/dist/assets/{ganttDiagram-EL5Y4UJY-DEnztfWv.js → ganttDiagram-EL5Y4UJY-Bw1lo_RG.js} +1 -1
  838. package/runtime/webapp/dist/assets/{gitGraphDiagram-WWUBYQGX-U_QimY5P.js → gitGraphDiagram-WWUBYQGX-CMxwIm3p.js} +1 -1
  839. package/runtime/webapp/dist/assets/index-6B8SDnzK.css +1 -0
  840. package/runtime/webapp/dist/assets/{index-DzIkFOL8.js → index-CkVSxxim.js} +53 -68
  841. package/runtime/webapp/dist/assets/{infoDiagram-27XIBGKW-Db9evdVP.js → infoDiagram-27XIBGKW-DEWyQUst.js} +1 -1
  842. package/runtime/webapp/dist/assets/{ishikawaDiagram-5VMMS53U-BOaYc_-H.js → ishikawaDiagram-5VMMS53U-BfJdGhe_.js} +1 -1
  843. package/runtime/webapp/dist/assets/{journeyDiagram-3NMN7TZE--bpKX21G.js → journeyDiagram-3NMN7TZE-C6gh2ejc.js} +1 -1
  844. package/runtime/webapp/dist/assets/{kanban-definition-UXKFOSKX-CA_e9zyr.js → kanban-definition-UXKFOSKX-1UHi9Lfv.js} +1 -1
  845. package/runtime/webapp/dist/assets/{layout-BWROikQL.js → layout-CKq-cSTm.js} +1 -1
  846. package/runtime/webapp/dist/assets/{linear-Cs-tTwlC.js → linear-DF4sJk10.js} +1 -1
  847. package/runtime/webapp/dist/assets/{loader-circle-CCZ5vEFX.js → loader-circle-Dpjix4wZ.js} +1 -1
  848. package/runtime/webapp/dist/assets/{mermaid.core-DC45Ncse.js → mermaid.core-OAHUFl3p.js} +5 -5
  849. package/runtime/webapp/dist/assets/{mindmap-definition-YA3MSWOX-CcBYbQBC.js → mindmap-definition-YA3MSWOX-JiyyEKeC.js} +1 -1
  850. package/runtime/webapp/dist/assets/{page-3RMj5dQT.js → page-DqgtSgo3.js} +3 -3
  851. package/runtime/webapp/dist/assets/{pegDiagram-XKGWAZYB-nG1uS_No.js → pegDiagram-XKGWAZYB-CpBwPi33.js} +1 -1
  852. package/runtime/webapp/dist/assets/{pieDiagram-E7YTZNPT-BrT1k-K2.js → pieDiagram-E7YTZNPT-BjM_PcYH.js} +1 -1
  853. package/runtime/webapp/dist/assets/qoder-CGHn7M84.png +0 -0
  854. package/runtime/webapp/dist/assets/{quadrantDiagram-AXDQQJYC-C13tJOvq.js → quadrantDiagram-AXDQQJYC-Vdz77obz.js} +1 -1
  855. package/runtime/webapp/dist/assets/{railroadDiagram-O6MQD6OU-DnJ5PQG8.js → railroadDiagram-O6MQD6OU-DsQjNf1f.js} +1 -1
  856. package/runtime/webapp/dist/assets/{requirementDiagram-BXWQKSXE-BQqwdK06.js → requirementDiagram-BXWQKSXE-TpfT8TjT.js} +1 -1
  857. package/runtime/webapp/dist/assets/{rotate-ccw-DC73nBn1.js → rotate-ccw-wJiVuYlm.js} +1 -1
  858. package/runtime/webapp/dist/assets/{rotate-cw-DqS4ePZN.js → rotate-cw-CtpBETpM.js} +1 -1
  859. package/runtime/webapp/dist/assets/{sankeyDiagram-P5KCCOFB-BsDbHSXS.js → sankeyDiagram-P5KCCOFB-Ckh_skQw.js} +1 -1
  860. package/runtime/webapp/dist/assets/{send-DAfqf9Ri.js → send-DL0qj0xE.js} +1 -1
  861. package/runtime/webapp/dist/assets/{sequenceDiagram-WJ2MYXX4-BBDPxIMt.js → sequenceDiagram-WJ2MYXX4-CkKC0JEA.js} +1 -1
  862. package/runtime/webapp/dist/assets/{shield-check-BfU-zJrL.js → shield-check-B5q8YhWs.js} +1 -1
  863. package/runtime/webapp/dist/assets/{sizeCapture-INFHLROL-C6YHKU_U.js → sizeCapture-INFHLROL-DB_NzdXU.js} +1 -1
  864. package/runtime/webapp/dist/assets/{smartphone-DiwRttf1.js → smartphone-DJEfFl42.js} +1 -1
  865. package/runtime/webapp/dist/assets/{stateDiagram-D77RDMKH-hLZSwbqs.js → stateDiagram-D77RDMKH-Ch2r76jY.js} +1 -1
  866. package/runtime/webapp/dist/assets/stateDiagram-v2-MP3YSRHH-BCjtOHJv.js +1 -0
  867. package/runtime/webapp/dist/assets/{swimlanes-42K2YHIH-DE3K-s08.js → swimlanes-42K2YHIH-BBMlDhHH.js} +1 -1
  868. package/runtime/webapp/dist/assets/swimlanesDiagram-VR7AAH4N-CYzCynNs.js +8 -0
  869. package/runtime/webapp/dist/assets/{timeline-definition-24CTP7MA-CCGtRdJn.js → timeline-definition-24CTP7MA-BELJuISI.js} +1 -1
  870. package/runtime/webapp/dist/assets/{trash-2-DypDAsgq.js → trash-2-D4LqA3q5.js} +1 -1
  871. package/runtime/webapp/dist/assets/{vennDiagram-4TSXK5OY-h20IaWBe.js → vennDiagram-4TSXK5OY-NSlXdmyy.js} +1 -1
  872. package/runtime/webapp/dist/assets/{wardleyDiagram-VM6X3IG4-CbMZyM2K.js → wardleyDiagram-VM6X3IG4-BVbNDhZr.js} +1 -1
  873. package/runtime/webapp/dist/assets/{web--NKliblj.js → web-BpA_VIiS.js} +1 -1
  874. package/runtime/webapp/dist/assets/{web-COkIp2EM.js → web-CoxxvfFh.js} +1 -1
  875. package/runtime/webapp/dist/assets/workbuddy-hEyEE8dU.png +0 -0
  876. package/runtime/webapp/dist/assets/{xychartDiagram-S5SC5T6Z-pPLfOQTQ.js → xychartDiagram-S5SC5T6Z-Bt3XghTc.js} +1 -1
  877. package/runtime/webapp/dist/assets/zcode-CsXrmDtX.png +0 -0
  878. package/runtime/webapp/dist/index.html +2 -2
  879. package/runtime/.next/static/chunks/app/web/layout-249cdd2909744bce.js +0 -1
  880. package/runtime/.next/static/chunks/app/web/page-2ce49f8aebe2474a.js +0 -1
  881. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-azmey26z.mjs +0 -52
  882. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-jhgm58v5.mjs +0 -40
  883. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-qw4t51gr.mjs +0 -27
  884. package/runtime/node_modules/@anthropic-ai/claude-agent-sdk/core-x7q9bdvq.mjs +0 -26
  885. package/runtime/webapp/dist/assets/App-Bh7-ZKY-.js +0 -174
  886. package/runtime/webapp/dist/assets/SessionDashboard-DAzTBMO2.css +0 -1
  887. package/runtime/webapp/dist/assets/SessionDashboard-DFOqRo3U.js +0 -16
  888. package/runtime/webapp/dist/assets/SessionDashboardBridge-K2ripwXe.js +0 -1
  889. package/runtime/webapp/dist/assets/channel-DRUF4BK-.js +0 -1
  890. package/runtime/webapp/dist/assets/classDiagram-ZZMXUADV-jMAd-PMJ.js +0 -1
  891. package/runtime/webapp/dist/assets/classDiagram-v2-VYDZK3BY-jMAd-PMJ.js +0 -1
  892. package/runtime/webapp/dist/assets/index-8zCfKdi_.css +0 -1
  893. package/runtime/webapp/dist/assets/stateDiagram-v2-MP3YSRHH-BJ_AsUFj.js +0 -1
  894. package/runtime/webapp/dist/assets/swimlanesDiagram-VR7AAH4N-5nRFPxoo.js +0 -8
  895. /package/runtime/.next/static/{yFTf4OsMQId8Kv7Is6hgk → irWde_R_H09SV2jvfhWC2}/_buildManifest.js +0 -0
  896. /package/runtime/.next/static/{yFTf4OsMQId8Kv7Is6hgk → irWde_R_H09SV2jvfhWC2}/_ssgManifest.js +0 -0
@@ -977,6 +977,13 @@ var Mediabunny = (() => {
977
977
  }
978
978
  return chromiumVersionCache = Number(match[1]);
979
979
  };
980
+ var isAndroidCache = null;
981
+ var isAndroid = () => {
982
+ if (isAndroidCache !== null) {
983
+ return isAndroidCache;
984
+ }
985
+ return isAndroidCache = typeof navigator !== "undefined" && /Android/.test(navigator.userAgent);
986
+ };
980
987
  var missingWebCodecsClassMessage = (className) => {
981
988
  if (typeof globalThis.isSecureContext !== "undefined" && !globalThis.isSecureContext) {
982
989
  return `${className} is not available in this environment; this may be because this page is running in an insecure context. Try serving your page over HTTPS or use localhost.`;
@@ -1157,7 +1164,7 @@ var Mediabunny = (() => {
1157
1164
  let minValue = Infinity;
1158
1165
  for (let i = 0; i < array.length; i++) {
1159
1166
  const value = getValue(array[i]);
1160
- if (value < minValue) {
1167
+ if (minIndex === -1 || value < minValue) {
1161
1168
  minValue = value;
1162
1169
  minIndex = i;
1163
1170
  }
@@ -1169,7 +1176,7 @@ var Mediabunny = (() => {
1169
1176
  let maxValue = -Infinity;
1170
1177
  for (let i = 0; i < array.length; i++) {
1171
1178
  const value = getValue(array[i]);
1172
- if (value > maxValue) {
1179
+ if (maxIndex === -1 || value > maxValue) {
1173
1180
  maxValue = value;
1174
1181
  maxIndex = i;
1175
1182
  }
@@ -1566,9 +1573,9 @@ var Mediabunny = (() => {
1566
1573
  throw new TypeError("tags.raw, when provided, must be an object.");
1567
1574
  }
1568
1575
  for (const value of Object.values(tags.raw)) {
1569
- if (value !== null && typeof value !== "string" && !(Array.isArray(value) && value.every((x) => typeof x === "string")) && !(value instanceof Uint8Array) && !(value instanceof RichImageData) && !(value instanceof AttachedFile) && !isRecordStringString(value)) {
1576
+ if (value !== null && typeof value !== "string" && !(Array.isArray(value) && value.every((x) => typeof x === "string")) && !(value instanceof Uint8Array) && !(Array.isArray(value) && value.every((x) => x instanceof Uint8Array)) && !(value instanceof RichImageData) && !(value instanceof AttachedFile) && !isRecordStringString(value)) {
1570
1577
  throw new TypeError(
1571
- "Each value in tags.raw must be a string, string array, Uint8Array, RichImageData, AttachedFile, Record<string, string>, or null."
1578
+ "Each value in tags.raw must be a string, string array, Uint8Array, Uint8Array array, RichImageData, AttachedFile, Record<string, string>, or null."
1572
1579
  );
1573
1580
  }
1574
1581
  }
@@ -1703,6 +1710,7 @@ var Mediabunny = (() => {
1703
1710
  7350
1704
1711
  ];
1705
1712
  var aacChannelMap = [-1, 1, 2, 3, 4, 5, 6, 8];
1713
+ var generalAudioObjectTypes = [1, 2, 3, 4, 6, 7, 17, 19, 20, 21, 22];
1706
1714
  var parseAacAudioSpecificConfig = (bytes2) => {
1707
1715
  if (!bytes2 || bytes2.byteLength < 2) {
1708
1716
  throw new TypeError("AAC description must be at least 2 bytes long.");
@@ -1725,7 +1733,12 @@ var Mediabunny = (() => {
1725
1733
  if (coreObjectType === 22) {
1726
1734
  bitstream.skipBits(4);
1727
1735
  }
1728
- } else {
1736
+ }
1737
+ let frameLength = 1024;
1738
+ if (generalAudioObjectTypes.includes(coreObjectType)) {
1739
+ frameLength = bitstream.readBits(1) ? 960 : 1024;
1740
+ }
1741
+ if (objectType !== 5 && objectType !== 29) {
1729
1742
  while (bitstream.getBitsLeft() > 15) {
1730
1743
  const searchStart = bitstream.pos;
1731
1744
  if (bitstream.readBits(11) !== 695) {
@@ -1749,8 +1762,10 @@ var Mediabunny = (() => {
1749
1762
  coreObjectType,
1750
1763
  frequencyIndex,
1751
1764
  channelConfiguration,
1765
+ coreSampleRate: sampleRate,
1752
1766
  outputSampleRate,
1753
- outputNumberOfChannels: psPresent && numberOfChannels === 1 ? 2 : numberOfChannels
1767
+ outputNumberOfChannels: psPresent && numberOfChannels === 1 ? 2 : numberOfChannels,
1768
+ frameLength
1754
1769
  };
1755
1770
  };
1756
1771
  var readAacObjectType = (bitstream) => {
@@ -1851,12 +1866,289 @@ var Mediabunny = (() => {
1851
1866
  bitstream.writeBits(13, frameLength);
1852
1867
  };
1853
1868
 
1869
+ // shared/mp3-misc.ts
1870
+ var MP3_FRAME_HEADER_SIZE = 4;
1871
+ var MP3_DECODER_DELAY = 529;
1872
+ var SAMPLING_RATES = [44100, 48e3, 32e3];
1873
+ var KILOBIT_RATES = [
1874
+ // lowSamplingFrequency === 0
1875
+ -1,
1876
+ -1,
1877
+ -1,
1878
+ -1,
1879
+ -1,
1880
+ -1,
1881
+ -1,
1882
+ -1,
1883
+ -1,
1884
+ -1,
1885
+ -1,
1886
+ -1,
1887
+ -1,
1888
+ -1,
1889
+ -1,
1890
+ -1,
1891
+ // layer = 0
1892
+ -1,
1893
+ 32,
1894
+ 40,
1895
+ 48,
1896
+ 56,
1897
+ 64,
1898
+ 80,
1899
+ 96,
1900
+ 112,
1901
+ 128,
1902
+ 160,
1903
+ 192,
1904
+ 224,
1905
+ 256,
1906
+ 320,
1907
+ -1,
1908
+ // layer 1
1909
+ -1,
1910
+ 32,
1911
+ 48,
1912
+ 56,
1913
+ 64,
1914
+ 80,
1915
+ 96,
1916
+ 112,
1917
+ 128,
1918
+ 160,
1919
+ 192,
1920
+ 224,
1921
+ 256,
1922
+ 320,
1923
+ 384,
1924
+ -1,
1925
+ // layer = 2
1926
+ -1,
1927
+ 32,
1928
+ 64,
1929
+ 96,
1930
+ 128,
1931
+ 160,
1932
+ 192,
1933
+ 224,
1934
+ 256,
1935
+ 288,
1936
+ 320,
1937
+ 352,
1938
+ 384,
1939
+ 416,
1940
+ 448,
1941
+ -1,
1942
+ // layer = 3
1943
+ // lowSamplingFrequency === 1
1944
+ -1,
1945
+ -1,
1946
+ -1,
1947
+ -1,
1948
+ -1,
1949
+ -1,
1950
+ -1,
1951
+ -1,
1952
+ -1,
1953
+ -1,
1954
+ -1,
1955
+ -1,
1956
+ -1,
1957
+ -1,
1958
+ -1,
1959
+ -1,
1960
+ // layer = 0
1961
+ -1,
1962
+ 8,
1963
+ 16,
1964
+ 24,
1965
+ 32,
1966
+ 40,
1967
+ 48,
1968
+ 56,
1969
+ 64,
1970
+ 80,
1971
+ 96,
1972
+ 112,
1973
+ 128,
1974
+ 144,
1975
+ 160,
1976
+ -1,
1977
+ // layer = 1
1978
+ -1,
1979
+ 8,
1980
+ 16,
1981
+ 24,
1982
+ 32,
1983
+ 40,
1984
+ 48,
1985
+ 56,
1986
+ 64,
1987
+ 80,
1988
+ 96,
1989
+ 112,
1990
+ 128,
1991
+ 144,
1992
+ 160,
1993
+ -1,
1994
+ // layer = 2
1995
+ -1,
1996
+ 32,
1997
+ 48,
1998
+ 56,
1999
+ 64,
2000
+ 80,
2001
+ 96,
2002
+ 112,
2003
+ 128,
2004
+ 144,
2005
+ 160,
2006
+ 176,
2007
+ 192,
2008
+ 224,
2009
+ 256,
2010
+ -1
2011
+ // layer = 3
2012
+ ];
2013
+ var XING = 1483304551;
2014
+ var INFO = 1231971951;
2015
+ var computeMp3FrameSize = (lowSamplingFrequency, layer, bitrate, sampleRate, padding) => {
2016
+ if (layer === 0) {
2017
+ return 0;
2018
+ } else if (layer === 1) {
2019
+ return Math.floor(144 * bitrate / (sampleRate << lowSamplingFrequency)) + padding;
2020
+ } else if (layer === 2) {
2021
+ return Math.floor(144 * bitrate / sampleRate) + padding;
2022
+ } else {
2023
+ return (Math.floor(12 * bitrate / sampleRate) + padding) * 4;
2024
+ }
2025
+ };
2026
+ var computeAverageMp3FrameSize = (lowSamplingFrequency, layer, bitrate, sampleRate) => {
2027
+ if (layer === 0) {
2028
+ return 0;
2029
+ } else if (layer === 1) {
2030
+ return 144 * bitrate / (sampleRate << lowSamplingFrequency);
2031
+ } else if (layer === 2) {
2032
+ return 144 * bitrate / sampleRate;
2033
+ } else {
2034
+ return 12 * bitrate / sampleRate * 4;
2035
+ }
2036
+ };
2037
+ var getXingOffset = (mpegVersionId, channel) => {
2038
+ return mpegVersionId === 3 ? channel === 3 ? 21 : 36 : channel === 3 ? 13 : 21;
2039
+ };
2040
+ var readMp3FrameHeader = (word, remainingBytes) => {
2041
+ const firstByte = word >>> 24;
2042
+ const secondByte = word >>> 16 & 255;
2043
+ const thirdByte = word >>> 8 & 255;
2044
+ const fourthByte = word & 255;
2045
+ if (firstByte !== 255 && secondByte !== 255 && thirdByte !== 255 && fourthByte !== 255) {
2046
+ return {
2047
+ header: null,
2048
+ bytesAdvanced: 4
2049
+ };
2050
+ }
2051
+ if (firstByte !== 255) {
2052
+ return { header: null, bytesAdvanced: 1 };
2053
+ }
2054
+ if ((secondByte & 224) !== 224) {
2055
+ return { header: null, bytesAdvanced: 1 };
2056
+ }
2057
+ let lowSamplingFrequency = 0;
2058
+ let mpeg25 = 0;
2059
+ if (secondByte & 1 << 4) {
2060
+ lowSamplingFrequency = secondByte & 1 << 3 ? 0 : 1;
2061
+ } else {
2062
+ lowSamplingFrequency = 1;
2063
+ mpeg25 = 1;
2064
+ }
2065
+ const mpegVersionId = secondByte >> 3 & 3;
2066
+ const layer = secondByte >> 1 & 3;
2067
+ const bitrateIndex = thirdByte >> 4 & 15;
2068
+ const frequencyIndex = (thirdByte >> 2 & 3) % 3;
2069
+ const padding = thirdByte >> 1 & 1;
2070
+ const channel = fourthByte >> 6 & 3;
2071
+ const modeExtension = fourthByte >> 4 & 3;
2072
+ const copyright = fourthByte >> 3 & 1;
2073
+ const original = fourthByte >> 2 & 1;
2074
+ const emphasis = fourthByte & 3;
2075
+ const kilobitRate = KILOBIT_RATES[lowSamplingFrequency * 16 * 4 + layer * 16 + bitrateIndex];
2076
+ if (kilobitRate === -1) {
2077
+ return { header: null, bytesAdvanced: 1 };
2078
+ }
2079
+ const bitrate = kilobitRate * 1e3;
2080
+ const sampleRate = SAMPLING_RATES[frequencyIndex] >> lowSamplingFrequency + mpeg25;
2081
+ const frameLength = computeMp3FrameSize(lowSamplingFrequency, layer, bitrate, sampleRate, padding);
2082
+ if (remainingBytes !== null && remainingBytes < frameLength) {
2083
+ return { header: null, bytesAdvanced: 1 };
2084
+ }
2085
+ let audioSamplesInFrame;
2086
+ if (mpegVersionId === 3) {
2087
+ audioSamplesInFrame = layer === 3 ? 384 : 1152;
2088
+ } else {
2089
+ if (layer === 3) {
2090
+ audioSamplesInFrame = 384;
2091
+ } else if (layer === 2) {
2092
+ audioSamplesInFrame = 1152;
2093
+ } else {
2094
+ audioSamplesInFrame = 576;
2095
+ }
2096
+ }
2097
+ return {
2098
+ header: {
2099
+ totalSize: frameLength,
2100
+ mpegVersionId,
2101
+ lowSamplingFrequency,
2102
+ layer,
2103
+ bitrate,
2104
+ frequencyIndex,
2105
+ sampleRate,
2106
+ channel,
2107
+ modeExtension,
2108
+ copyright,
2109
+ original,
2110
+ emphasis,
2111
+ audioSamplesInFrame
2112
+ },
2113
+ bytesAdvanced: 1
2114
+ };
2115
+ };
2116
+ var encodeSynchsafe = (unsynchsafed) => {
2117
+ let mask = 127;
2118
+ let synchsafed = 0;
2119
+ let unsynchsafedRest = unsynchsafed;
2120
+ while ((mask ^ 2147483647) !== 0) {
2121
+ synchsafed = unsynchsafedRest & ~mask;
2122
+ synchsafed <<= 1;
2123
+ synchsafed |= unsynchsafedRest & mask;
2124
+ mask = (mask + 1 << 8) - 1;
2125
+ unsynchsafedRest = synchsafed;
2126
+ }
2127
+ return synchsafed;
2128
+ };
2129
+ var decodeSynchsafe = (synchsafed) => {
2130
+ let mask = 2130706432;
2131
+ let unsynchsafed = 0;
2132
+ while (mask !== 0) {
2133
+ unsynchsafed >>= 1;
2134
+ unsynchsafed |= synchsafed & mask;
2135
+ mask >>= 8;
2136
+ }
2137
+ return unsynchsafed;
2138
+ };
2139
+ var getMp3ChannelCount = (channel) => {
2140
+ return channel === 3 ? 1 : 2;
2141
+ };
2142
+
1854
2143
  // shared/ac3-misc.ts
1855
2144
  var AC3_SAMPLE_RATES = [48e3, 44100, 32e3];
1856
2145
  var EAC3_REDUCED_SAMPLE_RATES = [24e3, 22050, 16e3];
1857
2146
 
2147
+ // shared/truehd-misc.ts
2148
+ var TRUEHD_MAJOR_SYNC_WORD = 4168249274;
2149
+
1858
2150
  // src/version.ts
1859
- var VERSION = "1.62.1";
2151
+ var VERSION = "1.64.0";
1860
2152
  var VERSIONED_NAME = `Mediabunny v${VERSION}`;
1861
2153
 
1862
2154
  // src/codec-data.ts
@@ -3749,6 +4041,14 @@ var Mediabunny = (() => {
3749
4041
  ;
3750
4042
  }
3751
4043
  };
4044
+ var determineAudioPacketType = (codec, packetData) => {
4045
+ if (codec === "truehd") {
4046
+ const syncWord = packetData.byteLength >= 8 ? toDataView(packetData).getUint32(4) : null;
4047
+ return syncWord === TRUEHD_MAJOR_SYNC_WORD ? "key" : "delta";
4048
+ } else {
4049
+ return "key";
4050
+ }
4051
+ };
3752
4052
  var readVorbisComments = (bytes2, metadataTags) => {
3753
4053
  const commentView = toDataView(bytes2);
3754
4054
  let commentPos = 0;
@@ -4796,7 +5096,8 @@ var Mediabunny = (() => {
4796
5096
  "flac",
4797
5097
  "ac3",
4798
5098
  "eac3",
4799
- "dts"
5099
+ "dts",
5100
+ "truehd"
4800
5101
  ];
4801
5102
  var AUDIO_CODECS = [
4802
5103
  ...NON_PCM_AUDIO_CODECS,
@@ -4805,6 +5106,7 @@ var Mediabunny = (() => {
4805
5106
  var SUBTITLE_CODECS = [
4806
5107
  "webvtt"
4807
5108
  ];
5109
+ var AUDIO_CODECS_WITH_DELTA_PACKETS = ["truehd"];
4808
5110
  var AVC_LEVEL_TABLE = [
4809
5111
  { maxMacroblocks: 99, maxBitrate: 64e3, maxDpbMbs: 396, level: 10 },
4810
5112
  // Level 1
@@ -5011,14 +5313,15 @@ var Mediabunny = (() => {
5011
5313
  ];
5012
5314
  var buildVideoCodecString = (codec, width, height, bitrate, alpha) => {
5013
5315
  if (codec === "avc") {
5014
- const profileIndication = 100;
5316
+ const constrainedBaseline = isWebKit();
5317
+ const profileIndication = constrainedBaseline ? 66 : 100;
5015
5318
  const totalMacroblocks = Math.ceil(width / 16) * Math.ceil(height / 16);
5016
5319
  const levelInfo = AVC_LEVEL_TABLE.find(
5017
5320
  (level) => totalMacroblocks <= level.maxMacroblocks && bitrate <= level.maxBitrate
5018
5321
  ) ?? last(AVC_LEVEL_TABLE);
5019
5322
  const levelIndication = levelInfo ? levelInfo.level : 0;
5020
5323
  const hexProfileIndication = profileIndication.toString(16).padStart(2, "0");
5021
- const hexProfileCompatibility = "00";
5324
+ const hexProfileCompatibility = constrainedBaseline ? "40" : "00";
5022
5325
  const hexLevelIndication = levelIndication.toString(16).padStart(2, "0");
5023
5326
  return `avc1.${hexProfileIndication}${hexProfileCompatibility}${hexLevelIndication}`;
5024
5327
  } else if (codec === "hevc") {
@@ -5377,6 +5680,8 @@ var Mediabunny = (() => {
5377
5680
  return "ec-3";
5378
5681
  } else if (codec === "dts") {
5379
5682
  return "dtsc";
5683
+ } else if (codec === "truehd") {
5684
+ return "mlpa";
5380
5685
  } else if (PCM_AUDIO_CODECS.includes(codec)) {
5381
5686
  return codec;
5382
5687
  }
@@ -5414,6 +5719,8 @@ var Mediabunny = (() => {
5414
5719
  return "ec-3";
5415
5720
  } else if (codec === "dts") {
5416
5721
  return dtsFormat ?? "dtsc";
5722
+ } else if (codec === "truehd") {
5723
+ return "mlpa";
5417
5724
  } else if (codec && PCM_AUDIO_CODECS.includes(codec)) {
5418
5725
  return codec;
5419
5726
  }
@@ -5449,7 +5756,80 @@ var Mediabunny = (() => {
5449
5756
  return void 0;
5450
5757
  }
5451
5758
  };
5759
+ var getAudioPreRollDuration = (codec, decoderConfig) => {
5760
+ switch (codec) {
5761
+ case "aac": {
5762
+ if (!decoderConfig.description) {
5763
+ return 1024 / decoderConfig.sampleRate;
5764
+ }
5765
+ const audioSpecificConfig = parseAacAudioSpecificConfig(toUint8Array(decoderConfig.description));
5766
+ if (audioSpecificConfig.coreSampleRate === null) {
5767
+ throw new Error("Invalid AAC sampling frequency index.");
5768
+ }
5769
+ return audioSpecificConfig.frameLength / audioSpecificConfig.coreSampleRate;
5770
+ }
5771
+ case "opus": {
5772
+ return OPUS_PRE_ROLL_DURATION;
5773
+ }
5774
+ case "mp3": {
5775
+ const { sampleRate, numberOfChannels } = decoderConfig;
5776
+ const isMpeg1 = sampleRate >= 32e3;
5777
+ const frameSamples = isMpeg1 ? 1152 : 576;
5778
+ const minBitrate = isMpeg1 ? 32e3 : 8e3;
5779
+ const maxMainDataBegin = isMpeg1 ? 511 : 255;
5780
+ const sideInfoSize = isMpeg1 ? numberOfChannels === 1 ? 17 : 32 : numberOfChannels === 1 ? 9 : 17;
5781
+ const minFrameSize = Math.floor(frameSamples / 8 * minBitrate / sampleRate);
5782
+ const minMainDataSize = minFrameSize - MP3_FRAME_HEADER_SIZE - sideInfoSize;
5783
+ const frameCount = 1 + Math.ceil(maxMainDataBegin / minMainDataSize);
5784
+ return frameCount * frameSamples / sampleRate;
5785
+ }
5786
+ case "vorbis": {
5787
+ assert(decoderConfig.description);
5788
+ const bytes2 = toUint8Array(decoderConfig.description);
5789
+ let pos = 1;
5790
+ let lacedLengthsLeft = 2;
5791
+ while (lacedLengthsLeft > 0) {
5792
+ if (bytes2[pos++] < 255) {
5793
+ lacedLengthsLeft--;
5794
+ }
5795
+ }
5796
+ const blockSizeByte = bytes2[pos + 28];
5797
+ const longBlockSize = 1 << (blockSizeByte >> 4);
5798
+ return longBlockSize / 2 / decoderConfig.sampleRate;
5799
+ }
5800
+ case "ac3":
5801
+ case "eac3": {
5802
+ return 256 / decoderConfig.sampleRate;
5803
+ }
5804
+ case "dts": {
5805
+ return 512 / decoderConfig.sampleRate;
5806
+ }
5807
+ case "flac":
5808
+ case "truehd":
5809
+ case "pcm-s16":
5810
+ case "pcm-s16be":
5811
+ case "pcm-s24":
5812
+ case "pcm-s24be":
5813
+ case "pcm-s32":
5814
+ case "pcm-s32be":
5815
+ case "pcm-f32":
5816
+ case "pcm-f32be":
5817
+ case "pcm-f64":
5818
+ case "pcm-f64be":
5819
+ case "pcm-u8":
5820
+ case "pcm-s8":
5821
+ case "ulaw":
5822
+ case "alaw": {
5823
+ return 0;
5824
+ }
5825
+ default: {
5826
+ assertNever(codec);
5827
+ assert(false);
5828
+ }
5829
+ }
5830
+ };
5452
5831
  var OPUS_SAMPLE_RATE = 48e3;
5832
+ var OPUS_PRE_ROLL_DURATION = 0.4;
5453
5833
  var PCM_CODEC_REGEX = /^pcm-([usf])(\d+)(be)?$/;
5454
5834
  var parsePcmCodec = (codec) => {
5455
5835
  assert(PCM_AUDIO_CODECS.includes(codec));
@@ -5503,6 +5883,8 @@ var Mediabunny = (() => {
5503
5883
  return "eac3";
5504
5884
  } else if (DTS_FOURCCS.includes(codecString)) {
5505
5885
  return "dts";
5886
+ } else if (codecString === "mlpa") {
5887
+ return "truehd";
5506
5888
  } else if (codecString === "ulaw") {
5507
5889
  return "ulaw";
5508
5890
  } else if (codecString === "alaw") {
@@ -5691,7 +6073,8 @@ var Mediabunny = (() => {
5691
6073
  "pcm",
5692
6074
  "ac-3",
5693
6075
  "ec-3",
5694
- "dts"
6076
+ "dts",
6077
+ "mlpa"
5695
6078
  ];
5696
6079
  var validateAudioChunkMetadata = (metadata, trackCodec) => {
5697
6080
  if (!metadata) {
@@ -5786,6 +6169,10 @@ var Mediabunny = (() => {
5786
6169
  `Audio chunk metadata decoder configuration codec string for DTS must be one of the following four-character codes: ${DTS_FOURCCS.join(", ")}.`
5787
6170
  );
5788
6171
  }
6172
+ } else if (metadata.decoderConfig.codec.startsWith("mlpa")) {
6173
+ if (metadata.decoderConfig.codec !== "mlpa") {
6174
+ throw new TypeError('Audio chunk metadata decoder configuration codec string for TrueHD must be "mlpa".');
6175
+ }
5789
6176
  } else if (metadata.decoderConfig.codec.startsWith("pcm") || metadata.decoderConfig.codec.startsWith("ulaw") || metadata.decoderConfig.codec.startsWith("alaw")) {
5790
6177
  if (!PCM_AUDIO_CODECS.includes(metadata.decoderConfig.codec)) {
5791
6178
  throw new TypeError(
@@ -5817,279 +6204,6 @@ var Mediabunny = (() => {
5817
6204
  }
5818
6205
  };
5819
6206
 
5820
- // shared/mp3-misc.ts
5821
- var MP3_FRAME_HEADER_SIZE = 4;
5822
- var SAMPLING_RATES = [44100, 48e3, 32e3];
5823
- var KILOBIT_RATES = [
5824
- // lowSamplingFrequency === 0
5825
- -1,
5826
- -1,
5827
- -1,
5828
- -1,
5829
- -1,
5830
- -1,
5831
- -1,
5832
- -1,
5833
- -1,
5834
- -1,
5835
- -1,
5836
- -1,
5837
- -1,
5838
- -1,
5839
- -1,
5840
- -1,
5841
- // layer = 0
5842
- -1,
5843
- 32,
5844
- 40,
5845
- 48,
5846
- 56,
5847
- 64,
5848
- 80,
5849
- 96,
5850
- 112,
5851
- 128,
5852
- 160,
5853
- 192,
5854
- 224,
5855
- 256,
5856
- 320,
5857
- -1,
5858
- // layer 1
5859
- -1,
5860
- 32,
5861
- 48,
5862
- 56,
5863
- 64,
5864
- 80,
5865
- 96,
5866
- 112,
5867
- 128,
5868
- 160,
5869
- 192,
5870
- 224,
5871
- 256,
5872
- 320,
5873
- 384,
5874
- -1,
5875
- // layer = 2
5876
- -1,
5877
- 32,
5878
- 64,
5879
- 96,
5880
- 128,
5881
- 160,
5882
- 192,
5883
- 224,
5884
- 256,
5885
- 288,
5886
- 320,
5887
- 352,
5888
- 384,
5889
- 416,
5890
- 448,
5891
- -1,
5892
- // layer = 3
5893
- // lowSamplingFrequency === 1
5894
- -1,
5895
- -1,
5896
- -1,
5897
- -1,
5898
- -1,
5899
- -1,
5900
- -1,
5901
- -1,
5902
- -1,
5903
- -1,
5904
- -1,
5905
- -1,
5906
- -1,
5907
- -1,
5908
- -1,
5909
- -1,
5910
- // layer = 0
5911
- -1,
5912
- 8,
5913
- 16,
5914
- 24,
5915
- 32,
5916
- 40,
5917
- 48,
5918
- 56,
5919
- 64,
5920
- 80,
5921
- 96,
5922
- 112,
5923
- 128,
5924
- 144,
5925
- 160,
5926
- -1,
5927
- // layer = 1
5928
- -1,
5929
- 8,
5930
- 16,
5931
- 24,
5932
- 32,
5933
- 40,
5934
- 48,
5935
- 56,
5936
- 64,
5937
- 80,
5938
- 96,
5939
- 112,
5940
- 128,
5941
- 144,
5942
- 160,
5943
- -1,
5944
- // layer = 2
5945
- -1,
5946
- 32,
5947
- 48,
5948
- 56,
5949
- 64,
5950
- 80,
5951
- 96,
5952
- 112,
5953
- 128,
5954
- 144,
5955
- 160,
5956
- 176,
5957
- 192,
5958
- 224,
5959
- 256,
5960
- -1
5961
- // layer = 3
5962
- ];
5963
- var XING = 1483304551;
5964
- var INFO = 1231971951;
5965
- var computeMp3FrameSize = (lowSamplingFrequency, layer, bitrate, sampleRate, padding) => {
5966
- if (layer === 0) {
5967
- return 0;
5968
- } else if (layer === 1) {
5969
- return Math.floor(144 * bitrate / (sampleRate << lowSamplingFrequency)) + padding;
5970
- } else if (layer === 2) {
5971
- return Math.floor(144 * bitrate / sampleRate) + padding;
5972
- } else {
5973
- return (Math.floor(12 * bitrate / sampleRate) + padding) * 4;
5974
- }
5975
- };
5976
- var computeAverageMp3FrameSize = (lowSamplingFrequency, layer, bitrate, sampleRate) => {
5977
- if (layer === 0) {
5978
- return 0;
5979
- } else if (layer === 1) {
5980
- return 144 * bitrate / (sampleRate << lowSamplingFrequency);
5981
- } else if (layer === 2) {
5982
- return 144 * bitrate / sampleRate;
5983
- } else {
5984
- return 12 * bitrate / sampleRate * 4;
5985
- }
5986
- };
5987
- var getXingOffset = (mpegVersionId, channel) => {
5988
- return mpegVersionId === 3 ? channel === 3 ? 21 : 36 : channel === 3 ? 13 : 21;
5989
- };
5990
- var readMp3FrameHeader = (word, remainingBytes) => {
5991
- const firstByte = word >>> 24;
5992
- const secondByte = word >>> 16 & 255;
5993
- const thirdByte = word >>> 8 & 255;
5994
- const fourthByte = word & 255;
5995
- if (firstByte !== 255 && secondByte !== 255 && thirdByte !== 255 && fourthByte !== 255) {
5996
- return {
5997
- header: null,
5998
- bytesAdvanced: 4
5999
- };
6000
- }
6001
- if (firstByte !== 255) {
6002
- return { header: null, bytesAdvanced: 1 };
6003
- }
6004
- if ((secondByte & 224) !== 224) {
6005
- return { header: null, bytesAdvanced: 1 };
6006
- }
6007
- let lowSamplingFrequency = 0;
6008
- let mpeg25 = 0;
6009
- if (secondByte & 1 << 4) {
6010
- lowSamplingFrequency = secondByte & 1 << 3 ? 0 : 1;
6011
- } else {
6012
- lowSamplingFrequency = 1;
6013
- mpeg25 = 1;
6014
- }
6015
- const mpegVersionId = secondByte >> 3 & 3;
6016
- const layer = secondByte >> 1 & 3;
6017
- const bitrateIndex = thirdByte >> 4 & 15;
6018
- const frequencyIndex = (thirdByte >> 2 & 3) % 3;
6019
- const padding = thirdByte >> 1 & 1;
6020
- const channel = fourthByte >> 6 & 3;
6021
- const modeExtension = fourthByte >> 4 & 3;
6022
- const copyright = fourthByte >> 3 & 1;
6023
- const original = fourthByte >> 2 & 1;
6024
- const emphasis = fourthByte & 3;
6025
- const kilobitRate = KILOBIT_RATES[lowSamplingFrequency * 16 * 4 + layer * 16 + bitrateIndex];
6026
- if (kilobitRate === -1) {
6027
- return { header: null, bytesAdvanced: 1 };
6028
- }
6029
- const bitrate = kilobitRate * 1e3;
6030
- const sampleRate = SAMPLING_RATES[frequencyIndex] >> lowSamplingFrequency + mpeg25;
6031
- const frameLength = computeMp3FrameSize(lowSamplingFrequency, layer, bitrate, sampleRate, padding);
6032
- if (remainingBytes !== null && remainingBytes < frameLength) {
6033
- return { header: null, bytesAdvanced: 1 };
6034
- }
6035
- let audioSamplesInFrame;
6036
- if (mpegVersionId === 3) {
6037
- audioSamplesInFrame = layer === 3 ? 384 : 1152;
6038
- } else {
6039
- if (layer === 3) {
6040
- audioSamplesInFrame = 384;
6041
- } else if (layer === 2) {
6042
- audioSamplesInFrame = 1152;
6043
- } else {
6044
- audioSamplesInFrame = 576;
6045
- }
6046
- }
6047
- return {
6048
- header: {
6049
- totalSize: frameLength,
6050
- mpegVersionId,
6051
- lowSamplingFrequency,
6052
- layer,
6053
- bitrate,
6054
- frequencyIndex,
6055
- sampleRate,
6056
- channel,
6057
- modeExtension,
6058
- copyright,
6059
- original,
6060
- emphasis,
6061
- audioSamplesInFrame
6062
- },
6063
- bytesAdvanced: 1
6064
- };
6065
- };
6066
- var encodeSynchsafe = (unsynchsafed) => {
6067
- let mask = 127;
6068
- let synchsafed = 0;
6069
- let unsynchsafedRest = unsynchsafed;
6070
- while ((mask ^ 2147483647) !== 0) {
6071
- synchsafed = unsynchsafedRest & ~mask;
6072
- synchsafed <<= 1;
6073
- synchsafed |= unsynchsafedRest & mask;
6074
- mask = (mask + 1 << 8) - 1;
6075
- unsynchsafedRest = synchsafed;
6076
- }
6077
- return synchsafed;
6078
- };
6079
- var decodeSynchsafe = (synchsafed) => {
6080
- let mask = 2130706432;
6081
- let unsynchsafed = 0;
6082
- while (mask !== 0) {
6083
- unsynchsafed >>= 1;
6084
- unsynchsafed |= synchsafed & mask;
6085
- mask >>= 8;
6086
- }
6087
- return unsynchsafed;
6088
- };
6089
- var getMp3ChannelCount = (channel) => {
6090
- return channel === 3 ? 1 : 2;
6091
- };
6092
-
6093
6207
  // src/demuxer.ts
6094
6208
  var Demuxer = class {
6095
6209
  constructor(input) {
@@ -6619,6 +6733,7 @@ var Mediabunny = (() => {
6619
6733
  };
6620
6734
 
6621
6735
  // src/isobmff/isobmff-demuxer.ts
6736
+ var TRUEHD_CHANNEL_ASSIGNMENT_COUNTS = [2, 1, 1, 2, 2, 2, 2, 1, 1, 2, 2, 1, 1];
6622
6737
  var MAX_BOX_NESTING_DEPTH = 64;
6623
6738
  var IsobmffDemuxer = class _IsobmffDemuxer extends Demuxer {
6624
6739
  constructor(input) {
@@ -7427,6 +7542,8 @@ var Mediabunny = (() => {
7427
7542
  } else if (DTS_FOURCCS.includes(codecName)) {
7428
7543
  track.info.codec = "dts";
7429
7544
  track.info.dtsFormat = codecName;
7545
+ } else if (codecName === "mlpa") {
7546
+ track.info.codec = "truehd";
7430
7547
  } else if (codecName === "twos") {
7431
7548
  if (sampleSize === 8) {
7432
7549
  track.info.codec = "pcm-s8";
@@ -7979,6 +8096,32 @@ var Mediabunny = (() => {
7979
8096
  }
7980
8097
  ;
7981
8098
  break;
8099
+ case "dmlp":
8100
+ {
8101
+ const track = this.currentTrack;
8102
+ if (!track || track.info?.type !== "audio") {
8103
+ break;
8104
+ }
8105
+ const formatInfo = readU32Be(slice);
8106
+ const rateBits = formatInfo >>> 28;
8107
+ if (rateBits === 15) {
8108
+ Logging._warn("Invalid dmlp box contents, ignoring.");
8109
+ break;
8110
+ }
8111
+ track.info.sampleRate = (rateBits & 8 ? 44100 : 48e3) << (rateBits & 7);
8112
+ const sixChannelAssignment = formatInfo >>> 15 & 31;
8113
+ const eightChannelAssignment = formatInfo & 8191;
8114
+ const channelAssignment = eightChannelAssignment || sixChannelAssignment;
8115
+ let numberOfChannels = 0;
8116
+ for (let i = 0; i < TRUEHD_CHANNEL_ASSIGNMENT_COUNTS.length; i++) {
8117
+ if (channelAssignment & 1 << i) {
8118
+ numberOfChannels += TRUEHD_CHANNEL_ASSIGNMENT_COUNTS[i];
8119
+ }
8120
+ }
8121
+ track.info.numberOfChannels = numberOfChannels;
8122
+ }
8123
+ ;
8124
+ break;
7982
8125
  case "stts":
7983
8126
  {
7984
8127
  const track = this.currentTrack;
@@ -10465,6 +10608,7 @@ var Mediabunny = (() => {
10465
10608
  "ac3": "A_AC3",
10466
10609
  "eac3": "A_EAC3",
10467
10610
  "dts": "A_DTS",
10611
+ "truehd": "A_TRUEHD",
10468
10612
  "pcm-u8": "A_PCM/INT/LIT",
10469
10613
  "pcm-s16": "A_PCM/INT/LIT",
10470
10614
  "pcm-s16be": "A_PCM/INT/BIG",
@@ -10754,6 +10898,7 @@ var Mediabunny = (() => {
10754
10898
  if (track.defaultDurationNs !== null) {
10755
10899
  track.defaultDuration = this.currentSegment.timestampFactor * track.defaultDurationNs / 1e9;
10756
10900
  }
10901
+ track.codecDelay = Math.round(this.currentSegment.timestampFactor * track.codecDelayNs / 1e9);
10757
10902
  }
10758
10903
  for (const cuePoint of this.currentSegment.cuePoints) {
10759
10904
  const track = this.currentSegment.idToTrack.get(cuePoint.trackId);
@@ -11152,6 +11297,8 @@ var Mediabunny = (() => {
11152
11297
  codecPrivate: null,
11153
11298
  defaultDuration: null,
11154
11299
  defaultDurationNs: null,
11300
+ codecDelay: 0,
11301
+ codecDelayNs: 0,
11155
11302
  name: null,
11156
11303
  languageCode: "eng",
11157
11304
  // The default in Matroska
@@ -11251,6 +11398,8 @@ var Mediabunny = (() => {
11251
11398
  } else if (this.currentTrack.codecId === "A_DTS/LOSSLESS") {
11252
11399
  this.currentTrack.info.dtsFormat = "dtsl";
11253
11400
  }
11401
+ } else if (codecIdWithoutSuffix === CODEC_STRING_MAP.truehd) {
11402
+ this.currentTrack.info.codec = "truehd";
11254
11403
  } else if (this.currentTrack.codecId === "A_PCM/INT/LIT") {
11255
11404
  if (this.currentTrack.info.bitDepth === 8) {
11256
11405
  this.currentTrack.info.codec = "pcm-u8";
@@ -11408,6 +11557,13 @@ var Mediabunny = (() => {
11408
11557
  }
11409
11558
  ;
11410
11559
  break;
11560
+ case 22186 /* CodecDelay */:
11561
+ {
11562
+ if (!this.currentTrack) break;
11563
+ this.currentTrack.codecDelayNs = readUnsignedInt(slice, size);
11564
+ }
11565
+ ;
11566
+ break;
11411
11567
  case 21358 /* Name */:
11412
11568
  {
11413
11569
  if (!this.currentTrack) break;
@@ -11676,7 +11832,7 @@ var Mediabunny = (() => {
11676
11832
  const flags = readU8(blockSlice);
11677
11833
  const lacing = flags >> 1 & 3;
11678
11834
  let isKeyFrame = !!(flags & 128);
11679
- if (trackData.track.info?.type === "audio" && trackData.track.info.codec) {
11835
+ if (trackData.track.info?.type === "audio" && trackData.track.info.codec && !AUDIO_CODECS_WITH_DELTA_PACKETS.includes(trackData.track.info.codec)) {
11680
11836
  isKeyFrame = true;
11681
11837
  }
11682
11838
  const blockData = readBytes(blockSlice, blockSlice.remainingLength);
@@ -12152,7 +12308,8 @@ var Mediabunny = (() => {
12152
12308
  if (segment.duration <= 0) {
12153
12309
  return null;
12154
12310
  }
12155
- return segment.duration / segment.timestampFactor;
12311
+ const minCodecDelay = Math.min(...segment.tracks.map((x) => x.codecDelay));
12312
+ return (segment.duration - minCodecDelay) / segment.timestampFactor;
12156
12313
  }
12157
12314
  };
12158
12315
  var MatroskaTrackBacking = class {
@@ -12241,7 +12398,7 @@ var Mediabunny = (() => {
12241
12398
  );
12242
12399
  }
12243
12400
  intoTimescale(timestamp) {
12244
- return roundIfAlmostInteger(timestamp * this.internalTrack.segment.timestampFactor);
12401
+ return roundIfAlmostInteger(timestamp * this.internalTrack.segment.timestampFactor) + this.internalTrack.codecDelay;
12245
12402
  }
12246
12403
  async getPacket(timestamp, options) {
12247
12404
  const timestampInTimescale = this.intoTimescale(timestamp);
@@ -12393,8 +12550,9 @@ var Mediabunny = (() => {
12393
12550
  block.postProcessed = true;
12394
12551
  }
12395
12552
  const data = options.metadataOnly ? PLACEHOLDER_DATA : block.data;
12396
- const timestamp = block.timestamp / this.internalTrack.segment.timestampFactor;
12397
- const duration = block.duration / this.internalTrack.segment.timestampFactor;
12553
+ const { codecDelay, segment } = this.internalTrack;
12554
+ const timestamp = (block.timestamp - codecDelay) / segment.timestampFactor;
12555
+ const duration = block.duration / segment.timestampFactor;
12398
12556
  const sideData = {};
12399
12557
  if (block.mainAdditional && this.internalTrack.info?.type === "video" && this.internalTrack.info.alphaMode) {
12400
12558
  sideData.alpha = options.metadataOnly ? PLACEHOLDER_DATA : block.mainAdditional;
@@ -12726,6 +12884,7 @@ var Mediabunny = (() => {
12726
12884
  this.lastSampleLoaded = false;
12727
12885
  this.lastLoadedPos = 0;
12728
12886
  this.nextTimestampInSamples = 0;
12887
+ this.primingDelay = 0;
12729
12888
  this.reader = input._reader;
12730
12889
  }
12731
12890
  async readMetadata() {
@@ -12790,9 +12949,24 @@ var Mediabunny = (() => {
12790
12949
  const view2 = toDataView(xingData);
12791
12950
  const flags = view2.getUint32(0, false);
12792
12951
  this.xingData = {
12952
+ // LAME and FFmpeg write the same header with 'Info' in place of 'Xing' for CBR streams
12953
+ isVbr: word === XING,
12793
12954
  frameCount: flags & 1 /* FrameCount */ ? view2.getUint32(4, false) : null,
12794
12955
  fileSize: flags & 2 /* FileSize */ ? view2.getUint32(8, false) : null
12795
12956
  };
12957
+ const lameOffset = result.startPos + xingOffset + 8 + (flags & 1 /* FrameCount */ ? 4 : 0) + (flags & 2 /* FileSize */ ? 4 : 0) + (flags & 4 /* Toc */ ? 100 : 0) + (flags & 8 /* Quality */ ? 4 : 0);
12958
+ if (!this.firstFrameHeader && lameOffset + 24 <= result.startPos + header.totalSize) {
12959
+ let lameSlice = this.reader.requestSlice(lameOffset, 24);
12960
+ if (isThenable(lameSlice)) lameSlice = await lameSlice;
12961
+ if (lameSlice) {
12962
+ const lame = readBytes(lameSlice, 24);
12963
+ const encoder = String.fromCharCode(...lame.subarray(0, 4));
12964
+ if (encoder === "LAME" || encoder === "Lavf" || encoder === "Lavc") {
12965
+ this.primingDelay = (lame[21] << 4 | lame[22] >> 4) + MP3_DECODER_DELAY;
12966
+ this.nextTimestampInSamples = -this.primingDelay;
12967
+ }
12968
+ }
12969
+ }
12796
12970
  }
12797
12971
  }
12798
12972
  return;
@@ -12875,7 +13049,7 @@ var Mediabunny = (() => {
12875
13049
  }
12876
13050
  getTimeResolution() {
12877
13051
  assert(this.demuxer.firstFrameHeader);
12878
- return this.demuxer.firstFrameHeader.sampleRate / this.demuxer.firstFrameHeader.audioSamplesInFrame;
13052
+ return this.demuxer.firstFrameHeader.sampleRate;
12879
13053
  }
12880
13054
  isRelativeToUnixEpoch() {
12881
13055
  return false;
@@ -12896,11 +13070,9 @@ var Mediabunny = (() => {
12896
13070
  const demuxer = this.demuxer;
12897
13071
  assert(demuxer.firstFrameHeader !== null);
12898
13072
  assert(demuxer.firstFrameHeaderPos !== null);
12899
- if (demuxer.xingData) {
12900
- if (demuxer.xingData.frameCount !== null) {
12901
- return demuxer.xingData.frameCount * demuxer.firstFrameHeader.audioSamplesInFrame / demuxer.firstFrameHeader.sampleRate;
12902
- }
12903
- } else {
13073
+ if (demuxer.xingData && demuxer.xingData.frameCount !== null) {
13074
+ return (demuxer.xingData.frameCount * demuxer.firstFrameHeader.audioSamplesInFrame - demuxer.primingDelay) / demuxer.firstFrameHeader.sampleRate;
13075
+ } else if (!demuxer.xingData?.isVbr) {
12904
13076
  if (demuxer.reader.fileSize !== null) {
12905
13077
  const averageFrameSize = computeAverageMp3FrameSize(
12906
13078
  demuxer.firstFrameHeader.lowSamplingFrequency,
@@ -12909,7 +13081,7 @@ var Mediabunny = (() => {
12909
13081
  demuxer.firstFrameHeader.sampleRate
12910
13082
  );
12911
13083
  const frameCount = (demuxer.reader.fileSize - demuxer.firstFrameHeaderPos) / averageFrameSize;
12912
- return Math.round(frameCount) * demuxer.firstFrameHeader.audioSamplesInFrame / demuxer.firstFrameHeader.sampleRate;
13084
+ return (Math.round(frameCount) * demuxer.firstFrameHeader.audioSamplesInFrame - demuxer.primingDelay) / demuxer.firstFrameHeader.sampleRate;
12913
13085
  }
12914
13086
  }
12915
13087
  return null;
@@ -13069,7 +13241,7 @@ var Mediabunny = (() => {
13069
13241
  if (modeNumber >= codecInfo.vorbisInfo.modeBlockflags.length) {
13070
13242
  throw new Error("Invalid mode number.");
13071
13243
  }
13072
- let prevBlocksize = vorbisLastBlocksize;
13244
+ let prevBlocksize = vorbisLastBlocksize ?? codecInfo.vorbisInfo.blocksizes[0];
13073
13245
  const blockflag = codecInfo.vorbisInfo.modeBlockflags[modeNumber];
13074
13246
  currentBlocksize = codecInfo.vorbisInfo.blocksizes[blockflag];
13075
13247
  if (blockflag === 1) {
@@ -13077,7 +13249,7 @@ var Mediabunny = (() => {
13077
13249
  const flag = data[0] & prevMask ? 1 : 0;
13078
13250
  prevBlocksize = codecInfo.vorbisInfo.blocksizes[flag];
13079
13251
  }
13080
- durationInSamples = prevBlocksize !== null ? prevBlocksize + currentBlocksize >> 2 : 0;
13252
+ durationInSamples = prevBlocksize + currentBlocksize >> 2;
13081
13253
  } else if (codecInfo.codec === "opus") {
13082
13254
  const toc = parseOpusTocByte(data);
13083
13255
  durationInSamples = toc.durationInSamples;
@@ -13541,16 +13713,14 @@ var Mediabunny = (() => {
13541
13713
  let { durationInSamples } = sampleMetadata;
13542
13714
  const isEos = !!(packet.endPage.headerType & 4);
13543
13715
  if (isEos && packet.endSegmentIndex === packet.endPage.lacingValues.length - 1) {
13544
- const endTimestampInSamples2 = this.granulePositionToTimestampInSamples(packet.endPage.granulePosition);
13545
- durationInSamples = clamp(endTimestampInSamples2 - additional.timestampInSamples, 0, durationInSamples);
13716
+ const endTimestampInSamples = this.granulePositionToTimestampInSamples(packet.endPage.granulePosition);
13717
+ durationInSamples = clamp(endTimestampInSamples - additional.timestampInSamples, 0, durationInSamples);
13546
13718
  }
13547
- const startTimestampInSamples = Math.max(additional.timestampInSamples, 0);
13548
- const endTimestampInSamples = Math.max(additional.timestampInSamples + durationInSamples, 0);
13549
13719
  const encodedPacket = new EncodedPacket(
13550
13720
  options.metadataOnly ? PLACEHOLDER_DATA : packet.data,
13551
13721
  "key",
13552
- startTimestampInSamples / this.internalSampleRate,
13553
- (endTimestampInSamples - startTimestampInSamples) / this.internalSampleRate,
13722
+ additional.timestampInSamples / this.internalSampleRate,
13723
+ durationInSamples / this.internalSampleRate,
13554
13724
  packet.endPage.headerStartPos + packet.endSegmentIndex,
13555
13725
  packet.data.byteLength
13556
13726
  );
@@ -13573,6 +13743,7 @@ var Mediabunny = (() => {
13573
13743
  }
13574
13744
  let firstEndPage = null;
13575
13745
  let totalDurationInSamples = 0;
13746
+ let firstPacketDurationInSamples = null;
13576
13747
  let vorbisLastBlocksize = null;
13577
13748
  while (position) {
13578
13749
  const packet = await this.demuxer.readPacket(position.startPage, position.startSegmentIndex);
@@ -13589,13 +13760,16 @@ var Mediabunny = (() => {
13589
13760
  vorbisLastBlocksize
13590
13761
  );
13591
13762
  totalDurationInSamples += durationInSamples;
13763
+ firstPacketDurationInSamples ??= durationInSamples;
13592
13764
  vorbisLastBlocksize = vorbisBlockSize;
13593
13765
  position = await this.demuxer.findNextPacketStart(packet);
13594
13766
  }
13595
13767
  if (!firstEndPage) {
13596
13768
  return defaultTimestampInSamples;
13597
13769
  }
13598
- return defaultTimestampInSamples + Math.max(firstEndPage.granulePosition - totalDurationInSamples, 0);
13770
+ assert(firstPacketDurationInSamples !== null);
13771
+ const minStartInSamples = this.bitstream.codecInfo.codec === "vorbis" ? -firstPacketDurationInSamples : 0;
13772
+ return defaultTimestampInSamples + Math.max(firstEndPage.granulePosition - totalDurationInSamples, minStartInSamples);
13599
13773
  })();
13600
13774
  }
13601
13775
  async getFirstPacket(options) {
@@ -13644,10 +13818,10 @@ var Mediabunny = (() => {
13644
13818
  }
13645
13819
  const timestampInSamples = roundIfAlmostInteger(timestamp * this.internalSampleRate);
13646
13820
  const firstTimestampInSamples = await this.getFirstTimestampInSamples();
13647
- if (timestampInSamples === Math.max(firstTimestampInSamples, 0)) {
13821
+ if (timestampInSamples === firstTimestampInSamples) {
13648
13822
  return this.getFirstPacket(options);
13649
13823
  }
13650
- if (timestampInSamples < Math.max(firstTimestampInSamples, 0)) {
13824
+ if (timestampInSamples < firstTimestampInSamples) {
13651
13825
  return null;
13652
13826
  }
13653
13827
  assert(this.bitstream.lastMetadataPacket);
@@ -13848,7 +14022,7 @@ var Mediabunny = (() => {
13848
14022
  lastEncodedPacket = encodedPacket;
13849
14023
  lastEncodedPacketMetadata = encodedPacketMetadata;
13850
14024
  if (currentTimestampIsCorrect && // Next timestamp will be too late
13851
- (Math.max(currentTimestampInSamples, 0) > timestampInSamples || Math.max(encodedPacketMetadata.timestampInSamples, 0) === timestampInSamples)) {
14025
+ (currentTimestampInSamples > timestampInSamples || encodedPacketMetadata.timestampInSamples === timestampInSamples)) {
13852
14026
  break;
13853
14027
  }
13854
14028
  }
@@ -14615,8 +14789,7 @@ var Mediabunny = (() => {
14615
14789
  return 1;
14616
14790
  }
14617
14791
  getTimeResolution() {
14618
- const sampleRate = this.getSampleRate();
14619
- return sampleRate / SAMPLES_PER_AAC_FRAME;
14792
+ return this.getSampleRate();
14620
14793
  }
14621
14794
  isRelativeToUnixEpoch() {
14622
14795
  return false;
@@ -15074,7 +15247,7 @@ var Mediabunny = (() => {
15074
15247
  const maximumSliceLength = effectiveMaxFrameSize + maximumHeaderLength;
15075
15248
  const slice = await this.reader.requestSliceRange(
15076
15249
  startPos,
15077
- maximumHeaderLength,
15250
+ minimumHeaderLength,
15078
15251
  maximumSliceLength
15079
15252
  );
15080
15253
  if (!slice) {
@@ -15391,7 +15564,7 @@ var Mediabunny = (() => {
15391
15564
  };
15392
15565
 
15393
15566
  // src/mpeg-ts/mpeg-ts-misc.ts
15394
- var TIMESCALE = 9e4;
15567
+ var MPEG_TS_TIMESCALE = 9e4;
15395
15568
  var TIMESTAMP_MODULUS = 2 ** 33;
15396
15569
  var TS_PACKET_SIZE = 188;
15397
15570
  var buildMpegTsMimeType = (codecStrings) => {
@@ -15402,6 +15575,23 @@ var Mediabunny = (() => {
15402
15575
  }
15403
15576
  return string;
15404
15577
  };
15578
+ var secondsToMpegTsTimestamp = (seconds) => {
15579
+ return modEuclid(Math.round(MPEG_TS_TIMESCALE * seconds), TIMESTAMP_MODULUS);
15580
+ };
15581
+ var createTimestampWrapInfo = (firstTimestamp) => {
15582
+ const tolerance = 60 * MPEG_TS_TIMESCALE;
15583
+ return {
15584
+ reference: firstTimestamp - tolerance,
15585
+ offset: firstTimestamp >= TIMESTAMP_MODULUS - tolerance ? -TIMESTAMP_MODULUS : TIMESTAMP_MODULUS
15586
+ };
15587
+ };
15588
+ var normalizeWrappedTimestamp = (timestamp, wrapInfo) => {
15589
+ const { reference, offset } = wrapInfo;
15590
+ if (offset < 0 && timestamp >= reference || offset > 0 && timestamp < reference) {
15591
+ return timestamp + offset;
15592
+ }
15593
+ return timestamp;
15594
+ };
15405
15595
 
15406
15596
  // src/mpeg-ts/mpeg-ts-demuxer.ts
15407
15597
  var MISSING_PTS_ERROR_MESSAGE = "PES packet is missing PTS where it was expected. PES packets without PTS are not currently supported. If you think this file should be supported, please report it.";
@@ -16085,18 +16275,8 @@ var Mediabunny = (() => {
16085
16275
  };
16086
16276
  }
16087
16277
  normalizeTimestamp(timestamp) {
16088
- if (!this.timestampWrapInfo) {
16089
- const tolerance = 60 * TIMESCALE;
16090
- this.timestampWrapInfo = {
16091
- reference: timestamp - tolerance,
16092
- offset: timestamp >= TIMESTAMP_MODULUS - tolerance ? -TIMESTAMP_MODULUS : TIMESTAMP_MODULUS
16093
- };
16094
- }
16095
- const { reference, offset } = this.timestampWrapInfo;
16096
- if (offset < 0 && timestamp >= reference || offset > 0 && timestamp < reference) {
16097
- return timestamp + offset;
16098
- }
16099
- return timestamp;
16278
+ this.timestampWrapInfo ??= createTimestampWrapInfo(timestamp);
16279
+ return normalizeWrappedTimestamp(timestamp, this.timestampWrapInfo);
16100
16280
  }
16101
16281
  };
16102
16282
  var readPesPacketHeader = (demuxer, section, expectPts) => {
@@ -16210,7 +16390,7 @@ var Mediabunny = (() => {
16210
16390
  };
16211
16391
  }
16212
16392
  getTimeResolution() {
16213
- return TIMESCALE;
16393
+ return MPEG_TS_TIMESCALE;
16214
16394
  }
16215
16395
  isRelativeToUnixEpoch() {
16216
16396
  return false;
@@ -16243,8 +16423,8 @@ var Mediabunny = (() => {
16243
16423
  return new EncodedPacket(
16244
16424
  options.metadataOnly ? PLACEHOLDER_DATA : suppliedPacket.data,
16245
16425
  packetType,
16246
- suppliedPacket.pts / TIMESCALE,
16247
- Math.max(duration / TIMESCALE, 0),
16426
+ suppliedPacket.pts / MPEG_TS_TIMESCALE,
16427
+ Math.max(duration / MPEG_TS_TIMESCALE, 0),
16248
16428
  suppliedPacket.sequenceNumber,
16249
16429
  suppliedPacket.data.byteLength
16250
16430
  );
@@ -16327,7 +16507,7 @@ var Mediabunny = (() => {
16327
16507
  * make it more performant for small files and over high-latency readers such as the network.
16328
16508
  */
16329
16509
  async doPacketLookup(timestamp, keyframesOnly, options) {
16330
- const searchPts = roundIfAlmostInteger(timestamp * TIMESCALE);
16510
+ const searchPts = roundIfAlmostInteger(timestamp * MPEG_TS_TIMESCALE);
16331
16511
  const demuxer = this.elementaryStream.demuxer;
16332
16512
  const { reader, seekChunkSize } = demuxer;
16333
16513
  const pid = this.elementaryStream.pid;
@@ -16366,7 +16546,7 @@ var Mediabunny = (() => {
16366
16546
  const referencePesPackets = this.elementaryStream.referencePesPackets;
16367
16547
  const referencePointIndex = binarySearchLessOrEqual(referencePesPackets, searchPts, (x) => x.pts);
16368
16548
  const referencePoint = referencePointIndex !== -1 ? referencePesPackets[referencePointIndex] : null;
16369
- if (referencePoint && searchPts - referencePoint.pts < TIMESCALE / 2) {
16549
+ if (referencePoint && searchPts - referencePoint.pts < MPEG_TS_TIMESCALE / 2) {
16370
16550
  scanStartPos = referencePoint.sectionStartPos;
16371
16551
  } else {
16372
16552
  let startChunkIndex = 0;
@@ -16716,7 +16896,12 @@ var Mediabunny = (() => {
16716
16896
  }
16717
16897
  }
16718
16898
  }
16719
- referencePesPackets.splice(index + 1, 0, pesPacketHeader);
16899
+ referencePesPackets.splice(index + 1, 0, {
16900
+ sectionStartPos: pesPacketHeader.sectionStartPos,
16901
+ sectionEndPos: pesPacketHeader.sectionEndPos,
16902
+ pts: pesPacketHeader.pts,
16903
+ randomAccessIndicator: pesPacketHeader.randomAccessIndicator
16904
+ });
16720
16905
  return true;
16721
16906
  };
16722
16907
  var PacketReadingContext = class {
@@ -16992,7 +17177,9 @@ var Mediabunny = (() => {
16992
17177
  if (isThenable(remaining3)) remaining3 = await remaining3;
16993
17178
  return this.supplyPacket(
16994
17179
  remaining3,
16995
- Math.round(SAMPLES_PER_AAC_FRAME * TIMESCALE / elementaryStream.info.sampleRate)
17180
+ Math.round(
17181
+ SAMPLES_PER_AAC_FRAME * MPEG_TS_TIMESCALE / elementaryStream.info.sampleRate
17182
+ )
16996
17183
  );
16997
17184
  } else {
16998
17185
  this.seekTo(possibleHeaderStartPos + 1);
@@ -17015,7 +17202,7 @@ var Mediabunny = (() => {
17015
17202
  this.seekTo(possibleHeaderStartPos);
17016
17203
  let remaining3 = this.ensureBuffered(result.header.totalSize);
17017
17204
  if (isThenable(remaining3)) remaining3 = await remaining3;
17018
- const duration = result.header.audioSamplesInFrame * TIMESCALE / elementaryStream.info.sampleRate;
17205
+ const duration = result.header.audioSamplesInFrame * MPEG_TS_TIMESCALE / elementaryStream.info.sampleRate;
17019
17206
  return this.supplyPacket(remaining3, Math.round(duration));
17020
17207
  } else {
17021
17208
  this.seekTo(possibleHeaderStartPos + 1);
@@ -17048,7 +17235,7 @@ var Mediabunny = (() => {
17048
17235
  remaining2 = this.ensureBuffered(frameSize);
17049
17236
  if (isThenable(remaining2)) remaining2 = await remaining2;
17050
17237
  const duration = Math.round(
17051
- AC3_SAMPLES_PER_FRAME * TIMESCALE / elementaryStream.info.sampleRate
17238
+ AC3_SAMPLES_PER_FRAME * MPEG_TS_TIMESCALE / elementaryStream.info.sampleRate
17052
17239
  );
17053
17240
  return this.supplyPacket(remaining2, duration);
17054
17241
  } else if (codec === "eac3") {
@@ -17077,7 +17264,7 @@ var Mediabunny = (() => {
17077
17264
  if (isThenable(remaining2)) remaining2 = await remaining2;
17078
17265
  const samplesPerFrame = numblks * 256;
17079
17266
  const duration = Math.round(
17080
- samplesPerFrame * TIMESCALE / elementaryStream.info.sampleRate
17267
+ samplesPerFrame * MPEG_TS_TIMESCALE / elementaryStream.info.sampleRate
17081
17268
  );
17082
17269
  return this.supplyPacket(remaining2, duration);
17083
17270
  } else if (codec === "dts") {
@@ -17134,7 +17321,7 @@ var Mediabunny = (() => {
17134
17321
  remaining2 = this.ensureBuffered(frameSize);
17135
17322
  if (isThenable(remaining2)) remaining2 = await remaining2;
17136
17323
  const duration = Math.round(
17137
- sampleCount * TIMESCALE / elementaryStream.info.sampleRate
17324
+ sampleCount * MPEG_TS_TIMESCALE / elementaryStream.info.sampleRate
17138
17325
  );
17139
17326
  return this.supplyPacket(remaining2, duration);
17140
17327
  } else {
@@ -17305,10 +17492,12 @@ var Mediabunny = (() => {
17305
17492
  var TAG_BYTERANGE = "#EXT-X-BYTERANGE:";
17306
17493
  var TAG_PROGRAM_DATE_TIME = "#EXT-X-PROGRAM-DATE-TIME:";
17307
17494
  var TAG_DISCONTINUITY = "#EXT-X-DISCONTINUITY";
17495
+ var TAG_DISCONTINUITY_SEQUENCE = "#EXT-X-DISCONTINUITY-SEQUENCE:";
17308
17496
  var TAG_TARGETDURATION = "#EXT-X-TARGETDURATION:";
17309
17497
  var TAG_ENDLIST = "#EXT-X-ENDLIST";
17310
17498
  var TAG_PLAYLIST_TYPE = "#EXT-X-PLAYLIST-TYPE:";
17311
17499
  var TAG_I_FRAMES_ONLY = "#EXT-X-I-FRAMES-ONLY";
17500
+ var TIMESTAMP_PRIV_OWNER = "com.apple.streaming.transportStreamTimestamp";
17312
17501
  var canIgnoreLine = (line) => line.length === 0 || line.startsWith("#") && !line.startsWith("#EXT");
17313
17502
  var AttributeList = class {
17314
17503
  constructor(str, variables) {
@@ -17445,7 +17634,9 @@ var Mediabunny = (() => {
17445
17634
  this.inputCache = [];
17446
17635
  this.trackBackingsPromise = null;
17447
17636
  this.firstSegment = null;
17448
- this.firstSegmentFirstTimestamps = /* @__PURE__ */ new WeakMap();
17637
+ // Roughly maps local segment timestamps onto actual packet timestamps
17638
+ this.learnedSegmentTimestampOffset = null;
17639
+ this.segmentMediaOffsets = /* @__PURE__ */ new WeakMap();
17449
17640
  this.input = input;
17450
17641
  this.path = path;
17451
17642
  this.trackDeclarations = trackDeclarations;
@@ -17457,7 +17648,7 @@ var Mediabunny = (() => {
17457
17648
  if (!lastSegment) {
17458
17649
  return null;
17459
17650
  }
17460
- return lastSegment.timestamp + lastSegment.duration;
17651
+ return lastSegment.timestamp + await this.getFirstSegmentTimestampOffset() + lastSegment.duration;
17461
17652
  }
17462
17653
  async getUnixTimeForTimestamp(timestamp) {
17463
17654
  let segment = await this.getSegmentAt(timestamp, {});
@@ -17465,7 +17656,7 @@ var Mediabunny = (() => {
17465
17656
  if (!segment || segment.unixEpochTimestamp === null) {
17466
17657
  return null;
17467
17658
  }
17468
- const elapsed = timestamp - segment.timestamp;
17659
+ const elapsed = timestamp - (segment.timestamp + await this.getFirstSegmentTimestampOffset());
17469
17660
  return segment.unixEpochTimestamp + elapsed;
17470
17661
  }
17471
17662
  async getTrackBackings() {
@@ -17515,19 +17706,29 @@ var Mediabunny = (() => {
17515
17706
  return backings;
17516
17707
  })();
17517
17708
  }
17518
- async getMediaOffset(segment, input) {
17519
- const format = await input.getFormat();
17520
- if (!format.supportsTimestampedMediaData) {
17521
- return segment.timestamp;
17522
- }
17523
- const firstSegment = segment.firstSegment ?? segment;
17524
- let firstSegmentFirstTimestamp = this.firstSegmentFirstTimestamps.get(firstSegment);
17525
- if (firstSegmentFirstTimestamp === void 0) {
17526
- const firstInput = this.getInputForSegment(firstSegment);
17527
- firstSegmentFirstTimestamp = await firstInput.getFirstTimestamp();
17528
- this.firstSegmentFirstTimestamps.set(firstSegment, firstSegmentFirstTimestamp);
17529
- }
17530
- return firstSegment.timestamp - firstSegmentFirstTimestamp;
17709
+ getMediaOffset(segment, input) {
17710
+ let promise = this.segmentMediaOffsets.get(segment);
17711
+ if (promise) {
17712
+ return promise;
17713
+ }
17714
+ promise = (async () => {
17715
+ const rawTimestampOffset = await this.getRawTimestampOffset(input);
17716
+ if (rawTimestampOffset === null) {
17717
+ return segment.timestamp;
17718
+ }
17719
+ let mediaOffset = rawTimestampOffset + await this.getMediaOffsetForDiscontinuity(segment.discontinuityNumber);
17720
+ const period = this.getTimestampWrapPeriod();
17721
+ if (period < Infinity) {
17722
+ const tracks = await input.getTracks();
17723
+ const track = tracks.find((x) => x.type === "video") ?? tracks[0];
17724
+ assert(track);
17725
+ const mediaStart = await track.getFirstTimestamp() + mediaOffset;
17726
+ mediaOffset += period * Math.round((segment.timestamp - mediaStart) / period);
17727
+ }
17728
+ return mediaOffset;
17729
+ })();
17730
+ this.segmentMediaOffsets.set(segment, promise);
17731
+ return promise;
17531
17732
  }
17532
17733
  dispose() {
17533
17734
  for (const entry of this.inputCache) {
@@ -17745,6 +17946,21 @@ var Mediabunny = (() => {
17745
17946
  continue;
17746
17947
  }
17747
17948
  const mediaOffset = await this.segmentedInput.getMediaOffset(currentSegment, input);
17949
+ const firstPacket = this.segmentedInput.learnedSegmentTimestampOffset === null ? await track._backing.getFirstPacket({ ...options, metadataOnly: true }) : null;
17950
+ if (firstPacket) {
17951
+ const segmentStart = firstPacket.timestamp + mediaOffset;
17952
+ this.segmentedInput.learnedSegmentTimestampOffset = segmentStart - currentSegment.timestamp;
17953
+ const distance = timestamp - segmentStart;
17954
+ if (distance < -currentSegment.duration || distance >= 2 * currentSegment.duration) {
17955
+ const segment = await this.segmentedInput.getSegmentAt(timestamp, {
17956
+ skipLiveWait: options.skipLiveWait
17957
+ });
17958
+ if (segment !== currentSegment) {
17959
+ currentSegment = segment;
17960
+ continue;
17961
+ }
17962
+ }
17963
+ }
17748
17964
  const offsetTimestamp = timestamp - mediaOffset;
17749
17965
  const packet = keyframesOnly ? await track._backing.getKeyPacket(offsetTimestamp, options) : await track._backing.getPacket(offsetTimestamp, options);
17750
17966
  if (!packet) {
@@ -18379,6 +18595,7 @@ var Mediabunny = (() => {
18379
18595
  }
18380
18596
  /** @internal */
18381
18597
  async _runWorker(worker) {
18598
+ let consecutiveEmptyResponses = 0;
18382
18599
  while (true) {
18383
18600
  if (worker.aborted) {
18384
18601
  this._orchestrator.signalWorkerStoppedRunning(worker);
@@ -18452,6 +18669,7 @@ var Mediabunny = (() => {
18452
18669
  return;
18453
18670
  }
18454
18671
  const reader = response.body.getReader();
18672
+ const responseStartPos = worker.currentPos;
18455
18673
  while (true) {
18456
18674
  if (worker.currentPos >= worker.targetPos || worker.aborted) {
18457
18675
  abortController.abort();
@@ -18484,6 +18702,18 @@ var Mediabunny = (() => {
18484
18702
  return;
18485
18703
  }
18486
18704
  if (worker.strictTarget) {
18705
+ if (worker.currentPos > responseStartPos) {
18706
+ consecutiveEmptyResponses = 0;
18707
+ break;
18708
+ }
18709
+ consecutiveEmptyResponses++;
18710
+ const error = new Error("Range response ended without delivering any data.");
18711
+ const retryDelayInSeconds = this._getRetryDelay(consecutiveEmptyResponses, error, this._url);
18712
+ if (retryDelayInSeconds === null) {
18713
+ throw error;
18714
+ }
18715
+ Logging._error("Retrying range request that ended without delivering any data.");
18716
+ await wait(1e3 * retryDelayInSeconds);
18487
18717
  break;
18488
18718
  } else {
18489
18719
  this._orchestrator.onWorkerFinished(worker);
@@ -19644,15 +19874,17 @@ var Mediabunny = (() => {
19644
19874
  var BASE64_DATA_URI_REGEX = /^data:.*;base64,/i;
19645
19875
  var MAX_DURATION = 1e9;
19646
19876
  var HlsSegmentedInput = class extends SegmentedInput {
19647
- // Reasonable default in case the playlist doesn't specify it
19648
19877
  constructor(demuxer, path, trackDeclarations, lines) {
19649
19878
  super(demuxer.input, path, trackDeclarations);
19650
19879
  this.segments = [];
19651
19880
  this.nextLines = null;
19652
19881
  this.currentUpdateSegmentsPromise = null;
19653
19882
  this.streamHasEnded = false;
19883
+ this.neverRemovesSegments = false;
19654
19884
  this.lastSegmentUpdateTime = -Infinity;
19655
19885
  this.refreshInterval = 5;
19886
+ // Reasonable default in case the playlist doesn't specify it
19887
+ this.segmentTimestampOffsetPromise = null;
19656
19888
  this.rootPath = path;
19657
19889
  this.demuxer = demuxer;
19658
19890
  this.nextLines = lines;
@@ -19722,13 +19954,12 @@ var Mediabunny = (() => {
19722
19954
  let nextSegmentDuration = null;
19723
19955
  let currentKey = null;
19724
19956
  let nextSequenceNumber = 0;
19957
+ let nextDiscontinuityNumber = 0;
19725
19958
  let currentFirstSegment = null;
19726
19959
  let currentInitSegment = null;
19727
19960
  let lastByteRangeEnd = null;
19728
19961
  let nextByteRange = null;
19729
19962
  let lastProgramDateTimeSeconds = null;
19730
- let targetDuration = null;
19731
- let segmentSeen = false;
19732
19963
  let prevLastSegment = last(this.segments) ?? null;
19733
19964
  const parseByteRange = (content) => {
19734
19965
  const atIndex = content.indexOf("@");
@@ -19791,6 +20022,7 @@ var Mediabunny = (() => {
19791
20022
  index: this.segments.length,
19792
20023
  timestamp: accumulatedTime,
19793
20024
  unixEpochTimestamp: accumulatedUnixTime,
20025
+ discontinuityNumber: nextDiscontinuityNumber,
19794
20026
  firstSegment: currentFirstSegment,
19795
20027
  sequenceNumber: nextSequenceNumber,
19796
20028
  location,
@@ -19817,15 +20049,8 @@ var Mediabunny = (() => {
19817
20049
  }
19818
20050
  if (line.startsWith(TAG_EXTINF)) {
19819
20051
  if (prevLastSegment) {
19820
- segmentSeen = true;
19821
20052
  continue;
19822
20053
  }
19823
- if (!segmentSeen) {
19824
- if (lastProgramDateTimeSeconds === null && nextSequenceNumber > 0 && targetDuration !== null) {
19825
- accumulatedTime = nextSequenceNumber * targetDuration;
19826
- }
19827
- segmentSeen = true;
19828
- }
19829
20054
  const extinfContent = line.slice(TAG_EXTINF.length);
19830
20055
  const commaIndex = extinfContent.indexOf(",");
19831
20056
  const durationStr = commaIndex === -1 ? extinfContent : extinfContent.slice(0, commaIndex);
@@ -19864,6 +20089,7 @@ var Mediabunny = (() => {
19864
20089
  index: -1,
19865
20090
  timestamp: accumulatedTime,
19866
20091
  unixEpochTimestamp: accumulatedUnixTime,
20092
+ discontinuityNumber: nextDiscontinuityNumber,
19867
20093
  firstSegment: null,
19868
20094
  sequenceNumber: null,
19869
20095
  location,
@@ -19997,6 +20223,14 @@ var Mediabunny = (() => {
19997
20223
  }
19998
20224
  } else if (line === TAG_DISCONTINUITY) {
19999
20225
  currentFirstSegment = null;
20226
+ nextDiscontinuityNumber++;
20227
+ } else if (line.startsWith(TAG_DISCONTINUITY_SEQUENCE)) {
20228
+ const value = line.slice(TAG_DISCONTINUITY_SEQUENCE.length);
20229
+ const number = Number(value);
20230
+ if (!Number.isSafeInteger(number) || number < 0) {
20231
+ throw new Error(`Invalid EXT-X-DISCONTINUITY-SEQUENCE value '${value}'.`);
20232
+ }
20233
+ nextDiscontinuityNumber = number;
20000
20234
  } else if (line.startsWith(TAG_TARGETDURATION)) {
20001
20235
  const value = line.slice(TAG_TARGETDURATION.length);
20002
20236
  const duration = Number(value);
@@ -20004,15 +20238,17 @@ var Mediabunny = (() => {
20004
20238
  throw new Error(`Invalid EXT-X-TARGETDURATION value '${value}'.`);
20005
20239
  }
20006
20240
  this.refreshInterval = clamp(duration, 0.5, 3600);
20007
- targetDuration = duration;
20008
20241
  } else if (line === TAG_ENDLIST) {
20009
20242
  this.streamHasEnded = true;
20010
20243
  break;
20011
20244
  } else if (line.startsWith(TAG_PLAYLIST_TYPE)) {
20012
- const type = line.slice(TAG_PLAYLIST_TYPE.length);
20013
- if (type.toLowerCase() === "vod") {
20245
+ const type = line.slice(TAG_PLAYLIST_TYPE.length).toLowerCase();
20246
+ if (type === "vod") {
20014
20247
  this.streamHasEnded = true;
20015
20248
  }
20249
+ if (type === "vod" || type === "event") {
20250
+ this.neverRemovesSegments = true;
20251
+ }
20016
20252
  }
20017
20253
  }
20018
20254
  if (!headerRead) {
@@ -20029,9 +20265,10 @@ var Mediabunny = (() => {
20029
20265
  if (this.segments.length === 0) {
20030
20266
  await this.runUpdateSegments();
20031
20267
  }
20268
+ const playlistTimestamp = timestamp - (this.learnedSegmentTimestampOffset ?? 0);
20032
20269
  let isLazy = !!options.skipLiveWait && this.getRemainingWaitTimeMs() > 0;
20033
20270
  while (true) {
20034
- const index = binarySearchLessOrEqual(this.segments, timestamp, (x) => x.timestamp);
20271
+ const index = binarySearchLessOrEqual(this.segments, playlistTimestamp, (x) => x.timestamp);
20035
20272
  if (index === -1) {
20036
20273
  return null;
20037
20274
  }
@@ -20039,7 +20276,7 @@ var Mediabunny = (() => {
20039
20276
  return this.segments[index];
20040
20277
  }
20041
20278
  const segment = this.segments[index];
20042
- if (timestamp < segment.timestamp + segment.duration) {
20279
+ if (playlistTimestamp < segment.timestamp + segment.duration) {
20043
20280
  return segment;
20044
20281
  }
20045
20282
  await this.runUpdateSegments();
@@ -20196,6 +20433,65 @@ var Mediabunny = (() => {
20196
20433
  }
20197
20434
  return this.streamHasEnded ? null : this.refreshInterval;
20198
20435
  }
20436
+ getMediaOffsetForDiscontinuity(discontinuityNumber) {
20437
+ return this.demuxer.getMediaOffsetForDiscontinuity(discontinuityNumber);
20438
+ }
20439
+ getFirstSegmentTimestampOffset() {
20440
+ return this.segmentTimestampOffsetPromise ??= (async () => {
20441
+ const firstSegment = await this.getFirstSegment();
20442
+ assert(firstSegment);
20443
+ const referenceSegmentedInput = this.demuxer.getReferenceSegmentedInput();
20444
+ if (this === referenceSegmentedInput) {
20445
+ return 0;
20446
+ }
20447
+ const referenceFirstSegment = await referenceSegmentedInput.getFirstSegment();
20448
+ if (referenceFirstSegment && (this.listsAllSegments() && referenceSegmentedInput.listsAllSegments() || firstSegment.unixEpochTimestamp === firstSegment.timestamp && referenceFirstSegment.unixEpochTimestamp === referenceFirstSegment.timestamp)) {
20449
+ return 0;
20450
+ }
20451
+ const input = this.getInputForSegment(firstSegment);
20452
+ if (await this.getRawTimestampOffset(input) === null) {
20453
+ return 0;
20454
+ }
20455
+ const tracks = await input.getTracks();
20456
+ const track = tracks.find((x) => x.type === "video") ?? tracks[0];
20457
+ if (!track) {
20458
+ throw new Error("The playlist's first segment contains no tracks.");
20459
+ }
20460
+ const mediaOffset = await this.getMediaOffset(firstSegment, input);
20461
+ const offset = await track.getFirstTimestamp() + mediaOffset - firstSegment.timestamp;
20462
+ this.learnedSegmentTimestampOffset ??= offset;
20463
+ return offset;
20464
+ })();
20465
+ }
20466
+ listsAllSegments() {
20467
+ return this.segments[0].sequenceNumber === 0 || this.neverRemovesSegments;
20468
+ }
20469
+ async getRawTimestampOffset(input) {
20470
+ const format = await input.getFormat();
20471
+ if (format.supportsTimestampedMediaData) {
20472
+ return 0;
20473
+ }
20474
+ const tags = await input.getMetadataTags();
20475
+ const priv = tags.raw?.["PRIV"];
20476
+ for (const frame of toArray(priv)) {
20477
+ if (!(frame instanceof Uint8Array) || frame.length !== TIMESTAMP_PRIV_OWNER.length + 1 + 8 || textDecoder.decode(frame.subarray(0, TIMESTAMP_PRIV_OWNER.length)) !== TIMESTAMP_PRIV_OWNER || frame[TIMESTAMP_PRIV_OWNER.length] !== 0) {
20478
+ continue;
20479
+ }
20480
+ const view2 = toDataView(frame);
20481
+ const timestampHigh = view2.getUint32(TIMESTAMP_PRIV_OWNER.length + 1);
20482
+ const timestampLow = view2.getUint32(TIMESTAMP_PRIV_OWNER.length + 5);
20483
+ if (timestampHigh > 1) {
20484
+ continue;
20485
+ }
20486
+ const timestamp = 2 ** 32 * timestampHigh + timestampLow;
20487
+ const privTimestamp = normalizeWrappedTimestamp(timestamp, createTimestampWrapInfo(timestamp)) / MPEG_TS_TIMESCALE;
20488
+ return privTimestamp - await input.getFirstTimestamp();
20489
+ }
20490
+ return null;
20491
+ }
20492
+ getTimestampWrapPeriod() {
20493
+ return TIMESTAMP_MODULUS / MPEG_TS_TIMESCALE;
20494
+ }
20199
20495
  };
20200
20496
 
20201
20497
  // src/hls/hls-demuxer.ts
@@ -20210,6 +20506,7 @@ var Mediabunny = (() => {
20210
20506
  this.segmentedInputs = [];
20211
20507
  this.hasMasterPlaylist = true;
20212
20508
  this.masterPlaylistVariables = null;
20509
+ this.mediaOffsets = /* @__PURE__ */ new Map();
20213
20510
  }
20214
20511
  readMetadata() {
20215
20512
  return this.metadataPromise ??= (async () => {
@@ -20588,6 +20885,46 @@ var Mediabunny = (() => {
20588
20885
  assert(this.trackBackings);
20589
20886
  return this.trackBackings;
20590
20887
  }
20888
+ getMediaOffsetForDiscontinuity(discontinuityNumber) {
20889
+ let promise = this.mediaOffsets.get(discontinuityNumber);
20890
+ if (promise) {
20891
+ return promise;
20892
+ }
20893
+ promise = (async () => {
20894
+ const referenceSegmentedInput = this.getReferenceSegmentedInput();
20895
+ let segment = await referenceSegmentedInput.getFirstSegment();
20896
+ while (segment && segment.discontinuityNumber < discontinuityNumber) {
20897
+ segment = await referenceSegmentedInput.getNextSegment(segment, {});
20898
+ }
20899
+ if (!segment || segment.discontinuityNumber !== discontinuityNumber) {
20900
+ throw new Error(
20901
+ `The reference playlist contains no segment in discontinuity ${discontinuityNumber}, so the discontinuity can't be synchronized across tracks. If you think this is a bug, please raise an issue and include the playlist.`
20902
+ );
20903
+ }
20904
+ const input = referenceSegmentedInput.getInputForSegment(segment);
20905
+ const rawTimestampOffset = await referenceSegmentedInput.getRawTimestampOffset(input) ?? 0;
20906
+ const tracks = await input.getTracks();
20907
+ const track = tracks.find((x) => x.type === "video") ?? tracks[0];
20908
+ if (!track) {
20909
+ throw new Error("The reference playlist's segment contains no tracks.");
20910
+ }
20911
+ return segment.timestamp - (rawTimestampOffset + await track.getFirstTimestamp());
20912
+ })();
20913
+ this.mediaOffsets.set(discontinuityNumber, promise);
20914
+ return promise;
20915
+ }
20916
+ getReferenceSegmentedInput() {
20917
+ if (!this.hasMasterPlaylist) {
20918
+ return this.segmentedInputs[0];
20919
+ }
20920
+ assert(this.internalTracks);
20921
+ const candidates = this.internalTracks.filter((x) => !x.hasOnlyKeyPackets);
20922
+ const videoCandidates = candidates.filter((x) => x.info.type === "video");
20923
+ const pool = videoCandidates.length > 0 ? videoCandidates : candidates;
20924
+ const index = arrayArgmin(pool, (x) => x.peakBitrate ?? Infinity);
20925
+ assert(index !== -1);
20926
+ return this.getSegmentedInputForPath(pool[index].fullPath);
20927
+ }
20591
20928
  getSegmentedInputForPath(path) {
20592
20929
  let segmentedInput = this.segmentedInputs.find((x) => x.path === path);
20593
20930
  if (segmentedInput) {
@@ -23923,7 +24260,7 @@ var Mediabunny = (() => {
23923
24260
  throw new TypeError(`Invalid audio codec '${config.codec}'. Must be one of: ${AUDIO_CODECS.join(", ")}.`);
23924
24261
  }
23925
24262
  const bitrate = config.bitrate;
23926
- if (config.quality === void 0 && bitrate === void 0 && !(PCM_AUDIO_CODECS.includes(config.codec) || config.codec === "flac")) {
24263
+ if (config.quality === void 0 && bitrate === void 0 && !(PCM_AUDIO_CODECS.includes(config.codec) || config.codec === "flac" || config.codec === "truehd")) {
23927
24264
  throw new TypeError("config.quality must be provided for compressed audio codecs.");
23928
24265
  }
23929
24266
  if (config.quality !== void 0 && bitrate !== void 0) {
@@ -24104,7 +24441,7 @@ var Mediabunny = (() => {
24104
24441
  }
24105
24442
  /** @internal */
24106
24443
  _toAudioBitrate(codec) {
24107
- if (PCM_AUDIO_CODECS.includes(codec) || codec === "flac") {
24444
+ if (PCM_AUDIO_CODECS.includes(codec) || codec === "flac" || codec === "truehd") {
24108
24445
  return void 0;
24109
24446
  }
24110
24447
  if (this._bitrate !== void 0) {
@@ -24952,7 +25289,12 @@ var Mediabunny = (() => {
24952
25289
  });
24953
25290
  decoder.onDequeue = () => onQueueDequeue();
24954
25291
  const packetSink = this._createPacketSink();
24955
- const keyPacket = await packetSink.getKeyPacket(startTimestamp, packetRetrievalOptions) ?? await packetSink.getFirstKeyPacket(packetRetrievalOptions);
25292
+ const preRollDuration = await this._getPreRollDuration();
25293
+ const startPacket = await packetSink.getPacket(startTimestamp, packetRetrievalOptions);
25294
+ const keyPacket = await packetSink.getKeyPacket(
25295
+ (startPacket?.timestamp ?? startTimestamp) - preRollDuration,
25296
+ packetRetrievalOptions
25297
+ ) ?? await packetSink.getFirstKeyPacket(packetRetrievalOptions);
24956
25298
  let currentPacket = keyPacket;
24957
25299
  const endPacket = void 0;
24958
25300
  const packets = packetSink.packets(keyPacket ?? void 0, endPacket, packetRetrievalOptions);
@@ -25056,6 +25398,16 @@ var Mediabunny = (() => {
25056
25398
  onQueueNotEmpty();
25057
25399
  ({ promise: queueNotEmpty, resolve: onQueueNotEmpty } = promiseWithResolvers());
25058
25400
  };
25401
+ let heldSample = null;
25402
+ const emitHeldSample = (count) => {
25403
+ for (let i = 0; i < count; i++) {
25404
+ pushToQueue(heldSample && (i < count - 1 ? heldSample.clone() : heldSample));
25405
+ }
25406
+ if (count === 0) {
25407
+ heldSample?.close();
25408
+ }
25409
+ heldSample = null;
25410
+ };
25059
25411
  const retrievalOptions = {
25060
25412
  ...options,
25061
25413
  verifyKeyPackets: true,
@@ -25068,18 +25420,13 @@ var Mediabunny = (() => {
25068
25420
  sample.close();
25069
25421
  return;
25070
25422
  }
25071
- let sampleUses = 0;
25072
- while (timestampsOfInterest.length > 0 && sample.timestamp - timestampsOfInterest[0] > -1e-10) {
25073
- sampleUses++;
25423
+ let heldSampleUses = 0;
25424
+ while (timestampsOfInterest.length > 0 && sample.timestamp - timestampsOfInterest[0] > 1e-10) {
25425
+ heldSampleUses++;
25074
25426
  timestampsOfInterest.shift();
25075
25427
  }
25076
- if (sampleUses > 0) {
25077
- for (let i = 0; i < sampleUses; i++) {
25078
- pushToQueue(i < sampleUses - 1 ? sample.clone() : sample);
25079
- }
25080
- } else {
25081
- sample.close();
25082
- }
25428
+ emitHeldSample(heldSampleUses);
25429
+ heldSample = sample;
25083
25430
  }, (error) => {
25084
25431
  if (!hasOutOfBandError) {
25085
25432
  outOfBandError = error;
@@ -25089,14 +25436,20 @@ var Mediabunny = (() => {
25089
25436
  });
25090
25437
  decoder.onDequeue = () => onQueueDequeue();
25091
25438
  const packetSink = this._createPacketSink();
25439
+ const preRollDuration = await this._getPreRollDuration();
25092
25440
  let lastPacket = null;
25441
+ let lastTimestamp = -Infinity;
25093
25442
  let lastKeyPacket = null;
25443
+ let lastDecodedPacket = null;
25094
25444
  let maxSequenceNumber = -1;
25095
25445
  const decodePackets = async () => {
25096
25446
  assert(lastKeyPacket);
25097
25447
  assert(decoder);
25098
- let currentPacket = lastKeyPacket;
25099
- decoder.decode(currentPacket);
25448
+ let currentPacket = lastDecodedPacket;
25449
+ if (!currentPacket) {
25450
+ currentPacket = lastKeyPacket;
25451
+ decoder.decode(currentPacket);
25452
+ }
25100
25453
  while (currentPacket.sequenceNumber < maxSequenceNumber) {
25101
25454
  while (sampleQueue.length + decoder.getDecodeQueueSize() >= MAX_QUEUE_SIZE && !terminated) {
25102
25455
  ({ promise: queueDequeue, resolve: onQueueDequeue } = promiseWithResolvers());
@@ -25112,14 +25465,12 @@ var Mediabunny = (() => {
25112
25465
  decoder.decode(nextPacket);
25113
25466
  currentPacket = nextPacket;
25114
25467
  }
25115
- maxSequenceNumber = -1;
25468
+ lastDecodedPacket = currentPacket;
25116
25469
  };
25117
25470
  const flushDecoder = async () => {
25118
25471
  assert(decoder);
25119
25472
  await decoder.flush();
25120
- for (let i = 0; i < timestampsOfInterest.length; i++) {
25121
- pushToQueue(null);
25122
- }
25473
+ emitHeldSample(timestampsOfInterest.length);
25123
25474
  timestampsOfInterest.length = 0;
25124
25475
  };
25125
25476
  for await (const timestamp of timestampIterator) {
@@ -25128,29 +25479,39 @@ var Mediabunny = (() => {
25128
25479
  break;
25129
25480
  }
25130
25481
  const targetPacket = await packetSink.getPacket(timestamp, retrievalOptions);
25131
- const keyPacket = targetPacket && await packetSink.getKeyPacket(timestamp, retrievalOptions);
25132
- if (!keyPacket) {
25133
- if (maxSequenceNumber !== -1) {
25134
- await decodePackets();
25482
+ let keyPacket = targetPacket && await packetSink.getKeyPacket(
25483
+ targetPacket.timestamp - preRollDuration,
25484
+ retrievalOptions
25485
+ );
25486
+ if (targetPacket && !keyPacket) {
25487
+ const firstKeyPacket = await packetSink.getFirstKeyPacket(retrievalOptions);
25488
+ if (firstKeyPacket && firstKeyPacket.timestamp <= targetPacket.timestamp) {
25489
+ keyPacket = firstKeyPacket;
25490
+ }
25491
+ }
25492
+ if (!targetPacket || !keyPacket) {
25493
+ if (lastPacket) {
25135
25494
  await flushDecoder();
25136
25495
  }
25137
25496
  pushToQueue(null);
25138
25497
  lastPacket = null;
25139
25498
  continue;
25140
25499
  }
25141
- if (lastPacket && (keyPacket.sequenceNumber !== lastKeyPacket.sequenceNumber || targetPacket.timestamp < lastPacket.timestamp)) {
25142
- await decodePackets();
25143
- await flushDecoder();
25500
+ if (!lastPacket || keyPacket.sequenceNumber > maxSequenceNumber + 1 || timestamp < lastTimestamp) {
25501
+ if (lastPacket) {
25502
+ await flushDecoder();
25503
+ }
25504
+ lastKeyPacket = keyPacket;
25505
+ lastDecodedPacket = null;
25506
+ maxSequenceNumber = -1;
25144
25507
  }
25145
- timestampsOfInterest.push(targetPacket.timestamp);
25508
+ timestampsOfInterest.push(timestamp);
25146
25509
  maxSequenceNumber = Math.max(targetPacket.sequenceNumber, maxSequenceNumber);
25147
25510
  lastPacket = targetPacket;
25148
- lastKeyPacket = keyPacket;
25511
+ lastTimestamp = timestamp;
25512
+ await decodePackets();
25149
25513
  }
25150
25514
  if (!terminated && !this._track.input._disposed) {
25151
- if (maxSequenceNumber !== -1) {
25152
- await decodePackets();
25153
- }
25154
25515
  await flushDecoder();
25155
25516
  }
25156
25517
  decoderIsFlushed = true;
@@ -25166,6 +25527,8 @@ var Mediabunny = (() => {
25166
25527
  });
25167
25528
  const track = this._track;
25168
25529
  const closeSamples = () => {
25530
+ heldSample?.close();
25531
+ heldSample = null;
25169
25532
  for (const sample of sampleQueue) {
25170
25533
  sample?.close();
25171
25534
  }
@@ -25245,6 +25608,9 @@ var Mediabunny = (() => {
25245
25608
  // For HEVC stuff
25246
25609
  this.finalSamples = [];
25247
25610
  this.mergeAlphaPromises = [];
25611
+ this.flushing = false;
25612
+ // Needed for a Chromium for Android workaround
25613
+ this.frameCopyContext = null;
25248
25614
  const MatchingCustomDecoder = customVideoDecoders.find((x) => x.supports(codec, decoderConfig));
25249
25615
  if (MatchingCustomDecoder) {
25250
25616
  this.customDecoder = new MatchingCustomDecoder();
@@ -25310,7 +25676,7 @@ var Mediabunny = (() => {
25310
25676
  this.decoder = new VideoDecoder({
25311
25677
  output: (frame) => {
25312
25678
  try {
25313
- colorHandler(frame);
25679
+ colorHandler(this.copyFrameIfNeeded(frame));
25314
25680
  } catch (error) {
25315
25681
  this.onError(error);
25316
25682
  }
@@ -25434,7 +25800,7 @@ var Mediabunny = (() => {
25434
25800
  this.alphaDecoder = new VideoDecoder({
25435
25801
  output: (frame) => {
25436
25802
  try {
25437
- alphaHandler(frame);
25803
+ alphaHandler(this.copyFrameIfNeeded(frame));
25438
25804
  } catch (error) {
25439
25805
  this.onError(error);
25440
25806
  }
@@ -25550,15 +25916,60 @@ var Mediabunny = (() => {
25550
25916
  resolver.resolve();
25551
25917
  }
25552
25918
  }
25919
+ /**
25920
+ * This is a workaround for https://issues.chromium.org/issues/579043455. It circumvents the problem by instantly
25921
+ * drawing a frame to a new region of GPU memory (a canvas), which we know for certain won't get fucked up by
25922
+ * other draws.
25923
+ * Also see: https://github.com/Vanilagy/mediabunny/issues/573
25924
+ */
25925
+ copyFrameIfNeeded(frame) {
25926
+ if (!isChromium() || !isAndroid()) {
25927
+ return frame;
25928
+ }
25929
+ const visibleRect = frame.visibleRect;
25930
+ const width = visibleRect.width;
25931
+ const height = visibleRect.height;
25932
+ if (!this.frameCopyContext) {
25933
+ let context;
25934
+ if (typeof OffscreenCanvas !== "undefined") {
25935
+ context = new OffscreenCanvas(width, height).getContext("2d", { alpha: false });
25936
+ } else {
25937
+ context = document.createElement("canvas").getContext("2d", { alpha: false });
25938
+ }
25939
+ if (!context) {
25940
+ throw new Error("The '2d' canvas context is required to decode video on Chromium for Android.");
25941
+ }
25942
+ this.frameCopyContext = context;
25943
+ }
25944
+ const canvas = this.frameCopyContext.canvas;
25945
+ if (canvas.width !== width || canvas.height !== height) {
25946
+ canvas.width = width;
25947
+ canvas.height = height;
25948
+ }
25949
+ this.frameCopyContext.drawImage(frame, 0, 0, width, height);
25950
+ if (this.flushing) {
25951
+ this.frameCopyContext.getImageData(0, 0, 1, 1);
25952
+ }
25953
+ const copy = new VideoFrame(canvas, {
25954
+ timestamp: frame.timestamp,
25955
+ duration: frame.duration ?? void 0,
25956
+ displayWidth: frame.displayWidth,
25957
+ displayHeight: frame.displayHeight
25958
+ });
25959
+ frame.close();
25960
+ return copy;
25961
+ }
25553
25962
  async flush() {
25554
25963
  if (this.customDecoder) {
25555
25964
  await this.customDecoderCallSerializer.call(() => this.customDecoder.flush());
25556
25965
  } else {
25557
25966
  assert(this.decoder);
25967
+ this.flushing = true;
25558
25968
  await Promise.all([
25559
25969
  this.decoder.flush(),
25560
25970
  this.alphaDecoder?.flush()
25561
25971
  ]);
25972
+ this.flushing = false;
25562
25973
  await Promise.all(this.mergeAlphaPromises);
25563
25974
  this.colorQueue.forEach((x) => x.close());
25564
25975
  this.colorQueue.length = 0;
@@ -25884,6 +26295,10 @@ var Mediabunny = (() => {
25884
26295
  _createPacketSink() {
25885
26296
  return new EncodedPacketSink(this._track);
25886
26297
  }
26298
+ /** @internal */
26299
+ async _getPreRollDuration() {
26300
+ return 0;
26301
+ }
25887
26302
  /**
25888
26303
  * Retrieves the video sample (frame) corresponding to the given timestamp, in seconds. More specifically, returns
25889
26304
  * the last video sample (in presentation order) with a start timestamp less than or equal to the given timestamp.
@@ -26120,11 +26535,11 @@ var Mediabunny = (() => {
26120
26535
  // Chromium does not respect negative packet timestamps, so we must do the fixin' ourselves
26121
26536
  this.expectedFirstTimestamp = null;
26122
26537
  this.timestampOffset = 0;
26538
+ const opusPreSkip = codec === "opus" && decoderConfig.description ? parseOpusIdentificationHeader(toUint8Array(decoderConfig.description)).preSkip / OPUS_SAMPLE_RATE : 0;
26123
26539
  const sampleHandler = (sample) => {
26124
26540
  let sampleTimestamp = sample.timestamp;
26125
26541
  if (this.expectedFirstTimestamp !== null && this.currentTimestamp === null) {
26126
- this.timestampOffset = this.expectedFirstTimestamp - sampleTimestamp;
26127
- ;
26542
+ this.timestampOffset = this.expectedFirstTimestamp + opusPreSkip - sampleTimestamp;
26128
26543
  }
26129
26544
  sampleTimestamp += this.timestampOffset;
26130
26545
  if (this.currentTimestamp === null || Math.abs(sampleTimestamp - this.currentTimestamp) >= sample.duration) {
@@ -26433,6 +26848,12 @@ var Mediabunny = (() => {
26433
26848
  _createPacketSink() {
26434
26849
  return new EncodedPacketSink(this._track);
26435
26850
  }
26851
+ /** @internal */
26852
+ async _getPreRollDuration() {
26853
+ const preRollDuration = await this._track.getPreRollDuration();
26854
+ assert(preRollDuration !== null);
26855
+ return preRollDuration;
26856
+ }
26436
26857
  /**
26437
26858
  * Retrieves the audio sample corresponding to the given timestamp, in seconds. More specifically, returns
26438
26859
  * the last audio sample (in presentation order) with a start timestamp less than or equal to the given timestamp.
@@ -27238,7 +27659,8 @@ var Mediabunny = (() => {
27238
27659
  return requireSync(this._backing.getCodec(), "codec", "getCodec");
27239
27660
  }
27240
27661
  async hasOnlyKeyPackets() {
27241
- return await this._backing.getHasOnlyKeyPackets?.() ?? true;
27662
+ const codec = await this._backing.getCodec();
27663
+ return await this._backing.getHasOnlyKeyPackets?.() ?? (codec === null || !AUDIO_CODECS_WITH_DELTA_PACKETS.includes(codec));
27242
27664
  }
27243
27665
  /** Returns the number of audio channels in the track. */
27244
27666
  async getNumberOfChannels() {
@@ -27278,6 +27700,20 @@ var Mediabunny = (() => {
27278
27700
  const decoderConfig = await this._backing.getDecoderConfig();
27279
27701
  return decoderConfig?.codec ?? null;
27280
27702
  }
27703
+ /**
27704
+ * Returns the decoder pre-roll duration for this track. It specifies how far ahead of any given timestamp,
27705
+ * in seconds, decoding must start so that the audio at that timestamp comes out correctly and the codec state has
27706
+ * properly converged. Returns `null` if the track's codec is unknown.
27707
+ */
27708
+ async getPreRollDuration() {
27709
+ const codec = await this._backing.getCodec();
27710
+ if (codec === null) {
27711
+ return null;
27712
+ }
27713
+ const decoderConfig = await this._backing.getDecoderConfig();
27714
+ assert(decoderConfig);
27715
+ return getAudioPreRollDuration(codec, decoderConfig);
27716
+ }
27281
27717
  async canDecode() {
27282
27718
  try {
27283
27719
  const decoderConfig = await this._backing.getDecoderConfig();
@@ -27307,10 +27743,14 @@ var Mediabunny = (() => {
27307
27743
  if (!(packet instanceof EncodedPacket)) {
27308
27744
  throw new TypeError("packet must be an EncodedPacket.");
27309
27745
  }
27310
- if (await this.getCodec() === null) {
27746
+ if (packet.isMetadataOnly) {
27747
+ throw new TypeError("packet must not be metadata-only to determine its type.");
27748
+ }
27749
+ const codec = await this.getCodec();
27750
+ if (codec === null) {
27311
27751
  return null;
27312
27752
  }
27313
- return "key";
27753
+ return determineAudioPacketType(codec, packet.data);
27314
27754
  }
27315
27755
  };
27316
27756
  var asc = (value) => {
@@ -28598,7 +29038,15 @@ var Mediabunny = (() => {
28598
29038
  } else if (frame.id[0] === "T") {
28599
29039
  tags.raw[frame.id] ??= reader.readId3V2EncodingAndText(frameEndPos);
28600
29040
  } else {
28601
- tags.raw[frame.id] ??= reader.readBytes(frameEndPos - reader.pos);
29041
+ const bytes3 = reader.readBytes(frameEndPos - reader.pos);
29042
+ const existing = tags.raw[frame.id];
29043
+ if (existing instanceof Uint8Array) {
29044
+ tags.raw[frame.id] = [existing, bytes3];
29045
+ } else if (Array.isArray(existing)) {
29046
+ existing.push(bytes3);
29047
+ } else {
29048
+ tags.raw[frame.id] ??= bytes3;
29049
+ }
28602
29050
  }
28603
29051
  reader.pos = frameStartPos;
28604
29052
  switch (frame.id) {
@@ -29114,8 +29562,9 @@ var Mediabunny = (() => {
29114
29562
  if (value == null || key.length !== 4 || writtenTags.has(key)) {
29115
29563
  continue;
29116
29564
  }
29117
- let bytes2;
29565
+ let frames;
29118
29566
  if (typeof value === "string") {
29567
+ let bytes2;
29119
29568
  const useIso88591 = isIso88591Compatible(value);
29120
29569
  if (useIso88591) {
29121
29570
  bytes2 = new Uint8Array(value.length + 2);
@@ -29129,8 +29578,11 @@ var Mediabunny = (() => {
29129
29578
  bytes2[0] = 3 /* UTF_8 */;
29130
29579
  bytes2.set(encoded, 1);
29131
29580
  }
29581
+ frames = [bytes2];
29132
29582
  } else if (value instanceof Uint8Array) {
29133
- bytes2 = value;
29583
+ frames = [value];
29584
+ } else if (Array.isArray(value) && value.every((x) => x instanceof Uint8Array)) {
29585
+ frames = value;
29134
29586
  } else if (key === "TXXX" && isRecordStringString(value)) {
29135
29587
  for (const description in value) {
29136
29588
  const frameValue = value[description];
@@ -29158,10 +29610,12 @@ var Mediabunny = (() => {
29158
29610
  } else {
29159
29611
  continue;
29160
29612
  }
29161
- this.writeAscii(key);
29162
- this.writeSynchsafeU32(bytes2.byteLength);
29163
- this.writeU16(0);
29164
- this.writer.write(bytes2);
29613
+ for (const bytes2 of frames) {
29614
+ this.writeAscii(key);
29615
+ this.writeSynchsafeU32(bytes2.byteLength);
29616
+ this.writeU16(0);
29617
+ this.writer.write(bytes2);
29618
+ }
29165
29619
  }
29166
29620
  }
29167
29621
  const framesEndPos = this.writer.getPos();
@@ -30240,7 +30694,8 @@ var Mediabunny = (() => {
30240
30694
  stsc(trackData),
30241
30695
  stsz(trackData),
30242
30696
  stco(trackData),
30243
- stss(trackData)
30697
+ stss(trackData),
30698
+ ...sgpdAndSbgp(trackData.samples, false)
30244
30699
  ]);
30245
30700
  };
30246
30701
  var stsd = (trackData) => {
@@ -30406,7 +30861,7 @@ var Mediabunny = (() => {
30406
30861
  version = 1;
30407
30862
  }
30408
30863
  }
30409
- if (trackData.muxer.isQuickTime) {
30864
+ if (trackData.muxer.isQuickTime && trackData.track.source._codec !== "truehd") {
30410
30865
  version = 1;
30411
30866
  }
30412
30867
  if (version === 0) {
@@ -30429,10 +30884,12 @@ var Mediabunny = (() => {
30429
30884
  // Compression ID
30430
30885
  u16(0),
30431
30886
  // Packet size
30432
- u16(trackData.info.sampleRate < 2 ** 16 ? trackData.info.sampleRate : 0),
30433
- // Sample rate (upper)
30434
- u16(0)
30435
- // Sample rate (lower)
30887
+ trackData.track.source._codec === "truehd" ? u32(trackData.info.sampleRate) : [
30888
+ u16(trackData.info.sampleRate < 2 ** 16 ? trackData.info.sampleRate : 0),
30889
+ // Sample rate (upper)
30890
+ u16(0)
30891
+ // Sample rate (lower)
30892
+ ]
30436
30893
  ];
30437
30894
  } else {
30438
30895
  const compressionId = isPcmCodec ? 0 : -2;
@@ -30578,7 +31035,7 @@ var Mediabunny = (() => {
30578
31035
  };
30579
31036
  var dOps = (trackData) => {
30580
31037
  let outputChannelCount = trackData.info.numberOfChannels;
30581
- let preSkip = 3840;
31038
+ let preSkip = 312;
30582
31039
  let inputSampleRate = trackData.info.sampleRate;
30583
31040
  let outputGain = 0;
30584
31041
  let channelMappingFamily = 0;
@@ -30698,6 +31155,26 @@ var Mediabunny = (() => {
30698
31155
  }
30699
31156
  return box("ddts", [...buildDtsSpecificBox(frameInfo)]);
30700
31157
  };
31158
+ var dmlp = (trackData) => {
31159
+ assert(trackData.info.primingPacket);
31160
+ const data = trackData.info.primingPacket.data;
31161
+ if (determineAudioPacketType("truehd", data) !== "key") {
31162
+ throw new Error(
31163
+ "Couldn't extract TrueHD stream info from the audio packet. Ensure the first packet is an access unit carrying a major sync."
31164
+ );
31165
+ }
31166
+ const view2 = toDataView(data);
31167
+ const formatInfo = view2.getUint32(8);
31168
+ const peakDataRate = view2.getUint16(18) & 32767;
31169
+ return box("dmlp", [
31170
+ u32(formatInfo),
31171
+ // Format info
31172
+ u16(peakDataRate << 1),
31173
+ // Peak data rate (15 bits) + reserved (1 bit)
31174
+ u32(0)
31175
+ // Reserved
31176
+ ]);
31177
+ };
30701
31178
  var subtitleSampleDescription = (compressionType, trackData) => box(compressionType, [
30702
31179
  Array(6).fill(0),
30703
31180
  // Reserved
@@ -30835,6 +31312,55 @@ var Mediabunny = (() => {
30835
31312
  // Composition end time
30836
31313
  ]);
30837
31314
  };
31315
+ var sgpdAndSbgp = (samples, inTrackFragment) => {
31316
+ const entries = [];
31317
+ for (const sample of samples) {
31318
+ if (entries.length === 0) {
31319
+ entries.push({
31320
+ sampleCount: 1,
31321
+ prerollSamples: sample.prerollSamples
31322
+ });
31323
+ } else {
31324
+ const lastEntry = entries[entries.length - 1];
31325
+ if (lastEntry.prerollSamples === sample.prerollSamples) {
31326
+ lastEntry.sampleCount++;
31327
+ } else {
31328
+ entries.push({
31329
+ sampleCount: 1,
31330
+ prerollSamples: sample.prerollSamples
31331
+ });
31332
+ }
31333
+ }
31334
+ }
31335
+ const rollEntries = entries.filter((x) => x.prerollSamples !== 0);
31336
+ if (rollEntries.length === 0) {
31337
+ return [];
31338
+ }
31339
+ let nextGroupIndex = inTrackFragment ? 65537 : 1;
31340
+ return [
31341
+ fullBox("sgpd", 1, 0, [
31342
+ ascii("roll"),
31343
+ // Grouping type
31344
+ u32(2),
31345
+ // Default length
31346
+ u32(rollEntries.length),
31347
+ // Entry count
31348
+ ...rollEntries.map((x) => i16(x.prerollSamples))
31349
+ ]),
31350
+ fullBox("sbgp", 0, 0, [
31351
+ ascii("roll"),
31352
+ // Grouping type
31353
+ u32(entries.length),
31354
+ // Entry count
31355
+ ...entries.map((x) => [
31356
+ u32(x.sampleCount),
31357
+ // Sample count
31358
+ u32(x.prerollSamples !== 0 ? nextGroupIndex++ : 0)
31359
+ // Samples with no preroll belong to no group
31360
+ ])
31361
+ ])
31362
+ ];
31363
+ };
30838
31364
  var mvex = (trackDatas) => {
30839
31365
  return box("mvex", void 0, trackDatas.map(trex));
30840
31366
  };
@@ -30882,7 +31408,8 @@ var Mediabunny = (() => {
30882
31408
  return box("traf", void 0, [
30883
31409
  tfhd(trackData),
30884
31410
  tfdt(trackData),
30885
- trun(trackData)
31411
+ trun(trackData),
31412
+ ...sgpdAndSbgp(trackData.currentChunk.samples, true)
30886
31413
  ]);
30887
31414
  };
30888
31415
  var tfhd = (trackData) => {
@@ -31400,6 +31927,8 @@ var Mediabunny = (() => {
31400
31927
  return "ec-3";
31401
31928
  case "dts":
31402
31929
  return fullCodecString;
31930
+ case "truehd":
31931
+ return "mlpa";
31403
31932
  }
31404
31933
  if (isQuickTime) {
31405
31934
  switch (codec) {
@@ -31467,6 +31996,8 @@ var Mediabunny = (() => {
31467
31996
  return dec3;
31468
31997
  case "dts":
31469
31998
  return ddts;
31999
+ case "truehd":
32000
+ return dmlp;
31470
32001
  }
31471
32002
  if (isQuickTime) {
31472
32003
  switch (codec) {
@@ -31698,6 +32229,8 @@ var Mediabunny = (() => {
31698
32229
  }
31699
32230
  /** @internal */
31700
32231
  _ensureSize(size) {
32232
+ assert(this._buffer);
32233
+ assert(this._bytes);
31701
32234
  let newLength = this._buffer.byteLength;
31702
32235
  while (newLength < size) newLength *= 2;
31703
32236
  if (newLength === this._buffer.byteLength) return;
@@ -31721,6 +32254,7 @@ var Mediabunny = (() => {
31721
32254
  }
31722
32255
  /** @internal */
31723
32256
  _write(data, pos) {
32257
+ assert(this._bytes);
31724
32258
  this._ensureSize(pos + data.byteLength);
31725
32259
  this._bytes.set(data, pos);
31726
32260
  this._maxPos = Math.max(this._maxPos, pos + data.byteLength);
@@ -31731,7 +32265,14 @@ var Mediabunny = (() => {
31731
32265
  }
31732
32266
  /** @internal */
31733
32267
  async _finalize() {
31734
- this.buffer = this._buffer.slice(0, this._maxPos);
32268
+ assert(this._buffer);
32269
+ if ("transferToFixedLength" in this._buffer) {
32270
+ this.buffer = this._buffer.transferToFixedLength(this._maxPos);
32271
+ } else {
32272
+ this.buffer = this._buffer.slice(0, this._maxPos);
32273
+ }
32274
+ this._buffer = null;
32275
+ this._bytes = null;
31735
32276
  if (this._options.onFinalize) {
31736
32277
  await this._options.onFinalize(this.buffer);
31737
32278
  }
@@ -31742,6 +32283,7 @@ var Mediabunny = (() => {
31742
32283
  }
31743
32284
  /** @internal */
31744
32285
  _getSlice(start, end) {
32286
+ assert(this._bytes);
31745
32287
  return this._bytes.slice(start, end);
31746
32288
  }
31747
32289
  };
@@ -32153,6 +32695,7 @@ var Mediabunny = (() => {
32153
32695
  // src/isobmff/isobmff-muxer.ts
32154
32696
  var GLOBAL_TIMESCALE = 57600;
32155
32697
  var TIMESTAMP_OFFSET = 2082844800;
32698
+ var MIN_CHUNK_DURATION = 0.5;
32156
32699
  var getTrackMetadata = (trackData) => {
32157
32700
  const metadata = {};
32158
32701
  const track = trackData.track;
@@ -32448,6 +32991,9 @@ var Mediabunny = (() => {
32448
32991
  if (track.source._codec === "dts") {
32449
32992
  throw new Error("DTS requires a priming packet.");
32450
32993
  }
32994
+ if (track.source._codec === "truehd") {
32995
+ throw new Error("TrueHD requires a priming packet.");
32996
+ }
32451
32997
  }
32452
32998
  const newTrackData = {
32453
32999
  muxer: this,
@@ -32460,7 +33006,12 @@ var Mediabunny = (() => {
32460
33006
  requiresPcmTransformation: !this.isFragmented && PCM_AUDIO_CODECS.includes(track.source._codec),
32461
33007
  expectedNextPcmPacketTimestamp: null,
32462
33008
  requiresAdtsStripping,
32463
- primingPacket: packet
33009
+ primingPacket: packet,
33010
+ preroll: {
33011
+ packetCount: 0,
33012
+ accumulatedAudioSamples: 0,
33013
+ audioSampleDurationHistory: []
33014
+ }
32464
33015
  },
32465
33016
  timescale: decoderConfig.sampleRate,
32466
33017
  samples: [],
@@ -32552,7 +33103,8 @@ var Mediabunny = (() => {
32552
33103
  packetData,
32553
33104
  packet.timestamp,
32554
33105
  packet.duration,
32555
- packet.type
33106
+ packet.type,
33107
+ 0
32556
33108
  );
32557
33109
  await this.registerSample(trackData, internalSample);
32558
33110
  } finally {
@@ -32600,12 +33152,31 @@ var Mediabunny = (() => {
32600
33152
  }
32601
33153
  trackData.info.expectedNextPcmPacketTimestamp = timestamp + duration;
32602
33154
  }
33155
+ const { preroll } = trackData.info;
33156
+ let prerollSamples = 0;
33157
+ if (track.source._codec === "aac" || track.source._codec === "vorbis") {
33158
+ prerollSamples = -Math.min(1, preroll.packetCount);
33159
+ } else if (track.source._codec === "mp3") {
33160
+ prerollSamples = -Math.min(2, preroll.packetCount);
33161
+ } else if (track.source._codec === "opus") {
33162
+ const OPUS_PREROLL_SAMPLES = Math.round(OPUS_PRE_ROLL_DURATION * OPUS_SAMPLE_RATE);
33163
+ prerollSamples = -preroll.audioSampleDurationHistory.length;
33164
+ const toc = parseOpusTocByte(packetData);
33165
+ preroll.accumulatedAudioSamples += toc.durationInSamples;
33166
+ preroll.audioSampleDurationHistory.push(toc.durationInSamples);
33167
+ while (preroll.accumulatedAudioSamples - preroll.audioSampleDurationHistory[0] >= OPUS_PREROLL_SAMPLES) {
33168
+ preroll.accumulatedAudioSamples -= preroll.audioSampleDurationHistory.shift();
33169
+ assert(preroll.audioSampleDurationHistory.length > 0);
33170
+ }
33171
+ }
33172
+ preroll.packetCount++;
32603
33173
  const internalSample = this.createSampleForTrack(
32604
33174
  trackData,
32605
33175
  packetData,
32606
33176
  timestamp,
32607
33177
  duration,
32608
- packet.type
33178
+ packet.type,
33179
+ prerollSamples
32609
33180
  );
32610
33181
  await this.registerSample(trackData, internalSample);
32611
33182
  } finally {
@@ -32626,7 +33197,8 @@ var Mediabunny = (() => {
32626
33197
  new Uint8Array(data.buffer),
32627
33198
  timestamp,
32628
33199
  duration,
32629
- "key"
33200
+ "key",
33201
+ 0
32630
33202
  );
32631
33203
  await this.registerSample(trackData, paddingSample);
32632
33204
  }
@@ -32672,7 +33244,8 @@ var Mediabunny = (() => {
32672
33244
  body2,
32673
33245
  trackData.lastCueEndTimestamp,
32674
33246
  sampleStart - trackData.lastCueEndTimestamp,
32675
- "key"
33247
+ "key",
33248
+ 0
32676
33249
  );
32677
33250
  await this.registerSample(trackData, sample2);
32678
33251
  trackData.lastCueEndTimestamp = sampleStart;
@@ -32708,12 +33281,12 @@ var Mediabunny = (() => {
32708
33281
  }
32709
33282
  }
32710
33283
  const body = this.auxTarget._getSlice(0, this.auxWriter.getPos());
32711
- const sample = this.createSampleForTrack(trackData, body, sampleStart, sampleEnd - sampleStart, "key");
33284
+ const sample = this.createSampleForTrack(trackData, body, sampleStart, sampleEnd - sampleStart, "key", 0);
32712
33285
  await this.registerSample(trackData, sample);
32713
33286
  trackData.lastCueEndTimestamp = sampleEnd;
32714
33287
  }
32715
33288
  }
32716
- createSampleForTrack(trackData, data, timestamp, duration, type) {
33289
+ createSampleForTrack(trackData, data, timestamp, duration, type, prerollSamples) {
32717
33290
  const sample = {
32718
33291
  timestamp,
32719
33292
  decodeTimestamp: timestamp,
@@ -32722,8 +33295,9 @@ var Mediabunny = (() => {
32722
33295
  data,
32723
33296
  size: data.byteLength,
32724
33297
  type,
32725
- timescaleUnitsToNextSample: intoTimescale(duration, trackData.timescale)
33298
+ timescaleUnitsToNextSample: intoTimescale(duration, trackData.timescale),
32726
33299
  // Will be refined
33300
+ prerollSamples
32727
33301
  };
32728
33302
  return sample;
32729
33303
  }
@@ -32837,14 +33411,8 @@ var Mediabunny = (() => {
32837
33411
  this.processTimestamps(trackData, sample);
32838
33412
  }
32839
33413
  trackData.timestampProcessingQueue.push(sample);
32840
- if (this.isFragmented) {
32841
- trackData.sampleQueue.push(sample);
32842
- await this.interleaveSamples();
32843
- } else if (this.fastStart === "reserve") {
32844
- await this.registerSampleFastStartReserve(trackData, sample);
32845
- } else {
32846
- await this.addSampleToTrack(trackData, sample);
32847
- }
33414
+ trackData.sampleQueue.push(sample);
33415
+ await this.interleaveSamples();
32848
33416
  }
32849
33417
  async addSampleToTrack(trackData, sample) {
32850
33418
  if (!this.isFragmented) {
@@ -32884,12 +33452,15 @@ var Mediabunny = (() => {
32884
33452
  await this.finalizeFragment();
32885
33453
  }
32886
33454
  } else {
32887
- beginNewChunk = currentChunkDuration >= 0.5;
33455
+ beginNewChunk = currentChunkDuration >= MIN_CHUNK_DURATION;
32888
33456
  }
32889
33457
  }
32890
33458
  if (beginNewChunk) {
32891
- if (trackData.currentChunk) {
32892
- await this.finalizeCurrentChunk(trackData);
33459
+ if (!this.isFragmented) {
33460
+ const tracksToFinalize = this.trackDatas.filter((x) => x.currentChunk && sample.timestamp - x.currentChunk.startTimestamp >= MIN_CHUNK_DURATION).sort((a, b) => a.currentChunk.startTimestamp - b.currentChunk.startTimestamp);
33461
+ for (const otherTrackData of tracksToFinalize) {
33462
+ await this.finalizeCurrentChunk(otherTrackData);
33463
+ }
32893
33464
  }
32894
33465
  trackData.currentChunk = {
32895
33466
  startTimestamp: sample.timestamp,
@@ -32910,12 +33481,14 @@ var Mediabunny = (() => {
32910
33481
  async finalizeCurrentChunk(trackData) {
32911
33482
  assert(!this.isFragmented);
32912
33483
  assert(this.writer);
32913
- if (!trackData.currentChunk) return;
32914
- trackData.finalizedChunks.push(trackData.currentChunk);
32915
- this.finalizedChunks.push(trackData.currentChunk);
32916
- let sampleCount = trackData.currentChunk.samples.length;
33484
+ const chunk = trackData.currentChunk;
33485
+ assert(chunk);
33486
+ trackData.currentChunk = null;
33487
+ trackData.finalizedChunks.push(chunk);
33488
+ this.finalizedChunks.push(chunk);
33489
+ let sampleCount = chunk.samples.length;
32917
33490
  if (trackData.type === "audio" && trackData.info.requiresPcmTransformation) {
32918
- sampleCount = trackData.currentChunk.samples.reduce((acc, sample) => acc + intoTimescale(sample.duration, trackData.timescale), 0);
33491
+ sampleCount = chunk.samples.reduce((acc, sample) => acc + intoTimescale(sample.duration, trackData.timescale), 0);
32919
33492
  }
32920
33493
  if (trackData.compactlyCodedChunkTable.length === 0 || last(trackData.compactlyCodedChunkTable).samplesPerChunk !== sampleCount) {
32921
33494
  trackData.compactlyCodedChunkTable.push({
@@ -32925,11 +33498,11 @@ var Mediabunny = (() => {
32925
33498
  });
32926
33499
  }
32927
33500
  if (this.fastStart === "in-memory") {
32928
- trackData.currentChunk.offset = 0;
33501
+ chunk.offset = 0;
32929
33502
  return;
32930
33503
  }
32931
- trackData.currentChunk.offset = this.writer.getPos();
32932
- for (const sample of trackData.currentChunk.samples) {
33504
+ chunk.offset = this.writer.getPos();
33505
+ for (const sample of chunk.samples) {
32933
33506
  assert(sample.data);
32934
33507
  this.writer.write(sample.data);
32935
33508
  sample.data = null;
@@ -32937,10 +33510,12 @@ var Mediabunny = (() => {
32937
33510
  await this.writer.flush();
32938
33511
  }
32939
33512
  async interleaveSamples(isFinalCall = false) {
32940
- assert(this.isFragmented);
32941
33513
  if (!isFinalCall && !this.allTracksAreKnown()) {
32942
33514
  return;
32943
33515
  }
33516
+ if (this.fastStart === "reserve" && !this.mdat) {
33517
+ await this.createFastStartReserveMdat();
33518
+ }
32944
33519
  outer:
32945
33520
  while (true) {
32946
33521
  let trackWithMinTimestamp = null;
@@ -33062,16 +33637,6 @@ var Mediabunny = (() => {
33062
33637
  await this.writer.flush();
33063
33638
  }
33064
33639
  }
33065
- async registerSampleFastStartReserve(trackData, sample) {
33066
- if (this.allTracksAreKnown()) {
33067
- if (!this.mdat) {
33068
- await this.createFastStartReserveMdat();
33069
- }
33070
- await this.addSampleToTrack(trackData, sample);
33071
- } else {
33072
- trackData.sampleQueue.push(sample);
33073
- }
33074
- }
33075
33640
  async createFastStartReserveMdat() {
33076
33641
  assert(this.writer);
33077
33642
  assert(this.boxWriter);
@@ -33086,12 +33651,6 @@ var Mediabunny = (() => {
33086
33651
  }
33087
33652
  this.mdat = mdat(true);
33088
33653
  this.boxWriter.writeBox(this.mdat);
33089
- for (const trackData of this.trackDatas) {
33090
- for (const sample of trackData.sampleQueue) {
33091
- await this.addSampleToTrack(trackData, sample);
33092
- }
33093
- trackData.sampleQueue.length = 0;
33094
- }
33095
33654
  }
33096
33655
  computeSampleTableSizeUpperBound() {
33097
33656
  assert(this.fastStart === "reserve");
@@ -33122,9 +33681,7 @@ var Mediabunny = (() => {
33122
33681
  if (this.allTracksAreKnown()) {
33123
33682
  this.allTracksKnown.resolve();
33124
33683
  }
33125
- if (this.isFragmented) {
33126
- await this.interleaveSamples();
33127
- }
33684
+ await this.interleaveSamples();
33128
33685
  release();
33129
33686
  }
33130
33687
  ensureOneEnabledTrack() {
@@ -33165,9 +33722,6 @@ var Mediabunny = (() => {
33165
33722
  const release = await this.mutex.acquire();
33166
33723
  this.allTracksKnown.resolve();
33167
33724
  this.ensureOneEnabledTrack();
33168
- if (!this.mdat && this.fastStart === "reserve") {
33169
- await this.createFastStartReserveMdat();
33170
- }
33171
33725
  for (const trackData of this.trackDatas) {
33172
33726
  trackData.closed = true;
33173
33727
  if (trackData.type === "subtitle" && trackData.track.source._codec === "webvtt") {
@@ -33175,12 +33729,15 @@ var Mediabunny = (() => {
33175
33729
  }
33176
33730
  this.processTimestamps(trackData);
33177
33731
  }
33732
+ await this.interleaveSamples(true);
33178
33733
  if (this.isFragmented) {
33179
- await this.interleaveSamples(true);
33180
33734
  await this.finalizeFragment(false);
33181
33735
  } else {
33182
- for (const trackData of this.trackDatas) {
33736
+ const tracksToFinalize = this.trackDatas.filter((x) => x.currentChunk).sort((a, b) => a.currentChunk.startTimestamp - b.currentChunk.startTimestamp);
33737
+ for (const trackData of tracksToFinalize) {
33183
33738
  await this.finalizeCurrentChunk(trackData);
33739
+ }
33740
+ for (const trackData of this.trackDatas) {
33184
33741
  const span = presentationSpan(trackData);
33185
33742
  if (span > 0) {
33186
33743
  let totalBytes = 0;
@@ -33333,10 +33890,9 @@ var Mediabunny = (() => {
33333
33890
  this.attachmentsElement = null;
33334
33891
  this.segmentDuration = null;
33335
33892
  this.cues = null;
33336
- this.currentCluster = null;
33893
+ this.currentClusterBlocks = [];
33337
33894
  this.currentClusterStartMsTimestamp = null;
33338
33895
  this.currentClusterMaxMsTimestamp = null;
33339
- this.trackDatasInCurrentCluster = /* @__PURE__ */ new Map();
33340
33896
  this.startTimestamp = Infinity;
33341
33897
  this.endTimestamp = -Infinity;
33342
33898
  this.warnedAboutTooNegativeTimestamp = false;
@@ -33468,14 +34024,12 @@ var Mediabunny = (() => {
33468
34024
  }
33469
34025
  }
33470
34026
  let seekPreRollNs = 0;
33471
- if (trackData.type === "audio" && trackData.track.source._codec === "opus") {
33472
- seekPreRollNs = 1e6 * 80;
33473
- const description = trackData.info.decoderConfig.description;
33474
- if (description) {
33475
- const bytes2 = toUint8Array(description);
33476
- const header = parseOpusIdentificationHeader(bytes2);
33477
- seekPreRollNs = Math.round(1e9 * (header.preSkip / OPUS_SAMPLE_RATE));
33478
- }
34027
+ if (trackData.type === "audio") {
34028
+ const preRollDuration = getAudioPreRollDuration(
34029
+ trackData.track.source._codec,
34030
+ trackData.info.decoderConfig
34031
+ );
34032
+ seekPreRollNs = Math.round(1e9 * preRollDuration);
33479
34033
  }
33480
34034
  tracksElement.data.push({ id: 174 /* TrackEntry */, data: [
33481
34035
  { id: 215 /* TrackNumber */, data: trackData.track.id },
@@ -33491,6 +34045,7 @@ var Mediabunny = (() => {
33491
34045
  { id: 2274716 /* Language */, data: trackData.track.metadata.languageCode ?? UNDETERMINED_LANGUAGE },
33492
34046
  { id: 134 /* CodecID */, data: codecId },
33493
34047
  trackData.codecPrivate ? { id: 25506 /* CodecPrivate */, data: toUint8Array(trackData.codecPrivate) } : null,
34048
+ trackData.type === "audio" && trackData.info.codecDelay ? { id: 22186 /* CodecDelay */, data: Math.round(1e9 * trackData.info.codecDelay) } : null,
33494
34049
  seekPreRollNs > 0 ? { id: 22203 /* SeekPreRoll */, data: seekPreRollNs } : null,
33495
34050
  trackData.track.metadata.name !== void 0 ? { id: 21358 /* Name */, data: new EBMLUnicodeString(trackData.track.metadata.name) } : null,
33496
34051
  trackData.type === "video" ? this.videoSpecificTrackInfo(trackData) : null,
@@ -33953,7 +34508,8 @@ var Mediabunny = (() => {
33953
34508
  numberOfChannels: meta.decoderConfig.numberOfChannels,
33954
34509
  sampleRate: meta.decoderConfig.sampleRate,
33955
34510
  decoderConfig,
33956
- requiresAdtsStripping
34511
+ requiresAdtsStripping,
34512
+ codecDelay: null
33957
34513
  },
33958
34514
  chunkQueue: [],
33959
34515
  lastWrittenMsTimestamp: null,
@@ -34037,7 +34593,13 @@ var Mediabunny = (() => {
34037
34593
  }
34038
34594
  const isKeyFrame = packet.type === "key";
34039
34595
  this.validateTimestamp(trackData.track, packet.timestamp, isKeyFrame);
34040
- const audioChunk = this.createInternalChunk(packetData, packet.timestamp, packet.duration, packet.type);
34596
+ trackData.info.codecDelay ??= Math.max(-packet.timestamp, 0);
34597
+ const audioChunk = this.createInternalChunk(
34598
+ packetData,
34599
+ packet.timestamp + trackData.info.codecDelay,
34600
+ packet.duration,
34601
+ packet.type
34602
+ );
34041
34603
  trackData.chunkQueue.push(audioChunk);
34042
34604
  await this.interleaveChunks();
34043
34605
  } finally {
@@ -34095,7 +34657,7 @@ ${cue.notes ?? ""}`;
34095
34657
  break;
34096
34658
  }
34097
34659
  const chunk = trackWithMinTimestamp.chunkQueue.shift();
34098
- this.writeBlock(trackWithMinTimestamp, chunk);
34660
+ this.addBlock(trackWithMinTimestamp, chunk);
34099
34661
  }
34100
34662
  if (!isFinalCall) {
34101
34663
  await this.writer.flush();
@@ -34141,8 +34703,8 @@ ${cue.notes ?? ""}`;
34141
34703
  };
34142
34704
  return internalChunk;
34143
34705
  }
34144
- /** Writes a block containing media data to the file. */
34145
- writeBlock(trackData, chunk) {
34706
+ /** Adds a block containing media data to the current cluster. */
34707
+ addBlock(trackData, chunk) {
34146
34708
  if (!this.segment) {
34147
34709
  this.createSegment();
34148
34710
  }
@@ -34158,16 +34720,15 @@ ${cue.notes ?? ""}`;
34158
34720
  return otherTrackData.closed;
34159
34721
  });
34160
34722
  let shouldCreateNewCluster = false;
34161
- if (!this.currentCluster) {
34723
+ if (this.currentClusterStartMsTimestamp === null) {
34162
34724
  shouldCreateNewCluster = true;
34163
34725
  } else {
34164
- assert(this.currentClusterStartMsTimestamp !== null);
34165
34726
  assert(this.currentClusterMaxMsTimestamp !== null);
34166
34727
  const relativeTimestamp2 = msTimestamp - this.currentClusterStartMsTimestamp;
34167
34728
  shouldCreateNewCluster = keyFrameQueuedEverywhere && msTimestamp > this.currentClusterMaxMsTimestamp && relativeTimestamp2 >= 1e3 * (this.format._options.minimumClusterDuration ?? 1) || relativeTimestamp2 > MAX_CLUSTER_TIMESTAMP_MS;
34168
34729
  }
34169
34730
  if (shouldCreateNewCluster) {
34170
- this.createNewCluster(msTimestamp);
34731
+ this.startNewCluster(msTimestamp);
34171
34732
  }
34172
34733
  const relativeTimestamp = msTimestamp - this.currentClusterStartMsTimestamp;
34173
34734
  if (relativeTimestamp < MIN_CLUSTER_TIMESTAMP_MS) {
@@ -34180,109 +34741,124 @@ ${cue.notes ?? ""}`;
34180
34741
  }
34181
34742
  return;
34182
34743
  }
34183
- const prelude = new Uint8Array(4);
34184
- const view2 = new DataView(prelude.buffer);
34185
- view2.setUint8(0, 128 | trackData.track.id);
34186
- view2.setInt16(1, relativeTimestamp, false);
34187
- const msDuration = Math.round(1e3 * chunk.duration);
34188
- const needsBlockGroup = !!chunk.additions || trackData.type === "subtitle";
34189
- if (!needsBlockGroup) {
34190
- view2.setUint8(3, Number(chunk.type === "key") << 7);
34191
- const simpleBlock = { id: 163 /* SimpleBlock */, data: [
34192
- prelude,
34193
- chunk.data
34194
- ] };
34195
- this.ebmlWriter.writeEBML(simpleBlock);
34196
- } else {
34197
- const blockGroup = { id: 160 /* BlockGroup */, data: [
34198
- { id: 161 /* Block */, data: [
34199
- prelude,
34200
- chunk.data
34201
- ] },
34202
- chunk.type === "delta" ? {
34203
- id: 251 /* ReferenceBlock */,
34204
- data: new EBMLSignedInt(trackData.lastWrittenMsTimestamp - msTimestamp)
34205
- } : null,
34206
- chunk.additions ? { id: 30113 /* BlockAdditions */, data: [
34207
- { id: 166 /* BlockMore */, data: [
34208
- { id: 238 /* BlockAddID */, data: 1 },
34209
- // Some players expect BlockAddID to come first
34210
- { id: 165 /* BlockAdditional */, data: chunk.additions }
34211
- ] }
34212
- ] } : null,
34213
- msDuration > 0 ? { id: 155 /* BlockDuration */, data: msDuration } : null
34214
- ] };
34215
- this.ebmlWriter.writeEBML(blockGroup);
34216
- }
34744
+ this.currentClusterBlocks.push({
34745
+ trackData,
34746
+ chunk,
34747
+ msTimestamp,
34748
+ previousMsTimestamp: trackData.lastWrittenMsTimestamp
34749
+ });
34217
34750
  this.startTimestamp = Math.min(this.startTimestamp, msTimestamp);
34218
- this.endTimestamp = Math.max(this.endTimestamp, msTimestamp + msDuration);
34751
+ this.endTimestamp = Math.max(this.endTimestamp, msTimestamp + Math.round(1e3 * chunk.duration));
34219
34752
  trackData.lastWrittenMsTimestamp = msTimestamp;
34220
- if (!this.trackDatasInCurrentCluster.has(trackData)) {
34221
- this.trackDatasInCurrentCluster.set(trackData, {
34222
- firstMsTimestamp: msTimestamp
34223
- });
34224
- }
34225
34753
  this.currentClusterMaxMsTimestamp = Math.max(this.currentClusterMaxMsTimestamp, msTimestamp);
34226
34754
  }
34227
- /** Creates a new Cluster element to contain media chunks. */
34228
- createNewCluster(msTimestamp) {
34229
- msTimestamp = Math.max(0, msTimestamp);
34230
- if (this.currentCluster) {
34231
- this.finalizeCurrentCluster();
34232
- }
34233
- if (this.format._options.onCluster) {
34234
- this.writer.startTrackingWrites();
34755
+ /** Writes out the current cluster, if any, and begins a new one. */
34756
+ startNewCluster(msTimestamp) {
34757
+ if (this.currentClusterStartMsTimestamp !== null) {
34758
+ this.writeCurrentCluster();
34759
+ }
34760
+ const clusterMsTimestamp = Math.max(0, msTimestamp);
34761
+ this.currentClusterStartMsTimestamp = clusterMsTimestamp;
34762
+ this.currentClusterMaxMsTimestamp = clusterMsTimestamp;
34763
+ }
34764
+ /** Writes the current cluster with all of its blocks to the file. */
34765
+ writeCurrentCluster() {
34766
+ assert(this.currentClusterStartMsTimestamp !== null);
34767
+ const clusterMsTimestamp = this.currentClusterStartMsTimestamp;
34768
+ const firstKeyBlockPerTrack = /* @__PURE__ */ new Map();
34769
+ const lastBlockPerTrack = /* @__PURE__ */ new Map();
34770
+ for (const block of this.currentClusterBlocks) {
34771
+ if (block.chunk.type === "key" && !firstKeyBlockPerTrack.has(block.trackData)) {
34772
+ firstKeyBlockPerTrack.set(block.trackData, block);
34773
+ }
34774
+ lastBlockPerTrack.set(block.trackData, block);
34775
+ }
34776
+ const blockElements = /* @__PURE__ */ new Map();
34777
+ for (const block of this.currentClusterBlocks) {
34778
+ blockElements.set(block, this.createBlockElement(
34779
+ block,
34780
+ clusterMsTimestamp,
34781
+ lastBlockPerTrack.get(block.trackData) === block
34782
+ ));
34235
34783
  }
34236
- this.currentCluster = {
34784
+ const cluster = {
34237
34785
  id: 524531317 /* Cluster */,
34238
34786
  size: this.format._options.appendOnly ? -1 : CLUSTER_SIZE_BYTES,
34239
34787
  data: [
34240
- { id: 231 /* Timestamp */, data: msTimestamp }
34788
+ { id: 231 /* Timestamp */, data: clusterMsTimestamp },
34789
+ ...blockElements.values()
34241
34790
  ]
34242
34791
  };
34243
- this.ebmlWriter.writeEBML(this.currentCluster);
34244
- this.currentClusterStartMsTimestamp = msTimestamp;
34245
- this.currentClusterMaxMsTimestamp = msTimestamp;
34246
- this.trackDatasInCurrentCluster.clear();
34247
- }
34248
- finalizeCurrentCluster() {
34249
- assert(this.currentCluster);
34250
- if (!this.format._options.appendOnly) {
34251
- const clusterSize = this.writer.getPos() - this.ebmlWriter.dataOffsets.get(this.currentCluster);
34252
- const endPos = this.writer.getPos();
34253
- this.writer.seek(this.ebmlWriter.offsets.get(this.currentCluster) + 4);
34254
- this.ebmlWriter.writeVarInt(clusterSize, CLUSTER_SIZE_BYTES);
34255
- this.writer.seek(endPos);
34792
+ if (this.format._options.onCluster) {
34793
+ this.writer.startTrackingWrites();
34256
34794
  }
34795
+ this.ebmlWriter.writeEBML(cluster);
34796
+ this.currentClusterBlocks = [];
34257
34797
  if (this.format._options.onCluster) {
34258
- assert(this.currentClusterStartMsTimestamp !== null);
34259
34798
  const { data, start } = this.writer.stopTrackingWrites();
34260
- this.format._options.onCluster(data, start, this.currentClusterStartMsTimestamp / 1e3);
34799
+ this.format._options.onCluster(data, start, clusterMsTimestamp / 1e3);
34261
34800
  }
34262
- const clusterOffsetFromSegment = this.ebmlWriter.offsets.get(this.currentCluster) - this.segmentDataOffset;
34801
+ const clusterOffsetFromSegment = this.ebmlWriter.offsets.get(cluster) - this.segmentDataOffset;
34802
+ const clusterDataOffset = this.ebmlWriter.dataOffsets.get(cluster);
34263
34803
  const groupedByTimestamp = /* @__PURE__ */ new Map();
34264
- for (const [trackData, { firstMsTimestamp }] of this.trackDatasInCurrentCluster) {
34265
- if (!groupedByTimestamp.has(firstMsTimestamp)) {
34266
- groupedByTimestamp.set(firstMsTimestamp, []);
34804
+ for (const block of firstKeyBlockPerTrack.values()) {
34805
+ if (!groupedByTimestamp.has(block.msTimestamp)) {
34806
+ groupedByTimestamp.set(block.msTimestamp, []);
34267
34807
  }
34268
- groupedByTimestamp.get(firstMsTimestamp).push(trackData);
34808
+ groupedByTimestamp.get(block.msTimestamp).push(block);
34269
34809
  }
34270
34810
  const groupedAndSortedByTimestamp = [...groupedByTimestamp.entries()].sort((a, b) => a[0] - b[0]);
34271
- for (const [msTimestamp, trackDatas] of groupedAndSortedByTimestamp) {
34811
+ for (const [msTimestamp, blocks] of groupedAndSortedByTimestamp) {
34272
34812
  assert(this.cues);
34273
34813
  this.cues.data.push({ id: 187 /* CuePoint */, data: [
34274
34814
  { id: 179 /* CueTime */, data: Math.max(0, msTimestamp) },
34275
34815
  // CueTime is unsigned
34276
- // Create CueTrackPositions for each track that starts at this timestamp
34277
- ...trackDatas.map((trackData) => {
34816
+ // Create CueTrackPositions for each track whose first key packet is at this timestamp
34817
+ ...blocks.map((block) => {
34818
+ const blockOffset = this.ebmlWriter.offsets.get(blockElements.get(block));
34278
34819
  return { id: 183 /* CueTrackPositions */, data: [
34279
- { id: 247 /* CueTrack */, data: trackData.track.id },
34280
- { id: 241 /* CueClusterPosition */, data: clusterOffsetFromSegment }
34820
+ { id: 247 /* CueTrack */, data: block.trackData.track.id },
34821
+ { id: 241 /* CueClusterPosition */, data: clusterOffsetFromSegment },
34822
+ { id: 240 /* CueRelativePosition */, data: blockOffset - clusterDataOffset }
34281
34823
  ] };
34282
34824
  })
34283
34825
  ] });
34284
34826
  }
34285
34827
  }
34828
+ createBlockElement(block, clusterMsTimestamp, isLastOfTrack) {
34829
+ const { trackData, chunk, msTimestamp } = block;
34830
+ const prelude = new Uint8Array(4);
34831
+ const view2 = new DataView(prelude.buffer);
34832
+ view2.setUint8(0, 128 | trackData.track.id);
34833
+ view2.setInt16(1, msTimestamp - clusterMsTimestamp, false);
34834
+ const msDuration = Math.round(1e3 * chunk.duration);
34835
+ const needsBlockGroup = !!chunk.additions || trackData.type === "subtitle" || isLastOfTrack && msDuration > 0;
34836
+ if (!needsBlockGroup) {
34837
+ view2.setUint8(3, Number(chunk.type === "key") << 7);
34838
+ return { id: 163 /* SimpleBlock */, data: [
34839
+ prelude,
34840
+ chunk.data
34841
+ ] };
34842
+ }
34843
+ return { id: 160 /* BlockGroup */, data: [
34844
+ { id: 161 /* Block */, data: [
34845
+ prelude,
34846
+ chunk.data
34847
+ ] },
34848
+ chunk.type === "delta" ? {
34849
+ id: 251 /* ReferenceBlock */,
34850
+ data: new EBMLSignedInt(block.previousMsTimestamp - msTimestamp)
34851
+ } : null,
34852
+ chunk.additions ? { id: 30113 /* BlockAdditions */, data: [
34853
+ { id: 166 /* BlockMore */, data: [
34854
+ { id: 238 /* BlockAddID */, data: 1 },
34855
+ // Some players expect BlockAddID to come first
34856
+ { id: 165 /* BlockAdditional */, data: chunk.additions }
34857
+ ] }
34858
+ ] } : null,
34859
+ msDuration > 0 ? { id: 155 /* BlockDuration */, data: msDuration } : null
34860
+ ] };
34861
+ }
34286
34862
  // eslint-disable-next-line @typescript-eslint/no-misused-promises
34287
34863
  async onTrackClose(track) {
34288
34864
  const release = await this.mutex.acquire();
@@ -34307,8 +34883,8 @@ ${cue.notes ?? ""}`;
34307
34883
  this.createSegment();
34308
34884
  }
34309
34885
  await this.interleaveChunks(true);
34310
- if (this.currentCluster) {
34311
- this.finalizeCurrentCluster();
34886
+ if (this.currentClusterStartMsTimestamp !== null) {
34887
+ this.writeCurrentCluster();
34312
34888
  }
34313
34889
  assert(this.cues);
34314
34890
  this.ebmlWriter.writeEBML(this.cues);
@@ -34335,13 +34911,24 @@ ${cue.notes ?? ""}`;
34335
34911
  this.writer = writer;
34336
34912
  this.helper = new Uint8Array(8);
34337
34913
  this.helperView = new DataView(this.helper.buffer);
34914
+ this.crc = 0;
34915
+ }
34916
+ writeAndUpdateCrc(bytes2) {
34917
+ for (const byte of bytes2) {
34918
+ this.crc ^= byte;
34919
+ for (let bit = 0; bit < 8; bit++) {
34920
+ this.crc = this.crc >>> 1 ^ (this.crc & 1 ? 40961 : 0);
34921
+ }
34922
+ }
34923
+ this.writer.write(bytes2);
34338
34924
  }
34339
34925
  writeU32(value) {
34340
34926
  this.helperView.setUint32(0, value, false);
34341
- this.writer.write(this.helper.subarray(0, 4));
34927
+ this.writeAndUpdateCrc(this.helper.subarray(0, 4));
34342
34928
  }
34343
34929
  writeXingFrame(data) {
34344
34930
  const startPos = this.writer.getPos();
34931
+ this.crc = 0;
34345
34932
  const firstByte = 255;
34346
34933
  const secondByte = 224 | data.mpegVersionId << 3 | data.layer << 1;
34347
34934
  let lowSamplingFrequency;
@@ -34351,7 +34938,8 @@ ${cue.notes ?? ""}`;
34351
34938
  lowSamplingFrequency = 1;
34352
34939
  }
34353
34940
  const padding = 0;
34354
- const neededBytes = 155;
34941
+ const xingOffset = getXingOffset(data.mpegVersionId, data.channel);
34942
+ const neededBytes = data.encoderDelayInSamples === null ? 155 : xingOffset + 8 + 4 + 4 + 100 + 36;
34355
34943
  let bitrateIndex = -1;
34356
34944
  const bitrateOffset = lowSamplingFrequency * 16 * 4 + data.layer * 16;
34357
34945
  for (let i = 0; i < 16; i++) {
@@ -34371,10 +34959,9 @@ ${cue.notes ?? ""}`;
34371
34959
  this.helper[1] = secondByte;
34372
34960
  this.helper[2] = thirdByte;
34373
34961
  this.helper[3] = fourthByte;
34374
- this.writer.write(this.helper.subarray(0, 4));
34375
- const xingOffset = getXingOffset(data.mpegVersionId, data.channel);
34376
- this.writer.seek(startPos + xingOffset);
34377
- this.writeU32(XING);
34962
+ this.writeAndUpdateCrc(this.helper.subarray(0, 4));
34963
+ this.writeAndUpdateCrc(new Uint8Array(xingOffset - 4));
34964
+ this.writeU32(data.isCbr ? INFO : XING);
34378
34965
  let flags = 0;
34379
34966
  if (data.frameCount !== null) {
34380
34967
  flags |= 1 /* FrameCount */;
@@ -34388,7 +34975,17 @@ ${cue.notes ?? ""}`;
34388
34975
  this.writeU32(flags);
34389
34976
  this.writeU32(data.frameCount ?? 0);
34390
34977
  this.writeU32(data.fileSize ?? 0);
34391
- this.writer.write(data.toc ?? new Uint8Array(100));
34978
+ this.writeAndUpdateCrc(data.toc ?? new Uint8Array(100));
34979
+ if (data.encoderDelayInSamples !== null) {
34980
+ const lame = new Uint8Array(36);
34981
+ lame.set([76, 65, 77, 69]);
34982
+ lame[21] = data.encoderDelayInSamples >> 4;
34983
+ lame[22] = (data.encoderDelayInSamples & 15) << 4 | MP3_DECODER_DELAY >> 8;
34984
+ lame[23] = MP3_DECODER_DELAY & 255;
34985
+ this.writeAndUpdateCrc(lame.subarray(0, 34));
34986
+ new DataView(lame.buffer).setUint16(34, this.crc);
34987
+ this.writer.write(lame.subarray(34));
34988
+ }
34392
34989
  const kilobitRate = KILOBIT_RATES[bitrateOffset + bitrateIndex];
34393
34990
  const frameSize = computeMp3FrameSize(
34394
34991
  lowSamplingFrequency,
@@ -34407,6 +35004,8 @@ ${cue.notes ?? ""}`;
34407
35004
  super(output);
34408
35005
  this.xingFrameData = null;
34409
35006
  this.frameCount = 0;
35007
+ this.frameBitrate = null;
35008
+ this.hasVariableBitrate = false;
34410
35009
  this.framePositions = [];
34411
35010
  this.xingFramePos = null;
34412
35011
  this.format = format;
@@ -34431,7 +35030,7 @@ ${cue.notes ?? ""}`;
34431
35030
  async addEncodedAudioPacket(track, packet) {
34432
35031
  const release = await this.mutex.acquire();
34433
35032
  try {
34434
- if (!this.xingFrameData && this.writeXingHeader) {
35033
+ if (this.writeXingHeader) {
34435
35034
  const view2 = toDataView(packet.data);
34436
35035
  if (view2.byteLength < 4) {
34437
35036
  throw new Error("Invalid MP3 header in sample.");
@@ -34441,31 +35040,44 @@ ${cue.notes ?? ""}`;
34441
35040
  if (!header) {
34442
35041
  throw new Error("Invalid MP3 header in sample.");
34443
35042
  }
34444
- const xingOffset = getXingOffset(header.mpegVersionId, header.channel);
34445
- if (view2.byteLength >= xingOffset + 4) {
34446
- const word2 = view2.getUint32(xingOffset, false);
34447
- const isXing = word2 === XING || word2 === INFO;
34448
- if (isXing) {
34449
- return;
35043
+ if (!this.xingFrameData) {
35044
+ const xingOffset = getXingOffset(header.mpegVersionId, header.channel);
35045
+ if (view2.byteLength >= xingOffset + 4) {
35046
+ const word2 = view2.getUint32(xingOffset, false);
35047
+ const isXing = word2 === XING || word2 === INFO;
35048
+ if (isXing) {
35049
+ return;
35050
+ }
34450
35051
  }
35052
+ let encoderDelay = packet.timestamp < 0 ? Math.round(-packet.timestamp * header.sampleRate) - MP3_DECODER_DELAY : null;
35053
+ if (encoderDelay !== null && (encoderDelay < 0 || encoderDelay > 4095)) {
35054
+ encoderDelay = null;
35055
+ }
35056
+ this.xingFrameData = {
35057
+ mpegVersionId: header.mpegVersionId,
35058
+ layer: header.layer,
35059
+ frequencyIndex: header.frequencyIndex,
35060
+ sampleRate: header.sampleRate,
35061
+ channel: header.channel,
35062
+ modeExtension: header.modeExtension,
35063
+ copyright: header.copyright,
35064
+ original: header.original,
35065
+ emphasis: header.emphasis,
35066
+ isCbr: false,
35067
+ frameCount: null,
35068
+ fileSize: null,
35069
+ toc: null,
35070
+ encoderDelayInSamples: encoderDelay
35071
+ };
35072
+ this.xingFramePos = this.writer.getPos();
35073
+ this.mp3Writer.writeXingFrame(this.xingFrameData);
35074
+ this.frameCount++;
35075
+ }
35076
+ if (this.frameBitrate === null) {
35077
+ this.frameBitrate = header.bitrate;
35078
+ } else if (header.bitrate !== this.frameBitrate) {
35079
+ this.hasVariableBitrate = true;
34451
35080
  }
34452
- this.xingFrameData = {
34453
- mpegVersionId: header.mpegVersionId,
34454
- layer: header.layer,
34455
- frequencyIndex: header.frequencyIndex,
34456
- sampleRate: header.sampleRate,
34457
- channel: header.channel,
34458
- modeExtension: header.modeExtension,
34459
- copyright: header.copyright,
34460
- original: header.original,
34461
- emphasis: header.emphasis,
34462
- frameCount: null,
34463
- fileSize: null,
34464
- toc: null
34465
- };
34466
- this.xingFramePos = this.writer.getPos();
34467
- this.mp3Writer.writeXingFrame(this.xingFrameData);
34468
- this.frameCount++;
34469
35081
  }
34470
35082
  this.validateTimestamp(track, packet.timestamp, packet.type === "key");
34471
35083
  if (this.writeXingHeader) {
@@ -34513,9 +35125,11 @@ ${cue.notes ?? ""}`;
34513
35125
  copyright: header.copyright,
34514
35126
  original: header.original,
34515
35127
  emphasis: header.emphasis,
35128
+ isCbr: false,
34516
35129
  frameCount: null,
34517
35130
  fileSize: null,
34518
- toc: null
35131
+ toc: null,
35132
+ encoderDelayInSamples: null
34519
35133
  };
34520
35134
  } else if (track.metadata.decoderConfig) {
34521
35135
  const { sampleRate, numberOfChannels } = track.metadata.decoderConfig;
@@ -34544,9 +35158,11 @@ ${cue.notes ?? ""}`;
34544
35158
  copyright: 0,
34545
35159
  original: 0,
34546
35160
  emphasis: 0,
35161
+ isCbr: false,
34547
35162
  frameCount: null,
34548
35163
  fileSize: null,
34549
- toc: null
35164
+ toc: null,
35165
+ encoderDelayInSamples: null
34550
35166
  };
34551
35167
  } else {
34552
35168
  throw new Error(
@@ -34572,6 +35188,7 @@ ${cue.notes ?? ""}`;
34572
35188
  }
34573
35189
  this.xingFrameData.toc = toc;
34574
35190
  }
35191
+ this.xingFrameData.isCbr = this.frameBitrate !== null && !this.hasVariableBitrate;
34575
35192
  this.xingFrameData.frameCount = this.frameCount;
34576
35193
  this.xingFrameData.fileSize = audioDataEndPos;
34577
35194
  if (this.format._options.onXingFrame) {
@@ -34643,7 +35260,7 @@ ${cue.notes ?? ""}`;
34643
35260
  },
34644
35261
  vorbisLastBlocksize: null,
34645
35262
  packetQueue: [],
34646
- startTimestampInSamples: null,
35263
+ startOffsetInSamples: null,
34647
35264
  currentTimestampInSamples: 0,
34648
35265
  audioPacketCount: 0,
34649
35266
  pagesWritten: 0,
@@ -34765,22 +35382,24 @@ ${cue.notes ?? ""}`;
34765
35382
  try {
34766
35383
  const trackData = this.getTrackData(track, meta);
34767
35384
  this.validateTimestamp(trackData.track, packet.timestamp, packet.type === "key");
34768
- if (trackData.startTimestampInSamples === null) {
34769
- const timestampInSamples = Math.round(packet.timestamp * trackData.internalSampleRate);
34770
- const preSkip = trackData.codecInfo.opusInfo?.preSkip ?? 0;
34771
- trackData.startTimestampInSamples = timestampInSamples > 0 ? timestampInSamples + preSkip : 0;
34772
- trackData.currentTimestampInSamples = trackData.startTimestampInSamples;
34773
- }
34774
- const currentTimestampInSamples = trackData.currentTimestampInSamples;
34775
35385
  const { durationInSamples, vorbisBlockSize } = extractSampleMetadata(
34776
35386
  packet.data,
34777
35387
  trackData.codecInfo,
34778
35388
  trackData.vorbisLastBlocksize
34779
35389
  );
35390
+ if (trackData.startOffsetInSamples === null) {
35391
+ const timestampInSamples = Math.round(packet.timestamp * trackData.internalSampleRate);
35392
+ const preSkip = trackData.codecInfo.opusInfo?.preSkip ?? 0;
35393
+ const minTimestampInSamples = trackData.codecInfo.codec === "vorbis" ? -durationInSamples : -preSkip;
35394
+ const startTimestampInSamples = Math.max(timestampInSamples, minTimestampInSamples);
35395
+ trackData.startOffsetInSamples = startTimestampInSamples - minTimestampInSamples;
35396
+ trackData.currentTimestampInSamples = startTimestampInSamples + preSkip;
35397
+ }
35398
+ const currentTimestampInSamples = trackData.currentTimestampInSamples;
34780
35399
  trackData.currentTimestampInSamples += durationInSamples;
34781
35400
  trackData.vorbisLastBlocksize = vorbisBlockSize;
34782
35401
  const trimmedDurationInSamples = packet.duration > 0 ? clamp(Math.round(packet.duration * trackData.internalSampleRate), 0, durationInSamples) : durationInSamples;
34783
- const forcePageFlush = trackData.startTimestampInSamples > 0 && trackData.audioPacketCount === 1;
35402
+ const forcePageFlush = trackData.startOffsetInSamples > 0 && trackData.audioPacketCount === 1;
34784
35403
  trackData.audioPacketCount++;
34785
35404
  trackData.packetQueue.push({
34786
35405
  data: packet.data,
@@ -34989,6 +35608,7 @@ ${cue.notes ?? ""}`;
34989
35608
  this.adaptationFieldBuffer = new Uint8Array(184);
34990
35609
  this.payloadBuffer = new Uint8Array(184);
34991
35610
  this.format = format;
35611
+ this.timestampOffset = format._options.timestampOffset ?? 0;
34992
35612
  }
34993
35613
  async start() {
34994
35614
  const release = await this.mutex.acquire();
@@ -35358,8 +35978,7 @@ ${cue.notes ?? ""}`;
35358
35978
  pesView.setUint8(6, 132);
35359
35979
  pesView.setUint8(7, includeDts ? 192 : 128);
35360
35980
  pesView.setUint8(8, headerDataLength);
35361
- const unwrappedPts = Math.round(queuedPacket.presentationTimestamp * TIMESCALE);
35362
- const pts = modEuclid(unwrappedPts, TIMESTAMP_MODULUS);
35981
+ const pts = secondsToMpegTsTimestamp(queuedPacket.presentationTimestamp + this.timestampOffset);
35363
35982
  ptsDtsBitstream.pos = 0;
35364
35983
  ptsDtsBitstream.writeBits(4, includeDts ? 3 : 2);
35365
35984
  ptsDtsBitstream.writeBits(3, Math.floor(pts / 2 ** 30));
@@ -35370,8 +35989,7 @@ ${cue.notes ?? ""}`;
35370
35989
  ptsDtsBitstream.writeBits(1, 1);
35371
35990
  if (includeDts) {
35372
35991
  assert(queuedPacket.decodeTimestamp !== null);
35373
- const unwrappedDts = Math.round(queuedPacket.decodeTimestamp * TIMESCALE);
35374
- const dts = modEuclid(unwrappedDts, TIMESTAMP_MODULUS);
35992
+ const dts = secondsToMpegTsTimestamp(queuedPacket.decodeTimestamp + this.timestampOffset);
35375
35993
  ptsDtsBitstream.writeBits(4, 1);
35376
35994
  ptsDtsBitstream.writeBits(3, Math.floor(dts / 2 ** 30));
35377
35995
  ptsDtsBitstream.writeBits(1, 1);
@@ -35992,10 +36610,12 @@ ${cue.notes ?? ""}`;
35992
36610
  const sourceDataSize = audioSample.allocationSize({ planeIndex: 0, format: "f32" });
35993
36611
  const sourceView = new Float32Array(this.tempSourceBuffer.buffer, 0, sourceDataSize / 4);
35994
36612
  audioSample.copyTo(sourceView, { planeIndex: 0, format: "f32" });
35995
- const inputStartTime = audioSample.timestamp - this.startTime;
35996
- const inputEndTime = inputStartTime + audioSample.duration;
35997
- const outputStartFrame = Math.floor((inputStartTime - 1 / this.sourceSampleRate) * this.targetSampleRate) + 1;
35998
- const outputEndFrame = Math.ceil(inputEndTime * this.targetSampleRate);
36613
+ const sourceStartFrame = Math.round((audioSample.timestamp - this.startTime) * this.sourceSampleRate);
36614
+ const sourceEndFrame = sourceStartFrame + audioSample.numberOfFrames;
36615
+ const outputStartFrame = Math.floor(
36616
+ (sourceStartFrame - 1) * this.targetSampleRate / this.sourceSampleRate
36617
+ ) + 1;
36618
+ const outputEndFrame = Math.ceil(sourceEndFrame * this.targetSampleRate / this.sourceSampleRate);
35999
36619
  for (let outputFrame = outputStartFrame; outputFrame < outputEndFrame; outputFrame++) {
36000
36620
  if (outputFrame < this.bufferStartFrame) {
36001
36621
  continue;
@@ -36006,9 +36626,7 @@ ${cue.notes ?? ""}`;
36006
36626
  }
36007
36627
  const bufferFrameIndex = outputFrame - this.bufferStartFrame;
36008
36628
  assert(bufferFrameIndex < this.bufferCapacityInFrames);
36009
- const outputTime = outputFrame / this.targetSampleRate;
36010
- const inputTime = outputTime - inputStartTime;
36011
- const sourcePosition = inputTime * this.sourceSampleRate;
36629
+ const sourcePosition = outputFrame * this.sourceSampleRate / this.targetSampleRate - sourceStartFrame;
36012
36630
  const sourceLowerFrame = Math.floor(sourcePosition);
36013
36631
  const sourceUpperFrame = Math.ceil(sourcePosition);
36014
36632
  const fraction = sourcePosition - sourceLowerFrame;
@@ -37691,7 +38309,7 @@ ${cue.notes ?? ""}`;
37691
38309
  }
37692
38310
  ensureEncoder(audioSample) {
37693
38311
  this.ensureEncoderPromise = (async () => {
37694
- const { numberOfChannels, sampleRate } = audioSample;
38312
+ const { numberOfChannels, sampleRate, timestamp } = audioSample;
37695
38313
  const quality = resolveQuality(this.encodingConfig.quality, this.encodingConfig.bitrate);
37696
38314
  const encoderConfig = buildAudioEncoderConfig({
37697
38315
  numberOfChannels,
@@ -37743,39 +38361,33 @@ ${cue.notes ?? ""}`;
37743
38361
  `This specific encoder configuration (${encoderConfig.codec}, ${encoderConfig.bitrate} bps, ${encoderConfig.numberOfChannels} channels, ${encoderConfig.sampleRate} Hz) is not supported in this environment. Consider using another codec or changing your audio parameters.`
37744
38362
  );
37745
38363
  }
38364
+ const primingShiftInSamples = await detectAudioEncoderPrimingShift(
38365
+ this.encodingConfig.codec,
38366
+ encoderConfig.codec
38367
+ );
38368
+ const primingShift = primingShiftInSamples / encoderConfig.sampleRate;
38369
+ let opusPreSkip = 0;
37746
38370
  const stack = new Error("Encoding error").stack;
37747
38371
  this.encoder = new AudioEncoder({
37748
38372
  output: (chunk, meta) => {
37749
- if (this.encodingConfig.codec === "aac" && meta?.decoderConfig) {
37750
- if (meta.decoderConfig.description && meta.decoderConfig.description.byteLength > 0 && toUint8Array(meta.decoderConfig.description)[0] === 3) {
37751
- const { decoderSpecificInfo } = readEsDescriptor(
37752
- FileSlice4.tempFromBytes(toUint8Array(meta.decoderConfig.description))
37753
- );
37754
- meta.decoderConfig.description = decoderSpecificInfo ?? void 0;
37755
- }
37756
- let needsDescriptionOverwrite = false;
37757
- if (!meta.decoderConfig.description || meta.decoderConfig.description.byteLength < 2) {
37758
- needsDescriptionOverwrite = true;
37759
- } else {
37760
- const audioSpecificConfig = parseAacAudioSpecificConfig(
37761
- toUint8Array(meta.decoderConfig.description)
37762
- );
37763
- needsDescriptionOverwrite = audioSpecificConfig.objectType === 0;
37764
- }
37765
- if (needsDescriptionOverwrite) {
37766
- const objectType = Number(last(encoderConfig.codec.split(".")));
37767
- meta.decoderConfig.description = buildAacAudioSpecificConfig({
37768
- objectType,
37769
- outputNumberOfChannels: meta.decoderConfig.numberOfChannels,
37770
- outputSampleRate: meta.decoderConfig.sampleRate
37771
- });
38373
+ if (meta?.decoderConfig) {
38374
+ fixAudioDecoderConfig(this.encodingConfig.codec, encoderConfig, meta.decoderConfig);
38375
+ if (this.encodingConfig.codec === "opus" && meta.decoderConfig.description) {
38376
+ const description = toUint8Array(meta.decoderConfig.description);
38377
+ opusPreSkip = parseOpusIdentificationHeader(description).preSkip / OPUS_SAMPLE_RATE;
37772
38378
  }
37773
38379
  }
37774
38380
  let packet = EncodedPacket.fromEncodedChunk(chunk);
37775
38381
  packet = packet.clone({
37776
- timestamp: roundToDivisor(packet.timestamp, encoderConfig.sampleRate),
38382
+ timestamp: roundToDivisor(
38383
+ packet.timestamp - primingShift - opusPreSkip,
38384
+ encoderConfig.sampleRate
38385
+ ),
37777
38386
  duration: chunk.duration != null ? roundToDivisor(packet.duration, encoderConfig.sampleRate) : void 0
37778
38387
  });
38388
+ if (isFirefox()) {
38389
+ opusPreSkip = 0;
38390
+ }
37779
38391
  this.encodingConfig.onEncodedPacket?.(packet, meta);
37780
38392
  this.lastMuxerPromise = this.muxer.addEncodedAudioPacket(this.source._connectedTrack, packet, meta).catch((error) => {
37781
38393
  this.setError(error);
@@ -37787,6 +38399,9 @@ ${cue.notes ?? ""}`;
37787
38399
  }
37788
38400
  });
37789
38401
  this.encoder.configure(encoderConfig);
38402
+ if (this.encodingConfig.codec === "aac" && isWebKit()) {
38403
+ encodeAacSilencePrefix(this.encoder, numberOfChannels, sampleRate, timestamp);
38404
+ }
37790
38405
  }
37791
38406
  assert(this.source._connectedTrack);
37792
38407
  this.muxer = this.source._connectedTrack.output._muxer;
@@ -37941,6 +38556,138 @@ ${cue.notes ?? ""}`;
37941
38556
  }
37942
38557
  }
37943
38558
  };
38559
+ var audioEncoderPrimingShiftPromises = /* @__PURE__ */ new Map();
38560
+ var detectAudioEncoderPrimingShift = (codec, codecString) => {
38561
+ let promise = audioEncoderPrimingShiftPromises.get(codecString);
38562
+ if (promise) {
38563
+ return promise;
38564
+ }
38565
+ promise = (async () => {
38566
+ const numberOfChannels = 1;
38567
+ const sampleRate = 48e3;
38568
+ const encoderConfig = {
38569
+ codec: codecString,
38570
+ numberOfChannels,
38571
+ sampleRate,
38572
+ ...getAudioEncoderConfigExtension(codec)
38573
+ };
38574
+ const impulseIndex = 4096;
38575
+ const numberOfFrames = 2 * impulseIndex;
38576
+ const chunks = [];
38577
+ let decoderConfig = null;
38578
+ let peakIndex = null;
38579
+ let peakValue = -Infinity;
38580
+ let decodedFrames = 0;
38581
+ let codecError = null;
38582
+ const encoder = new AudioEncoder({
38583
+ output: (chunk, meta) => {
38584
+ if (meta?.decoderConfig) {
38585
+ decoderConfig ??= meta.decoderConfig;
38586
+ }
38587
+ chunks.push(chunk);
38588
+ },
38589
+ error: (error) => {
38590
+ codecError ??= error;
38591
+ }
38592
+ });
38593
+ const decoder = new AudioDecoder({
38594
+ output: (audioData) => {
38595
+ const values = new Float32Array(audioData.numberOfFrames);
38596
+ audioData.copyTo(values, { planeIndex: 0, format: "f32-planar" });
38597
+ audioData.close();
38598
+ for (let i = 0; i < values.length; i++) {
38599
+ if (values[i] > peakValue) {
38600
+ peakValue = values[i];
38601
+ peakIndex = decodedFrames + i;
38602
+ }
38603
+ }
38604
+ decodedFrames += values.length;
38605
+ },
38606
+ error: (error) => {
38607
+ codecError ??= error;
38608
+ }
38609
+ });
38610
+ try {
38611
+ encoder.configure(encoderConfig);
38612
+ if (codec === "aac" && isWebKit()) {
38613
+ encodeAacSilencePrefix(encoder, numberOfChannels, sampleRate, 0);
38614
+ }
38615
+ const data = new Float32Array(numberOfChannels * numberOfFrames);
38616
+ data[impulseIndex] = 1;
38617
+ const audioData = new AudioData({
38618
+ data,
38619
+ format: "f32-planar",
38620
+ numberOfChannels,
38621
+ numberOfFrames,
38622
+ sampleRate,
38623
+ timestamp: 0
38624
+ });
38625
+ encoder.encode(audioData);
38626
+ audioData.close();
38627
+ await encoder.flush();
38628
+ assert(decoderConfig);
38629
+ fixAudioDecoderConfig(codec, encoderConfig, decoderConfig);
38630
+ decoder.configure(decoderConfig);
38631
+ for (const chunk of chunks) {
38632
+ decoder.decode(chunk);
38633
+ }
38634
+ await decoder.flush();
38635
+ } catch (error) {
38636
+ throw codecError ?? error;
38637
+ } finally {
38638
+ if (encoder.state !== "closed") {
38639
+ encoder.close();
38640
+ }
38641
+ if (decoder.state !== "closed") {
38642
+ decoder.close();
38643
+ }
38644
+ }
38645
+ assert(peakIndex !== null);
38646
+ const firstChunkTimestampInSamples = Math.round(chunks[0].timestamp / 1e6 * sampleRate);
38647
+ return peakIndex - impulseIndex + firstChunkTimestampInSamples;
38648
+ })();
38649
+ audioEncoderPrimingShiftPromises.set(codecString, promise);
38650
+ promise.catch(() => audioEncoderPrimingShiftPromises.delete(codecString));
38651
+ return promise;
38652
+ };
38653
+ var encodeAacSilencePrefix = (encoder, numberOfChannels, sampleRate, timestamp) => {
38654
+ const numberOfFrames = 1024;
38655
+ const audioData = new AudioData({
38656
+ data: new Float32Array(numberOfChannels * numberOfFrames),
38657
+ format: "f32-planar",
38658
+ numberOfChannels,
38659
+ numberOfFrames,
38660
+ sampleRate,
38661
+ timestamp: Math.round(1e6 * (timestamp - numberOfFrames / sampleRate))
38662
+ });
38663
+ encoder.encode(audioData);
38664
+ audioData.close();
38665
+ };
38666
+ var fixAudioDecoderConfig = (codec, encoderConfig, decoderConfig) => {
38667
+ if (codec === "aac") {
38668
+ if (decoderConfig.description && decoderConfig.description.byteLength > 0 && toUint8Array(decoderConfig.description)[0] === 3) {
38669
+ const { decoderSpecificInfo } = readEsDescriptor(
38670
+ FileSlice4.tempFromBytes(toUint8Array(decoderConfig.description))
38671
+ );
38672
+ decoderConfig.description = decoderSpecificInfo ?? void 0;
38673
+ }
38674
+ let needsDescriptionOverwrite = false;
38675
+ if (!decoderConfig.description || decoderConfig.description.byteLength < 2) {
38676
+ needsDescriptionOverwrite = true;
38677
+ } else {
38678
+ const audioSpecificConfig = parseAacAudioSpecificConfig(toUint8Array(decoderConfig.description));
38679
+ needsDescriptionOverwrite = audioSpecificConfig.objectType === 0;
38680
+ }
38681
+ if (needsDescriptionOverwrite) {
38682
+ const objectType = Number(last(encoderConfig.codec.split(".")));
38683
+ decoderConfig.description = buildAacAudioSpecificConfig({
38684
+ objectType,
38685
+ outputNumberOfChannels: decoderConfig.numberOfChannels,
38686
+ outputSampleRate: decoderConfig.sampleRate
38687
+ });
38688
+ }
38689
+ }
38690
+ };
37944
38691
  var AudioSampleSource = class extends AudioSource {
37945
38692
  /**
37946
38693
  * Creates a new {@link AudioSampleSource} whose samples are encoded according to the specified
@@ -38365,6 +39112,7 @@ ${cue.notes ?? ""}`;
38365
39112
  }
38366
39113
  super(output);
38367
39114
  this.trackDatas = [];
39115
+ this.firstPacketTimestamp = null;
38368
39116
  this.isRelativeToUnixEpoch = false;
38369
39117
  this.numWrittenMasterPlaylists = 0;
38370
39118
  this.playlists = [];
@@ -38374,6 +39122,7 @@ ${cue.notes ?? ""}`;
38374
39122
  this.singleFilePerPlaylist = format._options.singleFilePerPlaylist ?? false;
38375
39123
  this.isLive = format._options.live ?? false;
38376
39124
  this.maxLiveSegmentCount = format._options.maxLiveSegmentCount ?? Infinity;
39125
+ this.mediaTimestampBase = format._options.mediaTimestampBase ?? 10;
38377
39126
  this.globalTargetDuration = this.targetSegmentDuration;
38378
39127
  this.getPlaylistPath = format._options.getPlaylistPath ?? (({ n }) => `playlist-${n}.m3u8`);
38379
39128
  this.getSegmentPath = format._options.getSegmentPath ?? ((info) => info.isSingleFile ? `segments-${info.playlist.n}${info.format.fileExtension}` : `segment-${info.playlist.n}-${info.n}${info.format.fileExtension}`);
@@ -38745,6 +39494,7 @@ ${cue.notes ?? ""}`;
38745
39494
  try {
38746
39495
  this.validateTimestamp(track, packet.timestamp, packet.type === "key");
38747
39496
  trackData.packets.push(packet);
39497
+ this.firstPacketTimestamp ??= packet.timestamp;
38748
39498
  if (playlist.currentSegmentStartTimestamp === null) {
38749
39499
  playlist.currentSegmentStartTimestamp = packet.timestamp;
38750
39500
  } else if (!playlist.currentSegmentStartTimestampIsFixed) {
@@ -38765,6 +39515,7 @@ ${cue.notes ?? ""}`;
38765
39515
  try {
38766
39516
  this.validateTimestamp(track, packet.timestamp, packet.type === "key");
38767
39517
  trackData.packets.push(packet);
39518
+ this.firstPacketTimestamp ??= packet.timestamp;
38768
39519
  if (playlist.currentSegmentStartTimestamp === null) {
38769
39520
  playlist.currentSegmentStartTimestamp = packet.timestamp;
38770
39521
  } else if (!playlist.currentSegmentStartTimestampIsFixed) {
@@ -39100,6 +39851,16 @@ ${cue.notes ?? ""}`;
39100
39851
  decoderConfig: audioTrack.info.decoderConfig,
39101
39852
  primingPacket: audioTrack.info.primingPacket ?? void 0
39102
39853
  });
39854
+ if (!playlist.segmentFormat.supportsTimestampedMediaData && audioEndIndex > 0) {
39855
+ const firstTimestamp = this.toMediaTimestamp(audioTrack.packets[0].timestamp);
39856
+ const pts = secondsToMpegTsTimestamp(firstTimestamp);
39857
+ const priv = new Uint8Array(TIMESTAMP_PRIV_OWNER.length + 1 + 8);
39858
+ priv.set(textEncoder.encode(TIMESTAMP_PRIV_OWNER), 0);
39859
+ const view2 = toDataView(priv);
39860
+ view2.setUint32(TIMESTAMP_PRIV_OWNER.length + 1, Math.floor(pts / 2 ** 32));
39861
+ view2.setUint32(TIMESTAMP_PRIV_OWNER.length + 5, pts % 2 ** 32);
39862
+ output.setMetadataTags({ raw: { PRIV: priv } });
39863
+ }
39103
39864
  }
39104
39865
  await output.start();
39105
39866
  }
@@ -39108,7 +39869,10 @@ ${cue.notes ?? ""}`;
39108
39869
  const meta = { decoderConfig: videoTrack.info.decoderConfig };
39109
39870
  for (let i = 0; i < videoEndIndex; i++) {
39110
39871
  const packet = videoTrack.packets[i];
39111
- await videoSource.add(packet, meta);
39872
+ const offsetPacket = packet.clone({
39873
+ timestamp: this.toMediaTimestamp(packet.timestamp)
39874
+ });
39875
+ await videoSource.add(offsetPacket, meta);
39112
39876
  maxEndTimestamp = Math.max(maxEndTimestamp, packet.timestamp + packet.duration);
39113
39877
  }
39114
39878
  }
@@ -39117,7 +39881,10 @@ ${cue.notes ?? ""}`;
39117
39881
  const meta = { decoderConfig: audioTrack.info.decoderConfig };
39118
39882
  for (let i = 0; i < audioEndIndex; i++) {
39119
39883
  const packet = audioTrack.packets[i];
39120
- await audioSource.add(packet, meta);
39884
+ const offsetPacket = packet.clone({
39885
+ timestamp: this.toMediaTimestamp(packet.timestamp)
39886
+ });
39887
+ await audioSource.add(offsetPacket, meta);
39121
39888
  maxEndTimestamp = Math.max(maxEndTimestamp, packet.timestamp + packet.duration);
39122
39889
  }
39123
39890
  }
@@ -39194,6 +39961,10 @@ ${cue.notes ?? ""}`;
39194
39961
  }
39195
39962
  }
39196
39963
  }
39964
+ toMediaTimestamp(timestamp) {
39965
+ assert(this.firstPacketTimestamp !== null);
39966
+ return timestamp - this.firstPacketTimestamp + this.mediaTimestampBase;
39967
+ }
39197
39968
  async onPlaylistDone(playlist) {
39198
39969
  assert(!playlist.done);
39199
39970
  playlist.done = true;
@@ -40078,6 +40849,9 @@ ${cue.notes ?? ""}`;
40078
40849
  if (!options || typeof options !== "object") {
40079
40850
  throw new TypeError("options must be an object.");
40080
40851
  }
40852
+ if (options.timestampOffset !== void 0 && (!Number.isFinite(options.timestampOffset) || options.timestampOffset < 0)) {
40853
+ throw new TypeError("options.timestampOffset, when provided, must be a non-negative number.");
40854
+ }
40081
40855
  if (options.onPacket !== void 0 && typeof options.onPacket !== "function") {
40082
40856
  throw new TypeError("options.onPacket, when provided, must be a function.");
40083
40857
  }
@@ -40148,6 +40922,9 @@ ${cue.notes ?? ""}`;
40148
40922
  if (options.maxLiveSegmentCount !== void 0 && (typeof options.maxLiveSegmentCount !== "number" || options.maxLiveSegmentCount < 1 || Number.isFinite(options.maxLiveSegmentCount) && !Number.isInteger(options.maxLiveSegmentCount))) {
40149
40923
  throw new TypeError("options.maxLiveSegmentCount, when provided, must be a positive integer or Infinity.");
40150
40924
  }
40925
+ if (options.mediaTimestampBase !== void 0 && !Number.isFinite(options.mediaTimestampBase)) {
40926
+ throw new TypeError("options.mediaTimestampBase, when provided, must be a finite number.");
40927
+ }
40151
40928
  if (options.getPlaylistPath !== void 0 && typeof options.getPlaylistPath !== "function") {
40152
40929
  throw new TypeError("options.getPlaylistPath, when provided, must be a function.");
40153
40930
  }
@@ -40191,6 +40968,9 @@ ${cue.notes ?? ""}`;
40191
40968
  }
40192
40969
  getSupportedCodecs() {
40193
40970
  const uniqueCodecs = new Set(toArray(this._options.segmentFormat).flatMap((x) => x.getSupportedCodecs()));
40971
+ for (const codec of AUDIO_CODECS_WITH_DELTA_PACKETS) {
40972
+ uniqueCodecs.delete(codec);
40973
+ }
40194
40974
  return [...uniqueCodecs];
40195
40975
  }
40196
40976
  getSupportedTrackCounts() {
@@ -41786,7 +42566,7 @@ The @mediabunny/mp3-encoder extension package provides support for encoding MP3.
41786
42566
  const tempSource = new VideoSampleSource(encodingConfig);
41787
42567
  tempOutput.addVideoTrack(tempSource);
41788
42568
  await tempOutput.start();
41789
- const sink = new VideoSampleSink(track);
42569
+ const sink = new VideoSampleSink(track, { hardwareAcceleration: trackOptions.hardwareAcceleration });
41790
42570
  const firstSample = __using(_stack, await sink.getSample(await track.getFirstTimestamp()));
41791
42571
  if (firstSample) {
41792
42572
  try {
@@ -41836,7 +42616,7 @@ The @mediabunny/mp3-encoder extension package provides support for encoding MP3.
41836
42616
  const source = new VideoSampleSource(encodingConfig);
41837
42617
  videoSource = source;
41838
42618
  this._registerTrackPump(async (pump) => {
41839
- const sink = new VideoSampleSink(track);
42619
+ const sink = new VideoSampleSink(track, { hardwareAcceleration: trackOptions.hardwareAcceleration });
41840
42620
  for await (var _sample of sink.samples(this._startTimestamp, this._endTimestamp)) {
41841
42621
  var _stack2 = [];
41842
42622
  try {
@@ -41919,18 +42699,17 @@ The @mediabunny/mp3-encoder extension package provides support for encoding MP3.
41919
42699
  let copyStartPacket = null;
41920
42700
  if (!needsTranscode) {
41921
42701
  const sink = new EncodedPacketSink(track);
41922
- let startPacket = await sink.getKeyPacket(this._startTimestamp) ?? await sink.getFirstKeyPacket();
42702
+ let startPacket = await sink.getKeyPacket(this._startTimestamp, { verifyKeyPackets: true }) ?? await sink.getFirstKeyPacket({ verifyKeyPackets: true });
41923
42703
  if (startPacket && (this._copyBoundaryPolicy === "shrink" && startPacket.timestamp < this._startTimestamp || this._copyBoundaryPolicy === "expand" && startPacket.timestamp + startPacket.duration <= this._startTimestamp)) {
41924
- startPacket = await sink.getNextKeyPacket(startPacket);
42704
+ startPacket = await sink.getNextKeyPacket(startPacket, { verifyKeyPackets: true });
41925
42705
  }
41926
- const hasDecoderWarmup = NON_PCM_AUDIO_CODECS.includes(sourceCodec) && sourceCodec !== "flac";
41927
- if (startPacket && this._copyBoundaryPolicy === "expand" && hasDecoderWarmup) {
41928
- const previousPacket = await sink.getKeyPacket(
41929
- startPacket.timestamp - 1 / await track.getTimeResolution()
41930
- );
41931
- if (previousPacket) {
41932
- startPacket = previousPacket;
41933
- }
42706
+ const preRollDuration = await track.getPreRollDuration();
42707
+ assert(preRollDuration !== null);
42708
+ if (startPacket && this._copyBoundaryPolicy === "expand" && preRollDuration > 0) {
42709
+ startPacket = await sink.getKeyPacket(
42710
+ startPacket.timestamp - preRollDuration,
42711
+ { verifyKeyPackets: true }
42712
+ ) ?? await sink.getFirstKeyPacket({ verifyKeyPackets: true });
41934
42713
  }
41935
42714
  copyStartPacket = startPacket;
41936
42715
  if (startPacket) {