対応ブラウザ
- <ph type="x-smartling-placeholder">
- <ph type="x-smartling-placeholder">
- <ph type="x-smartling-placeholder">
- <ph type="x-smartling-placeholder">
Document Picture-in-Picture API を使用すると、任意の HTML コンテンツを表示する常時表示のウィンドウを開くことができます。これは、HTML の <video>
要素のみをピクチャー イン ピクチャー ウィンドウに配置できるようにする既存の <video>
用 Picture-in-Picture API を拡張します。
Document Picture-in-Picture API の ピクチャー イン ピクチャー ウィンドウは、window.open()
で開いた空白の同一オリジン ウィンドウと似ていますが、次の点が異なります。
- ピクチャー イン ピクチャー ウィンドウは、他のウィンドウの上にフロート表示されます。
- ピクチャー イン ピクチャー ウィンドウが開始ウィンドウより長くなることはありません。
- ピクチャー イン ピクチャー ウィンドウは移動できません。
- ピクチャー イン ピクチャーのウィンドウの位置はウェブサイトで設定できません。
現在のステータス
ステップ | ステータス |
---|---|
1. 説明を作成 | 完了 |
2. 仕様の初期ドラフトを作成する | 作成中 |
3. フィードバックの収集と設計の反復処理 | 作成中 |
4. オリジン トライアル | 完了 |
5. 導入 | 完了(パソコン) |
ユースケース
カスタム動画プレーヤー
ウェブサイトは既存の <video>
用 Picture-in-Picture API を使用して、ピクチャー イン ピクチャーでの動画エクスペリエンスを提供できますが、制限は非常に限定的です。既存のピクチャー イン ピクチャー ウィンドウは入力が少なく、スタイル設定機能に制限があります。完全なドキュメント イン ピクチャーで、ウェブサイトでカスタム コントロールと入力機能(字幕、再生リスト、タイムスクラバー、動画に高評価や低評価を付けるなど)を提供して、ユーザーのピクチャー イン ピクチャー動画のエクスペリエンスを向上させることができます。
ビデオ会議
ビデオ会議セッション中に、通話を表示したいユーザーは別のタブを表示する、マルチタスクを行っているなど、ユーザーがブラウザタブを離れることが多いため、これはピクチャー イン ピクチャーの主要なユースケースです。繰り返しになりますが、現在のところ、ビデオ会議のウェブサイトが <video>
の Picture-in-Picture API を介して提供できるエクスペリエンスは、スタイルと入力が制限されています。ピクチャー イン ピクチャーでドキュメント全体を作成することで、ウェブサイトはキャンバス ハッキングに頼ることなく、複数の動画ストリームを 1 つの PIP ウィンドウに簡単に結合できます。また、メッセージの送信、別のユーザーのミュート、挙手などのカスタム コントロールも利用できます。
仕事効率化
調査によれば、ユーザーはウェブで生産性を高めるために、もっと多くの方法を必要としていることがわかっています。ピクチャー イン ピクチャーでドキュメントを作成すると、ウェブアプリでより多くのことを柔軟に処理できるようになります。テキスト編集、メモ作成、タスクリスト、メッセージング、チャット、デザイン&開発ツールなど、ウェブアプリのコンテンツにいつでもアクセスできます。
インターフェース
プロパティ
documentPictureInPicture.window
- 現在のピクチャー イン ピクチャー ウィンドウを返します(存在する場合)。それ以外の場合は、
null
を返します。
メソッド
documentPictureInPicture.requestWindow(options)
ピクチャー イン ピクチャー ウィンドウが開かれたときに解決される Promise を返します。 ユーザー操作なしで呼び出された場合、Promise は拒否されます。
options
ディクショナリには、次のオプションのメンバーが含まれます。width
- ピクチャー イン ピクチャー ウィンドウの初期の幅を設定します。
height
- ピクチャー イン ピクチャー ウィンドウの初期の高さを設定します。
disallowReturnToOpener
- [タブに戻る] が非表示になります] ボタンをクリックします。デフォルトでは false です。
イベント
documentPictureInPicture.onenter
- ピクチャー イン ピクチャー ウィンドウが開いているときに
documentPictureInPicture
に呼び出されます。
例
次の HTML は、カスタムの動画プレーヤーと、動画プレーヤーをピクチャー イン ピクチャー ウィンドウで開きます。
<div id="playerContainer">
<div id="player">
<video id="video"></video>
</div>
</div>
<button id="pipButton">Open Picture-in-Picture window</button>
ピクチャー イン ピクチャー ウィンドウを開く
次の JavaScript は、ユーザーがボタンをクリックして空白のピクチャー イン ピクチャー ウィンドウを開くと、documentPictureInPicture.requestWindow()
を呼び出します。返される Promise は、ピクチャー イン ピクチャー ウィンドウの JavaScript オブジェクトで解決されます。append()
を使用して動画プレーヤーをそのウィンドウに移動します。
pipButton.addEventListener('click', async () => {
const player = document.querySelector("#player");
// Open a Picture-in-Picture window.
const pipWindow = await documentPictureInPicture.requestWindow();
// Move the player to the Picture-in-Picture window.
pipWindow.document.body.append(player);
});
ピクチャー イン ピクチャー ウィンドウのサイズを設定する
ピクチャー イン ピクチャー ウィンドウのサイズを設定するには、documentPictureInPicture.requestWindow()
の width
オプションと height
オプションを目的のピクチャー イン ピクチャー ウィンドウ サイズに設定します。ユーザー フレンドリーなウィンドウ サイズに収まらない場合は、オプション値が大きすぎるか小さすぎる場合、オプションの値がクランプされることがあります。
pipButton.addEventListener("click", async () => {
const player = document.querySelector("#player");
// Open a Picture-in-Picture window whose size is
// the same as the player's.
const pipWindow = await documentPictureInPicture.requestWindow({
width: player.clientWidth,
height: player.clientHeight,
});
// Move the player to the Picture-in-Picture window.
pipWindow.document.body.append(player);
});
[タブに戻る] を非表示にする[ピクチャー イン ピクチャー] ウィンドウの
ユーザーがオープナー タブに戻ることができるピクチャー イン ピクチャー ウィンドウのボタンを非表示にするには、documentPictureInPicture.requestWindow()
の disallowReturnToOpener
オプションを true
に設定します。
pipButton.addEventListener("click", async () => {
// Open a Picture-in-Picture window which hides the "back to tab" button.
const pipWindow = await documentPictureInPicture.requestWindow({
disallowReturnToOpener: true,
});
});
ピクチャー イン ピクチャー ウィンドウにスタイルシートをコピーする
元のウィンドウからすべての CSS スタイルシートをコピーするには、ドキュメントに明示的にリンクされている、またはドキュメントに埋め込まれている styleSheets
をループして、ピクチャー イン ピクチャー ウィンドウに追加します。これは 1 回限りのコピーであることに注意してください。
pipButton.addEventListener("click", async () => {
const player = document.querySelector("#player");
// Open a Picture-in-Picture window.
const pipWindow = await documentPictureInPicture.requestWindow();
// Copy style sheets over from the initial document
// so that the player looks the same.
[...document.styleSheets].forEach((styleSheet) => {
try {
const cssRules = [...styleSheet.cssRules].map((rule) => rule.cssText).join('');
const style = document.createElement('style');
style.textContent = cssRules;
pipWindow.document.head.appendChild(style);
} catch (e) {
const link = document.createElement('link');
link.rel = 'stylesheet';
link.type = styleSheet.type;
link.media = styleSheet.media;
link.href = styleSheet.href;
pipWindow.document.head.appendChild(link);
}
});
// Move the player to the Picture-in-Picture window.
pipWindow.document.body.append(player);
});
ピクチャー イン ピクチャー ウィンドウが閉じたときに処理する
ウィンドウの "pagehide"
イベントをリッスンして、ピクチャー イン ピクチャー ウィンドウがいつ閉じられたか(ウェブサイトによって開始されたか、ユーザーが手動で閉じたため)を確認します。イベント ハンドラは、以下のように、ピクチャー イン ピクチャー ウィンドウから要素を元に戻すのに適しています。
pipButton.addEventListener("click", async () => {
const player = document.querySelector("#player");
// Open a Picture-in-Picture window.
const pipWindow = await documentPictureInPicture.requestWindow();
// Move the player to the Picture-in-Picture window.
pipWindow.document.body.append(player);
// Move the player back when the Picture-in-Picture window closes.
pipWindow.addEventListener("pagehide", (event) => {
const playerContainer = document.querySelector("#playerContainer");
const pipPlayer = event.target.querySelector("#player");
playerContainer.append(pipPlayer);
});
});
close()
メソッドを使用して、ピクチャー イン ピクチャー ウィンドウをプログラムで閉じます。
// Close the Picture-in-Picture window programmatically.
// The "pagehide" event will fire normally.
pipWindow.close();
ウェブサイトがピクチャー イン ピクチャーに切り替わったときに音声を聞く
documentPictureInPicture
の "enter"
イベントをリッスンして、ピクチャー イン ピクチャー ウィンドウが開かれたことを把握します。このイベントには、ピクチャー イン ピクチャー ウィンドウにアクセスするための window
オブジェクトが含まれています。
documentPictureInPicture.addEventListener("enter", (event) => {
const pipWindow = event.window;
});
ピクチャー イン ピクチャー ウィンドウの要素にアクセスする
ピクチャー イン ピクチャー ウィンドウの要素にアクセスするには、documentPictureInPicture.requestWindow()
によって返されたオブジェクトから、または以下に示すように documentPictureInPicture.window
を使用します。
const pipWindow = documentPictureInPicture.window;
if (pipWindow) {
// Mute video playing in the Picture-in-Picture window.
const pipVideo = pipWindow.document.querySelector("#video");
pipVideo.muted = true;
}
ピクチャー イン ピクチャー ウィンドウからのイベントを処理する
JavaScript で通常行うように、ボタンとコントロールを作成し、"click"
などのユーザーの入力イベントに応答します。
// Add a "mute" button to the Picture-in-Picture window.
const pipMuteButton = pipWindow.document.createElement("button");
pipMuteButton.textContent = "Mute";
pipMuteButton.addEventListener("click", () => {
const pipVideo = pipWindow.document.querySelector("#video");
pipVideo.muted = true;
});
pipWindow.document.body.append(pipMuteButton);
ピクチャー イン ピクチャー ウィンドウのサイズを変更する
ピクチャー イン ピクチャー ウィンドウのサイズを変更するには、ウィンドウ メソッド resizeBy()
と resizeTo()
を使用します。どちらの方法でも、ユーザー操作が必要です。
const resizeButton = pipWindow.document.createElement('button');
resizeButton.textContent = 'Resize';
resizeButton.addEventListener('click', () => {
// Expand the Picture-in-Picture window's width by 20px and height by 30px.
pipWindow.resizeBy(20, 30);
});
pipWindow.document.body.append(resizeButton);
オープナー ウィンドウにフォーカスする
focus()
ウィンドウ メソッドを使用して、ピクチャー イン ピクチャー ウィンドウからオープナー ウィンドウにフォーカスします。このメソッドを使用するには、ユーザー操作が必要です。
const returnToTabButton = pipWindow.document.createElement("button");
returnToTabButton.textContent = "Return to opener tab";
returnToTabButton.addEventListener("click", () => {
window.focus();
});
pipWindow.document.body.append(returnToTabButton);
CSS ピクチャー イン ピクチャーの表示モード
CSS picture-in-picture
表示モードを使用すると、ウェブアプリ(の一部)がピクチャー イン ピクチャー モードで表示されている場合にのみ適用される特定の CSS ルールを記述します。
@media all and (display-mode: picture-in-picture) {
body {
margin: 0;
}
h1 {
font-size: 0.8em;
}
}
機能検出
Document Picture-in-Picture API がサポートされているかどうかを確認するには、次のコマンドを使用します。
if ('documentPictureInPicture' in window) {
// The Document Picture-in-Picture API is supported.
}
デモ
VideoJS プレーヤー
Document Picture-in-Picture API の VideoJS プレーヤーのデモを試すことができます。必ずソースコードを確認してください。
ポモドーロ
ポモドーロ ウェブアプリである Tomodoro も、Document Picture-in-Picture API を利用します(GitHub の pull リクエストを参照)。
<ph type="x-smartling-placeholder">フィードバック
ご提案やご質問がございましたら、GitHub で問題を報告してください。
役に立つリンク
- 公開解説
- WICG の仕様
- Chromium のトラッキング バグ
- ChromeStatus.com のエントリ
- Blink コンポーネント:
Blink>Media>PictureInPicture
- TAG の確認
- テストの意図
- Intent to Ship(出荷の意図)
謝辞
ヒーロー画像作成者: Jakob Owens