Запись экрана с использованием RecordRTC - Невозможно записать видео звуки, воспроизводимые на экране или через динамик - PullRequest
0 голосов
/ 03 мая 2018

Я пытаюсь записать экран с воспроизведением видео на экране + микрофон пользователя.

См. Демонстрацию: https://jsfiddle.net/4z447wpn/5/

Код ниже:

<!DOCTYPE html>
<html>
<head>
<title>Screen recording using RecordRTC</title>
<style>
    html, body{
        margin: 0!important;
        padding: 0!important;
        width: 100%;
        height: 100%;
    }
</style>
</head>
<body>

<video controls autoplay height="600" width="800" style="float: left; margin-top: 20px"></video>

<iframe width="420" height="315"  style="float: right; margin-top: 20px"
src="https://www.youtube.com/embed/9Zr2jjg1X-U">
</iframe> 

<script src="https://cdn.webrtc-experiment.com/RecordRTC.js"></script>
<script src="https://webrtc.github.io/adapter/adapter-latest.js"></script>
<script src="https://cdn.WebRTC-Experiment.com/getScreenId.js"></script>
<script>
function captureScreen(cb) {
    getScreenId(function (error, sourceId, screen_constraints) {
        navigator.mediaDevices.getUserMedia(screen_constraints).then(cb).catch(function(error) {
          console.error('getScreenId error', error);
          alert('Failed to capture your screen. Please check browser console logs for further information.');
        });
    });
}
function captureAudio(cb) {
    navigator.mediaDevices.getUserMedia({audio: true, video: false}).then(cb);
}
function keepStreamActive(stream) {
    var video = document.createElement('video');
    video.muted = true;
    setSrcObject(stream, video);
    video.style.display = 'none';
    (document.body || document.documentElement).appendChild(video);
}

captureScreen(function(screen) {
    keepStreamActive(screen);

    captureAudio(function(mic) {
        keepStreamActive(mic);

        screen.width = window.screen.width;
        screen.height = window.screen.height;
        screen.fullcanvas = true;

        var recorder = RecordRTC([screen, mic], {
            type: 'video',
            mimeType: 'video/webm',
            previewStream: function(s) {
                document.querySelector('video').muted = true;
                setSrcObject(s, document.querySelector('video'));
            }
        });

        //Start recording
        recorder.startRecording();

        //Stop recording after specific seconds
        setTimeout(function() {
            recorder.stopRecording(function() {
                var blob = recorder.getBlob();
                document.querySelector('video').src = URL.createObjectURL(blob);
                document.querySelector('video').muted = false;
                screen.getVideoTracks().forEach(function(track) {
                    track.stop();
                });
                screen.getAudioTracks().forEach(function(track) {
                    track.stop();
                });
                mic.getVideoTracks().forEach(function(track) {
                    track.stop();
                });
                mic.getAudioTracks().forEach(function(track) {
                    track.stop();
                });
            });
        }, 20 * 1000);

    });
});
</script>
</body>
</html>

Примечания:

(1) Воспроизведение видео iframe (загруженного справа) быстро после того, как вы разрешите доступ к экрану браузера и микрофону, чтобы оно начало все записывать и через 20 секунд автоматически остановится и воспроизведет записанное видео. Приостановить правое видео для прослушивания записанного звука.

(2) пользователю Chrome необходимо установить расширение: https://chrome.google.com/webstore/detail/screen-capturing/ajhifddimkapgcifgcodmmfdlknahffk

Проблемы, с которыми я сталкиваюсь:

(1) Это не запись звуков, воспроизводимых в видео на экране. Хотя он захватывает весь экран с микрофоном пользователя.

(2) Если я выберу текущий экран в качестве окна захвата экрана, он отобразит тот же экран в цикле.

См. Проблемы на изображении: recordRTC-screenshot

1 Ответ

0 голосов
/ 04 мая 2018

Ваша демонстрация работает на локальном хосте или на веб-сайте HTTP, не основанном на iframe, после передачи параметра " second " через getScreenId, например,

getScreenId(callback, true);

Где второй аргумент, т. Е. Логическое значение true , включило динамики .

