调用位于ContentPage xaml CS类中的ContentView上的媒体元素事件。

huangapple go评论52阅读模式
英文:

calling media element events located on ContentView from ContentPage xaml CS class

问题

I have set up a BindableProperty for Media Element that works just fine. But I would like to access the events from the page where I am using the custom class. I have the various bools and string working as well as the methods mostly. I just need to get events working. Here is some sample code.

MediaControl.xaml:

<ContentView
    x:Class="NerdNewsNavigator2.Controls.MediaControl"
    xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
    xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
    xmlns:item="clr-namespace:NerdNewsNavigator2.Controls"
    xmlns:page="clr-namespace:NerdNewsNavigator2.View"
    xmlns:toolkit="http://schemas.microsoft.com/dotnet/2022/maui/toolkit"
    xmlns:vm="clr-namespace:NerdNewsNavigator2.ViewModel"
    Unloaded="ContentView_Unloaded">
    <Grid>

        <Grid.GestureRecognizers>
            <TapGestureRecognizer Command="{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=MovedCommand}" />
            <SwipeGestureRecognizer Direction="Up" Swiped="SwipeGestureRecognizer_Swiped" />
            <SwipeGestureRecognizer Direction="Down" Swiped="SwipeGestureRecognizer_Swiped" />
        </Grid.GestureRecognizers>

        <toolkit:MediaElement
            x:Name="mediaElement"
            ShouldAutoPlay="True"
            ShouldKeepScreenOn="True"
            ShouldShowPlaybackControls="False" />

        <Frame
            BackgroundColor="Black"
            IsEnabled="{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}"
            IsVisible="{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}"
            Opacity="0.5" />

        <Grid IsEnabled="{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}" IsVisible="{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}>

            <ImageButton
                x:Name="btnFullScreen"
                Margin="10"
                BackgroundColor="Transparent"
                Clicked="BtnFullScreen_Clicked"
                HeightRequest="40"
                HorizontalOptions="End"
                Source="whitefs.png"
                VerticalOptions="Start"
                WidthRequest="40" />

            <VerticalStackLayout VerticalOptions="End">

                <HorizontalStackLayout HorizontalOptions="Center">

                    <ImageButton
                        x:Name="BtnRewind"
                        Margin="10"
                        BackgroundColor="Transparent"
                        BindingContext="{x:Reference mediaElement}"
                        Clicked="BtnRewind_Clicked"
                        HeightRequest="40"
                        HorizontalOptions="Center"
                        Source="rewind.png"
                        VerticalOptions="End"
                        WidthRequest="40" />

                    <ImageButton
                        x:Name="BtnPLay"
                        Margin="10"
                        BackgroundColor="Transparent"
                        BindingContext="{x:Reference mediaElement}"
                        Clicked="BtnPlay_Clicked"
                        HeightRequest="40"
                        HorizontalOptions="Center"
                        Source="pause.png"
                        VerticalOptions="End"
                        WidthRequest="40" />

                    <ImageButton
                        x:Name="BtnForward"
                        Margin="10"
                        BackgroundColor="Transparent"
                        BindingContext="{x:Reference mediaElement}"
                        Clicked="BtnForward_Clicked"
                        HeightRequest="40"
                        HorizontalOptions="Center"
                        Source="fastforward.png"
                        VerticalOptions="End"
                        WidthRequest="40" />

                    <ImageButton
                        x:Name="ImageButtonMute"
                        Margin="10"
                        BackgroundColor="Transparent"
                        Clicked="OnMuteClicked"
                        HeightRequest="40"
                        Source="muted.png"
                        WidthRequest="40">
                        <ImageButton.Triggers>
                            <DataTrigger
                                Binding="{Binding ShouldMute, Source={x:Reference mediaElement}}"
                                TargetType="ImageButton"
                                Value="True" />
                            <DataTrigger
                                Binding="{Binding ShouldMute, Source={x:Reference mediaElement}}"
                                TargetType="ImageButton"
                                Value="False" />
                        </ImageButton.Triggers>
                    </ImageButton>

                </HorizontalStackLayout>

                <HorizontalStackLayout HorizontalOptions="Start" VerticalOptions="End">

                    <Label
                        Margin="5"
                        FontSize="12"
                        HorizontalOptions="Center"
                        Text="{Binding Source={RelativeSource AncestorType={x:Type item:MediaControl}}, Path=PlayPosition}"
                        TextColor="White" />
                </HorizontalStackLayout>

                <Slider
                    x:Name="PositionSlider"
                    Margin="10"
                    DragCompleted="Slider_DragCompleted"
                    DragStarted="Slider_DragStarted"
                    MaximumTrackColor="LightGray"
                    MinimumTrackColor="Red" />

            </VerticalStackLayout>

        </Grid>
    </Grid>

