Archived
1
0

Closed captions

This commit is contained in:
Michael Gordeev
2018-09-08 23:49:56 +03:00
parent de240c8188
commit cc117a161c
6 changed files with 235 additions and 271 deletions
+26
View File
@@ -0,0 +1,26 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace FoxTube.Classes
{
public class Caption
{
public TimeSpan Start { get; private set; }
public TimeSpan Duration { get; private set; }
public TimeSpan End
{
get { return Start + Duration; }
}
public string Text { get; private set; }
public Caption(int startTime, int duration, string text)
{
Start = TimeSpan.FromMilliseconds(startTime);
Duration = TimeSpan.FromMilliseconds(duration);
Text = text;
}
}
}
+2 -2
View File
@@ -8,9 +8,9 @@
mc:Ignorable="d" mc:Ignorable="d"
HorizontalAlignment="Center" HorizontalAlignment="Center"
VerticalAlignment="Bottom" VerticalAlignment="Bottom"
Margin="0,75"> Margin="0,55">
<Grid Background="#99000000"> <Grid Background="#99000000">
<TextBlock Text="Hello, World!" Margin="5" FontSize="24"/> <TextBlock Text="Hello, World!" Name="text" Margin="5" FontSize="24"/>
</Grid> </Grid>
</UserControl> </UserControl>
+62 -1
View File
@@ -1,4 +1,5 @@
using System; using FoxTube.Classes;
using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.IO; using System.IO;
using System.Linq; using System.Linq;
@@ -12,6 +13,8 @@ using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Input; using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media; using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Navigation; using Windows.UI.Xaml.Navigation;
using System.Xml;
using System.Diagnostics;
// The User Control item template is documented at https://go.microsoft.com/fwlink/?LinkId=234236 // The User Control item template is documented at https://go.microsoft.com/fwlink/?LinkId=234236
@@ -19,9 +22,67 @@ namespace FoxTube.Controls
{ {
public sealed partial class LiveCaptions : UserControl public sealed partial class LiveCaptions : UserControl
{ {
public MediaElement Player { get; set; }
DispatcherTimer timer = new DispatcherTimer() { Interval = TimeSpan.FromMilliseconds(10) };
List<Caption> captions = new List<Caption>();
Caption currentCaption = null;
public LiveCaptions() public LiveCaptions()
{ {
this.InitializeComponent(); this.InitializeComponent();
timer.Tick += UpdateCaption;
}
private void UpdateCaption(object sender, object e)
{
TimeSpan currentPosition = Player.Position;
bool found = false;
captions.ForEach((x) =>
{
if (Player.Position >= x.Start && Player.Position <= x.End)
{
currentCaption = x;
text.Text = currentCaption.Text;
Visibility = Visibility.Visible;
found = true;
}
});
if (!found)
{
currentCaption = null;
Visibility = Visibility.Collapsed;
}
}
public void Initialize(string source)
{
XmlDocument doc = new XmlDocument();
doc.Load(source);
foreach (XmlElement i in doc["timedtext"]["body"].ChildNodes)
captions.Add(new Caption(int.Parse(i.GetAttribute("t")), int.Parse(i.GetAttribute("d")), i.InnerText));
captions.ForEach((x) =>
{
if(Player.Position > x.Start && Player.Position < x.End)
{
currentCaption = x;
text.Text = currentCaption.Text;
Visibility = Visibility.Visible;
}
});
timer.Start();
}
public void Close()
{
captions.Clear();
currentCaption = null;
Visibility = Visibility.Collapsed;
timer.Stop();
} }
} }
} }
+28 -25
View File
@@ -19,7 +19,7 @@
<Grid Background="White" Name="grid" Tapped="UserControl_Tapped"> <Grid Background="White" Name="grid" Tapped="UserControl_Tapped">
<MediaElement IsDoubleTapEnabled="False" CurrentStateChanged="videoSource_CurrentStateChanged" AutoPlay="False" Name="videoSource" AreTransportControlsEnabled="False" PosterSource="ms-appx:///Assets/videoThumbSample.png"/> <MediaElement IsDoubleTapEnabled="False" CurrentStateChanged="videoSource_CurrentStateChanged" AutoPlay="False" Name="videoSource" AreTransportControlsEnabled="False" PosterSource="ms-appx:///Assets/videoThumbSample.png"/>
<controls1:LiveCaptions/> <controls1:LiveCaptions Player="{x:Bind videoSource}" Visibility="Collapsed"/>
<Grid Name="controls" Visibility="Visible"> <Grid Name="controls" Visibility="Visible">
<Grid.RowDefinitions> <Grid.RowDefinitions>
@@ -36,7 +36,7 @@
<Button Click="minimize_Click" Name="minimize" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE011;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Minimize"/> <Button Click="minimize_Click" Name="minimize" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE011;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Minimize"/>
<StackPanel Grid.Column="1" Margin="10,0,10,0" VerticalAlignment="Center"> <StackPanel Grid.Column="1" Margin="10,0,10,0" VerticalAlignment="Center">
<TextBlock Name="title" Text="[Title]" Foreground="White" VerticalAlignment="Center" TextWrapping="WrapWholeWords" FontSize="20" MaxLines="1" ToolTipService.ToolTip="Title"/> <TextBlock Name="title" Text="[Title]" Foreground="White" VerticalAlignment="Center" TextWrapping="WrapWholeWords" FontSize="20" MaxLines="1" ToolTipService.ToolTip="Title"/>
<TextBlock Foreground="Gray" Text="[Channel name]" Name="channelName" FontStyle="Italic"/> <TextBlock Foreground="LightGray" Text="[Channel name]" Name="channelName" FontStyle="Italic"/>
</StackPanel> </StackPanel>
<StackPanel Grid.Column="2" Orientation="Horizontal" HorizontalAlignment="Right"> <StackPanel Grid.Column="2" Orientation="Horizontal" HorizontalAlignment="Right">
<Button Name="closeHeader" Click="close_Click" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE10A;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Close video"/> <Button Name="closeHeader" Click="close_Click" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE10A;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Close video"/>
@@ -83,14 +83,17 @@
<StackPanel Orientation="Horizontal"> <StackPanel Orientation="Horizontal">
<Button Click="play_Click" Name="play" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE768;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Play"/> <Button Click="play_Click" Name="play" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE768;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Play"/>
<Button Name="next" Click="next_Click" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE101;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Next video"/> <Button Name="next" Click="next_Click" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE101;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Next video"/>
<Button Name="openVolume" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE995;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Volume" Click="openVolume_Click"/> <Button Name="openVolume" Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE995;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Volume">
</StackPanel> <Button.Flyout>
<Popup Grid.Column="0" Margin="100,-200,50,0" IsOpen="False" IsLightDismissEnabled="True" Name="volumePane"> <Flyout>
<StackPanel Background="#7F000000" Width="50" Height="200"> <StackPanel Orientation="Horizontal" Margin="-10">
<Slider Orientation="Vertical" HorizontalAlignment="Center" Height="135" Margin="5,10,10,5" Name="volume" ValueChanged="volume_ValueChanged"/>
<Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE995;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Mute" Name="muteBtn" Click="muteBtn_Click"/> <Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE995;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Mute" Name="muteBtn" Click="muteBtn_Click"/>
<Slider Orientation="Horizontal" Width="150" Margin="10,5,10,0" VerticalAlignment="Center" Name="volume" ValueChanged="volume_ValueChanged"/>
</StackPanel>
</Flyout>
</Button.Flyout>
</Button>
</StackPanel> </StackPanel>
</Popup>
<Grid Grid.Column="1"> <Grid Grid.Column="1">
<TextBlock Name="elapsedTime" Foreground="White" Text="[Elapsed]" VerticalAlignment="Bottom" HorizontalAlignment="Left" ToolTipService.ToolTip="Time elapsed"/> <TextBlock Name="elapsedTime" Foreground="White" Text="[Elapsed]" VerticalAlignment="Bottom" HorizontalAlignment="Left" ToolTipService.ToolTip="Time elapsed"/>
@@ -104,23 +107,20 @@
<Line Stroke="White" StrokeThickness="2" Y1="5" Y2="45"/> <Line Stroke="White" StrokeThickness="2" Y1="5" Y2="45"/>
<Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE190;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Subtitles" Name="openSubs" Click="openSubs_Click"/> <Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE190;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Subtitles" Name="captionsBtn">
<Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE713;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Video quality" Name="openSets" Click="openSets_Click"/> <Button.Flyout>
<Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE740;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Full screen" Name="fullscreen" Click="fullscreen_Click"/> <Flyout>
<StackPanel Width="225">
<ToggleSwitch Name="subsSwitch" Toggled="subsSwitch_Toggled" OnContent="Subtitles" OffContent="Subtitles"/>
<ComboBox Name="subsLang" Header="Language" PlaceholderText="No subtitles are available" Visibility="Collapsed" HorizontalAlignment="Stretch" SelectionChanged="subsLang_SelectionChanged"/>
</StackPanel> </StackPanel>
</Flyout>
<Popup Grid.Column="2" Margin="0,-100,50,0" IsOpen="False" IsLightDismissEnabled="True" Name="subsPane"> </Button.Flyout>
<StackPanel Background="#7F000000" Width="252" Height="100" Padding="10"> </Button>
<ToggleSwitch Name="subsSwitch" Toggled="subsSwitch_Toggled" Foreground="White" OffContent="Show subtitles" OnContent="Show subtitles"/> <Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE713;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Video quality">
<ComboBox Name="subsLang" Width="232" PlaceholderText="No subtitles are available"/> <Button.Flyout>
</StackPanel> <Flyout>
</Popup> <ComboBox Width="225" Header="Quality" Name="quality" SelectionChanged="quality_SelectionChanged">
<Popup Grid.Column="2" IsOpen="False" Margin="0,-75,0,0" IsLightDismissEnabled="True" Name="qualityPane">
<StackPanel Background="#7F000000" Width="252" Height="75" Padding="10">
<TextBlock Text="Quality" Foreground="White"/>
<Line X1="0" X2="232" Stroke="White" StrokeThickness="2"/>
<ComboBox Width="232" Name="quality" SelectionChanged="quality_SelectionChanged">
<!--<ComboBoxItem Content="Auto"/>--> <!--<ComboBoxItem Content="Auto"/>-->
<ComboBoxItem Content="2160P" Visibility="Collapsed"/> <ComboBoxItem Content="2160P" Visibility="Collapsed"/>
<ComboBoxItem Content="1080p" Visibility="Collapsed"/> <ComboBoxItem Content="1080p" Visibility="Collapsed"/>
@@ -130,8 +130,11 @@
<ComboBoxItem Content="240p" Visibility="Collapsed"/> <ComboBoxItem Content="240p" Visibility="Collapsed"/>
<ComboBoxItem Content="144p" Visibility="Collapsed"/> <ComboBoxItem Content="144p" Visibility="Collapsed"/>
</ComboBox> </ComboBox>
</Flyout>
</Button.Flyout>
</Button>
<Button Background="Transparent" FontFamily="Segoe MDL2 Assets" Content="&#xE740;" Foreground="White" Width="50" Height="50" FontSize="25" ToolTipService.ToolTip="Full screen" Name="fullscreen" Click="fullscreen_Click"/>
</StackPanel> </StackPanel>
</Popup>
</Grid> </Grid>
</Grid> </Grid>
</Grid> </Grid>
+90 -217
View File
@@ -20,7 +20,6 @@ using Microsoft.Toolkit.Uwp.UI.Animations;
using Google.Apis.YouTube.v3.Data; using Google.Apis.YouTube.v3.Data;
using Google.Apis.YouTube.v3; using Google.Apis.YouTube.v3;
using Windows.UI.Xaml.Media.Imaging; using Windows.UI.Xaml.Media.Imaging;
using MyToolkit.Multimedia;
using Windows.Networking.Connectivity; using Windows.Networking.Connectivity;
using System.Diagnostics; using System.Diagnostics;
using Windows.Media; using Windows.Media;
@@ -32,6 +31,10 @@ using Windows.UI;
using Windows.Graphics.Display; using Windows.Graphics.Display;
using Windows.Media.Casting; using Windows.Media.Casting;
using YoutubeExplode.Models.MediaStreams; using YoutubeExplode.Models.MediaStreams;
using YoutubeExplode;
using YoutubeExplode.Models.ClosedCaptions;
using System.Globalization;
using FoxTube.Controls;
// The User Control item template is documented at https://go.microsoft.com/fwlink/?LinkId=234236 // The User Control item template is documented at https://go.microsoft.com/fwlink/?LinkId=234236
@@ -56,11 +59,15 @@ namespace FoxTube
Video item; Video item;
string avatar; string avatar;
double timecodeBackup; double timecodeBackup = 0;
bool needUpdateTimecode = false;
SystemMediaTransportControls systemControls = SystemMediaTransportControls.GetForCurrentView(); SystemMediaTransportControls systemControls = SystemMediaTransportControls.GetForCurrentView();
LiveCaptions captions;
List<YouTubeUri> uris = new List<YouTubeUri>(); YoutubeClient client = new YoutubeClient();
IReadOnlyList<ClosedCaptionTrackInfo> ccInfo;
MediaStreamInfoSet streamInfo;
ApplicationDataContainer settings = ApplicationData.Current.LocalSettings; ApplicationDataContainer settings = ApplicationData.Current.LocalSettings;
Timer t = new Timer() Timer t = new Timer()
@@ -81,6 +88,8 @@ namespace FoxTube
if (!ApplicationView.GetForCurrentView().IsViewModeSupported(ApplicationViewMode.CompactOverlay)) if (!ApplicationView.GetForCurrentView().IsViewModeSupported(ApplicationViewMode.CompactOverlay))
miniViewBtn.Visibility = Visibility.Collapsed;; miniViewBtn.Visibility = Visibility.Collapsed;;
captions = grid.Children[1] as LiveCaptions;
volume.Value = Convert.ToDouble(settings.Values["volume"]); volume.Value = Convert.ToDouble(settings.Values["volume"]);
videoSource.AutoPlay = (bool)settings.Values["videoAutoplay"]; videoSource.AutoPlay = (bool)settings.Values["videoAutoplay"];
@@ -94,121 +103,48 @@ namespace FoxTube
avatar = channelAvatar; avatar = channelAvatar;
videoId = item.Id; videoId = item.Id;
#region Checking qualities availability #region Retrieving info for CC and Media streams
uris = new List<YouTubeUri>(await YouTube.GetUrisAsync(videoId)); //Loading streams
streamInfo = await client.GetVideoMediaStreamInfosAsync(item.Id);
foreach (YouTubeUri i in uris.ToList()) foreach(MuxedStreamInfo i in streamInfo.Muxed)
if (!i.HasAudio || !i.HasVideo)
uris.Remove(i);
foreach (YouTubeUri u in uris)
{ {
Debug.WriteLine("-----------------"); if (i.VideoQuality == VideoQuality.High2160)
Debug.WriteLine("URI: " + u.Uri);
Debug.WriteLine("Has video: " + u.HasVideo);
Debug.WriteLine("Has audio: " + u.HasAudio);
Debug.WriteLine("Type: " + u.Type);
Debug.WriteLine("Video quality: " + u.VideoQuality);
Debug.WriteLine("Audio quality: " + u.AudioQuality);
Debug.WriteLine("-----------------");
}
foreach(YouTubeUri i in uris)
switch(i.VideoQuality)
{
case YouTubeQuality.Quality2160P:
(quality.Items[0] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[0] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.High1080)
case YouTubeQuality.Quality1080P:
(quality.Items[1] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[1] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.High720)
case YouTubeQuality.Quality720P:
(quality.Items[2] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[2] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.Medium480)
case YouTubeQuality.Quality480P:
(quality.Items[3] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[3] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.Medium360)
case YouTubeQuality.Quality360P:
(quality.Items[4] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[4] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.Low240)
case YouTubeQuality.Quality240P:
(quality.Items[5] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[5] as ComboBoxItem).Visibility = Visibility.Visible;
break; if (i.VideoQuality == VideoQuality.Low144)
case YouTubeQuality.Quality144P:
(quality.Items[6] as ComboBoxItem).Visibility = Visibility.Visible; (quality.Items[6] as ComboBoxItem).Visibility = Visibility.Visible;
break;
} }
int k = (int)settings.Values["quality"]; int k = (int)settings.Values["quality"];
switch(k) if ((quality.Items[k] as ComboBoxItem).Visibility == Visibility.Visible)
quality.SelectedIndex = k;
else
quality.SelectedItem = quality.Items.First(x => (x as ComboBoxItem).Visibility == Visibility.Visible);
//Loading captions
ccInfo = await client.GetVideoClosedCaptionTrackInfosAsync(item.Id);
foreach (ClosedCaptionTrackInfo cc in ccInfo)
subsLang.Items.Add(new ComboBoxItem()
{ {
case 0: Content = string.Format("{1}{0}", CultureInfo.GetCultureInfo(cc.Language.Code).DisplayName, cc.IsAutoGenerated ? " (Auto-generated)" : ""),
foreach(YouTubeUri i in uris) Tag = cc
if(i.VideoQuality == YouTubeQuality.Quality2160P) });
{ if(ccInfo.Count > 0)
quality.SelectedIndex = 0; subsLang.SelectedIndex = 0;
break; else
} captionsBtn.Visibility = Visibility.Collapsed;
SetFirstQuality();
break;
case 1:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality1080P)
{
quality.SelectedIndex = 1;
break;
}
SetFirstQuality();
break;
case 2:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality720P)
{
quality.SelectedIndex = 2;
break;
}
SetFirstQuality();
break;
case 3:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality480P)
{
quality.SelectedIndex = 3;
break;
}
SetFirstQuality();
break;
case 4:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality360P)
{
quality.SelectedIndex = 4;
break;
}
SetFirstQuality();
break;
case 5:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality240P)
{
quality.SelectedIndex = 5;
break;
}
SetFirstQuality();
break;
case 6:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality144P)
{
quality.SelectedIndex = 6;
break;
}
SetFirstQuality();
break;
}
#endregion #endregion
if(item.ContentDetails.ContentRating != null) if (item.ContentDetails.ContentRating != null)
{ {
if(SecretsVault.IsAuthorized && settings.Values["showMature"] != null) if(SecretsVault.IsAuthorized && settings.Values["showMature"] != null)
{ {
@@ -261,34 +197,6 @@ namespace FoxTube
Visibility = Visibility.Visible; Visibility = Visibility.Visible;
} }
void SetFirstQuality()
{
switch (uris[0].VideoQuality)
{
case YouTubeQuality.Quality2160P:
quality.SelectedIndex = 0;
break;
case YouTubeQuality.Quality1080P:
quality.SelectedIndex = 1;
break;
case YouTubeQuality.Quality720P:
quality.SelectedIndex = 2;
break;
case YouTubeQuality.Quality480P:
quality.SelectedIndex = 3;
break;
case YouTubeQuality.Quality360P:
quality.SelectedIndex = 4;
break;
case YouTubeQuality.Quality240P:
quality.SelectedIndex = 5;
break;
case YouTubeQuality.Quality144P:
quality.SelectedIndex = 6;
break;
}
}
private async void SystemControls_Engaged(SystemMediaTransportControls sender, SystemMediaTransportControlsButtonPressedEventArgs args) private async void SystemControls_Engaged(SystemMediaTransportControls sender, SystemMediaTransportControlsButtonPressedEventArgs args)
{ {
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () => await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
@@ -327,18 +235,15 @@ namespace FoxTube
} }
void Elapsed() void Elapsed()
{
if(!volumePane.IsOpen && !qualityPane.IsOpen && !subsPane.IsOpen)
{ {
controls.Visibility = Visibility.Collapsed; controls.Visibility = Visibility.Collapsed;
if(!miniView) if (!miniView)
touchCentral.Visibility = Visibility.Collapsed; touchCentral.Visibility = Visibility.Collapsed;
if (pointerCaptured) if (pointerCaptured)
Window.Current.CoreWindow.PointerCursor = null; Window.Current.CoreWindow.PointerCursor = null;
seekIndicator.Visibility = Visibility.Collapsed; seekIndicator.Visibility = Visibility.Collapsed;
t.Stop(); t.Stop();
} }
}
public void UpdateSize() public void UpdateSize()
{ {
@@ -349,11 +254,6 @@ namespace FoxTube
} }
} }
private void openVolume_Click(object sender, RoutedEventArgs e)
{
volumePane.IsOpen = true;
}
private void volume_ValueChanged(object sender, RangeBaseValueChangedEventArgs e) private void volume_ValueChanged(object sender, RangeBaseValueChangedEventArgs e)
{ {
double v = volume.Value; double v = volume.Value;
@@ -373,17 +273,6 @@ namespace FoxTube
videoSource.Volume = volume.Value * 0.01; videoSource.Volume = volume.Value * 0.01;
} }
private void openSets_Click(object sender, RoutedEventArgs e)
{
qualityPane.IsOpen = true;
}
private void openSubs_Click(object sender, RoutedEventArgs e)
{
subsPane.IsOpen = true;
subsSwitch.IsOn = !subsSwitch.IsOn;
}
private void muteBtn_Click(object sender, RoutedEventArgs e) private void muteBtn_Click(object sender, RoutedEventArgs e)
{ {
if(volume.Value != 0) if(volume.Value != 0)
@@ -397,7 +286,7 @@ namespace FoxTube
private void UserControl_Tapped(object sender, TappedRoutedEventArgs e) private void UserControl_Tapped(object sender, TappedRoutedEventArgs e)
{ {
if (e.PointerDeviceType != Windows.Devices.Input.PointerDeviceType.Mouse) if (e.PointerDeviceType == Windows.Devices.Input.PointerDeviceType.Touch)
{ {
touchCentral.Visibility = Visibility.Visible; touchCentral.Visibility = Visibility.Visible;
if (t.Enabled) if (t.Enabled)
@@ -405,7 +294,6 @@ namespace FoxTube
else else
ShowControls(); ShowControls();
} }
//else play_Click(this, null);
} }
private void UserControl_PointerMoved(object sender, PointerRoutedEventArgs e) private void UserControl_PointerMoved(object sender, PointerRoutedEventArgs e)
@@ -426,91 +314,64 @@ namespace FoxTube
private void quality_SelectionChanged(object sender, SelectionChangedEventArgs e) private void quality_SelectionChanged(object sender, SelectionChangedEventArgs e)
{ {
if(uris.Count > 0) try
{ {
videoSource.Pause(); videoSource.Pause();
timecodeBackup = videoSource.Position.TotalSeconds; timecodeBackup = videoSource.Position.TotalSeconds;
switch(quality.SelectedIndex) switch((quality.SelectedItem as ComboBoxItem).Content)
{ {
case 0: case "2160p":
foreach (YouTubeUri i in uris) videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.High2160).Url);
if (i.VideoQuality == YouTubeQuality.Quality2160P)
{
videoSource.Source = i.Uri;
break; break;
} case "1080p":
videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.High1080).Url);
break; break;
case 1: case "720p":
foreach (YouTubeUri i in uris) videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.High720).Url);
if (i.VideoQuality == YouTubeQuality.Quality1080P)
{
videoSource.Source = i.Uri;
break; break;
} case "480p":
videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.Medium480).Url);
break; break;
case 2: case "360p":
foreach (YouTubeUri i in uris) videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.Medium360).Url);
if (i.VideoQuality == YouTubeQuality.Quality720P)
{
videoSource.Source = i.Uri;
break; break;
} case "240p":
videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.Low240).Url);
break; break;
case 3: case "144p":
foreach (YouTubeUri i in uris) videoSource.Source = new Uri(streamInfo.Muxed.First(x => x.VideoQuality == VideoQuality.Low144).Url);
if (i.VideoQuality == YouTubeQuality.Quality480P)
{
videoSource.Source = i.Uri;
break;
}
break;
case 4:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality360P)
{
videoSource.Source = i.Uri;
break;
}
break;
case 5:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality240P)
{
videoSource.Source = i.Uri;
break;
}
break;
case 6:
foreach (YouTubeUri i in uris)
if (i.VideoQuality == YouTubeQuality.Quality144P)
{
videoSource.Source = i.Uri;
break;
}
break; break;
} }
needUpdateTimecode = true;
videoSource.Play(); videoSource.Play();
Timer timer = new Timer(1000);
timer.Elapsed += Timer_Elapsed;
timer.Start();
}
} }
catch
{
private async void Timer_Elapsed(object sender, ElapsedEventArgs e) }
{
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
{
(sender as Timer).Stop();
videoSource.Position = TimeSpan.FromSeconds(timecodeBackup);
});
} }
private void subsSwitch_Toggled(object sender, RoutedEventArgs e) private void subsSwitch_Toggled(object sender, RoutedEventArgs e)
{ {
if (subsSwitch.IsOn)
subsLang.Visibility = Visibility.Visible;
else
subsLang.Visibility = Visibility.Collapsed;
LoadTrack();
}
void LoadTrack()
{
if (subsSwitch.IsOn)
{
captions.Initialize(ccInfo[subsLang.SelectedIndex].Url);
}
else
captions.Close();
} }
private void fullscreen_Click(object sender, RoutedEventArgs e) private void fullscreen_Click(object sender, RoutedEventArgs e)
@@ -543,6 +404,12 @@ namespace FoxTube
private void videoSource_CurrentStateChanged(object sender, RoutedEventArgs e) private void videoSource_CurrentStateChanged(object sender, RoutedEventArgs e)
{ {
if(videoSource.CurrentState == MediaElementState.Playing && needUpdateTimecode)
{
videoSource.Position = TimeSpan.FromSeconds(timecodeBackup);
needUpdateTimecode = false;
}
switch(videoSource.CurrentState) switch(videoSource.CurrentState)
{ {
case MediaElementState.Buffering: case MediaElementState.Buffering:
@@ -824,5 +691,11 @@ namespace FoxTube
break; break;
} }
} }
private void subsLang_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (subsSwitch.IsOn)
captions.Initialize(ccInfo[subsLang.SelectedIndex].Url);
}
} }
} }
+1
View File
@@ -96,6 +96,7 @@
<Compile Include="App.xaml.cs"> <Compile Include="App.xaml.cs">
<DependentUpon>App.xaml</DependentUpon> <DependentUpon>App.xaml</DependentUpon>
</Compile> </Compile>
<Compile Include="Classes\Caption.cs" />
<Compile Include="Classes\InboxItem.cs" /> <Compile Include="Classes\InboxItem.cs" />
<Compile Include="Classes\Methods.cs" /> <Compile Include="Classes\Methods.cs" />
<Compile Include="Classes\ObjectEventArgs.cs" /> <Compile Include="Classes\ObjectEventArgs.cs" />