Merge pull request #54 from azakhi/master

3.4 Update and Improvements
This commit is contained in:
Ben Wallis 2018-08-29 22:39:36 +01:00 committed by GitHub
commit dc6ed934b2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
116 changed files with 3708 additions and 327 deletions

View File

@ -3,9 +3,9 @@ using System.ComponentModel;
using System.Linq;
using System.Windows.Markup;
namespace Filtration.Extensions
namespace Filtration.Common.Extensions
{
internal class EnumerationExtension : MarkupExtension
public class EnumerationExtension : MarkupExtension
{
private Type _enumType;

View File

@ -4,7 +4,7 @@ using System.Windows;
using System.Windows.Documents;
using System.Windows.Navigation;
namespace Filtration.Extensions
namespace Filtration.Common.Extensions
{
public static class HyperlinkExtensions
{

View File

@ -75,6 +75,8 @@
<Compile Include="Converters\ColorToSolidColorBrushConverter.cs" />
<Compile Include="Converters\InverseBooleanVisibilityConverter.cs" />
<Compile Include="Converters\StringToVisibilityConverter.cs" />
<Compile Include="Extensions\EnumerationExtension.cs" />
<Compile Include="Extensions\HyperlinkExtensions.cs" />
<Compile Include="Messages\ThemeClosedMessage.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Services\FileSystemService.cs" />

View File

@ -67,6 +67,7 @@ namespace Filtration.ItemFilterPreview.Tests.Services
}
[Test]
[Ignore("Outdated item filter")]
public void ProcessItemsAgainstItemFilterScript_IntegrationTest()
{
//Arrange
@ -102,6 +103,7 @@ namespace Filtration.ItemFilterPreview.Tests.Services
}
[Test]
[Ignore("Outdated item filter")]
public void ProcessItemsAgainstItemFilterScript_IntegrationTest_10Items()
{
//Arrange

View File

@ -66,6 +66,9 @@
<ItemGroup>
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Service Include="{82A7F48D-3B50-4B1E-B82E-3ADA8210C358}" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\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

@ -4,7 +4,7 @@ using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class ColorBlockItem : BlockItemBase, IAudioVisualBlockItem
public abstract class ColorBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private Color _color;
private ThemeComponent _themeComponent;
@ -63,7 +63,7 @@ namespace Filtration.ObjectModel.BlockItemBaseTypes
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Color = ((ThemeComponent) sender).Color;
Color = ((ColorThemeComponent) sender).Color;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)

View File

@ -0,0 +1,53 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class ColorBooleanBlockItem : BlockItemBase, IAudioVisualBlockItem
{
private Color _color;
private bool _booleanValue;
protected ColorBooleanBlockItem()
{
}
protected ColorBooleanBlockItem(Color color, bool booleanValue)
{
Color = color;
BooleanValue = booleanValue;
}
public override string OutputText => PrefixText + " " + +Color.R + " " + Color.G + " "
+ Color.B + (Color.A < 255 ? " " + Color.A : string.Empty) +
(BooleanValue ? " True" : " False");
public override string SummaryText => string.Empty;
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public Color Color
{
get { return _color; }
set
{
_color = value;
IsDirty = true;
OnPropertyChanged();
}
}
public bool BooleanValue
{
get { return _booleanValue; }
set
{
_booleanValue = value;
IsDirty = true;
OnPropertyChanged();
}
}
}
}

View File

@ -0,0 +1,90 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.Enums;
using Filtration.ObjectModel.Extensions;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class EffectColorBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private EffectColor _color;
private bool _temporary;
private ThemeComponent _themeComponent;
protected EffectColorBlockItem()
{
}
protected EffectColorBlockItem(EffectColor color, bool temporary)
{
Color = color;
Temporary = temporary;
}
public override string OutputText => PrefixText + " " + Color.GetAttributeDescription() +
(Temporary ? " " + "Temp" : string.Empty) +
(ThemeComponent != null ? " # " + ThemeComponent.ComponentName : string.Empty);
public override string SummaryText => string.Empty;
public ThemeComponent ThemeComponent
{
get { return _themeComponent; }
set
{
if (_themeComponent == value) { return; }
if (_themeComponent != null)
{
_themeComponent.ThemeComponentUpdated -= OnThemeComponentUpdated;
_themeComponent.ThemeComponentDeleted -= OnThemeComponentDeleted;
}
if (value != null)
{
value.ThemeComponentUpdated += OnThemeComponentUpdated;
value.ThemeComponentDeleted += OnThemeComponentDeleted;
}
_themeComponent = value;
OnPropertyChanged();
}
}
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public EffectColor Color
{
get { return _color; }
set
{
_color = value;
IsDirty = true;
OnPropertyChanged();
}
}
public bool Temporary
{
get { return _temporary; }
set
{
_temporary = value;
IsDirty = true;
OnPropertyChanged();
}
}
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Color = ((EffectColorThemeComponent)sender).EffectColor;
Temporary = ((EffectColorThemeComponent)sender).Temporary;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)
{
ThemeComponent = null;
}
}
}

View File

@ -0,0 +1,103 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.Enums;
using Filtration.ObjectModel.Extensions;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class IconBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private IconSize _size;
private IconColor _color;
private IconShape _shape;
private ThemeComponent _themeComponent;
protected IconBlockItem()
{
}
protected IconBlockItem(IconSize size, IconColor color, IconShape shape)
{
Size = size;
Color = color;
Shape = shape;
}
public override string OutputText => PrefixText + " " + (int)Size + " " + Color.GetAttributeDescription() + " " + Shape.GetAttributeDescription() +
(ThemeComponent != null ? " # " + ThemeComponent.ComponentName : string.Empty);
public override string SummaryText => string.Empty;
public ThemeComponent ThemeComponent
{
get { return _themeComponent; }
set
{
if (_themeComponent == value) { return; }
if (_themeComponent != null)
{
_themeComponent.ThemeComponentUpdated -= OnThemeComponentUpdated;
_themeComponent.ThemeComponentDeleted -= OnThemeComponentDeleted;
}
if (value != null)
{
value.ThemeComponentUpdated += OnThemeComponentUpdated;
value.ThemeComponentDeleted += OnThemeComponentDeleted;
}
_themeComponent = value;
OnPropertyChanged();
}
}
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public IconSize Size
{
get { return _size; }
set
{
_size = value;
IsDirty = true;
OnPropertyChanged();
}
}
public IconColor Color
{
get { return _color; }
set
{
_color = value;
IsDirty = true;
OnPropertyChanged();
}
}
public IconShape Shape
{
get { return _shape; }
set
{
_shape = value;
IsDirty = true;
OnPropertyChanged();
}
}
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Size = ((IconThemeComponent)sender).IconSize;
Color = ((IconThemeComponent)sender).IconColor;
Shape = ((IconThemeComponent)sender).IconShape;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)
{
ThemeComponent = null;
}
}
}

View File

@ -1,10 +1,13 @@
using System.Windows.Media;
using System;
using System.Windows.Media;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class IntegerBlockItem : BlockItemBase, IAudioVisualBlockItem
public abstract class IntegerBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private int _value;
private ThemeComponent _themeComponent;
protected IntegerBlockItem()
{
@ -15,7 +18,7 @@ namespace Filtration.ObjectModel.BlockItemBaseTypes
Value = value;
}
public override string OutputText => PrefixText + " " + Value;
public override string OutputText => PrefixText + " " + Value + (ThemeComponent != null ? " # " + ThemeComponent.ComponentName : string.Empty);
public override string SummaryText => string.Empty;
public override Color SummaryBackgroundColor => Colors.Transparent;
@ -24,6 +27,29 @@ namespace Filtration.ObjectModel.BlockItemBaseTypes
public abstract int Minimum { get; }
public abstract int Maximum { get; }
public ThemeComponent ThemeComponent
{
get { return _themeComponent; }
set
{
if (_themeComponent == value) { return; }
if (_themeComponent != null)
{
_themeComponent.ThemeComponentUpdated -= OnThemeComponentUpdated;
_themeComponent.ThemeComponentDeleted -= OnThemeComponentDeleted;
}
if (value != null)
{
value.ThemeComponentUpdated += OnThemeComponentUpdated;
value.ThemeComponentDeleted += OnThemeComponentDeleted;
}
_themeComponent = value;
OnPropertyChanged();
}
}
public int Value
{
get { return _value; }
@ -34,5 +60,15 @@ namespace Filtration.ObjectModel.BlockItemBaseTypes
OnPropertyChanged();
}
}
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Value = ((IntegerBlockItem)sender).Value;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)
{
ThemeComponent = null;
}
}
}

View File

@ -0,0 +1,87 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class StrIntBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private string _value;
private int _secondValue;
private ThemeComponent _themeComponent;
protected StrIntBlockItem()
{
}
protected StrIntBlockItem(string value, int secondValue)
{
Value = value;
SecondValue = secondValue;
Value = value;
SecondValue = secondValue;
}
public override string OutputText => PrefixText + " " + Value + " " + SecondValue + (ThemeComponent != null ? " # " + ThemeComponent.ComponentName : string.Empty);
public override string SummaryText => string.Empty;
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public ThemeComponent ThemeComponent
{
get { return _themeComponent; }
set
{
if (_themeComponent == value) { return; }
if (_themeComponent != null)
{
_themeComponent.ThemeComponentUpdated -= OnThemeComponentUpdated;
_themeComponent.ThemeComponentDeleted -= OnThemeComponentDeleted;
}
if (value != null)
{
value.ThemeComponentUpdated += OnThemeComponentUpdated;
value.ThemeComponentDeleted += OnThemeComponentDeleted;
}
_themeComponent = value;
OnPropertyChanged();
}
}
public string Value
{
get { return _value; }
set
{
_value = value;
IsDirty = true;
OnPropertyChanged();
}
}
public int SecondValue
{
get { return _secondValue; }
set
{
_secondValue = value;
IsDirty = true;
OnPropertyChanged();
}
}
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Value = ((StrIntBlockItem)sender).Value;
SecondValue = ((StrIntBlockItem)sender).SecondValue;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)
{
ThemeComponent = null;
}
}
}

View File

@ -0,0 +1,72 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class StringBlockItem : BlockItemBase, IAudioVisualBlockItem, IBlockItemWithTheme
{
private string _value;
private ThemeComponent _themeComponent;
protected StringBlockItem()
{
}
protected StringBlockItem(string value)
{
Value = value;
}
public override string OutputText => PrefixText + " \"" + Value + "\""
+ (ThemeComponent != null ? " # " + ThemeComponent.ComponentName : string.Empty);
public override string SummaryText => string.Empty;
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public ThemeComponent ThemeComponent
{
get { return _themeComponent; }
set
{
if (_themeComponent == value) { return; }
if (_themeComponent != null)
{
_themeComponent.ThemeComponentUpdated -= OnThemeComponentUpdated;
_themeComponent.ThemeComponentDeleted -= OnThemeComponentDeleted;
}
if (value != null)
{
value.ThemeComponentUpdated += OnThemeComponentUpdated;
value.ThemeComponentDeleted += OnThemeComponentDeleted;
}
_themeComponent = value;
OnPropertyChanged();
}
}
public string Value
{
get { return _value; }
set
{
_value = value;
IsDirty = true;
OnPropertyChanged();
}
}
private void OnThemeComponentUpdated(object sender, EventArgs e)
{
Value = ((StringThemeComponent)sender).Value;
}
private void OnThemeComponentDeleted(object sender, EventArgs e)
{
ThemeComponent = null;
}
}
}

View File

@ -1,50 +0,0 @@
using System.Windows.Media;
namespace Filtration.ObjectModel.BlockItemBaseTypes
{
public abstract class StrIntBlockItem : BlockItemBase, IAudioVisualBlockItem
{
private string _value;
private int _secondValue;
protected StrIntBlockItem()
{
}
protected StrIntBlockItem(string value, int secondValue)
{
Value = value;
SecondValue = secondValue;
Value = value;
SecondValue = secondValue;
}
public override string OutputText => PrefixText + " " + Value + " " + SecondValue;
public override string SummaryText => string.Empty;
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public string Value
{
get { return _value; }
set
{
_value = value;
IsDirty = true;
OnPropertyChanged();
}
}
public int SecondValue
{
get { return _secondValue; }
set
{
_secondValue = value;
IsDirty = true;
OnPropertyChanged();
}
}
}
}

View File

@ -16,6 +16,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "SetBackgroundColor";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Background Color";
public override int SortOrder => 18;
public override int SortOrder => 23;
}
}

View File

@ -33,6 +33,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override Color SummaryBackgroundColor => Colors.MediumTurquoise;
public override Color SummaryTextColor => Colors.Black;
public override int SortOrder => 16;
public override int SortOrder => 20;
}
}

View File

@ -16,6 +16,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "SetBorderColor";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Border Color";
public override int SortOrder => 19;
public override int SortOrder => 24;
}
}

View File

@ -33,6 +33,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override Color SummaryBackgroundColor => Colors.MediumSeaGreen;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 15;
public override int SortOrder => 19;
}
}

View File

@ -0,0 +1,21 @@
using Filtration.ObjectModel.BlockItemBaseTypes;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class CustomSoundBlockItem : StringBlockItem
{
public CustomSoundBlockItem()
{
Value = "placeholder.mp3";
}
public CustomSoundBlockItem(string value) : base(value)
{
}
public override string PrefixText => "CustomAlertSound";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Custom Alert Sound";
public override int SortOrder => 31;
}
}

View File

@ -0,0 +1,23 @@
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
namespace Filtration.ObjectModel.BlockItemTypes
{
public sealed class DisableDropSoundBlockItem : BooleanBlockItem, IAudioVisualBlockItem
{
public DisableDropSoundBlockItem()
{
}
public DisableDropSoundBlockItem(bool booleanValue) : base(booleanValue)
{
}
public override string PrefixText => "DisableDropSound";
public override string DisplayHeading => "Disable Drop Sound";
public override Color SummaryBackgroundColor => Colors.Transparent;
public override Color SummaryTextColor => Colors.Transparent;
public override int SortOrder => 28;
}
}

View File

@ -21,7 +21,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string SummaryText => "Drop Level " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.DodgerBlue;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 13;
public override int SortOrder => 15;
public override int Minimum => 0;
public override int Maximum => 100;
}

View File

@ -0,0 +1,23 @@
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
namespace Filtration.ObjectModel.BlockItemTypes
{
public sealed class ElderMapBlockItem : BooleanBlockItem
{
public ElderMapBlockItem()
{
}
public ElderMapBlockItem(bool booleanValue) : base(booleanValue)
{
}
public override string PrefixText => "ElderMap";
public override string DisplayHeading => "Elder Map";
public override Color SummaryBackgroundColor => Colors.DarkGoldenrod;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 10;
}
}

View File

@ -16,7 +16,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "SetFontSize";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Font Size";
public override int SortOrder => 20;
public override int SortOrder => 25;
public override int Minimum => 11;
public override int Maximum => 45;
}

View File

@ -0,0 +1,28 @@
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class GemLevelBlockItem : NumericFilterPredicateBlockItem
{
public GemLevelBlockItem()
{
}
public GemLevelBlockItem(FilterPredicateOperator predicateOperator, int predicateOperand)
: base(predicateOperator, predicateOperand)
{
}
public override string PrefixText => "GemLevel";
public override int MaximumAllowed => 2;
public override string DisplayHeading => "Gem Level";
public override string SummaryText => "Gem Level " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.DarkSlateGray;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 16;
public override int Minimum => 0;
public override int Maximum => 21;
}
}

View File

@ -0,0 +1,38 @@
using System.Linq;
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class HasExplicitModBlockItem : StringListBlockItem
{
public override string PrefixText => "HasExplicitMod";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Has Explicit Mod";
public override string SummaryText
{
get
{
if (Items.Count > 0 && Items.Count < 4)
{
return "Item Explicit Mods: " +
Items.Aggregate(string.Empty, (current, i) => current + i + ", ").TrimEnd(' ').TrimEnd(',');
}
if (Items.Count >= 4)
{
var remaining = Items.Count - 3;
return "Item Explicit Mods: " + Items.Take(3)
.Aggregate(string.Empty, (current, i) => current + i + ", ")
.TrimEnd(' ')
.TrimEnd(',') + " (+" + remaining + " more)";
}
return "Item Explicit Mods: (none)";
}
}
public override Color SummaryBackgroundColor => Colors.MidnightBlue;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 21;
}
}

View File

@ -21,7 +21,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string SummaryText => "Height " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.LightBlue;
public override Color SummaryTextColor => Colors.Black;
public override int SortOrder => 10;
public override int SortOrder => 12;
public override int Minimum => 0;
public override int Maximum => 6;
}

View File

@ -20,7 +20,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string SummaryText => "Item Level " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.DarkSlateGray;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 12;
public override int SortOrder => 14;
public override int Minimum => 0;
public override int Maximum => 100;
}

View File

@ -0,0 +1,24 @@
using Filtration.ObjectModel.BlockItemBaseTypes;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class MapIconBlockItem : IconBlockItem
{
public MapIconBlockItem()
{
Size = IconSize.Largest;
Color = IconColor.Red;
Shape = IconShape.Circle;
}
public MapIconBlockItem(IconSize size, IconColor iconColor, IconShape iconShape) : base(size, iconColor, iconShape)
{
}
public override string PrefixText => "MinimapIcon";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Minimap Icon";
public override int SortOrder => 29;
}
}

View File

