與系統媒體傳輸控制項整合

本文說明如何與系統媒體傳輸控制項 (SMTC) 互動。 SMTC 是一組所有 Windows 10 裝置常見的控制項,為使用者提供一致的方式來控制,所有使用 MediaPlayer 進行播放的正在執行的應用程式媒體播放。

系統媒體傳輸控制項可讓媒體應用程式開發人員與內建系統 UI 整合,以顯示媒體中繼資料,例如藝術家、專輯標題或章節標題。 系統傳輸控制項也允許使用者使用內建系統 UI 來控制媒體應用程式的播放,例如暫停播放,並在播放清單中向前和向後略過。

System Media Transtport Controls

如需示範與 SMTC 整合的完整範例,請參閱 github 上的系統媒體傳輸控制範例

自動與 SMTC 整合

從 Windows 10 版本 1607 開始,預設情況下,使用 MediaPlayer 類別播放媒體的 UWP 應用程式會自動與 SMTC 整合。 只需將 MediaPlayer 的新執行個體具現化,並將 MediaSourceMediaPlaybackItem 或 , or MediaPlaybackList 指派給播放器的 Source 屬性,使用者就會在 SMTC 中看到您的應用程式名稱,並可以使用 SMTC 控制項在播放清單中播放、暫停和移動。

您的應用程式可以一次建立及使用多個 MediaPlayer 物件。 對於應用程式中的每個使用中 MediaPlayer 執行個體,SMTC 中都會建立一個單獨的索引標籤,允許使用者在使用中媒體播放器和其他正在執行的應用程式的媒體播放器之間切換。 在 SMTC 中目前選取的媒體播放器,就是控制項會影響的媒體播放器。

有關在應用程式中使用 MediaPlayer 的詳細資訊,包括將其繫結到 XAML 頁面中的 MediaPlayerElement,請參閱使用 MediaPlayer 播放音訊和視訊

有關使用 MediaSourceMediaPlaybackItemMediaPlaybackList 的詳細資訊,請參閱媒體項目、播放清單與曲目

新增要由 SMTC 顯示的中繼資料

如果要新增或修改 SMTC 中為媒體項目顯示的中繼資料 (例如影片或歌曲標題),則需要更新代表媒體項目的 MediaPlaybackItem的顯示屬性。 首先,透過呼叫 GetDisplayProperties 來取得 MediaItemDisplayProperties 物件的參考。 接下來,使用 Type 屬性為項目設定媒體類型、音樂或影片。 然後,您可以填入 MusicPropertiesVideoProperties 的欄位,實際情況取決於您指定的媒體類型。 最後,透過呼叫 ApplyDisplayProperties 更新媒體項目的中繼資料。

MediaItemDisplayProperties props = mediaPlaybackItem.GetDisplayProperties();
props.Type = Windows.Media.MediaPlaybackType.Video;
props.VideoProperties.Title = "Video title";
props.VideoProperties.Subtitle = "Video subtitle";
props.VideoProperties.Genres.Add("Documentary");
mediaPlaybackItem.ApplyDisplayProperties(props);
props = mediaPlaybackItem.GetDisplayProperties();
props.Type = Windows.Media.MediaPlaybackType.Music;
props.MusicProperties.Title = "Song title";
props.MusicProperties.Artist = "Song artist";
props.MusicProperties.Genres.Add("Polka");
mediaPlaybackItem.ApplyDisplayProperties(props);

注意

應用程式應該為 Type 屬性設定一個值,即使它們不提供由系統媒體傳輸控制項顯示的其他媒體中繼資料。 此值可協助系統正確處理您的媒體內容,包括防止螢幕保護程式在播放期間啟用。

使用 CommandManager 修改或覆寫預設 SMTC 命令

您的應用程式可以使用 MediaPlaybackCommandManager 類別修改或完全覆寫 SMTC 控制項的行為。 透過存取 CommandManager 屬性,可以為 MediaPlayer 類別的每個執行個體取得命令管理員執行個體。

對於每個命令 (例如預設跳到 MediaPlaybackList 中的下一項的 Next 命令),命令管理員會公開接收到的事件 (如 NextReceived) 以及管理命令行為的物件 (如 NextBehavior)。

以下範例為 NextBehaviorNextReceived 事件和 IsEnabledChanged 事件註冊一個處理常式。

_mediaPlayer.CommandManager.NextReceived += CommandManager_NextReceived;
_mediaPlayer.CommandManager.NextBehavior.IsEnabledChanged += NextBehavior_IsEnabledChanged;

