mirror of
https://github.com/Artemis-RGB/Artemis
synced 2025-12-13 05:48:35 +00:00
Profile editor - Fixed easing options not applying
Device properties - Fixed layout changes not saving
This commit is contained in:
parent
e866afbfb0
commit
f985682e78
@ -31,11 +31,6 @@ public interface IRenderService : IArtemisService
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
bool IsPaused { get; set; }
|
bool IsPaused { get; set; }
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Gets or sets a boolean indicating whether to flush the RGB.NET LEDs during next update
|
|
||||||
/// </summary>
|
|
||||||
bool FlushLeds { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The time the last frame took to render
|
/// The time the last frame took to render
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|||||||
@ -70,21 +70,10 @@ internal class RenderService : IRenderService, IRenderer, IDisposable
|
|||||||
/// <inheritdoc />
|
/// <inheritdoc />
|
||||||
public TimeSpan FrameTime { get; private set; }
|
public TimeSpan FrameTime { get; private set; }
|
||||||
|
|
||||||
/// <inheritdoc />
|
|
||||||
public bool FlushLeds { get; set; }
|
|
||||||
|
|
||||||
/// <inheritdoc />
|
/// <inheritdoc />
|
||||||
public void Render(SKCanvas canvas, double delta)
|
public void Render(SKCanvas canvas, double delta)
|
||||||
{
|
{
|
||||||
_frameStopWatch.Restart();
|
_frameStopWatch.Restart();
|
||||||
|
|
||||||
if (FlushLeds)
|
|
||||||
{
|
|
||||||
FlushLeds = false;
|
|
||||||
Surface.Update(true);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
OnFrameRendering(new FrameRenderingEventArgs(canvas, delta, _surfaceManager.Surface));
|
OnFrameRendering(new FrameRenderingEventArgs(canvas, delta, _surfaceManager.Surface));
|
||||||
|
|||||||
@ -218,8 +218,7 @@ public class DeviceGeneralTabViewModel : ActivatableViewModelBase
|
|||||||
Device.RedScale = RedScale / 100f;
|
Device.RedScale = RedScale / 100f;
|
||||||
Device.GreenScale = GreenScale / 100f;
|
Device.GreenScale = GreenScale / 100f;
|
||||||
Device.BlueScale = BlueScale / 100f;
|
Device.BlueScale = BlueScale / 100f;
|
||||||
|
Device.RgbDevice.Update(true);
|
||||||
_renderService.FlushLeds = true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void ResetScaling()
|
public void ResetScaling()
|
||||||
@ -227,6 +226,7 @@ public class DeviceGeneralTabViewModel : ActivatableViewModelBase
|
|||||||
RedScale = _initialRedScale * 100;
|
RedScale = _initialRedScale * 100;
|
||||||
GreenScale = _initialGreenScale * 100;
|
GreenScale = _initialGreenScale * 100;
|
||||||
BlueScale = _initialBlueScale * 100;
|
BlueScale = _initialBlueScale * 100;
|
||||||
|
Device.RgbDevice.Update(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OnFrameRendering(object? sender, FrameRenderingEventArgs e)
|
private void OnFrameRendering(object? sender, FrameRenderingEventArgs e)
|
||||||
|
|||||||
@ -37,11 +37,7 @@ public class DeviceLayoutTabViewModel : ActivatableViewModelBase
|
|||||||
this.WhenActivated(d =>
|
this.WhenActivated(d =>
|
||||||
{
|
{
|
||||||
Device.PropertyChanged += DeviceOnPropertyChanged;
|
Device.PropertyChanged += DeviceOnPropertyChanged;
|
||||||
|
Disposable.Create(() => Device.PropertyChanged -= DeviceOnPropertyChanged).DisposeWith(d);
|
||||||
Disposable.Create(() =>
|
|
||||||
{
|
|
||||||
Device.PropertyChanged -= DeviceOnPropertyChanged;
|
|
||||||
}).DisposeWith(d);
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -51,7 +47,7 @@ public class DeviceLayoutTabViewModel : ActivatableViewModelBase
|
|||||||
|
|
||||||
public string? ImagePath => Device.Layout?.Image?.LocalPath;
|
public string? ImagePath => Device.Layout?.Image?.LocalPath;
|
||||||
|
|
||||||
public string CustomLayoutPath => Device.CustomLayoutPath;
|
public string? CustomLayoutPath => Device.CustomLayoutPath;
|
||||||
|
|
||||||
public bool HasCustomLayout => Device.CustomLayoutPath != null;
|
public bool HasCustomLayout => Device.CustomLayoutPath != null;
|
||||||
|
|
||||||
@ -61,6 +57,8 @@ public class DeviceLayoutTabViewModel : ActivatableViewModelBase
|
|||||||
_notificationService.CreateNotification()
|
_notificationService.CreateNotification()
|
||||||
.WithMessage("Cleared imported layout.")
|
.WithMessage("Cleared imported layout.")
|
||||||
.WithSeverity(NotificationSeverity.Informational);
|
.WithSeverity(NotificationSeverity.Informational);
|
||||||
|
|
||||||
|
_deviceService.SaveDevice(Device);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task BrowseCustomLayout()
|
public async Task BrowseCustomLayout()
|
||||||
@ -77,6 +75,8 @@ public class DeviceLayoutTabViewModel : ActivatableViewModelBase
|
|||||||
.WithTitle("Imported layout")
|
.WithTitle("Imported layout")
|
||||||
.WithMessage($"File loaded from {files[0]}")
|
.WithMessage($"File loaded from {files[0]}")
|
||||||
.WithSeverity(NotificationSeverity.Informational);
|
.WithSeverity(NotificationSeverity.Informational);
|
||||||
|
|
||||||
|
_deviceService.SaveDevice(Device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -153,6 +153,10 @@ public class DeviceLayoutTabViewModel : ActivatableViewModelBase
|
|||||||
private void DeviceOnPropertyChanged(object? sender, PropertyChangedEventArgs e)
|
private void DeviceOnPropertyChanged(object? sender, PropertyChangedEventArgs e)
|
||||||
{
|
{
|
||||||
if (e.PropertyName is nameof(Device.CustomLayoutPath) or nameof(Device.DisableDefaultLayout))
|
if (e.PropertyName is nameof(Device.CustomLayoutPath) or nameof(Device.DisableDefaultLayout))
|
||||||
|
{
|
||||||
Task.Run(() => _deviceService.ApplyDeviceLayout(Device, Device.GetBestDeviceLayout()));
|
Task.Run(() => _deviceService.ApplyDeviceLayout(Device, Device.GetBestDeviceLayout()));
|
||||||
|
this.RaisePropertyChanged(nameof(CustomLayoutPath));
|
||||||
|
this.RaisePropertyChanged(nameof(HasCustomLayout));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3,17 +3,21 @@
|
|||||||
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:keyframes="clr-namespace:Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes"
|
xmlns:keyframes="clr-namespace:Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes"
|
||||||
|
xmlns:avalonia="clr-namespace:Material.Icons.Avalonia;assembly=Material.Icons.Avalonia"
|
||||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||||
x:Class="Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes.TimelineEasingView"
|
x:Class="Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes.TimelineEasingView"
|
||||||
x:DataType="keyframes:TimelineEasingViewModel">
|
x:DataType="keyframes:TimelineEasingViewModel">
|
||||||
<StackPanel Orientation="Horizontal">
|
<Grid ColumnDefinitions="25,30,*">
|
||||||
<Polyline Stroke="{DynamicResource TextFillColorPrimaryBrush}"
|
<avalonia:MaterialIcon Grid.Column="0" Kind="Check" IsVisible="{CompiledBinding IsEasingModeSelected}" HorizontalAlignment="Left"/>
|
||||||
|
<Polyline Grid.Column="1"
|
||||||
|
Stroke="{DynamicResource TextFillColorPrimaryBrush}"
|
||||||
StrokeThickness="1"
|
StrokeThickness="1"
|
||||||
Points="{CompiledBinding EasingPoints}"
|
Points="{CompiledBinding EasingPoints}"
|
||||||
Stretch="Uniform"
|
Stretch="Uniform"
|
||||||
Width="20"
|
Width="20"
|
||||||
Height="20"
|
Height="20"
|
||||||
Margin="0 0 10 0" />
|
HorizontalAlignment="Left"/>
|
||||||
<TextBlock Text="{CompiledBinding Description}" />
|
<TextBlock Grid.Column="2" Text="{CompiledBinding Description}" HorizontalAlignment="Left"/>
|
||||||
</StackPanel>
|
</Grid>
|
||||||
|
|
||||||
</UserControl>
|
</UserControl>
|
||||||
@ -1,8 +1,10 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Reactive;
|
||||||
using Artemis.Core;
|
using Artemis.Core;
|
||||||
using Artemis.UI.Shared;
|
using Artemis.UI.Shared;
|
||||||
using Avalonia;
|
using Avalonia;
|
||||||
using Humanizer;
|
using Humanizer;
|
||||||
|
using ReactiveUI;
|
||||||
|
|
||||||
namespace Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes;
|
namespace Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes;
|
||||||
|
|
||||||
@ -10,11 +12,12 @@ public class TimelineEasingViewModel : ViewModelBase
|
|||||||
{
|
{
|
||||||
private readonly ILayerPropertyKeyframe _keyframe;
|
private readonly ILayerPropertyKeyframe _keyframe;
|
||||||
|
|
||||||
public TimelineEasingViewModel(Easings.Functions easingFunction, ILayerPropertyKeyframe keyframe)
|
public TimelineEasingViewModel(Easings.Functions easingFunction, ILayerPropertyKeyframe keyframe, ReactiveCommand<Easings.Functions, Unit> selectEasingFunction)
|
||||||
{
|
{
|
||||||
_keyframe = keyframe;
|
_keyframe = keyframe;
|
||||||
|
|
||||||
EasingFunction = easingFunction;
|
EasingFunction = easingFunction;
|
||||||
|
SelectEasingFunction = selectEasingFunction;
|
||||||
Description = easingFunction.Humanize();
|
Description = easingFunction.Humanize();
|
||||||
|
|
||||||
EasingPoints = new List<Point>();
|
EasingPoints = new List<Point>();
|
||||||
@ -27,6 +30,7 @@ public class TimelineEasingViewModel : ViewModelBase
|
|||||||
}
|
}
|
||||||
|
|
||||||
public Easings.Functions EasingFunction { get; }
|
public Easings.Functions EasingFunction { get; }
|
||||||
|
public ReactiveCommand<Easings.Functions, Unit> SelectEasingFunction { get; }
|
||||||
public List<Point> EasingPoints { get; }
|
public List<Point> EasingPoints { get; }
|
||||||
public string Description { get; }
|
public string Description { get; }
|
||||||
public bool IsEasingModeSelected => _keyframe.EasingFunction == EasingFunction;
|
public bool IsEasingModeSelected => _keyframe.EasingFunction == EasingFunction;
|
||||||
|
|||||||
@ -3,6 +3,7 @@
|
|||||||
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:avalonia="clr-namespace:Material.Icons.Avalonia;assembly=Material.Icons.Avalonia"
|
xmlns:avalonia="clr-namespace:Material.Icons.Avalonia;assembly=Material.Icons.Avalonia"
|
||||||
|
xmlns:keyframes="clr-namespace:Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes"
|
||||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||||
x:Class="Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes.TimelineKeyframeView"
|
x:Class="Artemis.UI.Screens.ProfileEditor.Properties.Timeline.Keyframes.TimelineKeyframeView"
|
||||||
ClipToBounds="False">
|
ClipToBounds="False">
|
||||||
@ -34,16 +35,9 @@
|
|||||||
<MenuFlyout Opening="FlyoutBase_OnOpening">
|
<MenuFlyout Opening="FlyoutBase_OnOpening">
|
||||||
<MenuItem Header="Easing" ItemsSource="{Binding EasingViewModels}">
|
<MenuItem Header="Easing" ItemsSource="{Binding EasingViewModels}">
|
||||||
<MenuItem.Styles>
|
<MenuItem.Styles>
|
||||||
<Style Selector="MenuItem > MenuItem">
|
<Style Selector="MenuItem > MenuItem" x:DataType="keyframes:TimelineEasingViewModel">
|
||||||
<Setter Property="Icon">
|
<Setter Property="Command" Value="{CompiledBinding SelectEasingFunction}" />
|
||||||
<Setter.Value>
|
<Setter Property="CommandParameter" Value="{CompiledBinding EasingFunction}" />
|
||||||
<Template>
|
|
||||||
<CheckBox IsHitTestVisible="False" IsChecked="{Binding IsEasingModeSelected}" />
|
|
||||||
</Template>
|
|
||||||
</Setter.Value>
|
|
||||||
</Setter>
|
|
||||||
<Setter Property="Command" Value="{Binding $parent[UserControl].DataContext.SelectEasingFunction}" />
|
|
||||||
<Setter Property="CommandParameter" Value="{Binding EasingFunction}" />
|
|
||||||
</Style>
|
</Style>
|
||||||
</MenuItem.Styles>
|
</MenuItem.Styles>
|
||||||
<MenuItem.Icon>
|
<MenuItem.Icon>
|
||||||
|
|||||||
@ -54,10 +54,12 @@ public class TimelineKeyframeViewModel<T> : ActivatableViewModelBase, ITimelineK
|
|||||||
Copy = ReactiveCommand.CreateFromTask(ExecuteCopy);
|
Copy = ReactiveCommand.CreateFromTask(ExecuteCopy);
|
||||||
Paste = ReactiveCommand.CreateFromTask(ExecutePaste);
|
Paste = ReactiveCommand.CreateFromTask(ExecutePaste);
|
||||||
Delete = ReactiveCommand.Create(ExecuteDelete);
|
Delete = ReactiveCommand.Create(ExecuteDelete);
|
||||||
|
SelectEasingFunction = ReactiveCommand.Create<Easings.Functions>(ExecuteSelectEasingFunction);
|
||||||
}
|
}
|
||||||
|
|
||||||
public LayerPropertyKeyframe<T> LayerPropertyKeyframe { get; }
|
public LayerPropertyKeyframe<T> LayerPropertyKeyframe { get; }
|
||||||
public ObservableCollection<TimelineEasingViewModel> EasingViewModels { get; }
|
public ObservableCollection<TimelineEasingViewModel> EasingViewModels { get; }
|
||||||
|
|
||||||
|
|
||||||
public double X
|
public double X
|
||||||
{
|
{
|
||||||
@ -93,7 +95,8 @@ public class TimelineKeyframeViewModel<T> : ActivatableViewModelBase, ITimelineK
|
|||||||
public ReactiveCommand<Unit, Unit> Copy { get; }
|
public ReactiveCommand<Unit, Unit> Copy { get; }
|
||||||
public ReactiveCommand<Unit, Unit> Paste { get; }
|
public ReactiveCommand<Unit, Unit> Paste { get; }
|
||||||
public ReactiveCommand<Unit, Unit> Delete { get; }
|
public ReactiveCommand<Unit, Unit> Delete { get; }
|
||||||
|
public ReactiveCommand<Easings.Functions, Unit> SelectEasingFunction { get; }
|
||||||
|
|
||||||
public bool IsSelected => _isSelected?.Value ?? false;
|
public bool IsSelected => _isSelected?.Value ?? false;
|
||||||
public TimeSpan Position => LayerPropertyKeyframe.Position;
|
public TimeSpan Position => LayerPropertyKeyframe.Position;
|
||||||
public ILayerPropertyKeyframe Keyframe => LayerPropertyKeyframe;
|
public ILayerPropertyKeyframe Keyframe => LayerPropertyKeyframe;
|
||||||
@ -255,10 +258,10 @@ public class TimelineKeyframeViewModel<T> : ActivatableViewModelBase, ITimelineK
|
|||||||
|
|
||||||
EasingViewModels.AddRange(Enum.GetValues(typeof(Easings.Functions))
|
EasingViewModels.AddRange(Enum.GetValues(typeof(Easings.Functions))
|
||||||
.Cast<Easings.Functions>()
|
.Cast<Easings.Functions>()
|
||||||
.Select(e => new TimelineEasingViewModel(e, Keyframe)));
|
.Select(e => new TimelineEasingViewModel(e, Keyframe, SelectEasingFunction)));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SelectEasingFunction(Easings.Functions easingFunction)
|
private void ExecuteSelectEasingFunction(Easings.Functions easingFunction)
|
||||||
{
|
{
|
||||||
_profileEditorService.ExecuteCommand(new ChangeKeyframeEasing(Keyframe, easingFunction));
|
_profileEditorService.ExecuteCommand(new ChangeKeyframeEasing(Keyframe, easingFunction));
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user