Add project files.

This commit is contained in:
misak
2024-02-10 14:48:59 +09:00
parent bb04c21f6e
commit 307701c6c5
30 changed files with 1096 additions and 0 deletions

17
App.xaml Normal file
View File

@@ -0,0 +1,17 @@
<Application
x:Class="DownloadManager.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
DispatcherUnhandledException="OnDispatcherUnhandledException"
Exit="OnExit"
Startup="OnStartup">
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ui:ThemesDictionary Theme="Dark" />
<ui:ControlsDictionary />
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
</Application>

97
App.xaml.cs Normal file
View File

@@ -0,0 +1,97 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.IO;
using System.Reflection;
using System.Windows.Threading;
using DownloadManager.Services;
using DownloadManager.ViewModels.Pages;
using DownloadManager.ViewModels.Windows;
using DownloadManager.Views.Pages;
using DownloadManager.Views.Windows;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Wpf.Ui;
namespace DownloadManager;
/// <summary>
/// Interaction logic for App.xaml
/// </summary>
public partial class App
{
// The.NET Generic Host provides dependency injection, configuration, logging, and other services.
// https://docs.microsoft.com/dotnet/core/extensions/generic-host
// https://docs.microsoft.com/dotnet/core/extensions/dependency-injection
// https://docs.microsoft.com/dotnet/core/extensions/configuration
// https://docs.microsoft.com/dotnet/core/extensions/logging
private static readonly IHost _host = Host
.CreateDefaultBuilder()
.ConfigureAppConfiguration(c => { c.SetBasePath(Path.GetDirectoryName(Assembly.GetEntryAssembly()!.Location)); })
.ConfigureServices((context, services) =>
{
services.AddHostedService<ApplicationHostService>();
// Page resolver service
services.AddSingleton<IPageService, PageService>();
// Theme manipulation
services.AddSingleton<IThemeService, ThemeService>();
// TaskBar manipulation
services.AddSingleton<ITaskBarService, TaskBarService>();
// Service containing navigation, same as INavigationWindow... but without window
services.AddSingleton<INavigationService, NavigationService>();
// Main window with navigation
services.AddSingleton<INavigationWindow, MainWindow>();
services.AddSingleton<MainWindowViewModel>();
services.AddSingleton<DashboardPage>();
services.AddSingleton<DashboardViewModel>();
services.AddSingleton<DataPage>();
services.AddSingleton<DataViewModel>();
services.AddSingleton<SettingsPage>();
services.AddSingleton<SettingsViewModel>();
}).Build();
/// <summary>
/// Gets registered service.
/// </summary>
/// <typeparam name="T">Type of the service to get.</typeparam>
/// <returns>Instance of the service or <see langword="null"/>.</returns>
public static T GetService<T>()
where T : class
{
return _host.Services.GetService(typeof(T)) as T;
}
/// <summary>
/// Occurs when the application is loading.
/// </summary>
private void OnStartup(object sender, StartupEventArgs e)
{
_host.Start();
}
/// <summary>
/// Occurs when the application is closing.
/// </summary>
private async void OnExit(object sender, ExitEventArgs e)
{
await _host.StopAsync();
_host.Dispose();
}
/// <summary>
/// Occurs when an exception is thrown by an application but not handled.
/// </summary>
private void OnDispatcherUnhandledException(object sender, DispatcherUnhandledExceptionEventArgs e)
{
// For more info see https://docs.microsoft.com/en-us/dotnet/api/system.windows.application.dispatcherunhandledexception?view=windowsdesktop-6.0
}
}

15
AssemblyInfo.cs Normal file
View File

@@ -0,0 +1,15 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Windows;
[assembly: ThemeInfo(
ResourceDictionaryLocation.None, //where theme specific resource dictionaries are located
//(used if a resource is not found in the page,
// or application resource dictionaries)
ResourceDictionaryLocation.SourceAssembly //where the generic resource dictionary is located
//(used if a resource is not found in the page,
// app, or any theme specific resource dictionaries)
)]

BIN
Assets/wpfui-icon-1024.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

BIN
Assets/wpfui-icon-256.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

33
DownloadManager.csproj Normal file
View File

