Tuỳ chỉnh thông báo về nội dung nghe nhìn và bộ điều khiển chế độ phát bằng Media Session API

Cách tích hợp với các phím phương tiện phần cứng, tuỳ chỉnh thông báo về nội dung nghe nhìn, v.v.

[Tên người]
François Beaufort

Để cho người dùng biết nội dung đang phát trong trình duyệt của họ và điều khiển nội dung đó mà không cần quay lại trang đã khởi chạy nội dung đó, chúng tôi ra mắt Media Session API. Dịch vụ này cho phép các nhà phát triển web tuỳ chỉnh trải nghiệm này thông qua siêu dữ liệu trong các thông báo tuỳ chỉnh về nội dung nghe nhìn, các sự kiện nội dung đa phương tiện như phát, tạm dừng, tìm kiếm, thay đổi bản nhạc và các sự kiện hội nghị truyền hình như tắt tiếng/bật tiếng micrô, bật/tắt máy quay và cúp máy. Các tuỳ chỉnh này có sẵn trong một số ngữ cảnh, bao gồm trung tâm nội dung nghe nhìn trên máy tính, thông báo về nội dung nghe nhìn trên thiết bị di động và thậm chí trên cả thiết bị đeo. Tôi sẽ mô tả các tùy chỉnh này trong bài viết này.

Ảnh chụp màn hình ngữ cảnh Phiên phát nội dung đa phương tiện.
Trung tâm nội dung nghe nhìn trên máy tính, thông báo về nội dung nghe nhìn trên thiết bị di động và thiết bị đeo.

Giới thiệu về API Phiên phát nội dung đa phương tiện

API phiên phát nội dung đa phương tiện mang lại một số lợi ích và khả năng:

  • Hỗ trợ phím phương tiện phần cứng.
  • Thông báo về nội dung nghe nhìn được tuỳ chỉnh trên thiết bị di động, máy tính và thiết bị đeo đã ghép nối.
  • Trung tâm phương tiện có sẵn trên máy tính.
  • Các chế độ điều khiển nội dung nghe nhìn trên màn hình khoá có trên ChromeOS và thiết bị di động.
  • Bạn có thể sử dụng các nút điều khiển cửa sổ hình trong hình để phát âm thanh, hội nghị truyền hìnhtrình bày trang trình bày.
  • Bạn có thể sử dụng tính năng tích hợp Trợ lý trên thiết bị di động.

Hỗ trợ trình duyệt

  • 73
  • 79
  • 82
  • 15

Nguồn

Một vài ví dụ sẽ minh hoạ một vài điểm trong số này.

Ví dụ 1: Nếu người dùng nhấn phím đa phương tiện "bản nhạc tiếp theo" trên bàn phím, thì nhà phát triển web có thể xử lý hành động này của người dùng cho dù trình duyệt đang chạy ở nền trước hay trong nền.

Ví dụ 2: Nếu người dùng nghe podcast trên web trong khi màn hình thiết bị đang khoá, họ vẫn có thể nhấn vào biểu tượng "tìm kiếm lùi lại" từ trình điều khiển nội dung nghe nhìn trên màn hình khoá để nhà phát triển web lùi thời gian phát vài giây.

Ví dụ 3: Nếu có các thẻ đang phát âm thanh, người dùng có thể dễ dàng dừng phát qua trung tâm nội dung đa phương tiện trên máy tính để nhà phát triển web có thể xoá trạng thái của mình.

Ví dụ 4: Nếu người dùng đang gọi video, họ có thể nhấn vào nút điều khiển "bật micrô" trong cửa sổ Hình trong hình để ngăn trang web nhận dữ liệu micrô.

Có thể thực hiện việc này thông qua 2 giao diện: Giao diện MediaSession và giao diện MediaMetadata. Chế độ đầu tiên cho phép người dùng điều khiển bất kỳ nội dung nào đang phát. Thứ hai là cách bạn cho MediaSession biết những nội dung cần kiểm soát.

Để minh hoạ, hình ảnh dưới đây cho thấy mối liên hệ giữa các giao diện này với các chế độ điều khiển nội dung đa phương tiện cụ thể, trong trường hợp này là thông báo về nội dung đa phương tiện trên thiết bị di động.

Hình minh hoạ giao diện Phiên phát nội dung đa phương tiện.
Cấu tạo của thông báo đa phương tiện trên thiết bị di động.