@ -0,0 +1,18 @@
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class MapTierBlockItem : NumericFilterPredicateBlockItem
{
public override string PrefixText => "MapTier";
public override int MaximumAllowed => 2;
public override string DisplayHeading => "Map Tier";
public override string SummaryText => "Map Tier " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.DarkSlateGray;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 8;
public override int Minimum => 1;
public override int Maximum => 16;
}
}

View File

@ -0,0 +1,23 @@
using Filtration.ObjectModel.BlockItemBaseTypes;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class PlayEffectBlockItem : EffectColorBlockItem
{
public PlayEffectBlockItem()
{
Color = EffectColor.Red;
Temporary = false;
}
public PlayEffectBlockItem(EffectColor effectColor, bool temporary) : base(effectColor, temporary)
{
}
public override string PrefixText => "PlayEffect";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Play Effect";
public override int SortOrder => 30;
}
}

View File

@ -17,6 +17,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "PlayAlertSoundPositional";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Play Positional Alert Sound";
public override int SortOrder => 22;
public override int SortOrder => 27;
}
}

View File

@ -30,7 +30,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
((ItemRarity) FilterPredicate.PredicateOperand).GetAttributeDescription();
public override Color SummaryBackgroundColor => Colors.LightCoral;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 14;
public override int SortOrder => 18;
public override int Minimum => 0;
public override int Maximum => (int)ItemRarity.Unique;
}

View File

@ -17,7 +17,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string DisplayHeading => "Shaped Map";
public override Color SummaryBackgroundColor => Colors.DarkGoldenrod;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 8;
public override int SortOrder => 9;
}
}

View File

@ -39,7 +39,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override Color SummaryBackgroundColor => Colors.GhostWhite;
public override Color SummaryTextColor => Colors.Black;
public override int SortOrder => 9;
public override int SortOrder => 11;
private SocketColor StringToSocketColor(char socketColorString)
{

View File

@ -17,6 +17,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "PlayAlertSound";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Play Alert Sound";
public override int SortOrder => 21;
public override int SortOrder => 26;
}
}

View File

@ -0,0 +1,28 @@
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.BlockItemTypes
{
public class StackSizeBlockItem : NumericFilterPredicateBlockItem
{
public StackSizeBlockItem()
{
}
public StackSizeBlockItem(FilterPredicateOperator predicateOperator, int predicateOperand)
: base(predicateOperator, predicateOperand)
{
}
public override string PrefixText => "StackSize";
public override int MaximumAllowed => 2;
public override string DisplayHeading => "Stack Size";
public override string SummaryText => "Stack Size " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.DarkSlateGray;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 17;
public override int Minimum => 0;
public override int Maximum => 1000;
}
}

View File

@ -16,6 +16,6 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string PrefixText => "SetTextColor";
public override int MaximumAllowed => 1;
public override string DisplayHeading => "Text Color";
public override int SortOrder => 17;
public override int SortOrder => 22;
}
}

View File

@ -21,7 +21,7 @@ namespace Filtration.ObjectModel.BlockItemTypes
public override string SummaryText => "Width " + FilterPredicate;
public override Color SummaryBackgroundColor => Colors.MediumPurple;
public override Color SummaryTextColor => Colors.White;
public override int SortOrder => 11;
public override int SortOrder => 13;
public override int Minimum => 0;
public override int Maximum => 2;
}

View File

@ -0,0 +1,49 @@
using System.Collections.Generic;
namespace Filtration.ObjectModel.Commands.ItemFilterScript
{
public class MoveSectionToIndexCommand : IUndoableCommand
{
private readonly IItemFilterScript _itemFilterScript;
private int _sectionStart;
private int _sectionSize;
private int _index;
public MoveSectionToIndexCommand(IItemFilterScript itemFilterScript, int sectionStart, int sectionSize, int index)
{
_itemFilterScript = itemFilterScript;
_sectionStart = sectionStart;
_sectionSize = sectionSize;
_index = index;
}
public void Execute()
{
List<IItemFilterBlockBase> blocksToMove = new List<IItemFilterBlockBase>();
for(var i = 0; i < _sectionSize; i++)
{
blocksToMove.Add(_itemFilterScript.ItemFilterBlocks[_sectionStart]);
_itemFilterScript.ItemFilterBlocks.RemoveAt(_sectionStart);
}
for (var i = 0; i < _sectionSize; i++)
{
_itemFilterScript.ItemFilterBlocks.Insert(_index + i, blocksToMove[i]);
}
}
public void Undo()
{
List<IItemFilterBlockBase> blocksToMove = new List<IItemFilterBlockBase>();
for (var i = 0; i < _sectionSize; i++)
{
blocksToMove.Add(_itemFilterScript.ItemFilterBlocks[_index]);
_itemFilterScript.ItemFilterBlocks.RemoveAt(_index);
}
for (var i = 0; i < _sectionSize; i++)
{
_itemFilterScript.ItemFilterBlocks.Insert(_sectionStart + i, blocksToMove[i]);
}
}
public void Redo() => Execute();
}
}

View File

@ -0,0 +1,49 @@
using System;
using System.Collections.Generic;
namespace Filtration.ObjectModel.Commands.ItemFilterScript
{
public class PasteSectionCommand : IUndoableCommand
{
private readonly IItemFilterScript _itemFilterScript;
private readonly List<IItemFilterBlockBase> _pastedItemFilterBlocks;
private readonly IItemFilterBlockBase _addAfterItemFilterBlock;
public PasteSectionCommand(IItemFilterScript itemFilterScript, List<IItemFilterBlockBase> pastedItemFilterBlocks, IItemFilterBlockBase addAfterItemFilterBlock)
{
_itemFilterScript = itemFilterScript;
_pastedItemFilterBlocks = pastedItemFilterBlocks;
_addAfterItemFilterBlock = addAfterItemFilterBlock;
}
public void Execute()
{
if (_addAfterItemFilterBlock != null)
{
var lastAddedBlock = _addAfterItemFilterBlock;
foreach(var block in _pastedItemFilterBlocks)
{
_itemFilterScript.ItemFilterBlocks.Insert(_itemFilterScript.ItemFilterBlocks.IndexOf(lastAddedBlock) + 1, block);
lastAddedBlock = block;
}
}
else
{
foreach (var block in _pastedItemFilterBlocks)
{
_itemFilterScript.ItemFilterBlocks.Add(block);
}
}
}
public void Undo()
{
foreach (var block in _pastedItemFilterBlocks)
{
_itemFilterScript.ItemFilterBlocks.Remove(block);
}
}
public void Redo() => Execute();
}
}

View File

@ -0,0 +1,42 @@
using System;
using System.Collections.Generic;
namespace Filtration.ObjectModel.Commands.ItemFilterScript
{
public class RemoveSectionCommand : IUndoableCommand
{
private readonly IItemFilterScript _itemFilterScript;
private List<IItemFilterBlockBase> _removedItemFilterBlocks;
private int _sectionStart;
private int _sectionSize;
public RemoveSectionCommand(IItemFilterScript itemFilterScript, int sectionStart, int sectionSize)
{
_itemFilterScript = itemFilterScript;
_sectionStart = sectionStart;
_sectionSize = sectionSize;
_removedItemFilterBlocks = new List<IItemFilterBlockBase>();
for(var i = 0; i < _sectionSize; i++)
{
_removedItemFilterBlocks.Add(_itemFilterScript.ItemFilterBlocks[_sectionStart + i]);
}
}
public void Execute()
{
for (var i = 0; i < _sectionSize; i++)
{
_itemFilterScript.ItemFilterBlocks.RemoveAt(_sectionStart);
}
}
public void Undo()
{
for (var i = 0; i < _sectionSize; i++)
{
_itemFilterScript.ItemFilterBlocks.Insert(_sectionStart + i, _removedItemFilterBlocks[i]);
}
}
public void Redo() => Execute();
}
}

View File

@ -0,0 +1,20 @@
using System.ComponentModel;
namespace Filtration.ObjectModel.Enums
{
public enum EffectColor
{
[Description("Red")]
Red,
[Description("Green")]
Green,
[Description("Blue")]
Blue,
[Description("Brown")]
Brown,
[Description("White")]
White,
[Description("Yellow")]
Yellow
}
}

View File

@ -0,0 +1,20 @@
using System.ComponentModel;
namespace Filtration.ObjectModel.Enums
{
public enum IconColor
{
[Description("Red")]
Red,
[Description("Green")]
Green,
[Description("Blue")]
Blue,
[Description("Brown")]
Brown,
[Description("White")]
White,
[Description("Yellow")]
Yellow
}
}

View File

@ -0,0 +1,20 @@
using System.ComponentModel;
namespace Filtration.ObjectModel.Enums
{
public enum IconShape
{
[Description("Circle")]
Circle,
[Description("Diamond")]
Diamond,
[Description("Hexagon")]
Hexagon,
[Description("Square")]
Square,
[Description("Star")]
Star,
[Description("Triangle")]
Triangle
}
}

View File

@ -0,0 +1,14 @@
using System.ComponentModel;
namespace Filtration.ObjectModel.Enums
{
public enum IconSize
{
[Description("Largest")]
Largest,
[Description("Medium")]
Medium,
[Description("Small")]
Small
}
}

View File

@ -9,6 +9,16 @@ namespace Filtration.ObjectModel.Enums
[Description("Background")]
BackgroundColor,
[Description("Border")]
BorderColor
BorderColor,
[Description("Font Size")]
FontSize,
[Description("Alert Sound")]
AlertSound,
[Description("Custom Sound")]
CustomSound,
[Description("Icon")]
Icon,
[Description("Effect")]
Effect
}
}

View File

@ -37,10 +37,26 @@
<Reference Include="Castle.Windsor, Version=3.4.0.0, Culture=neutral, PublicKeyToken=407dd0808d44fbdc, processorArchitecture=MSIL">
<HintPath>..\packages\Castle.Windsor.3.4.0\lib\net45\Castle.Windsor.dll</HintPath>
</Reference>
<Reference Include="CommonServiceLocator, Version=2.0.2.0, Culture=neutral, PublicKeyToken=489b6accfaf20ef0, processorArchitecture=MSIL">
<HintPath>..\packages\CommonServiceLocator.2.0.2\lib\net45\CommonServiceLocator.dll</HintPath>
</Reference>
<Reference Include="GalaSoft.MvvmLight, Version=5.3.0.19026, Culture=neutral, PublicKeyToken=e7570ab207bcb616, processorArchitecture=MSIL">
<HintPath>..\packages\MvvmLightLibs.5.3.0.0\lib\net45\GalaSoft.MvvmLight.dll</HintPath>
</Reference>
<Reference Include="GalaSoft.MvvmLight.Extras, Version=5.3.0.19032, Culture=neutral, PublicKeyToken=669f0b5e8f868abf, processorArchitecture=MSIL">
<HintPath>..\packages\MvvmLightLibs.5.3.0.0\lib\net45\GalaSoft.MvvmLight.Extras.dll</HintPath>
</Reference>
<Reference Include="GalaSoft.MvvmLight.Platform, Version=5.3.0.19032, Culture=neutral, PublicKeyToken=5f873c45e98af8a1, processorArchitecture=MSIL">
<HintPath>..\packages\MvvmLightLibs.5.3.0.0\lib\net45\GalaSoft.MvvmLight.Platform.dll</HintPath>
</Reference>
<Reference Include="PresentationCore" />
<Reference Include="PresentationFramework" />
<Reference Include="System" />
<Reference Include="System.ComponentModel.DataAnnotations" />
<Reference Include="System.Core" />
<Reference Include="System.Windows.Interactivity, Version=4.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
<HintPath>..\packages\MvvmLightLibs.5.3.0.0\lib\net45\System.Windows.Interactivity.dll</HintPath>
</Reference>
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="Microsoft.CSharp" />
@ -52,15 +68,27 @@
<Compile Include="BlockItemBaseTypes\BlockItemBase.cs" />
<Compile Include="BlockItemBaseTypes\BooleanBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\ColorBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\ColorBooleanBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\DualIntegerBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\StringIntBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\EffectColorBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\IconBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\StringBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\StrIntBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\IntegerBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\NumericFilterPredicateBlockItem.cs" />
<Compile Include="BlockItemBaseTypes\StringListBlockItem.cs" />
<Compile Include="BlockItemTypes\BackgroundColorBlockItem.cs" />
<Compile Include="BlockItemTypes\BaseTypeBlockItem.cs" />
<Compile Include="BlockItemTypes\MapTierBlockItem.cs" />
<Compile Include="BlockItemTypes\PlayEffectBlockItem.cs" />
<Compile Include="BlockItemTypes\BorderColorBlockItem.cs" />
<Compile Include="BlockItemTypes\ClassBlockItem.cs" />
<Compile Include="BlockItemTypes\CustomSoundBlockItem.cs" />
<Compile Include="BlockItemTypes\DisableDropSoundBlockItem.cs" />
<Compile Include="BlockItemTypes\ElderMapBlockItem.cs" />
<Compile Include="BlockItemTypes\GemLevelBlockItem.cs" />
<Compile Include="BlockItemTypes\HasExplicitModBlockItem.cs" />
<Compile Include="BlockItemTypes\MapIconBlockItem.cs" />
<Compile Include="BlockItemTypes\ShapedMapBlockItem.cs" />
<Compile Include="BlockItemTypes\ShaperItemBlockItem.cs" />
<Compile Include="BlockItemTypes\ElderItemBlockItem.cs" />
@ -77,24 +105,32 @@
<Compile Include="BlockItemTypes\SocketsBlockItem.cs" />
<Compile Include="BlockItemTypes\PositionalSoundBlockItem.cs" />
<Compile Include="BlockItemTypes\SoundBlockItem.cs" />
<Compile Include="BlockItemTypes\StackSizeBlockItem.cs" />
<Compile Include="BlockItemTypes\TextColorBlockItem.cs" />
<Compile Include="BlockItemTypes\WidthBlockItem.cs" />
<Compile Include="Commands\CommandManager.cs" />
<Compile Include="Commands\ICommand.cs" />
<Compile Include="Commands\ItemFilterScript\MoveSectionToIndexCommand.cs" />
<Compile Include="Commands\ItemFilterScript\PasteBlockCommand.cs" />
<Compile Include="Commands\ItemFilterScript\MoveBlockToBottomCommand.cs" />
<Compile Include="Commands\ItemFilterScript\AddCommentBlockCommand.cs" />
<Compile Include="Commands\ItemFilterScript\MoveBlockDownCommand.cs" />
<Compile Include="Commands\ItemFilterScript\MoveBlockUpCommand.cs" />
<Compile Include="Commands\ItemFilterScript\MoveBlockToTopCommand.cs" />
<Compile Include="Commands\ItemFilterScript\PasteSectionCommand.cs" />
<Compile Include="Commands\ItemFilterScript\RemoveSectionCommand.cs" />
<Compile Include="Commands\ItemFilterScript\SetScriptDescriptionCommand.cs" />
<Compile Include="Commands\ItemFilterScript\RemoveBlockCommand.cs" />
<Compile Include="Commands\ItemFilterScript\AddBlockCommand.cs" />
<Compile Include="Commands\IUndoableCommand.cs" />
<Compile Include="Enums\BlockAction.cs" />
<Compile Include="Enums\BlockItemType.cs" />
<Compile Include="Enums\EffectColor.cs" />
<Compile Include="Enums\FilterPredicateOperator.cs" />
<Compile Include="Enums\FilterType.cs" />
<Compile Include="Enums\IconColor.cs" />
<Compile Include="Enums\IconShape.cs" />
<Compile Include="Enums\IconSize.cs" />
<Compile Include="Enums\ItemRarity.cs" />
<Compile Include="Enums\SocketColor.cs" />
<Compile Include="Enums\ThemeComponentType.cs" />
@ -103,6 +139,7 @@
<Compile Include="Factories\IItemFilterScriptFactory.cs" />
<Compile Include="FilteredItem.cs" />
<Compile Include="IAudioVisualBlockItem.cs" />
<Compile Include="IBlockItemWithTheme.cs" />
<Compile Include="IItemFilterBlockItem.cs" />
<Compile Include="Item.cs" />
<Compile Include="ItemFilterBlock.cs" />
@ -118,12 +155,21 @@
<Compile Include="ReplaceColorsParameterSet.cs" />
<Compile Include="Socket.cs" />
<Compile Include="SocketGroup.cs" />
<Compile Include="ThemeEditor\EffectColorThemeComponent.cs" />
<Compile Include="ThemeEditor\IconThemeComponent.cs" />
<Compile Include="ThemeEditor\StringThemeComponent.cs" />
<Compile Include="ThemeEditor\StrIntThemeComponent.cs" />
<Compile Include="ThemeEditor\IntegerThemeComponent.cs" />
<Compile Include="ThemeEditor\Theme.cs" />
<Compile Include="ThemeEditor\ColorThemeComponent.cs" />
<Compile Include="ThemeEditor\ThemeComponent.cs" />
<Compile Include="ThemeEditor\ThemeComponentCollection.cs" />
<Compile Include="WindsorInstallers\CommandsInstaller.cs" />
<Compile Include="WindsorInstallers\ModelsInstaller.cs" />
</ItemGroup>
<ItemGroup>
<None Include="packages.config" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\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

@ -0,0 +1,9 @@
using Filtration.ObjectModel.ThemeEditor;
namespace Filtration.ObjectModel
{
public interface IBlockItemWithTheme : IItemFilterBlockItem
{
ThemeComponent ThemeComponent { get; }
}
}

View File