</ContentView>

Abbreviated code showing the properties and Bindable Properties. MediaControl.xaml.cs:

using Application = Microsoft.Maui.Controls.Application;
using Platform = Microsoft.Maui.ApplicationModel.Platform;

// ... (omitting other using statements for clarity)

public partial class MediaControl : ContentView
{
    // ... (omitting properties and methods for clarity)

    // Events
    private void MediaElement_PropertyChanged(object? sender, PropertyChangedEventArgs e)
    {
        // ... (handling PropertyChanged event)
    }

    private void OnPositionChanged(object? sender, MediaPositionChangedEventArgs e)
    {
        // ... (handling PositionChanged event)
    }

    private void SwipeGestureRecognizer_Swiped(object sender, SwipedEventArgs e)
    {
        // ... (handling SwipeGestureRecognizer's Swiped event)
    }

    private void Slider_DragCompleted(object? sender, EventArgs e)
    {
        // ... (handling Slider's DragCompleted event)
    }

    private void Slider_DragStarted(object sender, EventArgs e)
    {
        // ... (handling Slider's DragStarted event)
    }

    private void ChangedPosition(object sender, EventArgs e)
    {
        // ... (handling ChangedPosition event)
    }

    // Buttons
    private void BtnRewind_Clicked(object sender, EventArgs e)
    {
        // ... (handling BtnRewind Clicked event)
    }

    private void BtnForward_Clicked(object sender, EventArgs e)
    {
        // ... (handling BtnForward Clicked event)
    }
}

In the provided code, you've defined various events and event handlers within the MediaControl class. To access and trigger these events from another page that uses the MediaControl, you can do the following:

  1. Make sure that the MediaControl instance is accessible from the content page where you want to trigger the events.

  2. To trigger an event, you can call the respective event handler method. For example, to trigger the SwipeGestureRecognizer_Swiped event, you can call the SwipeGestureRecognizer_Swiped method within your content page.

  3. If you want to subscribe to the events from another page, you need a reference to the MediaControl instance. You can do this by exposing a public event on the MediaControl class and then subscribing to that event from your content page.

Here's a simplified example:

// Inside MediaControl.xaml.cs

public

<details>
<summary>英文:</summary>

I have set up a BindableProperty for Media Elemement that works just fine. But I would like to access the events from the page where I am using the custom class. I have the various bools and string working as well as the methods mostly. I just need to get events working. Here is some sample code.

MediaControl.xaml:

<?xml version="1.0" encoding="utf-8" ?>
<ContentView
x:Class="NerdNewsNavigator2.Controls.MediaControl"
xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:item="clr-namespace:NerdNewsNavigator2.Controls"
xmlns:page="clr-namespace:NerdNewsNavigator2.View"
xmlns:toolkit="http://schemas.microsoft.com/dotnet/2022/maui/toolkit"
xmlns:vm="clr-namespace:NerdNewsNavigator2.ViewModel"
Unloaded="ContentView_Unloaded">
<Grid>

    &lt;Grid.GestureRecognizers&gt;
