- add: menu

This commit is contained in:
2024-12-21 15:15:04 +03:00
parent 42fde38db6
commit d9161f837b
15 changed files with 174 additions and 62 deletions

View File

@@ -10,6 +10,9 @@
<entry key="Nebula.Launcher/Views/MainView.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/MainView.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/MainWindow.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/MainWindow.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/Pages/AccountInfoPage.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/Pages/AccountInfoPage.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/Pages/AccountInfoView.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/Pages/ServerListPage.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/Pages/ServerListView.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/ServerContainer.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/ServerContainer.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/ServerList.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/ServerList.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />
<entry key="Nebula.Launcher/Views/Tabs/AccountInfoTab.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" /> <entry key="Nebula.Launcher/Views/Tabs/AccountInfoTab.axaml" value="Nebula.Launcher/Nebula.Launcher.csproj" />

View File

@@ -56,5 +56,12 @@
<Setter Property="BorderThickness" Value="0,0,0,1" /> <Setter Property="BorderThickness" Value="0,0,0,1" />
<Setter Property="BorderBrush" Value="#f7f7ff" /> <Setter Property="BorderBrush" Value="#f7f7ff" />
</Style> </Style>
<Style Selector="ListBoxItem">
<Setter Property="CornerRadius" Value="0,8,8,0" />
<Setter Property="Margin" Value="0,0,0,5" />
<Setter Property="Padding" Value="8" />
<Setter Property="Background" Value="#00000000" />
</Style>
</Application.Styles> </Application.Styles>
</Application> </Application>

View File

@@ -39,7 +39,8 @@ public static class ServiceCollectionExtensions
{ {
services.AddTransient<MainWindow>(); services.AddTransient<MainWindow>();
services.AddView<MainView, MainViewModel>(); services.AddView<MainView, MainViewModel>();
services.AddView<AccountInfoPage, AccountInfoViewModel>(); services.AddView<AccountInfoView, AccountInfoViewModel>();
services.AddView<ServerListView, ServerListViewModel>();
} }
private static void AddView<TView, TViewModel>(this IServiceCollection services) private static void AddView<TView, TViewModel>(this IServiceCollection services)

View File

@@ -0,0 +1,13 @@
using System;
namespace Nebula.Launcher.ViewHelper;
public class ViewRegisterAttribute : Attribute
{
public Type Type { get; }
public ViewRegisterAttribute(Type type)
{
Type = type;
}
}

View File

@@ -1,6 +1,8 @@
using System; using System;
using System.Reflection;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Controls.Templates; using Avalonia.Controls.Templates;
using Nebula.Launcher.ViewHelper;
using Nebula.Launcher.ViewModels; using Nebula.Launcher.ViewModels;
namespace Nebula.Launcher; namespace Nebula.Launcher;
@@ -12,15 +14,14 @@ public class ViewLocator : IDataTemplate
if (param is null) if (param is null)
return null; return null;
var name = param.GetType().FullName!.Replace("ViewModel", "View", StringComparison.Ordinal); var type = param.GetType().GetCustomAttribute<ViewRegisterAttribute>()?.Type;
var type = Type.GetType(name);
if (type != null) if (type != null)
{ {
return (Control)Activator.CreateInstance(type)!; return (Control)Activator.CreateInstance(type)!;
} }
return new TextBlock { Text = "Not Found: " + name }; return new TextBlock { Text = "Not Found: " + param.GetType()};
} }
public bool Match(object? data) public bool Match(object? data)

View File

@@ -1,8 +1,13 @@
using System;
using Nebula.Launcher.ViewHelper;
using Nebula.Launcher.Views.Pages; using Nebula.Launcher.Views.Pages;
namespace Nebula.Launcher.ViewModels; namespace Nebula.Launcher.ViewModels;
public class AccountInfoViewModel : ViewModelBase, ITab [ViewRegister(typeof(AccountInfoView))]
public class AccountInfoViewModel : ViewModelBase
{ {
public AccountInfoViewModel(IServiceProvider serviceProvider) : base(serviceProvider)
{
}
} }

