如何使用 JavaScript 减少视频的长度? [关闭]

Posted

技术标签:

【中文标题】如何使用 JavaScript 减少视频的长度? [关闭]【英文标题】:How to reduce the length of a video using JavaScript? [closed] 【发布时间】:2016-12-12 21:25:20 【问题描述】:

我正在尝试从头或尾修剪浏览器中视频的长度。我目前拥有的是一个使用 MediaRecorder API 录制的 MediaStream,我使用它在录制结束时生成一个 Blob,类型设置为“video/mp4”。这很好用,我可以播放视频,但是我想要一种在开始或结束时修剪视频的方法。

在对 MediaStream API 进行进一步调查后,我发现了 SourceBuffer 对象,您可以从 MediaStreamTrack 获取该对象并使用它来删除时间片,这正是我想要的。但是我不确定如何从视频(blob)中获取 MediaStreamTrack,因为 video.srcObject 属性返回 null。

【问题讨论】:

您是要删除部分视频以播放编辑后的视频,还是提供编辑后的视频以供下载? 有趣的问题。这家伙提到媒体片段是一种可能的解决方案。 ***.com/a/16992434/1567255我自己没试过。 @guest271314 both...Kosch 嗯,这似乎是一种只在特定时间部分播放视频的方法(这是我想要的一部分),但不能真正修剪文件本身,谢谢不过。 @naughtyboy "我目前拥有的是一个使用 MediaRecorder API 录制的 MediaStream,我使用它在录制结束时生成一个 Blob,类型设置为 'video/ mp4'" 你能在问题中加入javascript 吗? <video> src 是否在getUserMedia() 成功回调处理程序中设置为stream 【参考方案1】:

我正在尝试在浏览器中修剪视频的长度,从 无论是开头还是结尾。

您可以使用Array.prototype.slice() 以一秒1000ms 的数据块或其他时间范围删除包含在MediaRecorder dataavailable 事件中的数组的包含blob 的数组末尾的段。其中MediaRecorder.start()用参数1000调用,将每个记录的Blob设置为记录数据的1000ms

方法使用 https://github.com/samdutton/simpl/tree/gh-pages/mediarecorder 的修改版本。添加了<input type="number"> 元素以设置从录制的视频中删除1s 的块,以便使用.slice() 进行播放和下载

html

<video id="gum" autoplay muted controls></video>
<video id="recorded" autoplay controls></video>

<div>
  <button id="record">Start Recording</button><label for="record"></label><br>
  <span>Seconds of recorded video to play (min 1):</span><input min="1" type="number" disabled />
  <button id="play" disabled>Play</button>
  <span>Seconds of recorded video to download (min 1):</span><input min="1" type="number" disabled /><button id="download" disabled>Download</button>
</div>

javascript

'use strict';

/* globals MediaRecorder */

// This code is adapted from
// https://rawgit.com/Miguelao/demos/master/mediarecorder.html

'use strict';

/* globals MediaRecorder */

// This code is adapted from
// https://rawgit.com/Miguelao/demos/master/mediarecorder.html

var mediaSource = new MediaSource();
mediaSource.addEventListener('sourceopen', handleSourceOpen, false);
var mediaRecorder;
var recordedBlobs;
var sourceBuffer;
var gumVideo = document.querySelector('video#gum');
var recordedVideo = document.querySelector('video#recorded');
var input = document.querySelectorAll("input[type=number]");
recordedVideo.ontimeupdate = function(e) 
  console.log("recorded video currentTime:", e.target.currentTime)

gumVideo.onprogress = function(e) 
  // console.log("getUserMedia video currentTime:", e.target.currentTime)

var recordButton = document.querySelector('button#record');
var playButton = document.querySelector('button#play');
var downloadButton = document.querySelector('button#download');
recordButton.onclick = toggleRecording;
playButton.onclick = play;
downloadButton.onclick = download;

var currentTimes = [];
recordButton.nextElementSibling.innerHTML = "recorded video " 
                                            + currentTimes.length 
                                            + "s";
// window.isSecureContext could be used for Chrome
var isSecureOrigin = location.protocol === 'https:' ||
  location.host === 'localhost';
if (!isSecureOrigin) 
  alert('getUserMedia() must be run from a secure origin: HTTPS or localhost.' +
    '\n\nChanging protocol to HTTPS');
  location.protocol = 'HTTPS';


// Use old-style gUM to avoid requirement to enable the
// Enable experimental Web Platform features flag in Chrome 49

navigator.getUserMedia = navigator.getUserMedia ||
  navigator.webkitGetUserMedia || navigator.mozGetUserMedia;

var constraints = 
  audio: true,
  video: true
;

navigator.getUserMedia(constraints, successCallback, errorCallback);

function successCallback(stream) 
  console.log('getUserMedia() got stream: ', stream);
  window.stream = stream;
  if (window.URL) 
    gumVideo.src = window.URL.createObjectURL(stream);
   else 
    gumVideo.src = stream;
  


function errorCallback(error) 
  console.log('navigator.getUserMedia error: ', error);


// navigator.mediaDevices.getUserMedia(constraints)
// .then(function(stream) 
//   console.log('getUserMedia() got stream: ', stream);
//   window.stream = stream; // make available to browser console
//   if (window.URL) 
//     gumVideo.src = window.URL.createObjectURL(stream);
//    else 
//     gumVideo.src = stream;
//   
// ).catch(function(error) 
//   console.log('navigator.getUserMedia error: ', error);
// );

