FIL-4 Completed refactoring of Sections to ItemFilterCommentBlocks

This commit is contained in:
Ben Wallis 2017-06-17 12:19:54 +01:00
parent 43c6149832
commit b65fad0679
32 changed files with 518 additions and 275 deletions

View File

@ -117,7 +117,6 @@
<None Include="packages.config" />
<None Include="Resources\MuldiniFilterScript.txt" />
</ItemGroup>
<Import Project="$(VSToolsPath)\TeamTest\Microsoft.TestTools.targets" Condition="Exists('$(VSToolsPath)\TeamTest\Microsoft.TestTools.targets')" />
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets.

View File

@ -6,7 +6,6 @@ using System.Xml.Serialization;
using Filtration.ObjectModel;
using Filtration.ObjectModel.Enums;
using NUnit.Framework;
using YamlDotNet.Serialization;
namespace Filtration.ItemFilterPreview.Tests.Services
{
@ -40,7 +39,6 @@ namespace Filtration.ItemFilterPreview.Tests.Services
output = textWriter.ToString();
}
var x = 2;
//Assert
}
}

View File

@ -32,7 +32,6 @@ namespace Filtration.ItemFilterPreview.Services
var matchedBlock = itemFilterScript.ItemFilterBlocks
.OfType<IItemFilterBlock>()
.Where(b => !(b is ItemFilterSection))
.FirstOrDefault(block => _blockItemMatcher.ItemBlockMatch(block, item));
filteredItems.Add(new FilteredItem(item, matchedBlock));

View File

@ -85,7 +85,6 @@
<Compile Include="ItemFilterBlockGroup.cs" />
<Compile Include="ItemFilterScript.cs" />
<Compile Include="ItemFilterScriptSettings.cs" />
<Compile Include="ItemFilterSection.cs" />
<Compile Include="ItemSet.cs" />
<Compile Include="NumericFilterPredicate.cs" />
<Compile Include="PathOfExileNamedColors.cs" />

View File

@ -37,13 +37,11 @@ namespace Filtration.ObjectModel
public interface IItemFilterCommentBlock : IItemFilterBlockBase
{
string Comment { get; set; }
bool IsSection { get; set; }
}
public class ItemFilterCommentBlock : ItemFilterBlockBase, IItemFilterCommentBlock
{
public string Comment { get; set; }
public bool IsSection { get; set; }
}
public class ItemFilterBlock : ItemFilterBlockBase, IItemFilterBlock

View File

@ -81,15 +81,9 @@ namespace Filtration.ObjectModel
private bool BlockIsColorReplacementCandidate(ReplaceColorsParameterSet replaceColorsParameterSet, IItemFilterBlock block)
{
var textColorItem = block.HasBlockItemOfType<TextColorBlockItem>()
? block.BlockItems.OfType<TextColorBlockItem>().First()
: null;
var backgroundColorItem = block.HasBlockItemOfType<BackgroundColorBlockItem>()
? block.BlockItems.OfType<BackgroundColorBlockItem>().First()
: null;
var borderColorItem = block.HasBlockItemOfType<BorderColorBlockItem>()
? block.BlockItems.OfType<BorderColorBlockItem>().First()
: null;
var textColorItem = block.BlockItems.OfType<TextColorBlockItem>().FirstOrDefault();
var backgroundColorItem = block.BlockItems.OfType<BackgroundColorBlockItem>().FirstOrDefault();
var borderColorItem = block.BlockItems.OfType<BorderColorBlockItem>().FirstOrDefault();
// If we don't have all of the things we want to replace, then we aren't a candidate for replacing those things.
if ((textColorItem == null && replaceColorsParameterSet.ReplaceTextColor) ||

View File

@ -1,6 +0,0 @@
namespace Filtration.ObjectModel
{
public class ItemFilterSection : ItemFilterBlock
{
}
}

View File

@ -9,5 +9,7 @@ namespace Filtration.Parser.Interface.Services
string TranslateItemFilterBlockToString(IItemFilterBlock block);
void ReplaceAudioVisualBlockItemsFromString(ObservableCollection<IItemFilterBlockItem> blockItems, string inputString);
IItemFilterCommentBlock TranslateStringToItemFilterCommentBlock(string inputString);
string TranslateItemFilterCommentBlockToString(IItemFilterCommentBlock itemFilterCommentBlock);
string TranslateItemFilterBlockBaseToString(IItemFilterBlockBase itemFilterBlockBase);
}
}

View File