View File

@@ -8,16 +8,27 @@ using CommunityToolkit.Mvvm.DependencyInjection;
using CommunityToolkit.Mvvm.Input; using CommunityToolkit.Mvvm.Input;
using CommunityToolkit.Mvvm.Messaging; using CommunityToolkit.Mvvm.Messaging;
using Nebula.Launcher.Models; using Nebula.Launcher.Models;
using Nebula.Launcher.ViewHelper;
using Nebula.Launcher.Views;
using Nebula.Launcher.Views.Pages;
namespace Nebula.Launcher.ViewModels; namespace Nebula.Launcher.ViewModels;
[ViewRegister(typeof(MainView))]
public partial class MainViewModel : ViewModelBase public partial class MainViewModel : ViewModelBase
{ {
public MainViewModel(AccountInfoViewModel accountInfoViewModel, IServiceProvider serviceProvider) public MainViewModel()
{
TryGetViewModel(typeof(AccountInfoViewModel), out var model);
_currentPage = model!;
Items = new ObservableCollection<ListItemTemplate>(_templates);
SelectedListItem = Items.First(vm => vm.ModelType == typeof(AccountInfoViewModel));
}
public MainViewModel(AccountInfoViewModel accountInfoViewModel, IServiceProvider serviceProvider): base(serviceProvider)
{ {
_currentPage = accountInfoViewModel; _currentPage = accountInfoViewModel;
_serviceProvider = serviceProvider;
Items = new ObservableCollection<ListItemTemplate>(_templates); Items = new ObservableCollection<ListItemTemplate>(_templates);
SelectedListItem = Items.First(vm => vm.ModelType == typeof(AccountInfoViewModel)); SelectedListItem = Items.First(vm => vm.ModelType == typeof(AccountInfoViewModel));
@@ -26,6 +37,7 @@ public partial class MainViewModel : ViewModelBase
private readonly List<ListItemTemplate> _templates = private readonly List<ListItemTemplate> _templates =
[ [
new ListItemTemplate(typeof(AccountInfoViewModel), "HomeRegular", "Account"), new ListItemTemplate(typeof(AccountInfoViewModel), "HomeRegular", "Account"),
new ListItemTemplate(typeof(ServerListViewModel), "List", "Servers")
]; ];
[ObservableProperty] [ObservableProperty]
@@ -34,20 +46,19 @@ public partial class MainViewModel : ViewModelBase
[ObservableProperty] [ObservableProperty]
private ViewModelBase _currentPage; private ViewModelBase _currentPage;
private readonly IServiceProvider _serviceProvider;
[ObservableProperty] [ObservableProperty]
private ListItemTemplate? _selectedListItem; private ListItemTemplate? _selectedListItem;
partial void OnSelectedListItemChanged(ListItemTemplate? value) partial void OnSelectedListItemChanged(ListItemTemplate? value)
{ {
Console.WriteLine("FUCKED " + value?.ModelType);
if (value is null) return; if (value is null) return;
var vm = Design.IsDesignMode if(!TryGetViewModel(value.ModelType, out var vmb))
? Activator.CreateInstance(value.ModelType) {
: _serviceProvider.GetService(value.ModelType); Console.WriteLine("FUCKCCC");
return;
if (vm is not ViewModelBase vmb) return; }
CurrentPage = vmb; CurrentPage = vmb;
} }

View File

@@ -0,0 +1,13 @@
using System;
using Nebula.Launcher.ViewHelper;
using Nebula.Launcher.Views.Pages;
namespace Nebula.Launcher.ViewModels;
[ViewRegister(typeof(ServerListView))]
public class ServerListViewModel : ViewModelBase
{
public ServerListViewModel(IServiceProvider serviceProvider) : base(serviceProvider)
{
}
}

View File

@@ -1,8 +1,40 @@
using Avalonia.Controls; using System;
using System.Diagnostics.CodeAnalysis;
using Avalonia.Controls;
using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.ComponentModel;
namespace Nebula.Launcher.ViewModels; namespace Nebula.Launcher.ViewModels;
public abstract class ViewModelBase : ObservableObject public abstract class ViewModelBase : ObservableObject
{ {
private readonly IServiceProvider _serviceProvider;
public ViewModelBase()
{
AssertDesignMode();
_serviceProvider = default!;
}
public ViewModelBase(IServiceProvider serviceProvider)
{
_serviceProvider = serviceProvider;
}
public bool TryGetViewModel(Type type,[NotNullWhen(true)] out ViewModelBase? viewModelBase)
{
viewModelBase = null;
var vm = Design.IsDesignMode
? Activator.CreateInstance(type)
: _serviceProvider.GetService(type);
Console.WriteLine(vm?.ToString());
if (vm is not ViewModelBase vmb) return false;
viewModelBase = vmb;
return true;
}
public void AssertDesignMode()
{
if (!Design.IsDesignMode) throw new Exception();
}
} }

View File

@@ -11,12 +11,23 @@
xmlns:models="clr-namespace:Nebula.Launcher.Models" xmlns:models="clr-namespace:Nebula.Launcher.Models"
xmlns:viewModels="clr-namespace:Nebula.Launcher.ViewModels" xmlns:viewModels="clr-namespace:Nebula.Launcher.ViewModels"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Design.DataContext>
<viewModels:MainViewModel />
</Design.DataContext>
<Grid <Grid
ColumnDefinitions="*" ColumnDefinitions="65,*"
Margin="0" Margin="0"
RowDefinitions="*,40"> RowDefinitions="*,40">
<TransitioningContentControl
Grid.Column="1"
Grid.Row="0"
Content="{Binding CurrentPage}" />
<SplitView <SplitView
Grid.Row="0" Grid.Column="0"
Grid.ColumnSpan="2"
CompactPaneLength="65" CompactPaneLength="65"
DisplayMode="CompactInline" DisplayMode="CompactInline"
IsPaneOpen="{Binding IsPaneOpen}" IsPaneOpen="{Binding IsPaneOpen}"
@@ -29,33 +40,35 @@
Grid.Row="0" Grid.Row="0"
Margin="0,0,5,0" Margin="0,0,5,0"
Padding="0"> Padding="0">
<Grid ColumnDefinitions="*" RowDefinitions="*,40">
<ListBox <ListBox
ItemsSource="{Binding Items}" ItemsSource="{Binding Items}"
Margin="2,0,-100,0"
Padding="0" Padding="0"
Background="#00000000"
SelectedItem="{Binding SelectedListItem}"> SelectedItem="{Binding SelectedListItem}">
<ListBox.Styles>
<Style Selector="ListBoxItem">
<Setter Property="Padding" Value="12 8" />
</Style>
</ListBox.Styles>
<ListBox.ItemTemplate> <ListBox.ItemTemplate>
<DataTemplate DataType="{x:Type models:ListItemTemplate}"> <DataTemplate DataType="{x:Type models:ListItemTemplate}">
<StackPanel Orientation="Horizontal" Spacing="17"> <StackPanel Orientation="Horizontal" Spacing="17">
<PathIcon Data="{Binding IconKey, Converter={x:Static converters:TypeConverters.IconConverter}}" Width="14" /> <PathIcon Data="{Binding IconKey,
<TextBlock Text="{Binding Label}"> Converter={x:Static converters:TypeConverters.IconConverter}}" Height="40" Width="40"/>
<TextBlock.IsVisible /> <TextBlock Text="{Binding Label}" VerticalAlignment="Center"/>
</TextBlock>
</StackPanel> </StackPanel>
</DataTemplate> </DataTemplate>
</ListBox.ItemTemplate> </ListBox.ItemTemplate>
</ListBox> </ListBox>
<Button Grid.Row="1" HorizontalAlignment="Left" VerticalAlignment="Stretch" Classes="ViewSelectButton"
Padding="15,0,15,0"
Command="{Binding TriggerPaneCommand}">
<Label VerticalAlignment="Center" HorizontalAlignment="Center">|||</Label>
</Button>
</Grid>
</Border> </Border>
</SplitView.Pane> </SplitView.Pane>
</SplitView> </SplitView>
<Border <Border
Grid.Column="0"
Grid.ColumnSpan="2"
BorderThickness="0,2,0,0" BorderThickness="0,2,0,0"
CornerRadius="0,0,0,0" CornerRadius="0,0,0,0"
Grid.Row="1" Grid.Row="1"

View File

@@ -2,12 +2,14 @@
d:DesignHeight="450" d:DesignHeight="450"
d:DesignWidth="800" d:DesignWidth="800"
mc:Ignorable="d" mc:Ignorable="d"
x:Class="Nebula.Launcher.Views.Pages.AccountInfoPage" x:Class="Nebula.Launcher.Views.Pages.AccountInfoView"
x:DataType="viewModels:AccountInfoViewModel"
xmlns="https://github.com/avaloniaui" xmlns="https://github.com/avaloniaui"
xmlns:controls="clr-namespace:Nebula.Launcher.Views.Controls" xmlns:controls="clr-namespace:Nebula.Launcher.Views.Controls"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:viewModels="clr-namespace:Nebula.Launcher.ViewModels">
<Grid ColumnDefinitions="*,1.5*" RowDefinitions="*"> <Grid ColumnDefinitions="*,1.5*" RowDefinitions="*">
<StackPanel Grid.Column="0" Grid.Row="0"> <StackPanel Grid.Column="0" Grid.Row="0">
<Border <Border

View File

@@ -4,14 +4,14 @@ using Nebula.Launcher.ViewModels;
namespace Nebula.Launcher.Views.Pages; namespace Nebula.Launcher.Views.Pages;
public interface ITab; public interface ITab;
public partial class AccountInfoPage : UserControl public partial class AccountInfoView : UserControl
{ {
public AccountInfoPage() public AccountInfoView()
{ {
InitializeComponent(); InitializeComponent();
} }
public AccountInfoPage(AccountInfoViewModel viewModel) public AccountInfoView(ViewModels.AccountInfoViewModel viewModel)
: this() : this()
{ {
DataContext = viewModel; DataContext = viewModel;

View File

@@ -1,11 +0,0 @@
using Avalonia.Controls;
namespace Nebula.Launcher.Views.Pages;
public partial class ServerListPage : UserControl
{
public ServerListPage()
{
InitializeComponent();
}
}

View File

@@ -2,12 +2,14 @@
d:DesignHeight="450" d:DesignHeight="450"
d:DesignWidth="800" d:DesignWidth="800"
mc:Ignorable="d" mc:Ignorable="d"
x:Class="Nebula.Launcher.Views.Pages.ServerListPage" x:Class="Nebula.Launcher.Views.Pages.ServerListView"
x:DataType="pages:ServerListView"
xmlns="https://github.com/avaloniaui" xmlns="https://github.com/avaloniaui"
xmlns:controls="clr-namespace:Nebula.Launcher.Views.Controls" xmlns:controls="clr-namespace:Nebula.Launcher.Views.Controls"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:pages="clr-namespace:Nebula.Launcher.Views.Pages">
<Grid ColumnDefinitions="*" RowDefinitions="*,40"> <Grid ColumnDefinitions="*" RowDefinitions="*,40">
<ScrollViewer Margin="0,0,0,10" Padding="0,0,8,0"> <ScrollViewer Margin="0,0,0,10" Padding="0,0,8,0">
<StackPanel> <StackPanel>

View File

@@ -0,0 +1,20 @@
using Avalonia.Controls;
using Nebula.Launcher.ViewModels;
namespace Nebula.Launcher.Views.Pages;
public partial class ServerListView : UserControl
{
// This constructor is used when the view is created by the XAML Previewer
public ServerListView()
{
InitializeComponent();
}
// This constructor is used when the view is created via dependency injection
public ServerListView(ServerListViewModel viewModel)
: this()
{
DataContext = viewModel;
}
}