Use nullable

This commit is contained in:
Alexey Golub
2019-11-13 19:19:36 +02:00
parent 1bf9d9e2e2
commit e5a2852165
42 changed files with 195 additions and 196 deletions

View File

@@ -7,7 +7,7 @@ namespace DiscordChatExporter.Gui.ViewModels.Components
{
public Channel Model { get; set; }
public string Category { get; set; }
public string? Category { get; set; }
}
public partial class ChannelViewModel

View File

@@ -6,7 +6,6 @@ using DiscordChatExporter.Core.Services;
using DiscordChatExporter.Core.Services.Helpers;
using DiscordChatExporter.Gui.ViewModels.Components;
using DiscordChatExporter.Gui.ViewModels.Framework;
using Tyrrrz.Extensions;
namespace DiscordChatExporter.Gui.ViewModels.Dialogs
{
@@ -21,12 +20,12 @@ namespace DiscordChatExporter.Gui.ViewModels.Dialogs
public bool IsSingleChannel => Channels.Count == 1;
public string OutputPath { get; set; }
public string? OutputPath { get; set; }
public IReadOnlyList<ExportFormat> AvailableFormats =>
Enum.GetValues(typeof(ExportFormat)).Cast<ExportFormat>().ToArray();
public ExportFormat SelectedFormat { get; set; } = ExportFormat.HtmlDark;
public ExportFormat SelectedFormat { get; set; }
public DateTimeOffset? After { get; set; }
@@ -38,11 +37,6 @@ namespace DiscordChatExporter.Gui.ViewModels.Dialogs
{
_dialogManager = dialogManager;
_settingsService = settingsService;
}
protected override void OnViewLoaded()
{
base.OnViewLoaded();
// Persist preferences
SelectedFormat = _settingsService.LastExportFormat;
@@ -85,7 +79,7 @@ namespace DiscordChatExporter.Gui.ViewModels.Dialogs
}
// If canceled - return
if (OutputPath.IsNullOrWhiteSpace())
if (string.IsNullOrWhiteSpace(OutputPath))
return;
// Close dialog

View File

@@ -1,4 +1,5 @@
using System.IO;
using System;
using System.IO;
using System.Threading.Tasks;
using MaterialDesignThemes.Wpf;
using Microsoft.Win32;
@@ -22,10 +23,10 @@ namespace DiscordChatExporter.Gui.ViewModels.Framework
var view = _viewManager.CreateAndBindViewForModelIfNecessary(dialogScreen);
// Set up event routing that will close the view when called from viewmodel
void OnDialogOpened(object sender, DialogOpenedEventArgs openArgs)
void OnDialogOpened(object? sender, DialogOpenedEventArgs openArgs)
{
// Delegate to close the dialog and unregister event handler
void OnScreenClosed(object o, CloseEventArgs closeArgs)
void OnScreenClosed(object? o, EventArgs closeArgs)
{
openArgs.Session.Close();
dialogScreen.Closed -= OnScreenClosed;
@@ -41,7 +42,7 @@ namespace DiscordChatExporter.Gui.ViewModels.Framework
return dialogScreen.DialogResult;
}
public string PromptSaveFilePath(string filter = "All files|*.*", string defaultFilePath = "")
public string? PromptSaveFilePath(string filter = "All files|*.*", string defaultFilePath = "")
{
// Create dialog
var dialog = new SaveFileDialog
@@ -56,7 +57,7 @@ namespace DiscordChatExporter.Gui.ViewModels.Framework
return dialog.ShowDialog() == true ? dialog.FileName : null;
}
public string PromptDirectoryPath(string defaultDirPath = "")
public string? PromptDirectoryPath(string defaultDirPath = "")
{
// Create dialog
var dialog = new VistaFolderBrowserDialog

View File

@@ -1,22 +1,18 @@
using Stylet;
using System;
using Stylet;
namespace DiscordChatExporter.Gui.ViewModels.Framework
{
public abstract class DialogScreen<T> : Screen
public abstract class DialogScreen<T> : PropertyChangedBase
{
public T DialogResult { get; private set; }
public event EventHandler? Closed;
public void Close(T dialogResult = default)
{
// Set the result
DialogResult = dialogResult;
// If there is a parent - ask them to close this dialog
if (Parent != null)
RequestClose(Equals(dialogResult, default(T)));
// Otherwise close ourselves
else
((IScreenState) this).Close();
Closed?.Invoke(this, EventArgs.Empty);
}
}

View File

@@ -7,8 +7,7 @@ namespace DiscordChatExporter.Gui.ViewModels.Framework
{
public static class Extensions
{
public static ChannelViewModel CreateChannelViewModel(this IViewModelFactory factory, Channel model,
string category = null)
public static ChannelViewModel CreateChannelViewModel(this IViewModelFactory factory, Channel model, string? category = null)
{
var viewModel = factory.CreateChannelViewModel();
viewModel.Model = model;

View File

@@ -3,7 +3,6 @@ using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Reflection;
using System.Threading.Tasks;
using DiscordChatExporter.Core.Models;
using DiscordChatExporter.Core.Services;
@@ -38,13 +37,13 @@ namespace DiscordChatExporter.Gui.ViewModels
public bool IsBotToken { get; set; }
public string TokenValue { get; set; }
public string? TokenValue { get; set; }
public IReadOnlyList<GuildViewModel> AvailableGuilds { get; private set; }
public IReadOnlyList<GuildViewModel>? AvailableGuilds { get; private set; }
public GuildViewModel SelectedGuild { get; set; }
public GuildViewModel? SelectedGuild { get; set; }
public IReadOnlyList<ChannelViewModel> SelectedChannels { get; set; }
public IReadOnlyList<ChannelViewModel>? SelectedChannels { get; set; }
public RootViewModel(IViewModelFactory viewModelFactory, DialogManager dialogManager,
SettingsService settingsService, UpdateService updateService, DataService dataService,
@@ -58,8 +57,7 @@ namespace DiscordChatExporter.Gui.ViewModels
_exportService = exportService;
// Set title
var version = Assembly.GetExecutingAssembly().GetName().Version.ToString(3);
DisplayName = $"DiscordChatExporter v{version}";
DisplayName = $"{App.Name} v{App.VersionString}";
// Update busy state when progress manager changes
ProgressManager.Bind(o => o.IsActive, (sender, args) => IsBusy = ProgressManager.IsActive);
@@ -83,7 +81,7 @@ namespace DiscordChatExporter.Gui.ViewModels
return;
// Notify user of an update and prepare it
Notifications.Enqueue($"Downloading update to DiscordChatExporter v{updateVersion}...");
Notifications.Enqueue($"Downloading update to {App.Name} v{updateVersion}...");
await _updateService.PrepareUpdateAsync(updateVersion);
// Prompt user to install update (otherwise install it when application exits)
@@ -140,7 +138,7 @@ namespace DiscordChatExporter.Gui.ViewModels
await _dialogManager.ShowDialogAsync(dialog);
}
public bool CanPopulateGuildsAndChannels => !IsBusy && !TokenValue.IsNullOrWhiteSpace();
public bool CanPopulateGuildsAndChannels => !IsBusy && !string.IsNullOrWhiteSpace(TokenValue);
public async void PopulateGuildsAndChannels()
{
@@ -150,7 +148,7 @@ namespace DiscordChatExporter.Gui.ViewModels
try
{
// Sanitize token
TokenValue = TokenValue.Trim('"');
TokenValue = TokenValue!.Trim('"');
// Create token
var token = new AuthToken(
@@ -253,15 +251,15 @@ namespace DiscordChatExporter.Gui.ViewModels
}
}
public bool CanExportChannels => !IsBusy && !SelectedChannels.IsNullOrEmpty();
public bool CanExportChannels => !IsBusy && SelectedGuild != null && SelectedChannels != null && SelectedChannels.Any();
public async void ExportChannels()
{
// Get last used token
var token = _settingsService.LastToken;
var token = _settingsService.LastToken!;
// Create dialog
var dialog = _viewModelFactory.CreateExportSetupViewModel(SelectedGuild, SelectedChannels);
var dialog = _viewModelFactory.CreateExportSetupViewModel(SelectedGuild!, SelectedChannels!);
// Show dialog, if canceled - return
if (await _dialogManager.ShowDialogAsync(dialog) != true)
@@ -281,7 +279,7 @@ namespace DiscordChatExporter.Gui.ViewModels
try
{
// Generate file path if necessary
var filePath = dialog.OutputPath;
var filePath = dialog.OutputPath!;
if (ExportHelper.IsDirectoryPath(filePath))
{
// Generate default file name