Arrêter / fermer la webcam qui est ouverte par navigator.getUserMedia

139

J'ai ouvert une webcam en utilisant le code JavaScript suivant: navigator.getUserMedia

Existe-t-il un code JavaScript pour arrêter ou fermer la webcam? Merci tout le monde.

Shih-En Chou
la source

Réponses:

199

ÉDITER

Depuis que cette réponse a été publiée à l'origine, l'API du navigateur a changé. .stop()n'est plus disponible sur le flux qui est transmis au rappel. Le développeur devra accéder aux pistes qui composent le flux (audio ou vidéo) et arrêter chacune d'elles individuellement.

Plus d'informations ici: https://developers.google.com/web/updates/2015/07/mediastream-deprecations?hl=en#stop-ended-and-active

Exemple (à partir du lien ci-dessus):

stream.getTracks().forEach(function(track) {
  track.stop();
});

La prise en charge du navigateur peut différer.

Réponse originale

navigator.getUserMediavous fournit un flux dans le rappel de réussite, vous pouvez appeler .stop()ce flux pour arrêter l'enregistrement (au moins dans Chrome, semble que FF ne l'aime pas)

Andrei
la source
2
Je pense que cela ne fonctionne pas stream.stop()pour Chrome, mediaRecorder.stop()arrête l'enregistrement, alors que cela n'arrête pas le flux fourni par le navigateur. Pouvez-vous consulter ce stackoverflow.com/questions/34715357/…
Muthu
@Muntu, je pense que cela dépend, pour moi stream.stop () fonctionne (en chrome). Parce que j'ai un flux webRTC. Donc, si vous enregistrez dans le navigateur mediaRecorder.stop () fonctionnera?
Johan Hoeksma
oui, mais cela soulève un autre problème. Cette fonction d'arrêt de l'enregistrement devrait se produire après avoir accordé quelques secondes / minutes d'enregistrement. Comment pouvez-vous contrôler cela: pour l'arrêter après une heure d'enregistrement par défaut? Je vous remercie!
Emanuela Colta
1
Cela arrête les flux, mais l'indicateur vidéo sur Chrome reste toujours actif jusqu'au rechargement. Y a-t-il un moyen de supprimer cela aussi?
Cybersupernova
@Cybersupernova Avez-vous trouvé une solution pour cela? Je pense que l'actualisation de la page pourrait fonctionner
samayo
59

Utilisez l'une de ces fonctions:

// stop both mic and camera
function stopBothVideoAndAudio(stream) {
    stream.getTracks().forEach(function(track) {
        if (track.readyState == 'live') {
            track.stop();
        }
    });
}

// stop only camera
function stopVideoOnly(stream) {
    stream.getTracks().forEach(function(track) {
        if (track.readyState == 'live' && track.kind === 'video') {
            track.stop();
        }
    });
}

// stop only mic
function stopAudioOnly(stream) {
    stream.getTracks().forEach(function(track) {
        if (track.readyState == 'live' && track.kind === 'audio') {
            track.stop();
        }
    });
}

Remarque: La réponse a été mise à jour le: 06/09/2020

Muaz Khan
la source
2
Merci pour cela. mediaStream.stop est obsolète.
Dan Brown
@DanBrown quelle est votre solution?
Webwoman
Je déconseillerais fortement de modifier le prototype d'une API native pour restaurer une fonctionnalité qui a été officiellement obsolète et supprimée du navigateur. C'est irrégulier et susceptible de semer la confusion plus tard. Lorsque vous avez besoin d'arrêter toutes les pistes d'un flux, pourquoi ne pas le faire stream.getTracks().forEach(track => { track.stop() })? Ou si vous faites cela assez souvent pour justifier un raccourci, vous pouvez toujours définir une fonction d'assistance comme stopAllTracks(stream).
callum
45

Ne pas utiliser stream.stop(), c'est obsolète

Obsolescence de MediaStream