@ -1,5 +1,6 @@
using System;
using System.Collections.ObjectModel;
using System.Collections.Specialized;
using System.Linq;
using System.Windows.Media;
using Filtration.ObjectModel.BlockItemBaseTypes;
@ -22,12 +23,18 @@ namespace Filtration.ObjectModel
Color DisplayTextColor { get; }
Color DisplayBorderColor { get; }
double DisplayFontSize { get; }
int DisplayIconSize { get; }
int DisplayIconColor { get; }
int DisplayIconShape { get; }
Color DisplayEffectColor { get; }
bool HasBlockItemOfType<T>();
bool HasBlockGroupInParentHierarchy(ItemFilterBlockGroup targetBlockGroup, ItemFilterBlockGroup startingBlockGroup);
}
public interface IItemFilterBlockBase
{
bool IsEdited { get; set; }
string OriginalText { get; set; }
}
public abstract class ItemFilterBlockBase : IItemFilterBlockBase
@ -44,6 +51,8 @@ namespace Filtration.ObjectModel
public ICommandManager CommandManager { get; }
public IItemFilterScript ParentScript { get; set; }
public bool IsEdited { get; set; }
public string OriginalText { get; set; }
}
public interface IItemFilterCommentBlock : IItemFilterBlockBase
@ -53,29 +62,60 @@ namespace Filtration.ObjectModel
public class ItemFilterCommentBlock : ItemFilterBlockBase, IItemFilterCommentBlock
{
private string _comment;
public ItemFilterCommentBlock(IItemFilterScript parentScript) : base(parentScript)
{
}
public string Comment { get; set; }
public string Comment
{
get { return _comment; }
set
{
_comment = value;
IsEdited = true;
}
}
}
public class ItemFilterBlock : ItemFilterBlockBase, IItemFilterBlock
{
private ItemFilterBlockGroup _blockGroup;
private bool _enabled;
private string _description;
internal ItemFilterBlock()
{
BlockItems = new ObservableCollection<IItemFilterBlockItem> { ActionBlockItem };
BlockItems.CollectionChanged += new NotifyCollectionChangedEventHandler(OnBlockItemsChanged);
_enabled = true;
}
public ItemFilterBlock(IItemFilterScript parentScript) : base(parentScript)
{
BlockItems = new ObservableCollection<IItemFilterBlockItem> { ActionBlockItem };
BlockItems.CollectionChanged += new NotifyCollectionChangedEventHandler(OnBlockItemsChanged);
_enabled = true;
}
public bool Enabled { get; set; } = true;
public string Description { get; set; }
public bool Enabled
{
get { return _enabled; }
set
{
_enabled = value;
IsEdited = true;
}
}
public string Description
{
get { return _description; }
set
{
_description = value;
IsEdited = true;
}
}
public ItemFilterBlockGroup BlockGroup
{
@ -114,12 +154,17 @@ namespace Filtration.ObjectModel
{
var actionBlock = BlockItems.OfType<ActionBlockItem>().First();
actionBlock.Action = value;
IsEdited = true;
}
}
public ActionBlockItem ActionBlockItem { get; } = new ActionBlockItem(BlockAction.Show);
public ObservableCollection<IItemFilterBlockItem> BlockItems { get; }
private void OnBlockItemsChanged(object sender, NotifyCollectionChangedEventArgs e)
{
IsEdited = true;
}
public bool AddBlockItemAllowed(Type type)
{
@ -219,5 +264,70 @@ namespace Filtration.ObjectModel
return fontSizeBlockItem?.Value ?? 34;
}
}
public int DisplayIconSize
{
get
{
var mapIconBlockItem = BlockItems.OfType<MapIconBlockItem>().FirstOrDefault();
if (mapIconBlockItem != null)
return (int)mapIconBlockItem.Size;
return -1;
}
}
public int DisplayIconColor
{
get
{
var mapIconBlockItem = BlockItems.OfType<MapIconBlockItem>().FirstOrDefault();
if (mapIconBlockItem != null)
return (int)mapIconBlockItem.Color;
return -1;
}
}
public int DisplayIconShape
{
get
{
var mapIconBlockItem = BlockItems.OfType<MapIconBlockItem>().FirstOrDefault();
if (mapIconBlockItem != null)
return (int)mapIconBlockItem.Shape;
return -1;
}
}
public Color DisplayEffectColor
{
get
{
var beamBlockItem = BlockItems.OfType<PlayEffectBlockItem>().FirstOrDefault();
if (beamBlockItem != null)
{
switch (beamBlockItem.Color)
{
case EffectColor.Red:
return Colors.Red;
case EffectColor.Green:
return Colors.Green;
case EffectColor.Blue:
return Colors.Blue;
case EffectColor.Brown:
return Colors.Brown;
case EffectColor.White:
return Colors.White;
case EffectColor.Yellow:
return Colors.Yellow;
}
}
return Colors.Transparent;
}
}
}
}

View File