@@ -0,0 +1,33 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>WinExe</OutputType>
<TargetFramework>net8.0-windows</TargetFramework>
<ApplicationManifest>app.manifest</ApplicationManifest>
<ApplicationIcon>wpfui-icon.ico</ApplicationIcon>
<Nullable>enable</Nullable>
<ImplicitUsings>enable</ImplicitUsings>
<UseWPF>true</UseWPF>
</PropertyGroup>
<ItemGroup>
<Content Include="wpfui-icon.ico" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="WPF-UI" Version="3.0.0" />
<PackageReference Include="Microsoft.Extensions.Hosting" Version="8.0.0" />
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.2.2 "/>
</ItemGroup>
<ItemGroup>
<None Remove="Assets\wpfui-icon-256.png" />
<None Remove="Assets\wpfui-icon-1024.png" />
</ItemGroup>
<ItemGroup>
<Resource Include="Assets\wpfui-icon-256.png" />
<Resource Include="Assets\wpfui-icon-1024.png" />
</ItemGroup>
</Project>

25
DownloadManager.sln Normal file
View File

@@ -0,0 +1,25 @@
Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17
VisualStudioVersion = 17.8.34525.116
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "DownloadManager", "DownloadManager.csproj", "{DEF43597-97A3-45F6-9169-EB295836D699}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{DEF43597-97A3-45F6-9169-EB295836D699}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{DEF43597-97A3-45F6-9169-EB295836D699}.Debug|Any CPU.Build.0 = Debug|Any CPU
{DEF43597-97A3-45F6-9169-EB295836D699}.Release|Any CPU.ActiveCfg = Release|Any CPU
{DEF43597-97A3-45F6-9169-EB295836D699}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {B3BB94A8-F4F1-4B53-8AD3-B1650991117B}
EndGlobalSection
EndGlobal

View File

@@ -0,0 +1,39 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Globalization;
using System.Windows.Data;
using Wpf.Ui.Appearance;
namespace DownloadManager.Helpers;
internal class EnumToBooleanConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
if (parameter is not String enumString)
{
throw new ArgumentException("ExceptionEnumToBooleanConverterParameterMustBeAnEnumName");
}
if (!Enum.IsDefined(typeof(ApplicationTheme), value))
{
throw new ArgumentException("ExceptionEnumToBooleanConverterValueMustBeAnEnum");
}
var enumValue = Enum.Parse(typeof(ApplicationTheme), enumString);
return enumValue.Equals(value);
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
if (parameter is not String enumString)
{
throw new ArgumentException("ExceptionEnumToBooleanConverterParameterMustBeAnEnumName");
}
return Enum.Parse(typeof(ApplicationTheme), enumString);
}
}

19
Models/AppConfig.cs Normal file
View File

@@ -0,0 +1,19 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
namespace DownloadManager.Models;
public class AppConfig
{
public string ConfigurationsFolder
{
get; set;
}
public string AppPropertiesFileName
{
get; set;
}
}

15
Models/DataColor.cs Normal file
View File

@@ -0,0 +1,15 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Windows.Media;
namespace DownloadManager.Models;
public struct DataColor
{
public Brush Color
{
get; set;
}
}

View File

@@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace DownloadManager.Models;
public class DownloadItemData
{
public required string FileName
{
get; set;
}
public required string Url
{
get; set;
}
public required long FileSize
{
get; set;
}
public required long Speed
{
get; set;
}
public required int Progress
{
get; set;
}
public required DownloadStatus Status
{
get; set;
}
}

14
Models/DownloadStatus.cs Normal file
View File

@@ -0,0 +1,14 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace DownloadManager.Models;
public enum DownloadStatus
{
Downloading,
Pausing,
Done,
Cancel
}

10
Resources/Translations.cs Normal file
View File

@@ -0,0 +1,10 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
namespace DownloadManager.Resources;
public partial class Translations
{
}

View File