&lt;TapGestureRecognizer Command=&quot;{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=MovedCommand}&quot; /&gt;
&lt;SwipeGestureRecognizer Direction=&quot;Up&quot; Swiped=&quot;SwipeGestureRecognizer_Swiped&quot; /&gt;
&lt;SwipeGestureRecognizer Direction=&quot;Down&quot; Swiped=&quot;SwipeGestureRecognizer_Swiped&quot; /&gt;
&lt;/Grid.GestureRecognizers&gt;
&lt;toolkit:MediaElement
x:Name=&quot;mediaElement&quot;
ShouldAutoPlay=&quot;True&quot;
ShouldKeepScreenOn=&quot;True&quot;
ShouldShowPlaybackControls=&quot;False&quot; /&gt;
&lt;Frame
BackgroundColor=&quot;Black&quot;
IsEnabled=&quot;{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}&quot;
IsVisible=&quot;{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}&quot;
Opacity=&quot;0.5&quot; /&gt;
&lt;Grid IsEnabled=&quot;{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}&quot; IsVisible=&quot;{Binding Source={RelativeSource AncestorType={x:Type vm:BaseViewModel}}, Path=SetFullScreen}&quot;&gt;
&lt;ImageButton
x:Name=&quot;btnFullScreen&quot;
Margin=&quot;10&quot;
BackgroundColor=&quot;Transparent&quot;
Clicked=&quot;BtnFullScreen_Clicked&quot;
HeightRequest=&quot;40&quot;
HorizontalOptions=&quot;End&quot;
Source=&quot;whitefs.png&quot;
VerticalOptions=&quot;Start&quot;
WidthRequest=&quot;40&quot; /&gt;
&lt;VerticalStackLayout VerticalOptions=&quot;End&quot;&gt;
&lt;HorizontalStackLayout HorizontalOptions=&quot;Center&quot;&gt;
&lt;ImageButton
x:Name=&quot;BtnRewind&quot;
Margin=&quot;10&quot;
BackgroundColor=&quot;Transparent&quot;
BindingContext=&quot;{x:Reference mediaElement}&quot;
Clicked=&quot;BtnRewind_Clicked&quot;
HeightRequest=&quot;40&quot;
HorizontalOptions=&quot;Center&quot;
Source=&quot;rewind.png&quot;
VerticalOptions=&quot;End&quot;
WidthRequest=&quot;40&quot; /&gt;
&lt;ImageButton
x:Name=&quot;BtnPLay&quot;
Margin=&quot;10&quot;
BackgroundColor=&quot;Transparent&quot;
BindingContext=&quot;{x:Reference mediaElement}&quot;
Clicked=&quot;BtnPlay_Clicked&quot;
HeightRequest=&quot;40&quot;
HorizontalOptions=&quot;Center&quot;
Source=&quot;pause.png&quot;
VerticalOptions=&quot;End&quot;
WidthRequest=&quot;40&quot; /&gt;
&lt;ImageButton
x:Name=&quot;BtnForward&quot;
Margin=&quot;10&quot;
BackgroundColor=&quot;Transparent&quot;
BindingContext=&quot;{x:Reference mediaElement}&quot;
Clicked=&quot;BtnForward_Clicked&quot;
HeightRequest=&quot;40&quot;
HorizontalOptions=&quot;Center&quot;
Source=&quot;fastforward.png&quot;
VerticalOptions=&quot;End&quot;
WidthRequest=&quot;40&quot; /&gt;
&lt;ImageButton
x:Name=&quot;ImageButtonMute&quot;
Margin=&quot;10&quot;
BackgroundColor=&quot;Transparent&quot;
Clicked=&quot;OnMuteClicked&quot;
HeightRequest=&quot;40&quot;
Source=&quot;muted.png&quot;
WidthRequest=&quot;40&quot;&gt;
&lt;ImageButton.Triggers&gt;
&lt;DataTrigger
Binding=&quot;{Binding ShouldMute, Source={x:Reference mediaElement}}&quot;
TargetType=&quot;ImageButton&quot;
Value=&quot;True&quot; /&gt;
&lt;DataTrigger
Binding=&quot;{Binding ShouldMute, Source={x:Reference mediaElement}}&quot;
TargetType=&quot;ImageButton&quot;
Value=&quot;False&quot; /&gt;
&lt;/ImageButton.Triggers&gt;
&lt;/ImageButton&gt;
&lt;/HorizontalStackLayout&gt;
&lt;HorizontalStackLayout HorizontalOptions=&quot;Start&quot; VerticalOptions=&quot;End&quot;&gt;
&lt;Label
Margin=&quot;5&quot;
FontSize=&quot;12&quot;
HorizontalOptions=&quot;Center&quot;
Text=&quot;{Binding Source={RelativeSource AncestorType={x:Type item:MediaControl}}, Path=PlayPosition}&quot;
TextColor=&quot;White&quot; /&gt;
&lt;/HorizontalStackLayout&gt;
&lt;Slider
x:Name=&quot;PositionSlider&quot;
Margin=&quot;10&quot;
DragCompleted=&quot;Slider_DragCompleted&quot;
DragStarted=&quot;Slider_DragStarted&quot;
MaximumTrackColor=&quot;LightGray&quot;
MinimumTrackColor=&quot;Red&quot; /&gt;
&lt;/VerticalStackLayout&gt;
&lt;/Grid&gt;
&lt;/Grid&gt;