Utilisation stream.getTracks().forEach(track => track.stop())

sol404
la source
1
Merci beaucoup, cela fonctionne parfaitement bien, en raison de la dépréciation, les gens déroutent ce que l'on travaille, mais à partir de mars 2019, la solution ci-dessus fonctionne bien dans le chrome .. 🙂
PANKAJ NAROLA
10

FF, Chrome et Opera ont commencé à exposer getUserMediavia navigator.mediaDevicesen standard maintenant (pourrait changer :)

démo en ligne

navigator.mediaDevices.getUserMedia({audio:true,video:true})
    .then(stream => {
        window.localStream = stream;
    })
    .catch( (err) =>{
        console.log(err);
    });
// later you can do below
// stop both video and audio
localStream.getTracks().forEach( (track) => {
track.stop();
});
// stop only audio
localStream.getAudioTracks()[0].stop();
// stop only video
localStream.getVideoTracks()[0].stop();
Sasi Varunan
la source
9

Démarrage de la vidéo webcam avec différents navigateurs

Pour Opera 12

window.navigator.getUserMedia(param, function(stream) {
                            video.src =window.URL.createObjectURL(stream);
                        }, videoError );

Pour Firefox Nightly 18.0

window.navigator.mozGetUserMedia(param, function(stream) {
                            video.mozSrcObject = stream;
                        }, videoError );

Pour Chrome 22

window.navigator.webkitGetUserMedia(param, function(stream) {
                            video.src =window.webkitURL.createObjectURL(stream);
                        },  videoError );

Arrêt de la vidéo webcam avec différents navigateurs

Pour Opera 12

video.pause();
video.src=null;

Pour Firefox Nightly 18.0

video.pause();
video.mozSrcObject=null;

Pour Chrome 22

video.pause();
video.src="";

Avec cela, la lumière de la webcam s'éteint à chaque fois ...

Alain Saurat
la source
10
Cela arrête uniquement d'afficher la vidéo dans la balise <video>, mais n'arrête pas la caméra.
G.Führ
8

Supposons que nous ayons un streaming dans la balise vidéo et que l'identifiant soit la vidéo - <video id="video"></video>alors nous devrions avoir le code suivant -

var videoEl = document.getElementById('video');
// now get the steam 
stream = videoEl.srcObject;
// now get all tracks
tracks = stream.getTracks();
// now close each track by having forEach loop
tracks.forEach(function(track) {
   // stopping every track
   track.stop();
});
// assign null to srcObject of video
videoEl.srcObject = null;
Veshraj Joshi
la source
6

Vous pouvez terminer le flux directement à l'aide de l'objet de flux renvoyé dans le gestionnaire de succès pour getUserMedia. par exemple

localMediaStream.stop()

video.src=""ou nullsupprimerait simplement la source de la balise vidéo. Il ne libérera pas le matériel.

Bhavin
la source
Je vois. Je vais essayer plus tard.
Shih-En Chou
1
Pas vraiment ... Sur Firefox ne fonctionne pas. La documentation mentionne que cette méthode n'est pas implémentée dans tous les navigateurs ...
Sdra
La solution ci-dessus n'a pas fonctionné pour moi. Cela l'a fait.
Scottmas
5

Essayez la méthode ci-dessous:

var mediaStream = null;
    navigator.getUserMedia(
        {
            audio: true,
            video: true
        },
        function (stream) {
            mediaStream = stream;
            mediaStream.stop = function () {
                this.getAudioTracks().forEach(function (track) {
                    track.stop();
                });
                this.getVideoTracks().forEach(function (track) { //in case... :)
                    track.stop();
                });
            };
            /*
             * Rest of your code.....
             * */
        });

    /*
    * somewhere insdie your code you call
    * */
    mediaStream.stop();
imal hasaranga perera
la source
4