@@ -0,0 +1,62 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using DownloadManager.Views.Pages;
using DownloadManager.Views.Windows;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Wpf.Ui;
namespace DownloadManager.Services;
/// <summary>
/// Managed host of the application.
/// </summary>
public class ApplicationHostService : IHostedService
{
private readonly IServiceProvider _serviceProvider;
private INavigationWindow _navigationWindow;
public ApplicationHostService(IServiceProvider serviceProvider)
{
_serviceProvider = serviceProvider;
}
/// <summary>
/// Triggered when the application host is ready to start the service.
/// </summary>
/// <param name="cancellationToken">Indicates that the start process has been aborted.</param>
public async Task StartAsync(CancellationToken cancellationToken)
{
await HandleActivationAsync();
}
/// <summary>
/// Triggered when the application host is performing a graceful shutdown.
/// </summary>
/// <param name="cancellationToken">Indicates that the shutdown process should no longer be graceful.</param>
public async Task StopAsync(CancellationToken cancellationToken)
{
await Task.CompletedTask;
}
/// <summary>
/// Creates main window during activation.
/// </summary>
private async Task HandleActivationAsync()
{
if (!Application.Current.Windows.OfType<MainWindow>().Any())
{
_navigationWindow = (
_serviceProvider.GetService(typeof(INavigationWindow)) as INavigationWindow
)!;
_navigationWindow!.ShowWindow();
_navigationWindow.Navigate(typeof(Views.Pages.DashboardPage));
}
await Task.CompletedTask;
}
}

45
Services/PageService.cs Normal file
View File

@@ -0,0 +1,45 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using Wpf.Ui;
namespace DownloadManager.Services;
/// <summary>
/// Service that provides pages for navigation.
/// </summary>
public class PageService : IPageService
{
/// <summary>
/// Service which provides the instances of pages.
/// </summary>
private readonly IServiceProvider _serviceProvider;
/// <summary>
/// Creates new instance and attaches the <see cref="IServiceProvider"/>.
/// </summary>
public PageService(IServiceProvider serviceProvider)
{
_serviceProvider = serviceProvider;
}
/// <inheritdoc />
public T? GetPage<T>()
where T : class
{
if (!typeof(FrameworkElement).IsAssignableFrom(typeof(T)))
throw new InvalidOperationException("The page should be a WPF control.");
return (T?)_serviceProvider.GetService(typeof(T));
}
/// <inheritdoc />
public FrameworkElement? GetPage(Type pageType)
{
if (!typeof(FrameworkElement).IsAssignableFrom(pageType))
throw new InvalidOperationException("The page should be a WPF control.");
return _serviceProvider.GetService(pageType) as FrameworkElement;
}
}

4
Usings.cs Normal file
View File

@@ -0,0 +1,4 @@
global using System;
global using System.Windows;
global using CommunityToolkit.Mvvm.ComponentModel;
global using CommunityToolkit.Mvvm.Input;

View File

@@ -0,0 +1,18 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
namespace DownloadManager.ViewModels.Pages;
public partial class DashboardViewModel : ObservableObject
{
[ObservableProperty]
private int _counter = 0;
[RelayCommand]
private void OnCounterIncrement()
{
Counter++;
}
}

View File

@@ -0,0 +1,52 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Windows.Media;
using DownloadManager.Models;
using Wpf.Ui.Controls;
namespace DownloadManager.ViewModels.Pages;
public partial class DataViewModel : ObservableObject, INavigationAware
{
private bool _isInitialized = false;
[ObservableProperty]
private IEnumerable<DataColor> _colors;
public void OnNavigatedTo()
{
if (!_isInitialized)
InitializeViewModel();
}
public void OnNavigatedFrom()
{
}
private void InitializeViewModel()
{
var random = new Random();
var colorCollection = new List<DataColor>();
for (int i = 0; i < 8192; i++)
colorCollection.Add(
new DataColor
{
Color = new SolidColorBrush(
Color.FromArgb(
(byte)200,
(byte)random.Next(0, 250),
(byte)random.Next(0, 250),
(byte)random.Next(0, 250)
)
)
}
);
Colors = colorCollection;
_isInitialized = true;
}
}

View File

