7

アップデート:

SOオフセットタイムスタンププロパティを使用してこれを機能させることができました(各ビデオを追加した後にインクリメントします)。

私の質問: 1) MediaSource.mode をシーケンスに設定するときに、これが正しく行われないのはなぜですか?

2) MediaSource.duration が常に「Infinity」であり、正しい期間ではないのはなぜですか?


MediaSource API を使用して、複数のビデオ ファイルを追加し、1 つのビデオのようにシームレスに再生しようとしています。

仕様 (DASH-MPEG) に従ってビデオを適切にトランスコードしましたが、個別に再生すると正常に動作します。

ただし、複数を追加しようとすると、セグメントが互いに上書きされたり、期間が正しくないなどの問題が発生します。すべてが期待どおりに実行されているように見えますが。

私はoffsetTimestampをいじってみましたが、ドキュメントによると、MediaSource.modeを「sequence」に設定すると、これが自動的に処理されます。また、何らかの理由で、セグメントを追加した後でも MediaSource.duration は常に「無限」のようです。

これが私のコードです:

<script>
 function downloadData(url, cb) {
    console.log("Downloading " + url);

    var xhr = new XMLHttpRequest;
    xhr.open('get', url);
    xhr.responseType = 'arraybuffer';
    xhr.onload = function () {
        cb(new Uint8Array(xhr.response));
    };
    xhr.send();
}

if (MediaSource.isTypeSupported('video/mp4; codecs="avc1.64001E"')) {
    console.log("mp4 codec supported");
}

var videoSources = [
    "{% static 'mp4/ff_97.mp4' %}",
    "{% static 'mp4/ff_98.mp4' %}",
    "{% static 'mp4/ff_99.mp4' %}",
    "{% static 'mp4/ff_118.mp4' %}"
]

var mediaSource = new MediaSource();


mediaSource.addEventListener('sourceopen', function(e) {


    var sourceBuffer = mediaSource.addSourceBuffer('video/mp4; codecs="avc1.64001E"');
    sourceBuffer.mode = 'sequence';

    console.log('SourceBuffer mode set to ' + sourceBuffer.mode);

    sourceBuffer.addEventListener('updateend', function(e) {
        console.log('Finished updating buffer');
        console.log('New duration is ' + String(mediaSource.duration));

        if (videoSources.length == 0) {
            mediaSource.endOfStream();
            video.currentTime = 0;
            video.play();
            return;
        }

        downloadData(videoSources.pop(), function(arrayBuffer) {
            console.log('Finished downloading buffer of size ' + String(arrayBuffer.length));
            console.log('Updating buffer');
            sourceBuffer.appendBuffer(arrayBuffer);
        });

        console.log('New duration: ' + String(mediaSource.duration));

    });

    downloadData(videoSources.pop(), function(arrayBuffer) {
        console.log('Finished downloading buffer of size ' + String(arrayBuffer.length));
        console.log('Updating buffer');
        sourceBuffer.appendBuffer(arrayBuffer);
    });



}, false);

var video = document.querySelector('video');
video.src = window.URL.createObjectURL(mediaSource);

そして、ここにログがあります:

mp4 codec supported
(index):78 SourceBuffer mode set to sequence
(index):45 Downloading /static/mp4/ff_118.mp4
(index):103 Finished downloading buffer of size 89107
(index):104 Updating buffer
(index):81 Finished updating buffer
(index):82 New duration is Infinity
(index):45 Downloading /static/mp4/ff_99.mp4
(index):98 New duration: Infinity
(index):92 Finished downloading buffer of size 46651
(index):93 Updating buffer
(index):81 Finished updating buffer
(index):82 New duration is Infinity
(index):45 Downloading /static/mp4/ff_98.mp4
(index):98 New duration: Infinity
(index):92 Finished downloading buffer of size 79242
(index):93 Updating buffer
(index):81 Finished updating buffer
(index):82 New duration is Infinity
(index):45 Downloading /static/mp4/ff_97.mp4
(index):98 New duration: Infinity
(index):92 Finished downloading buffer of size 380070
(index):93 Updating buffer
(index):81 Finished updating buffer
(index):82 New duration is Infinity
4

2 に答える 2

4

2) MediaSource.duration が常に「Infinity」であり、正しい期間ではないのはなぜですか?

MediaSource.endOfStream()MediaSource オブジェクトがその 内のセグメントの実際の継続時間を計算するには、を呼び出す必要がありますSourceBuffer。これを行っているのはわかりますが、 をMediaSource.duration呼び出す前にアクセスしようとしているようですendOfStream()MSE 仕様のストリーム アルゴリズムの終わりを読むことをお勧めします。これにより、期間変更アルゴリズムが呼び出されることがわかります。

<video>要素が を呼び出す前に期間を報告するようにしたい場合は、追加されたセグメントの独自の見積もりに基づいて、を使用してMediaSource.endOfStream()実際に値を設定できます。MediaSource.duration

1) MediaSource.mode をシーケンスに設定すると、これが正しく行われないのはなぜですか?

私の知る限り、そうすべきです。しかし、バッファ内のはるか先にセグメントを追加したい場合に柔軟性が向上するため、私は明示的なtimestampOffsetアプローチを好みました(つまり、ユーザーが現在のバッファの終わりよりも先にシークする場合、ギャップの後にロード+追加を開始する必要があります) )。私はあなたのユースケースの要件ではないことを感謝しています.

于 2016-02-06T16:57:15.157 に答える