分包+主播库
This commit is contained in:
82
src/composables/useStreams.js
Normal file
82
src/composables/useStreams.js
Normal file
@@ -0,0 +1,82 @@
|
||||
// composables/useStreams.js
|
||||
import { nextTick } from 'vue'
|
||||
|
||||
export function useStreams({ instanceList, videoElement, wslist, openStr, VideoConverter }) {
|
||||
// 用 Map 做延迟队列,避免固定 8 个的限制
|
||||
const feedState = new Map()
|
||||
|
||||
function ensureState(index) {
|
||||
if (!feedState.has(index)) {
|
||||
feedState.set(index, { processing: false, pending: null })
|
||||
}
|
||||
return feedState.get(index)
|
||||
}
|
||||
|
||||
function pushFrame(index, buf) {
|
||||
const st = ensureState(index)
|
||||
if (st.processing) {
|
||||
// 覆盖旧的等待帧,保留最新
|
||||
st.pending = buf
|
||||
return
|
||||
}
|
||||
st.processing = true
|
||||
try {
|
||||
instanceList[index].converter.appendRawData(new Uint8Array(buf))
|
||||
} finally {
|
||||
st.processing = false
|
||||
if (st.pending) {
|
||||
const next = st.pending
|
||||
st.pending = null
|
||||
queueMicrotask(() => pushFrame(index, next))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function resetFeedState(index) {
|
||||
const st = feedState.get(index)
|
||||
if (!st) return
|
||||
st.processing = false
|
||||
st.pending = null
|
||||
}
|
||||
|
||||
async function waitForVideoEl(udid, tries = 20, delay = 16) {
|
||||
for (let i = 0; i < tries; i++) {
|
||||
const el = videoElement.value?.[udid]
|
||||
if (el) return el
|
||||
await nextTick()
|
||||
await new Promise(r => setTimeout(r, delay))
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
function refreshStream(index, hard = true) {
|
||||
const devices = Object.keys(videoElement.value || {})
|
||||
const udid = devices[index]
|
||||
const video = videoElement.value?.[udid]
|
||||
if (!video || !instanceList[index]) return
|
||||
|
||||
resetFeedState(index)
|
||||
try { instanceList[index].converter?.destroy?.() } catch { }
|
||||
instanceList[index].converter = null
|
||||
|
||||
if (hard) {
|
||||
try { video.pause?.() } catch { }
|
||||
try { video.removeAttribute?.('src') } catch { }
|
||||
try { video.load?.() } catch { }
|
||||
}
|
||||
|
||||
// 重新挂新的 converter
|
||||
instanceList[index].converter = new VideoConverter(video, 60, 1)
|
||||
|
||||
// 让后端尽快推关键帧
|
||||
try { wslist[index]?.send?.(openStr) } catch { }
|
||||
}
|
||||
|
||||
return {
|
||||
feedState,
|
||||
pushFrame,
|
||||
resetFeedState,
|
||||
waitForVideoEl,
|
||||
refreshStream,
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user