@@ -0,0 +1,68 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using Wpf.Ui.Appearance;
using Wpf.Ui.Controls;
namespace DownloadManager.ViewModels.Pages;
public partial class SettingsViewModel : ObservableObject, INavigationAware
{
private bool _isInitialized = false;
[ObservableProperty]
private string _appVersion = String.Empty;
[ObservableProperty]
private ApplicationTheme _currentTheme = ApplicationTheme.Unknown;
public void OnNavigatedTo()
{
if (!_isInitialized)
InitializeViewModel();
}
public void OnNavigatedFrom()
{
}
private void InitializeViewModel()
{
CurrentTheme = ApplicationThemeManager.GetAppTheme();
AppVersion = $"UiDesktopApp1 - {GetAssemblyVersion()}";
_isInitialized = true;
}
private string GetAssemblyVersion()
{
return System.Reflection.Assembly.GetExecutingAssembly().GetName().Version?.ToString()
?? String.Empty;
}
[RelayCommand]
private void OnChangeTheme(string parameter)
{
switch (parameter)
{
case "theme_light":
if (CurrentTheme == ApplicationTheme.Light)
break;
ApplicationThemeManager.Apply(ApplicationTheme.Light);
CurrentTheme = ApplicationTheme.Light;
break;
default:
if (CurrentTheme == ApplicationTheme.Dark)
break;
ApplicationThemeManager.Apply(ApplicationTheme.Dark);
CurrentTheme = ApplicationTheme.Dark;
break;
}
}
}

View File

@@ -0,0 +1,48 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Collections.ObjectModel;
using Wpf.Ui.Controls;
namespace DownloadManager.ViewModels.Windows;
public partial class MainWindowViewModel : ObservableObject
{
[ObservableProperty]
private string _applicationTitle = "WPF UI - Downloader";
[ObservableProperty]
private ObservableCollection<object> _menuItems = new()
{
new NavigationViewItem()
{
Content = "Home",
Icon = new SymbolIcon { Symbol = SymbolRegular.Home24 },
TargetPageType = typeof(Views.Pages.DashboardPage)
},
new NavigationViewItem()
{
Content = "Data",
Icon = new SymbolIcon { Symbol = SymbolRegular.DataHistogram24 },
TargetPageType = typeof(Views.Pages.DataPage)
}
};
[ObservableProperty]
private ObservableCollection<object> _footerMenuItems = new()
{
new NavigationViewItem()
{
Content = "Settings",
Icon = new SymbolIcon { Symbol = SymbolRegular.Settings24 },
TargetPageType = typeof(Views.Pages.SettingsPage)
}
};
[ObservableProperty]
private ObservableCollection<MenuItem> _trayMenuItems = new()
{
new MenuItem { Header = "Home", Tag = "tray_home" }
};
}

View File

@@ -0,0 +1,105 @@
<Page
x:Class="DownloadManager.Views.Pages.DashboardPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:DownloadManager.Views.Pages"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
Title="DashboardPage"
d:DataContext="{d:DesignInstance local:DashboardPage,
IsDesignTimeCreatable=False}"
d:DesignHeight="450"
d:DesignWidth="800"
ui:Design.Background="{DynamicResource ApplicationBackgroundBrush}"
ui:Design.Foreground="{DynamicResource TextFillColorPrimaryBrush}"
Foreground="{DynamicResource TextFillColorPrimaryBrush}"
mc:Ignorable="d">
<Grid>
<ItemsControl>
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel/>
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<Border Height="60" CornerRadius="5">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="60"/>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="75"/>
</Grid.ColumnDefinitions>
<Grid Grid.Column="0">
<ui:SymbolIcon Symbol="Document24" FontSize="40"/>
</Grid>
<Grid Grid.Column="1" Margin="0,0">
<Grid.RowDefinitions>
<RowDefinition Height="*"/>
<RowDefinition Height="10"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<Grid Grid.Row="0" Margin="2, 0">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="50"/>
</Grid.ColumnDefinitions>
<Grid Grid.Column="0">
<TextBlock Text="File Name" FontWeight="SemiBold" VerticalAlignment="Center"/>
</Grid>
<Grid Grid.Column="1">
<TextBlock Text="Progress" FontSize="11" HorizontalAlignment="Right" VerticalAlignment="Center"/>
</Grid>
</Grid>
<Grid Grid.Row="1">
<ProgressBar Height="7"/>
</Grid>
<Grid Grid.Row="2" Margin="2, 0">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="75"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid Grid.Column="0">
<TextBlock Text="Speed" FontSize="10" Opacity="0.75"/>
</Grid>
<Grid Grid.Column="1">
<TextBlock Text="File Size" FontSize="10" Opacity="0.75"/>
</Grid>
</Grid>
</Grid>
<Grid Grid.Column="2" Margin="5,0,0,0">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid Grid.Column="0">
<ui:Button Height="20" Margin="2" Appearance="Transparent" BorderThickness="0" HorizontalAlignment="Stretch"/>
<ui:SymbolIcon Symbol="Pause20" FontSize="15"/>
</Grid>
<Grid Grid.Column="1">
<ui:Button Height="20" Margin="2" Appearance="Transparent" BorderThickness="0" HorizontalAlignment="Stretch"/>
<ui:SymbolIcon Symbol="Dismiss20" FontSize="15"/>
</Grid>
</Grid>
</Grid>
</Border>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</Grid>
</Page>