</ContentView>

Abbreviated code showing the properties and Bindable Properties.
MediaControl.xaml.cs:

using Application = Microsoft.Maui.Controls.Application;
using Platform = Microsoft.Maui.ApplicationModel.Platform;

#if ANDROID
using Views = AndroidX.Core.View;
#endif

#if WINDOWS
using Microsoft.UI;
using Microsoft.UI.Windowing;
using WinRT;
using Microsoft.Maui.Controls;
using CommunityToolkit.Maui.Core.Primitives;
#endif

namespace NerdNewsNavigator2.Controls;

public partial class MediaControl : ContentView
{
#region Properties and Bindable Properties
/// <summary>
/// Initilizes a new instance of the <see cref="Position"/> class
/// </summary>
private Position Pos { get; set; } = new();
public string PlayPosition { get; set; }
public Page CurrentPage { get; set; }

private bool _fullScreen = false;

#if WINDOWS
private static MauiWinUIWindow CurrentWindow { get; set; }
#endif

public static readonly BindableProperty TitleProperty = BindableProperty.Create(nameof(Name), typeof(MediaElement), typeof(MediaControl), propertyChanged: (bindable, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindable;
control.mediaElement.ShouldAutoPlay = (bool)newValue;
control.mediaElement.ShouldKeepScreenOn = (bool)newValue;
control.mediaElement.Source = newValue as MediaSource;
control.mediaElement.ShouldShowPlaybackControls = (bool)newValue;
control.mediaElement.StateChanged += (System.EventHandler&lt;MediaStateChangedEventArgs&gt;)newValue;
control.mediaElement.MediaOpened += (System.EventHandler)newValue;
});
public static readonly BindableProperty SourceProperty = BindableProperty.Create(nameof(Source), typeof(MediaSource), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.Source = newValue as MediaSource;
});
public TimeSpan Position
{
get =&gt; (TimeSpan)GetValue(TitleProperty);
}
public MediaSource Source
{
get =&gt; GetValue(SourceProperty) as MediaSource;
set =&gt; SetValue(SourceProperty, value);
}
public MediaElement Name
{
get =&gt; GetValue(TitleProperty) as MediaElement;
set =&gt; SetValue(TitleProperty, value);
}
public bool ShouldShowPlaybackControls
{
get =&gt; (bool)GetValue(TitleProperty);
set =&gt; SetValue(TitleProperty, value);
}
public bool ShouldAutoPlay
{
get =&gt; (bool)GetValue(TitleProperty);
set =&gt; SetValue(TitleProperty, value);
}
public bool ShouldKeepScreenOn
{
get =&gt; (bool)GetValue(TitleProperty);
set =&gt; SetValue(TitleProperty, value);
}
#endregion
public MediaControl()
{
InitializeComponent();
PlayPosition = string.Empty;
mediaElement.PropertyChanged += MediaElement_PropertyChanged;
mediaElement.PositionChanged += ChangedPosition;
CurrentPage = Shell.Current.CurrentPage;
}
public void SeekTo(TimeSpan position)
{
mediaElement.SeekTo(position);
}
public void Stop()
{
mediaElement.Stop();
}
#region Events

#nullable enable
private void MediaElement_PropertyChanged(object? sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == MediaElement.DurationProperty.PropertyName)
{
PositionSlider.Maximum = mediaElement.Duration.TotalSeconds;
}
}
private void OnPositionChanged(object? sender, MediaPositionChangedEventArgs e)
{
PositionSlider.Value = e.Position.TotalSeconds;
}
private void SwipeGestureRecognizer_Swiped(object sender, SwipedEventArgs e)
{
#if WINDOWS
CurrentWindow = BaseViewModel.CurrentWindow;
#endif
if (e.Direction == SwipeDirection.Up)
{
SetFullScreen();
}
if (e.Direction == SwipeDirection.Down)
{
RestoreScreen();
}
}
private void Slider_DragCompleted(object? sender, EventArgs e)
{
ArgumentNullException.ThrowIfNull(sender);

    var newValue = ((Slider)sender).Value;
mediaElement.SeekTo(TimeSpan.FromSeconds(newValue));
mediaElement.Play();
}

