430 lines
14 KiB
C#
430 lines
14 KiB
C#
using CommunityToolkit.Mvvm.ComponentModel;
|
|
using CommunityToolkit.Mvvm.Input;
|
|
using CommunityToolkit.WinUI.Helpers;
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Net.Http;
|
|
using System.Text;
|
|
using System.Threading.Tasks;
|
|
using VDownload.Core.Strings;
|
|
using VDownload.Core.Tasks;
|
|
using VDownload.Models;
|
|
using VDownload.Services.Data.Configuration;
|
|
using VDownload.Services.Data.Settings;
|
|
using VDownload.Services.Data.Subscriptions;
|
|
using VDownload.Services.UI.Dialogs;
|
|
using VDownload.Sources;
|
|
using VDownload.Sources.Common;
|
|
using VDownload.Sources.Twitch.Configuration.Models;
|
|
|
|
namespace VDownload.Core.ViewModels.Home
|
|
{
|
|
public partial class HomeViewModel : ObservableObject
|
|
{
|
|
#region ENUMS
|
|
|
|
public enum OptionBarContentType
|
|
{
|
|
None,
|
|
VideoSearch,
|
|
PlaylistSearch
|
|
}
|
|
|
|
public enum MainContentType
|
|
{
|
|
Downloads,
|
|
Video
|
|
}
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region SERVICES
|
|
|
|
protected readonly IConfigurationService _configurationService;
|
|
protected readonly ISettingsService _settingsService;
|
|
protected readonly ISearchService _searchService;
|
|
protected readonly ISubscriptionsDataService _subscriptionsDataService;
|
|
protected readonly IDialogsService _dialogsService;
|
|
|
|
protected readonly IDownloadTaskManager _downloadTaskManager;
|
|
|
|
protected readonly HomeVideoViewModel _videoViewModel;
|
|
protected readonly HomeVideoCollectionViewModel _videoCollectionViewModel;
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region FIELDS
|
|
|
|
protected readonly Type _downloadsView = typeof(HomeDownloadsViewModel);
|
|
protected readonly Type _videoView = typeof(HomeVideoViewModel);
|
|
protected readonly Type _videoCollectionView = typeof(HomeVideoCollectionViewModel);
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region PROPERTIES
|
|
|
|
[ObservableProperty]
|
|
private Type _mainContent;
|
|
|
|
[ObservableProperty]
|
|
private string _optionBarError;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarIsErrorOpened;
|
|
|
|
[ObservableProperty]
|
|
private OptionBarContentType _optionBarContent;
|
|
|
|
[ObservableProperty]
|
|
private string _optionBarMessage;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarLoading;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarLoadSubscriptionButtonChecked;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarVideoSearchButtonChecked;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarPlaylistSearchButtonChecked;
|
|
|
|
[ObservableProperty]
|
|
private bool _optionBarSearchNotPending;
|
|
|
|
[ObservableProperty]
|
|
private string _optionBarVideoSearchTBValue;
|
|
|
|
[ObservableProperty]
|
|
private string _optionBarPlaylistSearchTBValue;
|
|
|
|
[ObservableProperty]
|
|
private int _optionBarPlaylistSearchNBValue;
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region CONSTRUCTORS
|
|
|
|
public HomeViewModel(IConfigurationService configurationService, ISettingsService settingsService, ISearchService searchService, ISubscriptionsDataService subscriptionsDataService, IDialogsService dialogsService, IDownloadTaskManager downloadTaskManager, HomeVideoViewModel videoViewModel, HomeVideoCollectionViewModel videoCollectionViewModel)
|
|
{
|
|
_configurationService = configurationService;
|
|
_settingsService = settingsService;
|
|
_searchService = searchService;
|
|
_subscriptionsDataService = subscriptionsDataService;
|
|
_dialogsService = dialogsService;
|
|
|
|
_downloadTaskManager = downloadTaskManager;
|
|
|
|
_videoViewModel = videoViewModel;
|
|
_videoViewModel.CloseRequested += BackToDownload_EventHandler;
|
|
|
|
_videoCollectionViewModel = videoCollectionViewModel;
|
|
_videoCollectionViewModel.CloseRequested += BackToDownload_EventHandler;
|
|
}
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region COMMANDS
|
|
|
|
[RelayCommand]
|
|
public async Task Navigation()
|
|
{
|
|
await _settingsService.Load();
|
|
|
|
MainContent = _downloadsView;
|
|
|
|
OptionBarContent = OptionBarContentType.None;
|
|
OptionBarLoading = false;
|
|
OptionBarMessage = null;
|
|
OptionBarError = null;
|
|
OptionBarIsErrorOpened = true;
|
|
OptionBarLoadSubscriptionButtonChecked = false;
|
|
OptionBarVideoSearchButtonChecked = false;
|
|
OptionBarPlaylistSearchButtonChecked = false;
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarVideoSearchTBValue = string.Empty;
|
|
OptionBarPlaylistSearchNBValue = _settingsService.Data.Common.Searching.MaxNumberOfVideosToGetFromPlaylist;
|
|
OptionBarPlaylistSearchTBValue = string.Empty;
|
|
}
|
|
|
|
[RelayCommand]
|
|
public async Task LoadFromSubscription()
|
|
{
|
|
SearchButtonClicked();
|
|
|
|
if (OptionBarLoadSubscriptionButtonChecked)
|
|
{
|
|
if (!NetworkHelper.Instance.ConnectionInformation.IsInternetAvailable)
|
|
{
|
|
ShowError(ErrorNoInternetConnection());
|
|
OptionBarLoadSubscriptionButtonChecked = false;
|
|
return;
|
|
}
|
|
|
|
OptionBarContent = OptionBarContentType.None;
|
|
OptionBarVideoSearchButtonChecked = false;
|
|
OptionBarPlaylistSearchButtonChecked = false;
|
|
|
|
StartSearch();
|
|
|
|
SubscriptionsVideoList subList = new SubscriptionsVideoList { Name = StringResourcesManager.Common.Get("SubscriptionVideoListName") };
|
|
List<Task> tasks = new List<Task>();
|
|
try
|
|
{
|
|
foreach (Subscription sub in _subscriptionsDataService.Data.ToArray())
|
|
{
|
|
tasks.Add(Task.Run(async () =>
|
|
{
|
|
Playlist playlist;
|
|
try
|
|
{
|
|
playlist = await _searchService.SearchPlaylist(sub.Url.OriginalString, 0);
|
|
}
|
|
catch (MediaSearchException)
|
|
{
|
|
return;
|
|
}
|
|
|
|
IEnumerable<Video> newIds = playlist.Where(x => !sub.VideoIds.Contains(x.Id));
|
|
subList.AddRange(newIds);
|
|
foreach (Video video in newIds)
|
|
{
|
|
sub.VideoIds.Add(video.Id);
|
|
}
|
|
}));
|
|
}
|
|
await Task.WhenAll(tasks);
|
|
await _subscriptionsDataService.Save();
|
|
}
|
|
catch (Exception ex) when (ex is TaskCanceledException || ex is HttpRequestException)
|
|
{
|
|
ShowError(ErrorSearchTimeout());
|
|
return;
|
|
}
|
|
|
|
if (subList.Count > 0)
|
|
{
|
|
OptionBarMessage = $"{StringResourcesManager.HomeView.Get("OptionBarMessageVideosFound")} {subList.Count}";
|
|
|
|
_videoCollectionViewModel.LoadCollection(subList);
|
|
MainContent = _videoCollectionView;
|
|
}
|
|
else
|
|
{
|
|
OptionBarMessage = StringResourcesManager.HomeView.Get("OptionBarMessageVideosNotFound");
|
|
}
|
|
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarLoading = false;
|
|
}
|
|
}
|
|
|
|
[RelayCommand]
|
|
public void VideoSearchShow()
|
|
{
|
|
SearchButtonClicked();
|
|
|
|
if (OptionBarContent != OptionBarContentType.VideoSearch)
|
|
{
|
|
OptionBarContent = OptionBarContentType.VideoSearch;
|
|
OptionBarPlaylistSearchButtonChecked = false;
|
|
OptionBarLoadSubscriptionButtonChecked = false;
|
|
}
|
|
else
|
|
{
|
|
OptionBarContent = OptionBarContentType.None;
|
|
}
|
|
}
|
|
|
|
[RelayCommand]
|
|
public void PlaylistSearchShow()
|
|
{
|
|
SearchButtonClicked();
|
|
|
|
if (OptionBarContent != OptionBarContentType.PlaylistSearch)
|
|
{
|
|
OptionBarContent = OptionBarContentType.PlaylistSearch;
|
|
OptionBarVideoSearchButtonChecked = false;
|
|
OptionBarLoadSubscriptionButtonChecked = false;
|
|
}
|
|
else
|
|
{
|
|
OptionBarContent = OptionBarContentType.None;
|
|
}
|
|
}
|
|
|
|
[RelayCommand]
|
|
public async Task VideoSearchStart()
|
|
{
|
|
if (!NetworkHelper.Instance.ConnectionInformation.IsInternetAvailable)
|
|
{
|
|
ShowError(ErrorNoInternetConnection());
|
|
return;
|
|
}
|
|
|
|
StartSearch();
|
|
|
|
Video video;
|
|
try
|
|
{
|
|
video = await _searchService.SearchVideo(OptionBarVideoSearchTBValue);
|
|
}
|
|
catch (MediaSearchException ex)
|
|
{
|
|
ShowError(StringResourcesManager.Search.Get(ex.StringCode));
|
|
return;
|
|
}
|
|
catch (Exception ex) when (ex is TaskCanceledException || ex is HttpRequestException)
|
|
{
|
|
ShowError(ErrorSearchTimeout());
|
|
return;
|
|
}
|
|
|
|
await _videoViewModel.LoadVideo(video);
|
|
|
|
MainContent = _videoView;
|
|
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarLoading = false;
|
|
OptionBarMessage = null;
|
|
}
|
|
|
|
[RelayCommand]
|
|
public async Task PlaylistSearchStart()
|
|
{
|
|
if (!NetworkHelper.Instance.ConnectionInformation.IsInternetAvailable)
|
|
{
|
|
ShowError(ErrorNoInternetConnection());
|
|
return;
|
|
}
|
|
|
|
StartSearch();
|
|
|
|
Playlist playlist;
|
|
try
|
|
{
|
|
playlist = await _searchService.SearchPlaylist(OptionBarPlaylistSearchTBValue, OptionBarPlaylistSearchNBValue);
|
|
}
|
|
catch (MediaSearchException ex)
|
|
{
|
|
ShowError(StringResourcesManager.Search.Get(ex.StringCode));
|
|
return;
|
|
}
|
|
catch (Exception ex) when (ex is TaskCanceledException || ex is HttpRequestException)
|
|
{
|
|
ShowError(ErrorSearchTimeout());
|
|
return;
|
|
}
|
|
|
|
_videoCollectionViewModel.LoadCollection(playlist);
|
|
|
|
MainContent = _videoCollectionView;
|
|
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarLoading = false;
|
|
OptionBarMessage = null;
|
|
}
|
|
|
|
[RelayCommand]
|
|
public async Task Download()
|
|
{
|
|
if (_downloadTaskManager.Tasks.Count > 0)
|
|
{
|
|
if (!NetworkHelper.Instance.ConnectionInformation.IsInternetAvailable)
|
|
{
|
|
ShowError(ErrorNoInternetConnection());
|
|
return;
|
|
}
|
|
|
|
if
|
|
(
|
|
_settingsService.Data.Common.Tasks.ShowMeteredConnectionWarnings
|
|
&&
|
|
NetworkHelper.Instance.ConnectionInformation.IsInternetOnMeteredConnection
|
|
)
|
|
{
|
|
string title = StringResourcesManager.Common.Get("StartAtMeteredConnectionDialogTitle");
|
|
string message = StringResourcesManager.Common.Get("StartAtMeteredConnectionDialogMessage");
|
|
DialogResultYesNo result = await _dialogsService.ShowYesNo(title, message);
|
|
if (result == DialogResultYesNo.No)
|
|
{
|
|
return;
|
|
}
|
|
}
|
|
|
|
foreach (DownloadTask task in _downloadTaskManager.Tasks)
|
|
{
|
|
task.Enqueue();
|
|
}
|
|
}
|
|
}
|
|
|
|
[RelayCommand]
|
|
public async Task Cancel()
|
|
{
|
|
List<Task> tasks = new List<Task>();
|
|
foreach (DownloadTask task in _downloadTaskManager.Tasks)
|
|
{
|
|
tasks.Add(task.Cancel());
|
|
}
|
|
await Task.WhenAll(tasks);
|
|
}
|
|
|
|
[RelayCommand]
|
|
public void CloseError()
|
|
{
|
|
OptionBarError = null;
|
|
OptionBarIsErrorOpened = true;
|
|
}
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region PRIVATE METHODS
|
|
|
|
protected void ShowError(string message)
|
|
{
|
|
OptionBarError = message;
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarLoading = false;
|
|
OptionBarMessage = null;
|
|
}
|
|
|
|
protected void SearchButtonClicked()
|
|
{
|
|
OptionBarSearchNotPending = true;
|
|
OptionBarLoading = false;
|
|
OptionBarMessage = null;
|
|
MainContent = _downloadsView;
|
|
}
|
|
|
|
protected void StartSearch()
|
|
{
|
|
OptionBarSearchNotPending = false;
|
|
OptionBarLoading = true;
|
|
OptionBarMessage = StringResourcesManager.HomeView.Get("OptionBarMessageLoading");
|
|
}
|
|
|
|
protected async void BackToDownload_EventHandler(object sender, EventArgs e) => await Navigation();
|
|
|
|
protected string ErrorNoInternetConnection() => StringResourcesManager.HomeView.Get("ErrorInfoBarNoInternetConnection");
|
|
|
|
protected string ErrorSearchTimeout() => StringResourcesManager.Search.Get("SearchTimeout");
|
|
|
|
#endregion
|
|
}
|
|
}
|