View File

@@ -0,0 +1,24 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using DownloadManager.ViewModels.Pages;
using Wpf.Ui.Controls;
namespace DownloadManager.Views.Pages;
public partial class DashboardPage : INavigableView<DashboardViewModel>
{
public DashboardViewModel ViewModel
{
get;
}
public DashboardPage(DashboardViewModel viewModel)
{
ViewModel = viewModel;
DataContext = this;
InitializeComponent();
}
}

43
Views/Pages/DataPage.xaml Normal file
View File

@@ -0,0 +1,43 @@
<Page
x:Class="DownloadManager.Views.Pages.DataPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:DownloadManager.Views.Pages"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:models="clr-namespace:DownloadManager.Models"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
Title="DataPage"
d:DataContext="{d:DesignInstance local:DataPage,
IsDesignTimeCreatable=False}"
d:DesignHeight="450"
d:DesignWidth="800"
ui:Design.Background="{DynamicResource ApplicationBackgroundBrush}"
ui:Design.Foreground="{DynamicResource TextFillColorPrimaryBrush}"
Foreground="{DynamicResource TextFillColorPrimaryBrush}"
ScrollViewer.CanContentScroll="False"
mc:Ignorable="d">
<Grid>
<ui:VirtualizingItemsControl
Foreground="{DynamicResource TextFillColorSecondaryBrush}"
ItemsSource="{Binding ViewModel.Colors, Mode=OneWay}"
VirtualizingPanel.CacheLengthUnit="Item">
<ItemsControl.ItemTemplate>
<DataTemplate DataType="{x:Type models:DataColor}">
<ui:Button
Width="80"
Height="80"
Margin="2"
Padding="0"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
Appearance="Secondary"
Background="{Binding Color, Mode=OneWay}"
FontSize="25"
Icon="Fluent24" />
</DataTemplate>
</ItemsControl.ItemTemplate>
</ui:VirtualizingItemsControl>
</Grid>
</Page>

View File

@@ -0,0 +1,24 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using DownloadManager.ViewModels.Pages;
using Wpf.Ui.Controls;
namespace DownloadManager.Views.Pages;
public partial class DataPage : INavigableView<DataViewModel>
{
public DataViewModel ViewModel
{
get;
}
public DataPage(DataViewModel viewModel)
{
ViewModel = viewModel;
DataContext = this;
InitializeComponent();
}
}

View File

