MediaDevices API
This lesson explains MediaDevices API with clear examples, use cases, and best practices so you can use HTML5 APIs confidently in real web applications.
HTML5 Media Devices API Overview
The HTML5 Media Devices API allows web applications to access and manage
media input and output devices such as cameras, microphones, speakers, and
screen-sharing sources. It is available through
navigator.mediaDevices and is commonly used for video calls,
audio recording, QR scanners, live streaming, camera previews, and
browser-based media tools.
Media Devices APIs usually require HTTPS, user permission, and clear user
interaction because camera and microphone access is privacy-sensitive.
| Feature | Description |
| API Name | Media Devices API |
| Main Object | navigator.mediaDevices |
| Main Methods | getUserMedia(), enumerateDevices(), getDisplayMedia() |
| Returns | MediaStream and device information |
| Permissions | Camera, microphone, and screen permission |
| Security | Requires HTTPS in production |
Basic Camera Example
<video
id="preview"
autoplay
playsinline>
</video>
<script>
async function startCamera() {
try {
const stream =
await navigator.mediaDevices.getUserMedia(
{
video: true,
audio: false
}
);
document.querySelector("#preview").srcObject =
stream;
} catch (error) {
console.error(error.message);
}
}
startCamera();
</script>
This example requests camera access and displays the live camera stream in
a video element.
Media Devices API Methods
| Method | Description | Example Syntax |
getUserMedia() | Requests camera or microphone access. | navigator.mediaDevices.getUserMedia() |
enumerateDevices() | Lists available media input and output devices. | navigator.mediaDevices.enumerateDevices() |
getDisplayMedia() | Requests screen, window, or tab sharing. | navigator.mediaDevices.getDisplayMedia() |
devicechange | Event fired when media devices are connected or removed. | navigator.mediaDevices.addEventListener("devicechange", callback) |
Access Camera and Microphone
async function startMeeting() {
try {
const stream =
await navigator.mediaDevices.getUserMedia(
{
video: true,
audio: true
}
);
const video =
document.querySelector("#meetingVideo");
video.srcObject =
stream;
} catch (error) {
console.error("Permission denied or device unavailable.");
}
}
This pattern is commonly used in video conferencing, live chat, and
browser-based meeting applications.
Microphone Only Example
async function startMicrophone() {
const stream =
await navigator.mediaDevices.getUserMedia(
{
audio: true,
video: false
}
);
console.log(
stream.getAudioTracks()
);
}
Audio-only streams are useful for voice notes, speech recognition, podcast
tools, audio chat, and recording applications.
Media Constraints
const constraints =
{
video: {
width: 1280,
height: 720,
frameRate: 30,
facingMode: "user"
},
audio: {
echoCancellation: true,
noiseSuppression: true
}
};
const stream =
await navigator.mediaDevices.getUserMedia(
constraints
);
| Constraint | Description | Common Value |
video | Requests camera access. | true |
audio | Requests microphone access. | true |
width | Preferred video width. | 1280 |
height | Preferred video height. | 720 |
frameRate | Preferred frames per second. | 30 |
facingMode | Selects front or rear camera. | user, environment |
List Available Media Devices
async function listDevices() {
const devices =
await navigator.mediaDevices.enumerateDevices();
devices.forEach((device) => {
console.log(
device.kind,
device.label,
device.deviceId
);
});
}
listDevices();
Device labels may be hidden until the user grants camera or microphone
permission.
Media Device Types
| Device Kind | Description | Example |
videoinput | Camera device. | Webcam, front camera, rear camera. |
audioinput | Microphone device. | Built-in mic, headset mic. |
audiooutput | Speaker or audio output device. | Speakers, headphones. |
Select Specific Camera
async function startWithCamera(deviceId) {
const stream =
await navigator.mediaDevices.getUserMedia(
{
video: {
deviceId: {
exact: deviceId
}
}
}
);
document.querySelector("video").srcObject =
stream;
}
Use deviceId when users need to choose a specific camera or
microphone from a settings menu.
Screen Sharing with getDisplayMedia()
async function startScreenShare() {
try {
const stream =
await navigator.mediaDevices.getDisplayMedia(
{
video: true,
audio: true
}
);
document.querySelector("#screen").srcObject =
stream;
} catch (error) {
console.error("Screen sharing cancelled.");
}
}
Screen sharing is useful for meetings, remote support, presentations,
demos, tutorials, and collaborative tools.
Stop Camera, Microphone, or Screen Sharing
function stopStream(stream) {
stream.getTracks()
.forEach((track) => {
track.stop();
});
}
Always stop active tracks when the user ends a session to save battery,
release hardware, and protect privacy.
Detect Device Changes
navigator.mediaDevices.addEventListener(
"devicechange",
async () => {
console.log("Media device list changed.");
const devices =
await navigator.mediaDevices.enumerateDevices();
console.log(devices);
}
);
The devicechange event helps detect when users plug in or
remove cameras, microphones, or speakers.
MediaStream and Track Methods
| Method / Property | Description | Common Use |
stream.getTracks() | Returns all audio and video tracks. | Stop all media tracks. |
stream.getVideoTracks() | Returns video tracks only. | Camera settings. |
stream.getAudioTracks() | Returns audio tracks only. | Mute or unmute microphone. |
track.stop() | Stops a media track. | End camera or mic access. |
track.enabled | Enables or disables a track. | Mute mic or hide camera temporarily. |
track.getSettings() | Returns active track settings. | Check resolution, FPS, device ID. |
Mute and Unmute Microphone
function setMicrophoneMuted(stream, muted) {
stream.getAudioTracks()
.forEach((track) => {
track.enabled =
!muted;
});
}
Disabling a track pauses audio capture without fully stopping the
microphone device.
Capture Photo from Camera
function capturePhoto(video, canvas) {
const context =
canvas.getContext("2d");
context.drawImage(
video,
0,
0,
canvas.width,
canvas.height
);
return canvas.toDataURL("image/png");
}
This pattern is useful for profile photos, document scanning, QR code
scanning, and camera-based forms.
Common Media Devices Errors
| Error | Meaning | Possible Fix |
NotAllowedError | User denied permission. | Explain why access is needed and let user retry. |
NotFoundError | No matching device found. | Ask user to connect a camera or microphone. |
NotReadableError | Device is busy or unavailable. | Close other apps using the device. |
OverconstrainedError | Requested constraints cannot be satisfied. | Use lower resolution or simpler constraints. |
SecurityError | Browser security blocked access. | Use HTTPS and correct permissions. |
Feature Detection
if (
"mediaDevices" in navigator &&
"getUserMedia" in navigator.mediaDevices
) {
console.log("Media Devices API supported.");
} else {
console.log("Media Devices API not supported.");
}
Common Media Devices API Use Cases
- Video conferencing applications.
- Voice recording tools.
- QR code and barcode scanners.
- Document scanning applications.
- Live streaming platforms.
- Screen sharing and remote support tools.
- Camera-based authentication flows.
- Browser-based media editing applications.
Media Devices API Best Practices
- Use HTTPS in production.
- Request only the devices your feature needs.
- Ask for permission only after clear user action.
- Stop tracks when camera, microphone, or screen sharing is finished.
- Handle permission denial and missing devices gracefully.
- Show visible camera and microphone status indicators.
- Allow users to switch devices when multiple devices are available.
- Use lower constraints when high-resolution capture is not required.
Privacy and Security Considerations
- Clearly explain why camera or microphone access is needed.
- Never start recording without clear user awareness.
- Do not store recordings without user consent.
- Stop streams immediately when the user leaves or ends the session.
- Avoid requesting camera and microphone together unless both are needed.
- Use secure HTTPS connections.
- Provide obvious controls for mute, camera off, and stop sharing.
Common Media Devices API Mistakes
- Requesting camera or microphone access on page load.
- Forgetting to stop tracks after use.
- Ignoring permission errors.
- Using high-resolution video when not needed.
- Not providing fallback file upload options.
- Assuming all users have cameras or microphones.
- Not handling device changes during a session.
- Failing to show clear active recording indicators.
Media Devices API vs MediaRecorder API
| Feature | Media Devices API | MediaRecorder API |
| Main Purpose | Access camera, microphone, and screen streams. | Record audio or video streams. |
| Main Method | getUserMedia() | new MediaRecorder(stream) |
| Returns | MediaStream | Recorded Blob chunks. |
| Best Use | Live preview and device access. | Saving recordings. |
Key Takeaways
- The Media Devices API manages camera, microphone, speaker, and screen access.
getUserMedia() requests live camera or microphone streams. enumerateDevices() lists available media devices. getDisplayMedia() requests screen sharing. - Media access usually requires HTTPS and user permission.
- Always stop media tracks and respect user privacy.
Pro Tip
For production media apps, combine Media Devices with MediaRecorder,
WebRTC, Canvas, Web Audio, and clear permission UX. Always show users when
camera, microphone, or screen sharing is active.