mirror of
https://github.com/Artemis-RGB/Artemis
synced 2026-11-11 11:26:27 +00:00
Sidebar - Added category reordering
Sidebar - Fix disabled profiles not fading Sidebar - Fix module missing when editing existing profile configs Profile - Remove old undo/redo code
This commit is contained in:
1 parent
5873df250d
commit
b6e0c0fb66
8 files changed
+71
-216
No files matched your search
@@ -29,8 +29,6 @@ namespace Artemis.Core
|
||||
ProfileEntity = profileEntity;
|
||||
EntityId = profileEntity.Id;
|
||||
|
||||
UndoStack = new MaxStack<string>(20);
|
||||
RedoStack = new MaxStack<string>(20);
|
||||
Exceptions = new List<Exception>();
|
||||
Scripts = new ReadOnlyObservableCollection<ProfileScript>(_scripts);
|
||||
ScriptConfigurations = new ReadOnlyObservableCollection<ScriptConfiguration>(_scriptConfigurations);
|
||||
@@ -81,8 +79,6 @@ namespace Artemis.Core
|
||||
/// </summary>
|
||||
public ProfileEntity ProfileEntity { get; internal set; }
|
||||
|
||||
internal MaxStack<string> UndoStack { get; set; }
|
||||
internal MaxStack<string> RedoStack { get; set; }
|
||||
internal List<Exception> Exceptions { get; }
|
||||
|
||||
/// <inheritdoc />
|
||||
|
||||
@@ -10,11 +10,6 @@ namespace Artemis.Core.Services
|
||||
/// </summary>
|
||||
public interface IProfileService : IArtemisService
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the JSON serializer settings used to create profile mementos
|
||||
/// </summary>
|
||||
public static JsonSerializerSettings MementoSettings { get; } = new() {TypeNameHandling = TypeNameHandling.All};
|
||||
|
||||
/// <summary>
|
||||
/// Gets the JSON serializer settings used to import/export profiles
|
||||
/// </summary>
|
||||
@@ -101,26 +96,14 @@ namespace Artemis.Core.Services
|
||||
/// Saves the current icon of this profile
|
||||
/// </summary>
|
||||
void SaveProfileConfigurationIcon(ProfileConfiguration profileConfiguration);
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Writes the profile to persistent storage
|
||||
/// </summary>
|
||||
/// <param name="profile"></param>
|
||||
/// <param name="includeChildren"></param>
|
||||
void SaveProfile(Profile profile, bool includeChildren);
|
||||
|
||||
/// <summary>
|
||||
/// Attempts to restore the profile to the state it had before the last <see cref="SaveProfile" /> call.
|
||||
/// </summary>
|
||||
/// <param name="profile"></param>
|
||||
bool UndoSaveProfile(Profile profile);
|
||||
|
||||
/// <summary>
|
||||
/// Attempts to restore the profile to the state it had before the last <see cref="UndoSaveProfile" /> call.
|
||||
/// </summary>
|
||||
/// <param name="profile"></param>
|
||||
bool RedoSaveProfile(Profile profile);
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Exports the profile described in the given <see cref="ProfileConfiguration" /> into an export model
|
||||
/// </summary>
|
||||
|
||||
@@ -442,88 +442,24 @@ namespace Artemis.Core.Services
|
||||
_profileCategories.Sort((a, b) => a.Order - b.Order);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public void SaveProfile(Profile profile, bool includeChildren)
|
||||
{
|
||||
string memento = JsonConvert.SerializeObject(profile.ProfileEntity, IProfileService.MementoSettings);
|
||||
_logger.Debug("Updating profile - Saving {Profile}", profile);
|
||||
profile.Save();
|
||||
if (includeChildren)
|
||||
{
|
||||
foreach (RenderProfileElement child in profile.GetAllRenderElements())
|
||||
child.Save();
|
||||
}
|
||||
|
||||
// If there are no changes, don't bother saving
|
||||
string updatedMemento = JsonConvert.SerializeObject(profile.ProfileEntity, IProfileService.MementoSettings);
|
||||
if (memento.Equals(updatedMemento))
|
||||
{
|
||||
_logger.Debug("Updating profile - Skipping save, no changes");
|
||||
return;
|
||||
}
|
||||
|
||||
_logger.Debug("Updating profile - Saving " + profile);
|
||||
profile.RedoStack.Clear();
|
||||
profile.UndoStack.Push(memento);
|
||||
|
||||
|
||||
// At this point the user made actual changes, save that
|
||||
profile.IsFreshImport = false;
|
||||
profile.ProfileEntity.IsFreshImport = false;
|
||||
|
||||
_profileRepository.Save(profile.ProfileEntity);
|
||||
}
|
||||
|
||||
public bool UndoSaveProfile(Profile profile)
|
||||
{
|
||||
// Keep the profile from being rendered by locking it
|
||||
lock (profile)
|
||||
{
|
||||
if (profile.UndoStack.Count == 0)
|
||||
{
|
||||
_logger.Debug("Undo profile update - Failed, undo stack empty");
|
||||
return false;
|
||||
}
|
||||
|
||||
string top = profile.UndoStack.Pop();
|
||||
string memento = JsonConvert.SerializeObject(profile.ProfileEntity, IProfileService.MementoSettings);
|
||||
profile.RedoStack.Push(memento);
|
||||
profile.ProfileEntity =
|
||||
JsonConvert.DeserializeObject<ProfileEntity>(top, IProfileService.MementoSettings)
|
||||
?? throw new InvalidOperationException("Failed to deserialize memento");
|
||||
|
||||
profile.Load();
|
||||
profile.PopulateLeds(_rgbService.EnabledDevices);
|
||||
}
|
||||
|
||||
_logger.Debug("Undo profile update - Success");
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool RedoSaveProfile(Profile profile)
|
||||
{
|
||||
// Keep the profile from being rendered by locking it
|
||||
lock (profile)
|
||||
{
|
||||
if (profile.RedoStack.Count == 0)
|
||||
{
|
||||
_logger.Debug("Redo profile update - Failed, redo empty");
|
||||
return false;
|
||||
}
|
||||
|
||||
string top = profile.RedoStack.Pop();
|
||||
string memento = JsonConvert.SerializeObject(profile.ProfileEntity, IProfileService.MementoSettings);
|
||||
profile.UndoStack.Push(memento);
|
||||
profile.ProfileEntity =
|
||||
JsonConvert.DeserializeObject<ProfileEntity>(top, IProfileService.MementoSettings)
|
||||
?? throw new InvalidOperationException("Failed to deserialize memento");
|
||||
|
||||
profile.Load();
|
||||
profile.PopulateLeds(_rgbService.EnabledDevices);
|
||||
|
||||
_logger.Debug("Redo profile update - Success");
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public ProfileConfigurationExportModel ExportProfile(ProfileConfiguration profileConfiguration)
|
||||
{
|
||||
// The profile may not be active and in that case lets activate it real quick
|
||||
@@ -596,8 +532,6 @@ namespace Artemis.Core.Services
|
||||
/// <inheritdoc />
|
||||
public void AdaptProfile(Profile profile)
|
||||
{
|
||||
string memento = JsonConvert.SerializeObject(profile.ProfileEntity, IProfileService.MementoSettings);
|
||||
|
||||
List<ArtemisDevice> devices = _rgbService.EnabledDevices.ToList();
|
||||
foreach (Layer layer in profile.GetAllLayers())
|
||||
layer.Adapter.Adapt(devices);
|
||||
@@ -608,9 +542,6 @@ namespace Artemis.Core.Services
|
||||
renderProfileElement.Save();
|
||||
|
||||
_logger.Debug("Adapt profile - Saving " + profile);
|
||||
profile.RedoStack.Clear();
|
||||
profile.UndoStack.Push(memento);
|
||||
|
||||
_profileRepository.Save(profile.ProfileEntity);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,118 +0,0 @@
|
||||
// Source: https://ntsblog.homedev.com.au/index.php/2010/05/06/c-stack-with-maximum-limit/
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Artemis.Core
|
||||
{
|
||||
/// <summary>
|
||||
/// Generic stack implementation with a maximum limit
|
||||
/// When something is pushed on the last item is removed from the list
|
||||
/// </summary>
|
||||
[Serializable]
|
||||
internal class MaxStack<T>
|
||||
{
|
||||
#region Fields
|
||||
|
||||
private int _limit;
|
||||
private LinkedList<T> _list;
|
||||
|
||||
#endregion
|
||||
|
||||
#region Constructors
|
||||
|
||||
public MaxStack(int maxSize)
|
||||
{
|
||||
_limit = maxSize;
|
||||
_list = new LinkedList<T>();
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Public Stack Implementation
|
||||
|
||||
public void Push(T value)
|
||||
{
|
||||
if (_list.Count == _limit)
|
||||
{
|
||||
_list.RemoveLast();
|
||||
}
|
||||
_list.AddFirst(value);
|
||||
}
|
||||
|
||||
public T Pop()
|
||||
{
|
||||
if (_list.Count > 0)
|
||||
{
|
||||
T value = _list.First!.Value;
|
||||
_list.RemoveFirst();
|
||||
return value;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidOperationException("The Stack is empty");
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
public T Peek()
|
||||
{
|
||||
if (_list.Count > 0)
|
||||
{
|
||||
T value = _list.First!.Value;
|
||||
return value;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidOperationException("The Stack is empty");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
_list.Clear();
|
||||
|
||||
}
|
||||
|
||||
public int Count
|
||||
{
|
||||
get { return _list.Count; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Checks if the top object on the stack matches the value passed in
|
||||
/// </summary>
|
||||
/// <param name="value"></param>
|
||||
/// <returns></returns>
|
||||
public bool IsTop(T value)
|
||||
{
|
||||
bool result = false;
|
||||
if (Count > 0)
|
||||
{
|
||||
result = Peek()!.Equals(value);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public bool Contains(T value)
|
||||
{
|
||||
bool result = false;
|
||||
if (Count > 0)
|
||||
{
|
||||
result = _list.Contains(value);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public IEnumerator GetEnumerator()
|
||||
{
|
||||
return _list.GetEnumerator();
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user