@ -442,16 +442,31 @@ namespace Filtration.Parser.Services
return new Color();
}
// This method converts an ItemFilterBlock object into a string. This is used for copying a ItemFilterBlock
// to the clipboard, and when saving a ItemFilterScript.
public string TranslateItemFilterBlockToString(IItemFilterBlock block)
public string TranslateItemFilterBlockBaseToString(IItemFilterBlockBase itemFilterBlockBase)
{
// TODO: fix
if (block.GetType() == typeof (ItemFilterCommentBlock))
{
return "# Section: " + block.Description;
var itemFilterBlock = itemFilterBlockBase as IItemFilterBlock;
if (itemFilterBlock != null) return TranslateItemFilterBlockToString(itemFilterBlock);
var itemFilterCommentBlock = itemFilterBlockBase as IItemFilterCommentBlock;
if (itemFilterCommentBlock != null) return TranslateItemFilterCommentBlockToString(itemFilterCommentBlock);
throw new InvalidOperationException("Unable to translate unknown ItemFilterBlock type");
}
// TODO: Private
public string TranslateItemFilterCommentBlockToString(IItemFilterCommentBlock itemFilterCommentBlock)
{
// TODO: Handle multi-line
// TODO: Tests
// TODO: # Section: text?
return $"#{itemFilterCommentBlock.Comment}";
}
// This method converts an ItemFilterBlock object into a string. This is used for copying a ItemFilterBlock
// to the clipboard, and when saving a ItemFilterScript.
// TODO: Private
public string TranslateItemFilterBlockToString(IItemFilterBlock block)
{
var outputString = string.Empty;
if (!block.Enabled)

View File

@ -45,6 +45,9 @@
<converters:BooleanToBlockActionInverseConverter x:Key="BooleanToBlockActionInverseConverter" />
<converters:AvailableThemeComponentsConverter x:Key="AvailableThemeComponentsConverter" />
</ResourceDictionary>
<ResourceDictionary>
<RoutedCommand x:Key="OpenScriptRoutedCommand" />
</ResourceDictionary>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>

View File

@ -181,7 +181,10 @@
<Compile Include="UserControls\ThemeComponentSelectionControl.xaml.cs">
<DependentUpon>ThemeComponentSelectionControl.xaml</DependentUpon>
</Compile>
<Compile Include="Utility\RoutedCommandHandler.cs" />
<Compile Include="Utility\RoutedCommandHandlers.cs" />
<Compile Include="ViewModels\AvalonDockWorkspaceViewModel.cs" />
<Compile Include="ViewModels\IItemFilterCommentBlockViewModelFactory.cs" />
<Compile Include="ViewModels\SettingsPageViewModel.cs" />
<Compile Include="ViewModels\ToolPanes\BlockGroupBrowserViewModel.cs" />
<Compile Include="ViewModels\IItemFilterScriptViewModelFactory.cs" />
@ -191,7 +194,7 @@
<Compile Include="ViewModels\ItemFilterScriptViewModel.cs" />
<Compile Include="ViewModels\ToolPanes\BlockOutputPreviewViewModel.cs" />
<Compile Include="ViewModels\ReplaceColorsViewModel.cs" />
<Compile Include="ViewModels\ToolPanes\SectionBrowserViewModel.cs" />
<Compile Include="ViewModels\ToolPanes\CommentBlockBrowserViewModel.cs" />
<Compile Include="ViewModels\StartPageViewModel.cs" />
<Compile Include="ViewModels\ToolPanes\ToolViewModel.cs" />
<Compile Include="ViewModels\UpdateAvailableViewModel.cs" />
@ -220,7 +223,6 @@
<Compile Include="Views\ToolPanes\BlockGroupBrowserView.xaml.cs">
<DependentUpon>BlockGroupBrowserView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\BlockTemplateSelector.cs" />
<Compile Include="Views\ItemFilterScriptView.xaml.cs">
<DependentUpon>ItemFilterScriptView.xaml</DependentUpon>
</Compile>
@ -230,8 +232,8 @@
<Compile Include="UserControls\NumericFilterPredicateControl.xaml.cs">
<DependentUpon>NumericFilterPredicateControl.xaml</DependentUpon>
</Compile>
<Compile Include="Views\ItemFilterSectionView.xaml.cs">
<DependentUpon>ItemFilterSectionView.xaml</DependentUpon>
<Compile Include="Views\ItemFilterCommentBlockView.xaml.cs">
<DependentUpon>ItemFilterCommentBlockView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\AboutWindow.xaml.cs">
<DependentUpon>AboutWindow.xaml</DependentUpon>
@ -245,8 +247,8 @@
<Compile Include="Views\ToolPanes\BlockOutputPreviewView.xaml.cs">
<DependentUpon>BlockOutputPreviewView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\ToolPanes\SectionBrowserView.xaml.cs">
<DependentUpon>SectionBrowserView.xaml</DependentUpon>
<Compile Include="Views\ToolPanes\CommentBlockBrowserView.xaml.cs">
<DependentUpon>CommentBlockBrowserView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\StartPageView.xaml.cs">
<DependentUpon>StartPageView.xaml</DependentUpon>
@ -310,7 +312,7 @@
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Views\ToolPanes\SectionBrowserView.xaml">
<Page Include="Views\ToolPanes\CommentBlockBrowserView.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
@ -322,7 +324,7 @@
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Views\ItemFilterSectionView.xaml">
<Page Include="Views\ItemFilterCommentBlockView.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
@ -510,9 +512,7 @@
<Name>Filtration.ThemeEditor</Name>
</ProjectReference>
</ItemGroup>
<ItemGroup>
<Folder Include="Translators\" />
</ItemGroup>
<ItemGroup />
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="$(XamlSpyInstallPath)MSBuild\FirstFloor.XamlSpy.WPF.targets" Condition="'$(XamlSpyInstallPath)' != '' and '$(Configuration)' == 'DEBUG'" />
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.

View File

@ -0,0 +1,73 @@
using System.Windows;
using System.Windows.Input;
namespace Filtration.Utility
{
/// <summary>
/// Allows associated a routed command with a non-routed command. Used by
/// <see cref="RoutedCommandHandlers"/>.
/// </summary>
public class RoutedCommandHandler : Freezable
{
public static readonly DependencyProperty CommandProperty = DependencyProperty.Register(
"Command",
typeof(ICommand),
typeof(RoutedCommandHandler),
new PropertyMetadata(default(ICommand)));
/// <summary> The command that should be executed when the RoutedCommand fires. </summary>
public ICommand Command
{
get => (ICommand)GetValue(CommandProperty);
set => SetValue(CommandProperty, value);
}
public static readonly DependencyProperty IsActiveProperty = DependencyProperty.Register(
"IsActive", typeof(bool), typeof(RoutedCommandHandler), new PropertyMetadata(default(bool)));
public bool IsActive
{
get { return (bool) GetValue(IsActiveProperty); }
set { SetValue(IsActiveProperty, value); }
}
/// <summary> The command that triggers <see cref="ICommand"/>. </summary>
public ICommand RoutedCommand { get; set; }
/// <inheritdoc />
protected override Freezable CreateInstanceCore()
{
return new RoutedCommandHandler();
}
/// <summary>
/// Register this handler to respond to the registered RoutedCommand for the
/// given element.
/// </summary>
/// <param name="owner"> The element for which we should register the command
/// binding for the current routed command. </param>
internal void Register(FrameworkElement owner)
{
var binding = new CommandBinding(RoutedCommand, HandleExecuted, HandleCanExecute);
owner.CommandBindings.Add(binding);
}
/// <summary> Proxy to the current Command.CanExecute(object). </summary>
private void HandleCanExecute(object sender, CanExecuteRoutedEventArgs e)
{
if (!IsActive) return;
e.CanExecute = Command?.CanExecute(e.Parameter) != null;
e.Handled = true;
}
/// <summary> Proxy to the current Command.Execute(object). </summary>
private void HandleExecuted(object sender, ExecutedRoutedEventArgs e)
{
if (!IsActive) return;
Command?.Execute(e.Parameter);
e.Handled = true;
}
}
}

View File

@ -0,0 +1,79 @@
using System.Collections;
using System.Collections.Specialized;
using System.Windows;
namespace Filtration.Utility
{
/// <summary>
/// Holds a collection of <see cref="RoutedCommandHandler"/> that should be
/// turned into CommandBindings.
/// </summary>
public class RoutedCommandHandlers : FreezableCollection<RoutedCommandHandler>
{
/// <summary>
/// Hide this from WPF so that it's forced to go through
/// <see cref="GetCommands"/> and we can auto-create the collection
/// if it doesn't already exist. This isn't strictly necessary but it makes
/// the XAML much nicer.
/// </summary>
private static readonly DependencyProperty CommandsProperty = DependencyProperty.RegisterAttached(
"CommandsPrivate",
typeof(RoutedCommandHandlers),
typeof(RoutedCommandHandlers),
new PropertyMetadata(default(RoutedCommandHandlers)));
/// <summary>
/// Gets the collection of RoutedCommandHandler for a given element, creating
/// it if it doesn't already exist.
/// </summary>
public static RoutedCommandHandlers GetCommands(FrameworkElement element)
{
RoutedCommandHandlers handlers = (RoutedCommandHandlers)element.GetValue(CommandsProperty);
if (handlers == null)
{
handlers = new RoutedCommandHandlers(element);
element.SetValue(CommandsProperty, handlers);
}
return handlers;
}
private readonly FrameworkElement _owner;
/// <summary> Each collection is tied to a specific element. </summary>
/// <param name="owner"> The element for which this collection is created. </param>
public RoutedCommandHandlers(FrameworkElement owner)
{
_owner = owner;
// because we auto-create the collection, we don't know when items will be
// added. So, we observe ourself for changes manually.
var self = (INotifyCollectionChanged)this;
self.CollectionChanged += (sender, args) =>
{
// note this does not handle deletions, that's left as an exercise for the
// reader, but most of the time, that's not needed!
((RoutedCommandHandlers)sender).HandleAdditions(args.NewItems);
};
}
/// <summary> Invoked when new items are added to the collection. </summary>
/// <param name="newItems"> The new items that were added. </param>
private void HandleAdditions(IList newItems)
{
if (newItems == null)
return;
foreach (RoutedCommandHandler routedHandler in newItems)
{
routedHandler.Register(_owner);
}
}
/// <inheritdoc />
protected override Freezable CreateInstanceCore()
{
return new RoutedCommandHandlers(_owner);
}
}
}

View File

@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Windows;
using Filtration.Common.ViewModels;
using Filtration.Interface;
using Filtration.ThemeEditor.ViewModels;
@ -18,7 +19,7 @@ namespace Filtration.ViewModels
ReadOnlyObservableCollection<IDocument> OpenDocuments { get; }
IItemFilterScriptViewModel ActiveScriptViewModel { get; }
IThemeEditorViewModel ActiveThemeViewModel { get; }
ISectionBrowserViewModel SectionBrowserViewModel { get; }
ICommentBlockBrowserViewModel CommentBlockBrowserViewModel { get; }
IBlockGroupBrowserViewModel BlockGroupBrowserViewModel { get; }
IBlockOutputPreviewViewModel BlockOutputPreviewViewModel { get; }
void AddDocument(IDocument document);
@ -29,7 +30,7 @@ namespace Filtration.ViewModels
internal class AvalonDockWorkspaceViewModel : ViewModelBase, IAvalonDockWorkspaceViewModel
{
private readonly ISectionBrowserViewModel _sectionBrowserViewModel;
private readonly ICommentBlockBrowserViewModel _commentBlockBrowserViewModel;
private readonly IBlockGroupBrowserViewModel _blockGroupBrowserViewModel;
private readonly IBlockOutputPreviewViewModel _blockOutputPreviewViewModel;
@ -38,16 +39,16 @@ namespace Filtration.ViewModels
private IThemeEditorViewModel _activeThemeViewModel;
private readonly ObservableCollection<IDocument> _openDocuments;
public AvalonDockWorkspaceViewModel(ISectionBrowserViewModel sectionBrowserViewModel,
public AvalonDockWorkspaceViewModel(ICommentBlockBrowserViewModel commentBlockBrowserViewModel,
IBlockGroupBrowserViewModel blockGroupBrowserViewModel,
IStartPageViewModel startPageViewModel,
IBlockOutputPreviewViewModel blockOutputPreviewViewModel)
{
_sectionBrowserViewModel = sectionBrowserViewModel;
_commentBlockBrowserViewModel = commentBlockBrowserViewModel;
_blockGroupBrowserViewModel = blockGroupBrowserViewModel;
_blockOutputPreviewViewModel = blockOutputPreviewViewModel;
_sectionBrowserViewModel.Initialise(this);
_commentBlockBrowserViewModel.Initialise(this);
_blockGroupBrowserViewModel.Initialise(this);
_blockOutputPreviewViewModel.Initialise(this);
@ -94,13 +95,13 @@ namespace Filtration.ViewModels
public IThemeEditorViewModel ActiveThemeViewModel => _activeThemeViewModel;
public IBlockGroupBrowserViewModel BlockGroupBrowserViewModel => _blockGroupBrowserViewModel;
public IBlockOutputPreviewViewModel BlockOutputPreviewViewModel => _blockOutputPreviewViewModel;
public ISectionBrowserViewModel SectionBrowserViewModel => _sectionBrowserViewModel;
public ICommentBlockBrowserViewModel CommentBlockBrowserViewModel => _commentBlockBrowserViewModel;
private List<IToolViewModel> _tools;
public IEnumerable<IToolViewModel> Tools => _tools ?? (_tools = new List<IToolViewModel>
{
_sectionBrowserViewModel,
_commentBlockBrowserViewModel,
_blockGroupBrowserViewModel,
_blockOutputPreviewViewModel
});
@ -116,7 +117,7 @@ namespace Filtration.ViewModels
_activeThemeViewModel = (IThemeEditorViewModel) document;
}
_openDocuments.Add(document);
Application.Current.Dispatcher.Invoke(() => _openDocuments.Add(document));
ActiveDocument = document;
}
@ -129,7 +130,7 @@ namespace Filtration.ViewModels
if (document.IsScript && ActiveDocument == document)
{
_sectionBrowserViewModel.ClearDown();
_commentBlockBrowserViewModel.ClearDown();
_blockGroupBrowserViewModel.ClearDown();
_blockOutputPreviewViewModel.ClearDown();
}

View File

@ -0,0 +1,8 @@
namespace Filtration.ViewModels
{
internal interface IItemFilterCommentBlockViewModelFactory
{
IItemFilterCommentBlockViewModel Create();
void Release(IItemFilterCommentBlockViewModel itemFilterCommentBlockViewModel);
}
}

View File

@ -15,11 +15,9 @@ using Xceed.Wpf.Toolkit;
namespace Filtration.ViewModels
{
internal interface IItemFilterBlockViewModel
internal interface IItemFilterBlockViewModel : IItemFilterBlockViewModelBase
{
event EventHandler BlockBecameDirty;
void Initialise(IItemFilterBlock itemFilterBlock, ItemFilterScriptViewModel parentScriptViewModel);
bool IsDirty { get; set; }
bool IsExpanded { get; set; }
IItemFilterBlock Block { get; }
bool BlockEnabled { get; set; }
@ -27,7 +25,67 @@ namespace Filtration.ViewModels
void RefreshBlockPreview();
}
internal class ItemFilterBlockViewModel : ViewModelBase, IItemFilterBlockViewModel
internal interface IItemFilterBlockViewModelBase
{
IItemFilterBlockBase BaseBlock { get; }
bool IsDirty { get; set; }
event EventHandler BlockBecameDirty;
}
internal abstract class ItemFilterBlockViewModelBase : ViewModelBase, IItemFilterBlockViewModelBase
{
private bool _isDirty;
protected void Initialise(IItemFilterBlockBase itemfilterBlock)
{
BaseBlock = itemfilterBlock;
}
public event EventHandler BlockBecameDirty;
public IItemFilterBlockBase BaseBlock { get; protected set; }
public bool IsDirty
{
get => _isDirty;
set
{
if (value != _isDirty)
{
_isDirty = value;
RaisePropertyChanged();
BlockBecameDirty?.Invoke(this, EventArgs.Empty);
}
}
}
}
internal interface IItemFilterCommentBlockViewModel : IItemFilterBlockViewModelBase
{
void Initialise(IItemFilterCommentBlock itemFilterCommentBlock);
IItemFilterCommentBlock ItemFilterCommentBlock { get; }
string Comment { get; }
}
internal class ItemFilterCommentBlockViewModel : ItemFilterBlockViewModelBase, IItemFilterCommentBlockViewModel
{
public ItemFilterCommentBlockViewModel()
{
}
public void Initialise(IItemFilterCommentBlock itemFilterCommentBlock)
{
ItemFilterCommentBlock = itemFilterCommentBlock;
BaseBlock = itemFilterCommentBlock;
}
public IItemFilterCommentBlock ItemFilterCommentBlock { get; private set; }
public string Comment => ItemFilterCommentBlock.Comment;
}
internal class ItemFilterBlockViewModel : ItemFilterBlockViewModelBase, IItemFilterBlockViewModel
{
private readonly IStaticDataService _staticDataService;
private readonly IReplaceColorsViewModel _replaceColorsViewModel;
@ -37,7 +95,6 @@ namespace Filtration.ViewModels
private bool _displaySettingsPopupOpen;
private bool _isExpanded;
private bool _audioVisualBlockItemsGridVisible;
private bool _isDirty;
public ItemFilterBlockViewModel(IStaticDataService staticDataService, IReplaceColorsViewModel replaceColorsViewModel)
{
@ -63,8 +120,6 @@ namespace Filtration.ViewModels
PlaySoundCommand = new RelayCommand(OnPlaySoundCommand, () => HasSound);
}
public event EventHandler BlockBecameDirty;
public void Initialise(IItemFilterBlock itemFilterBlock, ItemFilterScriptViewModel parentScriptViewModel)
{
if (itemFilterBlock == null || parentScriptViewModel == null)
@ -75,51 +130,42 @@ namespace Filtration.ViewModels
_parentScriptViewModel = parentScriptViewModel;
Block = itemFilterBlock;
itemFilterBlock.BlockItems.CollectionChanged += OnBlockItemsCollectionChanged;
foreach (var blockItem in itemFilterBlock.BlockItems)
{
blockItem.PropertyChanged += OnBlockItemChanged;
}
base.Initialise(itemFilterBlock);
}
public RelayCommand CopyBlockCommand { get; private set; }
public RelayCommand PasteBlockCommand { get; private set; }
public RelayCommand CopyBlockStyleCommand { get; private set; }
public RelayCommand PasteBlockStyleCommand { get; private set; }
public RelayCommand AddBlockCommand { get; private set; }
public RelayCommand AddSectionCommand { get; private set; }
public RelayCommand DeleteBlockCommand { get; private set; }
public RelayCommand MoveBlockUpCommand { get; private set; }
public RelayCommand MoveBlockDownCommand { get; private set; }
public RelayCommand MoveBlockToTopCommand { get; private set; }
public RelayCommand MoveBlockToBottomCommand { get; private set; }
public RelayCommand ToggleBlockActionCommand { get; private set; }
public RelayCommand ReplaceColorsCommand { get; private set; }
public RelayCommand<Type> AddFilterBlockItemCommand { get; private set; }
public RelayCommand<IItemFilterBlockItem> RemoveFilterBlockItemCommand { get; private set; }
public RelayCommand PlaySoundCommand { get; private set; }
public RelayCommand SwitchBlockItemsViewCommand { get; private set; }
public RelayCommand CopyBlockCommand { get; }
public RelayCommand PasteBlockCommand { get; }
public RelayCommand CopyBlockStyleCommand { get; }
public RelayCommand PasteBlockStyleCommand { get; }
public RelayCommand AddBlockCommand { get; }
public RelayCommand AddSectionCommand { get; }
public RelayCommand DeleteBlockCommand { get; }
public RelayCommand MoveBlockUpCommand { get; }
public RelayCommand MoveBlockDownCommand { get; }
public RelayCommand MoveBlockToTopCommand { get; }
public RelayCommand MoveBlockToBottomCommand { get; }
public RelayCommand ToggleBlockActionCommand { get; }
public RelayCommand ReplaceColorsCommand { get; }
public RelayCommand<Type> AddFilterBlockItemCommand { get; }
public RelayCommand<IItemFilterBlockItem> RemoveFilterBlockItemCommand { get; }
public RelayCommand PlaySoundCommand { get; }
public RelayCommand SwitchBlockItemsViewCommand { get; }
public IItemFilterBlock Block { get; private set; }
public bool IsDirty
{
get { return _isDirty; }
set
{
if (value != _isDirty)
{
_isDirty = value;
RaisePropertyChanged();
BlockBecameDirty?.Invoke(this, EventArgs.Empty);
}
}
}
public bool IsExpanded
{
get { return _isExpanded; }
get => _isExpanded;
set
{
_isExpanded = value;

View File

@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Threading.Tasks;
@ -25,9 +26,9 @@ namespace Filtration.ViewModels
internal interface IItemFilterScriptViewModel : IEditableDocument
{
ItemFilterScript Script { get; }
IItemFilterBlockViewModel SelectedBlockViewModel { get; set; }
IItemFilterBlockViewModel SectionBrowserSelectedBlockViewModel { get; set; }
IEnumerable<IItemFilterBlockViewModel> ItemFilterSectionViewModels { get; }
IItemFilterBlockViewModelBase SelectedBlockViewModel { get; set; }
IItemFilterCommentBlockViewModel CommentBlockBrowserBrowserSelectedBlockViewModel { get; set; }
IEnumerable<IItemFilterCommentBlockViewModel> ItemFilterCommentBlockViewModels { get; }
Predicate<IItemFilterBlockViewModel> BlockFilterPredicate { get; set; }
bool ShowAdvanced { get; }
@ -58,11 +59,11 @@ namespace Filtration.ViewModels
RelayCommand<bool> ToggleShowAdvancedCommand { get; }
RelayCommand ClearFilterCommand { get; }
void AddSection(IItemFilterBlockViewModel targetBlockViewModel);
void AddBlock(IItemFilterBlockViewModel targetBlockViewModel);
void CopyBlock(IItemFilterBlockViewModel targetBlockViewModel);
void AddSection(IItemFilterBlockViewModelBase targetBlockViewModel);
void AddBlock(IItemFilterBlockViewModelBase targetBlockViewModel);
void CopyBlock(IItemFilterBlockViewModelBase targetBlockViewModel);
void CopyBlockStyle(IItemFilterBlockViewModel targetBlockViewModel);
void PasteBlock(IItemFilterBlockViewModel targetBlockViewModel);
void PasteBlock(IItemFilterBlockViewModelBase targetBlockViewModel);
void PasteBlockStyle(IItemFilterBlockViewModel targetBlockViewModel);
}
@ -72,6 +73,7 @@ namespace Filtration.ViewModels
private readonly IItemFilterBlockViewModelFactory _itemFilterBlockViewModelFactory;
private readonly IItemFilterBlockTranslator _blockTranslator;
private readonly IItemFilterCommentBlockViewModelFactory _itemFilterCommentBlockViewModelFactory;
private readonly IAvalonDockWorkspaceViewModel _avalonDockWorkspaceViewModel;
private readonly IItemFilterPersistenceService _persistenceService;
private readonly IMessageBoxService _messageBoxService;
@ -79,14 +81,15 @@ namespace Filtration.ViewModels
private readonly IBlockGroupHierarchyBuilder _blockGroupHierarchyBuilder;
private bool _isDirty;
private IItemFilterBlockViewModel _selectedBlockViewModel;
private IItemFilterBlockViewModel _sectionBrowserSelectedBlockViewModel;
private readonly ObservableCollection<IItemFilterBlockViewModel> _itemFilterBlockViewModels;
private IItemFilterBlockViewModelBase _selectedBlockViewModel;
private IItemFilterCommentBlockViewModel _sectionBrowserSelectedBlockViewModel;
private readonly ObservableCollection<IItemFilterBlockViewModelBase> _itemFilterBlockViewModels;
private ICollectionView _itemFilterBlockViewModelsCollectionView;
private Predicate<IItemFilterBlockViewModel> _blockFilterPredicate;
public ItemFilterScriptViewModel(IItemFilterBlockViewModelFactory itemFilterBlockViewModelFactory,
IItemFilterBlockTranslator blockTranslator,
IItemFilterCommentBlockViewModelFactory itemFilterCommentBlockViewModelFactory,
IAvalonDockWorkspaceViewModel avalonDockWorkspaceViewModel,
IItemFilterPersistenceService persistenceService,
IMessageBoxService messageBoxService,
@ -95,13 +98,19 @@ namespace Filtration.ViewModels
{
_itemFilterBlockViewModelFactory = itemFilterBlockViewModelFactory;
_blockTranslator = blockTranslator;
_itemFilterCommentBlockViewModelFactory = itemFilterCommentBlockViewModelFactory;
_avalonDockWorkspaceViewModel = avalonDockWorkspaceViewModel;
_avalonDockWorkspaceViewModel.ActiveDocumentChanged += OnActiveDocumentChanged;
_persistenceService = persistenceService;
_messageBoxService = messageBoxService;
_clipboardService = clipboardService;
_blockGroupHierarchyBuilder = blockGroupHierarchyBuilder;
_itemFilterBlockViewModels = new ObservableCollection<IItemFilterBlockViewModel>();
_itemFilterBlockViewModels = new ObservableCollection<IItemFilterBlockViewModelBase>();
_avalonDockWorkspaceViewModel.ActiveDocumentChanged += (s, e) =>
{
RaisePropertyChanged(nameof(IsActiveDocument));
};
ToggleShowAdvancedCommand = new RelayCommand<bool>(OnToggleShowAdvancedCommand);
ClearFilterCommand = new RelayCommand(OnClearFilterCommand, () => BlockFilterPredicate != null);
@ -148,7 +157,19 @@ namespace Filtration.ViewModels
public RelayCommand ExpandAllBlocksCommand { get; }
public RelayCommand CollapseAllBlocksCommand { get; }
public ObservableCollection<IItemFilterBlockViewModel> ItemFilterBlockViewModels
public bool IsActiveDocument
{
get
{
var isActiveDocument = _avalonDockWorkspaceViewModel.ActiveScriptViewModel == this;
Debug.WriteLine($"IsActiveDocument: {isActiveDocument}");
return isActiveDocument;
}
}
public ObservableCollection<IItemFilterBlockViewModelBase> ItemFilterBlockViewModels
{
get
{
@ -162,6 +183,8 @@ namespace Filtration.ViewModels
private bool BlockFilter(object item)
{
if (!(item is IItemFilterBlockViewModelBase)) return false;
if (item is IItemFilterCommentBlockViewModel) return true;
var blockViewModel = item as IItemFilterBlockViewModel;
if (BlockFilterPredicate != null)
@ -190,25 +213,22 @@ namespace Filtration.ViewModels
public Predicate<IItemFilterBlockViewModel> BlockFilterPredicate
{
get { return _blockFilterPredicate; }
get => _blockFilterPredicate;
set
{
_blockFilterPredicate = value;
RaisePropertyChanged("ItemFilterBlockViewModels");
RaisePropertyChanged(nameof(ItemFilterBlockViewModels));
}
}
public IEnumerable<IItemFilterBlockViewModel> ItemFilterSectionViewModels
{
get { return ItemFilterBlockViewModels.Where(b => b.Block.GetType() == typeof (ItemFilterSection)); }
}
public IEnumerable<IItemFilterCommentBlockViewModel> ItemFilterCommentBlockViewModels => ItemFilterBlockViewModels.OfType<IItemFilterCommentBlockViewModel>();
public bool IsScript => true;
public bool IsTheme => false;
public string Description
{
get { return Script.Description; }
get => Script.Description;
set
{
Script.Description = value;
@ -219,33 +239,39 @@ namespace Filtration.ViewModels
public bool ShowAdvanced
{
get { return _showAdvanced; }
get => _showAdvanced;
private set
{
_showAdvanced = value;
RaisePropertyChanged();
RaisePropertyChanged("ItemFilterBlockViewModels");
RaisePropertyChanged(nameof(ItemFilterBlockViewModels));
}
}
public bool HasSelectedBlock()
{
return SelectedBlockViewModel != null;
}
public bool HasSelectedEnabledBlock()
{
return HasSelectedBlock() && !(SelectedBlockViewModel.Block is ItemFilterSection) && SelectedBlockViewModel.BlockEnabled;
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel == null) return false;
return HasSelectedBlock() && selectedBlockViewModel.BlockEnabled;
}
public bool HasSelectedDisabledBlock()
{
return HasSelectedBlock() && !(SelectedBlockViewModel.Block is ItemFilterSection) && !SelectedBlockViewModel.BlockEnabled;
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel == null) return false;
return HasSelectedBlock() && !selectedBlockViewModel.BlockEnabled;
}
public IItemFilterBlockViewModel SelectedBlockViewModel
private bool HasSelectedBlock()
{
get { return _selectedBlockViewModel; }
return SelectedBlockViewModel != null;
}
public IItemFilterBlockViewModelBase SelectedBlockViewModel
{
get => _selectedBlockViewModel;
set
{
if (value != _selectedBlockViewModel)
@ -257,9 +283,9 @@ namespace Filtration.ViewModels
}
}
public IItemFilterBlockViewModel SectionBrowserSelectedBlockViewModel
public IItemFilterCommentBlockViewModel CommentBlockBrowserBrowserSelectedBlockViewModel
{
get { return _sectionBrowserSelectedBlockViewModel; }
get => _sectionBrowserSelectedBlockViewModel;
set
{
_sectionBrowserSelectedBlockViewModel = value;
@ -272,7 +298,7 @@ namespace Filtration.ViewModels
public bool IsDirty
{
get { return _isDirty || HasDirtyChildren; }
get => _isDirty || HasDirtyChildren;
set
{
if (_isDirty != value)
@ -295,15 +321,15 @@ namespace Filtration.ViewModels
{
CleanChildren();
IsDirty = false;
RaisePropertyChanged("Filename");
RaisePropertyChanged("DisplayName");
RaisePropertyChanged(nameof(Filename));
RaisePropertyChanged(nameof(DisplayName));
}
public void SetDirtyFlag()
{
IsDirty = true;
RaisePropertyChanged("Filename");
RaisePropertyChanged("DisplayName");
RaisePropertyChanged(nameof(Filename));
RaisePropertyChanged(nameof(DisplayName));
}
public string DisplayName => !string.IsNullOrEmpty(Filename) ? Filename : Description;
@ -320,12 +346,30 @@ namespace Filtration.ViewModels
ItemFilterBlockViewModels.Clear();
Script = itemFilterScript;
foreach (var block in Script.ItemFilterBlocks.OfType<ItemFilterBlock>())
foreach (var block in Script.ItemFilterBlocks)
{
var vm = _itemFilterBlockViewModelFactory.Create();
vm.Initialise(block, this);
vm.BlockBecameDirty += OnBlockBecameDirty;
ItemFilterBlockViewModels.Add(vm);
var itemFilterBlock = block as IItemFilterBlock;
if (itemFilterBlock != null)
{
var itemFilterBlockViewModel = _itemFilterBlockViewModelFactory.Create();
itemFilterBlockViewModel.Initialise(itemFilterBlock, this);
itemFilterBlockViewModel.BlockBecameDirty += OnBlockBecameDirty;
ItemFilterBlockViewModels.Add(itemFilterBlockViewModel);
continue;
}
var itemFilterCommentBlock = block as IItemFilterCommentBlock;
if (itemFilterCommentBlock == null)
{
throw new InvalidOperationException("Unknown item filter block type");
}
var itemFilterCommentBlockViewModel = _itemFilterCommentBlockViewModelFactory.Create();
itemFilterCommentBlockViewModel.Initialise(itemFilterCommentBlock);
itemFilterCommentBlockViewModel.BlockBecameDirty += OnBlockBecameDirty;
ItemFilterBlockViewModels.Add(itemFilterCommentBlockViewModel);
}
_filenameIsFake = newScript;
@ -550,12 +594,11 @@ namespace Filtration.ViewModels
CopyBlock(SelectedBlockViewModel);
}
public void CopyBlock(IItemFilterBlockViewModel targetBlockViewModel)
public void CopyBlock(IItemFilterBlockViewModelBase targetBlockViewModel)
{
try
{
_clipboardService.SetClipboardText(
_blockTranslator.TranslateItemFilterBlockToString(SelectedBlockViewModel.Block));
_clipboardService.SetClipboardText(_blockTranslator.TranslateItemFilterBlockBaseToString(SelectedBlockViewModel.BaseBlock));
}
catch
{
@ -566,7 +609,11 @@ namespace Filtration.ViewModels
private void OnCopyBlockStyleCommand()
{
CopyBlockStyle(SelectedBlockViewModel);
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel != null)
{
CopyBlockStyle(selectedBlockViewModel);
}
}
public void CopyBlockStyle(IItemFilterBlockViewModel targetBlockViewModel)
@ -594,7 +641,11 @@ namespace Filtration.ViewModels
private void OnPasteBlockStyleCommand()
{
PasteBlockStyle(SelectedBlockViewModel);
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel != null)
{
PasteBlockStyle(selectedBlockViewModel);
}
}
public void PasteBlockStyle(IItemFilterBlockViewModel targetBlockViewModel)
@ -614,7 +665,7 @@ namespace Filtration.ViewModels
PasteBlock(SelectedBlockViewModel);
}
public void PasteBlock(IItemFilterBlockViewModel targetBlockViewModel)
public void PasteBlock(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
try
{
@ -630,9 +681,9 @@ namespace Filtration.ViewModels
if (ItemFilterBlockViewModels.Count > 0)
{
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModel.Block) + 1,
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModelBase.BaseBlock) + 1,
translatedBlock);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModel) + 1, vm);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase) + 1, vm);
}
else
{
@ -661,18 +712,18 @@ namespace Filtration.ViewModels
MoveBlockToTop(SelectedBlockViewModel);
}
public void MoveBlockToTop(IItemFilterBlockViewModel targetBlockViewModel)
public void MoveBlockToTop(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModel);
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase);
if (currentIndex > 0)
{
var block = targetBlockViewModel.Block;
var block = targetBlockViewModelBase.BaseBlock;
Script.ItemFilterBlocks.Remove(block);
Script.ItemFilterBlocks.Insert(0, block);
ItemFilterBlockViewModels.Move(currentIndex, 0);
IsDirty = true;
RaisePropertyChanged(nameof(ItemFilterSectionViewModels));
RaisePropertyChanged(nameof(ItemFilterCommentBlockViewModels));
}
}
@ -681,19 +732,19 @@ namespace Filtration.ViewModels
MoveBlockUp(SelectedBlockViewModel);
}
public void MoveBlockUp(IItemFilterBlockViewModel targetBlockViewModel)
public void MoveBlockUp(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModel);
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase);
if (currentIndex > 0)
{
var block = targetBlockViewModel.Block;
var block = targetBlockViewModelBase.BaseBlock;
var blockPos = Script.ItemFilterBlocks.IndexOf(block);
Script.ItemFilterBlocks.RemoveAt(blockPos);
Script.ItemFilterBlocks.Insert(blockPos - 1, block);
ItemFilterBlockViewModels.Move(currentIndex, currentIndex - 1);
IsDirty = true;
RaisePropertyChanged(nameof(ItemFilterSectionViewModels));
RaisePropertyChanged(nameof(ItemFilterCommentBlockViewModels));
}
}
@ -702,19 +753,19 @@ namespace Filtration.ViewModels
MoveBlockDown(SelectedBlockViewModel);
}
public void MoveBlockDown(IItemFilterBlockViewModel targetBlockViewModel)
public void MoveBlockDown(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModel);
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase);
if (currentIndex < ItemFilterBlockViewModels.Count - 1)
{
var block = targetBlockViewModel.Block;
var block = targetBlockViewModelBase.BaseBlock;
var blockPos = Script.ItemFilterBlocks.IndexOf(block);
Script.ItemFilterBlocks.RemoveAt(blockPos);
Script.ItemFilterBlocks.Insert(blockPos + 1, block);
ItemFilterBlockViewModels.Move(currentIndex, currentIndex + 1);
IsDirty = true;
RaisePropertyChanged(nameof(ItemFilterSectionViewModels));
RaisePropertyChanged(nameof(ItemFilterCommentBlockViewModels));
}
}
@ -723,18 +774,18 @@ namespace Filtration.ViewModels
MoveBlockToBottom(SelectedBlockViewModel);
}
public void MoveBlockToBottom(IItemFilterBlockViewModel targetBlockViewModel)
public void MoveBlockToBottom(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModel);
var currentIndex = ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase);
if (currentIndex < ItemFilterBlockViewModels.Count - 1)
{
var block = targetBlockViewModel.Block;
var block = targetBlockViewModelBase.BaseBlock;
Script.ItemFilterBlocks.Remove(block);
Script.ItemFilterBlocks.Add(block);
ItemFilterBlockViewModels.Move(currentIndex, ItemFilterBlockViewModels.Count - 1);
IsDirty = true;
RaisePropertyChanged(nameof(ItemFilterSectionViewModels));
RaisePropertyChanged(nameof(ItemFilterCommentBlockViewModels));
}
}
@ -743,16 +794,16 @@ namespace Filtration.ViewModels
AddBlock(SelectedBlockViewModel);
}
public void AddBlock(IItemFilterBlockViewModel targetBlockViewModel)
public void AddBlock(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var vm = _itemFilterBlockViewModelFactory.Create();
var newBlock = new ItemFilterBlock();
vm.Initialise(newBlock, this);
if (targetBlockViewModel != null)
if (targetBlockViewModelBase != null)
{
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModel.Block) + 1, newBlock);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModel) + 1, vm);
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModelBase.BaseBlock) + 1, newBlock);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase) + 1, vm);
}
else
{
@ -776,23 +827,23 @@ namespace Filtration.ViewModels
AddSection(SelectedBlockViewModel);
}
public void AddSection(IItemFilterBlockViewModel targetBlockViewModel)
public void AddSection(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var vm = _itemFilterBlockViewModelFactory.Create();
var newSection = new ItemFilterSection { Description = "New Section" };
vm.Initialise(newSection, this);
var vm = _itemFilterCommentBlockViewModelFactory.Create();
var newSection = new ItemFilterCommentBlock { Comment = "New Comment Block" };
vm.Initialise(newSection);
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModel.Block), newSection);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModel), vm);
Script.ItemFilterBlocks.Insert(Script.ItemFilterBlocks.IndexOf(targetBlockViewModelBase.BaseBlock), newSection);
ItemFilterBlockViewModels.Insert(ItemFilterBlockViewModels.IndexOf(targetBlockViewModelBase), vm);
IsDirty = true;
SelectedBlockViewModel = vm;
RaisePropertyChanged(nameof(ItemFilterSectionViewModels));
RaisePropertyChanged(nameof(ItemFilterCommentBlockViewModels));
Messenger.Default.Send(new NotificationMessage("SectionsChanged"));
}
private void OnExpandAllBlocksCommand()
{
foreach (var blockViewModel in ItemFilterBlockViewModels)
foreach (var blockViewModel in ItemFilterBlockViewModels.OfType<IItemFilterBlockViewModel>())
{
blockViewModel.IsExpanded = true;
}
@ -800,7 +851,7 @@ namespace Filtration.ViewModels
private void OnCollapseAllBlocksCommand()
{
foreach (var blockViewModel in ItemFilterBlockViewModels)
foreach (var blockViewModel in ItemFilterBlockViewModels.OfType<IItemFilterBlockViewModel>())
{
blockViewModel.IsExpanded = false;
}
@ -811,7 +862,7 @@ namespace Filtration.ViewModels
DeleteBlock(SelectedBlockViewModel);
}
public void DeleteBlock(IItemFilterBlockViewModel targetBlockViewModel)
public void DeleteBlock(IItemFilterBlockViewModelBase targetBlockViewModelBase)
{
var result = _messageBoxService.Show("Delete Confirmation", "Are you sure you wish to delete this block?",
MessageBoxButton.YesNo,
@ -819,13 +870,13 @@ namespace Filtration.ViewModels
if (result == MessageBoxResult.Yes)
{
var isSection = targetBlockViewModel.Block is ItemFilterSection;
var isSection = targetBlockViewModelBase.BaseBlock is ItemFilterCommentBlock;
Script.ItemFilterBlocks.Remove(targetBlockViewModel.Block);
ItemFilterBlockViewModels.Remove(targetBlockViewModel);
Script.ItemFilterBlocks.Remove(targetBlockViewModelBase.BaseBlock);
ItemFilterBlockViewModels.Remove(targetBlockViewModelBase);
IsDirty = true;
targetBlockViewModel.BlockBecameDirty -= OnBlockBecameDirty;
targetBlockViewModelBase.BlockBecameDirty -= OnBlockBecameDirty;
if (isSection)
{
@ -838,22 +889,20 @@ namespace Filtration.ViewModels
private void OnDisableBlockCommand()
{
DisableBlock(SelectedBlockViewModel);
}
private void DisableBlock(IItemFilterBlockViewModel targetBlockViewModel)
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel != null)
{
targetBlockViewModel.BlockEnabled = false;
selectedBlockViewModel.BlockEnabled = false;
}
}
private void OnEnableBlockCommand()
{
EnableBlock(SelectedBlockViewModel);
}
private void EnableBlock(IItemFilterBlockViewModel targetBlockViewModel)
var selectedBlockViewModel = SelectedBlockViewModel as IItemFilterBlockViewModel;
if (selectedBlockViewModel != null)
{
targetBlockViewModel.BlockEnabled = true;
selectedBlockViewModel.BlockEnabled = true;
}
}
}
}

