如何为自定义传输控件创建事件

How to create event for custom transport controls

我正在创建自定义传输控件。在其中,我添加了一个带有 MenuFlyout 的新按钮来更改视频的质量。那么如何创建一个事件,该事件在单击特定 MenuFlyoutItem 时发生。

例如:
如果我使用

<MediaPlayerElement  Name="YoutubePlayer" MaxWidth="640" MaxHeight="360" AreTransportControlsEnabled="True">
    <MediaPlayerElement.TransportControls>
        <QualityTransportControls x:Name="CustomMediaControl" QualityChanged="CustomMediaControl_QualityChanged"/>
    </MediaPlayerElement.TransportControls>
</MediaPlayerElement>

在 XAML 中,每当我更改质量时它应该调用 CustomMediaControl_QualityChanged。可以使用

来完成
public event EventHandler QualityChanged
{
    add{}
    remove{}
}

但我不知道要在“添加”和“删除”中添加什么

这是我的自定义按钮代码。

<AppBarButton x:Name='QualityButton'
    Style='{StaticResource AppBarButtonStyle}'
    MediaTransportControlsHelper.DropoutOrder='3'>
    <AppBarButton.Flyout>
        <MenuFlyout>
            <MenuFlyoutItem x:Name="Quality144p" Text="144p"/>
            <MenuFlyoutItem x:Name="Quality240p" Text="240p"/>
            <MenuFlyoutItem x:Name="Quality360p" Text="360p"/>
            <MenuFlyoutItem x:Name="Quality480p" Text="480p"/>
            <MenuFlyoutItem x:Name="Quality720p" Text="720p"/>
            <MenuFlyoutItem x:Name="Quality1080p" Text="1080p"/>
        </MenuFlyout>
    </AppBarButton.Flyout>
    <AppBarButton.Icon>
        <SymbolIcon x:Name='QualitySymbol' Symbol='Setting' />
    </AppBarButton.Icon>
</AppBarButton>

这个解决方案对我有用:

在您的 ResourceDictionary 中添加 MediaTransportControls 的默认样式。
(可以在这里找到:C:\Program Files (x86)\Windows Kits\DesignTime\ CommonConfiguration\Neutral\UAP*your_version_Number*\Generic,
比简单地复制和粘贴整个
<Style TargetType="MediaTransportControls"> ... </Style> 标签,可在第 16350 行找到)

将第一行从 <Style TargetType="MediaTransportControls"> 更改为 <Style TargetType="QualityTransportControls"> 以定位您的控件。

您需要将控件的 xaml 代码添加到 ResourceDictionary,例如在 AudioTracksSelectionButton 之后(这取决于您希望控件出现的位置)。

<AppBarButton x:Name='AudioTracksSelectionButton'
              Style='{StaticResource AppBarButtonStyle}'
              MediaTransportControlsHelper.DropoutOrder='13'
              Visibility='Collapsed'>
    <AppBarButton.Icon>
        <FontIcon Glyph="&#xED1F;" />
    </AppBarButton.Icon>
</AppBarButton>
<AppBarButton x:Name='QualityButton'
              Style='{StaticResource AppBarButtonStyle}'
              MediaTransportControlsHelper.DropoutOrder='3'>
    <AppBarButton.Flyout>
        <MenuFlyout>
            <MenuFlyoutItem x:Name="Quality144p"
                            Text="144p" />
            <MenuFlyoutItem x:Name="Quality240p"
                            Text="240p" />
        </MenuFlyout>
    </AppBarButton.Flyout>
    <AppBarButton.Icon>
        <SymbolIcon x:Name='QualitySymbol'
                    Symbol='Setting' />
    </AppBarButton.Icon>
</AppBarButton>

然后在派生自 MediaTransportControls 并覆盖 OnApplyTemplate() 中创建一个新的 class,以便可以检索您的控件并可以手动添加点击事件。

public sealed class QualityTransportControls: MediaTransportControls
{
    //store the old quality for the custom event
    private int oldQuality = 144;
    private int quality = 144;
    public int Quality
    {
        get { return quality; }
        set {
            //update oldQuality
            oldQuality = quality;
            quality = value;
            //this method is responsible for raising the event
            OnQualityChanged();
        }
    }

    public QualityTransportControls()
    {
        this.DefaultStyleKey = typeof(QualityTransportControls);
    }

    protected override void OnApplyTemplate()
    {
        MenuFlyoutItem flyoutItem = GetTemplateChild("Quality144p") as MenuFlyoutItem;
        flyoutItem.Tapped += SetQuality144;

        MenuFlyoutItem flyoutItem2 = GetTemplateChild("Quality240p") as MenuFlyoutItem;
        flyoutItem.Tapped += SetQuality240;

        base.OnApplyTemplate();
    }

    private void SetQuality144(object sender, TappedRoutedEventArgs e)
    {
        Quality = 144;
    }

    private void SetQuality240(object sender, TappedRoutedEventArgs e)
    {
        Quality = 244;
    }

    private EventRegistrationTokenTable<EventHandler<QualityChangedEventArgs>> m_NumberChangedTokenTable = null;

    //this is your custom event which you can use within xaml
    public event EventHandler<QualityChangedEventArgs> QualityChanged
    {
        add
        {
            EventRegistrationTokenTable<EventHandler<QualityChangedEventArgs>>
                .GetOrCreateEventRegistrationTokenTable(ref m_NumberChangedTokenTable)
                .AddEventHandler(value);
        }
        remove
        {
            EventRegistrationTokenTable<EventHandler<QualityChangedEventArgs>>
                .GetOrCreateEventRegistrationTokenTable(ref m_NumberChangedTokenTable)
                .RemoveEventHandler(value);
        }
    }


    internal void OnQualityChanged()
    {
        //here you raise the event for every subscriber
        EventRegistrationTokenTable<EventHandler<QualityChangedEventArgs>>
        .GetOrCreateEventRegistrationTokenTable(ref m_NumberChangedTokenTable)
        .InvocationList?.Invoke(this, new QualityChangedEventArgs(oldQuality, Quality));
    }
}

然后您需要 class 用于 QualityChangedEventArgs,以便您可以向事件添加信息(例如,旧质量和新质量)。

public class QualityChangedEventArgs:EventArgs
{
    public int OldQuality { get; set; }
    public int NewQuality { get; set; }

    public QualityChangedEventArgs(int oldValue, int newValue)
    {
        OldQuality = oldValue;
        NewQuality = newValue;
    }
}

现在(构建后)您可以像使用 Tapped 等任何其他事件一样使用 QualityChanged 事件

<local:CustomMediaTransportControls
    QualityChanged="CustomMediaTransportControls_QualityChanged"/>

然后您在代码隐藏(例如您的 MainePage)中实现该方法,如下所示:

private void CustomMediaTransportControls_QualityChanged(object sender, QualityChangedEventArgs e)
{
    //here you can change the quality according to the new quality which is stored in e.NewQuality
}