@geekapps/silo-elements-nextjs 0.3.21 → 0.3.23

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.
@@ -20,9 +20,8 @@ function deviceSupportsHdr() {
20
20
  function deviceSupportsOpus() {
21
21
  if (typeof window === "undefined") return false;
22
22
  try {
23
- if (typeof MediaSource !== "undefined" && MediaSource.isTypeSupported) {
24
- if (MediaSource.isTypeSupported('audio/mp4; codecs="opus"')) return true;
25
- }
23
+ if (typeof MediaSource !== "undefined" && MediaSource.isTypeSupported)
24
+ return MediaSource.isTypeSupported('audio/mp4; codecs="opus"');
26
25
  const a = document.createElement("audio");
27
26
  return a.canPlayType('audio/ogg; codecs="opus"') !== "" || a.canPlayType('video/mp4; codecs="opus"') !== "";
28
27
  } catch {
@@ -873,6 +872,22 @@ function Video({
873
872
  const Hls = HlsModule.default;
874
873
  console.debug("[Silo/hls] Hls.isSupported()=", Hls.isSupported());
875
874
  if (Hls.isSupported()) {
875
+ let tryNextAudioTrack2 = function() {
876
+ const next = mappedAudioTracks.find((t) => t.supported && !failedAudioTracks.has(t.id));
877
+ if (next) {
878
+ console.debug("[Silo/hls] trying audio track", next.id, next.codec || "(unknown codec)");
879
+ hls.audioTrack = next.id;
880
+ if (pinnedAudio === -1) setSelectedAudio(next.id);
881
+ } else {
882
+ console.warn("[Silo/hls] all audio tracks failed \u2014 disabling demuxed audio");
883
+ setAudioTracks([]);
884
+ try {
885
+ hls.audioTrack = -1;
886
+ } catch {
887
+ }
888
+ }
889
+ };
890
+ var tryNextAudioTrack = tryNextAudioTrack2;
876
891
  const hls = new Hls({
877
892
  enableWorker: true,
878
893
  // Buffer ~20s ahead (≈1/6 of a 2min video). maxMaxBufferLength caps the
@@ -934,32 +949,27 @@ function Video({
934
949
  if (pinnedAudio >= 0) hls.audioTrack = pinnedAudio;
935
950
  setIsLoading(false);
936
951
  });
952
+ let mappedAudioTracks = [];
953
+ const failedAudioTracks = /* @__PURE__ */ new Set();
937
954
  hls.on(Hls.Events.AUDIO_TRACKS_UPDATED, (_, data) => {
938
955
  const tracks = data.audioTracks ?? [];
939
956
  console.debug("[Silo/hls] AUDIO_TRACKS_UPDATED", tracks.length);
940
957
  if (tracks.length > 0) {
941
- const mapped = tracks.map((t, i) => {
958
+ mappedAudioTracks = tracks.map((t, i) => {
942
959
  const codec = (t.attrs?.CODECS ?? t.codecSet ?? "").split(",")[0]?.trim() ?? "";
943
960
  const supported = deviceSupportsAudioCodec(codec);
944
961
  const label = friendlyAudioLabel(t.name, t.lang, codec, t.channels ?? t.attrs?.CHANNELS);
945
- return { id: i, label, supported };
962
+ return { id: i, label, supported, codec };
946
963
  });
947
- const currentTrackIdx = hls.audioTrack ?? 0;
948
- if (mapped[currentTrackIdx] && !mapped[currentTrackIdx].supported) {
949
- const firstSupported = mapped.findIndex((t) => t.supported);
950
- if (firstSupported >= 0) {
951
- console.debug("[Silo/hls] current audio track unsupported \u2014 switching to track", firstSupported);
952
- hls.audioTrack = firstSupported;
953
- if (pinnedAudio === -1) setSelectedAudio(firstSupported);
954
- } else {
955
- console.warn("[Silo/hls] no supported audio track found \u2014 disabling separate audio");
956
- try {
957
- hls.audioTrack = -1;
958
- } catch {
959
- }
964
+ if (pinnedAudio === -1) {
965
+ const first = mappedAudioTracks.find((t) => t.supported) ?? mappedAudioTracks[0];
966
+ if (first) {
967
+ hls.audioTrack = first.id;
968
+ setSelectedAudio(first.id);
969
+ console.debug("[Silo/hls] starting with audio track", first.id, first.codec || "(unknown codec)");
960
970
  }
961
971
  }
962
- if (mapped.length > 1) setAudioTracks(mapped);
972
+ if (mappedAudioTracks.length > 1) setAudioTracks(mappedAudioTracks.map(({ id, label, supported }) => ({ id, label, supported })));
963
973
  }
964
974
  if (pinnedAudio >= 0 && hls.audioTrack !== pinnedAudio) {
965
975
  hls.audioTrack = pinnedAudio;
@@ -993,7 +1003,6 @@ function Video({
993
1003
  console.debug("[Silo/hls] FRAG_LOADED", data.frag?.type, data.frag?.sn);
994
1004
  });
995
1005
  let mediaErrorAttempts = 0;
996
- let audioAppendErrors = 0;
997
1006
  let stalledOnPinnedLevel = 0;
998
1007
  hls.on(Hls.Events.ERROR, (_, data) => {
999
1008
  const fragUrl = (data.frag?.url ?? data.url ?? "").slice(-80);
@@ -1002,18 +1011,12 @@ function Video({
1002
1011
  if (!data.fatal) {
1003
1012
  const isAudioBufError = fragType === "audio" && (data.details === Hls.ErrorDetails.BUFFER_APPEND_ERROR || data.details === Hls.ErrorDetails.BUFFER_APPENDING_ERROR);
1004
1013
  if (isAudioBufError) {
1005
- audioAppendErrors += 1;
1006
- if (audioAppendErrors >= 3) {
1007
- console.warn("[Silo/hls] repeated audio buffer errors \u2014 disabling separate audio tracks");
1008
- setAudioTracks([]);
1009
- try {
1010
- hls.audioTrack = -1;
1011
- } catch {
1012
- }
1013
- audioAppendErrors = 0;
1014
+ const failedTrack = hls.audioTrack;
1015
+ if (failedTrack >= 0 && pinnedAudio === -1) {
1016
+ failedAudioTracks.add(failedTrack);
1017
+ console.warn("[Silo/hls] audio track", failedTrack, "failed \u2014 trying next");
1018
+ tryNextAudioTrack2();
1014
1019
  }
1015
- } else {
1016
- audioAppendErrors = 0;
1017
1020
  }
1018
1021
  if (data.details === Hls.ErrorDetails.BUFFER_STALLED_ERROR && pinnedLevel >= 0) {
1019
1022
  stalledOnPinnedLevel += 1;