Si le .stop()est obsolète, je ne pense pas que nous devrions le rajouter comme @MuazKhan dose. C'est une raison pour laquelle les choses sont obsolètes et ne devraient plus être utilisées. Créez simplement une fonction d'assistance à la place ... Voici une version plus ES6

function stopStream (stream) {
    for (let track of stream.getTracks()) { 
        track.stop()
    }
}
Interminable
la source
1
for (let track of stream.getTracks()) { track.stop() }
invité271314
7
stream.getTracks().forEach(function (track) { track.stop() })dans ES5, cela évite de longues transformations defor of
Babel
3

Puisque vous avez besoin des pistes pour fermer le streaming et que vous avez besoin du streamboject pour accéder aux pistes, le code que j'ai utilisé avec l'aide de la réponse de Muaz Khan ci-dessus est le suivant:

if (navigator.getUserMedia) {
    navigator.getUserMedia(constraints, function (stream) {
        videoEl.src = stream;
        videoEl.play();
        document.getElementById('close').addEventListener('click', function () {
            stopStream(stream);
        });
    }, errBack);

function stopStream(stream) {
console.log('stop called');
stream.getVideoTracks().forEach(function (track) {
    track.stop();
});

Bien sûr, cela fermera toutes les pistes vidéo actives. Si vous en avez plusieurs, vous devez sélectionner en conséquence.

mcy
la source
2

Vous devez arrêter toutes les pistes (depuis la webcam, le microphone):

localStream.getTracks().forEach(track => track.stop());
TopReseller
la source
0

L'utilisation de .stop () sur le flux fonctionne sur Chrome lorsqu'il est connecté via http. Cela ne fonctionne pas lors de l'utilisation de ssl (https).

ACEGL
la source
0

Veuillez vérifier ceci: https://jsfiddle.net/wazb1jks/3/

navigator.getUserMedia(mediaConstraints, function(stream) {
    window.streamReference = stream;
}, onMediaError);

Arrête d'enregistrer

function stopStream() {
    if (!window.streamReference) return;

    window.streamReference.getAudioTracks().forEach(function(track) {
        track.stop();
    });

    window.streamReference.getVideoTracks().forEach(function(track) {
        track.stop();
    });

    window.streamReference = null;
}

Akshay Italiya
la source
0

Le code suivant a fonctionné pour moi:

public vidOff() {

      let stream = this.video.nativeElement.srcObject;
      let tracks = stream.getTracks();

      tracks.forEach(function (track) {
          track.stop();
      });

      this.video.nativeElement.srcObject = null;
      this.video.nativeElement.stop();
  }
TechDo
la source
0

Démarrer et arrêter la webcam, (mise à jour 2020 React es6)

Démarrer la caméra Web

stopWebCamera =()=>

       //Start Web Came
      if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) {
        //use WebCam
        navigator.mediaDevices.getUserMedia({ video: true }).then(stream => {
          this.localStream = stream;
          this.video.srcObject = stream;
          this.video.play();
        });
      }
 }

Arrêter la lecture de la caméra Web ou de la vidéo en général

stopVideo =()=>
{
        this.video.pause();
        this.video.src = "";
        this.video.srcObject = null;

         // As per new API stop all streams
        if (this.localStream)
          this.localStream.getTracks().forEach(track => track.stop());
}

La fonction Stop Web Camera fonctionne même avec les flux vidéo:

  this.video.src = this.state.videoToTest;
  this.video.play();
Hitesh Sahu
la source
-1

Avoir une référence de succès de formulaire de flux

var streamRef;

var handleVideo = function (stream) {
    streamRef = stream;
}

//this will stop video and audio both track
streamRef.getTracks().map(function (val) {
    val.stop();
});
Pankaj Anupam
la source
1
Cette réponse est essentiellement la même que plusieurs autres qui ont déjà été données.
Dan Dascalescu
Pas de loin @DanDascalescu. Voir, dans cet exemple, il démontre clairement sa capacité à rappeler la fonction de carte.
charliebeck avec