diff --git a/DailyDesktop.Core/Configuration/AbstractConfiguration.cs b/DailyDesktop.Core/Configuration/AbstractConfiguration.cs index db47cf8..0fb4425 100644 --- a/DailyDesktop.Core/Configuration/AbstractConfiguration.cs +++ b/DailyDesktop.Core/Configuration/AbstractConfiguration.cs @@ -36,41 +36,12 @@ public AbstractConfiguration(string jsonPath = "") [JsonIgnore] public virtual bool IsAutoSerializing { get; set; } - /// - public event EventHandler? OnUpdate; - - /// - public event EventHandler? OnSerialize; - /// public event AsyncEventHandler? OnUpdateAsync; /// public event AsyncEventHandler? OnSerializeAsync; - /// - /// Deserialize a JSON file (located at ) to a configuration. - /// - public void Deserialize() - { - if (string.IsNullOrWhiteSpace(JsonPath)) - throw new InvalidOperationException($"{JsonPath} is null or whitespace."); - - var options = new JsonSerializerOptions(); - ConfigureDeserializer(options); - - T newConfig; - using (var jsonStream = File.OpenRead(JsonPath)) - newConfig = JsonSerializer.Deserialize(jsonStream, options) ?? throw new NullReferenceException("Deserialized config was null."); - - bool temp = IsAutoSerializing; - IsAutoSerializing = false; - - Load(newConfig); - - IsAutoSerializing = temp; - } - /// /// Asynchronously deserialize a JSON file (located at ) to a configuration. /// @@ -94,29 +65,6 @@ public async Task DeserializeAsync(CancellationToken cancellationToken) IsAutoSerializing = temp; } - /// - /// Try to deserialize a JSON file (located at ) to a configuration. - /// - /// - /// Whether or not the deserialiazation was successful. - /// - public bool TryDeserialize() - { - try - { - Deserialize(); - return true; - } - catch (Exception ex) when (ex is JsonException - || ex is IOException - || ex is SystemException - || ex is InvalidOperationException - || ex is NullReferenceException) - { - return false; - } - } - /// /// Try to asynchronously deserialize a JSON file (located at ) to a configuration. /// @@ -140,15 +88,6 @@ public async Task TryDeserializeAsync(CancellationToken cancellationToken) } } - /// - public void Update() - { - OnUpdate?.Invoke(this, EventArgs.Empty); - - if (IsAutoSerializing) - Serialize(); - } - /// public async Task UpdateAsync(CancellationToken cancellationToken) { @@ -158,24 +97,6 @@ public async Task UpdateAsync(CancellationToken cancellationToken) await SerializeAsync(cancellationToken); } - /// - public void Serialize() - { - if (!(this is T @this)) - throw new InvalidCastException($"this is not of type {nameof(T)}: {typeof(T).FullName}."); - - if (string.IsNullOrWhiteSpace(JsonPath)) - throw new InvalidOperationException($"{JsonPath} is null or whitespace."); - - var options = new JsonSerializerOptions(); - ConfigureSerializer(options); - - using (var jsonStream = File.Create(JsonPath)) - JsonSerializer.Serialize(jsonStream, @this, options); - - OnSerialize?.Invoke(this, EventArgs.Empty); - } - /// public async Task SerializeAsync(CancellationToken cancellationToken) { @@ -194,23 +115,6 @@ public async Task SerializeAsync(CancellationToken cancellationToken) await OnSerializeAsync.InvokeAsync(this, EventArgs.Empty, cancellationToken); } - /// - public bool TrySerialize() - { - try - { - Serialize(); - return true; - } - catch (Exception ex) when (ex is JsonException - || ex is IOException - || ex is SystemException - || ex is InvalidOperationException) - { - return false; - } - } - /// public async Task TrySerializeAsync(CancellationToken cancellationToken) { @@ -228,17 +132,6 @@ public async Task TrySerializeAsync(CancellationToken cancellationToken) } } - /// - /// Loads options from another configuration instance. Basically like - /// a copy constructor/method. - /// - /// The other configuration instance to copy options from. - public void Load(T other) - { - LoadImpl(other); - Update(); - } - /// /// Asynchronously loads options from another configuration instance. Basically like /// a copy constructor/method. @@ -252,8 +145,8 @@ public async Task LoadAsync(T other, CancellationToken cancellationToken) } /// - /// Implementation of /. - /// Should do the actual value copying. + /// Implementation of . Should do + /// the actual value copying. /// /// The other configuration instance to copy options from. protected abstract void LoadImpl(T other); diff --git a/DailyDesktop.Core/Configuration/IPublicNullableConfiguration.cs b/DailyDesktop.Core/Configuration/IPublicNullableConfiguration.cs index b404626..3b835c0 100644 --- a/DailyDesktop.Core/Configuration/IPublicNullableConfiguration.cs +++ b/DailyDesktop.Core/Configuration/IPublicNullableConfiguration.cs @@ -12,13 +12,6 @@ namespace DailyDesktop.Core.Configuration /// public interface IPublicNullableConfiguration { - /// - /// Nullifies all properties that satisfy - /// . - /// - /// The number of properties that were nullified. - int NullifyWhitespace(); - /// /// Asynchronously nullifies all properties that satisfy /// . diff --git a/DailyDesktop.Core/Configuration/IPublicPathConfiguration.cs b/DailyDesktop.Core/Configuration/IPublicPathConfiguration.cs index f30c53d..6b0eda6 100644 --- a/DailyDesktop.Core/Configuration/IPublicPathConfiguration.cs +++ b/DailyDesktop.Core/Configuration/IPublicPathConfiguration.cs @@ -12,21 +12,6 @@ namespace DailyDesktop.Core.Configuration /// public interface IPublicPathConfiguration : IReadOnlyPathConfiguration { - /// - /// The assembly directory (e.g. for the task executable). - /// - new string AssemblyDir { get; set; } - - /// - /// The providers directory (e.g. for DLL modules). - /// - new string ProvidersDir { get; set; } - - /// - /// The serialization directory (e.g. for the JSON). - /// - new string SerializationDir { get; set; } - /// /// Asynchronously sets the assembly directory (e.g. for the task executable). /// diff --git a/DailyDesktop.Core/Configuration/IPublicTaskConfiguration.cs b/DailyDesktop.Core/Configuration/IPublicTaskConfiguration.cs index 76a5afd..a46076a 100644 --- a/DailyDesktop.Core/Configuration/IPublicTaskConfiguration.cs +++ b/DailyDesktop.Core/Configuration/IPublicTaskConfiguration.cs @@ -13,39 +13,6 @@ namespace DailyDesktop.Core.Configuration /// public interface IPublicTaskConfiguration : IReadOnlyTaskConfiguration { - /// - /// The path of the DLL module. - /// - new string Dll { get; set; } - - /// - /// Whether wallpaper update triggers are - /// enabled or disabled. - /// - new bool IsEnabled { get; set; } - - /// - /// The time at which the daily wallpaper update trigger executes. Only applies if - /// is set to true. - /// - new DateTime UpdateTime { get; set; } - - /// - /// Whether or not to apply resize to wallpaper images to screen resolution, if larger. - /// - new bool DoResize { get; set; } - - /// - /// Whether or not to apply blurred-fit to wallpaper images. - /// - new bool DoBlurredFit { get; set; } - - /// - /// The blur strength for wallpaper images. Only applies if - /// is set to true. - /// - new int BlurStrength { get; set; } - /// /// Sets the path of the DLL module. /// @@ -63,7 +30,7 @@ public interface IPublicTaskConfiguration : IReadOnlyTaskConfiguration /// /// Sets the time at which the daily wallpaper update trigger executes. Only applies if - /// is set to true. + /// is true. /// /// The value to set as. /// The . @@ -85,7 +52,7 @@ public interface IPublicTaskConfiguration : IReadOnlyTaskConfiguration /// /// Sets the blur strength for wallpaper images. Only applies if - /// is set to true. + /// is set to true. /// /// The value to set as. /// The . diff --git a/DailyDesktop.Core/Configuration/IPublicWallpaperConfiguration.cs b/DailyDesktop.Core/Configuration/IPublicWallpaperConfiguration.cs index 5c24250..fa8d67e 100644 --- a/DailyDesktop.Core/Configuration/IPublicWallpaperConfiguration.cs +++ b/DailyDesktop.Core/Configuration/IPublicWallpaperConfiguration.cs @@ -11,36 +11,6 @@ namespace DailyDesktop.Core.Configuration /// public interface IPublicWallpaperConfiguration : IReadOnlyWallpaperConfiguration, IPublicNullableConfiguration { - /// - /// The URI of the image file. Cannot be null because there must be an image is necessary. - /// - new string ImageUri { get; set; } - - /// - /// The author of the work (i.e. the illustrator, photographer, painter, etc.) - /// - new string? Author { get; set; } - - /// - /// A URI to the . Usually a URL to the author's website or profile page. - /// - new string? AuthorUri { get; set; } - - /// - /// The title of the work. - /// - new string? Title { get; set; } - - /// - /// A URI to the work. Usually a URL to the image's page on the source website where it was downloaded from. - /// - new string? TitleUri { get; set; } - - /// - /// A description for the work. - /// - new string? Description { get; set; } - /// /// Asynchronously sets the URI of the image file. Cannot be null because there must be an image is necessary. /// @@ -56,7 +26,7 @@ public interface IPublicWallpaperConfiguration : IReadOnlyWallpaperConfiguration Task SetAuthorAsync(string? author, CancellationToken cancellationToken); /// - /// Asynchronously sets the URI to the . Usually a URL to the author's website or profile page. + /// Asynchronously sets the URI to the . Usually a URL to the author's website or profile page. /// /// The value to set as. /// The . diff --git a/DailyDesktop.Core/Configuration/IReadOnlyConfiguration.cs b/DailyDesktop.Core/Configuration/IReadOnlyConfiguration.cs index 8192b67..e511cc7 100644 --- a/DailyDesktop.Core/Configuration/IReadOnlyConfiguration.cs +++ b/DailyDesktop.Core/Configuration/IReadOnlyConfiguration.cs @@ -1,7 +1,6 @@ // Copyright (c) Alden Wu . Licensed under the MIT Licence. // See the LICENSE file in the repository root for full licence text. -using System; using System.Threading; using System.Threading.Tasks; using DailyDesktop.Core.Util; @@ -23,56 +22,27 @@ public interface IReadOnlyConfiguration /// bool IsAutoSerializing { get; } - /// - /// Event published on calls to . - /// - event EventHandler OnUpdate; - /// /// Asynchronous event published on calls to . /// event AsyncEventHandler OnUpdateAsync; - /// - /// Event published on successful calls to . - /// - event EventHandler OnSerialize; - /// /// Asynchronous event published on successful calls to . /// event AsyncEventHandler OnSerializeAsync; - /// - /// Automatically called upon setting properties. Can be called manually to - /// publish to and serialize (in case is true). - /// - void Update(); - /// /// Automatically called upon setting properties. Can be called manually to asynchronously /// publish to and serialize (in case is true). /// Task UpdateAsync(CancellationToken cancellationToken); - /// - /// Serialize configuration to a JSON file (located at ). - /// - void Serialize(); - /// /// Asynchronously serialize configuration to a JSON file (located at ). /// Task SerializeAsync(CancellationToken cancellationToken); - /// - /// Try to serialize configuration to a JSON file (located at ). - /// - /// - /// Whether or not the serialiazation was successful. - /// - bool TrySerialize(); - /// /// Try to asynchronously serialize configuration to a JSON file (located at ). /// diff --git a/DailyDesktop.Core/Configuration/PathConfiguration.cs b/DailyDesktop.Core/Configuration/PathConfiguration.cs index 49e0289..31dfa6d 100644 --- a/DailyDesktop.Core/Configuration/PathConfiguration.cs +++ b/DailyDesktop.Core/Configuration/PathConfiguration.cs @@ -6,7 +6,6 @@ using System.Threading; using System.Threading.Tasks; using System.Web; -using DailyDesktop.Core.Util; namespace DailyDesktop.Core.Configuration { @@ -22,61 +21,25 @@ public PathConfiguration(string jsonPath = "") } /// - public string AssemblyDir - { - get => assemblyDir; - set - { - if (assemblyDir == value) - return; - - Directory.CreateDirectory(value); - assemblyDir = value; - UpdateAsync(default).Wait(AsyncUtils.TimedCancel()); - } - } + public string AssemblyDir { get => assemblyDir; init => assemblyDir = value; } /// - public string ProvidersDir - { - get => providersDir; - set - { - if (providersDir == value) - return; - - Directory.CreateDirectory(value); - providersDir = value; - UpdateAsync(default).Wait(AsyncUtils.TimedCancel()); - } - } + public string ProvidersDir { get => providersDir; init => providersDir = value; } /// - public string SerializationDir - { - get => serializationDir; - set - { - if (serializationDir == value) - return; - - Directory.CreateDirectory(value); - serializationDir = value; - UpdateAsync(default).Wait(AsyncUtils.TimedCancel()); - } - } + public string SerializationDir { get => serializationDir; init => serializationDir = value; } /// [JsonIgnore] - public string TaskExecutable => HttpUtility.UrlDecode(Path.Combine(assemblyDir, "DailyDesktop.Task.exe")); + public string TaskExecutable => HttpUtility.UrlDecode(Path.Combine(AssemblyDir, "DailyDesktop.Task.exe")); /// [JsonIgnore] - public string TaskConfigJson => HttpUtility.UrlDecode(Path.Combine(serializationDir, "settings.json")); + public string TaskConfigJson => HttpUtility.UrlDecode(Path.Combine(SerializationDir, "settings.json")); /// [JsonIgnore] - public string WallpaperJson => HttpUtility.UrlDecode(Path.Combine(serializationDir, "wallpaper.json")); + public string WallpaperJson => HttpUtility.UrlDecode(Path.Combine(SerializationDir, "wallpaper.json")); /// public async Task SetAssemblyDirAsync(string assemblyDir, CancellationToken cancellationToken) diff --git a/DailyDesktop.Core/Configuration/TaskConfiguration.cs b/DailyDesktop.Core/Configuration/TaskConfiguration.cs index 627ca83..6389fef 100644 --- a/DailyDesktop.Core/Configuration/TaskConfiguration.cs +++ b/DailyDesktop.Core/Configuration/TaskConfiguration.cs @@ -19,88 +19,22 @@ public TaskConfiguration(string jsonPath = "") } /// - public string Dll - { - get => dll; - set - { - if (dll == value) - return; - - dll = value; - Update(); - } - } + public string Dll { get => dll; init => dll = value; } /// - public bool IsEnabled - { - get => isEnabled; - set - { - if (isEnabled == value) - return; - - isEnabled = value; - Update(); - } - } + public bool IsEnabled { get => isEnabled; init => isEnabled = value; } /// - public DateTime UpdateTime - { - get => updateTime; - set - { - if (updateTime == value) - return; - - updateTime = value; - Update(); - } - } + public DateTime UpdateTime { get => updateTime; init => updateTime = value; } /// - public bool DoResize - { - get => doResize; - set - { - if (doResize == value) - return; - - doResize = value; - Update(); - } - } + public bool DoResize { get => doResize; init => doResize = value; } /// - public bool DoBlurredFit - { - get => doBlurredFit; - set - { - if (doBlurredFit == value) - return; - - doBlurredFit = value; - Update(); - } - } + public bool DoBlurredFit { get => doBlurredFit; init => doBlurredFit = value; } /// - public int BlurStrength - { - get => blurStrength; - set - { - if (blurStrength == value) - return; - - blurStrength = value; - Update(); - } - } + public int BlurStrength { get => blurStrength; init => blurStrength = value; } /// public async Task SetDllAsync(string dll, CancellationToken cancellationToken) @@ -155,7 +89,7 @@ public async Task SetDoBlurredFitAsync(bool doBlurredFit, CancellationToken canc /// public async Task SetBlurStrengthAsync(int blurStrength, CancellationToken cancellationToken) { - if (this.blurStrength == blurStrength) + if (BlurStrength == blurStrength) return; this.blurStrength = blurStrength; diff --git a/DailyDesktop.Core/Configuration/WallpaperConfiguration.cs b/DailyDesktop.Core/Configuration/WallpaperConfiguration.cs index 263f440..870b8e6 100644 --- a/DailyDesktop.Core/Configuration/WallpaperConfiguration.cs +++ b/DailyDesktop.Core/Configuration/WallpaperConfiguration.cs @@ -19,142 +19,25 @@ public WallpaperConfiguration(string jsonPath = "") } /// - public string ImageUri - { - get => imageUri; - set - { - if (imageUri == value) - return; - - imageUri = value; - Update(); - } - } + public string ImageUri { get => imageUri; init => imageUri = value; } /// - public string? Author - { - get => author; - set - { - if (author == value) - return; - - author = value; - Update(); - } - } + public string? Author { get => author; init => author = value; } /// - public string? AuthorUri - { - get => authorUri; - set - { - if (authorUri == value) - return; - - authorUri = value; - Update(); - } - } + public string? AuthorUri { get => authorUri; init => authorUri = value; } /// - public string? Title - { - get => title; - set - { - if (title == value) - return; - - title = value; - Update(); - } - } + public string? Title { get => title; init => title = value; } /// - public string? TitleUri - { - get => titleUri; - set - { - if (titleUri == value) - return; - - titleUri = value; - Update(); - } - } - - /// - public string? Description - { - get => description; - set - { - if (description == value) - return; - - description = value; - Update(); - } - } + public string? TitleUri { get => titleUri; init => titleUri = value; } /// - public DateTime Date - { - get => date; - set - { - if (date == value) - return; - - date = value; - Update(); - } - } + public string? Description { get => description; init => description = value; } /// - public int NullifyWhitespace() - { - int count = 0; - - if (string.IsNullOrWhiteSpace(author)) - { - author = null; - count++; - } - - if (string.IsNullOrWhiteSpace(authorUri)) - { - authorUri = null; - count++; - } - - if (string.IsNullOrWhiteSpace(title)) - { - title = null; - count++; - } - - if (string.IsNullOrWhiteSpace(titleUri)) - { - titleUri = null; - count++; - } - - if (string.IsNullOrWhiteSpace(description)) - { - description = null; - count++; - } - - Update(); - - return count; - } + public DateTime Date { get => date; init => date = value; } /// public async Task SetImageUriAsync(string imageUri, CancellationToken cancellationToken) @@ -259,13 +142,13 @@ public async Task NullifyWhitespaceAsync(CancellationToken cancellationToke /// protected override void LoadImpl(WallpaperConfiguration other) { - imageUri = other.imageUri; - author = other.author; - authorUri = other.authorUri; - title = other.title; - titleUri = other.titleUri; - description = other.description; - date = other.date; + imageUri = other.ImageUri; + author = other.Author; + authorUri = other.AuthorUri; + title = other.Title; + titleUri = other.TitleUri; + description = other.Description; + date = other.Date; } private string imageUri = ""; diff --git a/DailyDesktop.Core/Providers/IProvider.cs b/DailyDesktop.Core/Providers/IProvider.cs index 8a68fba..852110e 100644 --- a/DailyDesktop.Core/Providers/IProvider.cs +++ b/DailyDesktop.Core/Providers/IProvider.cs @@ -79,7 +79,7 @@ public static async Task ConfigureWallpaperAsync(this IProvider provider, IPubli provider.ConfigureHttpRequestHeaders(HttpUtils.Client.DefaultRequestHeaders); await provider.ConfigureWallpaperAsync(HttpUtils.Client, wallpaperConfig, cancellationToken); - wallpaperConfig.NullifyWhitespace(); + await wallpaperConfig.NullifyWhitespaceAsync(cancellationToken); } } } diff --git a/DailyDesktop.Core/Providers/ProviderStore.cs b/DailyDesktop.Core/Providers/ProviderStore.cs index 0c165c0..e28ed91 100644 --- a/DailyDesktop.Core/Providers/ProviderStore.cs +++ b/DailyDesktop.Core/Providers/ProviderStore.cs @@ -32,22 +32,6 @@ public class ProviderStore /// public void Clear() => providers.Clear(); - /// - /// Adds one DLL module to . Will not - /// do anything if the DLL module has already been added - /// before. - /// - /// The path of the DLL module to add - /// The implementation . - public Type Add(string dllPath) - { - if (Providers.ContainsKey(dllPath)) - return Providers[dllPath]; - - var assembly = Assembly.Load(File.ReadAllBytes(dllPath)); - return addImpl(dllPath, assembly); - } - /// /// Asynchronously adds one DLL module to . Will not /// do anything if the DLL module has already been added @@ -62,11 +46,7 @@ public async Task AddAsync(string dllPath, CancellationToken cancellationT return Providers[dllPath]; var assembly = Assembly.Load(await File.ReadAllBytesAsync(dllPath, cancellationToken)); - return addImpl(dllPath, assembly); - } - - private Type addImpl(string dllPath, Assembly assembly) - { + foreach (var type in assembly.GetTypes()) { bool isPublic = type.IsPublic; @@ -81,29 +61,6 @@ private Type addImpl(string dllPath, Assembly assembly) throw new TypeLoadException($"No {nameof(IProvider)} implementation found in \"{dllPath}\"."); } - /// - /// Scans a directory for any DLL - /// modules and adds their paths to . - /// - /// The directory to scan - public void Scan(string directory) - { - if (!Directory.Exists(directory)) - throw new DirectoryNotFoundException($"{directory} does not exist"); - - foreach (var path in Directory.GetFiles(directory, PROVIDERS_SEARCH_PATTERN, SearchOption.AllDirectories)) - { - try - { - Add(path); - } - catch (SystemException se) - { - Console.WriteLine(se.StackTrace); - } - } - } - /// /// Asynchronously scans a directory for any DLL /// modules and adds their paths to . diff --git a/DailyDesktop.Core/Util/HttpUtils.cs b/DailyDesktop.Core/Util/HttpUtils.cs index 98ba6f9..82bd876 100644 --- a/DailyDesktop.Core/Util/HttpUtils.cs +++ b/DailyDesktop.Core/Util/HttpUtils.cs @@ -15,7 +15,9 @@ public static class HttpUtils /// /// An singleton for use everywhere. /// - public static readonly HttpClient Client = new HttpClient(); + public static HttpClient Client => client ??= new HttpClient(); + + private static HttpClient? client; /// /// Resets 's request headers, which includes adding diff --git a/DailyDesktop.Desktop/MainForm.cs b/DailyDesktop.Desktop/MainForm.cs index 8d3f0c3..826431b 100644 --- a/DailyDesktop.Desktop/MainForm.cs +++ b/DailyDesktop.Desktop/MainForm.cs @@ -46,7 +46,7 @@ public partial class MainForm : Form private TaskState previousState; - public static async Task CreateFormAsync() + public static async Task CreateFormAsync(CancellationToken cancellationToken) { string userId = System.Security.Principal.WindowsIdentity.GetCurrent().Name; string userName = userId.Split('\\').Last(); @@ -66,7 +66,7 @@ public static async Task CreateFormAsync() AssemblyDir = assemblyDir, ProvidersDir = providersDir, SerializationDir = serializationDir, - }, taskName, true, AsyncUtils.TimedCancel())); + }, taskName, true, cancellationToken)); } private MainForm(DailyDesktopCore core) diff --git a/DailyDesktop.Desktop/Program.cs b/DailyDesktop.Desktop/Program.cs index ebddc98..92efb55 100644 --- a/DailyDesktop.Desktop/Program.cs +++ b/DailyDesktop.Desktop/Program.cs @@ -4,6 +4,7 @@ using System; using System.Threading.Tasks; using System.Windows.Forms; +using DailyDesktop.Core.Util; namespace DailyDesktop.Desktop { @@ -18,7 +19,7 @@ private static async Task Main() Application.SetHighDpiMode(HighDpiMode.SystemAware); Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); - Application.Run(await MainForm.CreateFormAsync()); + Application.Run(await MainForm.CreateFormAsync(AsyncUtils.TimedCancel(3_500))); } } } diff --git a/DailyDesktop.Providers.CalvinAndHobbes/CalvinAndHobbesProvider.cs b/DailyDesktop.Providers.CalvinAndHobbes/CalvinAndHobbesProvider.cs index 866343a..109e4cd 100644 --- a/DailyDesktop.Providers.CalvinAndHobbes/CalvinAndHobbesProvider.cs +++ b/DailyDesktop.Providers.CalvinAndHobbes/CalvinAndHobbesProvider.cs @@ -23,9 +23,6 @@ public class CalvinAndHobbesProvider : IProvider public async Task ConfigureWallpaperAsync(HttpClient client, IPublicWallpaperConfiguration wallpaperConfig, CancellationToken cancellationToken) { - wallpaperConfig.Author = AUTHOR; - wallpaperConfig.Title = TITLE; - string pageHtml = await client.GetStringAsync(SourceUri, cancellationToken); string imageUri = Regex.Match(pageHtml, IMAGE_URI_PATTERN).Value;