@ -0,0 +1,35 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class ColorThemeComponent : ThemeComponent
{
private Color _color;
public ColorThemeComponent(ThemeComponentType componentType, string componentName, Color componentColor)
{
if (componentName == null || componentColor == null)
{
throw new ArgumentException("Null parameters not allowed in ColorThemeComponent constructor");
}
ComponentType = componentType;
Color = componentColor;
ComponentName = componentName;
}
public Color Color
{
get { return _color; }
set
{
_color = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
}
}

View File

@ -0,0 +1,47 @@
using System;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class EffectColorThemeComponent : ThemeComponent
{
private EffectColor _effectColor;
private bool _temporary;
public EffectColorThemeComponent(ThemeComponentType componentType, string componentName, EffectColor componentEffectColor, bool componentTemporary)
{
if (componentName == null)
{
throw new ArgumentException("Null parameters not allowed in EffectColorThemeComponent constructor");
}
ComponentType = componentType;
ComponentName = componentName;
EffectColor = componentEffectColor;
Temporary = componentTemporary;
}
public EffectColor EffectColor
{
get { return _effectColor; }
set
{
_effectColor = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
public bool Temporary
{
get { return _temporary; }
set
{
_temporary = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
}
}

View File

@ -0,0 +1,60 @@
using System;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class IconThemeComponent : ThemeComponent
{
private IconSize _iconSize;
private IconColor _iconColor;
private IconShape _iconShape;
public IconThemeComponent(ThemeComponentType componentType, string componentName, IconSize componentIconSize, IconColor componentIconColor, IconShape componentIconShape)
{
if (componentName == null)
{
throw new ArgumentException("Null parameters not allowed in IconThemeComponent constructor");
}
ComponentType = componentType;
ComponentName = componentName;
IconSize = componentIconSize;
IconColor = componentIconColor;
IconShape = componentIconShape;
}
public IconSize IconSize
{
get { return _iconSize; }
set
{
_iconSize = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
public IconColor IconColor
{
get { return _iconColor; }
set
{
_iconColor = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
public IconShape IconShape
{
get { return _iconShape; }
set
{
_iconShape = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
}
}

View File

@ -0,0 +1,35 @@
using System;
using System.Windows.Media;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class IntegerThemeComponent : ThemeComponent
{
private int _value;
public IntegerThemeComponent(ThemeComponentType componentType, string componentName, int componentValue)
{
if (componentName == null)
{
throw new ArgumentException("Null parameters not allowed in IntegerThemeComponent constructor");
}
ComponentType = componentType;
Value = componentValue;
ComponentName = componentName;
}
public int Value
{
get { return _value; }
set
{
_value = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
}
}

View File

@ -0,0 +1,47 @@
using System;
using Filtration.ObjectModel.Enums;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class StrIntThemeComponent : ThemeComponent
{
private string _value;
private int _secondValue;
public StrIntThemeComponent(ThemeComponentType componentType, string componentName, string componentValue, int componentSecondValue)
{
if (componentName == null || componentValue == null)
{
throw new ArgumentException("Null parameters not allowed in StrIntThemeComponent constructor");
}
ComponentType = componentType;
Value = componentValue;
SecondValue = componentSecondValue;
ComponentName = componentName;
}
public string Value
{
get { return _value; }
set
{
_value = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
public int SecondValue
{
get { return _secondValue; }
set
{
_secondValue = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
}
}

View File

@ -0,0 +1,82 @@
using System;
using System.Collections.ObjectModel;
using Filtration.ObjectModel.Enums;
using GalaSoft.MvvmLight.Command;
using Microsoft.Win32;
namespace Filtration.ObjectModel.ThemeEditor
{
[Serializable]
public class StringThemeComponent : ThemeComponent
{
private string _value;
public static ObservableCollection<string> _customSoundsAvailable;
public StringThemeComponent(ThemeComponentType componentType, string componentName, string componentValue)
{
if (componentName == null || componentValue == null)
{
throw new ArgumentException("Null parameters not allowed in StringThemeComponent constructor");
}
ComponentType = componentType;
Value = componentValue;
ComponentName = componentName;
if (_customSoundsAvailable == null || _customSoundsAvailable.Count < 1)
{
_customSoundsAvailable = new ObservableCollection<string> {
"1maybevaluable.mp3", "2currency.mp3", "3uniques.mp3", "4maps.mp3", "5highmaps.mp3",
"6veryvaluable.mp3", "7chancing.mp3", "12leveling.mp3", "placeholder.mp3"
};
}
if (_customSoundsAvailable.IndexOf(Value) < 0)
{
_customSoundsAvailable.Add(Value);
}
CustomSoundFileDialogCommand = new RelayCommand(OnCustomSoundFileDialog);
}
public RelayCommand CustomSoundFileDialogCommand { get; set; }
public ObservableCollection<string> CustomSoundsAvailable => _customSoundsAvailable;
public string Value
{
get { return _value; }
set
{
_value = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
private void OnCustomSoundFileDialog()
{
OpenFileDialog fileDialog = new OpenFileDialog();
fileDialog.DefaultExt = ".mp3";
var poePath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments).ToString() + @"\My Games\Path of Exile\";
fileDialog.InitialDirectory = poePath;
Nullable<bool> result = fileDialog.ShowDialog();
if (result == true)
{
var fileName = fileDialog.FileName;
if (fileName.StartsWith(poePath))
{
fileName = fileName.Replace(poePath, "");
}
if (CustomSoundsAvailable.IndexOf(fileName) < 0)
{
CustomSoundsAvailable.Add(fileName);
OnPropertyChanged(nameof(CustomSoundsAvailable));
}
Value = fileName;
}
}
}
}

View File

@ -32,7 +32,17 @@ namespace Filtration.ObjectModel.ThemeEditor
public void AddComponent(ThemeComponentType componentType, string componentName, Color componentColor)
{
_components.Add(new ThemeComponent(componentType, componentName, componentColor));
_components.Add(new ColorThemeComponent(componentType, componentName, componentColor));
}
public void AddComponent(ThemeComponentType componentType, string componentName, int componentValue)
{
_components.Add(new IntegerThemeComponent(componentType, componentName, componentValue));
}
public void AddComponent(ThemeComponentType componentType, string componentName, string componentValue, int componentSecondValue)
{
_components.Add(new StrIntThemeComponent(componentType, componentName, componentValue, componentSecondValue));
}
}
}

View File

@ -10,8 +10,7 @@ namespace Filtration.ObjectModel.ThemeEditor
[Serializable]
public class ThemeComponent : INotifyPropertyChanged
{
private Color _color;
private EventHandler _themeComponentUpdatedEventHandler;
protected EventHandler _themeComponentUpdatedEventHandler;
private readonly object _eventLock = new object();
public ThemeComponent()
@ -19,18 +18,6 @@ namespace Filtration.ObjectModel.ThemeEditor
}
public ThemeComponent(ThemeComponentType componentType, string componentName, Color componentColor)
{
if (componentName == null || componentColor == null)
{
throw new ArgumentException("Null parameters not allowed in ThemeComponent constructor");
}
ComponentType = componentType;
Color = componentColor;
ComponentName = componentName;
}
// By implementing a custom event accessor here we can keep the UsageCount up to date.
public event EventHandler ThemeComponentUpdated
{
@ -58,17 +45,6 @@ namespace Filtration.ObjectModel.ThemeEditor
public string ComponentName { get; set; }
public ThemeComponentType ComponentType{ get; set; }
public Color Color
{
get { return _color; }
set
{
_color = value;
OnPropertyChanged();
_themeComponentUpdatedEventHandler?.Invoke(this, EventArgs.Empty);
}
}
public int UsageCount
{
get

View File

@ -16,7 +16,72 @@ namespace Filtration.ObjectModel.ThemeEditor
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new ThemeComponent(componentType, componentName, componentColor);
var component = new ColorThemeComponent(componentType, componentName, componentColor);
Items.Add(component);
return component;
}
public ThemeComponent AddComponent(ThemeComponentType componentType, string componentName, int componentValue)
{
if (ComponentExists(componentType, componentName))
{
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new IntegerThemeComponent(componentType, componentName, componentValue);
Items.Add(component);
return component;
}
public ThemeComponent AddComponent(ThemeComponentType componentType, string componentName, string componentValue, int componentSecondValue)
{
if (ComponentExists(componentType, componentName))
{
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new StrIntThemeComponent(componentType, componentName, componentValue, componentSecondValue);
Items.Add(component);
return component;
}
public ThemeComponent AddComponent(ThemeComponentType componentType, string componentName, string componentValue)
{
if (ComponentExists(componentType, componentName))
{
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new StringThemeComponent(componentType, componentName, componentValue);
Items.Add(component);
return component;
}
public ThemeComponent AddComponent(ThemeComponentType componentType, string componentName, IconSize componentIconSize, IconColor componentIconColor, IconShape componentIconShape)
{
if (ComponentExists(componentType, componentName))
{
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new IconThemeComponent(componentType, componentName, componentIconSize, componentIconColor, componentIconShape);
Items.Add(component);
return component;
}
public ThemeComponent AddComponent(ThemeComponentType componentType, string componentName, EffectColor componentEffectColor, bool componentTemporary)
{
if (ComponentExists(componentType, componentName))
{
return Items.FirstOrDefault(t => t.ComponentName == componentName && t.ComponentType == componentType);
}
var component = new EffectColorThemeComponent(componentType, componentName, componentEffectColor, componentTemporary);
Items.Add(component);
return component;

View File

@ -2,4 +2,6 @@
<packages>
<package id="Castle.Core" version="3.3.0" targetFramework="net461" />
<package id="Castle.Windsor" version="3.4.0" targetFramework="net461" />
<package id="CommonServiceLocator" version="2.0.2" targetFramework="net461" />
<package id="MvvmLightLibs" version="5.3.0.0" targetFramework="net461" />
</packages>

View File

@ -5,8 +5,8 @@ namespace Filtration.Parser.Interface.Services
{
public interface IItemFilterBlockTranslator
{
IItemFilterBlock TranslateStringToItemFilterBlock(string inputString, IItemFilterScript parentItemFilterScript, bool initialiseBlockGroupHierarchyBuilder = false);
IItemFilterCommentBlock TranslateStringToItemFilterCommentBlock(string inputString, IItemFilterScript parentItemFilterScript);
IItemFilterBlock TranslateStringToItemFilterBlock(string inputString, IItemFilterScript parentItemFilterScript, string originalString = "", bool initialiseBlockGroupHierarchyBuilder = false);
IItemFilterCommentBlock TranslateStringToItemFilterCommentBlock(string inputString, IItemFilterScript parentItemFilterScript, string originalString = "");
string TranslateItemFilterBlockToString(IItemFilterBlock block);
void ReplaceAudioVisualBlockItemsFromString(ObservableCollection<IItemFilterBlockItem> blockItems, string inputString);

View File

@ -318,6 +318,42 @@ namespace Filtration.Parser.Tests.Services
Assert.AreEqual(FilterPredicateOperator.Equal, blockItem.FilterPredicate.PredicateOperator);
}
[Test]
public void TranslateStringToItemFilterBlock_GemLevel_ReturnsCorrectObject()
{
// Arrange
var inputString = "Show" + Environment.NewLine +
" GemLevel = 20";
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
// Assert
Assert.AreEqual(1, result.BlockItems.Count(b => b is GemLevelBlockItem));
var blockItem = result.BlockItems.OfType<GemLevelBlockItem>().First();
Assert.AreEqual(20, blockItem.FilterPredicate.PredicateOperand);
Assert.AreEqual(FilterPredicateOperator.Equal, blockItem.FilterPredicate.PredicateOperator);
}
[Test]
public void TranslateStringToItemFilterBlock_StackSize_ReturnsCorrectObject()
{
// Arrange
var inputString = "Show" + Environment.NewLine +
" StackSize > 5";
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
// Assert
Assert.AreEqual(1, result.BlockItems.Count(b => b is StackSizeBlockItem));
var blockItem = result.BlockItems.OfType<StackSizeBlockItem>().First();
Assert.AreEqual(5, blockItem.FilterPredicate.PredicateOperand);
Assert.AreEqual(FilterPredicateOperator.GreaterThan, blockItem.FilterPredicate.PredicateOperator);
}
[Test]
public void TranslateStringToItemFilterBlock_Corrupted_ReturnsCorrectObject()
{
@ -386,6 +422,23 @@ namespace Filtration.Parser.Tests.Services
Assert.IsFalse(blockItem.BooleanValue);
}
[Test]
public void TranslateStringToItemFilterBlock_ElderMap_ReturnsCorrectObject()
{
// Arrange
var inputString = "Show" + Environment.NewLine +
" ElderMap false";
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
// Assert
Assert.AreEqual(1, result.BlockItems.Count(b => b is ElderMapBlockItem));
var blockItem = result.BlockItems.OfType<ElderMapBlockItem>().First();
Assert.IsFalse(blockItem.BooleanValue);
}
[Test]
public void TranslateStringToItemFilterBlock_Identified_ReturnsCorrectObject()
{
@ -494,6 +547,25 @@ namespace Filtration.Parser.Tests.Services
Assert.Contains("Test BaseType 2", blockItem.Items);
}
[Test]
public void TranslateStringToItemFilterBlock_HasExplicitMod_ReturnsCorrectObject()
{
// Arrange
var inputString = "Show" + Environment.NewLine +
@" HasExplicitMod ""Test Mod 1"" ""TestOneWordModInQuotes"" TestOneWordModNotInQuotes ""Test Mod 2""";
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
// Assert
Assert.AreEqual(1, result.BlockItems.Count(b => b is HasExplicitModBlockItem));
var blockItem = result.BlockItems.OfType<HasExplicitModBlockItem>().First();
Assert.Contains("Test Mod 1", blockItem.Items);
Assert.Contains("TestOneWordModInQuotes", blockItem.Items);
Assert.Contains("TestOneWordModNotInQuotes", blockItem.Items);
Assert.Contains("Test Mod 2", blockItem.Items);
}
[Test]
public void TranslateStringToItemFilterBlock_Sockets_ReturnsCorrectObject()
{
@ -701,7 +773,7 @@ namespace Filtration.Parser.Tests.Services
// Arrange
var inputString = "Show" + Environment.NewLine +
" SetTextColor 255 20 100 # Rare Item Text";
var testComponent = new ThemeComponent(ThemeComponentType.TextColor, "Rare Item Text", new Color { R = 255, G = 20, B = 100});
var testComponent = new ColorThemeComponent(ThemeComponentType.TextColor, "Rare Item Text", new Color { R = 255, G = 20, B = 100});
var testInputThemeComponentCollection = new ThemeComponentCollection { testComponent };
// Act
@ -803,6 +875,23 @@ namespace Filtration.Parser.Tests.Services
Assert.AreEqual(95, blockItem.SecondValue);
}
[Test]
public void TranslateStringToItemFilterBlock_DisableDropSound_ReturnsCorrectObject()
{
// Arrange
var inputString = "Show" + Environment.NewLine +
" DisableDropSound True";
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
// Assert
Assert.AreEqual(1, result.BlockItems.Count(b => b is DisableDropSoundBlockItem));
var blockItem = result.BlockItems.OfType<DisableDropSoundBlockItem>().First();
Assert.IsTrue(blockItem.BooleanValue);
}
[Test]
public void TranslateStringToItemFilterBlock_Everything_ReturnsCorrectObject()
{
@ -813,6 +902,8 @@ namespace Filtration.Parser.Tests.Services
"Show" + Environment.NewLine +
" ItemLevel >= 50" + Environment.NewLine +
" DropLevel < 70" + Environment.NewLine +
" GemLevel = 20" + Environment.NewLine +
" StackSize > 2" + Environment.NewLine +
" Quality = 15" + Environment.NewLine +
" Rarity <= Unique" + Environment.NewLine +
" Identified True" + Environment.NewLine +
@ -820,8 +911,10 @@ namespace Filtration.Parser.Tests.Services
" ElderItem true" + Environment.NewLine +
" ShaperItem False" + Environment.NewLine +
" ShapedMap TRUE" + Environment.NewLine +
" ElderMap False" + Environment.NewLine +
@" Class ""My Item Class"" AnotherClass ""AndAnotherClass""" + Environment.NewLine +
@" BaseType MyBaseType ""Another BaseType""" + Environment.NewLine +
@" HasExplicitMod MyMod ""Another Mod""" + Environment.NewLine +
" JunkLine Let's ignore this one!" + Environment.NewLine +
" #Quality Commented out quality line" + Environment.NewLine +
" Sockets >= 3" + Environment.NewLine +
@ -831,7 +924,8 @@ namespace Filtration.Parser.Tests.Services
" SetBackgroundColor 255 100 5" + Environment.NewLine +
" SetBorderColor 0 0 0" + Environment.NewLine +
" SetFontSize 50" + Environment.NewLine +
" PlayAlertSound 3" + Environment.NewLine;
" PlayAlertSound 3" + Environment.NewLine +
" DisableDropSound False" + Environment.NewLine;
// Act
var result = _testUtility.Translator.TranslateStringToItemFilterBlock(inputString, _testUtility.MockItemFilterScript);
@ -857,10 +951,21 @@ namespace Filtration.Parser.Tests.Services
var shapedMapBlockItem = result.BlockItems.OfType<ShapedMapBlockItem>().First();
Assert.IsTrue(shapedMapBlockItem.BooleanValue);
var elderMapBlockItem = result.BlockItems.OfType<ElderMapBlockItem>().First();
Assert.IsFalse(elderMapBlockItem.BooleanValue);
var dropLevelblockItem = result.BlockItems.OfType<DropLevelBlockItem>().First();
Assert.AreEqual(FilterPredicateOperator.LessThan, dropLevelblockItem.FilterPredicate.PredicateOperator);
Assert.AreEqual(70, dropLevelblockItem.FilterPredicate.PredicateOperand);
var gemLevelBlockItem = result.BlockItems.OfType<GemLevelBlockItem>().First();
Assert.AreEqual(FilterPredicateOperator.Equal, gemLevelBlockItem.FilterPredicate.PredicateOperator);
Assert.AreEqual(20, gemLevelBlockItem.FilterPredicate.PredicateOperand);
var stackSizeBlockItem = result.BlockItems.OfType<StackSizeBlockItem>().First();
Assert.AreEqual(FilterPredicateOperator.GreaterThan, stackSizeBlockItem.FilterPredicate.PredicateOperator);
Assert.AreEqual(2, stackSizeBlockItem.FilterPredicate.PredicateOperand);
var qualityblockItem = result.BlockItems.OfType<QualityBlockItem>().First();
Assert.AreEqual(FilterPredicateOperator.Equal, qualityblockItem.FilterPredicate.PredicateOperator);
Assert.AreEqual(15, qualityblockItem.FilterPredicate.PredicateOperand);
@ -880,6 +985,11 @@ namespace Filtration.Parser.Tests.Services
Assert.Contains("MyBaseType", baseTypeblockItem.Items);
Assert.Contains("Another BaseType", baseTypeblockItem.Items);
var hasExplicitModBlockItem = result.BlockItems.OfType<HasExplicitModBlockItem>().First();
Assert.AreEqual(2, hasExplicitModBlockItem.Items.Count);
Assert.Contains("MyMod", hasExplicitModBlockItem.Items);
Assert.Contains("Another Mod", hasExplicitModBlockItem.Items);
var socketsblockItem = result.BlockItems.OfType<SocketsBlockItem>().First();
Assert.AreEqual(FilterPredicateOperator.GreaterThanOrEqual, socketsblockItem.FilterPredicate.PredicateOperator);
Assert.AreEqual(3, socketsblockItem.FilterPredicate.PredicateOperand);
@ -917,6 +1027,9 @@ namespace Filtration.Parser.Tests.Services
var soundblockItem = result.BlockItems.OfType<SoundBlockItem>().First();
Assert.AreEqual("3", soundblockItem.Value);
Assert.AreEqual(79, soundblockItem.SecondValue);
var disableDropSoundBlockItem = result.BlockItems.OfType<DisableDropSoundBlockItem>().First();
Assert.IsFalse(disableDropSoundBlockItem.BooleanValue);
}
[Test]
@ -1151,6 +1264,8 @@ namespace Filtration.Parser.Tests.Services
var expectedResult = "Show";
// Act
// TODO: Shouldn't be set to edited this way
_testUtility.TestBlock.IsEdited = true;
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
// Assert
@ -1168,6 +1283,8 @@ namespace Filtration.Parser.Tests.Services
var child2BlockGroup = new ItemFilterBlockGroup("Child 2 Block Group", child1BlockGroup);
_testUtility.TestBlock.BlockGroup = child2BlockGroup;
// TODO: Shouldn't be set to edited this way
_testUtility.TestBlock.IsEdited = true;
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
@ -1183,6 +1300,8 @@ namespace Filtration.Parser.Tests.Services
var expectedResult = $"Show #{testInputActionBlockComment}";
_testUtility.TestBlock.BlockItems.OfType<ActionBlockItem>().First().Comment = testInputActionBlockComment;
// TODO: Shouldn't be set to edited this way
_testUtility.TestBlock.IsEdited = true;
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
@ -1334,6 +1453,38 @@ namespace Filtration.Parser.Tests.Services
Assert.AreEqual(expectedResult, result);
}
[Test]
public void TranslateItemFilterBlockToString_GemLevel_ReturnsCorrectString()
{
// Arrange
var expectedResult = "Show" + Environment.NewLine +
" GemLevel <= 15";
_testUtility.TestBlock.BlockItems.Add(new GemLevelBlockItem(FilterPredicateOperator.LessThanOrEqual, 15));
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
// Assert
Assert.AreEqual(expectedResult, result);
}
[Test]
public void TranslateItemFilterBlockToString_StackSize_ReturnsCorrectString()
{
// Arrange
var expectedResult = "Show" + Environment.NewLine +
" StackSize = 5";
_testUtility.TestBlock.BlockItems.Add(new StackSizeBlockItem(FilterPredicateOperator.Equal, 5));
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
// Assert
Assert.AreEqual(expectedResult, result);
}
[Test]
public void TranslateItemFilterBlockToString_Quality_ReturnsCorrectString()
{
@ -1425,6 +1576,26 @@ namespace Filtration.Parser.Tests.Services
Assert.AreEqual(expectedResult, result);
}
[Test]
public void TranslateItemFilterBlockToString_HasExplicitMod_ReturnsCorrectString()
{
// Arrange
var expectedResult = "Show" + Environment.NewLine +
" HasExplicitMod \"Test Mod\" \"Another Mod\" \"Yet Another Mod\"";
var hasExplicitModBlockItem = new HasExplicitModBlockItem();
hasExplicitModBlockItem.Items.Add("Test Mod");
hasExplicitModBlockItem.Items.Add("Another Mod");
hasExplicitModBlockItem.Items.Add("Yet Another Mod");
_testUtility.TestBlock.BlockItems.Add(hasExplicitModBlockItem);
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);
// Assert
Assert.AreEqual(expectedResult, result);
}
[Test]
public void TranslateItemFilterBlockToString_Sockets_ReturnsCorrectString()
{
@ -1533,7 +1704,7 @@ namespace Filtration.Parser.Tests.Services
var blockItem = new TextColorBlockItem(new Color {A = 255, R = 54, G = 102, B = 255})
{
ThemeComponent = new ThemeComponent(ThemeComponentType.TextColor, "Test Theme Component", new Color())
ThemeComponent = new ColorThemeComponent(ThemeComponentType.TextColor, "Test Theme Component", new Color())
};
_testUtility.TestBlock.BlockItems.Add(blockItem);
@ -1671,10 +1842,8 @@ namespace Filtration.Parser.Tests.Services
public void TranslateItemFilterBlockToString_DisabledBlock_ReturnsCorrectString()
{
// Arrange
var expectedResult = "#Disabled Block Start" + Environment.NewLine +
"#Show" + Environment.NewLine +
"# Width = 4" + Environment.NewLine +
"#Disabled Block End";
var expectedResult = "#Show" + Environment.NewLine +
"# Width = 4";
_testUtility.TestBlock.Enabled = false;
@ -1700,20 +1869,25 @@ namespace Filtration.Parser.Tests.Services
" ElderItem True" + Environment.NewLine +
" ShaperItem False" + Environment.NewLine +
" ShapedMap True" + Environment.NewLine +
" ElderMap True" + Environment.NewLine +
" Height <= 6" + Environment.NewLine +
" Height >= 2" + Environment.NewLine +
" Width = 3" + Environment.NewLine +
" ItemLevel > 70" + Environment.NewLine +
" ItemLevel <= 85" + Environment.NewLine +
" DropLevel > 56" + Environment.NewLine +
" GemLevel < 15" + Environment.NewLine +
" StackSize >= 4" + Environment.NewLine +
" Rarity = Unique" + Environment.NewLine +
" Class \"Body Armour\" \"Gloves\" \"Belt\" \"Two Hand Axes\"" + Environment.NewLine +
" BaseType \"Greater Life Flask\" \"Simple Robe\" \"Full Wyrmscale\"" + Environment.NewLine +
" HasExplicitMod \"Guatelitzi's\" \"of Tacati\" \"Tyrannical\"" + Environment.NewLine +
" SetTextColor 255 89 0 56" + Environment.NewLine +
" SetBackgroundColor 0 0 0" + Environment.NewLine +
" SetBorderColor 255 1 254" + Environment.NewLine +
" SetFontSize 50" + Environment.NewLine +
" PlayAlertSound 6 90";
" PlayAlertSound 6 90" + Environment.NewLine +
" DisableDropSound True";
_testUtility.TestBlock.BlockItems.Add(new ActionBlockItem(BlockAction.Show));
_testUtility.TestBlock.BlockItems.Add(new IdentifiedBlockItem(true));
@ -1722,6 +1896,8 @@ namespace Filtration.Parser.Tests.Services
_testUtility.TestBlock.BlockItems.Add(new ItemLevelBlockItem(FilterPredicateOperator.GreaterThan, 70));
_testUtility.TestBlock.BlockItems.Add(new ItemLevelBlockItem(FilterPredicateOperator.LessThanOrEqual, 85));
_testUtility.TestBlock.BlockItems.Add(new DropLevelBlockItem(FilterPredicateOperator.GreaterThan, 56));
_testUtility.TestBlock.BlockItems.Add(new GemLevelBlockItem(FilterPredicateOperator.LessThan, 15));
_testUtility.TestBlock.BlockItems.Add(new StackSizeBlockItem(FilterPredicateOperator.GreaterThanOrEqual, 4));
_testUtility.TestBlock.BlockItems.Add(new QualityBlockItem(FilterPredicateOperator.GreaterThan, 2));
_testUtility.TestBlock.BlockItems.Add(new RarityBlockItem(FilterPredicateOperator.Equal, (int)ItemRarity.Unique));
var classItemblockItem = new ClassBlockItem();
@ -1735,6 +1911,11 @@ namespace Filtration.Parser.Tests.Services
baseTypeItemblockItem.Items.Add("Simple Robe");
baseTypeItemblockItem.Items.Add("Full Wyrmscale");
_testUtility.TestBlock.BlockItems.Add(baseTypeItemblockItem);
var hasExplicitModBlockItem = new HasExplicitModBlockItem();
hasExplicitModBlockItem.Items.Add("Guatelitzi's");
hasExplicitModBlockItem.Items.Add("of Tacati");
hasExplicitModBlockItem.Items.Add("Tyrannical");
_testUtility.TestBlock.BlockItems.Add(hasExplicitModBlockItem);
_testUtility.TestBlock.BlockItems.Add(new SocketsBlockItem(FilterPredicateOperator.LessThanOrEqual, 6));
_testUtility.TestBlock.BlockItems.Add(new LinkedSocketsBlockItem(FilterPredicateOperator.GreaterThanOrEqual, 4));
_testUtility.TestBlock.BlockItems.Add(new WidthBlockItem(FilterPredicateOperator.Equal, 3));
@ -1748,6 +1929,8 @@ namespace Filtration.Parser.Tests.Services
_testUtility.TestBlock.BlockItems.Add(new ElderItemBlockItem(true));
_testUtility.TestBlock.BlockItems.Add(new ShaperItemBlockItem(false));
_testUtility.TestBlock.BlockItems.Add(new ShapedMapBlockItem(true));
_testUtility.TestBlock.BlockItems.Add(new ElderMapBlockItem(true));
_testUtility.TestBlock.BlockItems.Add(new DisableDropSoundBlockItem(true));
// Act
var result = _testUtility.Translator.TranslateItemFilterBlockToString(_testUtility.TestBlock);

View File

@ -27,6 +27,7 @@ namespace Filtration.Parser.Tests.Services
}
[Test]
[Ignore("Outdated item filter")]
public void TranslateStringToItemFilterScript_ReturnsScriptWithCorrectNumberOfBlocks()
{
// Arrange
@ -40,7 +41,7 @@ namespace Filtration.Parser.Tests.Services
// Assert
Assert.AreEqual(5, script.ItemFilterBlocks.Count);
mockItemFilterBlockTranslator.Verify(t => t.TranslateStringToItemFilterBlock(It.IsAny<string>(), It.IsAny<IItemFilterScript>(), false));
mockItemFilterBlockTranslator.Verify(t => t.TranslateStringToItemFilterBlock(It.IsAny<string>(), It.IsAny<IItemFilterScript>(), "", false));
}
[Test]
@ -95,13 +96,29 @@ namespace Filtration.Parser.Tests.Services
// Assert
var expectedResult = Mock.Of<IItemFilterScript>(s => s.ItemFilterBlocks == new ObservableCollection<IItemFilterBlockBase>
{
Mock.Of<IItemFilterBlock>(c => c.Description == "Blockdescription"),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == " commentymccommentface"),
Mock.Of<IItemFilterBlock>(),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "commment\r\nmorecomment\r\nblah"),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "anothercomment"),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "notpartofblockdescription "),
Mock.Of<IItemFilterBlock>(c => c.Description == "blockdescription2")
Mock.Of<IItemFilterBlock>(c => c.Description == "Blockdescription"
&& c.OriginalText == "#Blockdescription" + Environment.NewLine +
"Show #Flasks - Endgame - Life/Mana - Divine/Eternal - Q10+ - Normal" + Environment.NewLine +
" Class \"Life Flasks\" \"Mana Flasks\"" + Environment.NewLine +
" Rarity Normal" + Environment.NewLine +
" SetFontSize 28"
),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == " commentymccommentface" && c.OriginalText == "# commentymccommentface"),
Mock.Of<IItemFilterBlock>(c => c.OriginalText == "Show" + Environment.NewLine +
" Class \"Life Flasks\" \"Mana Flasks\"" + Environment.NewLine +
" Rarity Normal" + Environment.NewLine +
" DropLevel >= 60"
),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "commment\r\nmorecomment\r\nblah"
&& c.OriginalText == "#commment" + Environment.NewLine + "#morecomment" + Environment.NewLine + "#blah"),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "anothercomment" && c.OriginalText == "#anothercomment"),
Mock.Of<IItemFilterCommentBlock>(c => c.Comment == "notpartofblockdescription " && c.OriginalText == "#notpartofblockdescription "),
Mock.Of<IItemFilterBlock>(c => c.Description == "blockdescription2"
&& c.OriginalText == "#blockdescription2" + Environment.NewLine +
"Show #TestBlock" + Environment.NewLine +
" Class \"Life Flasks\" \"Mana Flasks\"" + Environment.NewLine +
" Rarity Normal "
)
} && s.ItemFilterBlockGroups == new ObservableCollection<ItemFilterBlockGroup> { new ItemFilterBlockGroup("Root", null, false) }
&& s.ThemeComponents == new ThemeComponentCollection()
&& s.ItemFilterScriptSettings == new ItemFilterScriptSettings(new ThemeComponentCollection())
@ -155,7 +172,7 @@ namespace Filtration.Parser.Tests.Services
script.ItemFilterBlocks.Add(block1);
script.ItemFilterBlocks.Add(block2);
var expectedOutput = "# Script edited with Filtration - https://github.com/ben-wallis/Filtration" + Environment.NewLine +
var expectedOutput = "# Script edited with Filtration - https://github.com/ben-wallis/Filtration" + Environment.NewLine + Environment.NewLine +
"# Test Filter 1" + Environment.NewLine +
"Show" + Environment.NewLine +
" ItemLevel > 5" + Environment.NewLine +

View File

@ -30,9 +30,10 @@ namespace Filtration.Parser.Services
}
// Converts a string into an ItemFilterCommentBlock maintaining newlines and spaces but removing # characters
public IItemFilterCommentBlock TranslateStringToItemFilterCommentBlock(string inputString, IItemFilterScript parentItemFilterScript)
public IItemFilterCommentBlock TranslateStringToItemFilterCommentBlock(string inputString, IItemFilterScript parentItemFilterScript, string originalString = "")
{
var itemFilterCommentBlock = new ItemFilterCommentBlock(parentItemFilterScript);
itemFilterCommentBlock.OriginalText = originalString;
foreach (var line in new LineReader(() => new StringReader(inputString)))
{
@ -42,12 +43,13 @@ namespace Filtration.Parser.Services
itemFilterCommentBlock.Comment = itemFilterCommentBlock.Comment.TrimEnd('\r', '\n');
itemFilterCommentBlock.IsEdited = false;
return itemFilterCommentBlock;
}
// This method converts a string into a ItemFilterBlock. This is used for pasting ItemFilterBlocks
// and reading ItemFilterScripts from a file.
public IItemFilterBlock TranslateStringToItemFilterBlock(string inputString, IItemFilterScript parentItemFilterScript, bool initialiseBlockGroupHierarchyBuilder = false)
public IItemFilterBlock TranslateStringToItemFilterBlock(string inputString, IItemFilterScript parentItemFilterScript, string originalString = "", bool initialiseBlockGroupHierarchyBuilder = false)
{
if (initialiseBlockGroupHierarchyBuilder)
{
@ -57,6 +59,7 @@ namespace Filtration.Parser.Services
_masterComponentCollection = parentItemFilterScript.ItemFilterScriptSettings.ThemeComponentCollection;
var block = new ItemFilterBlock(parentItemFilterScript);
var showHideFound = false;
block.OriginalText = originalString;
foreach (var line in new LineReader(() => new StringReader(inputString)))
{
@ -214,11 +217,15 @@ namespace Filtration.Parser.Services
// Only ever use the last SetFontSize item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<FontSizeBlockItem>(block);
var match = Regex.Match(trimmedLine, @"\s+(\d+)");
if (match.Success)
var match = Regex.Matches(trimmedLine, @"(\s+(\d+)\s*)([#]?)(.*)");
if (match.Count > 0)
{
var blockItemValue = new FontSizeBlockItem(Convert.ToInt16(match.Value));
block.BlockItems.Add(blockItemValue);
var blockItem = new FontSizeBlockItem(Convert.ToInt16(match[0].Groups[2].Value));
if(match[0].Groups[3].Value == "#" && !string.IsNullOrWhiteSpace(match[0].Groups[4].Value))
{
blockItem.ThemeComponent = _masterComponentCollection.AddComponent(ThemeComponentType.FontSize, match[0].Groups[4].Value.Trim(), blockItem.Value);
}
block.BlockItems.Add(blockItem);
}
break;
}
@ -228,8 +235,9 @@ namespace Filtration.Parser.Services
// Only ever use the last PlayAlertSound item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<SoundBlockItem>(block);
RemoveExistingBlockItemsOfType<PositionalSoundBlockItem>(block);
RemoveExistingBlockItemsOfType<CustomSoundBlockItem>(block);
var match = Regex.Match(trimmedLine, @"\S+\s+(\S+)\s?(\d+)?");
var match = Regex.Match(trimmedLine, @"\S+\s+(\S+)\s?(\d+)?\s*([#]?)(.*)");
if (match.Success)
{
@ -245,6 +253,12 @@ namespace Filtration.Parser.Services
secondValue = 79;
}
ThemeComponent themeComponent = null;
if(match.Groups[3].Value == "#" && !string.IsNullOrWhiteSpace(match.Groups[4].Value))
{
themeComponent = _masterComponentCollection.AddComponent(ThemeComponentType.AlertSound, match.Groups[4].Value.Trim(), firstValue, secondValue);
}
if (lineOption == "PlayAlertSound")
{
var blockItemValue = new SoundBlockItem
@ -252,6 +266,7 @@ namespace Filtration.Parser.Services
Value = firstValue,
SecondValue = secondValue
};
blockItemValue.ThemeComponent = themeComponent;
block.BlockItems.Add(blockItemValue);
}
else
@ -261,14 +276,129 @@ namespace Filtration.Parser.Services
Value = firstValue,
SecondValue = secondValue
};
blockItemValue.ThemeComponent = themeComponent;
block.BlockItems.Add(blockItemValue);
}
}
break;
}
case "GemLevel":
{
AddNumericFilterPredicateItemToBlockItems<GemLevelBlockItem>(block, trimmedLine);
break;
}
case "StackSize":
{
AddNumericFilterPredicateItemToBlockItems<StackSizeBlockItem>(block, trimmedLine);
break;
}
case "HasExplicitMod":
{
AddStringListItemToBlockItems<HasExplicitModBlockItem>(block, trimmedLine);
break;
}
case "ElderMap":
{
AddBooleanItemToBlockItems<ElderMapBlockItem>(block, trimmedLine);
break;
}
case "DisableDropSound":
{
// Only ever use the last DisableDropSound item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<DisableDropSoundBlockItem>(block);
AddBooleanItemToBlockItems<DisableDropSoundBlockItem>(block, trimmedLine);
break;
}
case "MinimapIcon":
{
// Only ever use the last Icon item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<MapIconBlockItem>(block);
// TODO: Get size, color, shape values programmatically
var match = Regex.Match(trimmedLine,
@"\S+\s+(0|1|2)\s+(Red|Green|Blue|Brown|White|Yellow)\s+(Circle|Diamond|Hexagon|Square|Star|Triangle)\s*([#]?)(.*)",
RegexOptions.IgnoreCase);
if (match.Success)
{
var blockItemValue = new MapIconBlockItem
{
Size = (IconSize)Int16.Parse(match.Groups[1].Value),
Color = EnumHelper.GetEnumValueFromDescription<IconColor>(match.Groups[2].Value),
Shape = EnumHelper.GetEnumValueFromDescription<IconShape>(match.Groups[3].Value)
};
if(match.Groups[4].Value == "#" && !string.IsNullOrWhiteSpace(match.Groups[5].Value))
{
ThemeComponent themeComponent = _masterComponentCollection.AddComponent(ThemeComponentType.Icon, match.Groups[5].Value.Trim(),
blockItemValue.Size, blockItemValue.Color, blockItemValue.Shape);
blockItemValue.ThemeComponent = themeComponent;
}
block.BlockItems.Add(blockItemValue);
}
break;
}
case "PlayEffect":
{
// Only ever use the last BeamColor item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<PlayEffectBlockItem>(block);
// TODO: Get colors programmatically
var match = Regex.Match(trimmedLine, @"\S+\s+(Red|Green|Blue|Brown|White|Yellow)\s+(Temp)?\s*([#]?)(.*)", RegexOptions.IgnoreCase);
if (match.Success)
{
var blockItemValue = new PlayEffectBlockItem
{
Color = EnumHelper.GetEnumValueFromDescription<EffectColor>(match.Groups[1].Value),
Temporary = match.Groups[2].Value.Trim().ToLower() == "temp"
};
if(match.Groups[3].Value == "#" && !string.IsNullOrWhiteSpace(match.Groups[4].Value))
{
ThemeComponent themeComponent = _masterComponentCollection.AddComponent(ThemeComponentType.Effect, match.Groups[4].Value.Trim(),
blockItemValue.Color, blockItemValue.Temporary);
blockItemValue.ThemeComponent = themeComponent;
}
block.BlockItems.Add(blockItemValue);
}
break;
}
case "CustomAlertSound":
{
// Only ever use the last CustomSoundBlockItem item encountered as multiples aren't valid.
RemoveExistingBlockItemsOfType<CustomSoundBlockItem>(block);
RemoveExistingBlockItemsOfType<SoundBlockItem>(block);
RemoveExistingBlockItemsOfType<PositionalSoundBlockItem>(block);
var match = Regex.Match(trimmedLine, @"\S+\s+""(\S+)""\s*([#]?)(.*)");
if (match.Success)
{
var blockItemValue = new CustomSoundBlockItem
{
Value = match.Groups[1].Value
};
if(match.Groups[2].Value == "#" && !string.IsNullOrWhiteSpace(match.Groups[3].Value))
{
ThemeComponent themeComponent = _masterComponentCollection.AddComponent(ThemeComponentType.CustomSound, match.Groups[3].Value.Trim(), blockItemValue.Value);
blockItemValue.ThemeComponent = themeComponent;
}
block.BlockItems.Add(blockItemValue);
}
break;
}
case "MapTier":
{
AddNumericFilterPredicateItemToBlockItems<MapTierBlockItem>(block, trimmedLine);
break;
}
}
}
block.IsEdited = false;
return block;
}
@ -284,6 +414,7 @@ namespace Filtration.Parser.Services
private static void AddBooleanItemToBlockItems<T>(IItemFilterBlock block, string inputString) where T : BooleanBlockItem
{
inputString = Regex.Replace(inputString, @"\s+", " ");
var blockItem = Activator.CreateInstance<T>();
var splitString = inputString.Split(' ');
if (splitString.Length == 2)
@ -487,6 +618,11 @@ namespace Filtration.Parser.Services
// TODO: Private
public string TranslateItemFilterCommentBlockToString(IItemFilterCommentBlock itemFilterCommentBlock)
{
if (!itemFilterCommentBlock.IsEdited)
{
return itemFilterCommentBlock.OriginalText;
}
// TODO: Tests
// TODO: # Section: text?
var commentWithHashes = string.Empty;
@ -506,13 +642,13 @@ namespace Filtration.Parser.Services
// TODO: Private
public string TranslateItemFilterBlockToString(IItemFilterBlock block)
{
var outputString = string.Empty;
if (!block.Enabled)
if(!block.IsEdited)
{
outputString += "#Disabled Block Start" + Environment.NewLine;
return block.OriginalText;
}
var outputString = string.Empty;
if (!string.IsNullOrEmpty(block.Description))
{
outputString += "# " + block.Description + Environment.NewLine;
@ -538,10 +674,11 @@ namespace Filtration.Parser.Services
}
}
if (!block.Enabled)
{
outputString += Environment.NewLine + "#Disabled Block End";
}
//TODO: Disabled for the time being. A better solution is needed.
// Replace 'Maelström' to prevent encoding problems in other editors
//outputString.Replace("Maelström Staff", "Maelstr");
//outputString.Replace("Maelström of Chaos", "Maelstr");
//outputString.Replace("Maelström", "Maelstr");
return outputString;
}

View File

@ -51,60 +51,35 @@ namespace Filtration.Parser.Services
public static string PreprocessDisabledBlocks(string inputString)
{
bool inDisabledBlock = false;
var showHideFound = false;
var lines = Regex.Split(inputString, "\r\n|\r|\n").ToList();
var linesToRemove = new List<int>();
for (var i = 0; i < lines.Count; i++)
{
if (lines[i].StartsWith("#Disabled Block Start"))
if (!inDisabledBlock && lines[i].StartsWith("#"))
{
string curLine = Regex.Replace(lines[i].Substring(1), @"\s+", "");
if ((curLine.StartsWith("Show") || curLine.StartsWith("Hide")) && (curLine.Length == 4 || curLine[4] == '#'))
{
inDisabledBlock = true;
linesToRemove.Add(i);
lines[i] = lines[i].Substring(1).TrimStart(' ');
lines[i] = lines[i].Substring(0, 4) + "Disabled" + lines[i].Substring(4);
continue;
}
}
if (inDisabledBlock)
{
if (lines[i].StartsWith("#Disabled Block End"))
if (!lines[i].StartsWith("#"))
{
inDisabledBlock = false;
showHideFound = false;
linesToRemove.Add(i);
continue;
}
lines[i] = lines[i].TrimStart('#');
lines[i] = lines[i].Replace("#", " # ");
var spaceOrEndOfLinePos = lines[i].IndexOf(" ", StringComparison.Ordinal) > 0 ? lines[i].IndexOf(" ", StringComparison.Ordinal) : lines[i].Length;
var lineOption = lines[i].Substring(0, spaceOrEndOfLinePos);
// If we haven't found a Show or Hide line yet, then this is probably the block comment.
// Put its # back on and skip to the next line.
if (lineOption != "Show" && lineOption != "Hide" && showHideFound == false)
else
{
lines[i] = "#" + lines[i];
continue;
}
if (lineOption == "Show")
{
lines[i] = lines[i].Replace("Show", "ShowDisabled");
showHideFound = true;
}
else if (lineOption == "Hide")
{
lines[i] = lines[i].Replace("Hide", "HideDisabled");
showHideFound = true;
lines[i] = lines[i].Substring(1);
}
}
}
for (var i = linesToRemove.Count - 1; i >= 0; i--)
{
lines.RemoveAt(linesToRemove[i]);
}
return lines.Aggregate((c, n) => c + Environment.NewLine + n);
}
@ -113,11 +88,14 @@ namespace Filtration.Parser.Services
var script = _itemFilterScriptFactory.Create();
_blockGroupHierarchyBuilder.Initialise(script.ItemFilterBlockGroups.First());
//Remove old disabled tags
inputString = Regex.Replace(inputString, @"#Disabled\sBlock\s(Start|End).*?\n", "");
inputString = (inputString.EndsWith("\n#Disabled Block End")) ? inputString.Substring(0, inputString.Length - 19) : inputString;
var originalLines = Regex.Split(inputString, "\r\n|\r|\n");
inputString = inputString.Replace("\t", "");
if (inputString.Contains("#Disabled Block Start"))
{
inputString = PreprocessDisabledBlocks(inputString);
}
var conditionBoundaries = IdentifyBlockBoundaries(inputString);
@ -155,14 +133,24 @@ namespace Filtration.Parser.Services
var block = new string[end - begin];
Array.Copy(lines, begin, block, 0, end - begin);
var blockString = string.Join("\r\n", block);
Array.Copy(originalLines, begin, block, 0, end - begin);
var originalString = "";
for (var i = block.Length - 1; i >= 0; i--)
{
if(block[i].Replace(" ", "").Replace("\t", "").Length > 0)
{
originalString = string.Join("\r\n", block, 0, i + 1);
break;
}
}
if (boundary.Value.BoundaryType == ItemFilterBlockBoundaryType.ItemFilterBlock)
{
script.ItemFilterBlocks.Add(_blockTranslator.TranslateStringToItemFilterBlock(blockString, script));
script.ItemFilterBlocks.Add(_blockTranslator.TranslateStringToItemFilterBlock(blockString, script, originalString));
}
else
{
script.ItemFilterBlocks.Add(_blockTranslator.TranslateStringToItemFilterCommentBlock(blockString, script));
script.ItemFilterBlocks.Add(_blockTranslator.TranslateStringToItemFilterCommentBlock(blockString, script, originalString));
}
}
@ -251,8 +239,8 @@ namespace Filtration.Parser.Services
outputString += "# " + line + Environment.NewLine;
}
}
outputString += Environment.NewLine;
}
outputString += Environment.NewLine;
// ReSharper disable once LoopCanBeConvertedToQuery
foreach (var block in script.ItemFilterBlocks)

View File

@ -107,6 +107,9 @@
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
</EmbeddedResource>
</ItemGroup>
<ItemGroup>
<Service Include="{82A7F48D-3B50-4B1E-B82E-3ADA8210C358}" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\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

@ -73,6 +73,9 @@
<ItemGroup>
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Service Include="{82A7F48D-3B50-4B1E-B82E-3ADA8210C358}" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\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

@ -26,7 +26,7 @@ namespace Filtration.ThemeEditor.Tests.Services
var testInputTheme = new Theme();
var testInputThemeComponentColor = new Color{ R = 255, G = 0, B = 1 };
var testInputThemeComponent = new ThemeComponent(ThemeComponentType.TextColor, "Test Component 1", testInputThemeComponentColor);
var testInputThemeComponent = new ColorThemeComponent(ThemeComponentType.TextColor, "Test Component 1", testInputThemeComponentColor);
testInputTheme.Components.Add(testInputThemeComponent);
testInputBlockItem.ThemeComponent = testInputThemeComponent;
var mockMessageBoxService = new Mock<IMessageBoxService>();
@ -53,8 +53,8 @@ namespace Filtration.ThemeEditor.Tests.Services
var testInputTheme = new Theme();
var testInputThemeComponentColor = new Color { R = 255, G = 0, B = 1 };
var testInputThemeComponent = new ThemeComponent(ThemeComponentType.TextColor, "Test Component 1", testInputThemeComponentColor);
var testInputBlockItemThemeComponent = new ThemeComponent(ThemeComponentType.TextColor, "Different Component", testInputThemeComponentColor);
var testInputThemeComponent = new ColorThemeComponent(ThemeComponentType.TextColor, "Test Component 1", testInputThemeComponentColor);
var testInputBlockItemThemeComponent = new ColorThemeComponent(ThemeComponentType.TextColor, "Different Component", testInputThemeComponentColor);
testInputTheme.Components.Add(testInputThemeComponent);
testInputBlockItem.ThemeComponent = testInputBlockItemThemeComponent;

View File

@ -31,6 +31,18 @@ namespace Filtration.ThemeEditor.Converters
{
return "Background Color Theme Components";
}
case "Font Size":
{
return "Font Size Theme Components";
}
case "Alert Sound":
{
return "Alert Sound Theme Components";
}
case "Custom Sound":
{
return "Custom Alert Sound Theme Components";
}
}
return type.GetAttributeDescription();

View File

@ -108,6 +108,12 @@
<Compile Include="Providers\ThemeProvider.cs" />
<Compile Include="Services\ThemePersistenceService.cs" />
<Compile Include="Services\ThemeService.cs" />
<Compile Include="ViewModels\ColorThemeComponentViewModel.cs" />
<Compile Include="ViewModels\EffectColorThemeComponentViewModel.cs" />
<Compile Include="ViewModels\IconThemeComponentViewModel.cs" />
<Compile Include="ViewModels\StringThemeComponentViewModel.cs" />
<Compile Include="ViewModels\StrIntThemeComponentViewModel.cs" />
<Compile Include="ViewModels\IntegerThemeComponentViewModel.cs" />
<Compile Include="ViewModels\IThemeViewModelFactory.cs" />
<Compile Include="ViewModels\ThemeComponentViewModel.cs" />
<Compile Include="ViewModels\ThemeEditorViewModel.cs" />
@ -135,7 +141,10 @@
<Name>Filtration.ObjectModel</Name>
</ProjectReference>
</ItemGroup>
<ItemGroup />
<ItemGroup>
<Resource Include="Resources\open_icon.png" />
<Resource Include="Resources\speaker_icon.png" />
</ItemGroup>
<ItemGroup>
<Page Include="Views\ThemeComponentControl.xaml">
<SubType>Designer</SubType>

View File

@ -3,6 +3,7 @@ using System.Linq;
using System.Threading.Tasks;
using AutoMapper;
using Filtration.ObjectModel;
using Filtration.ObjectModel.Enums;
using Filtration.ObjectModel.ThemeEditor;
using Filtration.ThemeEditor.Services;
using Filtration.ThemeEditor.ViewModels;
@ -34,7 +35,20 @@ namespace Filtration.ThemeEditor.Providers
var themeComponentCollection = script.ThemeComponents.Aggregate(new ThemeComponentCollection(),
(c, component) =>
{
c.Add(new ThemeComponent(component.ComponentType, component.ComponentName, component.Color));
switch(component.ComponentType)
{
case ThemeComponentType.BackgroundColor:
case ThemeComponentType.BorderColor:
case ThemeComponentType.TextColor:
c.Add(new ColorThemeComponent(component.ComponentType, component.ComponentName, ((ColorThemeComponent)component).Color));
break;
case ThemeComponentType.FontSize:
c.Add(new IntegerThemeComponent(component.ComponentType, component.ComponentName, ((IntegerThemeComponent)component).Value));
break;
case ThemeComponentType.AlertSound:
c.Add(new StrIntThemeComponent(component.ComponentType, component.ComponentName, ((StrIntThemeComponent)component).Value, ((StrIntThemeComponent)component).SecondValue));
break;
}
return c;
});

Binary file not shown.

After

Width:  |  Height:  |  Size: 411 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

View File

@ -1,4 +1,5 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows;
using Filtration.Common.Services;
@ -29,38 +30,25 @@ namespace Filtration.ThemeEditor.Services
var mismatchedComponents = false;
foreach (var component in theme.Components)
{
var componentMatched = false;
Type targetType = null;
var blocks = script.ItemFilterBlocks.OfType<ItemFilterBlock>();
switch (component.ComponentType)
{
case ThemeComponentType.BackgroundColor:
targetType = typeof (BackgroundColorBlockItem);
mismatchedComponents = ApplyColorTheme(blocks, typeof(BackgroundColorBlockItem), component);
break;
case ThemeComponentType.TextColor:
targetType = typeof (TextColorBlockItem);
mismatchedComponents = ApplyColorTheme(blocks, typeof(TextColorBlockItem), component);
break;
case ThemeComponentType.BorderColor:
targetType = typeof (BorderColorBlockItem);
mismatchedComponents = ApplyColorTheme(blocks, typeof(BorderColorBlockItem), component);
break;
case ThemeComponentType.FontSize:
mismatchedComponents = ApplyIntegerTheme(blocks, typeof(FontSizeBlockItem), component);
break;
case ThemeComponentType.AlertSound:
mismatchedComponents = ApplyStrIntTheme(blocks, typeof(SoundBlockItem), component);
mismatchedComponents = ApplyStrIntTheme(blocks, typeof(PositionalSoundBlockItem), component);
break;
}
foreach (var block in script.ItemFilterBlocks.OfType<ItemFilterBlock>())
{
foreach (var blockItem in block.BlockItems.Where(i => i.GetType() == targetType))
{
var colorBlockItem = (ColorBlockItem) blockItem;
if (colorBlockItem.ThemeComponent != null &&
colorBlockItem.ThemeComponent.ComponentName == component.ComponentName)
{
colorBlockItem.Color = component.Color;
componentMatched = true;
}
}
}
if (!componentMatched)
{
mismatchedComponents = true;
}
}
@ -71,5 +59,66 @@ namespace Filtration.ThemeEditor.Services
MessageBoxButton.OK, MessageBoxImage.Exclamation);
}
}
private bool ApplyColorTheme(IEnumerable<ItemFilterBlock> blocks, Type type, ThemeComponent component)
{
var componentMatched = false;
foreach (var block in blocks)
{
foreach (var blockItem in block.BlockItems.Where(i => i.GetType() == type))
{
var colorBlockItem = (ColorBlockItem)blockItem;
if (colorBlockItem.ThemeComponent != null &&
colorBlockItem.ThemeComponent.ComponentName == component.ComponentName)
{
colorBlockItem.Color = ((ColorThemeComponent)component).Color;
componentMatched = true;
}
}
}
return !componentMatched;
}
private bool ApplyIntegerTheme(IEnumerable<ItemFilterBlock> blocks, Type type, ThemeComponent component)
{
var componentMatched = false;
foreach (var block in blocks)
{
foreach (var blockItem in block.BlockItems.Where(i => i.GetType() == type))
{
var colorBlockItem = (IntegerBlockItem)blockItem;
if (colorBlockItem.ThemeComponent != null &&
colorBlockItem.ThemeComponent.ComponentName == component.ComponentName)
{
colorBlockItem.Value = ((IntegerThemeComponent)component).Value;
componentMatched = true;
}
}
}
return !componentMatched;
}
private bool ApplyStrIntTheme(IEnumerable<ItemFilterBlock> blocks, Type type, ThemeComponent component)
{
var componentMatched = false;
foreach (var block in blocks)
{
foreach (var blockItem in block.BlockItems.Where(i => i.GetType() == type))
{
var colorBlockItem = (StrIntBlockItem)blockItem;
if (colorBlockItem.ThemeComponent != null &&
colorBlockItem.ThemeComponent.ComponentName == component.ComponentName)
{
colorBlockItem.Value = ((StrIntThemeComponent)component).Value;
colorBlockItem.SecondValue = ((StrIntThemeComponent)component).SecondValue;
componentMatched = true;
}
}
}
return !componentMatched;
}
}
}

