mirror of
https://github.com/Artemis-RGB/Artemis
synced 2025-12-13 05:48:35 +00:00
Sidebar - Added profile reordering and moving to different categories
This commit is contained in:
parent
cd97ed420c
commit
bcd03becc7
2
src/.idea/.idea.Artemis/.idea/avalonia.xml
generated
2
src/.idea/.idea.Artemis/.idea/avalonia.xml
generated
@ -55,7 +55,7 @@
|
||||
<entry key="Artemis.UI/Screens/Settings/Tabs/GeneralTabView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/ContentDialogs/SidebarCategoryEditView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/Dialogs/ProfileConfigurationEditView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/SidebarCategoryView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/SidebarCategoryView.axaml" value="Artemis.UI.Windows/Artemis.UI.Windows.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/SidebarProfileConfigurationView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/Sidebar/SidebarView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
<entry key="Artemis.UI/Screens/SurfaceEditor/ListDeviceView.axaml" value="Artemis.UI.Linux/Artemis.UI.Linux.csproj" />
|
||||
|
||||
@ -98,7 +98,10 @@ namespace Artemis.Core
|
||||
configuration.Category.RemoveProfileConfiguration(configuration);
|
||||
|
||||
if (targetIndex != null)
|
||||
_profileConfigurations.Insert(Math.Clamp(targetIndex.Value, 0, _profileConfigurations.Count), configuration);
|
||||
{
|
||||
targetIndex = Math.Clamp(targetIndex.Value, 0, _profileConfigurations.Count);
|
||||
_profileConfigurations.Insert(targetIndex.Value, configuration);
|
||||
}
|
||||
else
|
||||
_profileConfigurations.Add(configuration);
|
||||
configuration.Category = this;
|
||||
@ -116,7 +119,8 @@ namespace Artemis.Core
|
||||
|
||||
internal void RemoveProfileConfiguration(ProfileConfiguration configuration)
|
||||
{
|
||||
if (!_profileConfigurations.Remove(configuration)) return;
|
||||
if (!_profileConfigurations.Remove(configuration))
|
||||
return;
|
||||
|
||||
for (int index = 0; index < _profileConfigurations.Count; index++)
|
||||
_profileConfigurations[index].Order = index;
|
||||
|
||||
@ -90,7 +90,9 @@
|
||||
</Style>
|
||||
</UserControl.Styles>
|
||||
<Grid RowDefinitions="*,Auto">
|
||||
<TreeView Name="ProfileTreeView" Classes="no-right-margin draggable" Items="{CompiledBinding Children}" SelectedItem="{CompiledBinding SelectedChild}"
|
||||
<TreeView Name="ProfileTreeView" Classes="no-right-margin draggable"
|
||||
Items="{CompiledBinding Children}"
|
||||
SelectedItem="{CompiledBinding SelectedChild}"
|
||||
SelectionChanged="ProfileTreeView_OnSelectionChanged">
|
||||
<TreeView.Styles>
|
||||
<Style Selector="TreeViewItem">
|
||||
|
||||
@ -0,0 +1,124 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using Artemis.Core;
|
||||
using Artemis.UI.Screens.ProfileEditor.ProfileTree;
|
||||
using Avalonia;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls.Generators;
|
||||
using Avalonia.Input;
|
||||
using Avalonia.Interactivity;
|
||||
using Avalonia.VisualTree;
|
||||
using Avalonia.Xaml.Interactions.DragAndDrop;
|
||||
|
||||
namespace Artemis.UI.Screens.Sidebar.Behaviors;
|
||||
|
||||
public class SidebarCategoryViewDropHandler : DropHandlerBase
|
||||
{
|
||||
private bool Validate(ListBox listBox, DragEventArgs e, object? sourceContext, object? targetContext, bool bExecute)
|
||||
{
|
||||
if (sourceContext is not SidebarProfileConfigurationViewModel sourceItem || targetContext is not SidebarCategoryViewModel vm ||
|
||||
listBox.GetVisualAt(e.GetPosition(listBox)) is not IControl targetControl)
|
||||
return false;
|
||||
if (e.DragEffects != DragDropEffects.Move)
|
||||
return false;
|
||||
|
||||
SidebarProfileConfigurationViewModel? targetItem = targetControl.DataContext as SidebarProfileConfigurationViewModel;
|
||||
ListBoxItem? targetVisual = null;
|
||||
bool before = true;
|
||||
if (targetItem != null)
|
||||
{
|
||||
Point position = e.GetPosition(listBox);
|
||||
targetVisual = listBox.GetVisualAt(position).FindAncestorOfType<ListBoxItem>();
|
||||
if (targetVisual != null)
|
||||
{
|
||||
Point positionInTarget = e.GetPosition(targetVisual);
|
||||
if (positionInTarget.Y > (targetVisual.Bounds.Height / 2))
|
||||
before = false;
|
||||
}
|
||||
}
|
||||
|
||||
foreach (ItemContainerInfo? item in listBox.ItemContainerGenerator.Containers)
|
||||
SetDraggingPseudoClasses(item.ContainerControl, false, false);
|
||||
|
||||
if (bExecute)
|
||||
{
|
||||
if (targetItem != null)
|
||||
{
|
||||
int index = vm.ProfileConfigurations.IndexOf(targetItem);
|
||||
if (!before)
|
||||
index++;
|
||||
vm.AddProfileConfiguration(sourceItem.ProfileConfiguration, index);
|
||||
}
|
||||
else
|
||||
{
|
||||
vm.AddProfileConfiguration(sourceItem.ProfileConfiguration, null);
|
||||
}
|
||||
}
|
||||
else if (targetVisual != null)
|
||||
{
|
||||
SetDraggingPseudoClasses(targetVisual, true, before);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public override bool Validate(object? sender, DragEventArgs e, object? sourceContext, object? targetContext, object? state)
|
||||
{
|
||||
if (sender is ItemsControl itemsControl)
|
||||
{
|
||||
foreach (ItemContainerInfo? item in itemsControl.ItemContainerGenerator.Containers)
|
||||
SetDraggingPseudoClasses(item.ContainerControl, false, false);
|
||||
}
|
||||
|
||||
if (e.Source is IControl && sender is ListBox listBox)
|
||||
{
|
||||
return Validate(listBox, e, sourceContext, targetContext, false);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public override bool Execute(object? sender, DragEventArgs e, object? sourceContext, object? targetContext, object? state)
|
||||
{
|
||||
if (sender is ItemsControl itemsControl)
|
||||
{
|
||||
foreach (ItemContainerInfo? item in itemsControl.ItemContainerGenerator.Containers)
|
||||
SetDraggingPseudoClasses(item.ContainerControl, false, false);
|
||||
}
|
||||
|
||||
if (e.Source is IControl && sender is ListBox listBox)
|
||||
{
|
||||
return Validate(listBox, e, sourceContext, targetContext, true);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private void SetDraggingPseudoClasses(IControl control, bool dragging, bool before)
|
||||
{
|
||||
if (!dragging)
|
||||
{
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-before");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-after");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-into");
|
||||
}
|
||||
else
|
||||
{
|
||||
((IPseudoClasses) control.Classes).Add(":dragging");
|
||||
if (before)
|
||||
{
|
||||
((IPseudoClasses) control.Classes).Add(":dragging-before");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-after");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-into");
|
||||
}
|
||||
else
|
||||
{
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-before");
|
||||
((IPseudoClasses) control.Classes).Add(":dragging-after");
|
||||
((IPseudoClasses) control.Classes).Remove(":dragging-into");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -4,9 +4,17 @@
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:avalonia="clr-namespace:Material.Icons.Avalonia;assembly=Material.Icons.Avalonia"
|
||||
xmlns:local="clr-namespace:Artemis.UI.Screens.Sidebar"
|
||||
xmlns:i="clr-namespace:Avalonia.Xaml.Interactivity;assembly=Avalonia.Xaml.Interactivity"
|
||||
xmlns:idd="clr-namespace:Avalonia.Xaml.Interactions.DragAndDrop;assembly=Avalonia.Xaml.Interactions"
|
||||
xmlns:sb="clr-namespace:Artemis.UI.Screens.Sidebar.Behaviors"
|
||||
xmlns:converters="clr-namespace:Artemis.UI.Converters"
|
||||
xmlns:b="clr-namespace:Artemis.UI.Behaviors"
|
||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||
x:Class="Artemis.UI.Screens.Sidebar.SidebarCategoryView"
|
||||
x:DataType="local:SidebarCategoryViewModel">
|
||||
<UserControl.Resources>
|
||||
<converters:ColorOpacityConverter x:Key="ColorOpacityConverter" />
|
||||
</UserControl.Resources>
|
||||
<UserControl.Styles>
|
||||
<Style Selector=":is(Button).category-button">
|
||||
<Setter Property="IsVisible" Value="False" />
|
||||
@ -28,17 +36,66 @@
|
||||
<Setter Property="Opacity" Value="1" />
|
||||
</Style>
|
||||
<Style Selector=".sidebar-listbox > ListBoxItem">
|
||||
<Setter Property="Padding" Value="6 0"/>
|
||||
<Setter Property="Padding" Value="6 0" />
|
||||
</Style>
|
||||
|
||||
<!-- Dragging -->
|
||||
<Style Selector="ListBox.sidebar-listbox">
|
||||
<Style.Resources>
|
||||
<sb:SidebarCategoryViewDropHandler x:Key="SidebarCategoryViewDropHandler" />
|
||||
</Style.Resources>
|
||||
<Setter Property="(i:Interaction.Behaviors)">
|
||||
<i:BehaviorCollectionTemplate>
|
||||
<i:BehaviorCollection>
|
||||
<idd:ContextDropBehavior Handler="{StaticResource SidebarCategoryViewDropHandler}" />
|
||||
</i:BehaviorCollection>
|
||||
</i:BehaviorCollectionTemplate>
|
||||
</Setter>
|
||||
</Style>
|
||||
|
||||
<Style Selector="ListBox.sidebar-listbox ListBoxItem">
|
||||
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
|
||||
<Setter Property="(i:Interaction.Behaviors)">
|
||||
<i:BehaviorCollectionTemplate>
|
||||
<i:BehaviorCollection>
|
||||
<b:SimpleContextDragBehavior />
|
||||
</i:BehaviorCollection>
|
||||
</i:BehaviorCollectionTemplate>
|
||||
</Setter>
|
||||
</Style>
|
||||
|
||||
<Style Selector="ListBox.sidebar-listbox ListBoxItem:dragging-before">
|
||||
<Setter Property="Background">
|
||||
<Setter.Value>
|
||||
<LinearGradientBrush StartPoint="0,0" EndPoint="0,30">
|
||||
<GradientStop Color="{StaticResource SystemAccentColorLight3}" Offset="0.0" />
|
||||
<GradientStop Color="{StaticResource SystemAccentColorLight3}" Offset="0.05" />
|
||||
<GradientStop Color="{Binding Source={StaticResource SystemAccentColorLight3}, Converter={StaticResource ColorOpacityConverter}, ConverterParameter=0.25}" Offset="0.05" />
|
||||
<GradientStop Color="{Binding Source={StaticResource SystemAccentColorLight3}, Converter={StaticResource ColorOpacityConverter}, ConverterParameter=0}" Offset="0.25" />
|
||||
</LinearGradientBrush>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
<Style Selector="ListBox.sidebar-listbox ListBoxItem:dragging-after">
|
||||
<Setter Property="Background">
|
||||
<Setter.Value>
|
||||
<LinearGradientBrush StartPoint="0,0" EndPoint="0,32">
|
||||
<GradientStop Color="{Binding Source={StaticResource SystemAccentColorLight3}, Converter={StaticResource ColorOpacityConverter}, ConverterParameter=0}" Offset="0.75" />
|
||||
<GradientStop Color="{Binding Source={StaticResource SystemAccentColorLight3}, Converter={StaticResource ColorOpacityConverter}, ConverterParameter=0.25}" Offset="0.95" />
|
||||
<GradientStop Color="{StaticResource SystemAccentColorLight3}" Offset="0.95" />
|
||||
<GradientStop Color="{StaticResource SystemAccentColorLight3}" Offset="1" />
|
||||
</LinearGradientBrush>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
</UserControl.Styles>
|
||||
<Grid x:Name="ContainerGrid" Margin="0 8 0 0" RowDefinitions="Auto,*">
|
||||
<Grid Grid.Row="0" Background="Transparent" Margin="0 0 6 0" ColumnDefinitions="Auto,*,Auto,Auto,Auto,Auto">
|
||||
|
||||
<avalonia:MaterialIcon Classes.chevron-collapsed="{CompiledBinding !IsCollapsed}"
|
||||
Kind="ChevronUp"
|
||||
Grid.Column="0"
|
||||
Margin="5 0"
|
||||
PointerPressed="Title_OnPointerPressed"
|
||||
PointerReleased="InputElement_OnPointerReleased"
|
||||
Background="Transparent">
|
||||
<avalonia:MaterialIcon.Transitions>
|
||||
<Transitions>
|
||||
@ -56,7 +113,7 @@
|
||||
VerticalAlignment="Center"
|
||||
Text="{CompiledBinding ProfileCategory.Name, FallbackValue='Profile name'}"
|
||||
TextTrimming="CharacterEllipsis"
|
||||
PointerPressed="Title_OnPointerPressed"
|
||||
PointerReleased="InputElement_OnPointerReleased"
|
||||
Background="Transparent">
|
||||
<TextBlock.Transitions>
|
||||
<Transitions>
|
||||
@ -107,7 +164,8 @@
|
||||
</Grid>
|
||||
|
||||
<Border Grid.Row="1">
|
||||
<ListBox Classes="sidebar-listbox"
|
||||
<ListBox Name="SidebarListBox"
|
||||
Classes="sidebar-listbox"
|
||||
Items="{CompiledBinding ProfileConfigurations}"
|
||||
SelectedItem="{CompiledBinding SelectedProfileConfiguration}"
|
||||
MinHeight="10"
|
||||
|
||||
@ -1,15 +1,34 @@
|
||||
using System;
|
||||
using Avalonia;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls.Primitives;
|
||||
using Avalonia.Input;
|
||||
using Avalonia.Interactivity;
|
||||
using Avalonia.Layout;
|
||||
using Avalonia.LogicalTree;
|
||||
using Avalonia.Markup.Xaml;
|
||||
using Avalonia.Media;
|
||||
using Avalonia.Media.Imaging;
|
||||
using Avalonia.ReactiveUI;
|
||||
using Avalonia.VisualTree;
|
||||
|
||||
namespace Artemis.UI.Screens.Sidebar
|
||||
{
|
||||
public class SidebarCategoryView : ReactiveUserControl<SidebarCategoryViewModel>
|
||||
{
|
||||
private static Image? _dragAdorner;
|
||||
private Point _dragStartPosition;
|
||||
private Point _elementDragOffset;
|
||||
private ListBox _listBox;
|
||||
|
||||
public SidebarCategoryView()
|
||||
{
|
||||
InitializeComponent();
|
||||
_listBox = this.Get<ListBox>("SidebarListBox");
|
||||
|
||||
AddHandler(DragDrop.DragEnterEvent, HandleDragEnterEvent, RoutingStrategies.Direct | RoutingStrategies.Tunnel | RoutingStrategies.Bubble, true);
|
||||
AddHandler(DragDrop.DragOverEvent, HandleDragOver, RoutingStrategies.Direct | RoutingStrategies.Tunnel | RoutingStrategies.Bubble, true);
|
||||
AddHandler(PointerEnterEvent, HandlePointerEnter, RoutingStrategies.Direct | RoutingStrategies.Tunnel | RoutingStrategies.Bubble, true);
|
||||
}
|
||||
|
||||
private void InitializeComponent()
|
||||
@ -17,9 +36,104 @@ namespace Artemis.UI.Screens.Sidebar
|
||||
AvaloniaXamlLoader.Load(this);
|
||||
}
|
||||
|
||||
private void Title_OnPointerPressed(object? sender, PointerPressedEventArgs e)
|
||||
private void InputElement_OnPointerReleased(object? sender, PointerReleasedEventArgs e)
|
||||
{
|
||||
ViewModel?.ToggleCollapsed.Execute().Subscribe();
|
||||
if (e.InitialPressMouseButton == MouseButton.Left)
|
||||
ViewModel?.ToggleCollapsed.Execute().Subscribe();
|
||||
}
|
||||
|
||||
#region Dragging
|
||||
|
||||
private void HandlePointerEnter(object? sender, PointerEventArgs e)
|
||||
{
|
||||
DisposeDragAdorner();
|
||||
}
|
||||
|
||||
private void HandleDragEnterEvent(object? sender, DragEventArgs e)
|
||||
{
|
||||
CreateDragAdorner(e);
|
||||
}
|
||||
|
||||
private void CreateDragAdorner(DragEventArgs e)
|
||||
{
|
||||
if (_dragAdorner != null)
|
||||
return;
|
||||
|
||||
if (e.Source is not Control c)
|
||||
return;
|
||||
|
||||
// Get the list box item that raised the event
|
||||
ListBoxItem? container = c.FindLogicalAncestorOfType<ListBoxItem>();
|
||||
if (container == null)
|
||||
return;
|
||||
|
||||
// Take a snapshot of said tree view item and add it as an adorner
|
||||
ITransform? originalTransform = container.RenderTransform;
|
||||
try
|
||||
{
|
||||
_dragStartPosition = e.GetPosition(this.FindAncestorOfType<Window>());
|
||||
_elementDragOffset = e.GetPosition(container);
|
||||
|
||||
RenderTargetBitmap renderTarget = new(new PixelSize((int) container.Bounds.Width, (int) container.Bounds.Height));
|
||||
container.RenderTransform = new TranslateTransform(container.Bounds.X * -1, container.Bounds.Y * -1);
|
||||
renderTarget.Render(container);
|
||||
_dragAdorner = new Image
|
||||
{
|
||||
Source = renderTarget,
|
||||
VerticalAlignment = VerticalAlignment.Top,
|
||||
HorizontalAlignment = HorizontalAlignment.Left,
|
||||
Stretch = Stretch.None,
|
||||
IsHitTestVisible = false
|
||||
};
|
||||
AdornerLayer.GetAdornerLayer(this)!.Children.Add(_dragAdorner);
|
||||
}
|
||||
finally
|
||||
{
|
||||
container.RenderTransform = originalTransform;
|
||||
}
|
||||
}
|
||||
|
||||
private void HandleDragOver(object? sender, DragEventArgs e)
|
||||
{
|
||||
UpdateDragAdorner(e.GetPosition(this.FindAncestorOfType<Window>()));
|
||||
}
|
||||
|
||||
private void HandleLeaveEvent(object? sender, RoutedEventArgs e)
|
||||
{
|
||||
// If there is currently an adorner, dispose of it
|
||||
DisposeDragAdorner();
|
||||
}
|
||||
|
||||
private void HandleDrop(object? sender, DragEventArgs e)
|
||||
{
|
||||
// If there is currently an adorner, dispose of it
|
||||
DisposeDragAdorner();
|
||||
}
|
||||
|
||||
private void DisposeDragAdorner()
|
||||
{
|
||||
if (_dragAdorner == null)
|
||||
return;
|
||||
|
||||
AdornerLayer.GetAdornerLayer(this)!.Children.Remove(_dragAdorner);
|
||||
(_dragAdorner.Source as RenderTargetBitmap)?.Dispose();
|
||||
_dragAdorner = null;
|
||||
|
||||
}
|
||||
|
||||
private void UpdateDragAdorner(Point position)
|
||||
{
|
||||
if (_dragAdorner == null)
|
||||
return;
|
||||
|
||||
_dragAdorner.RenderTransform = new TranslateTransform(_dragStartPosition.X - _elementDragOffset.X, position.Y - _elementDragOffset.Y);
|
||||
}
|
||||
|
||||
private void InputElement_OnPointerMoved(object? sender, PointerEventArgs e)
|
||||
{
|
||||
DisposeDragAdorner();
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@ -14,6 +14,7 @@ using Artemis.UI.Shared.Services;
|
||||
using Artemis.UI.Shared.Services.Builders;
|
||||
using Artemis.UI.Shared.Services.ProfileEditor;
|
||||
using DynamicData;
|
||||
using DynamicData.Binding;
|
||||
using ReactiveUI;
|
||||
|
||||
namespace Artemis.UI.Screens.Sidebar
|
||||
@ -37,13 +38,13 @@ namespace Artemis.UI.Screens.Sidebar
|
||||
_vmFactory = vmFactory;
|
||||
|
||||
ProfileCategory = profileCategory;
|
||||
SourceCache<ProfileConfiguration, Guid> profileConfigurations = new(t => t.ProfileId);
|
||||
SourceList<ProfileConfiguration> profileConfigurations = new();
|
||||
|
||||
// Only show items when not collapsed
|
||||
IObservable<Func<ProfileConfiguration, bool>> profileConfigurationsFilter = this.WhenAnyValue(vm => vm.IsCollapsed).Select(b => new Func<object, bool>(_ => !b));
|
||||
profileConfigurations.Connect()
|
||||
.SortBy(c => c.Order)
|
||||
.Filter(profileConfigurationsFilter)
|
||||
.Sort(SortExpressionComparer<ProfileConfiguration>.Ascending(c => c.Order))
|
||||
.Transform(c => _vmFactory.SidebarProfileConfigurationViewModel(_sidebarViewModel, c))
|
||||
.Bind(out ReadOnlyObservableCollection<SidebarProfileConfigurationViewModel> profileConfigurationViewModels)
|
||||
.Subscribe();
|
||||
@ -58,7 +59,7 @@ namespace Artemis.UI.Screens.Sidebar
|
||||
{
|
||||
// Update the list of profiles whenever the category fires events
|
||||
Observable.FromEventPattern<ProfileConfigurationEventArgs>(x => profileCategory.ProfileConfigurationAdded += x, x => profileCategory.ProfileConfigurationAdded -= x)
|
||||
.Subscribe(e => profileConfigurations.AddOrUpdate(e.EventArgs.ProfileConfiguration))
|
||||
.Subscribe(e => profileConfigurations.Add(e.EventArgs.ProfileConfiguration))
|
||||
.DisposeWith(d);
|
||||
Observable.FromEventPattern<ProfileConfigurationEventArgs>(x => profileCategory.ProfileConfigurationRemoved += x, x => profileCategory.ProfileConfigurationRemoved -= x)
|
||||
.Subscribe(e => profileConfigurations.Remove(e.EventArgs.ProfileConfiguration))
|
||||
@ -77,7 +78,7 @@ namespace Artemis.UI.Screens.Sidebar
|
||||
profileConfigurations.Edit(updater =>
|
||||
{
|
||||
foreach (ProfileConfiguration profileConfiguration in profileCategory.ProfileConfigurations)
|
||||
updater.AddOrUpdate(profileConfiguration);
|
||||
updater.Add(profileConfiguration);
|
||||
});
|
||||
}
|
||||
|
||||
@ -135,5 +136,16 @@ namespace Artemis.UI.Screens.Sidebar
|
||||
ProfileCategory.IsSuspended = !ProfileCategory.IsSuspended;
|
||||
_profileService.SaveProfileCategory(ProfileCategory);
|
||||
}
|
||||
|
||||
public void AddProfileConfiguration(ProfileConfiguration profileConfiguration, int? index)
|
||||
{
|
||||
ProfileCategory oldCategory = profileConfiguration.Category;
|
||||
ProfileCategory.AddProfileConfiguration(profileConfiguration, index);
|
||||
|
||||
_profileService.SaveProfileCategory(ProfileCategory);
|
||||
// If the profile moved to a new category, also save the old category
|
||||
if (oldCategory != ProfileCategory)
|
||||
_profileService.SaveProfileCategory(oldCategory);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -7,6 +7,9 @@
|
||||
xmlns:svg="clr-namespace:Avalonia.Svg.Skia;assembly=Avalonia.Svg.Skia"
|
||||
mc:Ignorable="d" d:DesignWidth="240" d:DesignHeight="450"
|
||||
x:Class="Artemis.UI.Screens.Sidebar.SidebarView">
|
||||
<UserControl.Styles>
|
||||
<StyleInclude Source="avares://Avalonia.Xaml.Interactions/Draggable/Styles.axaml" />
|
||||
</UserControl.Styles>
|
||||
<Grid RowDefinitions="60,Auto,Auto,*,Auto,Auto">
|
||||
<Grid Grid.Row="0" IsHitTestVisible="False" ColumnDefinitions="Auto,*">
|
||||
<Image Grid.Column="0">
|
||||
@ -33,7 +36,7 @@
|
||||
<!-- Categories -->
|
||||
<ScrollViewer Grid.Row="3" VerticalScrollBarVisibility="Auto">
|
||||
<StackPanel>
|
||||
<ItemsControl Margin="10 2" Items="{Binding SidebarCategories}" />
|
||||
<ItemsControl Margin="10 2" Items="{Binding SidebarCategories}" Classes="profile-categories" />
|
||||
<Button Content="Add new category"
|
||||
Margin="10"
|
||||
HorizontalAlignment="Stretch"
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user