Cho người dùng biết nội dung đang phát

Khi một trang web đang phát âm thanh hoặc video, người dùng sẽ tự động nhận được thông báo về nội dung nghe nhìn trong khay thông báo trên thiết bị di động hoặc trung tâm nội dung nghe nhìn trên máy tính. Trình duyệt sẽ cố gắng hết sức để hiển thị thông tin phù hợp bằng cách sử dụng tiêu đề tài liệu và hình ảnh biểu tượng lớn nhất có thể tìm thấy. Với API Phiên phát nội dung đa phương tiện, bạn có thể tuỳ chỉnh thông báo về nội dung nghe nhìn bằng một số siêu dữ liệu nội dung đa phương tiện phong phú hơn như tiêu đề, tên nghệ sĩ, tên đĩa nhạc và hình minh hoạ như dưới đây.

Chrome yêu cầu quyền phát âm thanh "đầy đủ" để chỉ hiển thị thông báo về nội dung nghe nhìn khi thời lượng nội dung đa phương tiện là ít nhất 5 giây. Điều này đảm bảo rằng các âm thanh ngẫu nhiên như tiếng chuông tí hon sẽ không hiển thị thông báo.

// After media (video or audio) starts playing
await document.querySelector("video").play();

if ("mediaSession" in navigator) {
  navigator.mediaSession.metadata = new MediaMetadata({
    title: 'Never Gonna Give You Up',
    artist: 'Rick Astley',
    album: 'Whenever You Need Somebody',
    artwork: [
      { src: 'https://via.placeholder.com/96',   sizes: '96x96',   type: 'image/png' },
      { src: 'https://via.placeholder.com/128', sizes: '128x128', type: 'image/png' },
      { src: 'https://via.placeholder.com/192', sizes: '192x192', type: 'image/png' },
      { src: 'https://via.placeholder.com/256', sizes: '256x256', type: 'image/png' },
      { src: 'https://via.placeholder.com/384', sizes: '384x384', type: 'image/png' },
      { src: 'https://via.placeholder.com/512', sizes: '512x512', type: 'image/png' },
    ]
  });

  // TODO: Update playback state.
}

Khi quá trình phát kết thúc, bạn không cần "phát hành" phiên phát nội dung đa phương tiện vì thông báo sẽ tự động biến mất. Xin lưu ý rằng navigator.mediaSession.metadata sẽ được sử dụng khi lượt phát tiếp theo bắt đầu. Đây là lý do bạn cần phải cập nhật thông tin này khi nguồn phát nội dung đa phương tiện thay đổi để đảm bảo thông tin liên quan được hiển thị trong thông báo về nội dung nghe nhìn.

Có một vài điều bạn cần lưu ý về siêu dữ liệu nội dung nghe nhìn.

  • Mảng hình minh hoạ thông báo hỗ trợ URL blob và URL dữ liệu.
  • Nếu không có hình minh hoạ nào được xác định và có một hình ảnh biểu tượng (được chỉ định bằng <link rel=icon>) có kích thước mong muốn, thì các thông báo nội dung nghe nhìn sẽ sử dụng hình ảnh đó.
  • Kích thước đích của hình minh hoạ thông báo trong Chrome dành cho Android là 512x512. Đối với các thiết bị cấp thấp, giá trị này là 256x256.
  • Thuộc tính title của phần tử HTML nội dung đa phương tiện được dùng trong tiện ích macOS "Phát hiện nhạc".
  • Nếu tài nguyên nội dung đa phương tiện được nhúng (ví dụ: trong iframe), bạn phải đặt thông tin API Phiên phát nội dung đa phương tiện từ ngữ cảnh được nhúng. Hãy xem đoạn mã dưới đây.
<iframe id="iframe">
  <video>...</video>
</iframe>
<script>
  iframe.contentWindow.navigator.mediaSession.metadata = new MediaMetadata({
    title: 'Never Gonna Give You Up',
    ...
  });
</script>

Cho phép người dùng điều khiển nội dung đang phát

Hành động phiên phát nội dung đa phương tiện là một hành động (ví dụ: "phát" hoặc "tạm dừng") mà một trang web có thể xử lý cho người dùng khi họ tương tác với nội dung phát nội dung đa phương tiện hiện đang phát. Các hành động tương tự như các sự kiện và hoạt động giống như các sự kiện. Giống như các sự kiện, các hành động được triển khai bằng cách đặt trình xử lý trên một đối tượng thích hợp, trong trường hợp này là một thực thể của MediaSession. Một số hành động được kích hoạt khi người dùng nhấn các nút trên tai nghe, một thiết bị từ xa khác, bàn phím hoặc tương tác với một thông báo về nội dung nghe nhìn.