View File

@ -0,0 +1,9 @@
using System.Windows.Media;
namespace Filtration.ThemeEditor.ViewModels
{
public class ColorThemeComponentViewModel : ThemeComponentViewModel
{
public Color Color { get; set; }
}
}

View File

@ -0,0 +1,10 @@
using Filtration.ObjectModel.Enums;
namespace Filtration.ThemeEditor.ViewModels
{
public class EffectColorThemeComponentViewModel : ThemeComponentViewModel
{
public EffectColor EffectColor { get; set; }
public bool Temporary { get; set; }
}
}

View File

@ -0,0 +1,11 @@
using Filtration.ObjectModel.Enums;
namespace Filtration.ThemeEditor.ViewModels
{
public class IconThemeComponentViewModel : ThemeComponentViewModel
{
public IconSize IconSize { get; set; }
public IconColor IconColor { get; set; }
public IconShape IconShape { get; set; }
}
}

View File

@ -0,0 +1,7 @@
namespace Filtration.ThemeEditor.ViewModels
{
public class IntegerThemeComponentViewModel : ThemeComponentViewModel
{
public int Value { get; set; }
}
}

View File

@ -0,0 +1,8 @@
namespace Filtration.ThemeEditor.ViewModels
{
public class StrIntThemeComponentViewModel : ThemeComponentViewModel
{
public int Value { get; set; }
public int SecondValue { get; set; }
}
}