#nullable disable
private void Slider_DragStarted(object sender, EventArgs e)
{
mediaElement.Pause();
}
private void ChangedPosition(object sender, EventArgs e)
{
var playDuration = BaseViewModel.TimeConverter(mediaElement.Duration);
var position = BaseViewModel.TimeConverter(mediaElement.Position);
PlayPosition = $"{position}/{playDuration}";
OnPropertyChanged(nameof(PlayPosition));
}
#endregion

#region Buttons
private void BtnRewind_Clicked(object sender, EventArgs e)
{
var time = mediaElement.Position - TimeSpan.FromSeconds(15);
mediaElement.Pause();
mediaElement.SeekTo(time);
mediaElement.Play();
}
private void BtnForward_Clicked(object sender, EventArgs e)
{
var time = mediaElement.Position + TimeSpan.FromSeconds(15);
mediaElement.Pause();
mediaElement.SeekTo(time);
mediaElement.Play();
}

Here is example of event trigger method that I want to call from content page
TabletPlayPodcastPage.xaml:

/// <summary>
/// Manages IOS seeking for <see cref="mediaElement"/> with <see cref="Pos"/> at start of playback.
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
public async void SeekIOS(object? sender, MediaStateChangedEventArgs e)
{
if (sender == null)
{
return;
}
Pos.Title = Preferences.Default.Get("New_Url", string.Empty);
Pos.SavedPosition = TimeSpan.Zero;
var positionList = await App.PositionData.GetAllPositions();
foreach (var item in positionList)
{
if (Pos.Title == item.Title)
{
Pos.SavedPosition = item.SavedPosition;
Debug.WriteLine($"Retrieved Saved position from database is: {item.Title} - {item.SavedPosition}");
}
}
if (e.NewState == MediaElementState.Playing)
{
mediaElement.SeekTo(Pos.SavedPosition);
mediaElement.ShouldKeepScreenOn = true;
Debug.WriteLine("Media playback started. ShouldKeepScreenOn is set to true.");
}
}


Here is example calling function I want to use:

/// <summary>
/// A method that starts <see cref="MediaElement"/> event for <see cref="TabletPlayPodcastPage"/>
/// </summary>
public void Load()
{
#if WINDOWS || ANDROID
mediaElement.MediaOpened += Seek;
#endif

#if IOS || MACCATALYST
mediaElement.StateChanged += SeekIOS;
#endif
}

Trying to call mediaElement.StateChanged += SeekIOS gives an error CS1061 [Error Message Link][1]
[1]: https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/compiler-messages/cs1061?f1url=%3FappId%3Droslyn%26k%3Dk(CS1061)
If I use Visual studio quick actions I get this function that gets rid of error but does not let me access the event. 

public Action<object, EventArgs> MediaOpened { get; internal set; }

I no longer get an error message but the event does not trigger either. I am looking for a way to call the event from another page that uses MediaControl.  I created all of this to reduce code and all the functions and behaviors I want to have working do work and this is about reducing code and making it tidier.
</details>
# 答案1
**得分**: 0
这段代码似乎描述了如何创建一个自定义控件(`MediaControl`),并在其中定义了一些绑定属性(Bindable Properties),以便对`MediaElement`进行设置和事件处理。这让你能够使用`MediaElement`的各种属性和事件,同时保持页面代码的整洁。
<details>
<summary>英文:</summary>
Well It ended up I managed to figure it out myself. I looked at the media element code itself and realized through trial and error this solution

public static readonly BindableProperty TitleProperty = BindableProperty.Create(nameof(Name), typeof(MediaElement), typeof(MediaControl), propertyChanged: (bindable, oldValue, newValue) =>
{
var control = (MediaControl)bindable;
control.mediaElement.ShouldAutoPlay = (bool)newValue;
control.mediaElement.ShouldKeepScreenOn = (bool)newValue;
control.mediaElement.Source = newValue as MediaSource;
control.mediaElement.ShouldShowPlaybackControls = (bool)newValue;
control.mediaElement.PositionChanged += (EventHandler<MediaPositionChangedEventArgs>)newValue;
control.mediaElement.StateChanged += (EventHandler<MediaStateChangedEventArgs>)newValue;
control.mediaElement.MediaOpened += (EventHandler)newValue;
});