Примечание. Если функция по-прежнему не работает, выполните тестирование в режиме инкогнито, чтобы игнорировать / обойти кэш.

Примечание 2: Тестирование на локальном хосте или на веб-сайте, не поддерживающем iframe, т.е. на собственном домене вместо jsfiddle.


Обновлен ответ во вторник, 8 мая 2018 года

Пожалуйста, попробуйте этот код:

<!DOCTYPE html>
<html>
<head>
    <title>Screen recording using RecordRTC</title>
    <style>
        html, body{
            margin: 0!important;
            padding: 0!important;
            width: 100%;
            height: 100%;
        }
    </style>
</head>
<body>
    <button class="btn btn-primary" id="stoprecording">STOP RECORDING</button>

    <video id="preview-screen" controls autoplay height="600" width="800" style="float: left; margin-top: 20px"></video>

    <video width="420" height="315" controls="" autoplay="" loop="" style="float: right; margin-top: 20px" onloadedmetadata="typeof OnLoadedMetaData === 'function' ? OnLoadedMetaData() : setTimeout(function() {OnLoadedMetaData();}, 3000);">
        <source src="https://commondatastorage.googleapis.com/gtv-videos-bucket/sample/BigBuckBunny.mp4" type="video/mp4">
    </video>

    <script src="https://cdn.webrtc-experiment.com/RecordRTC.js"></script>
    <script src="https://webrtc.github.io/adapter/adapter-latest.js"></script>
    <script src="https://cdn.WebRTC-Experiment.com/getScreenId.js"></script>
    <script>
    function captureScreen(cb) {
        getScreenId(function (error, sourceId, screen_constraints) {
            navigator.mediaDevices.getUserMedia(screen_constraints).then(cb).catch(function(error) {
              console.error('getScreenId error', error);
              alert('Failed to capture your screen. Please check browser console logs for further information.');
            });
        }, true);
    }
    function captureAudio(cb) {
        navigator.mediaDevices.getUserMedia({audio: true, video: false}).then(cb);
    }
    function keepStreamActive(stream) {
        var video = document.createElement('video');
        video.muted = true;
        setSrcObject(stream, video);
        video.style.display = 'none';
        (document.body || document.documentElement).appendChild(video);
    }

    var recorder = '';
    var screenRec = '';
    var micRec = '';

    function OnLoadedMetaData (){
        captureScreen(function(screen) {
            keepStreamActive(screen);

            captureAudio(function(mic) {
                keepStreamActive(mic);

                screen.width = window.screen.width;
                screen.height = window.screen.height;
                screen.fullcanvas = true;

                recorder = RecordRTC([screen, mic], {
                    type: 'video',
                    mimeType: 'video/webm',
                    previewStream: function(s) {
                        document.querySelector('#preview-screen').muted = true;
                        setSrcObject(s, document.querySelector('#preview-screen'));
                    }
                });

                screenRec = screen;
                micRec = mic;

                //Start recording
                recorder.startRecording();

            });

            addStreamStopListener(screen, function() {
                btnStopRecording.click();
            });
        });
    }

    var btnStopRecording = document.getElementById('stoprecording');
    btnStopRecording.onclick = function() {
        this.disabled = true;

        recorder.stopRecording(function() {
            var blob = recorder.getBlob();

            document.querySelector('#preview-screen').src = URL.createObjectURL(blob);
            document.querySelector('#preview-screen').muted = false;

            screenRec.getTracks().concat(micRec.getTracks()).forEach(function(track) {
                track.stop();
            });
        });
    };

    function addStreamStopListener(stream, callback) {
        var streamEndedEvent = 'ended';
        if ('oninactive' in stream) {
            streamEndedEvent = 'inactive';
        }
        stream.addEventListener(streamEndedEvent, function() {
            callback();
            callback = function() {};
        }, false);
        stream.getAudioTracks().forEach(function(track) {
            track.addEventListener(streamEndedEvent, function() {
                callback();
                callback = function() {};
            }, false);
        });
        stream.getVideoTracks().forEach(function(track) {
            track.addEventListener(streamEndedEvent, function() {
                callback();
                callback = function() {};
            }, false);
        });
    }
    </script>
</body>
</html>
...