View File

@ -0,0 +1,9 @@
using System.Windows.Media;
namespace Filtration.ThemeEditor.ViewModels
{
public class StringThemeComponentViewModel : ThemeComponentViewModel
{
public string Value { get; set; }
}
}

View File

@ -7,13 +7,11 @@ namespace Filtration.ThemeEditor.ViewModels
{
string ComponentName { get; set; }
ThemeComponentType ComponentType { get; set; }
Color Color { get; set; }
}
public class ThemeComponentViewModel : IThemeComponentViewModel
{
public string ComponentName { get; set; }
public ThemeComponentType ComponentType { get; set; }
public Color Color { get; set; }
}
}

View File

@ -194,8 +194,30 @@ namespace Filtration.ThemeEditor.ViewModels
private void OnAddThemeComponentCommand(ThemeComponentType themeComponentType)
{
Components.Add(new ThemeComponent(themeComponentType, "Untitled Component",
switch (themeComponentType)
{
case ThemeComponentType.BackgroundColor:
case ThemeComponentType.BorderColor:
case ThemeComponentType.TextColor:
Components.Add(new ColorThemeComponent(themeComponentType, "Untitled Component",
new Color { A = 255, R = 255, G = 255, B = 255 }));
break;
case ThemeComponentType.FontSize:
Components.Add(new IntegerThemeComponent(themeComponentType, "Untitled Component", 35));
break;
case ThemeComponentType.AlertSound:
Components.Add(new StrIntThemeComponent(themeComponentType, "Untitled Component", "1", 100));
break;
case ThemeComponentType.CustomSound:
Components.Add(new StringThemeComponent(themeComponentType, "Untitled Component", "placeholder.mp3"));
break;
case ThemeComponentType.Icon:
Components.Add(new IconThemeComponent(themeComponentType, "Untitled Component", IconSize.Largest, IconColor.Red, IconShape.Circle));
break;
case ThemeComponentType.Effect:
Components.Add(new EffectColorThemeComponent(themeComponentType, "Untitled Component", EffectColor.Red, false));
break;
}
}
private void OnDeleteThemeComponentCommand(ThemeComponent themeComponent)

View File

@ -7,6 +7,8 @@
xmlns:commonConverters="clr-namespace:Filtration.Common.Converters;assembly=Filtration.Common"
xmlns:themeEditor="clr-namespace:Filtration.ObjectModel.ThemeEditor;assembly=Filtration.ObjectModel"
xmlns:views="clr-namespace:Filtration.ThemeEditor.Views"
xmlns:extensions="clr-namespace:Filtration.Common.Extensions;assembly=Filtration.Common"
xmlns:enums="clr-namespace:Filtration.ObjectModel.Enums;assembly=Filtration.ObjectModel"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance Type=themeEditor:ThemeComponent}"
d:DesignHeight="100" d:DesignWidth="200">
@ -17,7 +19,7 @@
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="25" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid.Resources>
<DataTemplate x:Key="EditableComponentNameTemplate">
@ -58,6 +60,79 @@
</Style>
</ContentControl.Style>
</ContentControl>
<xctk:ColorPicker Grid.Row="2" SelectedColor="{Binding Color}" />
<ContentControl Grid.Row="2" Content="{Binding Mode=OneWay}">
<ContentControl.Resources>
<!-- Color Theme Template -->
<DataTemplate DataType="{x:Type themeEditor:ColorThemeComponent}">
<xctk:ColorPicker SelectedColor="{Binding Color}" />
</DataTemplate>
<!-- Integer Theme Template -->
<DataTemplate DataType="{x:Type themeEditor:IntegerThemeComponent}">
<xctk:ShortUpDown Value="{Binding Value}" />
</DataTemplate>
<!-- String Integer Theme Template -->
<DataTemplate DataType="{x:Type themeEditor:StrIntThemeComponent}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<TextBox Grid.Column="0" Text="{Binding Value}" Height="25" Padding="2,-15,0,0" />
<xctk:ShortUpDown Grid.Column="1" Value="{Binding SecondValue}" HorizontalAlignment="Right"/>
</Grid>
</DataTemplate>
<!--TODO:File block type and string block type should be separate-->
<!-- Custom Sound Theme Template -->
<DataTemplate DataType="{x:Type themeEditor:StringThemeComponent}">
<Grid>
<!--TODO: Add play sound support-->
<!--<Button Grid.Column="0" Command="{Binding PlayCustomSoundCommand}" Width="20" Height="20" Background="Transparent" BorderBrush="Transparent">
<Image Source="/Filtration.ThemeEditor;component/Resources/speaker_icon.png" VerticalAlignment="Center" HorizontalAlignment="Center" />
</Button>-->
<ComboBox ItemsSource="{Binding CustomSoundsAvailable}"
SelectedValue="{Binding Value}" Style="{StaticResource MetroComboBox}"/>
<Button Command="{Binding CustomSoundFileDialogCommand}"
Width="20" Height="20" Background="Transparent" BorderBrush="Transparent" Margin="0,0,30,0" VerticalAlignment="Center" HorizontalAlignment="Right">
<Image Source="/Filtration.ThemeEditor;component/Resources/open_icon.png"/>
</Button>
</Grid>
</DataTemplate>
<!--Icon Theme Template-->
<DataTemplate DataType="{x:Type themeEditor:IconThemeComponent}">
<StackPanel Orientation="Vertical" Margin="5,5,5,5">
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconSize}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding IconSize}"
SelectedValuePath="Value" />
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconColor}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding IconColor}"
SelectedValuePath="Value" />
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconShape}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding IconShape}"
SelectedValuePath="Value" />
</StackPanel>
</DataTemplate>
<!--Effect Color Theme Template-->
<DataTemplate DataType="{x:Type themeEditor:EffectColorThemeComponent}">
<StackPanel>
<WrapPanel VerticalAlignment="Center" Margin="5,5,5,5">
<RadioButton IsChecked="{Binding Temporary, Converter={StaticResource BoolInverterConverter}}" Margin="0,0,10,0">Permanent</RadioButton>
<RadioButton IsChecked="{Binding Temporary}" >Temporary</RadioButton>
</WrapPanel>
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:EffectColor}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding EffectColor}"
SelectedValuePath="Value" />
</StackPanel>
</DataTemplate>
</ContentControl.Resources>
</ContentControl>
</Grid>
</UserControl>

View File

@ -46,6 +46,12 @@ namespace Filtration
cfg.ConstructServicesUsing(_container.Resolve);
cfg.CreateMap<Theme, IThemeEditorViewModel>().ConstructUsingServiceLocator();
cfg.CreateMap<ThemeComponent, ThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<ColorThemeComponent, ColorThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<IntegerThemeComponent, IntegerThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<StrIntThemeComponent, StrIntThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<StringThemeComponent, StringThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<IconThemeComponent, IconThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<EffectColorThemeComponent, EffectColorThemeComponentViewModel>().ReverseMap();
cfg.CreateMap<IThemeEditorViewModel, Theme>();
});

View File