以下範例說明了一個案例,其中應用程式希望在使用者按一下播放清單中的五個項目後停用 Next 命令,可能需要一些使用者互動才能繼續播放內容。 每次 ## 引發 NextReceived 事件時,計數器都會增加。 一旦計數器達到目標數字,Next 命令的 EnablingRule 將設定為 Never,進而停用該命令。

int _nextPressCount = 0;
private void CommandManager_NextReceived(MediaPlaybackCommandManager sender, MediaPlaybackCommandManagerNextReceivedEventArgs args)
{
    _nextPressCount++;
    if (_nextPressCount > 5)
    {
        sender.NextBehavior.EnablingRule = MediaCommandEnablingRule.Never;
        // Perform app tasks while the Next button is disabled
    }
}

您也可以將該命令設為 Always,這意味著即使對於 Next 命令範例,播放清單中沒有更多項目,該命令也將一律啟用。 或者您可以將命令設為 Auto,其中系統會根據目前播放的內容確定是否應啟用該命令。

對於上述案例,應用程式有時會想要重新啟用 Next 命令,並透過將 EnablingRule 設定為 Auto 來實現。

_mediaPlayer.CommandManager.NextBehavior.EnablingRule = MediaCommandEnablingRule.Auto;
_nextPressCount = 0;

由於您的應用程式在前景時可能有自己的 UI 用於控制播放,因此您可以使用 IsEnabledChanged 事件來更新自己的 UI,以符合 SMTC,因為可以透過存取傳遞到處理常式的 MediaPlaybackCommandManagerCommandBehaviorIsEnabled 來啟用或停用命令。

private void NextBehavior_IsEnabledChanged(MediaPlaybackCommandManagerCommandBehavior sender, object args)
{
    MyNextButton.IsEnabled = sender.IsEnabled;
}

在某些情況下,您可能想要完全覆寫 SMTC 命令的行為。 下面的範例說明了一個案例,其中應用程式使用 NextPrevious 命令在網路廣播電台之間切換,而不是在目前播放清單中的曲目之間跳轉。 與前面的範例一樣,當接收到命令時會註冊一個處理常式,在本案例中它是 PreviousReceived 事件。

_mediaPlayer.CommandManager.PreviousReceived += CommandManager_PreviousReceived;

PreviousReceived 處理常式中,首先透過呼叫傳遞到處理常式中的 MediaPlaybackCommandManagerPreviousReceivedEventArgsGetDeferral 來取得 Deferral。 這告訴系統等待延遲完成後再執行指令。 如果您要在處理常式中進行非同步呼叫,這一點非常重要。 此時,此範例會呼叫一個自訂方法,該方法傳回表示前一個廣播電台的 MediaPlaybackItem

接下來,檢查 Handled 屬性以確保該事件尚未由另一個處理常式處理。 如果不是,則 Handled 屬性設為 true。 這讓 SMTC 和任何其他已訂閱的處理常式知道,它們不應該採取任何動作來執行此命令,因為它已經被處理。 然後程式碼會設定媒體播放器的新來源,並啟動播放器。

最後,對延遲物件呼叫 Complete,讓系統知道您已完成對命令的處理。

private async void CommandManager_PreviousReceived(MediaPlaybackCommandManager sender, MediaPlaybackCommandManagerPreviousReceivedEventArgs args)
{
    var deferral = args.GetDeferral();
    MediaPlaybackItem mediaPlaybackItem = await GetPreviousStation();

    if(args.Handled != true)
    {
        args.Handled = true;
        sender.MediaPlayer.Source = mediaPlaybackItem;
        sender.MediaPlayer.Play();
    }
    deferral.Complete();
}

SMTC 的手動控制項

正如本文前面提到的,SMTC 將自動偵測並顯示您的應用程式所建立的每個 MediaPlayer 執行個體的資訊。 如果您想要使用 MediaPlayer 的多個執行個體,但希望 SMTC 為您的應用程式提供單一項目,那麼您必須手動控制 SMTC 的行為,而不是依賴自動整合。 此外,如果您使用 MediaTimelineController 控制一個或多個媒體播放器,則必須使用手動 SMTC 整合。 此外,如果您的應用程式使用 MediaPlayer 以外的 API (例如 AudioGraph 類別) 來播放媒體,您必須實作手動 SMTC 整合,以便使用者使用 SMTC 控制您的應用程式。 有關如何手動控制 SMTC 的資訊,請參閱系統媒體傳輸控制項的手動控制項