mirror of
https://github.com/Artemis-RGB/Artemis
synced 2026-11-12 11:56:30 +00:00
Core - Streamlined public parts of profile creation
UI - Started adjusting the VMs for the layer refactor
This commit is contained in:
1 parent
12ac50226f
commit
3e75f200f4
58 files changed
+694
-1196
No files matched your search
-36
@@ -1,36 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Artemis.Core;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Abstract
|
||||
{
|
||||
public abstract class LayerPropertyBaseViewModel : PropertyChangedBase, IDisposable
|
||||
{
|
||||
private BindableCollection<LayerPropertyBaseViewModel> _children;
|
||||
private bool _isExpanded;
|
||||
|
||||
protected LayerPropertyBaseViewModel()
|
||||
{
|
||||
Children = new BindableCollection<LayerPropertyBaseViewModel>();
|
||||
}
|
||||
|
||||
public abstract bool IsVisible { get; }
|
||||
|
||||
public virtual bool IsExpanded
|
||||
{
|
||||
get => _isExpanded;
|
||||
set => SetAndNotify(ref _isExpanded, value);
|
||||
}
|
||||
|
||||
public BindableCollection<LayerPropertyBaseViewModel> Children
|
||||
{
|
||||
get => _children;
|
||||
set => SetAndNotify(ref _children, value);
|
||||
}
|
||||
|
||||
public abstract void Dispose();
|
||||
|
||||
public abstract List<BaseLayerPropertyKeyframe> GetKeyframes(bool expandedOnly);
|
||||
}
|
||||
}
|
||||
+9
-19
@@ -9,32 +9,22 @@ using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.LayerEffects
|
||||
{
|
||||
public class EffectsViewModel : PropertyChangedBase
|
||||
public class EffectsViewModel : Conductor<LayerEffectDescriptor>.Collection.AllActive
|
||||
{
|
||||
private readonly IPluginService _pluginService;
|
||||
private readonly IProfileEditorService _profileEditorService;
|
||||
private readonly IRenderElementService _renderElementService;
|
||||
private BindableCollection<LayerEffectDescriptor> _layerEffectDescriptors;
|
||||
private LayerEffectDescriptor _selectedLayerEffectDescriptor;
|
||||
|
||||
public EffectsViewModel(LayerPropertiesViewModel layerPropertiesViewModel, IPluginService pluginService, IRenderElementService renderElementService, IProfileEditorService profileEditorService)
|
||||
public EffectsViewModel(LayerPropertiesViewModel layerPropertiesViewModel, IPluginService pluginService, IProfileEditorService profileEditorService)
|
||||
{
|
||||
_pluginService = pluginService;
|
||||
_renderElementService = renderElementService;
|
||||
_profileEditorService = profileEditorService;
|
||||
LayerPropertiesViewModel = layerPropertiesViewModel;
|
||||
LayerEffectDescriptors = new BindableCollection<LayerEffectDescriptor>();
|
||||
PropertyChanged += HandleSelectedLayerEffectChanged;
|
||||
}
|
||||
|
||||
public LayerPropertiesViewModel LayerPropertiesViewModel { get; }
|
||||
public bool HasLayerEffectDescriptors => LayerEffectDescriptors.Any();
|
||||
|
||||
public BindableCollection<LayerEffectDescriptor> LayerEffectDescriptors
|
||||
{
|
||||
get => _layerEffectDescriptors;
|
||||
set => SetAndNotify(ref _layerEffectDescriptors, value);
|
||||
}
|
||||
public bool HasLayerEffectDescriptors => Items.Any();
|
||||
|
||||
public LayerEffectDescriptor SelectedLayerEffectDescriptor
|
||||
{
|
||||
@@ -46,15 +36,15 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.LayerEffects
|
||||
{
|
||||
var layerBrushProviders = _pluginService.GetPluginsOfType<LayerEffectProvider>();
|
||||
var descriptors = layerBrushProviders.SelectMany(l => l.LayerEffectDescriptors).ToList();
|
||||
LayerEffectDescriptors.AddRange(descriptors.Except(LayerEffectDescriptors));
|
||||
LayerEffectDescriptors.RemoveRange(LayerEffectDescriptors.Except(descriptors));
|
||||
Items.AddRange(descriptors.Except(Items));
|
||||
Items.RemoveRange(Items.Except(descriptors));
|
||||
|
||||
// Sort by display name
|
||||
var index = 0;
|
||||
foreach (var layerEffectDescriptor in LayerEffectDescriptors.OrderBy(d => d.DisplayName).ToList())
|
||||
foreach (var layerEffectDescriptor in Items.OrderBy(d => d.DisplayName).ToList())
|
||||
{
|
||||
if (LayerEffectDescriptors.IndexOf(layerEffectDescriptor) != index)
|
||||
LayerEffectDescriptors.Move(LayerEffectDescriptors.IndexOf(layerEffectDescriptor), index);
|
||||
if (Items.IndexOf(layerEffectDescriptor) != index)
|
||||
((BindableCollection<LayerEffectDescriptor>) Items).Move(Items.IndexOf(layerEffectDescriptor), index);
|
||||
index++;
|
||||
}
|
||||
|
||||
@@ -78,7 +68,7 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.LayerEffects
|
||||
Execute.PostToUIThread(async () =>
|
||||
{
|
||||
await Task.Delay(500);
|
||||
_renderElementService.AddLayerEffect(renderElement, SelectedLayerEffectDescriptor);
|
||||
renderElement.AddLayerEffect(SelectedLayerEffectDescriptor);
|
||||
_profileEditorService.UpdateSelectedProfileElement();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -16,11 +16,10 @@ using Artemis.UI.Shared;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using GongSolutions.Wpf.DragDrop;
|
||||
using Stylet;
|
||||
using static Artemis.UI.Screens.ProfileEditor.LayerProperties.LayerPropertyGroupViewModel.ViewModelType;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
{
|
||||
public class LayerPropertiesViewModel : ProfileEditorPanelViewModel, IDropTarget
|
||||
public class LayerPropertiesViewModel : Conductor<IScreen>.Collection.AllActive, IProfileEditorPanelViewModel, IDropTarget
|
||||
{
|
||||
private readonly ILayerPropertyVmFactory _layerPropertyVmFactory;
|
||||
private readonly IDataBindingsVmFactory _dataBindingsVmFactory;
|
||||
|
||||
+23
-143
@@ -1,58 +1,31 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Artemis.Core;
|
||||
using Artemis.UI.Ninject.Factories;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Abstract;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Timeline;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using Humanizer;
|
||||
using Ninject;
|
||||
using Ninject.Parameters;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
{
|
||||
public class LayerPropertyGroupViewModel : LayerPropertyBaseViewModel
|
||||
public class LayerPropertyGroupViewModel : PropertyChangedBase, IDisposable
|
||||
{
|
||||
private readonly ILayerPropertyVmFactory _layerPropertyVmFactory;
|
||||
private ViewModelType _groupType;
|
||||
private TimelinePropertyGroupViewModel _timelinePropertyGroupViewModel;
|
||||
private TreePropertyGroupViewModel _treePropertyGroupViewModel;
|
||||
|
||||
public LayerPropertyGroupViewModel(LayerPropertyGroup layerPropertyGroup, PropertyGroupDescriptionAttribute propertyGroupDescription,
|
||||
IProfileEditorService profileEditorService, ILayerPropertyVmFactory layerPropertyVmFactory)
|
||||
public LayerPropertyGroupViewModel(LayerPropertyGroup layerPropertyGroup, ILayerPropertyVmFactory layerPropertyVmFactory)
|
||||
{
|
||||
_layerPropertyVmFactory = layerPropertyVmFactory;
|
||||
ProfileEditorService = profileEditorService;
|
||||
|
||||
LayerPropertyGroup = layerPropertyGroup;
|
||||
PropertyGroupDescription = propertyGroupDescription;
|
||||
|
||||
TreePropertyGroupViewModel = _layerPropertyVmFactory.TreePropertyGroupViewModel(this);
|
||||
TimelinePropertyGroupViewModel = _layerPropertyVmFactory.TimelinePropertyGroupViewModel(this);
|
||||
|
||||
// Generate a fallback name if the description does not contain one
|
||||
if (PropertyGroupDescription.Name == null)
|
||||
{
|
||||
var propertyInfo = LayerPropertyGroup.Parent?.GetType().GetProperties().FirstOrDefault(p => ReferenceEquals(p.GetValue(LayerPropertyGroup.Parent), LayerPropertyGroup));
|
||||
if (propertyInfo != null)
|
||||
PropertyGroupDescription.Name = propertyInfo.Name.Humanize();
|
||||
else
|
||||
PropertyGroupDescription.Name = "Unknown group";
|
||||
}
|
||||
|
||||
LayerPropertyGroup.VisibilityChanged += LayerPropertyGroupOnVisibilityChanged;
|
||||
LayerPropertyGroupTreeViewModel = layerPropertyVmFactory.LayerPropertyGroupTreeViewModel(this);
|
||||
PopulateChildren();
|
||||
DetermineType();
|
||||
}
|
||||
|
||||
public override bool IsVisible => !LayerPropertyGroup.IsHidden;
|
||||
public IProfileEditorService ProfileEditorService { get; }
|
||||
public LayerPropertyGroup LayerPropertyGroup { get; }
|
||||
public PropertyGroupDescriptionAttribute PropertyGroupDescription { get; }
|
||||
public LayerPropertyGroupTreeViewModel LayerPropertyGroupTreeViewModel { get; }
|
||||
public BindableCollection<PropertyChangedBase> Children { get; set; }
|
||||
|
||||
public override bool IsExpanded
|
||||
public bool IsVisible => !LayerPropertyGroup.IsHidden;
|
||||
|
||||
public bool IsExpanded
|
||||
{
|
||||
get => LayerPropertyGroup.ProfileElement.IsPropertyGroupExpanded(LayerPropertyGroup);
|
||||
set
|
||||
@@ -62,81 +35,10 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
}
|
||||
}
|
||||
|
||||
public ViewModelType GroupType
|
||||
{
|
||||
get => _groupType;
|
||||
set => SetAndNotify(ref _groupType, value);
|
||||
}
|
||||
|
||||
public TreePropertyGroupViewModel TreePropertyGroupViewModel
|
||||
{
|
||||
get => _treePropertyGroupViewModel;
|
||||
set => SetAndNotify(ref _treePropertyGroupViewModel, value);
|
||||
}
|
||||
|
||||
public TimelinePropertyGroupViewModel TimelinePropertyGroupViewModel
|
||||
{
|
||||
get => _timelinePropertyGroupViewModel;
|
||||
set => SetAndNotify(ref _timelinePropertyGroupViewModel, value);
|
||||
}
|
||||
|
||||
public override List<BaseLayerPropertyKeyframe> GetKeyframes(bool expandedOnly)
|
||||
{
|
||||
var result = new List<BaseLayerPropertyKeyframe>();
|
||||
if (expandedOnly && !IsExpanded || LayerPropertyGroup.IsHidden)
|
||||
return result;
|
||||
|
||||
foreach (var layerPropertyBaseViewModel in Children)
|
||||
result.AddRange(layerPropertyBaseViewModel.GetKeyframes(expandedOnly));
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public override void Dispose()
|
||||
{
|
||||
foreach (var layerPropertyBaseViewModel in Children)
|
||||
layerPropertyBaseViewModel.Dispose();
|
||||
|
||||
LayerPropertyGroup.VisibilityChanged -= LayerPropertyGroupOnVisibilityChanged;
|
||||
TimelinePropertyGroupViewModel.Dispose();
|
||||
}
|
||||
|
||||
public List<LayerPropertyBaseViewModel> GetAllChildren()
|
||||
{
|
||||
var result = new List<LayerPropertyBaseViewModel>();
|
||||
foreach (var layerPropertyBaseViewModel in Children)
|
||||
{
|
||||
result.Add(layerPropertyBaseViewModel);
|
||||
if (layerPropertyBaseViewModel is LayerPropertyGroupViewModel layerPropertyGroupViewModel)
|
||||
result.AddRange(layerPropertyGroupViewModel.GetAllChildren());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public void UpdateOrder(int order)
|
||||
{
|
||||
LayerPropertyGroup.LayerEffect.Order = order;
|
||||
NotifyOfPropertyChange(nameof(IsExpanded));
|
||||
}
|
||||
|
||||
private void DetermineType()
|
||||
{
|
||||
if (LayerPropertyGroup is LayerGeneralProperties)
|
||||
GroupType = ViewModelType.General;
|
||||
else if (LayerPropertyGroup is LayerTransformProperties)
|
||||
GroupType = ViewModelType.Transform;
|
||||
else if (LayerPropertyGroup.Parent == null && LayerPropertyGroup.LayerBrush != null)
|
||||
GroupType = ViewModelType.LayerBrushRoot;
|
||||
else if (LayerPropertyGroup.Parent == null && LayerPropertyGroup.LayerEffect != null)
|
||||
GroupType = ViewModelType.LayerEffectRoot;
|
||||
else
|
||||
GroupType = ViewModelType.None;
|
||||
}
|
||||
|
||||
private void PopulateChildren()
|
||||
{
|
||||
// Get all properties and property groups and create VMs for them
|
||||
// The group has methods for getting this without reflection but then we lose the order of the properties as they are defined on the group
|
||||
foreach (var propertyInfo in LayerPropertyGroup.GetType().GetProperties())
|
||||
{
|
||||
var propertyAttribute = (PropertyDescriptionAttribute) Attribute.GetCustomAttribute(propertyInfo, typeof(PropertyDescriptionAttribute));
|
||||
@@ -144,50 +46,28 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
var value = propertyInfo.GetValue(LayerPropertyGroup);
|
||||
|
||||
// Create VMs for properties on the group
|
||||
if (propertyAttribute != null && value is BaseLayerProperty baseLayerProperty)
|
||||
if (propertyAttribute != null && value is ILayerProperty layerProperty)
|
||||
{
|
||||
var viewModel = CreateLayerPropertyViewModel(baseLayerProperty, propertyAttribute);
|
||||
if (viewModel != null)
|
||||
Children.Add(viewModel);
|
||||
var layerPropertyViewModel = _layerPropertyVmFactory.LayerPropertyViewModel(layerProperty);
|
||||
// After creation ensure a supported input VM was found, if not, discard the VM
|
||||
if (!layerPropertyViewModel.LayerPropertyTreeViewModel.HasPropertyInputViewModel)
|
||||
layerPropertyViewModel.Dispose();
|
||||
else
|
||||
Children.Add(layerPropertyViewModel);
|
||||
}
|
||||
// Create VMs for child groups on this group, resulting in a nested structure
|
||||
else if (groupAttribute != null && value is LayerPropertyGroup layerPropertyGroup)
|
||||
Children.Add(_layerPropertyVmFactory.LayerPropertyGroupViewModel(layerPropertyGroup, groupAttribute));
|
||||
Children.Add(_layerPropertyVmFactory.LayerPropertyGroupViewModel(layerPropertyGroup));
|
||||
}
|
||||
}
|
||||
|
||||
private LayerPropertyBaseViewModel CreateLayerPropertyViewModel(BaseLayerProperty baseLayerProperty, PropertyDescriptionAttribute propertyDescription)
|
||||
public void Dispose()
|
||||
{
|
||||
// Go through the pain of instantiating a generic type VM now via reflection to make things a lot simpler down the line
|
||||
var genericType = baseLayerProperty.GetType().Name == typeof(LayerProperty<>).Name
|
||||
? baseLayerProperty.GetType().GetGenericArguments()[0]
|
||||
: baseLayerProperty.GetType().BaseType.GetGenericArguments()[0];
|
||||
|
||||
// Only create entries for types supported by a tree input VM
|
||||
if (!genericType.IsEnum && ProfileEditorService.RegisteredPropertyEditors.All(r => r.SupportedType != genericType))
|
||||
return null;
|
||||
var genericViewModel = typeof(LayerPropertyViewModel<>).MakeGenericType(genericType);
|
||||
var parameters = new IParameter[]
|
||||
foreach (var child in Children)
|
||||
{
|
||||
new ConstructorArgument("layerProperty", baseLayerProperty),
|
||||
new ConstructorArgument("propertyDescription", propertyDescription)
|
||||
};
|
||||
|
||||
return (LayerPropertyBaseViewModel) ProfileEditorService.Kernel.Get(genericViewModel, parameters);
|
||||
}
|
||||
|
||||
private void LayerPropertyGroupOnVisibilityChanged(object sender, EventArgs e)
|
||||
{
|
||||
NotifyOfPropertyChange(nameof(IsVisible));
|
||||
}
|
||||
|
||||
public enum ViewModelType
|
||||
{
|
||||
General,
|
||||
Transform,
|
||||
LayerBrushRoot,
|
||||
LayerEffectRoot,
|
||||
None
|
||||
if (child is IDisposable disposableChild)
|
||||
disposableChild.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,141 +1,37 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Artemis.Core;
|
||||
using Artemis.UI.Exceptions;
|
||||
using Artemis.UI.PropertyInput;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Abstract;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Timeline;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree;
|
||||
using Artemis.UI.Shared;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using Humanizer;
|
||||
using Ninject;
|
||||
using Ninject.Parameters;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
{
|
||||
public class LayerPropertyViewModel<T> : LayerPropertyViewModel
|
||||
public class LayerPropertyViewModel : PropertyChangedBase, IDisposable
|
||||
{
|
||||
private TimelinePropertyViewModel<T> _timelinePropertyViewModel;
|
||||
private TreePropertyViewModel<T> _treePropertyViewModel;
|
||||
|
||||
public LayerPropertyViewModel(IProfileEditorService profileEditorService, LayerProperty<T> layerProperty) : base(profileEditorService, layerProperty)
|
||||
public LayerPropertyViewModel(ILayerProperty layerProperty, IKernel kernel)
|
||||
{
|
||||
LayerProperty = layerProperty;
|
||||
|
||||
TreePropertyViewModel = CreateTreePropertyViewModel();
|
||||
TimelinePropertyViewModel = new TimelinePropertyViewModel<T>(this, profileEditorService);
|
||||
var parameter = new ConstructorArgument("layerProperty", LayerProperty);
|
||||
var treeViewModelType = typeof(LayerPropertyTreeViewModel<>).MakeGenericType(layerProperty.GetType().GetGenericArguments());
|
||||
var timelineViewModelType = typeof(LayerPropertyTimelineViewModel<>).MakeGenericType(layerProperty.GetType().GetGenericArguments());
|
||||
|
||||
TreePropertyBaseViewModel = TreePropertyViewModel;
|
||||
TimelinePropertyBaseViewModel = TimelinePropertyViewModel;
|
||||
|
||||
// Generate a fallback name if the description does not contain one
|
||||
if (LayerProperty.PropertyDescription.Name == null)
|
||||
{
|
||||
var propertyInfo = LayerProperty.Parent?.GetType().GetProperties().FirstOrDefault(p => ReferenceEquals(p.GetValue(LayerProperty.Parent), LayerProperty));
|
||||
if (propertyInfo != null)
|
||||
LayerProperty.PropertyDescription.Name = propertyInfo.Name.Humanize();
|
||||
else
|
||||
LayerProperty.PropertyDescription.Name = $"Unknown {typeof(T).Name} property";
|
||||
}
|
||||
|
||||
LayerProperty.VisibilityChanged += LayerPropertyOnVisibilityChanged;
|
||||
LayerPropertyTreeViewModel = (ILayerPropertyTreeViewModel) kernel.Get(treeViewModelType, parameter);
|
||||
LayerPropertyTimelineViewModel = (ILayerPropertyTimelineViewModel) kernel.Get(timelineViewModelType, parameter);
|
||||
}
|
||||
|
||||
public override bool IsVisible => !LayerProperty.IsHidden;
|
||||
public ILayerProperty LayerProperty { get; }
|
||||
public ILayerPropertyTreeViewModel LayerPropertyTreeViewModel { get; }
|
||||
public ILayerPropertyTimelineViewModel LayerPropertyTimelineViewModel { get; }
|
||||
|
||||
public LayerProperty<T> LayerProperty { get; }
|
||||
public bool IsVisible { get; set; }
|
||||
public bool IsExpanded { get; set; }
|
||||
|
||||
public TreePropertyViewModel<T> TreePropertyViewModel
|
||||
public void Dispose()
|
||||
{
|
||||
get => _treePropertyViewModel;
|
||||
set => SetAndNotify(ref _treePropertyViewModel, value);
|
||||
}
|
||||
|
||||
public TimelinePropertyViewModel<T> TimelinePropertyViewModel
|
||||
{
|
||||
get => _timelinePropertyViewModel;
|
||||
set => SetAndNotify(ref _timelinePropertyViewModel, value);
|
||||
}
|
||||
|
||||
public override List<BaseLayerPropertyKeyframe> GetKeyframes(bool expandedOnly)
|
||||
{
|
||||
if (LayerProperty.KeyframesEnabled && !LayerProperty.IsHidden)
|
||||
return LayerProperty.BaseKeyframes.ToList();
|
||||
return new List<BaseLayerPropertyKeyframe>();
|
||||
}
|
||||
|
||||
public override void Dispose()
|
||||
{
|
||||
TreePropertyViewModel.Dispose();
|
||||
TimelinePropertyViewModel.Dispose();
|
||||
|
||||
LayerProperty.VisibilityChanged -= LayerPropertyOnVisibilityChanged;
|
||||
}
|
||||
|
||||
public void SetCurrentValue(T value, bool saveChanges)
|
||||
{
|
||||
LayerProperty.SetCurrentValue(value, ProfileEditorService.CurrentTime);
|
||||
if (saveChanges)
|
||||
ProfileEditorService.UpdateSelectedProfileElement();
|
||||
else
|
||||
ProfileEditorService.UpdateProfilePreview();
|
||||
}
|
||||
|
||||
private TreePropertyViewModel<T> CreateTreePropertyViewModel()
|
||||
{
|
||||
// Make sure there is a supported property editor VM, unless the type is an enum, then we'll use the EnumPropertyInputViewModel
|
||||
Type vmType = null;
|
||||
if (typeof(T).IsEnum)
|
||||
vmType = typeof(EnumPropertyInputViewModel<>).MakeGenericType(typeof(T));
|
||||
else
|
||||
{
|
||||
var registration = ProfileEditorService.RegisteredPropertyEditors.FirstOrDefault(r => r.SupportedType == typeof(T));
|
||||
if (registration != null)
|
||||
vmType = registration.ViewModelType;
|
||||
}
|
||||
|
||||
if (vmType == null)
|
||||
throw new ArtemisUIException($"Cannot create a tree property view model for type {typeof(T)}, found no matching property editor");
|
||||
|
||||
var parameters = new IParameter[]
|
||||
{
|
||||
new ConstructorArgument("layerProperty", LayerProperty)
|
||||
};
|
||||
return new TreePropertyViewModel<T>(this, (PropertyInputViewModel<T>) ProfileEditorService.Kernel.Get(vmType, parameters), ProfileEditorService);
|
||||
}
|
||||
|
||||
private void LayerPropertyOnVisibilityChanged(object sender, EventArgs e)
|
||||
{
|
||||
NotifyOfPropertyChange(nameof(IsVisible));
|
||||
}
|
||||
}
|
||||
|
||||
public abstract class LayerPropertyViewModel : LayerPropertyBaseViewModel
|
||||
{
|
||||
private TimelinePropertyViewModel _timelinePropertyBaseViewModel;
|
||||
private TreePropertyViewModel _treePropertyBaseViewModel;
|
||||
|
||||
protected LayerPropertyViewModel(IProfileEditorService profileEditorService, BaseLayerProperty baseLayerProperty)
|
||||
{
|
||||
ProfileEditorService = profileEditorService;
|
||||
BaseLayerProperty = baseLayerProperty;
|
||||
}
|
||||
|
||||
public IProfileEditorService ProfileEditorService { get; }
|
||||
public BaseLayerProperty BaseLayerProperty { get; }
|
||||
|
||||
public TreePropertyViewModel TreePropertyBaseViewModel
|
||||
{
|
||||
get => _treePropertyBaseViewModel;
|
||||
set => SetAndNotify(ref _treePropertyBaseViewModel, value);
|
||||
}
|
||||
|
||||
public TimelinePropertyViewModel TimelinePropertyBaseViewModel
|
||||
{
|
||||
get => _timelinePropertyBaseViewModel;
|
||||
set => SetAndNotify(ref _timelinePropertyBaseViewModel, value);
|
||||
LayerPropertyTreeViewModel?.Dispose();
|
||||
LayerPropertyTimelineViewModel?.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
+26
@@ -0,0 +1,26 @@
|
||||
using System;
|
||||
using Artemis.Core;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties
|
||||
{
|
||||
public class LayerPropertyTimelineViewModel<T> : Screen, ILayerPropertyTimelineViewModel
|
||||
{
|
||||
public LayerProperty<T> LayerProperty { get; }
|
||||
public LayerPropertyViewModel LayerPropertyViewModel { get; }
|
||||
|
||||
public LayerPropertyTimelineViewModel(LayerProperty<T> layerProperty, LayerPropertyViewModel layerPropertyViewModel)
|
||||
{
|
||||
LayerProperty = layerProperty;
|
||||
LayerPropertyViewModel = layerPropertyViewModel;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
public interface ILayerPropertyTimelineViewModel : IScreen, IDisposable
|
||||
{
|
||||
}
|
||||
}
|
||||
+17
@@ -0,0 +1,17 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Artemis.Core;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Timeline.Rails
|
||||
{
|
||||
public class TimelineGroupViewModel
|
||||
{
|
||||
public LayerPropertyGroup LayerPropertyGroup { get; }
|
||||
|
||||
public TimelineGroupViewModel(LayerPropertyGroup layerPropertyGroup)
|
||||
{
|
||||
LayerPropertyGroup = layerPropertyGroup;
|
||||
}
|
||||
}
|
||||
}
|
||||
+26
-26
@@ -9,7 +9,7 @@
|
||||
xmlns:converters="clr-namespace:Artemis.UI.Converters"
|
||||
xmlns:dd="urn:gong-wpf-dragdrop"
|
||||
mc:Ignorable="d"
|
||||
d:DataContext="{d:DesignInstance local:TreePropertyGroupViewModel}"
|
||||
d:DataContext="{d:DesignInstance local:LayerPropertyGroupTreeViewModel}"
|
||||
d:DesignHeight="450" d:DesignWidth="800">
|
||||
<UserControl.Resources>
|
||||
<converters:NullToVisibilityConverter x:Key="NullToVisibilityConverter" />
|
||||
@@ -18,8 +18,8 @@
|
||||
<!-- Type: None -->
|
||||
<TextBlock
|
||||
dd:DragDrop.DragSourceIgnore="True"
|
||||
Text="{Binding LayerPropertyGroupViewModel.PropertyGroupDescription.Name}"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.PropertyGroupDescription.Description}"
|
||||
Text="{Binding LayerPropertyGroup.GroupDescription.Name}"
|
||||
ToolTip="{Binding LayerPropertyGroup.GroupDescription.Description}"
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Left"
|
||||
Margin="3 5 0 5">
|
||||
@@ -27,7 +27,7 @@
|
||||
<Style TargetType="{x:Type TextBlock}">
|
||||
<Setter Property="Visibility" Value="Collapsed" />
|
||||
<Style.Triggers>
|
||||
<DataTrigger Binding="{Binding LayerPropertyGroupViewModel.GroupType}" Value="None">
|
||||
<DataTrigger Binding="{Binding GroupType}" Value="None">
|
||||
<Setter Property="Visibility" Value="Visible" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
@@ -41,14 +41,14 @@
|
||||
<Style TargetType="{x:Type StackPanel}">
|
||||
<Setter Property="Visibility" Value="Collapsed" />
|
||||
<Style.Triggers>
|
||||
<DataTrigger Binding="{Binding LayerPropertyGroupViewModel.GroupType}" Value="General">
|
||||
<DataTrigger Binding="{Binding GroupType}" Value="General">
|
||||
<Setter Property="Visibility" Value="Visible" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
</Style>
|
||||
</StackPanel.Style>
|
||||
<materialDesign:PackIcon Kind="HammerWrench" Margin="0 -1 5 0" />
|
||||
<TextBlock ToolTip="{Binding LayerPropertyGroupViewModel.PropertyGroupDescription.Description}">General</TextBlock>
|
||||
<TextBlock ToolTip="{Binding LayerPropertyGroup.GroupDescription.Description}">General</TextBlock>
|
||||
</StackPanel>
|
||||
|
||||
<!-- Type: Transform -->
|
||||
@@ -57,14 +57,14 @@
|
||||
<Style TargetType="{x:Type StackPanel}">
|
||||
<Setter Property="Visibility" Value="Collapsed" />
|
||||
<Style.Triggers>
|
||||
<DataTrigger Binding="{Binding LayerPropertyGroupViewModel.GroupType}" Value="Transform">
|
||||
<DataTrigger Binding="{Binding GroupType}" Value="Transform">
|
||||
<Setter Property="Visibility" Value="Visible" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
</Style>
|
||||
</StackPanel.Style>
|
||||
<materialDesign:PackIcon Kind="TransitConnectionVariant" Margin="0 -1 5 0" />
|
||||
<TextBlock ToolTip="{Binding LayerPropertyGroupViewModel.PropertyGroupDescription.Description}">Transform</TextBlock>
|
||||
<TextBlock ToolTip="{Binding LayerPropertyGroup.GroupDescription.Description}">Transform</TextBlock>
|
||||
</StackPanel>
|
||||
|
||||
<!-- Type: LayerBrushRoot -->
|
||||
@@ -79,23 +79,23 @@
|
||||
<Style TargetType="{x:Type Grid}">
|
||||
<Setter Property="Visibility" Value="Collapsed" />
|
||||
<Style.Triggers>
|
||||
<DataTrigger Binding="{Binding LayerPropertyGroupViewModel.GroupType}" Value="LayerBrushRoot">
|
||||
<DataTrigger Binding="{Binding GroupType}" Value="LayerBrushRoot">
|
||||
<Setter Property="Visibility" Value="Visible" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
</Style>
|
||||
</Grid.Style>
|
||||
<materialDesign:PackIcon Grid.Column="0"
|
||||
Kind="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush.Descriptor.Icon}"
|
||||
Kind="{Binding LayerPropertyGroup.LayerBrush.Descriptor.Icon}"
|
||||
Margin="0 5 5 0" />
|
||||
<TextBlock Grid.Column="1"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush.Descriptor.Description}"
|
||||
ToolTip="{Binding LayerPropertyGroup.LayerBrush.Descriptor.Description}"
|
||||
Margin="0 5 0 0">
|
||||
Brush - 
|
||||
</TextBlock>
|
||||
<TextBlock Grid.Column="2"
|
||||
Text="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush.Descriptor.DisplayName}"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush.Descriptor.Description}"
|
||||
Text="{Binding LayerPropertyGroup.LayerBrush.Descriptor.DisplayName}"
|
||||
ToolTip="{Binding LayerPropertyGroup.LayerBrush.Descriptor.Description}"
|
||||
Margin="0 5 0 0" />
|
||||
|
||||
<Button Grid.Column="3"
|
||||
@@ -106,7 +106,7 @@
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Right"
|
||||
Command="{s:Action OpenBrushSettings}"
|
||||
Visibility="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush.ConfigurationDialog, Converter={StaticResource NullToVisibilityConverter}}">
|
||||
Visibility="{Binding LayerPropertyGroup.LayerBrush.ConfigurationDialog, Converter={StaticResource NullToVisibilityConverter}}">
|
||||
<materialDesign:PackIcon Kind="Settings" Height="16" Width="16" />
|
||||
</Button>
|
||||
</Grid>
|
||||
@@ -125,7 +125,7 @@
|
||||
<Style TargetType="{x:Type Grid}">
|
||||
<Setter Property="Visibility" Value="Collapsed" />
|
||||
<Style.Triggers>
|
||||
<DataTrigger Binding="{Binding LayerPropertyGroupViewModel.GroupType}" Value="LayerEffectRoot">
|
||||
<DataTrigger Binding="{Binding GroupType}" Value="LayerEffectRoot">
|
||||
<Setter Property="Visibility" Value="Visible" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
@@ -134,29 +134,29 @@
|
||||
<materialDesign:PackIcon
|
||||
Grid.Column="0"
|
||||
Cursor="SizeNS"
|
||||
Kind="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.Icon}"
|
||||
Kind="{Binding LayerPropertyGroup.LayerEffect.Descriptor.Icon}"
|
||||
Margin="0 5 5 0"
|
||||
Background="Transparent" />
|
||||
<TextBlock Grid.Column="1" ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.Description}" Margin="0 5 0 0">
|
||||
<TextBlock Grid.Column="1" ToolTip="{Binding LayerPropertyGroup.LayerEffect.Descriptor.Description}" Margin="0 5 0 0">
|
||||
Effect
|
||||
</TextBlock>
|
||||
<TextBlock Grid.Column="2"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
ToolTip="{Binding LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
Margin="3 5">
|
||||
-
|
||||
</TextBlock>
|
||||
|
||||
<!-- Show either the descriptors display name or, if set, the effect name -->
|
||||
<TextBlock Grid.Column="3"
|
||||
Text="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.DisplayName}"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
Text="{Binding LayerPropertyGroup.LayerEffect.Descriptor.DisplayName}"
|
||||
ToolTip="{Binding LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
Margin="0 5"
|
||||
Visibility="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Name, Converter={StaticResource NullToVisibilityConverter}, ConverterParameter=Inverted}" />
|
||||
Visibility="{Binding LayerPropertyGroup.LayerEffect.Name, Converter={StaticResource NullToVisibilityConverter}, ConverterParameter=Inverted}" />
|
||||
<TextBlock Grid.Column="4"
|
||||
Text="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Name}"
|
||||
ToolTip="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
Text="{Binding LayerPropertyGroup.LayerEffect.Name}"
|
||||
ToolTip="{Binding LayerPropertyGroup.LayerEffect.Descriptor.Description}"
|
||||
Margin="0 5"
|
||||
Visibility="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Name, Converter={StaticResource NullToVisibilityConverter}}" />
|
||||
Visibility="{Binding LayerPropertyGroup.LayerEffect.Name, Converter={StaticResource NullToVisibilityConverter}}" />
|
||||
|
||||
<StackPanel Grid.Column="5" Orientation="Horizontal">
|
||||
<ToggleButton
|
||||
@@ -164,7 +164,7 @@
|
||||
ToolTip="Toggle enabled state"
|
||||
Width="18"
|
||||
Height="18"
|
||||
IsChecked="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Enabled}"
|
||||
IsChecked="{Binding LayerPropertyGroup.LayerEffect.Enabled}"
|
||||
VerticalAlignment="Center" Padding="-25"
|
||||
Margin="5 0"
|
||||
Command="{s:Action EnableToggled}">
|
||||
@@ -184,7 +184,7 @@
|
||||
Height="24"
|
||||
VerticalAlignment="Center"
|
||||
Command="{s:Action OpenEffectSettings}"
|
||||
Visibility="{Binding LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.ConfigurationDialog, Converter={StaticResource NullToVisibilityConverter}}">
|
||||
Visibility="{Binding LayerPropertyGroup.LayerEffect.ConfigurationDialog, Converter={StaticResource NullToVisibilityConverter}}">
|
||||
<materialDesign:PackIcon Kind="Settings" Height="16" Width="16" />
|
||||
</Button>
|
||||
<Button Style="{StaticResource MaterialDesignIconButton}"
|
||||
+42
-15
@@ -1,13 +1,12 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using Artemis.Core;
|
||||
using Artemis.Core.LayerBrushes;
|
||||
using Artemis.Core.LayerEffects;
|
||||
using Artemis.Core.Services;
|
||||
using Artemis.UI.Exceptions;
|
||||
using Artemis.UI.Screens.ProfileEditor.Dialogs;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Abstract;
|
||||
using Artemis.UI.Screens.ProfileEditor.Windows;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using Ninject;
|
||||
using Ninject.Parameters;
|
||||
@@ -15,34 +14,36 @@ using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
{
|
||||
public class TreePropertyGroupViewModel : PropertyChangedBase
|
||||
public class LayerPropertyGroupTreeViewModel : PropertyChangedBase
|
||||
{
|
||||
private readonly IDialogService _dialogService;
|
||||
private readonly IKernel _kernel;
|
||||
private readonly IProfileEditorService _profileEditorService;
|
||||
private readonly IRenderElementService _renderElementService;
|
||||
private readonly IWindowManager _windowManager;
|
||||
|
||||
public TreePropertyGroupViewModel(LayerPropertyBaseViewModel layerPropertyBaseViewModel,
|
||||
public LayerPropertyGroupTreeViewModel(
|
||||
LayerPropertyGroupViewModel layerPropertyGroupViewModel,
|
||||
IProfileEditorService profileEditorService,
|
||||
IRenderElementService renderElementService,
|
||||
IDialogService dialogService,
|
||||
IWindowManager windowManager,
|
||||
IKernel kernel)
|
||||
{
|
||||
_profileEditorService = profileEditorService;
|
||||
_renderElementService = renderElementService;
|
||||
_dialogService = dialogService;
|
||||
_windowManager = windowManager;
|
||||
_kernel = kernel;
|
||||
LayerPropertyGroupViewModel = (LayerPropertyGroupViewModel) layerPropertyBaseViewModel;
|
||||
|
||||
LayerPropertyGroupViewModel = layerPropertyGroupViewModel;
|
||||
LayerPropertyGroup = LayerPropertyGroupViewModel.LayerPropertyGroup;
|
||||
}
|
||||
|
||||
public LayerPropertyGroupViewModel LayerPropertyGroupViewModel { get; }
|
||||
public LayerPropertyGroup LayerPropertyGroup { get; }
|
||||
public LayerPropertyGroupType GroupType { get; set; }
|
||||
|
||||
public void OpenBrushSettings()
|
||||
{
|
||||
var layerBrush = LayerPropertyGroupViewModel.LayerPropertyGroup.LayerBrush;
|
||||
var layerBrush = LayerPropertyGroup.LayerBrush;
|
||||
var configurationViewModel = layerBrush.ConfigurationDialog;
|
||||
if (configurationViewModel == null)
|
||||
return;
|
||||
@@ -69,7 +70,7 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
|
||||
public void OpenEffectSettings()
|
||||
{
|
||||
var layerEffect = LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect;
|
||||
var layerEffect = LayerPropertyGroup.LayerEffect;
|
||||
var configurationViewModel = layerEffect.ConfigurationDialog;
|
||||
if (configurationViewModel == null)
|
||||
return;
|
||||
@@ -100,20 +101,23 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
new Dictionary<string, object>
|
||||
{
|
||||
{"subject", "effect"},
|
||||
{"currentName", LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Name}
|
||||
{"currentName", LayerPropertyGroup.LayerEffect.Name}
|
||||
}
|
||||
);
|
||||
if (result is string newName)
|
||||
{
|
||||
LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.Name = newName;
|
||||
LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect.HasBeenRenamed = true;
|
||||
LayerPropertyGroup.LayerEffect.Name = newName;
|
||||
LayerPropertyGroup.LayerEffect.HasBeenRenamed = true;
|
||||
_profileEditorService.UpdateSelectedProfile();
|
||||
}
|
||||
}
|
||||
|
||||
public void DeleteEffect()
|
||||
{
|
||||
_renderElementService.RemoveLayerEffect(LayerPropertyGroupViewModel.LayerPropertyGroup.LayerEffect);
|
||||
if (LayerPropertyGroup.LayerEffect == null)
|
||||
return;
|
||||
|
||||
LayerPropertyGroup.ProfileElement.RemoveLayerEffect(LayerPropertyGroup.LayerEffect);
|
||||
_profileEditorService.UpdateSelectedProfile();
|
||||
}
|
||||
|
||||
@@ -121,5 +125,28 @@ namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
{
|
||||
_profileEditorService.UpdateSelectedProfile();
|
||||
}
|
||||
|
||||
private void DetermineGroupType()
|
||||
{
|
||||
if (LayerPropertyGroup is LayerGeneralProperties)
|
||||
GroupType = LayerPropertyGroupType.General;
|
||||
else if (LayerPropertyGroup is LayerTransformProperties)
|
||||
GroupType = LayerPropertyGroupType.Transform;
|
||||
else if (LayerPropertyGroup.Parent == null && LayerPropertyGroup.LayerBrush != null)
|
||||
GroupType = LayerPropertyGroupType.LayerBrushRoot;
|
||||
else if (LayerPropertyGroup.Parent == null && LayerPropertyGroup.LayerEffect != null)
|
||||
GroupType = LayerPropertyGroupType.LayerEffectRoot;
|
||||
else
|
||||
GroupType = LayerPropertyGroupType.None;
|
||||
}
|
||||
|
||||
public enum LayerPropertyGroupType
|
||||
{
|
||||
General,
|
||||
Transform,
|
||||
LayerBrushRoot,
|
||||
LayerEffectRoot,
|
||||
None
|
||||
}
|
||||
}
|
||||
}
|
||||
+6
-8
@@ -1,14 +1,12 @@
|
||||
<UserControl x:Class="Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree.TreePropertyView"
|
||||
<UserControl x:Class="Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree.LayerPropertyTreeView"
|
||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes"
|
||||
xmlns:s="https://github.com/canton7/Stylet"
|
||||
xmlns:tree="clr-namespace:Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree"
|
||||
mc:Ignorable="d"
|
||||
d:DesignHeight="450" d:DesignWidth="800"
|
||||
d:DataContext="{d:DesignInstance {x:Type tree:TreePropertyViewModel}}">
|
||||
d:DesignHeight="450" d:DesignWidth="800">
|
||||
<Grid Height="22" Margin="-20 0 0 0">
|
||||
<Grid.ColumnDefinitions>
|
||||
<ColumnDefinition Width="Auto" />
|
||||
@@ -22,7 +20,7 @@
|
||||
Width="18"
|
||||
Height="18"
|
||||
IsChecked="{Binding KeyframesEnabled}"
|
||||
IsEnabled="{Binding LayerPropertyViewModel.LayerProperty.KeyframesSupported}"
|
||||
IsEnabled="{Binding LayerProperty.KeyframesSupported}"
|
||||
VerticalAlignment="Center" Padding="-25">
|
||||
<materialDesign:PackIcon Kind="Stopwatch" Height="13" Width="13" />
|
||||
</ToggleButton>
|
||||
@@ -32,8 +30,8 @@
|
||||
Padding="0,0,5,0"
|
||||
VerticalAlignment="Center"
|
||||
TextTrimming="CharacterEllipsis"
|
||||
Text="{Binding LayerPropertyViewModel.LayerProperty.PropertyDescription.Name}"
|
||||
ToolTip="{Binding LayerPropertyViewModel.LayerProperty.PropertyDescription.Description}"
|
||||
Text="{Binding LayerProperty.PropertyDescription.Name}"
|
||||
ToolTip="{Binding LayerProperty.PropertyDescription.Description}"
|
||||
HorizontalAlignment="Left" />
|
||||
|
||||
<ContentControl Grid.Column="2" Margin="20 0" s:View.Model="{Binding PropertyInputViewModel}">
|
||||
@@ -51,7 +49,7 @@
|
||||
Width="20"
|
||||
Height="20"
|
||||
VerticalAlignment="Center"
|
||||
IsEnabled="{Binding LayerPropertyViewModel.LayerProperty.DataBindingsSupported}"
|
||||
IsEnabled="{Binding LayerProperty.DataBindingsSupported}"
|
||||
IsChecked="{Binding DataBindingsOpen}">
|
||||
<materialDesign:PackIcon Kind="VectorLink" Height="13" Width="13" />
|
||||
</ToggleButton>
|
||||
+93
@@ -0,0 +1,93 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using Artemis.Core;
|
||||
using Artemis.UI.Shared;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
{
|
||||
public class LayerPropertyTreeViewModel<T> : Screen, ILayerPropertyTreeViewModel
|
||||
{
|
||||
private readonly IProfileEditorService _profileEditorService;
|
||||
private PropertyInputViewModel<T> _propertyInputViewModel;
|
||||
|
||||
public LayerPropertyTreeViewModel(LayerProperty<T> layerProperty, LayerPropertyViewModel layerPropertyViewModel, IProfileEditorService profileEditorService)
|
||||
{
|
||||
_profileEditorService = profileEditorService;
|
||||
LayerProperty = layerProperty;
|
||||
LayerPropertyViewModel = layerPropertyViewModel;
|
||||
|
||||
PropertyInputViewModel = _profileEditorService.CreatePropertyInputViewModel(LayerProperty);
|
||||
_profileEditorService.SelectedDataBindingChanged += ProfileEditorServiceOnSelectedDataBindingChanged;
|
||||
}
|
||||
|
||||
public LayerProperty<T> LayerProperty { get; }
|
||||
public LayerPropertyViewModel LayerPropertyViewModel { get; }
|
||||
|
||||
public PropertyInputViewModel<T> PropertyInputViewModel
|
||||
{
|
||||
get => _propertyInputViewModel;
|
||||
set => SetAndNotify(ref _propertyInputViewModel, value);
|
||||
}
|
||||
|
||||
public bool HasPropertyInputViewModel => PropertyInputViewModel != null;
|
||||
|
||||
public bool KeyframesEnabled
|
||||
{
|
||||
get => LayerProperty.KeyframesEnabled;
|
||||
set => ApplyKeyframesEnabled(value);
|
||||
}
|
||||
|
||||
public bool DataBindingsOpen
|
||||
{
|
||||
get => _profileEditorService.SelectedDataBinding == LayerProperty;
|
||||
set => _profileEditorService.ChangeSelectedDataBinding(value ? LayerProperty : null);
|
||||
}
|
||||
|
||||
#region IDisposable
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
_propertyInputViewModel?.Dispose();
|
||||
_profileEditorService.SelectedDataBindingChanged -= ProfileEditorServiceOnSelectedDataBindingChanged;
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private void ApplyKeyframesEnabled(bool enable)
|
||||
{
|
||||
// If enabling keyframes for the first time, add a keyframe with the current value at the current position
|
||||
if (enable && !LayerProperty.Keyframes.Any())
|
||||
{
|
||||
LayerProperty.AddKeyframe(new LayerPropertyKeyframe<T>(
|
||||
LayerProperty.CurrentValue,
|
||||
_profileEditorService.CurrentTime,
|
||||
Easings.Functions.Linear,
|
||||
LayerProperty
|
||||
));
|
||||
}
|
||||
// If disabling keyframes, set the base value to the current value
|
||||
else if (!enable && LayerProperty.Keyframes.Any())
|
||||
LayerProperty.BaseValue = LayerProperty.CurrentValue;
|
||||
|
||||
LayerProperty.KeyframesEnabled = enable;
|
||||
|
||||
_profileEditorService.UpdateSelectedProfileElement();
|
||||
}
|
||||
|
||||
#region Event handlers
|
||||
|
||||
private void ProfileEditorServiceOnSelectedDataBindingChanged(object sender, EventArgs e)
|
||||
{
|
||||
NotifyOfPropertyChange(nameof(DataBindingsOpen));
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
|
||||
public interface ILayerPropertyTreeViewModel : IScreen, IDisposable
|
||||
{
|
||||
bool HasPropertyInputViewModel { get; }
|
||||
}
|
||||
}
|
||||
@@ -1,89 +0,0 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using Artemis.Core;
|
||||
using Artemis.UI.Screens.ProfileEditor.LayerProperties.Abstract;
|
||||
using Artemis.UI.Shared;
|
||||
using Artemis.UI.Shared.Services;
|
||||
using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
{
|
||||
public class TreePropertyViewModel<T> : TreePropertyViewModel
|
||||
{
|
||||
private readonly IProfileEditorService _profileEditorService;
|
||||
private PropertyInputViewModel<T> _propertyInputViewModel;
|
||||
|
||||
public TreePropertyViewModel(LayerPropertyBaseViewModel layerPropertyBaseViewModel, PropertyInputViewModel<T> propertyInputViewModel,
|
||||
IProfileEditorService profileEditorService) : base(layerPropertyBaseViewModel)
|
||||
{
|
||||
_profileEditorService = profileEditorService;
|
||||
LayerPropertyViewModel = (LayerPropertyViewModel<T>) layerPropertyBaseViewModel;
|
||||
PropertyInputViewModel = propertyInputViewModel;
|
||||
|
||||
_profileEditorService.SelectedDataBindingChanged += ProfileEditorServiceOnSelectedDataBindingChanged;
|
||||
}
|
||||
|
||||
public LayerPropertyViewModel<T> LayerPropertyViewModel { get; }
|
||||
|
||||
public PropertyInputViewModel<T> PropertyInputViewModel
|
||||
{
|
||||
get => _propertyInputViewModel;
|
||||
set => SetAndNotify(ref _propertyInputViewModel, value);
|
||||
}
|
||||
|
||||
public bool KeyframesEnabled
|
||||
{
|
||||
get => LayerPropertyViewModel.LayerProperty.KeyframesEnabled;
|
||||
set => ApplyKeyframesEnabled(value);
|
||||
}
|
||||
|
||||
public bool DataBindingsOpen
|
||||
{
|
||||
get => _profileEditorService.SelectedDataBinding == LayerPropertyViewModel.BaseLayerProperty;
|
||||
set => _profileEditorService.ChangeSelectedDataBinding(value ? LayerPropertyViewModel.BaseLayerProperty : null);
|
||||
}
|
||||
|
||||
public override void Dispose()
|
||||
{
|
||||
PropertyInputViewModel.Dispose();
|
||||
}
|
||||
|
||||
private void ProfileEditorServiceOnSelectedDataBindingChanged(object sender, EventArgs e)
|
||||
{
|
||||
NotifyOfPropertyChange(nameof(DataBindingsOpen));
|
||||
}
|
||||
|
||||
private void ApplyKeyframesEnabled(bool enable)
|
||||
{
|
||||
// If enabling keyframes for the first time, add a keyframe with the current value at the current position
|
||||
if (enable && !LayerPropertyViewModel.LayerProperty.Keyframes.Any())
|
||||
{
|
||||
LayerPropertyViewModel.LayerProperty.AddKeyframe(new LayerPropertyKeyframe<T>(
|
||||
LayerPropertyViewModel.LayerProperty.CurrentValue,
|
||||
_profileEditorService.CurrentTime,
|
||||
Easings.Functions.Linear,
|
||||
LayerPropertyViewModel.LayerProperty
|
||||
));
|
||||
}
|
||||
// If disabling keyframes, set the base value to the current value
|
||||
else if (!enable && LayerPropertyViewModel.LayerProperty.Keyframes.Any())
|
||||
LayerPropertyViewModel.LayerProperty.BaseValue = LayerPropertyViewModel.LayerProperty.CurrentValue;
|
||||
|
||||
LayerPropertyViewModel.LayerProperty.KeyframesEnabled = enable;
|
||||
|
||||
_profileEditorService.UpdateSelectedProfileElement();
|
||||
}
|
||||
}
|
||||
|
||||
public abstract class TreePropertyViewModel : PropertyChangedBase, IDisposable
|
||||
{
|
||||
protected TreePropertyViewModel(LayerPropertyBaseViewModel layerPropertyBaseViewModel)
|
||||
{
|
||||
LayerPropertyBaseViewModel = layerPropertyBaseViewModel;
|
||||
}
|
||||
|
||||
public LayerPropertyBaseViewModel LayerPropertyBaseViewModel { get; }
|
||||
|
||||
public abstract void Dispose();
|
||||
}
|
||||
}
|
||||
@@ -7,7 +7,7 @@
|
||||
xmlns:converters="clr-namespace:Artemis.UI.Converters"
|
||||
xmlns:dd="urn:gong-wpf-dragdrop"
|
||||
xmlns:tree="clr-namespace:Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree"
|
||||
xmlns:layerProperties1="clr-namespace:Artemis.UI.Screens.ProfileEditor.LayerProperties"
|
||||
xmlns:local="clr-namespace:Artemis.UI.Screens.ProfileEditor.LayerProperties"
|
||||
mc:Ignorable="d"
|
||||
d:DesignHeight="450" d:DesignWidth="800"
|
||||
d:DataContext="{d:DesignInstance {x:Type tree:TreeViewModel}}">
|
||||
@@ -98,11 +98,11 @@
|
||||
</Style>
|
||||
</TreeView.ItemContainerStyle>
|
||||
<TreeView.Resources>
|
||||
<HierarchicalDataTemplate DataType="{x:Type layerProperties1:LayerPropertyGroupViewModel}" ItemsSource="{Binding Children}">
|
||||
<ContentControl s:View.Model="{Binding TreePropertyGroupViewModel}" />
|
||||
<HierarchicalDataTemplate DataType="{x:Type local:LayerPropertyGroupViewModel}" ItemsSource="{Binding Items}">
|
||||
<ContentControl s:View.Model="{Binding LayerPropertyGroupTreeViewModel}" />
|
||||
</HierarchicalDataTemplate>
|
||||
<DataTemplate DataType="{x:Type layerProperties1:LayerPropertyViewModel}">
|
||||
<ContentControl s:View.Model="{Binding TreePropertyBaseViewModel}" dd:DragDrop.DragSourceIgnore="True" />
|
||||
<DataTemplate DataType="{x:Type local:LayerPropertyViewModel}">
|
||||
<ContentControl s:View.Model="{Binding LayerPropertyTreeViewModel}" dd:DragDrop.DragSourceIgnore="True" />
|
||||
</DataTemplate>
|
||||
</TreeView.Resources>
|
||||
</TreeView>
|
||||
|
||||
@@ -5,11 +5,13 @@ using Stylet;
|
||||
|
||||
namespace Artemis.UI.Screens.ProfileEditor.LayerProperties.Tree
|
||||
{
|
||||
public class TreeViewModel : PropertyChangedBase
|
||||
public class TreeViewModel : Screen
|
||||
{
|
||||
public TreeViewModel(LayerPropertiesViewModel layerPropertiesViewModel, BindableCollection<LayerPropertyGroupViewModel> layerPropertyGroups)
|
||||
{
|
||||
LayerPropertiesViewModel = layerPropertiesViewModel;
|
||||
|
||||
// Not using the Items collection because the list should persist even after this VM gets closed
|
||||
LayerPropertyGroups = layerPropertyGroups;
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user