MediaRecorder API 소개

27205 단어 webjavascript
인터넷에서 우리는 capture media streams from the user's camera, microphoneeven desktop을 볼 수 있다.우리는 이러한 미디어 흐름을 real time video chat over WebRTC에 사용할 수 있으며, MediaRecorder API을 통해 웹 브라우저에서 사용자의 오디오나 동영상을 직접 녹음하고 저장할 수 있다.
MediaRecorder API를 탐색하기 위해 HTML, CSS, JavaScript로 간단한 오디오 레코더 응용 프로그램을 구축합니다.

입문


이 프로그램을 구축하려면 텍스트 편집기 하나와 browser that supports the MediaRecorded API이 필요합니다.이 문서를 작성할 때 지원하는 브라우저는 Firefox, Chrome, Opera입니다.이 API를 Edge 및 Safari에 도입하는 작업도 진행 중입니다.
우선, this HTML filethis CSS file을 저장하는 폴더를 만들어서 시작합니다.CSS 파일 이름이 web-recorder-style.css인 동일한 폴더에 있는지 확인합니다.브라우저에서 HTML 파일을 열면 다음 내용이 표시됩니다.

이제 MediaRecorder API를 살펴보겠습니다.

MediaRecorder API


MediaRecorder API를 시작하려면 MediaStream이 필요합니다.<video> 또는 <audio> 요소에서 얻을 수 있으며, getUserMedia으로 전화를 걸어 사용자의 카메라와 마이크를 포착할 수도 있습니다.일단 흐름이 생기면, MediaRecorder을 초기화하면 녹화할 수 있다.
기록 기간에 MediaRecorder 대상은 dataavailable개의 이벤트를 발송하는데 그 중에서 기록된 데이터는 사건의 일부분이다.우리는 이 사건들을 정탐하고 수조의 데이터 블록을 정리할 것이다.녹화가 끝난 후, 우리는 블록 그룹을 Blob 대상에 다시 연결할 것이다.우리는 start 대상에 stopMediaRecorder을 호출하여 녹화의 시작과 끝을 제어할 수 있다.
우리들에게 그것의 실제 효과를 좀 봅시다.

getUserMedia


우리는 먼저 일부 사용자 인터페이스를 연결하고 첫 번째 단추를 사용하여 사용자의 마이크 흐름에 접근할 것이다.다운로드한 starter HTML 하단의 <script> 태그 사이에 이벤트를 등록하고 페이지 내용을 불러온 후 실행한 다음 우리가 사용할 UI 위치를 수집합니다.
<script>
  window.addEventListener('DOMContentLoaded', () => {
    const getMic = document.getElementById('mic');
    const recordButton = document.getElementById('record');
    const list = document.getElementById('recordings');

  });
</script>
다음으로, 우리는 브라우저가 우리가 작성하고 있는 코드를 지원하는지 검사할 것이다.없으면 페이지에 오류가 표시됩니다.
<script>
  window.addEventListener('DOMContentLoaded', () => {
    const getMic = document.getElementById('mic');
    const recordButton = document.getElementById('record');
    const list = document.getElementById('recordings');
    if ('MediaRecorder' in window) {
      // everything is good, let's go ahead
    } else {
      renderError("Sorry, your browser doesn't support the MediaRecorder API, so this demo will not work.");
    }
  });
</script>
renderError 방법에 대해, 우리는 <main> 요소의 내용을 오류 메시지로 대체할 것입니다.이벤트 탐지기 다음에 이 방법을 추가합니다.
    function renderError(message) {
      const main = document.querySelector('main');
      main.innerHTML = `<div class="error"><p>${message}</p></div>`;
    }