View File

@ -159,7 +159,7 @@ namespace Filtration.ViewModels
case "OpenScript":
{
#pragma warning disable 4014
OnOpenScriptCommand();
Task.Run(OnOpenScriptCommand).GetAwaiter().GetResult();
#pragma warning restore 4014
break;
}
@ -334,7 +334,7 @@ namespace Filtration.ViewModels
return;
}
await LoadScriptAsync(filePath);
await LoadScriptAsync(filePath); // TODO: fix crash
}
private async Task LoadScriptAsync(string scriptFilename)
@ -346,20 +346,19 @@ namespace Filtration.ViewModels
{
loadedViewModel = await _itemFilterScriptRepository.LoadScriptFromFileAsync(scriptFilename);
}
catch (IOException e)
{
Messenger.Default.Send(new NotificationMessage("HideLoadingBanner"));
if (Logger.IsErrorEnabled)
catch (Exception e)
{
Logger.Error(e);
}
_messageBoxService.Show("Script Load Error", "Error loading filter script - " + e.Message,
MessageBoxButton.OK,
MessageBoxImage.Error);
return;
}
finally
{
Messenger.Default.Send(new NotificationMessage("HideLoadingBanner"));
}
_avalonDockWorkspaceViewModel.AddDocument(loadedViewModel);
}
@ -382,12 +381,9 @@ namespace Filtration.ViewModels
{
loadedViewModel = await _themeProvider.LoadThemeFromFile(themeFilename);
}
catch (IOException e)
{
if (Logger.IsErrorEnabled)
catch (Exception e)
{
Logger.Error(e);
}
_messageBoxService.Show("Theme Load Error", "Error loading filter theme - " + e.Message,
MessageBoxButton.OK,
MessageBoxImage.Error);

View File

@ -73,8 +73,8 @@ namespace Filtration.ViewModels.ToolPanes
}
PreviewText =
_itemFilterBlockTranslator.TranslateItemFilterBlockToString(
AvalonDockWorkspaceViewModel.ActiveScriptViewModel.SelectedBlockViewModel.Block);
_itemFilterBlockTranslator.TranslateItemFilterBlockBaseToString(
AvalonDockWorkspaceViewModel.ActiveScriptViewModel.SelectedBlockViewModel.BaseBlock);
}
}
}