Ảnh chụp màn hình thông báo về nội dung nghe nhìn trong Windows 10.
Thông báo tuỳ chỉnh về nội dung nghe nhìn trong Windows 10.

Vì một số thao tác trong phiên phát nội dung đa phương tiện có thể không được hỗ trợ, bạn nên sử dụng khối try…catch khi đặt các thao tác đó.

const actionHandlers = [
  ['play',          () => { /* ... */ }],
  ['pause',         () => { /* ... */ }],
  ['previoustrack', () => { /* ... */ }],
  ['nexttrack',     () => { /* ... */ }],
  ['stop',          () => { /* ... */ }],
  ['seekbackward',  (details) => { /* ... */ }],
  ['seekforward',   (details) => { /* ... */ }],
  ['seekto',        (details) => { /* ... */ }],
  /* Video conferencing actions */
  ['togglemicrophone', () => { /* ... */ }],
  ['togglecamera',     () => { /* ... */ }],
  ['hangup',           () => { /* ... */ }],
  /* Presenting slides actions */
  ['previousslide', () => { /* ... */ }],
  ['nextslide',     () => { /* ... */ }],
];

for (const [action, handler] of actionHandlers) {
  try {
    navigator.mediaSession.setActionHandler(action, handler);
  } catch (error) {
    console.log(`The media session action "${action}" is not supported yet.`);
  }
}

Việc huỷ đặt trình xử lý hành động trong phiên phát nội dung đa phương tiện cũng dễ dàng như việc đặt trình xử lý này thành null.

try {
  // Unset the "nexttrack" action handler at the end of a playlist.
  navigator.mediaSession.setActionHandler('nexttrack', null);
} catch (error) {
  console.log(`The media session action "nexttrack" is not supported yet.`);
}

Sau khi được thiết lập, trình xử lý tác vụ phiên phát nội dung đa phương tiện sẽ vẫn tồn tại thông qua lượt phát nội dung đa phương tiện. Mô hình này tương tự như mẫu trình nghe sự kiện, ngoại trừ việc xử lý một sự kiện có nghĩa là trình duyệt sẽ ngừng thực hiện mọi hành vi mặc định và sử dụng hành vi này làm tín hiệu mà trang web hỗ trợ hành động đối với nội dung đa phương tiện. Do đó, các chế độ kiểm soát thao tác đối với nội dung đa phương tiện sẽ không hiển thị trừ phi bạn đặt trình xử lý hành động thích hợp.

Ảnh chụp màn hình tiện ích Phát hiện nhạc trong macOS Big Sur.
Tiện ích Phát hiện nhạc trong macOS Big Sur.

Phát / tạm dừng

Hành động "play" cho biết người dùng muốn tiếp tục phát nội dung đa phương tiện, còn "pause" cho biết muốn tạm dừng phát.

Biểu tượng "phát/tạm dừng" luôn hiển thị trong thông báo về nội dung đa phương tiện và trình duyệt sẽ tự động xử lý các sự kiện nội dung đa phương tiện có liên quan. Để ghi đè hành vi mặc định, hãy xử lý các thao tác "phát" và "tạm dừng" nội dung đa phương tiện như minh hoạ dưới đây.

Ví dụ: trình duyệt có thể coi một trang web đang không phát nội dung đa phương tiện khi tìm kiếm hoặc tải nội dung. Trong trường hợp này, hãy ghi đè hành vi này bằng cách đặt navigator.mediaSession.playbackState thành "playing" hoặc "paused" để đảm bảo giao diện người dùng của trang web luôn đồng bộ hoá với các chế độ điều khiển thông báo nội dung nghe nhìn.

const video = document.querySelector('video');

navigator.mediaSession.setActionHandler('play', async () => {
  // Resume playback
  await video.play();
});

navigator.mediaSession.setActionHandler('pause', () => {
  // Pause active playback
  video.pause();
});

video.addEventListener('play', () => {
  navigator.mediaSession.playbackState = 'playing';
});

video.addEventListener('pause', () => {
  navigator.mediaSession.playbackState = 'paused';
});