만약 우리가 MediaRecorder을 사용할 수 있다면, 우리는 지금 마이크로 녹화를 해야 한다.이를 위해, 우리는 getUserMedia API을 사용할 것이다.우리는 마이크에 대한 접근을 직접 요청하지 않을 것이다. 왜냐하면 이것은 어떤 사용자에게도 나쁜 체험이기 때문이다.반대로, 우리는 사용자가 단추를 누르면 마이크에 접근하고 물어보기를 기다릴 것이다.
    if ('MediaRecorder' in window) {
      getMic.addEventListener('click', async () => {
        getMic.setAttribute('hidden', 'hidden');
        try {
          const stream = await navigator.mediaDevices.getUserMedia({
            audio: true,
            video: false
          });
          console.log(stream);
        } catch {
          renderError(
            'You denied access to the microphone so this demo will not work.'
          );
        }
      });
    } else {
사용자가 미디어에 접근할 수 있도록 허락하면 navigator.mediaDevices.getUserMedia을 호출하여 약속을 되돌려줍니다.우리가 사용하는 것은 현대 자바스크립트이기 때문에, 우리는 async/await을 사용하여 이 약속을 동기화시킬 수 있다.우리는 클릭 처리 프로그램이 async 함수라고 성명한 다음에 getUserMedia을 호출할 때 await이 결과를 되돌려주고 계속합니다.
사용자가 마이크에 접근하는 것을 거부할 수도 있습니다. 우리는 호출을 try/catch 문장에 포장하여 처리할 것입니다.거부는 catch 블록을 실행합니다. renderError 함수를 다시 사용합니다.
파일을 저장하고 브라우저에서 엽니다.마이크 가져오기 버튼을 클릭합니다.마이크에 접근할 것인지 물어볼 것입니다. 받아들일 때 결과 MediaStream이 콘솔에 기록됩니다.

레코드


이제 우리는 마이크를 사용할 수 있다. 우리는 녹음기를 준비할 수 있다.우리는 또한 우리가 필요로 하는 다른 변수를 저장할 것이다.우선, 우리가 사용할 MIME 형식은 "audio/webm"입니다.이것은 브라우저가 오늘날까지 기록할 가장 광범위하게 지원하는 형식인 것 같다.우리는 또한 chunks이라는 수조를 만들어서 창설할 때의 일부 기록을 저장할 것이다.
MediaRecorder is initialised은 사용자 마이크에서 캡처한 미디어 흐름과 옵션 대상을 포함하고 앞에서 정의한 MIME 유형을 전달합니다.이전 console.log에서 다음으로 교체:
        try {
          const stream = await navigator.mediaDevices.getUserMedia({
            audio: true,
            video: false
          });
          const mimeType = 'audio/webm';
          let chunks = [];
          const recorder = new MediaRecorder(stream, { type: mimeType });
현재 MediaRecorder을 만들었습니다. 이벤트 탐지기를 설치해야 합니다.기록기는 여러 가지 다른 원인에서 사건을 낸다.많은 것들이 녹음기 자체의 상호작용과 관련이 있기 때문에 녹음, 정지, 복구, 정지를 시작할 때 이벤트를 들을 수 있습니다.가장 중요한 사건은 dataavailable 사건으로 이 사건은 기록기가 적극적으로 기록할 때 정기적으로 발생한다.이 이벤트는 기록의 일부분을 포함하고 있으며, 우리는 그것을 방금 만든 chunks 진열로 추정합니다.
응용 프로그램에 대해 dataavailable 이벤트 수집 블록을 듣고 stop 이벤트가 발생하면 모든 블록을 Blob 에 수집한 다음에 <audio> 요소를 사용하여 재생하고 chunks의 그룹을 재설정할 수 있습니다.
           const recorder = new MediaRecorder(stream, { type: mimeType });
           recorder.addEventListener('dataavailable', event => {
             if (typeof event.data === 'undefined') return;
               if (event.data.size === 0) return;
               chunks.push(event.data);
             });
           recorder.addEventListener('stop', () => {
             const recording = new Blob(chunks, {
               type: mimeType
             });
             renderRecording(recording, list);
             chunks = [];
           });
우리는 곧 renderRecording방법을 실현할 것이다.우리는 녹화를 시작하고 멈추기 위해 단추를 사용하기 위해 더 많은 일을 할 수 있을 뿐이다.
우리는 기록 숨기기 단추를 취소하고 이 단추를 눌렀을 때 기록기 자체의 상태에 따라 기록을 시작하거나 정지해야 한다.코드는 다음과 같습니다.
           const recorder = new MediaRecorder(stream, { type: mimeType });
           recorder.addEventListener('dataavailable', event => {
             if (typeof event.data === 'undefined') return;
               if (event.data.size === 0) return;
               chunks.push(event.data);
             });
           recorder.addEventListener('stop', () => {
             const recording = new Blob(chunks, {
               type: mimeType
             });
             renderRecording(recording, list);
             chunks = [];
           });
이 작은 프로그램을 완성하기 위해서, 우리는 녹음을 <audio>개의 요소로 과장하고, 사용자가 녹음을 데스크톱에 저장할 수 있도록 다운로드 링크를 제공할 것이다.여기서 관건은 Blob 방법으로 우리가 만든 URL.createObjectURL을 URL로 변환할 수 있다는 것이다.그리고 이 URL은 src 요소의 <audio> 및 닻의 href으로 사용할 수 있습니다.닻이 파일을 다운로드할 수 있도록 download 속성을 설정했습니다.
이 함수는 DOM 요소를 생성하고 기록 시간에 따라 파일 이름을 생성하는 데 주로 사용됩니다.renderError 함수 아래에 추가합니다.
  function renderRecording(blob, list) {
    const blobUrl = URL.createObjectURL(blob);
    const li = document.createElement('li');
    const audio = document.createElement('audio');
    const anchor = document.createElement('a');
    anchor.setAttribute('href', blobUrl);
    const now = new Date();
    anchor.setAttribute(
      'download',
      `recording-${now.getFullYear()}-${(now.getMonth() + 1).toString().padStart(2, '0')}-${now.getDay().toString().padStart(2, '0')}--${now.getHours().toString().padStart(2, '0')}-${now.getMinutes().toString().padStart(2, '0')}-${now.getSeconds().toString().padStart(2, '0')}.webm`
    );
    anchor.innerText = 'Download';
    audio.setAttribute('src', blobUrl);
    audio.setAttribute('controls', 'controls');
    li.appendChild(audio);
    li.appendChild(anchor);
    list.appendChild(li);
  }

테스트


웹 브라우저에서 이 페이지를 열고 "마이크 가져오기"단추를 누르십시오.권한 대화상자를 수락하고 기록 시작을 누르십시오.자신에게 메시지를 녹음한 다음 페이지에서 재생합니다.

WebM 파일


녹음을 다운로드하면 WebM 파일을 재생할 수 있는 미디어 플레이어가 없을 수도 있습니다.WebM is an open source format은 오디오와 동영상을 지원하지만 대부분 브라우저의 지원을 받는다.만약 VLC player이 있다면, 오디오를 재생할 수 있을 것입니다. 그렇지 않으면, convertio과 같은 온라인 도구를 사용하여 MP3나 WAV 파일로 변환하고 싶을 수도 있습니다. (또는 대담하다고 생각되면 터미널에 ffmpeg이 있습니다.)

브라우저는 지금 녹음기입니다.

MediaRecorder API는 브라우저에 대한 강력한 신규 추가입니다.이 글에서, 우리는 그것이 오디오를 녹음하는 능력을 보았지만, 그것은 이것에만 국한된 것이 아니다.현재 응용 프로그램은 오디오 파일을 저장하지 않기 때문에 페이지 리셋을 하면 이 파일들을 잃어버릴 수 있습니다.IndexedDB를 사용하여 저장하거나 서버에 전송할 수 있습니다.녹음을 재생할 수도 있습니다. 녹음하기 전에 웹 오디오 API를 통해 오디오를 전달할 수 있다고 상상해 보세요.만약 당신이 WebM 형식을 좋아하지 않는다면, 이것은 WebAssembly (또는 당신의 서버...) 의 작업일 수도 있지만, 전방에서 오디오를 다시 인코딩할 수 있습니다.
이 글의 코드를 사용해 보려면 live demo을 보십시오.모든 코드는 GitHub repo에서 찾을 수 있으며, remix the project on Glitch에서도 찾을 수 있습니다.MediaRecorder API에 대해 어떻게 생각하는지 알려주십시오.아래 댓글을 클릭하거나 트위터에 메시지를 남겨주세요.

좋은 웹페이지 즐겨찾기