/* This file is part of jellything (https://codeberg.org/metamuffin/jellything) which is licensed under the GNU Affero General Public License (version 3); see /COPYING. Copyright (C) 2026 metamuffin */ /// import { FormatInfo, StreamContainer } from "./types_stream.ts"; const cache = new Map() export type CodecSupport = "unsupported" | "supported" | "supported_smooth" export async function test_media_capability(format: FormatInfo, container: StreamContainer): Promise { const cache_key = JSON.stringify(format) + container const cached = cache.get(cache_key); if (cached !== undefined) return cached const r = await test_media_capability_inner(format, container) console.log(`media caps: codec=${format.codec} sup=${r}`); cache.set(cache_key, r) return r } async function test_media_capability_inner(format: FormatInfo, container: StreamContainer): Promise { if (format.codec == "S_TEXT/WEBVTT" || format.codec == "S_TEXT/UTF8" || format.codec == "D_WEBVTT/SUBTITLES") { return "supported" } let res; if (format.codec.startsWith("A_")) { res = await navigator.mediaCapabilities.decodingInfo({ type: "media-source", audio: { contentType: track_to_content_type(format, container), samplerate: format.samplerate, channels: "" + format.channels, bitrate: format.bitrate, } }) } else if (format.codec.startsWith("V_")) { res = await navigator.mediaCapabilities.decodingInfo({ type: "media-source", video: { contentType: track_to_content_type(format, container), framerate: format.samplerate ?? 60, width: format.width ?? 1920, height: format.height ?? 1080, bitrate: format.bitrate } }) } else { res = { supported: false, smooth: false } } return res.supported ? (res.smooth ? "supported_smooth" : "supported") : "unsupported" } export function track_to_content_type(format: FormatInfo, container: StreamContainer): string { let c = CONTAINER_TO_MIME_TYPE[container]; if (format.codec.startsWith("A_")) c = c.replace("video/", "audio/") return `${c}; codecs="${format.codec_param}"` } const CONTAINER_TO_MIME_TYPE: { [key in StreamContainer]: string } = { webvtt: "text/webvtt", webm: "video/webm", matroska: "video/x-matroska", mpeg4: "video/mp4", jvtt: "application/jellything-vtt+json" }