Bản nhạc trước

Thao tác "previoustrack" cho biết rằng người dùng muốn bắt đầu phát nội dung đa phương tiện hiện tại từ đầu nếu hoạt động phát nội dung đa phương tiện có khái niệm bắt đầu, hoặc chuyển về mục trước trong danh sách phát nếu lượt phát nội dung đa phương tiện có khái niệm danh sách phát.

navigator.mediaSession.setActionHandler('previoustrack', () => {
  // Play previous track.
});

Bài hát tiếp theo

Thao tác "nexttrack" cho biết rằng người dùng muốn chuyển nội dung nghe nhìn phát đến mục tiếp theo trong danh sách phát nếu trình phát nội dung nghe nhìn có khái niệm về danh sách phát.

navigator.mediaSession.setActionHandler('nexttrack', () => {
  // Play next track.
});

Dừng

Thao tác "stop" cho biết người dùng muốn dừng phát nội dung đa phương tiện và xoá trạng thái nếu thích hợp.

navigator.mediaSession.setActionHandler('stop', () => {
  // Stop playback and clear state if appropriate.
});

Tua lại / Tua đi

Thao tác "seekbackward" cho biết rằng người dùng muốn đẩy thời gian phát nội dung nghe nhìn lùi lại một khoảng thời gian ngắn, còn "seekforward" cho biết muốn di chuyển thời gian phát nội dung nghe nhìn về phía trước một khoảng thời gian ngắn. Trong cả hai trường hợp, một khoảng thời gian ngắn có nghĩa là vài giây.

Giá trị seekOffset được cung cấp trong trình xử lý hành động là thời gian tính bằng giây để di chuyển thời gian phát nội dung nghe nhìn. Nếu không được cung cấp (ví dụ: undefined), thì bạn nên sử dụng thời gian hợp lý (ví dụ: 10-30 giây).

const video = document.querySelector('video');
const defaultSkipTime = 10; /* Time to skip in seconds by default */

navigator.mediaSession.setActionHandler('seekbackward', (details) => {
  const skipTime = details.seekOffset || defaultSkipTime;
  video.currentTime = Math.max(video.currentTime - skipTime, 0);
  // TODO: Update playback state.
});

navigator.mediaSession.setActionHandler('seekforward', (details) => {
  const skipTime = details.seekOffset || defaultSkipTime;
  video.currentTime = Math.min(video.currentTime + skipTime, video.duration);
  // TODO: Update playback state.
});

Tua đến một thời điểm cụ thể

Thao tác "seekto" cho biết người dùng muốn di chuyển thời gian phát nội dung đa phương tiện đến một thời điểm cụ thể.

Giá trị seekTime được cung cấp trong trình xử lý hành động là thời gian tính bằng giây để chuyển thời gian phát nội dung nghe nhìn sang.

Boolean fastSeek được cung cấp trong trình xử lý hành động là đúng nếu hành động được gọi nhiều lần trong một trình tự và đây không phải là lệnh gọi cuối cùng trong trình tự đó.

const video = document.querySelector('video');

navigator.mediaSession.setActionHandler('seekto', (details) => {
  if (details.fastSeek && 'fastSeek' in video) {
    // Only use fast seek if supported.
    video.fastSeek(details.seekTime);
    return;
  }
  video.currentTime = details.seekTime;
  // TODO: Update playback state.
});

Đặt vị trí phát

Việc hiển thị chính xác vị trí phát nội dung nghe nhìn trong một thông báo cũng đơn giản như việc đặt trạng thái vị trí tại một thời điểm thích hợp như minh hoạ dưới đây. Trạng thái vị trí là tổ hợp của tốc độ phát nội dung đa phương tiện, thời lượng và thời gian hiện tại.

Ảnh chụp màn hình các chế độ điều khiển nội dung nghe nhìn trên màn hình khoá trong ChromeOS.
Các chế độ điều khiển nội dung nghe nhìn trên màn hình khoá trong ChromeOS.

Thời lượng phải được cung cấp và có giá trị dương. Vị trí phải là số dương và nhỏ hơn thời lượng. Tốc độ phát phải lớn hơn 0.

const video = document.querySelector('video');

function updatePositionState() {
  if ('setPositionState' in navigator.mediaSession) {
    navigator.mediaSession.setPositionState({
      duration: video.duration,
      playbackRate: video.playbackRate,
      position: video.currentTime,
    });
  }
}