@ -16,7 +16,7 @@ namespace Filtration.Converters
var themeComponentsList = values[0] as ThemeComponentCollection;
if (themeComponentsList == null || themeComponentsList.Count == 0) return null;
var blockItem = values[1] as ColorBlockItem;
var blockItem = values[1] as BlockItemBase;
if (blockItem == null) return null;
ThemeComponentType themeComponentType;
@ -33,6 +33,26 @@ namespace Filtration.Converters
{
themeComponentType = ThemeComponentType.BorderColor;
}
else if (blockItem.GetType() == typeof(FontSizeBlockItem))
{
themeComponentType = ThemeComponentType.FontSize;
}
else if (blockItem.GetType() == typeof(SoundBlockItem) || blockItem.GetType() == typeof(PositionalSoundBlockItem))
{
themeComponentType = ThemeComponentType.AlertSound;
}
else if (blockItem.GetType() == typeof(CustomSoundBlockItem))
{
themeComponentType = ThemeComponentType.CustomSound;
}
else if (blockItem.GetType() == typeof(MapIconBlockItem))
{
themeComponentType = ThemeComponentType.Icon;
}
else if (blockItem.GetType() == typeof(PlayEffectBlockItem))
{
themeComponentType = ThemeComponentType.Effect;
}
else
{
return null;

View File

@ -0,0 +1,37 @@
using Filtration.ObjectModel.Enums;
using System;
using System.Globalization;
using System.Windows.Data;
namespace Filtration.Converters
{
internal class IconShapeToSourceConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
var iconShape = (IconShape)(int)value;
switch (iconShape)
{
case IconShape.Circle:
return "/Filtration;component/Resources/DropIcons/Circle.png";
case IconShape.Diamond:
return "/Filtration;component/Resources/DropIcons/Diamond.png";
case IconShape.Hexagon:
return "/Filtration;component/Resources/DropIcons/Hexagon.png";
case IconShape.Square:
return "/Filtration;component/Resources/DropIcons/Square.png";
case IconShape.Star:
return "/Filtration;component/Resources/DropIcons/Star.png";
case IconShape.Triangle:
return "/Filtration;component/Resources/DropIcons/Triangle.png";
}
return "/Filtration;component/Resources/DropIcons/NoIcon.png";
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
}

View File

@ -0,0 +1,33 @@
using Filtration.ObjectModel.Enums;
using System;
using System.Globalization;
using System.Windows;
using System.Windows.Data;
namespace Filtration.Converters
{
internal class SizeColorToRectConverter : IMultiValueConverter
{
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
{
var size = (int)(values[0]);
var color = (int)(values[1]);
if (size < 0 || color < 0)
return new Rect(0, 0, 0, 0);
Rect cropArea = new Rect();
cropArea.Width = 64;
cropArea.Height = 64;
cropArea.X = 0 + size * 64;
cropArea.Y = 0 + color * 64;
return cropArea;
}
public object[] ConvertBack(object value, Type[] targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
}

View File

@ -167,11 +167,11 @@
<Compile Include="Converters\BooleanToBlockActionInverseConverter.cs" />
<Compile Include="Converters\BooleanToBlockActionConverter.cs" />
<Compile Include="Converters\BlockItemToRemoveEnabledVisibilityConverter.cs" />
<Compile Include="Converters\SizeColorToRectConverter.cs" />
<Compile Include="Converters\HashSignRemovalConverter.cs" />
<Compile Include="Converters\IconShapeToSourceConverter.cs" />
<Compile Include="Converters\ItemRarityConverter.cs" />
<Compile Include="Converters\TreeViewMarginConverter.cs" />
<Compile Include="Extensions\EnumerationExtension.cs" />
<Compile Include="Extensions\HyperlinkExtensions.cs" />
<Compile Include="Models\UpdateData.cs" />
<Compile Include="Properties\Annotations.cs" />
<Compile Include="Repositories\ItemFilterScriptRepository.cs" />
@ -190,6 +190,9 @@
<Compile Include="UserControls\EditableListBoxControl.xaml.cs">
<DependentUpon>EditableListBoxControl.xaml</DependentUpon>
</Compile>
<Compile Include="UserControls\ImageComboBoxControl.xaml.cs">
<DependentUpon>ImageComboBoxControl.xaml</DependentUpon>
</Compile>
<Compile Include="UserControls\ItemPreviewControl.xaml.cs">
<DependentUpon>ItemPreviewControl.xaml</DependentUpon>
</Compile>
@ -230,6 +233,10 @@
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="UserControls\ImageComboBoxControl.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="UserControls\ThemeComponentSelectionControl.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
@ -538,6 +545,13 @@
</None>
<Resource Include="Resources\Icons\redo_icon.png" />
<Resource Include="Resources\Icons\undo_icon.png" />
<Resource Include="Resources\DropIcons\NoIcon.png" />
<Resource Include="Resources\DropIcons\Circle.png" />
<Resource Include="Resources\DropIcons\Diamond.png" />
<Resource Include="Resources\DropIcons\Hexagon.png" />
<Resource Include="Resources\DropIcons\Square.png" />
<Resource Include="Resources\DropIcons\Star.png" />
<Resource Include="Resources\DropIcons\Triangle.png" />
<Content Include="Resources\ItemBaseTypes.txt" />
<Content Include="Resources\ItemClasses.txt" />
</ItemGroup>

Binary file not shown.

After

Width:  |  Height:  |  Size: 100 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 80 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 99 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 85 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 80 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 75 KiB

View File

@ -1,5 +1,6 @@
A Mother's Parting Gift
Abandoned Wealth
Aberrant Fossil
Abyssal Axe
Abyssal Cry
Abyssal Sceptre
@ -10,6 +11,7 @@ Added Cold Damage Support
Added Fire Damage Support
Added Lightning Damage Support
Additional Accuracy Support
Aetheric Fossil
Agate Amulet
Albino Rhoa Feather
Alchemy Shard
@ -111,9 +113,11 @@ Battle Sword
Bazaar Map
Beach Map
Bear Trap
Beauty Through Death
Behemoth Mace
Belfry Map
Bestel's Manuscript
Bestiary Orb
Beyond Leaguestone
Binding Shard
Birth of the Three
@ -131,6 +135,7 @@ Blast Rain
Blessed Orb
Blessing of Chayula
Blessing of Esh
Blessing of God
Blessing of Tul
Blessing of Uul-Netol
Blessing of Xoph
@ -146,6 +151,7 @@ Blood Raiment
Blood Sceptre
Bloodlines Leaguestone
Bloodlust Support
Bloodstained Fossil
Blue Pearl Amulet
Blunt Arrow Quiver
Boarding Axe
@ -159,9 +165,11 @@ Bone Helmet
Bone Offering
Bone Spirit Shield
Bonespire Talisman
Boon of the First Ones
Boot Blade
Boot Knife
Bottled Storm
Bound Fossil
Boundless Realms
Bowyer's Dream
Branded Kite Shield
@ -244,6 +252,7 @@ Chaos Orb
Chaos Shard
Chaotic Disposition
Charged Dash
Charged Traps Support
Chateau Map
Chayula's Breachstone
Chest Splitter
@ -290,6 +299,7 @@ Conjurer Boots
Conjurer Gloves
Conjurer's Vestment
Conquest Chainmail
Consecrated Path
Conservatory Map
Contagion
Controlled Destruction Support
@ -306,6 +316,7 @@ Core Map
Coronal Leather
Coronal Maul
Corroded Blade
Corroded Fossil
Corroded Tower Shield
Corrugated Buckler
Corsair Sword
@ -385,6 +396,7 @@ Defiled Cathedral Map
Deicide Mask
Demon Dagger
Demon's Horn
Dense Fossil
Desecrate
Desert Brigandine
Desert Map
@ -460,6 +472,8 @@ Emperor of Purity
Emperor's Luck
Empower Support
Enameled Buckler
Enchanted Fossil
Encrusted Fossil
Endurance Charge on Melee Stun Support
Enduring Cry
Enfeeble
@ -492,6 +506,7 @@ Exalted Orb
Exalted Shard
Excavation Map
Explosive Arrow
Explosive Trap
Exquisite Blade
Exquisite Leather
Eye Gouger
@ -504,6 +519,7 @@ Ezomyte Dagger
Ezomyte Spiked Shield
Ezomyte Staff
Ezomyte Tower Shield
Faceted Fossil
Factory Map
Fancy Foil
Fangjaw Talisman
@ -531,8 +547,10 @@ Flame Dash
Flame Surge
Flame Totem
Flameblast
Flamethrower Trap
Flammability
Flanged Mace
Flashpowder Keg
Flaying Knife
Flesh Offering
Fleshripper
@ -540,11 +558,13 @@ Flicker Strike
Flooded Mine Map
Fluted Bascinet
Footman Sword
Forbidden Power
Forge of the Phoenix Map
Fork Support
Fortify Support
Fossilised Spirit Shield
Foul Staff
Fractured Fossil
Fragment of the Chimera
Fragment of the Hydra
Fragment of the Minotaur
@ -554,6 +574,7 @@ Freezing Pulse
Frenzy
Fright Claw
Fright Maul
Frigid Fossil
Frontier Leather
Frost Blades
Frost Bomb
@ -583,6 +604,7 @@ Giant Mana Flask
Gift of the Gemling Queen
Gilded Axe
Gilded Buckler
Gilded Fossil
Gilded Sallet
Girded Tower Shield
Glacial Cascade
@ -595,6 +617,7 @@ Glassblower's Bauble
Glimmer of Hope
Glorious Leather
Glorious Plate
Glyphic Fossil
Gnarled Branch
Goat's Horn
Goathide Boots
@ -654,6 +677,7 @@ Harbinger's Orb
Harbinger's Shard
Harlequin Mask
Harmonic Spirit Shield
Harmony of Souls
Harpy Rapier
Haste
Hatred
@ -667,8 +691,10 @@ Heavy Quiver
Heavy Strike
Hellion's Paw
Her Mask
Herald of Agony
Herald of Ash
Herald of Ice
Herald of Purity
Herald of Thunder
Heterochromia
Hexclaw Talisman
@ -676,6 +702,7 @@ Highborn Bow
Highborn Staff
Highland Blade
Hinekora's Hair
Hollow Fossil
Holy Chainmail
Hook Sword
Hope
@ -705,6 +732,7 @@ Ignite Proliferation Support
Imbued Wand
Immolate Support
Immortal Call
Immortal Resolve
Imp Dagger
Imperial Bow
Imperial Buckler
@ -712,6 +740,7 @@ Imperial Claw
Imperial Maul
Imperial Skean
Imperial Staff
Imprinted Bestiary Orb
Incinerate
Increased Area of Effect Support
Increased Critical Damage Support
@ -749,6 +778,7 @@ Jade Chopper
Jade Flask
Jade Hatchet
Jagged Foil
Jagged Fossil
Jagged Maul
Jasper Axe
Jasper Chopper
@ -813,6 +843,7 @@ Light Quiver
Lighthouse Map
Lightning Arrow
Lightning Penetration Support
Lightning Spire Trap
Lightning Strike
Lightning Tendrils
Lightning Trap
@ -832,6 +863,7 @@ Lordly Plate
Loricated Ringmail
Lost Worlds
Loyalty
Lucent Fossil
Lucky Connections
Lucky Deck
Lunaris Circlet
@ -873,6 +905,7 @@ Merciless Armament
Mesa Map
Mesh Boots
Mesh Gloves
Metallic Fossil
Miasmeter
Midnight Blade
Might is Right
@ -923,6 +956,7 @@ Muttering Essence of Woe
Nailed Fist
Necromancer Circlet
Necromancer Silks
Necromancy Net
Necropolis Map
Nemesis Leaguestone
Nightmare Bascinet
@ -983,12 +1017,13 @@ Penetrating Arrow Quiver
Peninsula Map
Perandus Coin
Perandus Leaguestone
Perfect Fossil
Perfection
Pernarch
Petrified Club
Phantasmagoria Map
Phantom Mace
Phase Run
Physical Projectile Attack Damage Support
Physical to Lightning Support
Pier Map
Pierce Support
@ -1018,19 +1053,29 @@ Port Map
Portal
Portal Scroll
Portal Shredder
Potent Alchemical Resonator
Potent Chaotic Resonator
Power Charge On Critical Support
Power Siphon
Powerful Alchemical Resonator
Powerful Chaotic Resonator
Praetor Crown
Precinct Map
Prehistoric Claw
Pride Before the Fall
Primal Skull Talisman
Prime Alchemical Resonator
Prime Chaotic Resonator
Primeval Rapier
Primitive Alchemical Resonator
Primitive Chaotic Resonator
Primitive Staff
Primordial Pool Map
Primordial Staff
Prismatic Fossil
Prismatic Jewel
Prismatic Ring
Pristine Fossil
Profane Wand
Projectile Weakness
Promenade Map
@ -1082,7 +1127,10 @@ Regal Orb
Regal Shard
Regicide Mask
Reinforced Greaves
Reinforced Iron Net
Reinforced Kite Shield
Reinforced Rope Net
Reinforced Steel Net
Reinforced Tower Shield
Rejuvenation Totem
Relic Chambers Map
@ -1141,6 +1189,7 @@ Sambar Sceptre
Samite Gloves
Samite Helmet
Samite Slippers
Sanctified Fossil
Sanctified Life Flask
Sanctified Mana Flask
Sand of Eternity
@ -1157,7 +1206,9 @@ Scarlet Round Shield
Scholar Boots
Scholar of the Seas
Scholar's Robe
Scorched Fossil
Scorching Ray
Scourge Arrow
Screaming Essence
Screaming Essence of Anger
Screaming Essence of Anguish
@ -1185,6 +1236,7 @@ Scroll of Wisdom
Searching Eye Jewel
Searing Bond
Secutor Helm
Seismic Trap
Sekhem
Sekhema Feather
Sentinel Jacket
@ -1195,6 +1247,7 @@ Serpentscale Boots
Serpentscale Gauntlets
Serrated Arrow Quiver
Serrated Foil
Serrated Fossil
Shabby Jerkin
Shackled Boots
Shadow Axe
@ -1204,7 +1257,6 @@ Shagreen Gloves
Shagreen Tower Shield
Shaper's Orb
Shaper's Orb (Tier 1)
Shaper's Orb (Tier 10)
Shaper's Orb (Tier 2)
Shaper's Orb (Tier 3)
Shaper's Orb (Tier 4)
@ -1213,6 +1265,7 @@ Shaper's Orb (Tier 6)
Shaper's Orb (Tier 7)
Shaper's Orb (Tier 8)
Shaper's Orb (Tier 9)
Shaper's Orb (Tier 10)
Shard of Fate
Sharkskin Boots
Sharkskin Gloves
@ -1248,6 +1301,7 @@ Shrieking Essence of Woe
Shrieking Essence of Wrath
Shrieking Essence of Zeal
Shrine Map
Shuddering Fossil
Siege Axe
Siege Ballista
Siege Helmet
@ -1264,8 +1318,12 @@ Silver Coin
Silver Flask
Silver Key
Silver Locket
Simple Iron Net
Simple Robe
Simple Rope Net
Simple Steel Net
Sinner Tricorne
Siphoning Trap
Skean
Skinning Knife
Slaughter Knife
@ -1278,6 +1336,7 @@ Small Hybrid Flask
Small Life Flask
Small Mana Flask
Smallsword
Smite
Smoke Mine
Sniper Bow
Solar Maul
@ -1292,6 +1351,7 @@ Sovereign Spiked Shield
Spark
Sparkling Claw
Spectral Axe
Spectral Shield Throw
Spectral Sword
Spectral Throw
Spell Cascade Support
@ -1341,6 +1401,7 @@ Stibnite Flask
Stiletto
Stone Axe
Stone Hammer
Stone of Passage
Storm Barrier Support
Storm Blade
Storm Burst
@ -1349,6 +1410,9 @@ Strand Map
Strapped Boots
Strapped Leather
Strapped Mitts
Strong Iron Net
Strong Rope Net
Strong Steel Net
Struck by Lightning
Studded Belt
Studded Round Shield
@ -1359,8 +1423,10 @@ Sulphur Vents Map
Summit Map
Summon Chaos Golem
Summon Flame Golem
Summon Holy Relic
Summon Ice Golem
Summon Lightning Golem
Summon Phantasm on Kill Support
Summon Raging Spirit
Summon Skeleton
Summon Stone Golem
@ -1375,8 +1441,10 @@ Sweep
Swift Affliction Support
Talisman Leaguestone
Talon Axe
Tangled Fossil
Tarnished Spirit Shield
Teak Round Shield
Tectonic Slam
Tempered Foil
Tempest Leaguestone
Tempest Shield
@ -1386,38 +1454,50 @@ Tenderizer
Terrace Map
Terror Claw
Terror Maul
Thaumaturgical Net
Thaumetic Emblem
Thaumetic Sulphite
The Admirer
The Aesthete
The Arena Champion
The Army of Blood
The Artist
The Avenger
The Battle Born
The Beast
The Betrayal
The Black Flag
The Blazing Fire
The Body
The Breach
The Brittle Emperor
The Cacophony
The Calling
The Carrion Crow
The Cartographer
The Cataclysm
The Catalyst
The Celestial Justicar
The Celestial Stone
The Chains that Bind
The Coming Storm
The Conduit
The Cursed King
The Dapper Prodigy
The Dark Mage
The Darkest Dream
The Deceiver
The Demoness
The Devastator
The Doctor
The Doppelganger
The Dragon
The Dragon's Heart
The Dreamer
The Dreamland
The Drunken Aristocrat
The Encroaching Darkness
The Endless Darkness
The Endurance
The Enlightened
The Ethereal
@ -1425,6 +1505,7 @@ The Explorer
The Eye of Desire
The Eye of Fury
The Eye of the Dragon
The Fathomless Depths
The Feast
The Fiend
The Fletcher
@ -1437,15 +1518,20 @@ The Garish Power
The Gemcutter
The Gentleman
The Gladiator
The Hale Heart
The Harvester
The Hermit
The Hoarder
The Hunger
The Immortal
The Incantation
The Innocent
The Inoculated
The Insatiable
The Inventor
The Iron Bard
The Jester
The Jeweller's Boon
The King's Blade
The King's Heart
The Last One Standing
@ -1454,9 +1540,12 @@ The Lion
The Lord in Black
The Lover
The Lunaris Priestess
The Master
The Mayor
The Mercenary
The Metalsmith's Gift
The Oath
The Obscured
The Offering
The One With All
The Opulent
@ -1466,17 +1555,23 @@ The Penitent
The Poet
The Polymath
The Porcupine
The Price of Protection
The Professor
The Puzzle
The Queen
The Rabid Rhoa
The Realm
The Risk
The Rite of Elements
The Road to Power
The Ruthless Ceinture
The Saint's Treasure
The Samurai's Eye
The Scarred Meadow
The Scavenger
The Scholar
The Sephirot
The Shaper's Key
The Sigil
The Siren
The Soul
@ -1490,14 +1585,18 @@ The Sun
The Surgeon
The Surveyor
The Survivalist
The Sword King's Salute
The Teardrop
The Thaumaturgist
The Throne
The Tower
The Traitor
The Trial
The Twilight Moon
The Twins
The Tyrant
The Undaunted
The Undisputed
The Union
The Valkyrie
The Valley of Steel Boxes
@ -1508,11 +1607,14 @@ The Warden
The Warlord
The Watcher
The Web
The Wilted Rose
The Wind
The Witch
The Wolf
The Wolf's Shadow
The Wolven King's Bite
The Wolverine
The World Eater
The Wrath
The Wretched
Thicket Bow
@ -1523,6 +1625,7 @@ Thorn Rapier
Three Faces in the Dark
Three Hands Talisman
Three Rat Talisman
Three Voices
Thresher Claw
Throat Stabber
Thunderous Skies
@ -1532,6 +1635,7 @@ Tiger's Paw
Timber Axe
Time-Lost Relic
Timeworn Claw
Timeworn Reliquary Key
Titan Gauntlets
Titan Greaves
Titanium Spirit Shield
@ -1547,6 +1651,7 @@ Torture Chamber Map
Totemic Maul
Tower Key
Tower Map
Toxic Rain
Toxic Sewer Map
Tranquillity
Transmutation Shard
@ -1587,9 +1692,12 @@ Unset Ring
Unshaping Orb
Ursine Pelt
Uul-Netol's Breachstone
Vaal Ancestral Warchief
Vaal Arc
Vaal Axe
Vaal Blade
Vaal Blade Vortex
Vaal Blight
Vaal Breach
Vaal Buckler
Vaal Burning Arrow
@ -1600,6 +1708,7 @@ Vaal Cyclone
Vaal Detonate Dead
Vaal Discipline
Vaal Double Strike
Vaal Earthquake
Vaal Fireball
Vaal Flameblast
Vaal Gauntlets
@ -1612,6 +1721,9 @@ Vaal Haste
Vaal Hatchet
Vaal Ice Nova
Vaal Immortal Call
Vaal Impurity of Fire
Vaal Impurity of Ice
Vaal Impurity of Lightning
Vaal Lightning Strike
Vaal Lightning Trap
Vaal Lightning Warp
@ -1640,7 +1752,17 @@ Vault Map
Velvet Gloves
Velvet Slippers
Vengeance
Vial of Awakening
Vial of Consequence
Vial of Dominance
Vial of Fate
Vial Of Power
Vial of Sacrifice
Vial of Summoning
Vial of the Ghost
Vial of the Ritual
Vial of Transcendence
Vicious Projectiles Support
Vigilant Strike
Vile Staff
Vile Toxins Support
@ -1718,6 +1840,7 @@ Wild Leather
Wild Strike
Wings of Vastiri
Wither
Withering Touch Support
Wolf Pelt
Woodful Staff
Woodsplitter

View File

@ -9,6 +9,7 @@ Bows
Claws
Currency
Daggers
Delve Stackable Currency
Divination Card
Fishing Rods
Flasks
@ -16,6 +17,7 @@ Gems
Gloves
Helmets
Hybrid Flasks
Incursion Item
Jewel
Labyrinth Item
Labyrinth Map Item

View File

@ -7,7 +7,7 @@
xmlns:commonConverters="clr-namespace:Filtration.Common.Converters;assembly=Filtration.Common"
xmlns:blockItemBaseTypes="clr-namespace:Filtration.ObjectModel.BlockItemBaseTypes;assembly=Filtration.ObjectModel"
xmlns:blockItemTypes="clr-namespace:Filtration.ObjectModel.BlockItemTypes;assembly=Filtration.ObjectModel"
xmlns:extensions="clr-namespace:Filtration.Extensions"
xmlns:extensions="clr-namespace:Filtration.Common.Extensions;assembly=Filtration.Common"
xmlns:enums="clr-namespace:Filtration.ObjectModel.Enums;assembly=Filtration.ObjectModel"
xmlns:xctk="http://schemas.xceed.com/wpf/xaml/toolkit"
xmlns:views="clr-namespace:Filtration.Views"
@ -76,11 +76,38 @@
<userControls:EditableListBoxControl Margin="5,5,5,5" ItemsSource="{Binding Items}" AutoCompleteItemsSource="{Binding ElementName=TopLevelGrid, Path=DataContext.AutoCompleteItemBaseTypes}" />
</DataTemplate>
<!-- Explicit Mods Template -->
<DataTemplate DataType="{x:Type blockItemTypes:HasExplicitModBlockItem}">
<userControls:EditableListBoxControl Margin="5,5,5,5" ItemsSource="{Binding Items}" />
</DataTemplate>
<!-- Socket Groups Template -->
<DataTemplate DataType="{x:Type blockItemTypes:SocketGroupBlockItem}">
<userControls:EditableListBoxControl Margin="5,5,5,5" ItemsSource="{Binding Items}" />
</DataTemplate>
<!-- Play Effect Block Template -->
<DataTemplate DataType="{x:Type blockItemTypes:PlayEffectBlockItem}">
<StackPanel>
<WrapPanel VerticalAlignment="Center" Margin="5,5,5,5">
<RadioButton IsChecked="{Binding Temporary, Converter={StaticResource BoolInverterConverter}}" Margin="0,0,10,0">Permanent</RadioButton>
<RadioButton IsChecked="{Binding Temporary}" >Temporary</RadioButton>
</WrapPanel>
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:EffectColor}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding Color}"
SelectedValuePath="Value" />
<userControls:ThemeComponentSelectionControl ThemeComponent="{Binding ThemeComponent}" Margin="0,2,0,0">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</StackPanel>
</DataTemplate>
<!-- Color Template -->
<DataTemplate DataType="{x:Type blockItemBaseTypes:ColorBlockItem}">
<StackPanel>
@ -100,9 +127,21 @@
<!-- Font Size Template -->
<DataTemplate DataType="{x:Type blockItemTypes:FontSizeBlockItem}">
<WrapPanel HorizontalAlignment="Left">
<xctk:ShortUpDown Value="{Binding Value}" Minimum="{Binding Minimum}" Maximum="{Binding Maximum}" Width="50" />
</WrapPanel>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="50" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<xctk:ShortUpDown Grid.Column="0" Value="{Binding Value}" Minimum="{Binding Minimum}" Maximum="{Binding Maximum}" Margin="0,0,10,0" />
<userControls:ThemeComponentSelectionControl Grid.Column="1" ThemeComponent="{Binding ThemeComponent}">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</Grid>
</DataTemplate>
<!-- Sound Template -->
@ -113,6 +152,14 @@
</Button>
<ComboBox ItemsSource="{Binding ElementName=BlockItemContentControl, Path=DataContext.SoundsAvailable}" SelectedValue="{Binding Value}" Style="{StaticResource MetroComboBox}" />
<xctk:ShortUpDown Value="{Binding Path=SecondValue}" Minimum="1" Maximum="300" HorizontalAlignment="Right" ToolTip="Volume"/>
<userControls:ThemeComponentSelectionControl ThemeComponent="{Binding ThemeComponent}" Margin="0,2,0,0">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</WrapPanel>
</DataTemplate>
@ -124,8 +171,73 @@
</Button>
<ComboBox ItemsSource="{Binding ElementName=BlockItemContentControl, Path=DataContext.SoundsAvailable}" SelectedValue="{Binding Value}" Style="{StaticResource MetroComboBox}" />
<xctk:ShortUpDown Value="{Binding Path=SecondValue}" Minimum="1" Maximum="300" HorizontalAlignment="Right" ToolTip="Volume"/>
<userControls:ThemeComponentSelectionControl ThemeComponent="{Binding ThemeComponent}" Margin="0,2,0,0">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</WrapPanel>
</DataTemplate>
<!-- Map Icon Template -->
<DataTemplate DataType="{x:Type blockItemTypes:MapIconBlockItem}">
<StackPanel Orientation="Vertical" Margin="5,5,5,5">
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconSize}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding Size}"
SelectedValuePath="Value" />
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconColor}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding Color}"
SelectedValuePath="Value" />
<ComboBox ItemsSource="{Binding Source={extensions:Enumeration {x:Type enums:IconShape}}}" Style="{StaticResource MetroComboBox}"
DisplayMemberPath="Description"
SelectedValue="{Binding Shape}"
SelectedValuePath="Value" />
<userControls:ThemeComponentSelectionControl ThemeComponent="{Binding ThemeComponent}" Margin="0,2,0,0">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</StackPanel>
</DataTemplate>
<!-- Custom Sound Template -->
<DataTemplate DataType="{x:Type blockItemTypes:CustomSoundBlockItem}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="20"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<Button Grid.Column="0" Grid.Row="0" Command="{Binding Path=DataContext.PlayCustomSoundCommand, RelativeSource={RelativeSource AncestorType={x:Type views:ItemFilterBlockView}}}" Width="20" Height="20" Background="Transparent" BorderBrush="Transparent">
<Image Source="/Filtration;component/Resources/Icons/speaker_icon.png" VerticalAlignment="Center" HorizontalAlignment="Center" />
</Button>
<ComboBox Grid.Column="1" Grid.Row="0" ItemsSource="{Binding Path=DataContext.CustomSoundsAvailable, UpdateSourceTrigger=PropertyChanged, RelativeSource={RelativeSource AncestorType={x:Type views:ItemFilterBlockView}}}"
SelectedValue="{Binding Value, UpdateSourceTrigger=PropertyChanged}" Style="{StaticResource MetroComboBox}"/>
<Button Grid.Column="1" Grid.Row="0" Command="{Binding Path=DataContext.CustomSoundFileDialogCommand, RelativeSource={RelativeSource AncestorType={x:Type views:ItemFilterBlockView}}}"
Width="20" Height="20" Background="Transparent" BorderBrush="Transparent" Margin="0,0,30,0" VerticalAlignment="Center" HorizontalAlignment="Right">
<Image Grid.Column="1" Source="/Filtration;component/Resources/Icons/open_icon.png"/>
</Button>
<userControls:ThemeComponentSelectionControl Grid.Row="1" Grid.Column="1" ThemeComponent="{Binding ThemeComponent}" Margin="0,2,0,0">
<userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
<MultiBinding Converter="{StaticResource AvailableThemeComponentsConverter}">
<Binding Path="DataContext.Script.ThemeComponents" RelativeSource="{RelativeSource AncestorType={x:Type views:ItemFilterScriptView}}"/>
<Binding Path="." />
</MultiBinding>
</userControls:ThemeComponentSelectionControl.AvailableThemeComponents>
</userControls:ThemeComponentSelectionControl>
</Grid>
</DataTemplate>
</ContentControl.Resources>
</ContentControl>
</Grid>

