From f32edcf5026fbabbb41b0e584d0e07f49c03dc07 Mon Sep 17 00:00:00 2001 From: Robert Date: Fri, 29 Nov 2019 17:37:22 +0100 Subject: [PATCH] Implemented layer LED assignment Added a centralised ProfileEditorSurface for communication between VMs Prefixed Surface, Device and Led with Artemis to differentiate them better --- src/Artemis.Core/Artemis.Core.csproj | 10 +- .../Events/DeviceConfigurationEventArgs.cs | 4 +- .../Models/Profile/Abstract/ProfileElement.cs | 2 +- src/Artemis.Core/Models/Profile/Folder.cs | 2 +- src/Artemis.Core/Models/Profile/Layer.cs | 72 +++++++++-- src/Artemis.Core/Models/Profile/Profile.cs | 4 +- .../Surface/{Device.cs => ArtemisDevice.cs} | 14 +-- .../Surface/{DeviceLed.cs => ArtemisLed.cs} | 6 +- .../Surface/{Surface.cs => ArtemisSurface.cs} | 12 +- .../Plugins/Abstract/LayerType.cs | 2 +- src/Artemis.Core/Plugins/Abstract/Module.cs | 2 +- .../Plugins/Abstract/ProfileModule.cs | 2 +- src/Artemis.Core/ProfileElements/Folder.cs | 60 ---------- .../Interfaces/IProfileElement.cs | 35 ------ src/Artemis.Core/ProfileElements/Layer.cs | 80 ------------- src/Artemis.Core/ProfileElements/Profile.cs | 113 ------------------ src/Artemis.Core/Services/DeviceService.cs | 6 +- .../Storage/Interfaces/ISurfaceService.cs | 12 +- .../Services/Storage/ProfileService.cs | 2 +- .../Services/Storage/SurfaceService.cs | 30 ++--- .../BrushLayerType.cs | 2 +- .../GeneralModule.cs | 15 ++- .../Entities/Profile/LedEntity.cs | 6 +- src/Artemis.UI/Artemis.UI.csproj | 20 ++-- ...nged.cs => MainWindowFocusChangedEvent.cs} | 4 +- .../ProfileEditorSelectedElementChanged.cs | 15 --- .../ProfileEditorSelectedProfileChanged.cs | 14 --- .../IDeviceSettingsViewMOdelFactory.cs | 2 +- .../ProfileEditor/ProfileEditorView.xaml | 2 +- .../ProfileEditor/ProfileEditorViewModel.cs | 42 +++---- .../ProfileElement/FolderViewModel.cs | 12 -- .../ProfileElement/LayerViewModel.cs | 12 -- .../ProfileTreeView.xaml} | 16 ++- .../ProfileTreeViewModel.cs} | 82 ++++++------- .../TreeItem}/FolderView.xaml | 7 +- .../ProfileTree/TreeItem/FolderViewModel.cs | 14 +++ .../TreeItem}/LayerView.xaml | 7 +- .../ProfileTree/TreeItem/LayerViewModel.cs | 14 +++ .../TreeItem/TreeItemViewModel.cs} | 111 +++++++++-------- .../Visualization/ProfileDeviceViewModel.cs | 9 +- .../Visualization/ProfileLedView.xaml | 93 +++++++------- .../Visualization/ProfileLedViewModel.cs | 29 +++-- .../Visualization/ProfileViewModel.cs | 102 +++++++++++++--- src/Artemis.UI/Screens/RootViewModel.cs | 4 +- .../Tabs/Devices/DeviceSettingsViewModel.cs | 4 +- .../SurfaceEditor/SurfaceEditorView.xaml | 2 +- .../SurfaceEditor/SurfaceEditorViewModel.cs | 12 +- .../Visualization/SurfaceDeviceViewModel.cs | 4 +- .../Interfaces/IProfileEditorService.cs | 22 ++++ .../Services/ProfileEditorService.cs | 70 +++++++++++ 50 files changed, 556 insertions(+), 662 deletions(-) rename src/Artemis.Core/Models/Surface/{Device.cs => ArtemisDevice.cs} (86%) rename src/Artemis.Core/Models/Surface/{DeviceLed.cs => ArtemisLed.cs} (91%) rename src/Artemis.Core/Models/Surface/{Surface.cs => ArtemisSurface.cs} (84%) delete mode 100644 src/Artemis.Core/ProfileElements/Folder.cs delete mode 100644 src/Artemis.Core/ProfileElements/Interfaces/IProfileElement.cs delete mode 100644 src/Artemis.Core/ProfileElements/Layer.cs delete mode 100644 src/Artemis.Core/ProfileElements/Profile.cs rename src/Artemis.UI/Events/{MainWindowFocusChanged.cs => MainWindowFocusChangedEvent.cs} (57%) delete mode 100644 src/Artemis.UI/Events/ProfileEditorSelectedElementChanged.cs delete mode 100644 src/Artemis.UI/Events/ProfileEditorSelectedProfileChanged.cs delete mode 100644 src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderViewModel.cs delete mode 100644 src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerViewModel.cs rename src/Artemis.UI/Screens/Module/ProfileEditor/{ProfileElements/ProfileElementsView.xaml => ProfileTree/ProfileTreeView.xaml} (77%) rename src/Artemis.UI/Screens/Module/ProfileEditor/{ProfileElements/ProfileElementsViewModel.cs => ProfileTree/ProfileTreeViewModel.cs} (63%) rename src/Artemis.UI/Screens/Module/ProfileEditor/{ProfileElements/ProfileElement => ProfileTree/TreeItem}/FolderView.xaml (87%) create mode 100644 src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderViewModel.cs rename src/Artemis.UI/Screens/Module/ProfileEditor/{ProfileElements/ProfileElement => ProfileTree/TreeItem}/LayerView.xaml (81%) create mode 100644 src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerViewModel.cs rename src/Artemis.UI/Screens/Module/ProfileEditor/{ProfileElements/ProfileElement/ProfileElementViewModel.cs => ProfileTree/TreeItem/TreeItemViewModel.cs} (58%) create mode 100644 src/Artemis.UI/Services/Interfaces/IProfileEditorService.cs create mode 100644 src/Artemis.UI/Services/ProfileEditorService.cs diff --git a/src/Artemis.Core/Artemis.Core.csproj b/src/Artemis.Core/Artemis.Core.csproj index 825291b25..4a17e3e64 100644 --- a/src/Artemis.Core/Artemis.Core.csproj +++ b/src/Artemis.Core/Artemis.Core.csproj @@ -161,9 +161,9 @@ - - - + + + @@ -216,9 +216,7 @@ Artemis.Storage - - - + diff --git a/src/Artemis.Core/Events/DeviceConfigurationEventArgs.cs b/src/Artemis.Core/Events/DeviceConfigurationEventArgs.cs index a2fd7d2ca..94eae8f38 100644 --- a/src/Artemis.Core/Events/DeviceConfigurationEventArgs.cs +++ b/src/Artemis.Core/Events/DeviceConfigurationEventArgs.cs @@ -5,11 +5,11 @@ namespace Artemis.Core.Events { public class SurfaceConfigurationEventArgs : EventArgs { - public SurfaceConfigurationEventArgs(Surface surface) + public SurfaceConfigurationEventArgs(ArtemisSurface surface) { Surface = surface; } - public Surface Surface { get; } + public ArtemisSurface Surface { get; } } } \ No newline at end of file diff --git a/src/Artemis.Core/Models/Profile/Abstract/ProfileElement.cs b/src/Artemis.Core/Models/Profile/Abstract/ProfileElement.cs index c544b819b..06f08c99e 100644 --- a/src/Artemis.Core/Models/Profile/Abstract/ProfileElement.cs +++ b/src/Artemis.Core/Models/Profile/Abstract/ProfileElement.cs @@ -44,7 +44,7 @@ namespace Artemis.Core.Models.Profile.Abstract /// /// Renders the element /// - public abstract void Render(double deltaTime, Surface.Surface surface, Graphics graphics); + public abstract void Render(double deltaTime, Surface.ArtemisSurface surface, Graphics graphics); /// /// Applies the profile element's properties to the underlying storage entity diff --git a/src/Artemis.Core/Models/Profile/Folder.cs b/src/Artemis.Core/Models/Profile/Folder.cs index 9952527ed..72527628b 100644 --- a/src/Artemis.Core/Models/Profile/Folder.cs +++ b/src/Artemis.Core/Models/Profile/Folder.cs @@ -56,7 +56,7 @@ namespace Artemis.Core.Models.Profile profileElement.Update(deltaTime); } - public override void Render(double deltaTime, Surface.Surface surface, Graphics graphics) + public override void Render(double deltaTime, Surface.ArtemisSurface surface, Graphics graphics) { // Folders don't render but their children do foreach (var profileElement in Children) diff --git a/src/Artemis.Core/Models/Profile/Layer.cs b/src/Artemis.Core/Models/Profile/Layer.cs index 45870c7f2..4acf2ecbf 100644 --- a/src/Artemis.Core/Models/Profile/Layer.cs +++ b/src/Artemis.Core/Models/Profile/Layer.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Collections.ObjectModel; using System.Drawing; using System.Drawing.Drawing2D; using System.Linq; @@ -15,6 +16,8 @@ namespace Artemis.Core.Models.Profile { public sealed class Layer : ProfileElement { + private List _leds; + public Layer(Profile profile, ProfileElement parent, string name) { LayerEntity = new LayerEntity(); @@ -23,7 +26,7 @@ namespace Artemis.Core.Models.Profile Profile = profile; Parent = parent; Name = name; - Leds = new List(); + _leds = new List(); } internal Layer(Profile profile, ProfileElement parent, LayerEntity layerEntity, IPluginService pluginService) @@ -37,12 +40,12 @@ namespace Artemis.Core.Models.Profile Order = layerEntity.Order; LayerType = pluginService.GetLayerTypeByGuid(layerEntity.LayerTypeGuid); - Leds = new List(); + _leds = new List(); } internal LayerEntity LayerEntity { get; set; } - public List Leds { get; private set; } + public ReadOnlyCollection Leds => _leds.AsReadOnly(); public LayerType LayerType { get; private set; } public ILayerTypeConfiguration LayerTypeConfiguration { get; set; } @@ -60,7 +63,7 @@ namespace Artemis.Core.Models.Profile } } - public override void Render(double deltaTime, Surface.Surface surface, Graphics graphics) + public override void Render(double deltaTime, ArtemisSurface surface, Graphics graphics) { if (LayerType == null) return; @@ -81,19 +84,62 @@ namespace Artemis.Core.Models.Profile LayerEntity.Name = Name; LayerEntity.ProfileId = Profile.EntityId; - // TODO: LEDs, conditions, elements - } - public void ApplySurface(Surface.Surface surface) - { - var leds = new List(); - foreach (var surfaceDevice in surface.Devices) + LayerEntity.Leds.Clear(); + foreach (var artemisLed in Leds) { - var deviceHash = surfaceDevice.RgbDevice.GetDeviceHashCode(); - leds.AddRange(surfaceDevice.Leds.Where(dl => LayerEntity.Leds.Any(l => l.DeviceHash == deviceHash && l.LedName == dl.RgbLed.ToString()))); + var ledEntity = new LedEntity + { + DeviceHash = artemisLed.Device.RgbDevice.GetDeviceHashCode(), + LedName = artemisLed.RgbLed.Id.ToString() + }; + LayerEntity.Leds.Add(ledEntity); } - Leds = leds; + LayerEntity.Condition.Clear(); + + LayerEntity.Elements.Clear(); + } + + public void ApplySurface(ArtemisSurface surface) + { + var leds = new List(); + + // Get the surface LEDs for this layer + var availableLeds = surface.Devices.SelectMany(d => d.Leds).ToList(); + foreach (var ledEntity in LayerEntity.Leds) + { + var match = availableLeds.FirstOrDefault(a => a.Device.RgbDevice.GetDeviceHashCode() == ledEntity.DeviceHash && + a.RgbLed.Id.ToString() == ledEntity.LedName); + if (match != null) + leds.Add(match); + } + + _leds = leds; + CalculateRenderProperties(); + } + + public void AddLed(ArtemisLed led) + { + _leds.Add(led); + CalculateRenderProperties(); + } + + public void AddLeds(IEnumerable leds) + { + _leds.AddRange(leds); + CalculateRenderProperties(); + } + + public void RemoveLed(ArtemisLed led) + { + _leds.Remove(led); + CalculateRenderProperties(); + } + + public void ClearLeds() + { + _leds.Clear(); CalculateRenderProperties(); } diff --git a/src/Artemis.Core/Models/Profile/Profile.cs b/src/Artemis.Core/Models/Profile/Profile.cs index d16fc3b25..5caac88bf 100644 --- a/src/Artemis.Core/Models/Profile/Profile.cs +++ b/src/Artemis.Core/Models/Profile/Profile.cs @@ -56,7 +56,7 @@ namespace Artemis.Core.Models.Profile } } - public override void Render(double deltaTime, Surface.Surface surface, Graphics graphics) + public override void Render(double deltaTime, Surface.ArtemisSurface surface, Graphics graphics) { lock (this) { @@ -113,7 +113,7 @@ namespace Artemis.Core.Models.Profile return $"{nameof(Order)}: {Order}, {nameof(Name)}: {Name}, {nameof(PluginInfo)}: {PluginInfo}"; } - public void ApplySurface(Surface.Surface surface) + public void ApplySurface(Surface.ArtemisSurface surface) { foreach (var layer in GetAllLayers()) layer.ApplySurface(surface); diff --git a/src/Artemis.Core/Models/Surface/Device.cs b/src/Artemis.Core/Models/Surface/ArtemisDevice.cs similarity index 86% rename from src/Artemis.Core/Models/Surface/Device.cs rename to src/Artemis.Core/Models/Surface/ArtemisDevice.cs index be1dae749..d276921a6 100644 --- a/src/Artemis.Core/Models/Surface/Device.cs +++ b/src/Artemis.Core/Models/Surface/ArtemisDevice.cs @@ -11,15 +11,15 @@ using Rectangle = System.Drawing.Rectangle; namespace Artemis.Core.Models.Surface { - public class Device : PropertyChangedBase + public class ArtemisDevice : PropertyChangedBase { - internal Device(IRGBDevice rgbDevice, Plugin plugin, Surface surface) + internal ArtemisDevice(IRGBDevice rgbDevice, Plugin plugin, ArtemisSurface surface) { RgbDevice = rgbDevice; Plugin = plugin; Surface = surface; DeviceEntity = new DeviceEntity(); - Leds = rgbDevice.Select(l => new DeviceLed(l, this)).ToList().AsReadOnly(); + Leds = rgbDevice.Select(l => new ArtemisLed(l, this)).ToList().AsReadOnly(); Rotation = 0; Scale = 1; @@ -29,13 +29,13 @@ namespace Artemis.Core.Models.Surface CalculateRenderProperties(); } - internal Device(IRGBDevice rgbDevice, Plugin plugin, Surface surface, DeviceEntity deviceEntity) + internal ArtemisDevice(IRGBDevice rgbDevice, Plugin plugin, ArtemisSurface surface, DeviceEntity deviceEntity) { RgbDevice = rgbDevice; Plugin = plugin; Surface = surface; DeviceEntity = deviceEntity; - Leds = rgbDevice.Select(l => new DeviceLed(l, this)).ToList().AsReadOnly(); + Leds = rgbDevice.Select(l => new ArtemisLed(l, this)).ToList().AsReadOnly(); } public Rectangle RenderRectangle { get; private set; } @@ -43,9 +43,9 @@ namespace Artemis.Core.Models.Surface public IRGBDevice RgbDevice { get; } public Plugin Plugin { get; } - public Surface Surface { get; } + public ArtemisSurface Surface { get; } public DeviceEntity DeviceEntity { get; } - public ReadOnlyCollection Leds { get; set; } + public ReadOnlyCollection Leds { get; set; } public double X { diff --git a/src/Artemis.Core/Models/Surface/DeviceLed.cs b/src/Artemis.Core/Models/Surface/ArtemisLed.cs similarity index 91% rename from src/Artemis.Core/Models/Surface/DeviceLed.cs rename to src/Artemis.Core/Models/Surface/ArtemisLed.cs index 4e9ebb071..fdc6f1162 100644 --- a/src/Artemis.Core/Models/Surface/DeviceLed.cs +++ b/src/Artemis.Core/Models/Surface/ArtemisLed.cs @@ -5,9 +5,9 @@ using Rectangle = System.Drawing.Rectangle; namespace Artemis.Core.Models.Surface { - public class DeviceLed : PropertyChangedBase + public class ArtemisLed : PropertyChangedBase { - public DeviceLed(Led led, Device device) + public ArtemisLed(Led led, ArtemisDevice device) { RgbLed = led; Device = device; @@ -15,7 +15,7 @@ namespace Artemis.Core.Models.Surface } public Led RgbLed { get; } - public Device Device { get; } + public ArtemisDevice Device { get; } public Rectangle RenderRectangle { get; private set; } public Rectangle AbsoluteRenderRectangle { get; private set; } diff --git a/src/Artemis.Core/Models/Surface/Surface.cs b/src/Artemis.Core/Models/Surface/ArtemisSurface.cs similarity index 84% rename from src/Artemis.Core/Models/Surface/Surface.cs rename to src/Artemis.Core/Models/Surface/ArtemisSurface.cs index 32540db4c..0260df1d8 100644 --- a/src/Artemis.Core/Models/Surface/Surface.cs +++ b/src/Artemis.Core/Models/Surface/ArtemisSurface.cs @@ -7,9 +7,9 @@ using Stylet; namespace Artemis.Core.Models.Surface { - public class Surface : PropertyChangedBase + public class ArtemisSurface : PropertyChangedBase { - internal Surface(RGBSurface rgbSurface, string name, double scale) + internal ArtemisSurface(RGBSurface rgbSurface, string name, double scale) { SurfaceEntity = new SurfaceEntity {DeviceEntities = new List()}; EntityId = Guid.NewGuid(); @@ -20,12 +20,12 @@ namespace Artemis.Core.Models.Surface IsActive = false; // Devices are not populated here but as they are detected - Devices = new List(); + Devices = new List(); ApplyToEntity(); } - internal Surface(RGBSurface rgbSurface, SurfaceEntity surfaceEntity, double scale) + internal ArtemisSurface(RGBSurface rgbSurface, SurfaceEntity surfaceEntity, double scale) { SurfaceEntity = surfaceEntity; EntityId = surfaceEntity.Id; @@ -36,14 +36,14 @@ namespace Artemis.Core.Models.Surface IsActive = surfaceEntity.IsActive; // Devices are not populated here but as they are detected - Devices = new List(); + Devices = new List(); } public RGBSurface RgbSurface { get; } public double Scale { get; private set; } public string Name { get; set; } public bool IsActive { get; internal set; } - public List Devices { get; internal set; } + public List Devices { get; internal set; } internal SurfaceEntity SurfaceEntity { get; set; } internal Guid EntityId { get; set; } diff --git a/src/Artemis.Core/Plugins/Abstract/LayerType.cs b/src/Artemis.Core/Plugins/Abstract/LayerType.cs index a952dcdef..53987f8e9 100644 --- a/src/Artemis.Core/Plugins/Abstract/LayerType.cs +++ b/src/Artemis.Core/Plugins/Abstract/LayerType.cs @@ -24,6 +24,6 @@ namespace Artemis.Core.Plugins.Abstract /// /// Renders the layer type /// - public abstract void Render(Layer device, Surface surface, Graphics graphics); + public abstract void Render(Layer device, ArtemisSurface surface, Graphics graphics); } } \ No newline at end of file diff --git a/src/Artemis.Core/Plugins/Abstract/Module.cs b/src/Artemis.Core/Plugins/Abstract/Module.cs index 94b49f3ee..3f085ed03 100644 --- a/src/Artemis.Core/Plugins/Abstract/Module.cs +++ b/src/Artemis.Core/Plugins/Abstract/Module.cs @@ -38,7 +38,7 @@ namespace Artemis.Core.Plugins.Abstract /// Time since the last render /// The RGB Surface to render to /// - public abstract void Render(double deltaTime, Surface surface, Graphics graphics); + public abstract void Render(double deltaTime, ArtemisSurface surface, Graphics graphics); /// /// Called when the module's view model is being show, return view models here to create tabs for them diff --git a/src/Artemis.Core/Plugins/Abstract/ProfileModule.cs b/src/Artemis.Core/Plugins/Abstract/ProfileModule.cs index f4f969438..bb0f73e95 100644 --- a/src/Artemis.Core/Plugins/Abstract/ProfileModule.cs +++ b/src/Artemis.Core/Plugins/Abstract/ProfileModule.cs @@ -25,7 +25,7 @@ namespace Artemis.Core.Plugins.Abstract } /// - public override void Render(double deltaTime, Surface surface, Graphics graphics) + public override void Render(double deltaTime, ArtemisSurface surface, Graphics graphics) { lock (this) { diff --git a/src/Artemis.Core/ProfileElements/Folder.cs b/src/Artemis.Core/ProfileElements/Folder.cs deleted file mode 100644 index 8d5113e47..000000000 --- a/src/Artemis.Core/ProfileElements/Folder.cs +++ /dev/null @@ -1,60 +0,0 @@ -using System.Collections.Generic; -using System.Drawing; -using Artemis.Core.ProfileElements.Interfaces; -using Artemis.Core.Services.Interfaces; -using Artemis.Storage.Entities; -using RGB.NET.Core; - -namespace Artemis.Core.ProfileElements -{ - public class Folder : IProfileElement - { - public Folder(Profile profile) - { - Profile = profile; - Children = new List(); - } - - public Profile Profile { get; } - public List Children { get; set; } - public int Order { get; set; } - public string Name { get; set; } - - public void Update(double deltaTime) - { - // Folders don't update but their children do - foreach (var profileElement in Children) - profileElement.Update(deltaTime); - } - - public void Render(double deltaTime, RGBSurface surface, Graphics graphics) - { - // Folders don't render but their children do - foreach (var profileElement in Children) - profileElement.Render(deltaTime, surface, graphics); - } - - public static Folder FromFolderEntity(Profile profile, FolderEntity folderEntity, IPluginService pluginService) - { - var folder = new Folder(profile) - { - Name = folderEntity.Name, - Order = folderEntity.Order - }; - - // Load child folders - foreach (var childFolder in folderEntity.Folders) - folder.Children.Add(FromFolderEntity(profile, childFolder, pluginService)); - // Load child layers - foreach (var childLayer in folderEntity.Layers) - folder.Children.Add(Layer.FromLayerEntity(profile, childLayer, pluginService)); - - return folder; - } - - public override string ToString() - { - return $"{nameof(Profile)}: {Profile}, {nameof(Order)}: {Order}, {nameof(Name)}: {Name}"; - } - } -} \ No newline at end of file diff --git a/src/Artemis.Core/ProfileElements/Interfaces/IProfileElement.cs b/src/Artemis.Core/ProfileElements/Interfaces/IProfileElement.cs deleted file mode 100644 index 3188ff197..000000000 --- a/src/Artemis.Core/ProfileElements/Interfaces/IProfileElement.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System.Collections.Generic; -using System.Drawing; -using RGB.NET.Core; - -namespace Artemis.Core.ProfileElements.Interfaces -{ - public interface IProfileElement - { - /// - /// The element's children - /// - List Children { get; set; } - - /// - /// The order in which this element appears in the update loop and editor - /// - int Order { get; set; } - - /// - /// The name which appears in the editor - /// - string Name { get; set; } - - /// - /// Updates the element - /// - /// - void Update(double deltaTime); - - /// - /// Renders the element - /// - void Render(double deltaTime, RGBSurface surface, Graphics graphics); - } -} \ No newline at end of file diff --git a/src/Artemis.Core/ProfileElements/Layer.cs b/src/Artemis.Core/ProfileElements/Layer.cs deleted file mode 100644 index 5bb680113..000000000 --- a/src/Artemis.Core/ProfileElements/Layer.cs +++ /dev/null @@ -1,80 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Drawing; -using Artemis.Core.Plugins.Abstract; -using Artemis.Core.Plugins.Interfaces; -using Artemis.Core.ProfileElements.Interfaces; -using Artemis.Core.Services.Interfaces; -using Artemis.Storage.Entities; -using RGB.NET.Core; - -namespace Artemis.Core.ProfileElements -{ - public class Layer : IProfileElement - { - public Layer(Profile profile) - { - Profile = profile; - Children = new List(); - } - - public Profile Profile { get; } - public LayerType LayerType { get; private set; } - public ILayerTypeConfiguration LayerTypeConfiguration { get; set; } - public List Children { get; set; } - public int Order { get; set; } - public string Name { get; set; } - - public void Update(double deltaTime) - { - if (LayerType == null) - return; - - lock (LayerType) - { - LayerType.Update(this); - } - } - - public void Render(double deltaTime, RGBSurface surface, Graphics graphics) - { - if (LayerType == null) - return; - - lock (LayerType) - { - LayerType.Render(this, surface, graphics); - } - } - - public static Layer FromLayerEntity(Profile profile, LayerEntity layerEntity, IPluginService pluginService) - { - var layer = new Layer(profile) - { - Name = layerEntity.Name, - Order = layerEntity.Order, - LayerType = pluginService.GetLayerTypeByGuid(Guid.Parse(layerEntity.Guid)) - }; - - return layer; - } - - public void UpdateLayerType(LayerType layerType) - { - if (LayerType != null) - { - lock (LayerType) - { - LayerType.Dispose(); - } - } - - LayerType = layerType; - } - - public override string ToString() - { - return $"{nameof(Profile)}: {Profile}, {nameof(Order)}: {Order}, {nameof(Name)}: {Name}"; - } - } -} \ No newline at end of file diff --git a/src/Artemis.Core/ProfileElements/Profile.cs b/src/Artemis.Core/ProfileElements/Profile.cs deleted file mode 100644 index 1ee460042..000000000 --- a/src/Artemis.Core/ProfileElements/Profile.cs +++ /dev/null @@ -1,113 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Drawing; -using Artemis.Core.Exceptions; -using Artemis.Core.Plugins.Models; -using Artemis.Core.ProfileElements.Interfaces; -using Artemis.Core.Services.Interfaces; -using Artemis.Storage.Entities; -using RGB.NET.Core; - -namespace Artemis.Core.ProfileElements -{ - public class Profile : IProfileElement - { - private Profile(PluginInfo pluginInfo) - { - PluginInfo = pluginInfo; - } - - public PluginInfo PluginInfo { get; } - public bool IsActivated { get; private set; } - public int Order { get; set; } - public string Name { get; set; } - public List Children { get; set; } - - public void Update(double deltaTime) - { - lock (this) - { - if (!IsActivated) - throw new ArtemisCoreException($"Cannot update inactive profile: {this}"); - - foreach (var profileElement in Children) - profileElement.Update(deltaTime); - } - } - - public void Render(double deltaTime, RGBSurface surface, Graphics graphics) - { - lock (this) - { - if (!IsActivated) - throw new ArtemisCoreException($"Cannot render inactive profile: {this}"); - - foreach (var profileElement in Children) - profileElement.Render(deltaTime, surface, graphics); - } - } - - public static Profile FromProfileEntity(PluginInfo pluginInfo, ProfileEntity profileEntity, IPluginService pluginService) - { - var profile = new Profile(pluginInfo) {Name = profileEntity.Name}; - lock (profile) - { - // Populate the profile starting at the root, the rest is populated recursively - profile.Children.Add(Folder.FromFolderEntity(profile, profileEntity.RootFolder, pluginService)); - - return profile; - } - } - - public void Activate() - { - lock (this) - { - if (IsActivated) return; - - OnActivated(); - IsActivated = true; - } - } - - public void Deactivate() - { - lock (this) - { - if (!IsActivated) return; - - IsActivated = false; - OnDeactivated(); - } - } - - public override string ToString() - { - return $"{nameof(Order)}: {Order}, {nameof(Name)}: {Name}, {nameof(PluginInfo)}: {PluginInfo}"; - } - - #region Events - - /// - /// Occurs when the profile is being activated. - /// - public event EventHandler Activated; - - /// - /// Occurs when the profile is being deactivated. - /// - public event EventHandler Deactivated; - - private void OnActivated() - { - Activated?.Invoke(this, EventArgs.Empty); - } - - private void OnDeactivated() - { - Deactivated?.Invoke(this, EventArgs.Empty); - } - - #endregion - } -} \ No newline at end of file diff --git a/src/Artemis.Core/Services/DeviceService.cs b/src/Artemis.Core/Services/DeviceService.cs index 16632a6cd..6594f8e8d 100644 --- a/src/Artemis.Core/Services/DeviceService.cs +++ b/src/Artemis.Core/Services/DeviceService.cs @@ -19,12 +19,12 @@ namespace Artemis.Core.Services _coreService = coreService; } - public void IdentifyDevice(Device device) + public void IdentifyDevice(ArtemisDevice device) { BlinkDevice(device, 0); } - private void BlinkDevice(Device device, int blinkCount) + private void BlinkDevice(ArtemisDevice device, int blinkCount) { // Draw a white overlay over the device void DrawOverlay(object sender, FrameRenderingEventArgs args) @@ -59,6 +59,6 @@ namespace Artemis.Core.Services /// Identifies the device by making it blink white 5 times /// /// - void IdentifyDevice(Device device); + void IdentifyDevice(ArtemisDevice device); } } diff --git a/src/Artemis.Core/Services/Storage/Interfaces/ISurfaceService.cs b/src/Artemis.Core/Services/Storage/Interfaces/ISurfaceService.cs index 64cc44d3c..e70192d96 100644 --- a/src/Artemis.Core/Services/Storage/Interfaces/ISurfaceService.cs +++ b/src/Artemis.Core/Services/Storage/Interfaces/ISurfaceService.cs @@ -11,38 +11,38 @@ namespace Artemis.Core.Services.Storage.Interfaces /// /// Gets the currently active surface entity, to change config use /// - Surface ActiveSurface { get; } + ArtemisSurface ActiveSurface { get; } /// /// Gets a read-only list of all surface configurations /// - ReadOnlyCollection SurfaceConfigurations { get; } + ReadOnlyCollection SurfaceConfigurations { get; } /// /// Creates a new surface entity with the supplied name /// /// The name for the new surface entity /// - Surface CreateSurfaceConfiguration(string name); + ArtemisSurface CreateSurfaceConfiguration(string name); /// /// Sets the provided entity as active and applies it to the surface /// /// The entity to activate and apply - void SetActiveSurfaceConfiguration(Surface surface); + void SetActiveSurfaceConfiguration(ArtemisSurface surface); /// /// Saves the provided surface entity to permanent storage and if config is active, applies it to the surface /// /// The entity to save (and apply if active) /// Whether to also save devices. If false, devices changes won't be applied either - void UpdateSurfaceConfiguration(Surface surface, bool includeDevices); + void UpdateSurfaceConfiguration(ArtemisSurface surface, bool includeDevices); /// /// Deletes the supplied surface entity, surface entity may not be the active surface entity /// /// The surface entity to delete, may not be the active surface entity - void DeleteSurfaceConfiguration(Surface surface); + void DeleteSurfaceConfiguration(ArtemisSurface surface); /// /// Occurs when the active device entity has been changed diff --git a/src/Artemis.Core/Services/Storage/ProfileService.cs b/src/Artemis.Core/Services/Storage/ProfileService.cs index 351e44047..1e226638c 100644 --- a/src/Artemis.Core/Services/Storage/ProfileService.cs +++ b/src/Artemis.Core/Services/Storage/ProfileService.cs @@ -41,7 +41,7 @@ namespace Artemis.Core.Services.Storage ApplySurfaceToProfiles(e.Surface); } - private void ApplySurfaceToProfiles(Surface surface) + private void ApplySurfaceToProfiles(ArtemisSurface surface) { var profileModules = _pluginService.GetPluginsOfType(); foreach (var profileModule in profileModules.Where(p => p.ActiveProfile != null).ToList()) diff --git a/src/Artemis.Core/Services/Storage/SurfaceService.cs b/src/Artemis.Core/Services/Storage/SurfaceService.cs index 08bf0d9b4..caf39d8d9 100644 --- a/src/Artemis.Core/Services/Storage/SurfaceService.cs +++ b/src/Artemis.Core/Services/Storage/SurfaceService.cs @@ -21,7 +21,7 @@ namespace Artemis.Core.Services.Storage private readonly IPluginService _pluginService; private readonly PluginSetting _renderScaleSetting; private readonly IRgbService _rgbService; - private readonly List _surfaceConfigurations; + private readonly List _surfaceConfigurations; private readonly ISurfaceRepository _surfaceRepository; internal SurfaceService(ILogger logger, ISurfaceRepository surfaceRepository, IRgbService rgbService, IPluginService pluginService, ISettingsService settingsService) @@ -30,7 +30,7 @@ namespace Artemis.Core.Services.Storage _surfaceRepository = surfaceRepository; _rgbService = rgbService; _pluginService = pluginService; - _surfaceConfigurations = new List(); + _surfaceConfigurations = new List(); _renderScaleSetting = settingsService.GetSetting("Core.RenderScale", 1.0); LoadFromRepository(); @@ -39,19 +39,19 @@ namespace Artemis.Core.Services.Storage _renderScaleSetting.SettingChanged += RenderScaleSettingOnSettingChanged; } - public Surface ActiveSurface { get; private set; } - public ReadOnlyCollection SurfaceConfigurations => _surfaceConfigurations.AsReadOnly(); + public ArtemisSurface ActiveSurface { get; private set; } + public ReadOnlyCollection SurfaceConfigurations => _surfaceConfigurations.AsReadOnly(); - public Surface CreateSurfaceConfiguration(string name) + public ArtemisSurface CreateSurfaceConfiguration(string name) { // Create a blank config - var configuration = new Surface(_rgbService.Surface, name, _renderScaleSetting.Value); + var configuration = new ArtemisSurface(_rgbService.Surface, name, _renderScaleSetting.Value); // Add all current devices foreach (var rgbDevice in _rgbService.LoadedDevices) { var plugin = _pluginService.GetDevicePlugin(rgbDevice); - configuration.Devices.Add(new Device(rgbDevice, plugin, configuration)); + configuration.Devices.Add(new ArtemisDevice(rgbDevice, plugin, configuration)); } lock (_surfaceConfigurations) @@ -64,7 +64,7 @@ namespace Artemis.Core.Services.Storage } } - public void SetActiveSurfaceConfiguration(Surface surface) + public void SetActiveSurfaceConfiguration(ArtemisSurface surface) { if (ActiveSurface == surface) return; @@ -97,7 +97,7 @@ namespace Artemis.Core.Services.Storage OnActiveSurfaceConfigurationChanged(new SurfaceConfigurationEventArgs(ActiveSurface)); } - public void UpdateSurfaceConfiguration(Surface surface, bool includeDevices) + public void UpdateSurfaceConfiguration(ArtemisSurface surface, bool includeDevices) { surface.ApplyToEntity(); if (includeDevices) @@ -115,7 +115,7 @@ namespace Artemis.Core.Services.Storage OnSurfaceConfigurationUpdated(new SurfaceConfigurationEventArgs(surface)); } - public void DeleteSurfaceConfiguration(Surface surface) + public void DeleteSurfaceConfiguration(ArtemisSurface surface) { if (surface == ActiveSurface) throw new ArtemisCoreException($"Cannot delete surface entity '{surface.Name}' because it is active."); @@ -136,14 +136,14 @@ namespace Artemis.Core.Services.Storage foreach (var surfaceEntity in configs) { // Create the surface entity - var surfaceConfiguration = new Surface(_rgbService.Surface, surfaceEntity, _renderScaleSetting.Value); + var surfaceConfiguration = new ArtemisSurface(_rgbService.Surface, surfaceEntity, _renderScaleSetting.Value); foreach (var position in surfaceEntity.DeviceEntities) { var device = _rgbService.Surface.Devices.FirstOrDefault(d => d.GetDeviceHashCode() == position.DeviceHashCode); if (device != null) { var plugin = _pluginService.GetDevicePlugin(device); - surfaceConfiguration.Devices.Add(new Device(device, plugin, surfaceConfiguration, position)); + surfaceConfiguration.Devices.Add(new ArtemisDevice(device, plugin, surfaceConfiguration, position)); } } @@ -172,7 +172,7 @@ namespace Artemis.Core.Services.Storage #region Utilities - private void AddDeviceIfMissing(IRGBDevice rgbDevice, Surface surface) + private void AddDeviceIfMissing(IRGBDevice rgbDevice, ArtemisSurface surface) { var deviceHashCode = rgbDevice.GetDeviceHashCode(); var device = surface.Devices.FirstOrDefault(d => d.DeviceEntity.DeviceHashCode == deviceHashCode); @@ -185,7 +185,7 @@ namespace Artemis.Core.Services.Storage if (existingDeviceConfig != null) { var plugin = _pluginService.GetDevicePlugin(rgbDevice); - device = new Device(rgbDevice, plugin, surface, existingDeviceConfig); + device = new ArtemisDevice(rgbDevice, plugin, surface, existingDeviceConfig); } // Fall back on creating a new device else @@ -196,7 +196,7 @@ namespace Artemis.Core.Services.Storage deviceHashCode ); var plugin = _pluginService.GetDevicePlugin(rgbDevice); - device = new Device(rgbDevice, plugin, surface); + device = new ArtemisDevice(rgbDevice, plugin, surface); } surface.Devices.Add(device); diff --git a/src/Artemis.Plugins.LayerTypes.Brush/BrushLayerType.cs b/src/Artemis.Plugins.LayerTypes.Brush/BrushLayerType.cs index 29e0409cd..26e8ba980 100644 --- a/src/Artemis.Plugins.LayerTypes.Brush/BrushLayerType.cs +++ b/src/Artemis.Plugins.LayerTypes.Brush/BrushLayerType.cs @@ -31,7 +31,7 @@ namespace Artemis.Plugins.LayerTypes.Brush // Update the brush } - public override void Render(Layer device, Surface surface, Graphics graphics) + public override void Render(Layer device, ArtemisSurface surface, Graphics graphics) { } diff --git a/src/Artemis.Plugins.Modules.General/GeneralModule.cs b/src/Artemis.Plugins.Modules.General/GeneralModule.cs index 7f69ac188..b3858df98 100644 --- a/src/Artemis.Plugins.Modules.General/GeneralModule.cs +++ b/src/Artemis.Plugins.Modules.General/GeneralModule.cs @@ -8,7 +8,6 @@ using Artemis.Core.Plugins.Abstract; using Artemis.Core.Plugins.Models; using Artemis.Core.Services.Storage.Interfaces; using Artemis.Plugins.Modules.General.ViewModels; -using Device = Artemis.Core.Models.Surface.Device; namespace Artemis.Plugins.Modules.General { @@ -22,7 +21,7 @@ namespace Artemis.Plugins.Modules.General _settings = settings; DisplayName = "General"; ExpandsMainDataModel = true; - DeviceBrushes = new Dictionary(); + DeviceBrushes = new Dictionary(); var testSetting = _settings.GetSetting("TestSetting", DateTime.Now); @@ -69,7 +68,7 @@ namespace Artemis.Plugins.Modules.General } - public override void Render(double deltaTime, Surface surface, Graphics graphics) + public override void Render(double deltaTime, ArtemisSurface surface, Graphics graphics) { // Per-device coloring, slower RenderPerDevice(surface, graphics); @@ -78,11 +77,11 @@ namespace Artemis.Plugins.Modules.General // RenderPerLed(surface, graphics); } - public void RenderFullSurface(Surface surface, Graphics graphics) + public void RenderFullSurface(ArtemisSurface surface, Graphics graphics) { } - public void RenderPerDevice(Surface surface, Graphics graphics) + public void RenderPerDevice(ArtemisSurface surface, Graphics graphics) { foreach (var device in surface.Devices) { @@ -98,9 +97,9 @@ namespace Artemis.Plugins.Modules.General } } - public Dictionary DeviceBrushes { get; set; } + public Dictionary DeviceBrushes { get; set; } - private Image RenderGradientForDevice(Device device) + private Image RenderGradientForDevice(ArtemisDevice device) { var brush = new LinearGradientBrush(device.RenderRectangle, Color.Black, Color.Black, 0, false) { @@ -115,7 +114,7 @@ namespace Artemis.Plugins.Modules.General return bitmap; } - public void RenderPerLed(Surface surface, Graphics graphics) + public void RenderPerLed(ArtemisSurface surface, Graphics graphics) { var index = 0; foreach (var led in surface.Devices.SelectMany(d => d.Leds)) diff --git a/src/Artemis.Storage/Entities/Profile/LedEntity.cs b/src/Artemis.Storage/Entities/Profile/LedEntity.cs index 358648b10..74fd2d5dd 100644 --- a/src/Artemis.Storage/Entities/Profile/LedEntity.cs +++ b/src/Artemis.Storage/Entities/Profile/LedEntity.cs @@ -1,11 +1,7 @@ -using System; - -namespace Artemis.Storage.Entities.Profile +namespace Artemis.Storage.Entities.Profile { public class LedEntity { - public Guid Id { get; set; } - public string LedName { get; set; } public int DeviceHash { get; set; } } diff --git a/src/Artemis.UI/Artemis.UI.csproj b/src/Artemis.UI/Artemis.UI.csproj index 0f5d338d1..c7b7f18dd 100644 --- a/src/Artemis.UI/Artemis.UI.csproj +++ b/src/Artemis.UI/Artemis.UI.csproj @@ -152,9 +152,9 @@ - - - + + + @@ -182,11 +182,11 @@ - - - + + + - + @@ -258,15 +258,15 @@ Designer MSBuild:Compile - + Designer MSBuild:Compile - + Designer MSBuild:Compile - + Designer MSBuild:Compile diff --git a/src/Artemis.UI/Events/MainWindowFocusChanged.cs b/src/Artemis.UI/Events/MainWindowFocusChangedEvent.cs similarity index 57% rename from src/Artemis.UI/Events/MainWindowFocusChanged.cs rename to src/Artemis.UI/Events/MainWindowFocusChangedEvent.cs index ed3bbc0f1..d06a2fffe 100644 --- a/src/Artemis.UI/Events/MainWindowFocusChanged.cs +++ b/src/Artemis.UI/Events/MainWindowFocusChangedEvent.cs @@ -1,8 +1,8 @@ namespace Artemis.UI.Events { - public class MainWindowFocusChanged + public class MainWindowFocusChangedEvent { - public MainWindowFocusChanged(bool isFocused) + public MainWindowFocusChangedEvent(bool isFocused) { IsFocused = isFocused; } diff --git a/src/Artemis.UI/Events/ProfileEditorSelectedElementChanged.cs b/src/Artemis.UI/Events/ProfileEditorSelectedElementChanged.cs deleted file mode 100644 index 65277cfb0..000000000 --- a/src/Artemis.UI/Events/ProfileEditorSelectedElementChanged.cs +++ /dev/null @@ -1,15 +0,0 @@ -using Artemis.Core.Models.Profile; -using Artemis.Core.Models.Profile.Abstract; - -namespace Artemis.UI.Events -{ - public class ProfileEditorSelectedElementChanged - { - public ProfileEditorSelectedElementChanged(ProfileElement profileElement) - { - ProfileElement = profileElement; - } - - public ProfileElement ProfileElement { get; } - } -} \ No newline at end of file diff --git a/src/Artemis.UI/Events/ProfileEditorSelectedProfileChanged.cs b/src/Artemis.UI/Events/ProfileEditorSelectedProfileChanged.cs deleted file mode 100644 index 01b95a90e..000000000 --- a/src/Artemis.UI/Events/ProfileEditorSelectedProfileChanged.cs +++ /dev/null @@ -1,14 +0,0 @@ -using Artemis.Core.Models.Profile; - -namespace Artemis.UI.Events -{ - public class ProfileEditorSelectedProfileChanged - { - public ProfileEditorSelectedProfileChanged(Profile profile) - { - Profile = profile; - } - - public Profile Profile { get; } - } -} \ No newline at end of file diff --git a/src/Artemis.UI/Ninject/Factories/IDeviceSettingsViewMOdelFactory.cs b/src/Artemis.UI/Ninject/Factories/IDeviceSettingsViewMOdelFactory.cs index 62a113b84..5bbae036c 100644 --- a/src/Artemis.UI/Ninject/Factories/IDeviceSettingsViewMOdelFactory.cs +++ b/src/Artemis.UI/Ninject/Factories/IDeviceSettingsViewMOdelFactory.cs @@ -5,6 +5,6 @@ namespace Artemis.UI.Ninject.Factories { public interface IDeviceSettingsViewModelFactory : IArtemisUIFactory { - DeviceSettingsViewModel Create(Device device); + DeviceSettingsViewModel Create(ArtemisDevice device); } } \ No newline at end of file diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorView.xaml b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorView.xaml index c96765e37..4ee4b2843 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorView.xaml +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorView.xaml @@ -141,7 +141,7 @@ - + diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorViewModel.cs index 898f5219f..831660ead 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorViewModel.cs +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileEditorViewModel.cs @@ -13,7 +13,7 @@ using Artemis.UI.Screens.Module.ProfileEditor.Dialogs; using Artemis.UI.Screens.Module.ProfileEditor.DisplayConditions; using Artemis.UI.Screens.Module.ProfileEditor.ElementProperties; using Artemis.UI.Screens.Module.ProfileEditor.LayerElements; -using Artemis.UI.Screens.Module.ProfileEditor.ProfileElements; +using Artemis.UI.Screens.Module.ProfileEditor.ProfileTree; using Artemis.UI.Screens.Module.ProfileEditor.Visualization; using Artemis.UI.Services.Interfaces; using Stylet; @@ -22,16 +22,20 @@ namespace Artemis.UI.Screens.Module.ProfileEditor { public class ProfileEditorViewModel : Conductor.Collection.AllActive { - private readonly IEventAggregator _eventAggregator; + private readonly IProfileEditorService _profileEditorService; private readonly IProfileService _profileService; private readonly ISettingsService _settingsService; - public ProfileEditorViewModel(ProfileModule module, ICollection viewModels, IProfileService profileService, - IDialogService dialogService, ISettingsService settingsService, IEventAggregator eventAggregator) + public ProfileEditorViewModel(ProfileModule module, + ICollection viewModels, + IProfileEditorService profileEditorService, + IProfileService profileService, + IDialogService dialogService, + ISettingsService settingsService) { + _profileEditorService = profileEditorService; _profileService = profileService; _settingsService = settingsService; - _eventAggregator = eventAggregator; DisplayName = "Profile editor"; Module = module; @@ -40,7 +44,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor DisplayConditionsViewModel = (DisplayConditionsViewModel) viewModels.First(vm => vm is DisplayConditionsViewModel); ElementPropertiesViewModel = (ElementPropertiesViewModel) viewModels.First(vm => vm is ElementPropertiesViewModel); LayerElementsViewModel = (LayerElementsViewModel) viewModels.First(vm => vm is LayerElementsViewModel); - ProfileElementsViewModel = (ProfileElementsViewModel) viewModels.First(vm => vm is ProfileElementsViewModel); + ProfileTreeViewModel = (ProfileTreeViewModel) viewModels.First(vm => vm is ProfileTreeViewModel); ProfileViewModel = (ProfileViewModel) viewModels.First(vm => vm is ProfileViewModel); Profiles = new BindableCollection(); @@ -54,7 +58,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor public DisplayConditionsViewModel DisplayConditionsViewModel { get; } public ElementPropertiesViewModel ElementPropertiesViewModel { get; } public LayerElementsViewModel LayerElementsViewModel { get; } - public ProfileElementsViewModel ProfileElementsViewModel { get; } + public ProfileTreeViewModel ProfileTreeViewModel { get; } public ProfileViewModel ProfileViewModel { get; } public BindableCollection Profiles { get; set; } @@ -78,12 +82,13 @@ namespace Artemis.UI.Screens.Module.ProfileEditor var oldProfile = Module.ActiveProfile; Module.ChangeActiveProfile(profile); - _eventAggregator.Publish(new ProfileEditorSelectedProfileChanged(SelectedProfile)); - + if (oldProfile != null) _profileService.UpdateProfile(oldProfile, false); if (profile != null) _profileService.UpdateProfile(profile, false); + + _profileEditorService.ChangeSelectedProfile(profile); } public Profile CreateProfile(string name) @@ -135,11 +140,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor protected override void OnActivate() { LoadWorkspaceSettings(); - Task.Run(() => - { - LoadProfiles(); - _eventAggregator.Publish(new ProfileEditorSelectedProfileChanged(SelectedProfile)); - }); + Task.Run(() => LoadProfiles()); base.OnActivate(); } @@ -176,14 +177,13 @@ namespace Artemis.UI.Screens.Module.ProfileEditor profiles = profiles.Where(p => p.EntityId != activeProfile.EntityId).ToList(); profiles.Add(activeProfile); - Execute.PostToUIThread(() => - { - // Populate the UI collection - Profiles.Clear(); - Profiles.AddRange(profiles.OrderBy(p => p.Name)); + // Populate the UI collection + Profiles.Clear(); + Profiles.AddRange(profiles.OrderBy(p => p.Name)); - SelectedProfile = activeProfile; - }); + SelectedProfile = activeProfile; + + _profileEditorService.ChangeSelectedProfile(SelectedProfile); if (!activeProfile.IsActivated) Module.ChangeActiveProfile(activeProfile); diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderViewModel.cs deleted file mode 100644 index 7dbb257de..000000000 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderViewModel.cs +++ /dev/null @@ -1,12 +0,0 @@ -namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement -{ - public class FolderViewModel : ProfileElementViewModel - { - public FolderViewModel(ProfileElementViewModel parent, Core.Models.Profile.Abstract.ProfileElement folder, ProfileEditorViewModel profileEditorViewModel) - : base(parent, folder, profileEditorViewModel) - { - } - - public override bool SupportsChildren => true; - } -} \ No newline at end of file diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerViewModel.cs deleted file mode 100644 index 57101e0f1..000000000 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerViewModel.cs +++ /dev/null @@ -1,12 +0,0 @@ -namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement -{ - public class LayerViewModel : ProfileElementViewModel - { - public LayerViewModel(ProfileElementViewModel parent, Core.Models.Profile.Abstract.ProfileElement layer, ProfileEditorViewModel profileEditorViewModel) - : base(parent, layer, profileEditorViewModel) - { - } - - public override bool SupportsChildren => false; - } -} \ No newline at end of file diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsView.xaml b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeView.xaml similarity index 77% rename from src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsView.xaml rename to src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeView.xaml index 9a6814083..86cad251d 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsView.xaml +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeView.xaml @@ -1,20 +1,18 @@ - + d:DataContext="{d:DesignInstance {x:Type profileTree:ProfileTreeViewModel}}"> @@ -35,13 +33,13 @@ dd:DragDrop.IsDropTarget="True" dd:DragDrop.DropHandler="{Binding}"> - + - + - + diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeViewModel.cs similarity index 63% rename from src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsViewModel.cs rename to src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeViewModel.cs index 11579796f..4bf780760 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElementsViewModel.cs +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/ProfileTreeViewModel.cs @@ -1,37 +1,36 @@ -using System.Linq; +using System; +using System.Linq; using System.Windows; using Artemis.Core.Models.Profile; -using Artemis.Core.Services.Storage.Interfaces; -using Artemis.UI.Events; -using Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement; +using Artemis.UI.Screens.Module.ProfileEditor.ProfileTree.TreeItem; +using Artemis.UI.Services.Interfaces; using GongSolutions.Wpf.DragDrop; -using Stylet; -namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements +namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileTree { - public class ProfileElementsViewModel : ProfileEditorPanelViewModel, IDropTarget + public class ProfileTreeViewModel : ProfileEditorPanelViewModel, IDropTarget { - private readonly IProfileService _profileService; - private readonly IEventAggregator _eventAggregator; - private ProfileElementViewModel _selectedProfileElement; + private readonly IProfileEditorService _profileEditorService; + private TreeItemViewModel _selectedTreeItem; - public ProfileElementsViewModel(IProfileService profileService, IEventAggregator eventAggregator) + public ProfileTreeViewModel(IProfileEditorService profileEditorService) { - _profileService = profileService; - _eventAggregator = eventAggregator; + _profileEditorService = profileEditorService; CreateRootFolderViewModel(); + _profileEditorService.SelectedProfileChanged += OnSelectedProfileChanged; + _profileEditorService.SelectedProfileElementChanged += OnSelectedElementChanged; } public FolderViewModel RootFolder { get; set; } - public ProfileElementViewModel SelectedProfileElement + public TreeItemViewModel SelectedTreeItem { - get => _selectedProfileElement; + get => _selectedTreeItem; set { - _selectedProfileElement = value; - _eventAggregator.Publish(new ProfileEditorSelectedElementChanged(_selectedProfileElement.ProfileElement)); + _selectedTreeItem = value; + _profileEditorService.ChangeSelectedProfileElement(value?.ProfileElement); } } @@ -55,8 +54,8 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements public void Drop(IDropInfo dropInfo) { - var source = (ProfileElementViewModel) dropInfo.Data; - var target = (ProfileElementViewModel) dropInfo.TargetItem; + var source = (TreeItemViewModel) dropInfo.Data; + var target = (TreeItemViewModel) dropInfo.TargetItem; var dragDropType = GetDragDropType(dropInfo); switch (dragDropType) @@ -73,8 +72,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements break; } - _profileService.UpdateProfile(this.RootFolder.P); - ProfileEditorViewModel.OnProfileUpdated(this); + _profileEditorService.UpdateSelectedProfile(); } // ReSharper disable once UnusedMember.Global - Called from view @@ -89,36 +87,22 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements RootFolder?.AddLayer(); } - public override void ActiveProfileChanged() - { - CreateRootFolderViewModel(); - base.ActiveProfileChanged(); - } - - public override void ProfileElementSelected(ProfileElementViewModel profileElement) - { - // Don't set it using the setter or that will trigger the event again - _selectedProfileElement = profileElement; - NotifyOfPropertyChange(() => SelectedProfileElement); - - base.ProfileElementSelected(profileElement); - } - private void CreateRootFolderViewModel() { - if (!(ProfileEditorViewModel?.SelectedProfile?.Children?.FirstOrDefault() is Folder folder)) + var firstChild = _profileEditorService.SelectedProfile?.Children?.FirstOrDefault(); + if (!(firstChild is Folder folder)) { RootFolder = null; return; } - RootFolder = new FolderViewModel(null, folder, ProfileEditorViewModel); + RootFolder = new FolderViewModel(null, folder, _profileEditorService); } private static DragDropType GetDragDropType(IDropInfo dropInfo) { - var source = (ProfileElementViewModel) dropInfo.Data; - var target = (ProfileElementViewModel) dropInfo.TargetItem; + var source = (TreeItemViewModel) dropInfo.Data; + var target = (TreeItemViewModel) dropInfo.TargetItem; if (source == target) return DragDropType.None; @@ -143,6 +127,24 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements return DragDropType.None; } } + + #region Event handlers + + private void OnSelectedElementChanged(object sender, EventArgs e) + { + var vms = RootFolder.GetAllChildren(); + + // Don't set it using the setter or that will trigger the event again + _selectedTreeItem = vms.FirstOrDefault(vm => vm.ProfileElement == _profileEditorService.SelectedProfileElement); + NotifyOfPropertyChange(() => SelectedTreeItem); + } + + private void OnSelectedProfileChanged(object sender, EventArgs e) + { + CreateRootFolderViewModel(); + } + + #endregion } public enum DragDropType diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderView.xaml b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderView.xaml similarity index 87% rename from src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderView.xaml rename to src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderView.xaml index f49d47378..8575bf087 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/FolderView.xaml +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderView.xaml @@ -1,15 +1,14 @@ - + d:DataContext="{d:DesignInstance {x:Type treeItem:FolderViewModel}}"> diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderViewModel.cs new file mode 100644 index 000000000..0a011e090 --- /dev/null +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/FolderViewModel.cs @@ -0,0 +1,14 @@ +using Artemis.Core.Models.Profile.Abstract; +using Artemis.UI.Services.Interfaces; + +namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileTree.TreeItem +{ + public class FolderViewModel : TreeItemViewModel + { + public FolderViewModel(TreeItemViewModel parent, ProfileElement folder, IProfileEditorService profileEditorService) : base(parent, folder, profileEditorService) + { + } + + public override bool SupportsChildren => true; + } +} \ No newline at end of file diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerView.xaml b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerView.xaml similarity index 81% rename from src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerView.xaml rename to src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerView.xaml index 08a0cac47..2315ed732 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/LayerView.xaml +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerView.xaml @@ -1,15 +1,14 @@ - + d:DataContext="{d:DesignInstance {x:Type treeItem:LayerViewModel}}"> diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerViewModel.cs new file mode 100644 index 000000000..6ba30eb7c --- /dev/null +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/LayerViewModel.cs @@ -0,0 +1,14 @@ +using Artemis.Core.Models.Profile.Abstract; +using Artemis.UI.Services.Interfaces; + +namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileTree.TreeItem +{ + public class LayerViewModel : TreeItemViewModel + { + public LayerViewModel(TreeItemViewModel parent, ProfileElement layer, IProfileEditorService profileEditorService) : base(parent, layer, profileEditorService) + { + } + + public override bool SupportsChildren => false; + } +} \ No newline at end of file diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/ProfileElementViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/TreeItemViewModel.cs similarity index 58% rename from src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/ProfileElementViewModel.cs rename to src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/TreeItemViewModel.cs index e381637e6..787ad93c0 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileElements/ProfileElement/ProfileElementViewModel.cs +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/ProfileTree/TreeItem/TreeItemViewModel.cs @@ -2,32 +2,47 @@ using System.Linq; using System.Threading.Tasks; using Artemis.Core.Models.Profile; +using Artemis.Core.Models.Profile.Abstract; using Artemis.UI.Exceptions; -using Artemis.UI.Screens.Module.ProfileEditor.Dialogs; +using Artemis.UI.Services.Interfaces; using Stylet; -namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement +namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileTree.TreeItem { - public abstract class ProfileElementViewModel : PropertyChangedBase + public abstract class TreeItemViewModel : PropertyChangedBase { - protected ProfileElementViewModel(ProfileElementViewModel parent, Core.Models.Profile.Abstract.ProfileElement profileElement, ProfileEditorViewModel profileEditorViewModel) + protected TreeItemViewModel(TreeItemViewModel parent, ProfileElement profileElement, IProfileEditorService profileEditorService) { Parent = parent; ProfileElement = profileElement; - ProfileEditorViewModel = profileEditorViewModel; + ProfileEditorService = profileEditorService; - Children = new BindableCollection(); + Children = new BindableCollection(); UpdateProfileElements(); } + public TreeItemViewModel Parent { get; set; } + public ProfileElement ProfileElement { get; set; } + public IProfileEditorService ProfileEditorService { get; set; } + public abstract bool SupportsChildren { get; } - public ProfileElementViewModel Parent { get; set; } - public ProfileEditorViewModel ProfileEditorViewModel { get; set; } + public BindableCollection Children { get; set; } - public Core.Models.Profile.Abstract.ProfileElement ProfileElement { get; set; } - public BindableCollection Children { get; set; } + public List GetAllChildren() + { + var children = new List(); + foreach (var childFolder in Children) + { + // Add all children in this element + children.Add(childFolder); + // Add all children of children inside this element + children.AddRange(childFolder.GetAllChildren()); + } - public void SetElementInFront(ProfileElementViewModel source) + return children; + } + + public void SetElementInFront(TreeItemViewModel source) { if (source.Parent != Parent) { @@ -40,7 +55,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement Parent.UpdateProfileElements(); } - public void SetElementBehind(ProfileElementViewModel source) + public void SetElementBehind(TreeItemViewModel source) { if (source.Parent != Parent) { @@ -53,24 +68,24 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement Parent.UpdateProfileElements(); } - public void RemoveExistingElement(ProfileElementViewModel element) + public void RemoveExistingElement(TreeItemViewModel treeItem) { if (!SupportsChildren) throw new ArtemisUIException("Cannot remove a child from a profile element of type " + ProfileElement.GetType().Name); - ProfileElement.RemoveChild(element.ProfileElement); - Children.Remove(element); - element.Parent = null; + ProfileElement.RemoveChild(treeItem.ProfileElement); + Children.Remove(treeItem); + treeItem.Parent = null; } - public void AddExistingElement(ProfileElementViewModel element) + public void AddExistingElement(TreeItemViewModel treeItem) { if (!SupportsChildren) throw new ArtemisUIException("Cannot add a child to a profile element of type " + ProfileElement.GetType().Name); - ProfileElement.AddChild(element.ProfileElement); - Children.Add(element); - element.Parent = this; + ProfileElement.AddChild(treeItem.ProfileElement); + Children.Add(treeItem); + treeItem.Parent = this; } public void AddFolder() @@ -80,7 +95,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement ProfileElement.AddChild(new Folder(ProfileElement.Profile, ProfileElement, "New folder")); UpdateProfileElements(); - ProfileEditorViewModel.OnProfileUpdated(); + ProfileEditorService.UpdateSelectedProfile(); } public void AddLayer() @@ -90,40 +105,40 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement ProfileElement.AddChild(new Layer(ProfileElement.Profile, ProfileElement, "New layer")); UpdateProfileElements(); - ProfileEditorViewModel.OnProfileUpdated(); + ProfileEditorService.UpdateSelectedProfile(); } // ReSharper disable once UnusedMember.Global - Called from view public async Task RenameElement() { - var result = await ProfileEditorViewModel.DialogService.ShowDialog( - new Dictionary {{"profileElement", ProfileElement}} - ); - if (result is string newName) - { - ProfileElement.Name = newName; - ProfileEditorViewModel.OnProfileUpdated(); - } +// var result = await ProfileEditorService.DialogService.ShowDialog( +// new Dictionary {{"profileElement", ProfileElement}} +// ); +// if (result is string newName) +// { +// ProfileElement.Name = newName; +// ProfileEditorService.UpdateSelectedProfile(); +// } } // ReSharper disable once UnusedMember.Global - Called from view public async Task DeleteElement() { - var result = await ProfileEditorViewModel.DialogService.ShowConfirmDialog( - "Delete profile element", - "Are you sure you want to delete this element? This cannot be undone." - ); - - if (!result) - return; - - // Farewell, cruel world - var parent = Parent; - ProfileElement.Parent.RemoveChild(ProfileElement); - parent.RemoveExistingElement(this); - parent.UpdateProfileElements(); - - ProfileEditorViewModel.OnProfileUpdated(); +// var result = await ProfileEditorService.DialogService.ShowConfirmDialog( +// "Delete profile element", +// "Are you sure you want to delete this element? This cannot be undone." +// ); +// +// if (!result) +// return; +// +// // Farewell, cruel world +// var parent = Parent; +// ProfileElement.Parent.RemoveChild(ProfileElement); +// parent.RemoveExistingElement(this); +// parent.UpdateProfileElements(); +// +// ProfileEditorService.UpdateSelectedProfile(); } private void UpdateProfileElements() @@ -141,18 +156,18 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.ProfileElements.ProfileElement { foreach (var profileElement in ProfileElement.Children.OrderBy(c => c.Order)) { - ProfileElementViewModel existing = null; + TreeItemViewModel existing = null; if (profileElement is Folder folder) { existing = Children.FirstOrDefault(p => p is FolderViewModel vm && vm.ProfileElement == folder); if (existing == null) - Children.Add(new FolderViewModel(this, folder, ProfileEditorViewModel)); + Children.Add(new FolderViewModel(this, folder, ProfileEditorService)); } else if (profileElement is Layer layer) { existing = Children.FirstOrDefault(p => p is LayerViewModel vm && vm.ProfileElement == layer); if (existing == null) - Children.Add(new LayerViewModel(this, layer, ProfileEditorViewModel)); + Children.Add(new LayerViewModel(this, layer, ProfileEditorService)); } existing?.UpdateProfileElements(); diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileDeviceViewModel.cs b/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileDeviceViewModel.cs index f0fb95d62..b12ba9d4c 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileDeviceViewModel.cs +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileDeviceViewModel.cs @@ -9,17 +9,16 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.Visualization { public class ProfileDeviceViewModel : PropertyChangedBase { - public ProfileDeviceViewModel(Device device) + public ProfileDeviceViewModel(ArtemisDevice device) { Device = device; Leds = new ObservableCollection(); - if (Device.RgbDevice != null) - Task.Run(AddLedsAsync); + Task.Run(AddLedsAsync); } public ObservableCollection Leds { get; set; } - public Device Device { get; set; } + public ArtemisDevice Device { get; set; } public bool AddedLeds { get; private set; } public double X @@ -52,7 +51,7 @@ namespace Artemis.UI.Screens.Module.ProfileEditor.Visualization private async Task AddLedsAsync() { var index = 0; - foreach (var led in Device.RgbDevice.ToList()) + foreach (var led in Device.Leds.ToList()) { Execute.OnUIThreadSync(() => Leds.Add(new ProfileLedViewModel(led))); if (index % 5 == 0) diff --git a/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileLedView.xaml b/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileLedView.xaml index d4abe3b4c..fe127e10f 100644 --- a/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileLedView.xaml +++ b/src/Artemis.UI/Screens/Module/ProfileEditor/Visualization/ProfileLedView.xaml @@ -1,57 +1,60 @@ - + + - + + ImageSource="{Binding Led.RgbLed.Image, Converter={StaticResource NullToImageConverter}, Mode=OneWay}" /> - + - + +