public static readonly BindableProperty SourceProperty = BindableProperty.Create(nameof(Source), typeof(MediaSource), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.Source = newValue as MediaSource;
});
public static readonly BindableProperty StateChangedProperty = BindableProperty.Create(nameof(StateChanged), typeof(EventHandler&lt;MediaStateChangedEventArgs&gt;), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.StateChanged += (EventHandler&lt;MediaStateChangedEventArgs&gt;)newValue;
});
public static readonly BindableProperty MediaOpenedProperty = BindableProperty.Create(nameof(MediaOpened), typeof(EventHandler), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.MediaOpened += (EventHandler)newValue;
});
public static readonly BindableProperty ShouldKeepScreenOnProperty = BindableProperty.Create(nameof(ShouldKeepScreenOn), typeof(bool), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.ShouldKeepScreenOn = (bool)newValue;
});
public static readonly BindableProperty PositionProperty = BindableProperty.Create(nameof(Position), typeof(TimeSpan), typeof(MediaElement), TimeSpan.Zero);
public static readonly BindableProperty ShouldAutoPlayProperty = BindableProperty.Create(nameof(ShouldAutoPlay), typeof(bool), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.ShouldAutoPlay = (bool)newValue;
});
public static readonly BindableProperty ShouldShowPlaybackControlsProperty = BindableProperty.Create(nameof(ShouldShowPlaybackControls), typeof(bool), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.ShouldShowPlaybackControls = (bool)newValue;
});
public static readonly BindableProperty PositionChangedProperty = BindableProperty.Create(nameof(PositionChanged), typeof(EventHandler&lt;MediaPositionChangedEventArgs&gt;), typeof(MediaControl), propertyChanged: (bindableProperty, oldValue, newValue) =&gt;
{
var control = (MediaControl)bindableProperty;
control.mediaElement.PositionChanged += (EventHandler&lt;MediaPositionChangedEventArgs&gt;)newValue;
});
public EventHandler MediaOpened
{
get =&gt; GetValue(MediaOpenedProperty) as EventHandler;
set =&gt; SetValue(MediaOpenedProperty, value);
}
public EventHandler&lt;MediaStateChangedEventArgs&gt; StateChanged
{
get =&gt; GetValue(StateChangedProperty) as EventHandler&lt;MediaStateChangedEventArgs&gt;;
set =&gt; SetValue(StateChangedProperty, value);
}
public EventHandler&lt;MediaPositionChangedEventArgs&gt; PositionChanged
{
get =&gt; GetValue(PositionChangedProperty) as EventHandler&lt;MediaPositionChangedEventArgs&gt;;
set =&gt; SetValue(PositionChangedProperty, value);
}
public MediaSource Source
{
get =&gt; GetValue(SourceProperty) as MediaSource;
set =&gt; SetValue(SourceProperty, value);
}
public TimeSpan Position =&gt; mediaElement.Position;
public MediaElement Name
{
get =&gt; GetValue(TitleProperty) as MediaElement;
set =&gt; SetValue(TitleProperty, value);
}
public bool ShouldShowPlaybackControls
{
get =&gt; (bool)GetValue(ShouldShowPlaybackControlsProperty);
set =&gt; SetValue(ShouldShowPlaybackControlsProperty, value);
}
public bool ShouldAutoPlay
{
get =&gt; (bool)GetValue(ShouldAutoPlayProperty);
set =&gt; SetValue(ShouldAutoPlayProperty, value);
}
public bool ShouldKeepScreenOn
{
get =&gt; (bool)GetValue(ShouldKeepScreenOnProperty);
set =&gt; SetValue(ShouldKeepScreenOnProperty, value);
}
This lets me use all of the types of properties for media element I need to. It is not all of them. But I was able to move all my page specific code back to the actual pages and my ContentView class is no longer cluttered with code for other pages.
</details>

huangapple
  • 本文由 发表于 2023年3月31日 23:36:51
  • 转载请务必保留本文链接:https://go.coder-hub.com/75900343.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定