View File

@ -6,6 +6,8 @@ using System.Windows;
using Filtration.Annotations;
using Filtration.ObjectModel;
using Filtration.ObjectModel.BlockItemBaseTypes;
using Filtration.ObjectModel.Enums;
using Filtration.ObjectModel.ThemeEditor;
using Filtration.Views;
using GalaSoft.MvvmLight.CommandWpf;
using Xceed.Wpf.Toolkit;
@ -20,10 +22,10 @@ namespace Filtration.UserControls
// ReSharper disable once PossibleNullReferenceException
(Content as FrameworkElement).DataContext = this;
SetBlockColorCommand = new RelayCommand(OnSetBlockColorCommmand);
SetBlockValueCommand = new RelayCommand(OnSetBlockValueCommmand);
}
public RelayCommand SetBlockColorCommand { get; private set; }
public RelayCommand SetBlockValueCommand { get; private set; }
public static readonly DependencyProperty BlockItemProperty = DependencyProperty.Register(
"BlockItem",
@ -88,12 +90,45 @@ namespace Filtration.UserControls
"ShFusing", "ShRegal", "ShVaal"
};
private void OnSetBlockColorCommmand()
private void OnSetBlockValueCommmand()
{
var blockItem = BlockItem as ColorBlockItem;
if (blockItem?.ThemeComponent == null) return;
var blockItemWithTheme = BlockItem as IBlockItemWithTheme;
if (blockItemWithTheme?.ThemeComponent == null) return;
blockItem.Color = blockItem.ThemeComponent.Color;
var componentType = ((IBlockItemWithTheme)BlockItem).ThemeComponent.ComponentType;
switch(componentType)
{
case ThemeComponentType.BackgroundColor:
case ThemeComponentType.BorderColor:
case ThemeComponentType.TextColor:
var colorBlockItem = BlockItem as ColorBlockItem;
colorBlockItem.Color = ((ColorThemeComponent)colorBlockItem.ThemeComponent).Color;
break;
case ThemeComponentType.FontSize:
var integerBlockItem = BlockItem as IntegerBlockItem;
integerBlockItem.Value = ((IntegerThemeComponent)integerBlockItem.ThemeComponent).Value;
break;
case ThemeComponentType.AlertSound:
var strIntBlockItem = BlockItem as StrIntBlockItem;
strIntBlockItem.Value = ((StrIntThemeComponent)strIntBlockItem.ThemeComponent).Value;
strIntBlockItem.SecondValue = ((StrIntThemeComponent)strIntBlockItem.ThemeComponent).SecondValue;
break;
case ThemeComponentType.CustomSound:
var stringBlockItem = BlockItem as StringBlockItem;
stringBlockItem.Value = ((StringThemeComponent)stringBlockItem.ThemeComponent).Value;
break;
case ThemeComponentType.Icon:
var iconBlockItem = BlockItem as IconBlockItem;
iconBlockItem.Size = ((IconThemeComponent)iconBlockItem.ThemeComponent).IconSize;
iconBlockItem.Color = ((IconThemeComponent)iconBlockItem.ThemeComponent).IconColor;
iconBlockItem.Shape = ((IconThemeComponent)iconBlockItem.ThemeComponent).IconShape;
break;
case ThemeComponentType.Effect:
var effectColorBlockItem = BlockItem as EffectColorBlockItem;
effectColorBlockItem.Color = ((EffectColorThemeComponent)effectColorBlockItem.ThemeComponent).EffectColor;
effectColorBlockItem.Temporary = ((EffectColorThemeComponent)effectColorBlockItem.ThemeComponent).Temporary;
break;
}
}
public event PropertyChangedEventHandler PropertyChanged;

View File

@ -0,0 +1,26 @@
<UserControl
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:local="clr-namespace:Filtration.UserControls"
xmlns:Converters="clr-namespace:Filtration.Converters" x:Class="Filtration.UserControls.ImageComboBoxControl"
mc:Ignorable="d">
<UserControl.Resources>
<Converters:SizeColorToRectConverter x:Key="DropIconConverter"/>
</UserControl.Resources>
<Grid>
<ComboBox ItemsSource="{Binding DataContext.IconsAvailable, ElementName=BlockItemContentControl}" SelectedValue="{Binding Value}" Style="{StaticResource MetroComboBox}">
<ComboBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Image MaxWidth="20" MaxHeight="20" Source="{Binding Converter={StaticResource DropIconConverter}, Mode=OneWay}" />
<Label Content="{Binding}" VerticalAlignment="Stretch"/>
</StackPanel>
</DataTemplate>
</ComboBox.ItemTemplate>
</ComboBox>
</Grid>
</UserControl>

View File

@ -0,0 +1,28 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
namespace Filtration.UserControls
{
/// <summary>
/// Interaction logic for ImageComboBoxControl.xaml
/// </summary>
public partial class ImageComboBoxControl : UserControl
{
public ImageComboBoxControl()
{
InitializeComponent();
}
}
}

View File

@ -8,7 +8,7 @@
d:DataContext="{d:DesignInstance Type=userControls:ItemPreviewControl}"
d:DesignHeight="35" d:DesignWidth="170">
<Border BorderBrush="Black" BorderThickness="1">
<Grid Width="166" Height="39">
<Grid Width="200" Height="39">
<Image Source="pack://application:,,,/resources/groundtile.png" Stretch="Fill" />
<Grid>
<Grid.RowDefinitions>

Some files were not shown because too many files have changed in this diff Show More