// When video starts playing, update duration.
await video.play();
updatePositionState();

// When user wants to seek backward, update position.
navigator.mediaSession.setActionHandler('seekbackward', (details) => {
  /* ... */
  updatePositionState();
});

// When user wants to seek forward, update position.
navigator.mediaSession.setActionHandler('seekforward', (details) => {
  /* ... */
  updatePositionState();
});

// When user wants to seek to a specific time, update position.
navigator.mediaSession.setActionHandler('seekto', (details) => {
  /* ... */
  updatePositionState();
});

// When video playback rate changes, update position state.
video.addEventListener('ratechange', (event) => {
  updatePositionState();
});

Việc đặt lại trạng thái vị trí cũng dễ dàng như đặt nó thành null.

// Reset position state when media is reset.
navigator.mediaSession.setPositionState(null);

Thao tác trong hội nghị truyền hình

Khi người dùng đặt cuộc gọi video vào cửa sổ Hình trong hình, trình duyệt có thể hiển thị các nút điều khiển micrô và máy ảnh, cũng như để kết thúc cuộc gọi. Khi người dùng nhấp vào các URL đó, trang web sẽ xử lý các trường hợp đó thông qua các hành động hội nghị truyền hình dưới đây. Hãy xem mẫu Hội nghị truyền hình để tham khảo ví dụ.

Ảnh chụp màn hình các chế độ điều khiển hội nghị truyền hình trong cửa sổ Hình trong hình.
Các chế độ điều khiển hội nghị truyền hình trong cửa sổ Hình trong hình.

Bật/tắt micrô

Hành động "togglemicrophone" cho biết người dùng muốn tắt hoặc bật micrô. Phương thức setMicrophoneActive(isActive) cho trình duyệt biết liệu trang web hiện có coi micrô đang hoạt động hay không.

let isMicrophoneActive = false;

navigator.mediaSession.setActionHandler('togglemicrophone', () => {
  if (isMicrophoneActive) {
    // Mute the microphone.
  } else {
    // Unmute the microphone.
  }
  isMicrophoneActive = !isMicrophoneActive;
  navigator.mediaSession.setMicrophoneActive(isMicrophoneActive);
});

Chuyển đổi máy ảnh

Thao tác "togglecamera" cho biết người dùng muốn bật hoặc tắt máy ảnh đang hoạt động. Phương thức setCameraActive(isActive) cho biết liệu trình duyệt có xem trang web này là đang hoạt động hay không.

let isCameraActive = false;

navigator.mediaSession.setActionHandler('togglecamera', () => {
  if (isCameraActive) {
    // Disable the camera.
  } else {
    // Enable the camera.
  }
  isCameraActive = !isCameraActive;
  navigator.mediaSession.setCameraActive(isCameraActive);
});

Kết thúc

Hành động "hangup" cho biết người dùng muốn kết thúc cuộc gọi.

navigator.mediaSession.setActionHandler('hangup', () => {
  // End the call.
});

Đang trình bày các thao tác trong trang trình bày

Khi người dùng đưa bản trình bày của trang trình bày vào cửa sổ Hình trong hình, trình duyệt có thể hiển thị các nút điều khiển để di chuyển qua các trang trình bày. Khi người dùng nhấp vào các nút đó, trang web sẽ xử lý các trường hợp đó thông qua Media Session API. Để biết ví dụ, hãy xem mẫu Cách trình bày trên Trang trình bày.

Trang trình bày trước

Thao tác "previousslide" cho biết người dùng muốn quay lại trang trình bày trước đó khi trình bày các trang trình bày.

navigator.mediaSession.setActionHandler('previousslide', () => {
  // Show previous slide.
});

Hỗ trợ trình duyệt

  • 111
  • 111
  • x
  • x

Trang trình bày tiếp theo

Thao tác "nextslide" cho biết rằng người dùng muốn chuyển đến trang trình bày tiếp theo khi trình bày các trang trình bày.

navigator.mediaSession.setActionHandler('nextslide', () => {
  // Show next slide.
});

Hỗ trợ trình duyệt

  • 111
  • 111
  • x
  • x

Mẫu

Xem một số mẫu Phiên phát nội dung đa phương tiện gồm Blender Foundationtác phẩm của Jan Morgenstern.

Bản ghi màn hình minh hoạ API Phiên phát nội dung đa phương tiện.

Tài nguyên