Lors du développement pour le Web, la norme WebRTC fournit des API permettant d'accéder
caméras et micros connectés à l'ordinateur ou au smartphone. Ces appareils
sont communément appelés périphériques multimédias et sont accessibles via JavaScript
via l'objet navigator.mediaDevices
, qui implémente MediaDevices
de commande. À partir de cet objet, nous pouvons énumérer tous les appareils connectés, écouter
changement d'appareil (quand un appareil est connecté ou déconnecté), et ouvrir un appareil
pour récupérer un flux multimédia (voir ci-dessous).
La méthode la plus courante consiste à utiliser la fonction getUserMedia()
, qui
renvoie une promesse qui se résout en MediaStream
pour le contenu multimédia correspondant.
appareils. Cette fonction accepte un seul objet MediaStreamConstraints
qui
spécifie nos exigences. Par exemple, si vous souhaitez simplement ouvrir
le micro et la caméra par défaut, nous faisons ce qui suit.
Utiliser des promesses
const constraints = {
'video': true,
'audio': true
}
navigator.mediaDevices.getUserMedia(constraints)
.then(stream => {
console.log('Got MediaStream:', stream);
})
.catch(error => {
console.error('Error accessing media devices.', error);
});
Utiliser async/await
const openMediaDevices = async (constraints) => {
return await navigator.mediaDevices.getUserMedia(constraints);
}
try {
const stream = openMediaDevices({'video':true,'audio':true});
console.log('Got MediaStream:', stream);
} catch(error) {
console.error('Error accessing media devices.', error);
}
L'appel de getUserMedia()
déclenche une demande d'autorisation. Si l'utilisateur
accepte l'autorisation, la promesse est résolue avec une MediaStream
contenant
une vidéo et une piste audio. Si l'autorisation est refusée,
Une exception PermissionDeniedError
est générée. Si aucun appareil ne correspond
connecté, une erreur NotFoundError
est générée.
La documentation de référence complète de l'API pour l'interface MediaDevices
est disponible sur le site MDN web
d'assistance.
Interroger des appareils multimédias
Dans une application plus complexe, il est fort probable que nous voudrions vérifier
caméras et micros connectés et envoyer les commentaires appropriés aux
utilisateur. Pour ce faire, appelez la fonction enumerateDevices()
. Cela permettra
renvoyer une promesse qui renvoie vers un tableau de MediaDevicesInfo
qui décrit
chaque appareil multimédia connu. Nous pouvons l'utiliser pour présenter
une UI à l'utilisateur, ce qui
qu’ils choisissent celui
qu’ils préfèrent. Chaque MediaDevicesInfo
contient une propriété nommée
kind
avec la valeur audioinput
, audiooutput
ou videoinput
, indiquant
de quel type de périphérique
multimédia il s'agit.
Utiliser des promesses
function getConnectedDevices(type, callback) {
navigator.mediaDevices.enumerateDevices()
.then(devices => {
const filtered = devices.filter(device => device.kind === type);
callback(filtered);
});
}
getConnectedDevices('videoinput', cameras => console.log('Cameras found', cameras));
Utiliser async/await
async function getConnectedDevices(type) {
const devices = await navigator.mediaDevices.enumerateDevices();
return devices.filter(device => device.kind === type)
}
const videoCameras = getConnectedDevices('videoinput');
console.log('Cameras found:', videoCameras);
Écouter les modifications apportées aux appareils
La plupart des ordinateurs prennent en charge le branchement de différents périphériques pendant l'exécution. Il peut s'agir
webcam connectée par USB, un casque Bluetooth ou un ensemble de haut-parleurs externes. Dans
une application Web doit écouter les modifications
des périphériques multimédias. Pour ce faire, ajoutez un écouteur
navigator.mediaDevices
pour l'événement devicechange
.
// Updates the select element with the provided set of cameras
function updateCameraList(cameras) {
const listElement = document.querySelector('select#availableCameras');
listElement.innerHTML = '';
cameras.map(camera => {
const cameraOption = document.createElement('option');
cameraOption.label = camera.label;
cameraOption.value = camera.deviceId;
}).forEach(cameraOption => listElement.add(cameraOption));
}
// Fetch an array of devices of a certain type
async function getConnectedDevices(type) {
const devices = await navigator.mediaDevices.enumerateDevices();
return devices.filter(device => device.kind === type)
}
// Get the initial set of cameras connected
const videoCameras = getConnectedDevices('videoinput');
updateCameraList(videoCameras);
// Listen for changes to media devices and update the list accordingly
navigator.mediaDevices.addEventListener('devicechange', event => {
const newCameraList = getConnectedDevices('video');
updateCameraList(newCameraList);
});
Contraintes multimédias
L'objet de contraintes, qui doit implémenter MediaStreamConstraints
que nous transmettons en tant que paramètre à getUserMedia()
nous permet d'ouvrir
périphérique multimédia qui
répond à une certaine exigence. Cette exigence peut être très
définie de manière vague (audio et/ou vidéo), ou très spécifique (avec une configuration
ou un identifiant exact de l'appareil). Il est recommandé d'utiliser
l'API getUserMedia()
vérifie d'abord les appareils existants, puis spécifie un
qui correspond exactement à l'appareil concerné à l'aide de la contrainte deviceId
.
Si possible, les appareils seront également configurés en fonction des contraintes. Mer
peut activer l'annulation de l'écho sur les micros, ou définir une largeur minimale ou spécifique
et la hauteur de la vidéo de la caméra.
async function getConnectedDevices(type) {
const devices = await navigator.mediaDevices.enumerateDevices();
return devices.filter(device => device.kind === type)
}
// Open camera with at least minWidth and minHeight capabilities
async function openCamera(cameraId, minWidth, minHeight) {
const constraints = {
'audio': {'echoCancellation': true},
'video': {
'deviceId': cameraId,
'width': {'min': minWidth},
'height': {'min': minHeight}
}
}
return await navigator.mediaDevices.getUserMedia(constraints);
}
const cameras = getConnectedDevices('videoinput');
if (cameras && cameras.length > 0) {
// Open first available video camera with a resolution of 1280x720 pixels
const stream = openCamera(cameras[0].deviceId, 1280, 720);
}
La documentation complète de l'interface MediaStreamConstraints
est disponible
sur le MDN Web
d'assistance.
Lecture locale
Une fois qu'un appareil multimédia a été ouvert et qu'un MediaStream
est disponible, nous
vous pouvez l'attribuer à un élément audio ou vidéo pour le lire en local.
async function playVideoFromCamera() {
try {
const constraints = {'video': true, 'audio': true};
const stream = await navigator.mediaDevices.getUserMedia(constraints);
const videoElement = document.querySelector('video#localVideo');
videoElement.srcObject = stream;
} catch(error) {
console.error('Error opening video camera.', error);
}
}
Le code HTML requis pour un élément vidéo standard utilisé avec getUserMedia()
comportent généralement les attributs autoplay
et playsinline
. autoplay
lance la lecture automatique des nouveaux flux attribués à l'élément.
L'attribut playsinline
permet de lire la vidéo intégrée, au lieu d'être uniquement lue dans son intégralité.
sur certains navigateurs mobiles. Il est également recommandé d'utiliser
controls="false"
pour les diffusions en direct, sauf si l'utilisateur doit pouvoir les mettre en pause
de l'IA générative.
<html>
<head><title>Local video playback</title></head>
<body>
<video id="localVideo" autoplay playsinline controls="false"/>
</body>
</html>