@@ -0,0 +1,51 @@
<Page
x:Class="DownloadManager.Views.Pages.SettingsPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:helpers="clr-namespace:DownloadManager.Helpers"
xmlns:local="clr-namespace:DownloadManager.Views.Pages"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
Title="SettingsPage"
d:DataContext="{d:DesignInstance local:SettingsPage,
IsDesignTimeCreatable=False}"
d:DesignHeight="450"
d:DesignWidth="800"
ui:Design.Background="{DynamicResource ApplicationBackgroundBrush}"
ui:Design.Foreground="{DynamicResource TextFillColorPrimaryBrush}"
Foreground="{DynamicResource TextFillColorPrimaryBrush}"
mc:Ignorable="d">
<Page.Resources>
<helpers:EnumToBooleanConverter x:Key="EnumToBooleanConverter" />
</Page.Resources>
<StackPanel>
<TextBlock
FontSize="20"
FontWeight="Medium"
Text="Personalization" />
<TextBlock Margin="0,12,0,0" Text="Theme" />
<RadioButton
Margin="0,12,0,0"
Command="{Binding ViewModel.ChangeThemeCommand, Mode=OneWay}"
CommandParameter="theme_light"
Content="Light"
GroupName="themeSelect"
IsChecked="{Binding ViewModel.CurrentTheme, Converter={StaticResource EnumToBooleanConverter}, ConverterParameter=Light, Mode=OneWay}" />
<RadioButton
Margin="0,8,0,0"
Command="{Binding ViewModel.ChangeThemeCommand, Mode=OneWay}"
CommandParameter="theme_dark"
Content="Dark"
GroupName="themeSelect"
IsChecked="{Binding ViewModel.CurrentTheme, Converter={StaticResource EnumToBooleanConverter}, ConverterParameter=Dark, Mode=OneWay}" />
<TextBlock
Margin="0,24,0,0"
FontSize="20"
FontWeight="Medium"
Text="About Downloader" />
<TextBlock Margin="0,12,0,0" Text="{Binding ViewModel.AppVersion, Mode=OneWay}" />
</StackPanel>
</Page>

View File

@@ -0,0 +1,24 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using DownloadManager.ViewModels.Pages;
using Wpf.Ui.Controls;
namespace DownloadManager.Views.Pages;
public partial class SettingsPage : INavigableView<SettingsViewModel>
{
public SettingsViewModel ViewModel
{
get;
}
public SettingsPage(SettingsViewModel viewModel)
{
ViewModel = viewModel;
DataContext = this;
InitializeComponent();
}
}

View File

@@ -0,0 +1,65 @@
<ui:FluentWindow
x:Class="DownloadManager.Views.Windows.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:DownloadManager.Views.Windows"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
Title="{Binding ViewModel.ApplicationTitle, Mode=OneWay}"
Width="1100"
Height="650"
d:DataContext="{d:DesignInstance local:MainWindow,
IsDesignTimeCreatable=True}"
d:DesignHeight="450"
d:DesignWidth="800"
ui:Design.Background="{DynamicResource ApplicationBackgroundBrush}"
ui:Design.Foreground="{DynamicResource TextFillColorPrimaryBrush}"
ExtendsContentIntoTitleBar="True"
Foreground="{DynamicResource TextFillColorPrimaryBrush}"
WindowBackdropType="Mica"
WindowCornerPreference="Round"
WindowStartupLocation="CenterScreen"
mc:Ignorable="d">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<ui:NavigationView
x:Name="RootNavigation"
Grid.Row="1"
Padding="42,0,42,0"
BreadcrumbBar="{Binding ElementName=BreadcrumbBar}"
FooterMenuItemsSource="{Binding ViewModel.FooterMenuItems, Mode=OneWay}"
FrameMargin="0"
IsBackButtonVisible="Visible"
IsPaneToggleVisible="True"
MenuItemsSource="{Binding ViewModel.MenuItems, Mode=OneWay}"
PaneDisplayMode="LeftFluent">
<ui:NavigationView.Header>
<ui:BreadcrumbBar x:Name="BreadcrumbBar" Margin="42,32,42,20" />
</ui:NavigationView.Header>
<ui:NavigationView.ContentOverlay>
<Grid>
<ui:SnackbarPresenter x:Name="SnackbarPresenter" />
</Grid>
</ui:NavigationView.ContentOverlay>
</ui:NavigationView>
<ContentPresenter
x:Name="RootContentDialog"
Grid.Row="0"
Grid.RowSpan="2" />
<ui:TitleBar
x:Name="TitleBar"
Title="{Binding ViewModel.ApplicationTitle}"
Grid.Row="0"
CloseWindowByDoubleClickOnIcon="True">
<ui:TitleBar.Icon>
<ui:ImageIcon Source="pack://application:,,,/Assets/wpfui-icon-256.png" />
</ui:TitleBar.Icon>
</ui:TitleBar>
</Grid>
</ui:FluentWindow>

View File

