For some reason, MediaPlayerElement
's CC font size is affected by many factors, I can't get the exact font size. Refer to SO link, How to get system's closed caption font size?.
So do anyone has ideas how to create a second/bilingual subtitle, the same size to MediaPlayerElement's CC?
You can use the ControlTemplate
that modifies MediaPlayerElement
to create your custom subtitle control.
Making a complete subtitle control is more complicated. I will only provide one idea here.
1. We need to create a control class derived from MediaPlayerElement
as our test case.
public class CustomMediaPlayerElement:MediaPlayerElement
{
public string SecondCaption
{
get { return (string)GetValue(SecondCaptionProperty); }
set { SetValue(SecondCaptionProperty, value); }
}
public static readonly DependencyProperty SecondCaptionProperty =
DependencyProperty.Register("SecondCaption", typeof(string), typeof(CustomMediaPlayerElement), new PropertyMetadata(""));
}
We add a dependency property of SecondCaption
, which is the text of the second subtitle we are currently displaying. In the future, we can switch the displayed text with a timer.
2. Create the custom control template
Since MediaPlayerElement's CC font size is variable, we can use ViewBox
for simulation.
<Style TargetType="local:CustomMediaPlayerElement" x:Key="BasicMediaStyle">
<Setter Property="HorizontalAlignment" Value="Stretch" />
<Setter Property="VerticalAlignment" Value="Stretch" />
<Setter Property="IsTabStop" Value="False" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="local:CustomMediaPlayerElement">
<Grid x:Name="LayoutRoot">
<Border Background="Transparent" />
<Image x:Name="PosterImage"
Visibility="Collapsed"
Source="{TemplateBinding PosterSource}"
Stretch="{TemplateBinding Stretch}" />
<MediaPlayerPresenter x:Name="MediaPlayerPresenter"
IsFullWindow="{TemplateBinding IsFullWindow}"
Stretch="{TemplateBinding Stretch}"
MediaPlayer="{TemplateBinding MediaPlayer}" />
<ContentPresenter x:Name="TransportControlsPresenter"
Visibility="{TemplateBinding AreTransportControlsEnabled}" IsTapEnabled="False"/>
<Grid x:Name="TimedTextSourcePresenter" />
<Grid x:Name="SecondTimedTextSourceContainer">
<Viewbox>
<Grid>
<TextBlock Text="{TemplateBinding SecondCaption}" FontSize="15" VerticalAlignment="Bottom"
HorizontalAlignment="Center" TextAlignment="Center" Foreground="White"/>
</Grid>
</Viewbox>
</Grid>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
3. Add addition properties to make the subtitle display the correct size
If we only write as above, we will end up with a TextBlock
that fills the entire screen. In order for the ViewBox
to work as we expect, we need to add some new attributes to make the container where the subtitles are the right size.
CustomMediaPlayerElement.cs
public double SourceWidth
{
get { return (double)GetValue(SourceWidthProperty); }
set { SetValue(SourceWidthProperty, value); }
}
public static readonly DependencyProperty SourceWidthProperty =
DependencyProperty.Register("SourceWidth", typeof(double), typeof(CustomMediaPlayerElement), new PropertyMetadata(double.NaN));
public double SourceHeight
{
get { return (double)GetValue(SourceHeightProperty); }
set { SetValue(SourceHeightProperty, value); }
}
public static readonly DependencyProperty SourceHeightProperty =
DependencyProperty.Register("SourceHeight", typeof(double), typeof(CustomMediaPlayerElement), new PropertyMetadata(double.NaN));
CustomeMediaPlayerElement.xaml
...
<Viewbox>
<Grid Height="{TemplateBinding SourceHeight}" Width="{TemplateBinding SourceWidth}">
<TextBlock Text="{TemplateBinding SecondCaption}" FontSize="15" VerticalAlignment="Bottom"
HorizontalAlignment="Center" TextAlignment="Center" Foreground="White"/>
</Grid>
</Viewbox>
...
How to use
<controls:CustomMediaPlayerElement SecondCaption="Hello World" x:Name="MyPlayer"
AreTransportControlsEnabled="True" Style="{StaticResource BasicMediaStyle}"
/>
private async Task LoadVideo(StorageFile videoFile)
{
var player = new MediaPlayer();
var source = MediaSource.CreateFromStorageFile(videoFile);
player.Source = source;
player.MediaOpened += Media_Opened;
MyPlayer.SetMediaPlayer(player);
}
private async void Media_Opened(MediaPlayer sender, object args)
{
await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
{
MyPlayer.SourceWidth = sender.PlaybackSession.NaturalVideoWidth;
MyPlayer.SourceHeight = sender.PlaybackSession.NaturalVideoHeight;
});
}
In this way, you can get a subtitle control that will scale with MediaPlayerElement
, and modify the SecondCaption
with the timer to achieve the function of subtitles.
But as I said before, it is complicated to implement a complete subtitle control. This is just a way to add a new subtitle control, you need to customize according to your needs.
Thanks.