function handleSourceOpen(event) 
  console.log('MediaSource opened');
  sourceBuffer = mediaSource.addSourceBuffer('video/webm; codecs="vp8"');
  console.log('Source buffer: ', sourceBuffer);


function handleDataAvailable(event) 
  if (event.data && event.data.size > 0) 
    currentTimes.push(gumVideo.currentTime);
    recordedBlobs.push(event.data);
    recordButton.nextElementSibling.innerHTML = "recorded video " 
                                                + recordedBlobs.length 
                                                + "s";
  


function handleStop(event) 
  console.log('Recorder stopped: ', event);
  console.log("recorded times from getUserMedia video:", currentTimes);


function toggleRecording() 
  if (recordButton.textContent === 'Start Recording') 
    startRecording();
   else 
    stopRecording();
    recordButton.textContent = 'Start Recording';
    playButton.disabled = false;
    downloadButton.disabled = false;
  


// The nested try blocks will be simplified when Chrome 47 moves to Stable
function startRecording() 
  var options = 
    mimeType: 'video/webm',
    bitsPerSecond: 100000
  ;
  recordedBlobs = [];
  currentTimes = [];
  for (var i = 0; i < input.length; i++) 
    input[i].setAttribute("max", 1);
    input[i].setAttribute("disabled", "disabled");
  
  playButton.disabled = true;
  downloadButton.disabled = true;
  try 
    mediaRecorder = new MediaRecorder(window.stream, options);
   catch (e0) 
    console.log('Unable to create MediaRecorder with options Object: ', e0);
    try 
      options = 
        mimeType: 'video/webm,codecs=vp9',
        bitsPerSecond: 100000
      ;
      mediaRecorder = new MediaRecorder(window.stream, options);
     catch (e1) 
      console.log('Unable to create MediaRecorder with options Object: ', e1);
      try 
        options = 'video/vp8'; // Chrome 47
        mediaRecorder = new MediaRecorder(window.stream, options);
       catch (e2) 
        alert('MediaRecorder is not supported by this browser.\n\n' +
          'Try Firefox 29 or later, or Chrome 47 or later,'
          + ' with Enable experimental Web Platform features enabled '
          + ' from chrome://flags.');
        console.error('Exception while creating MediaRecorder:', e2);
        return;
      
    
  
  console.log('Created MediaRecorder', mediaRecorder, 'with options', options);
  recordButton.textContent = 'Stop Recording';
  playButton.disabled = true;
  downloadButton.disabled = true;
  mediaRecorder.onstop = handleStop;
  mediaRecorder.ondataavailable = handleDataAvailable;
  mediaRecorder.start(1000); // collect 1000ms of data
  console.log('MediaRecorder started', mediaRecorder);


function stopRecording() 
  mediaRecorder.stop();
  for (var i = 0; i < input.length; i++) 
    input[i].setAttribute("max", recordedBlobs.length);
    input[i].removeAttribute("disabled");
  
  console.log('Recorded Blobs: ', recordedBlobs);
  recordedVideo.controls = true;


function play() 
  console.log(`playing $input[0].values of getUserMedia video` 
             + `recorded by MediaRecorder from time ranges`
             , currentTimes.slice(0, input[0].value));
  // slice `input[0].value` amount, in seconds, from end of recorded video
  // for playback
  var file = recordedBlobs.slice(0, input[0].value);
  var superBuffer = new Blob(file, 
    type: 'video/webm'
  );
  recordedVideo.src = window.URL.createObjectURL(superBuffer);


function download() 
    // slice `input[1].value` amount, in seconds, from end of recorded video
    // for download
  var file = recordedBlobs.slice(0, input[1].value);
  var blob = new Blob(file, 
    type: 'video/webm'
  );
  var url = window.URL.createObjectURL(blob);
  var a = document.createElement('a');
  a.style.display = 'none';
  a.href = url;
  a.download = 'test.webm';
  document.body.appendChild(a);
  a.click();
  setTimeout(function() 
    document.body.removeChild(a);
    window.URL.revokeObjectURL(url);
  , 100);

plnkrhttps://plnkr.co/edit/LxuV5jMX0RZtDxOxT1qa?p=preview

【讨论】:

这是好东西,我的目的是记录流,将 blob 编码为视频,然后操作该视频。我也会让它在用户调整视频长度的同时播放,但这是我最终可能不得不采取的方法。 MediaRecorder 在 safari 上不工作 @UmeshPatadiya 好的。不确定这与问题有什么关系? 因为您使用 MediaRecorder() 在上面的 sn-p 中录制视频。它正在 chrome 和 mozilla 上运行,你能建议一些解决方案吗? @UmeshPatadiya 没试过 Safari。

以上是关于如何使用 JavaScript 减少视频的长度? [关闭]的主要内容,如果未能解决你的问题,请参考以下文章

text 如何使用linux减少视频噪音。

如何使用适用于 Android 的 OpenCV 减少实时视频序列中的运动效果?

JS判断视频Video的播放暂停结束完成及获取长度事件监听处理

JS判断视频Video的播放暂停结束完成及获取长度事件监听处理

JavaScript:如何使用 REGEX 减少 IF

如何使用 getID3 获取长度视频