@@ -0,0 +1,70 @@
// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using DownloadManager.ViewModels.Windows;
using Wpf.Ui;
using Wpf.Ui.Appearance;
using Wpf.Ui.Controls;
namespace DownloadManager.Views.Windows;
public partial class MainWindow : INavigationWindow
{
public MainWindowViewModel ViewModel
{
get;
}
public MainWindow(
MainWindowViewModel viewModel,
IPageService pageService,
INavigationService navigationService
)
{
ViewModel = viewModel;
DataContext = this;
SystemThemeWatcher.Watch(this);
InitializeComponent();
SetPageService(pageService);
navigationService.SetNavigationControl(RootNavigation);
}
#region INavigationWindow methods
public INavigationView GetNavigation() => RootNavigation;
public bool Navigate(Type pageType) => RootNavigation.Navigate(pageType);
public void SetPageService(IPageService pageService) => RootNavigation.SetPageService(pageService);
public void ShowWindow() => Show();
public void CloseWindow() => Close();
#endregion INavigationWindow methods
/// <summary>
/// Raises the closed event.
/// </summary>
protected override void OnClosed(EventArgs e)
{
base.OnClosed(e);
// Make sure that closing this window will begin the process of closing the application.
Application.Current.Shutdown();
}
INavigationView INavigationWindow.GetNavigation()
{
throw new NotImplementedException();
}
public void SetServiceProvider(IServiceProvider serviceProvider)
{
throw new NotImplementedException();
}
}

75
app.manifest Normal file
View File

@@ -0,0 +1,75 @@
<?xml version="1.0" encoding="utf-8"?>
<assembly manifestVersion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1">
<assemblyIdentity version="1.0.0.0" name="Downloader.app"/>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v2">
<security>
<requestedPrivileges xmlns="urn:schemas-microsoft-com:asm.v3">
<!-- UAC Manifest Options
If you want to change the Windows User Account Control level replace the
requestedExecutionLevel node with one of the following.
<requestedExecutionLevel level="asInvoker" uiAccess="false" />
<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
<requestedExecutionLevel level="highestAvailable" uiAccess="false" />
Specifying requestedExecutionLevel element will disable file and registry virtualization.
Remove this element if your application requires this virtualization for backwards
compatibility.
-->
<requestedExecutionLevel level="asInvoker" uiAccess="false" />
</requestedPrivileges>
</security>
</trustInfo>
<compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
<application>
<!-- A list of the Windows versions that this application has been tested on
and is designed to work with. Uncomment the appropriate elements
and Windows will automatically select the most compatible environment. -->
<!-- Windows Vista -->
<!--<supportedOS Id="{e2011457-1546-43c5-a5fe-008deee3d3f0}" />-->
<!-- Windows 7 -->
<!--<supportedOS Id="{35138b9a-5d96-4fbd-8e2d-a2440225f93a}" />-->
<!-- Windows 8 -->
<!--<supportedOS Id="{4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}" />-->
<!-- Windows 8.1 -->
<!--<supportedOS Id="{1f676c76-80e1-4239-95bb-83d0f6d0da78}" />-->
<!-- Windows 10 -->
<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}" />
</application>
</compatibility>
<!-- Indicates that the application is DPI-aware and will not be automatically scaled by Windows at higher
DPIs. Windows Presentation Foundation (WPF) applications are automatically DPI-aware and do not need
to opt in. Windows Forms applications targeting .NET Framework 4.6 that opt into this setting, should
also set the 'EnableWindowsFormsHighDpiAutoResizing' setting to 'true' in their app.config.
Makes the application long-path aware. See https://docs.microsoft.com/windows/win32/fileio/maximum-file-path-limitation -->
<application xmlns="urn:schemas-microsoft-com:asm.v3">
<windowsSettings>
<dpiAwareness xmlns="http://schemas.microsoft.com/SMI/2016/WindowsSettings">PerMonitor</dpiAwareness>
<dpiAware xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">true/PM</dpiAware>
<longPathAware xmlns="http://schemas.microsoft.com/SMI/2016/WindowsSettings">true</longPathAware>
</windowsSettings>
</application>
<!-- Enable themes for Windows common controls and dialogs (Windows XP and later) -->
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
processorArchitecture="*"
publicKeyToken="6595b64144ccf1df"
language="*" />
</dependentAssembly>
</dependency>
</assembly>

BIN
wpfui-icon.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 19 KiB