View File

@ -5,18 +5,18 @@ using GalaSoft.MvvmLight.Messaging;
namespace Filtration.ViewModels.ToolPanes
{
internal interface ISectionBrowserViewModel : IToolViewModel
internal interface ICommentBlockBrowserViewModel : IToolViewModel
{
void ClearDown();
bool IsVisible { get; set; }
}
internal class SectionBrowserViewModel : ToolViewModel, ISectionBrowserViewModel
internal class CommentBlockBrowserViewModel : ToolViewModel, ICommentBlockBrowserViewModel
{
private IEnumerable<IItemFilterBlockViewModel> _sectionBlockViewModels;
private IItemFilterBlockViewModel _selectedSectionBlockViewModel;
private IEnumerable<IItemFilterCommentBlockViewModel> _itemFilterCommentBlockViewModels;
private IItemFilterCommentBlockViewModel _selectedItemFilterCommentBlockViewModel;
public SectionBrowserViewModel() : base("Section Browser")
public CommentBlockBrowserViewModel() : base("Section Browser")
{
ContentId = ToolContentId;
var icon = new BitmapImage();
@ -40,25 +40,25 @@ namespace Filtration.ViewModels.ToolPanes
public const string ToolContentId = "SectionBrowserTool";
public IEnumerable<IItemFilterBlockViewModel> SectionBlockViewModels
public IEnumerable<IItemFilterCommentBlockViewModel> ItemFilterCommentBlockViewModels
{
get { return _sectionBlockViewModels; }
get => _itemFilterCommentBlockViewModels;
private set
{
_sectionBlockViewModels = value;
_itemFilterCommentBlockViewModels = value;
RaisePropertyChanged();
}
}
public IItemFilterBlockViewModel SelectedSectionBlockViewModel
public IItemFilterCommentBlockViewModel SelectedItemFilterCommentBlockViewModel
{
get { return _selectedSectionBlockViewModel; }
get => _selectedItemFilterCommentBlockViewModel;
set
{
_selectedSectionBlockViewModel = value;
_selectedItemFilterCommentBlockViewModel = value;
if (AvalonDockWorkspaceViewModel.ActiveDocument.IsScript)
{
AvalonDockWorkspaceViewModel.ActiveScriptViewModel.SectionBrowserSelectedBlockViewModel = value;
AvalonDockWorkspaceViewModel.ActiveScriptViewModel.CommentBlockBrowserBrowserSelectedBlockViewModel = value;
}
RaisePropertyChanged();
}
@ -68,7 +68,7 @@ namespace Filtration.ViewModels.ToolPanes
{
if (AvalonDockWorkspaceViewModel.ActiveScriptViewModel != null && AvalonDockWorkspaceViewModel.ActiveDocument.IsScript)
{
SectionBlockViewModels = AvalonDockWorkspaceViewModel.ActiveScriptViewModel.ItemFilterSectionViewModels;
ItemFilterCommentBlockViewModels = AvalonDockWorkspaceViewModel.ActiveScriptViewModel.ItemFilterCommentBlockViewModels;
}
else
{
@ -78,8 +78,8 @@ namespace Filtration.ViewModels.ToolPanes
public void ClearDown()
{
SectionBlockViewModels = null;
SelectedSectionBlockViewModel = null;
ItemFilterCommentBlockViewModels = null;
SelectedItemFilterCommentBlockViewModel = null;
}
}
}

View File

@ -43,7 +43,7 @@
</viewsAvalonDock:PanesTemplateSelector.BlockGroupBrowserTemplate>
<viewsAvalonDock:PanesTemplateSelector.SectionBrowserTemplate>
<DataTemplate>
<toolPanes:SectionBrowserView DataContext="{Binding}" />
<toolPanes:CommentBlockBrowserView DataContext="{Binding}" />
</DataTemplate>
</viewsAvalonDock:PanesTemplateSelector.SectionBrowserTemplate>
<viewsAvalonDock:PanesTemplateSelector.BlockOutputPreviewTemplate>

View File

@ -15,7 +15,7 @@ namespace Filtration.Views.AvalonDock
if (destinationContainer?.FindParent<LayoutFloatingWindow>() != null)
return false;
if (anchorableToShow.Content is SectionBrowserViewModel)
if (anchorableToShow.Content is CommentBlockBrowserViewModel)
{
var toolsPane = layout.Descendents().OfType<LayoutAnchorablePane>().FirstOrDefault(d => d.Name == "SectionBrowserPane");
if (toolsPane != null)

View File

@ -30,7 +30,7 @@ namespace Filtration.Views.AvalonDock
return ThemeTemplate;
}
if (item is SectionBrowserViewModel)
if (item is CommentBlockBrowserViewModel)
{
return SectionBrowserTemplate;
}

View File

@ -1,26 +0,0 @@
using System.Windows;
using System.Windows.Controls;
using Filtration.ObjectModel;
using Filtration.ViewModels;
namespace Filtration.Views
{
public class BlockTemplateSelector : DataTemplateSelector
{
public override DataTemplate SelectTemplate(object item, DependencyObject container)
{
var viewModel = item as ItemFilterBlockViewModel;
var element = container as FrameworkElement;
if (viewModel == null || element == null)
return null;
if (viewModel.Block is ItemFilterSection)
{
return element.FindResource("ItemFilterSectionTemplate") as DataTemplate;
}
return element.FindResource("ItemFilterBlockTemplate") as DataTemplate;
}
}
}

View File

@ -1,10 +1,10 @@
<UserControl x:Class="Filtration.Views.ItemFilterSectionView"
<UserControl x:Class="Filtration.Views.ItemFilterCommentBlockView"
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:viewModels="clr-namespace:Filtration.ViewModels"
d:DataContext="{d:DesignInstance Type=viewModels:ItemFilterBlockViewModel}"
d:DataContext="{d:DesignInstance Type=viewModels:ItemFilterCommentBlockViewModel}"
mc:Ignorable="d"
d:DesignHeight="50" d:DesignWidth="300">
<UserControl.Resources>
@ -45,7 +45,7 @@
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<TextBox Grid.Column ="0" Text="{Binding BlockDescription, UpdateSourceTrigger=PropertyChanged}" VerticalAlignment="Center" TextWrapping="Wrap" MinWidth="150"/>
<TextBox Grid.Column ="0" Text="{Binding Comment, UpdateSourceTrigger=PropertyChanged, Mode=OneWay}" VerticalAlignment="Center" TextWrapping="Wrap" MinWidth="150"/>
</Grid>
</Border>
</Grid>

View File

@ -1,8 +1,8 @@
namespace Filtration.Views
{
public partial class ItemFilterSectionView
public partial class ItemFilterCommentBlockView
{
public ItemFilterSectionView()
public ItemFilterCommentBlockView()
{
InitializeComponent();
}

View File

@ -7,6 +7,7 @@
xmlns:attachedProperties="clr-namespace:Filtration.Views.AttachedProperties"
xmlns:viewModels="clr-namespace:Filtration.ViewModels"
xmlns:userControls="clr-namespace:Filtration.UserControls"
xmlns:utility="clr-namespace:Filtration.Utility"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance Type=viewModels:ItemFilterScriptViewModel}"
d:DesignHeight="300" d:DesignWidth="600">
@ -16,19 +17,19 @@
<KeyBinding Command="{Binding CopyBlockStyleCommand}" Modifiers="Shift+Control" Key="C" />
<KeyBinding Command="{Binding PasteBlockStyleCommand}" Modifiers="Shift+Control" Key="V" />
</UserControl.InputBindings>
<utility:RoutedCommandHandlers.Commands>
<utility:RoutedCommandHandler RoutedCommand="{StaticResource MoveBlockUpRoutedCommand}" Command="{Binding MoveBlockUpCommand}" IsActive="{Binding IsActiveDocument}" />
</utility:RoutedCommandHandlers.Commands>
<UserControl.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary>
<!-- ReSharper disable once Xaml.RedundantResource -->
<DataTemplate x:Key="ItemFilterBlockTemplate">
<DataTemplate DataType="{x:Type viewModels:ItemFilterBlockViewModel}">
<views:ItemFilterBlockView Margin="1" />
</DataTemplate>
<!-- ReSharper disable once Xaml.RedundantResource -->
<DataTemplate x:Key="ItemFilterSectionTemplate">
<views:ItemFilterSectionView Margin="1" />
<DataTemplate DataType="{x:Type viewModels:ItemFilterCommentBlockViewModel}">
<views:ItemFilterCommentBlockView Margin="1" />
</DataTemplate>
<views:BlockTemplateSelector x:Key="BlockTemplateSelector" />
</ResourceDictionary>
<ResourceDictionary Source="ExpanderStyle.xaml" />
</ResourceDictionary.MergedDictionaries>
@ -41,6 +42,7 @@
</Grid.RowDefinitions>
<Border Grid.Row="0" BorderThickness="1" BorderBrush="DarkGray" Margin="5,5,5,0">
<StackPanel Margin="2,2,2,2">
<Button Command="{StaticResource MoveBlockUpRoutedCommand}">MOVE BLOCK UP TEST BUTTON</Button>
<Expander Style="{StaticResource ExpanderRightAlignStyle}">
<Expander.Header>
<TextBlock Text="Script Description" VerticalAlignment="Center" />
@ -59,9 +61,9 @@
BorderThickness="0"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
VirtualizingStackPanel.VirtualizationMode="Recycling"
ItemTemplateSelector="{StaticResource BlockTemplateSelector}"
attachedProperties:SelectingItemAttachedProperty.SelectingItem="{Binding SectionBrowserSelectedBlockViewModel}"
SelectedItem="{Binding SelectedBlockViewModel}" x:Name="BlocksListBox">
attachedProperties:SelectingItemAttachedProperty.SelectingItem="{Binding CommentBlockBrowserBrowserSelectedBlockViewModel}"
SelectedItem="{Binding SelectedBlockViewModel}">
<!--ItemTemplateSelector="{StaticResource BlockTemplateSelector}"-->
<ListBox.InputBindings>
<KeyBinding Key="Delete" Command="{Binding DeleteBlockCommand}" />
</ListBox.InputBindings>

View File

@ -9,15 +9,20 @@
xmlns:viewsAvalonDock="clr-namespace:Filtration.Views.AvalonDock"
xmlns:views="clr-namespace:Filtration.Views"
xmlns:gif="http://wpfanimatedgif.codeplex.com"
xmlns:utility="clr-namespace:Filtration.Utility"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance Type=viewModels:MainWindowViewModel}"
Title="{Binding WindowTitle}" Height="762" Width="1126" IsIconVisible="True"
Closing="MainWindow_OnClosing" Drop="MainWindow_OnDrop" AllowDrop="True">
<fluent:RibbonWindow.InputBindings>
<KeyBinding Command="{Binding SaveCommand}" Modifiers="Control" Key="S" />
<KeyBinding Command="{Binding OpenScriptCommand}" Modifiers="Control" Key="O" />
<KeyBinding Command="{Binding NewScriptCommand}" Modifiers="Control" Key="N" />
</fluent:RibbonWindow.InputBindings>
<utility:RoutedCommandHandlers.Commands>
<utility:RoutedCommandHandler RoutedCommand="{StaticResource OpenScriptRoutedCommand}" Command="{Binding OpenScriptCommand}" />
</utility:RoutedCommandHandlers.Commands>
<DockPanel x:Name="RootDockPanel">
<fluent:Ribbon DockPanel.Dock="Top" x:Name="RibbonRoot" IsEnabled="{Binding ShowLoadingBanner, Converter={StaticResource BoolInverterConverter}}">
<fluent:Ribbon.Menu>
@ -67,7 +72,7 @@
</fluent:Ribbon.ContextualGroups>
<fluent:RibbonTabItem Header="View">
<fluent:RibbonGroupBox Header="Tools">
<fluent:ToggleButton Header="Section Browser" Width="150" Size="Middle" Icon="{StaticResource AddSectionIcon}" IsChecked="{Binding AvalonDockWorkspaceViewModel.SectionBrowserViewModel.IsVisible}"/>
<fluent:ToggleButton Header="Section Browser" Width="150" Size="Middle" Icon="{StaticResource AddSectionIcon}" IsChecked="{Binding AvalonDockWorkspaceViewModel.CommentBlockBrowserViewModel.IsVisible}"/>
<fluent:ToggleButton Header="Block Group Browser" SizeDefinition="Middle" Icon="{StaticResource BlockGroupBrowserIcon}" IsChecked="{Binding AvalonDockWorkspaceViewModel.BlockGroupBrowserViewModel.IsVisible}" />
<fluent:ToggleButton Header="Block Output Preview" SizeDefinition="Middle" Icon="{StaticResource BlockOutputPreviewIcon}" IsChecked="{Binding AvalonDockWorkspaceViewModel.BlockOutputPreviewViewModel.IsVisible}" />
</fluent:RibbonGroupBox>
@ -147,3 +152,4 @@
</DockPanel>
</fluent:RibbonWindow>

View File

@ -8,7 +8,7 @@
<Grid>
<TextBlock FontStyle="Italic" Margin="5" FontSize="13">
Welcome to Filtration, to get started either
<Hyperlink Command="{Binding NewScriptCommand}">create a new script</Hyperlink> or <Hyperlink Command="{Binding OpenScriptCommand}">open an existing script</Hyperlink>
<Hyperlink Command="{Binding NewScriptCommand}">create a new script</Hyperlink> or <Hyperlink Command="{StaticResource OpenScriptRoutedCommand}">open an existing script</Hyperlink>
</TextBlock>
</Grid>
</UserControl>

View File

@ -1,19 +1,19 @@
<UserControl x:Class="Filtration.Views.ToolPanes.SectionBrowserView"
<UserControl x:Class="Filtration.Views.ToolPanes.CommentBlockBrowserView"
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:converters="clr-namespace:Filtration.Converters"
xmlns:toolPanes="clr-namespace:Filtration.ViewModels.ToolPanes"
d:DataContext="{d:DesignInstance Type=toolPanes:SectionBrowserViewModel}"
d:DataContext="{d:DesignInstance Type=toolPanes:CommentBlockBrowserViewModel}"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<UserControl.Resources>
<converters:HashSignRemovalConverter x:Key="HashSignRemovalConverter" />
</UserControl.Resources>
<Grid>
<ListBox ItemsSource="{Binding SectionBlockViewModels}"
SelectedItem="{Binding SelectedSectionBlockViewModel}"
<ListBox ItemsSource="{Binding ItemFilterCommentBlockViewModels}"
SelectedItem="{Binding SelectedItemFilterCommentBlockViewModel}"
x:Name="SectionBrowserListBox"
ScrollViewer.HorizontalScrollBarVisibility="Hidden"><!--SelectionChanged="SectionBrowserListBox_OnSelectionChanged"-->
<ListBox.Resources>
@ -21,7 +21,7 @@
</ListBox.Resources>
<ListBox.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding BlockDescription, Converter={StaticResource HashSignRemovalConverter}}" ToolTip="{Binding BlockDescription}" />
<TextBlock Text="{Binding Comment, Converter={StaticResource HashSignRemovalConverter}}" ToolTip="{Binding Comment}" />
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

View File

@ -1,8 +1,8 @@
namespace Filtration.Views.ToolPanes
{
public partial class SectionBrowserView
public partial class CommentBlockBrowserView
{
public SectionBrowserView()
public CommentBlockBrowserView()
{
InitializeComponent();
}

View File

@ -26,6 +26,11 @@ namespace Filtration.WindsorInstallers
.ImplementedBy<ItemFilterBlockViewModel>()
.LifeStyle.Transient);
container.Register(
Component.For<IItemFilterCommentBlockViewModel>()
.ImplementedBy<ItemFilterCommentBlockViewModel>()
.LifeStyle.Transient);
container.Register(
Component.For<IItemFilterScriptViewModel>()
.ImplementedBy<ItemFilterScriptViewModel>()
@ -42,8 +47,8 @@ namespace Filtration.WindsorInstallers
.LifeStyle.Singleton);
container.Register(
Component.For<ISectionBrowserViewModel>()
.ImplementedBy<SectionBrowserViewModel>()
Component.For<ICommentBlockBrowserViewModel>()
.ImplementedBy<CommentBlockBrowserViewModel>()
.LifeStyle.Singleton);
container.Register(
@ -69,6 +74,9 @@ namespace Filtration.WindsorInstallers
container.Register(
Component.For<IItemFilterBlockViewModelFactory>().AsFactory());
container.Register(
Component.For<IItemFilterCommentBlockViewModelFactory>().AsFactory());
container.Register(
Component.For<IItemFilterScriptViewModelFactory>().AsFactory());
}