diff --git a/eos-edit/App.axaml b/eos-edit/App.axaml
index 1b59822..656aa83 100644
--- a/eos-edit/App.axaml
+++ b/eos-edit/App.axaml
@@ -97,6 +97,9 @@
+
+
+
diff --git a/eos-edit/Assets/CustomDataTemplateResources.axaml b/eos-edit/Assets/CustomDataTemplateResources.axaml
index 5425b68..16efd1e 100644
--- a/eos-edit/Assets/CustomDataTemplateResources.axaml
+++ b/eos-edit/Assets/CustomDataTemplateResources.axaml
@@ -118,18 +118,30 @@
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -170,8 +182,9 @@
CompanionTemplate="{StaticResource companionTemplate}"
FamiliarTemplate="{StaticResource familiarTemplate}"
CustomObjectTemplate="{StaticResource customObjectVariantTemplate}"
- CustomEnumTemplate="{StaticResource customEnumVariantTemplate}"
- CustomDynamicTableTemplate="{StaticResource customDynamicTableTemplate}"/>
+ CustomTableTemplate="{StaticResource customTableVariantTemplate}"
+ CustomDynamicTableTemplate="{StaticResource customDynamicTableVariantTemplate}"
+ CustomEnumTemplate="{StaticResource customEnumVariantTemplate}"/>
@@ -242,6 +255,7 @@
CompanionTemplate="{StaticResource companionTemplate}"
FamiliarTemplate="{StaticResource familiarTemplate}"
CustomObjectTemplate="{StaticResource customObjectTemplate}"
- CustomEnumTemplate="{StaticResource customEnumTemplate}"
- CustomDynamicTableTemplate="{StaticResource customDynamicTableTemplate}"/>
+ CustomTableTemplate="{StaticResource customTableTemplate}"
+ CustomDynamicTableTemplate="{StaticResource customDynamicTableTemplate}"
+ CustomEnumTemplate="{StaticResource customEnumTemplate}"/>
diff --git a/eos-edit/Assets/StyleResources.axaml b/eos-edit/Assets/StyleResources.axaml
index 0227498..7c1403f 100644
--- a/eos-edit/Assets/StyleResources.axaml
+++ b/eos-edit/Assets/StyleResources.axaml
@@ -392,6 +392,10 @@
+
+
diff --git a/eos-edit/Extensions/InstancePropertyValueTemplateSelector.cs b/eos-edit/Extensions/InstancePropertyValueTemplateSelector.cs
index 7b81c94..aa3d466 100644
--- a/eos-edit/Extensions/InstancePropertyValueTemplateSelector.cs
+++ b/eos-edit/Extensions/InstancePropertyValueTemplateSelector.cs
@@ -53,8 +53,9 @@ public class InstancePropertyValueTemplateSelector : IDataTemplate
public DataTemplate? DamageTypeTemplate { get; set; }
public DataTemplate? DamageTypeGroupTemplate { get; set; }
public DataTemplate? CustomObjectTemplate { get; set; }
- public DataTemplate? CustomEnumTemplate { get; set; }
+ public DataTemplate? CustomTableTemplate { get; set; }
public DataTemplate? CustomDynamicTableTemplate { get; set; }
+ public DataTemplate? CustomEnumTemplate { get; set; }
public Control? Build(object? param)
@@ -149,10 +150,12 @@ public bool Match(object? data)
if (dataTypeDef.CustomType is CustomObject customObject)
return CustomObjectTemplate ?? ErrorTemplate;
- if (dataTypeDef.CustomType is CustomEnum customEnum)
- return CustomEnumTemplate ?? ErrorTemplate;
+ if (dataTypeDef.CustomType is CustomTable customTable)
+ return CustomTableTemplate ?? ErrorTemplate;
if (dataTypeDef.CustomType is CustomDynamicTable customDynTable)
return CustomDynamicTableTemplate ?? ErrorTemplate;
+ if (dataTypeDef.CustomType is CustomEnum customEnum)
+ return CustomEnumTemplate ?? ErrorTemplate;
return ErrorTemplate;
}
diff --git a/eos-edit/Usercontrols/CustomTableComboBox.axaml b/eos-edit/Usercontrols/CustomTableComboBox.axaml
new file mode 100644
index 0000000..221ee3d
--- /dev/null
+++ b/eos-edit/Usercontrols/CustomTableComboBox.axaml
@@ -0,0 +1,36 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/eos-edit/Usercontrols/CustomTableComboBox.axaml.cs b/eos-edit/Usercontrols/CustomTableComboBox.axaml.cs
new file mode 100644
index 0000000..04f1104
--- /dev/null
+++ b/eos-edit/Usercontrols/CustomTableComboBox.axaml.cs
@@ -0,0 +1,64 @@
+using Avalonia;
+using Avalonia.Controls;
+using Avalonia.Data;
+using Avalonia.Interactivity;
+using Eos.Models;
+using Eos.Models.Tables;
+using Eos.Repositories;
+using Eos.Services;
+using Eos.ViewModels.Base;
+using Eos.ViewModels.Dialogs;
+
+namespace Eos.Usercontrols
+{
+ public partial class CustomTableComboBox : UserControl
+ {
+ public CustomTableComboBox()
+ {
+ InitializeComponent();
+ }
+
+ public static readonly StyledProperty CustomTableTemplateProperty = AvaloniaProperty.Register("CustomTableTemplate", null);
+ public static readonly StyledProperty SelectedValueProperty = AvaloniaProperty.Register("SelectedValue", null, false, BindingMode.TwoWay);
+ public static readonly StyledProperty IsNullableProperty = AvaloniaProperty.Register("IsNullable", true);
+
+ public CustomTable? CustomTableTemplate
+ {
+ get { return GetValue(CustomTableTemplateProperty); }
+ set { SetValue(CustomTableTemplateProperty, value); }
+ }
+
+ public CustomTableInstance? SelectedValue
+ {
+ get { return GetValue(SelectedValueProperty); }
+ set { SetValue(SelectedValueProperty, value); }
+ }
+
+ public bool IsNullable
+ {
+ get { return GetValue(IsNullableProperty); }
+ set { SetValue(IsNullableProperty, value); }
+ }
+
+ private void btClear_Click(object sender, RoutedEventArgs e)
+ {
+ SetValue(SelectedValueProperty, null);
+ }
+
+ private void btSearch_Click(object sender, RoutedEventArgs e)
+ {
+ if (CustomTableTemplate != null)
+ {
+ var viewModel = new CustomTableInstanceSearchViewModel(CustomTableTemplate, MasterRepository.Project.CustomTableRepositories[CustomTableTemplate]);
+ WindowService.OpenDialog(viewModel);
+ if (viewModel.ResultModel != null)
+ SetValue(SelectedValueProperty, viewModel.ResultModel);
+ }
+ }
+
+ private void btGoto_Click(object sender, RoutedEventArgs e)
+ {
+ MessageDispatcher.Send(MessageType.OpenDetail, SelectedValue, true);
+ }
+ }
+}
diff --git a/eos-edit/ViewModels/Base/ViewModelBase.cs b/eos-edit/ViewModels/Base/ViewModelBase.cs
index 596da7f..d3bffb6 100644
--- a/eos-edit/ViewModels/Base/ViewModelBase.cs
+++ b/eos-edit/ViewModels/Base/ViewModelBase.cs
@@ -110,6 +110,11 @@ protected ViewModelQueryResult DoQuery(String title, String message, ViewModelQu
MessageDispatcher.Send(MessageType.NewCustomDetail, template);
});
+ public ReactiveCommand NewCustomTableCommand { get; private set; } = ReactiveCommand.Create(template =>
+ {
+ MessageDispatcher.Send(MessageType.NewCustomDetail, template);
+ });
+
public ReactiveCommand NewCustomDynamicTableCommand { get; private set; } = ReactiveCommand.Create(template =>
{
MessageDispatcher.Send(MessageType.NewCustomDetail, template);
diff --git a/eos-edit/ViewModels/Base/ViewModelFactory.cs b/eos-edit/ViewModels/Base/ViewModelFactory.cs
index dbcb02e..f6f610f 100644
--- a/eos-edit/ViewModels/Base/ViewModelFactory.cs
+++ b/eos-edit/ViewModels/Base/ViewModelFactory.cs
@@ -113,10 +113,14 @@ public static DataDetailViewModelBase CreateViewModel(object model)
return new CustomEnumViewModel(customEnum);
if (model is CustomObject customObject)
return new CustomObjectViewModel(customObject);
+ if (model is CustomTable customTable)
+ return new CustomTableViewModel(customTable);
if (model is CustomDynamicTable customDynamicTable)
return new CustomDynamicTableViewModel(customDynamicTable);
if (model is CustomObjectInstance customObjectInstance)
return new CustomObjectInstanceViewModel(customObjectInstance);
+ if (model is CustomTableInstance customTableInstance)
+ return new CustomTableInstanceViewModel(customTableInstance);
if (model is CustomDynamicTableInstance customDynamicTableInstance)
return new CustomDynamicTableInstanceViewModel(customDynamicTableInstance);
diff --git a/eos-edit/ViewModels/CustomDynamicTableInstanceViewModel.cs b/eos-edit/ViewModels/CustomDynamicTableInstanceViewModel.cs
index bac832d..4589c88 100644
--- a/eos-edit/ViewModels/CustomDynamicTableInstanceViewModel.cs
+++ b/eos-edit/ViewModels/CustomDynamicTableInstanceViewModel.cs
@@ -17,7 +17,7 @@ public class CustomDynamicTableInstanceViewModel : DataDetailViewModel(DeleteCustomDynTableItem);
- AddCustomDynTableItemCommand = ReactiveCommand.Create(AddItemPropertyTableItem);
+ AddCustomDynTableItemCommand = ReactiveCommand.Create(AddCustomDynTableItem);
MoveUpCommand = ReactiveCommand.Create(MoveUp);
MoveDownCommand = ReactiveCommand.Create(MoveDown);
@@ -26,7 +26,7 @@ public CustomDynamicTableInstanceViewModel() : base()
public CustomDynamicTableInstanceViewModel(CustomDynamicTableInstance instance) : base(instance)
{
DeleteCustomDynTableItemCommand = ReactiveCommand.Create(DeleteCustomDynTableItem);
- AddCustomDynTableItemCommand = ReactiveCommand.Create(AddItemPropertyTableItem);
+ AddCustomDynTableItemCommand = ReactiveCommand.Create(AddCustomDynTableItem);
MoveUpCommand = ReactiveCommand.Create(MoveUp);
MoveDownCommand = ReactiveCommand.Create(MoveDown);
@@ -45,7 +45,7 @@ protected override string GetHeader()
return Data.Label;
}
- private void AddItemPropertyTableItem()
+ private void AddCustomDynTableItem()
{
var newItem = new CustomDynamicTableInstanceItem(Data);
Data.Add(newItem);
diff --git a/eos-edit/ViewModels/CustomTableInstanceViewModel.cs b/eos-edit/ViewModels/CustomTableInstanceViewModel.cs
new file mode 100644
index 0000000..73b8a22
--- /dev/null
+++ b/eos-edit/ViewModels/CustomTableInstanceViewModel.cs
@@ -0,0 +1,57 @@
+using Eos.Models.Tables;
+using Eos.Types;
+using Eos.ViewModels.Base;
+using ReactiveUI;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Reactive;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace Eos.ViewModels
+{
+ public class CustomTableInstanceViewModel : DataDetailViewModel
+ {
+ public CustomTableInstanceViewModel() : base()
+ {
+ DeleteItemCommand = ReactiveCommand.Create(DeleteItem);
+ AddItemCommand = ReactiveCommand.Create(AddItem);
+ }
+
+ public CustomTableInstanceViewModel(CustomTableInstance instance) : base(instance)
+ {
+ DeleteItemCommand = ReactiveCommand.Create(DeleteItem);
+ AddItemCommand = ReactiveCommand.Create(AddItem);
+ }
+
+ protected override HashSet GetHeaderSourceFields()
+ {
+ return new HashSet()
+ {
+ "Label"
+ };
+ }
+
+ protected override string GetHeader()
+ {
+ return Data.Label;
+ }
+
+ private void AddItem()
+ {
+ var newItem = new CustomTableInstanceItem();
+ Data.Add(newItem);
+ NotifyPropertyChanged("Data");
+ }
+
+ private void DeleteItem(CustomTableInstanceItem item)
+ {
+ this.Data.Remove(item);
+ NotifyPropertyChanged("Data");
+ }
+
+ public ReactiveCommand DeleteItemCommand { get; private set; }
+ public ReactiveCommand AddItemCommand { get; private set; }
+ }
+}
diff --git a/eos-edit/ViewModels/CustomTableViewModel.cs b/eos-edit/ViewModels/CustomTableViewModel.cs
new file mode 100644
index 0000000..3a8d5e9
--- /dev/null
+++ b/eos-edit/ViewModels/CustomTableViewModel.cs
@@ -0,0 +1,91 @@
+using Eos.Models.Tables;
+using Eos.Types;
+using Eos.ViewModels.Base;
+using ReactiveUI;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Reactive;
+using System.Reflection;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace Eos.ViewModels
+{
+ public class CustomTableViewModel : DataDetailViewModel
+ {
+ public event EventHandler? OnDeleteCustomProperty;
+ public void RemoveAllEventsCalling(EventHandler method)
+ {
+ if (OnDeleteCustomProperty != null)
+ {
+ foreach (var d in OnDeleteCustomProperty.GetInvocationList())
+ {
+ if (d.Method == method.Method)
+ OnDeleteCustomProperty -= (EventHandler)d;
+ }
+ }
+ }
+
+ public CustomTableViewModel() : base()
+ {
+ DeleteObjectPropertyCommand = ReactiveCommand.Create(DeleteObjectProperty);
+ AddObjectPropertyCommand = ReactiveCommand.Create(AddObjectProperty);
+
+ MoveObjectPropertyUpCommand = ReactiveCommand.Create(MoveUp);
+ MoveObjectPropertyDownCommand = ReactiveCommand.Create(MoveDown);
+ }
+
+ public CustomTableViewModel(CustomTable customTable) : base(customTable)
+ {
+ DeleteObjectPropertyCommand = ReactiveCommand.Create(DeleteObjectProperty);
+ AddObjectPropertyCommand = ReactiveCommand.Create(AddObjectProperty);
+
+ MoveObjectPropertyUpCommand = ReactiveCommand.Create(MoveUp);
+ MoveObjectPropertyDownCommand = ReactiveCommand.Create(MoveDown);
+ }
+
+ protected override string GetHeader()
+ {
+ return Data.Name;
+ }
+
+ private void AddObjectProperty()
+ {
+ var newItem = new CustomObjectProperty();
+ Data.Add(newItem);
+ NotifyPropertyChanged("Data");
+ }
+
+ private void DeleteObjectProperty(CustomObjectProperty item)
+ {
+ var eventData = new DeleteCustomPropertyEventArgs(item);
+ OnDeleteCustomProperty?.Invoke(this, eventData);
+ if (eventData.CanDelete)
+ {
+ this.Data.Remove(item);
+ NotifyPropertyChanged("Data");
+ }
+ }
+
+ private void MoveUp(CustomObjectProperty item)
+ {
+ var index = Data.Items.IndexOf(item);
+ if (index > 0)
+ Data.Items.Move(index, index - 1);
+ }
+
+ private void MoveDown(CustomObjectProperty item)
+ {
+ var index = Data.Items.IndexOf(item);
+ if (index < Data.Items.Count - 1)
+ Data.Items.Move(index, index + 1);
+ }
+
+ public ReactiveCommand DeleteObjectPropertyCommand { get; private set; }
+ public ReactiveCommand AddObjectPropertyCommand { get; private set; }
+
+ public ReactiveCommand MoveObjectPropertyUpCommand { get; private set; }
+ public ReactiveCommand MoveObjectPropertyDownCommand { get; private set; }
+ }
+}
diff --git a/eos-edit/ViewModels/Dialogs/CustomTableInstanceSearchViewModel.cs b/eos-edit/ViewModels/Dialogs/CustomTableInstanceSearchViewModel.cs
new file mode 100644
index 0000000..f71841a
--- /dev/null
+++ b/eos-edit/ViewModels/Dialogs/CustomTableInstanceSearchViewModel.cs
@@ -0,0 +1,36 @@
+using Eos.Models;
+using Eos.Models.Tables;
+using Eos.Nwn.Tlk;
+using Eos.Repositories;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace Eos.ViewModels.Dialogs
+{
+ public class CustomTableInstanceSearchViewModel : ModelSearchViewModel
+ {
+ private CustomTable template;
+
+ public CustomTableInstanceSearchViewModel(CustomTable template, ModelRepository repository) : base(new VirtualModelRepository(repository))
+ {
+ this.template = template;
+ this.IsTableSearch = true;
+ }
+
+ protected override TLKStringSet? GetModelText(CustomTableInstance? model)
+ {
+ var tlk = new TLKStringSet();
+ foreach (var lang in Enum.GetValues())
+ tlk[lang].Text = model?.Name ?? "";
+ return tlk;
+ }
+
+ protected override string GetWindowTitle()
+ {
+ return "Search " + template.Name;
+ }
+ }
+}
diff --git a/eos-edit/ViewModels/Dialogs/MasterFeatSearchViewModel.cs b/eos-edit/ViewModels/Dialogs/MasterFeatSearchViewModel.cs
index 206109d..b9563fc 100644
--- a/eos-edit/ViewModels/Dialogs/MasterFeatSearchViewModel.cs
+++ b/eos-edit/ViewModels/Dialogs/MasterFeatSearchViewModel.cs
@@ -9,7 +9,7 @@
namespace Eos.ViewModels.Dialogs
{
- class MasterFeatSearchViewModel : ModelSearchViewModel
+ public class MasterFeatSearchViewModel : ModelSearchViewModel
{
public MasterFeatSearchViewModel(VirtualModelRepository repository) : base(repository)
{
diff --git a/eos-edit/ViewModels/MainWindowViewModel.cs b/eos-edit/ViewModels/MainWindowViewModel.cs
index 2fe4e94..ce559a8 100644
--- a/eos-edit/ViewModels/MainWindowViewModel.cs
+++ b/eos-edit/ViewModels/MainWindowViewModel.cs
@@ -16,7 +16,6 @@
using Eos.Config;
using Eos.ViewModels.Dialogs;
using Avalonia.Input;
-using Microsoft.CodeAnalysis.CSharp.Syntax;
namespace Eos.ViewModels
{
@@ -47,7 +46,7 @@ public DataDetailViewModelBase? CurrentView
private void OpenDetail(BaseModel model, bool jumpToOverride, bool changeView)
{
- if ((jumpToOverride) && !(model is CustomObjectInstance) && !(model is CustomDynamicTableInstance))
+ if ((jumpToOverride) && !(model is CustomObjectInstance) && !(model is CustomTableInstance) && !(model is CustomDynamicTableInstance))
model = MasterRepository.Project.GetOverride(model) ?? model;
if (!detailViewDict.ContainsKey(model))
@@ -100,6 +99,13 @@ private void DeleteDetail(BaseModel model)
message += "Do you still want to delete this Custom Object definition?";
queryResult = DoQuery("Delete Confirmation", message, ViewModelQueryType.Warning);
}
+ else if (model is CustomTable)
+ {
+ var message = "Do you really want to delete the definition of: \"" + model.GetLabel() + "\"?\n";
+ message += "WARNING: This will delete every instance of this table type!\n\n";
+ message += "Do you still want to delete this Custom Table definition?";
+ queryResult = DoQuery("Delete Confirmation", message, ViewModelQueryType.Warning);
+ }
else if (model is CustomDynamicTable)
{
var message = "Do you really want to delete the definition of: \"" + model.GetLabel() + "\"?\n";
@@ -126,6 +132,14 @@ private void DeleteDetail(BaseModel model)
CloseDetail(custObjInstance);
}
}
+ else if (model is CustomTable customTable)
+ {
+ foreach (var custTableInstance in MasterRepository.Project.CustomTableRepositories[customTable])
+ {
+ if (custTableInstance != null)
+ CloseDetail(custTableInstance);
+ }
+ }
else if (model is CustomDynamicTable customDynTable)
{
foreach (var custDynTableInstance in MasterRepository.Project.CustomDynamicTableRepositories[customDynTable])
@@ -176,6 +190,13 @@ private void MessageHandler(MessageType type, object? message, object? param)
MasterRepository.Add(instance);
MessageDispatcher.Send(MessageType.OpenDetail, instance);
}
+ else if (model is CustomTable tableTemplate)
+ {
+ var instance = new CustomTableInstance();
+ instance.Template = tableTemplate;
+ MasterRepository.Add(instance);
+ MessageDispatcher.Send(MessageType.OpenDetail, instance);
+ }
else if (model is CustomDynamicTable dynTableTemplate)
{
var instance = new CustomDynamicTableInstance();
diff --git a/eos-edit/Views/CustomDynamicTableView.axaml b/eos-edit/Views/CustomDynamicTableView.axaml
index 7e8c230..3c367f9 100644
--- a/eos-edit/Views/CustomDynamicTableView.axaml
+++ b/eos-edit/Views/CustomDynamicTableView.axaml
@@ -48,11 +48,11 @@
-
-
-
-
-
+
+
+
+
+
diff --git a/eos-edit/Views/CustomTableInstanceView.axaml b/eos-edit/Views/CustomTableInstanceView.axaml
new file mode 100644
index 0000000..4f1a807
--- /dev/null
+++ b/eos-edit/Views/CustomTableInstanceView.axaml
@@ -0,0 +1,60 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/eos-edit/Views/CustomTableInstanceView.axaml.cs b/eos-edit/Views/CustomTableInstanceView.axaml.cs
new file mode 100644
index 0000000..069c4f2
--- /dev/null
+++ b/eos-edit/Views/CustomTableInstanceView.axaml.cs
@@ -0,0 +1,84 @@
+using Avalonia.Controls;
+using Avalonia.Controls.Presenters;
+using Avalonia.Controls.Templates;
+using Avalonia.Markup.Xaml.Templates;
+using Eos.Extensions;
+using Eos.Models.Tables;
+using Eos.Usercontrols;
+using Eos.ViewModels;
+using Microsoft.CodeAnalysis.CSharp.Syntax;
+using System.Drawing.Printing;
+
+namespace Eos.Views
+{
+ public class CustomTableColumnDataTemplate : IDataTemplate
+ {
+ private CustomObjectProperty _property;
+ private IDataTemplate _templateSelector;
+
+ public CustomTableColumnDataTemplate(CustomObjectProperty property, IDataTemplate templateSelector)
+ {
+ _property = property;
+ _templateSelector = templateSelector;
+ }
+
+ public bool Match(object? data)
+ {
+ return true;
+ }
+
+ Control? ITemplate
+
+
+
+
+
@@ -478,6 +487,12 @@
+
+
+
+
+
+
@@ -1426,6 +1441,14 @@
+
+
+
+
+
+
+
+
@@ -1448,6 +1471,15 @@
+
+
+
+
+
+
+
+
+
@@ -1472,9 +1504,40 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/eos-edit/Views/MainWindow.axaml.cs b/eos-edit/Views/MainWindow.axaml.cs
index e45e98b..88eb270 100644
--- a/eos-edit/Views/MainWindow.axaml.cs
+++ b/eos-edit/Views/MainWindow.axaml.cs
@@ -150,7 +150,7 @@ private void ViewModel_PropertyChanged(object? sender, PropertyChangedEventArgs
var viewModel = (MainWindowViewModel?)DataContext;
if ((viewModel != null) && (e.PropertyName == nameof(viewModel.CurrentView)) && (viewModel.CurrentView?.GetDataObject() is BaseModel model))
{
- if ((model is CustomObjectInstance) || (model is CustomDynamicTableInstance))
+ if ((model is CustomObjectInstance) || (model is CustomDynamicTableInstance) || (model is CustomTableInstance))
{
if (tvAdditional.Items != null)
{
diff --git a/eos-edit/eos-edit.csproj b/eos-edit/eos-edit.csproj
index 9faf0e9..ba7d866 100644
--- a/eos-edit/eos-edit.csproj
+++ b/eos-edit/eos-edit.csproj
@@ -161,6 +161,9 @@
BaseItemComboBox.axaml
+
+ CustomTableComboBox.axaml
+
CustomDynamicTableComboBox.axaml
@@ -258,6 +261,9 @@
CustomDynamicTableView.axaml
+
+ CustomTableView.axaml
+
DamageTypeGroupView.axaml
@@ -270,6 +276,9 @@
ProgrammedEffectView.axaml
+
+ CustomTableInstanceView.axaml
+
VisualEffectView.axaml
diff --git a/eos/Models/BaseModel.cs b/eos/Models/BaseModel.cs
index a4ad6d8..3e4593c 100644
--- a/eos/Models/BaseModel.cs
+++ b/eos/Models/BaseModel.cs
@@ -351,6 +351,8 @@ public virtual void ResolveReferences()
{
if ((varModel is CustomObjectInstance coInstance) && (varValue.DataType?.CustomType is CustomObject template))
varValue.Value = MasterRepository.Project.CustomObjectRepositories[template].GetByID(coInstance.ID);
+ else if ((varModel is CustomTableInstance ctInstance) && (varValue.DataType?.CustomType is CustomTable tableTemplate))
+ varValue.Value = MasterRepository.Project.CustomTableRepositories[tableTemplate].GetByID(ctInstance.ID);
else if ((varModel is CustomDynamicTableInstance cdtInstance) && (varValue.DataType?.CustomType is CustomDynamicTable dynTableTemplate))
varValue.Value = MasterRepository.Project.CustomDynamicTableRepositories[dynTableTemplate].GetByID(cdtInstance.ID);
else
@@ -360,6 +362,8 @@ public virtual void ResolveReferences()
{
if ((model is CustomObjectInstance coInstance) && (prop.DataType?.CustomType is CustomObject template))
extensionValueDict[prop].Value = MasterRepository.Project.CustomObjectRepositories[template].GetByID(coInstance.ID);
+ else if ((model is CustomTableInstance ctInstance) && (prop.DataType?.CustomType is CustomTable tableTemplate))
+ extensionValueDict[prop].Value = MasterRepository.Project.CustomTableRepositories[tableTemplate].GetByID(ctInstance.ID);
else if ((model is CustomDynamicTableInstance cdtInstance) && (prop.DataType?.CustomType is CustomDynamicTable dynTableTemplate))
extensionValueDict[prop].Value = MasterRepository.Project.CustomDynamicTableRepositories[dynTableTemplate].GetByID(cdtInstance.ID);
else
@@ -419,6 +423,8 @@ public void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
+ if (propertyName == "Name") // Hacky McHack
+ PropertyChanged(this, new PropertyChangedEventArgs("Label"));
}
}
}
diff --git a/eos/Models/CustomDynamicTable.cs b/eos/Models/CustomDynamicTable.cs
index 25d4c60..68f5e6f 100644
--- a/eos/Models/CustomDynamicTable.cs
+++ b/eos/Models/CustomDynamicTable.cs
@@ -47,6 +47,9 @@ public CustomDynamicTable() : base()
private void InstanceRepository_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
{
+ // Delay, because otherwise bindings won't update immediately
+ Task.Delay(5).ContinueWith(t => NotifyPropertyChanged(nameof(InstanceRepository)));
+
// Suddenly works ??
//if ((e.Action == NotifyCollectionChangedAction.Reset) || (e.Action == NotifyCollectionChangedAction.Move))
// NotifyPropertyChanged(nameof(InstanceRepository));
@@ -65,12 +68,12 @@ public string Name
}
}
- public String ResourceName { get; set; } = "";
+ public String FileName { get; set; } = "";
protected override void SetDefaultValues()
{
Name = "New Dynamic Table";
- ResourceName = "newdyntable";
+ FileName = "newdyntable";
}
public override String GetLabel()
@@ -82,14 +85,14 @@ public override void FromJson(JsonObject json)
{
base.FromJson(json);
this.Name = json["Name"]?.GetValue() ?? "";
- this.ResourceName = json["ResourceName"]?.GetValue() ?? "";
+ this.FileName = json["FileName"]?.GetValue() ?? json["ResourceName"]?.GetValue() ?? "";
}
public override JsonObject ToJson()
{
var customDynTableJson = base.ToJson();
customDynTableJson.Add("Name", this.Name);
- customDynTableJson.Add("ResourceName", this.ResourceName);
+ customDynTableJson.Add("FileName", this.FileName);
return customDynTableJson;
}
diff --git a/eos/Models/Tables/BaseTable.cs b/eos/Models/Tables/BaseTable.cs
index 4ab1cd9..2d1b7a8 100644
--- a/eos/Models/Tables/BaseTable.cs
+++ b/eos/Models/Tables/BaseTable.cs
@@ -85,10 +85,16 @@ public void Add(T item)
if (Count < GetMaximumItems())
{
item.ParentTable = this;
+ OnItemAdd(item);
_items.Add(item);
}
}
+ protected virtual void OnItemAdd(T item)
+ {
+
+ }
+
public void Remove(T item)
{
item.ParentTable = null;
diff --git a/eos/Models/Tables/CustomObject.cs b/eos/Models/Tables/CustomObject.cs
index a958b16..3b502db 100644
--- a/eos/Models/Tables/CustomObject.cs
+++ b/eos/Models/Tables/CustomObject.cs
@@ -50,6 +50,9 @@ public CustomObject() : base()
private void InstanceRepository_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
{
+ // Delay, because otherwise bindings won't update immediately
+ Task.Delay(5).ContinueWith(t => NotifyPropertyChanged(nameof(InstanceRepository)));
+
// Suddenly works ??
//if ((e.Action == NotifyCollectionChangedAction.Reset) || (e.Action == NotifyCollectionChangedAction.Move))
// NotifyPropertyChanged(nameof(InstanceRepository));
diff --git a/eos/Models/Tables/CustomObjectProperty.cs b/eos/Models/Tables/CustomObjectProperty.cs
index b13272c..46a881a 100644
--- a/eos/Models/Tables/CustomObjectProperty.cs
+++ b/eos/Models/Tables/CustomObjectProperty.cs
@@ -66,6 +66,10 @@ public CustomObjectProperty(CustomObject parentTable) : base(parentTable)
{
}
+ public CustomObjectProperty(CustomTable parentTable) : base(parentTable)
+ {
+ }
+
public override void ResolveReferences()
{
DataType = MasterRepository.GetDataTypeById(DataType?.ID ?? Guid.Empty);
diff --git a/eos/Models/Tables/CustomTable.cs b/eos/Models/Tables/CustomTable.cs
new file mode 100644
index 0000000..7dd916c
--- /dev/null
+++ b/eos/Models/Tables/CustomTable.cs
@@ -0,0 +1,84 @@
+using Eos.Repositories;
+using Eos.Types;
+using System;
+using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.Collections.Specialized;
+using System.Linq;
+using System.Text;
+using System.Text.Json.Nodes;
+using System.Threading.Tasks;
+using System.Xml.Linq;
+
+namespace Eos.Models.Tables
+{
+ public class CustomTable : BaseTable
+ {
+ private DataTypeDefinition dataTypeDefinition = new DataTypeDefinition(Guid.Empty, String.Empty, null);
+
+ public DataTypeDefinition DataTypeDefinition
+ {
+ get
+ {
+ if (dataTypeDefinition.ID != ID)
+ {
+ dataTypeDefinition = new DataTypeDefinition(ID, Name, this, true);
+ dataTypeDefinition.ToJson = o => ((CustomTableInstance?)o)?.ToJsonRef();
+ dataTypeDefinition.To2DA = (o, lower, _) => lower ? ((CustomTableInstance?)o)?.Name?.ToLower() : ((CustomTableInstance?)o)?.Name;
+ dataTypeDefinition.FromJson = json => JsonUtils.CreateRefFromJson((JsonObject?)json);
+ }
+ return dataTypeDefinition;
+ }
+ }
+
+ public ModelRepository InstanceRepository { get; set; }
+
+ public event EventHandler? OnChanged;
+
+ public String FileName { get; set; } = "";
+
+ public CustomTable() : base()
+ {
+ InstanceRepository = MasterRepository.Project.CustomTableRepositories[this];
+ InstanceRepository.CollectionChanged += InstanceRepository_CollectionChanged;
+ }
+
+ ~CustomTable()
+ {
+ InstanceRepository.CollectionChanged -= InstanceRepository_CollectionChanged;
+ }
+
+ private void InstanceRepository_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
+ {
+ // Delay, because otherwise bindings won't update immediately
+ Task.Delay(5).ContinueWith(t => NotifyPropertyChanged(nameof(InstanceRepository)));
+
+ // Suddenly works ??
+ //if ((e.Action == NotifyCollectionChangedAction.Reset) || (e.Action == NotifyCollectionChangedAction.Move))
+ // NotifyPropertyChanged(nameof(InstanceRepository));
+ }
+
+ protected override void SetDefaultValues()
+ {
+ Name = "New Table";
+ }
+
+ public override JsonObject ToJson()
+ {
+ var json = base.ToJson();
+ json.Add("FileName", FileName);
+ return json;
+ }
+
+ public override void FromJson(JsonObject json)
+ {
+ base.FromJson(json);
+ FileName = json["FileName"]?.GetValue() ?? "";
+ }
+
+ protected override void Changed()
+ {
+ OnChanged?.Invoke(this, new EventArgs());
+ }
+ }
+}
diff --git a/eos/Models/Tables/CustomTableInstance.cs b/eos/Models/Tables/CustomTableInstance.cs
new file mode 100644
index 0000000..2d0ad97
--- /dev/null
+++ b/eos/Models/Tables/CustomTableInstance.cs
@@ -0,0 +1,60 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Text.Json.Nodes;
+using System.Threading.Tasks;
+using Eos.Repositories;
+
+using static Eos.Models.JsonUtils;
+
+namespace Eos.Models.Tables
+{
+ public class CustomTableInstance : BaseTable
+ {
+ private CustomTable? _template;
+
+ public CustomTable? Template
+ {
+ get { return _template; }
+ set
+ {
+ Set(ref _template, value);
+
+ foreach (var item in Items)
+ {
+ if (item == null) continue;
+ item.Template = _template;
+ }
+ }
+ }
+
+ protected override void SetDefaultValues()
+ {
+ Name = "NEW_TABLE";
+ }
+
+ protected override void OnItemAdd(CustomTableInstanceItem item)
+ {
+ if (item.Template == null)
+ item.Template = Template;
+ }
+
+ public override void FromJson(JsonObject json)
+ {
+ this.Name = json["Label"]?.GetValue() ?? "";
+ this.Template = MasterRepository.CustomTables.GetByID(ParseGuid(json["Template"]?["ID"]?.GetValue()));
+
+ base.FromJson(json);
+ }
+
+ public override JsonObject ToJson()
+ {
+ var customTableJson = base.ToJson();
+ customTableJson.Add("Label", this.Name);
+ customTableJson.Add("Template", CreateJsonRef(this.Template));
+
+ return customTableJson;
+ }
+ }
+}
diff --git a/eos/Models/Tables/CustomTableInstanceItem.cs b/eos/Models/Tables/CustomTableInstanceItem.cs
new file mode 100644
index 0000000..8d623e6
--- /dev/null
+++ b/eos/Models/Tables/CustomTableInstanceItem.cs
@@ -0,0 +1,155 @@
+using Eos.Repositories;
+using Eos.Types;
+using System;
+using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.Diagnostics.Metrics;
+using System.Linq;
+using System.Text;
+using System.Text.Json.Nodes;
+using System.Threading.Tasks;
+
+using static Eos.Models.JsonUtils;
+
+namespace Eos.Models.Tables
+{
+ public class CustomTableInstanceItem : TableItem
+ {
+ private CustomTable? _template;
+ private Dictionary valueDict = new Dictionary();
+
+ public CustomTableInstanceItem() : base()
+ {
+ }
+
+ public CustomTableInstanceItem(CustomTableInstance parentTable) : base(parentTable)
+ {
+
+ }
+
+ public ObservableCollection Values { get; } = new ObservableCollection();
+
+ public CustomTable? Template
+ {
+ get { return _template; }
+ set
+ {
+ if (_template != value)
+ {
+ if (_template != null)
+ _template.OnChanged -= _template_OnChanged;
+ Set(ref _template, value);
+ if (_template != null)
+ _template.OnChanged += _template_OnChanged;
+
+ InitValueDictionary();
+ }
+ }
+ }
+
+ private void _template_OnChanged(object? sender, EventArgs e)
+ {
+ InitValueDictionary();
+ }
+
+ private void InitValueDictionary()
+ {
+ if (_template == null)
+ {
+ Values.Clear();
+ }
+ else
+ {
+ // Remove missing values
+ foreach (var prop in valueDict.Keys)
+ {
+ if ((prop != null) && (!_template.Contains(prop)))
+ {
+ Values.Remove(valueDict[prop]);
+ valueDict.Remove(prop);
+ }
+ }
+
+ // Add new values
+ foreach (var prop in _template.Items)
+ {
+ if (prop != null)
+ {
+ if (!valueDict.ContainsKey(prop))
+ {
+ var valueInstance = new CustomValueInstance(prop);
+ valueDict[prop] = valueInstance;
+ Values.Add(valueInstance);
+ }
+ }
+ }
+
+ // Reorder
+ for (int i = 0; i < _template.Count; i++)
+ {
+ var prop = _template[i];
+ if (prop != null)
+ {
+ var custValue = Values.First(val => val.Property == prop);
+ var index = Values.IndexOf(custValue);
+ Values.Move(index, i);
+ }
+ }
+ }
+ }
+
+ public CustomValueInstance? GetPropertyValue(CustomObjectProperty property)
+ {
+ if (!valueDict.TryGetValue(property, out var value))
+ return null;
+
+ return value;
+ }
+
+ public override void ResolveReferences()
+ {
+ foreach (var prop in valueDict.Keys)
+ {
+ if ((valueDict[prop].Value is VariantValue varValue) && (varValue.Value is BaseModel varModel))
+ {
+ if ((varModel is CustomObjectInstance coInstance) && (varValue.DataType?.CustomType is CustomObject template))
+ varValue.Value = MasterRepository.Project.CustomObjectRepositories[template].GetByID(coInstance.ID);
+ else
+ varValue.Value = ResolveByType(varModel.GetType(), varModel.ID);
+ }
+ else if (valueDict[prop].Value is BaseModel model)
+ {
+ if ((model is CustomObjectInstance coInstance) && (prop.DataType?.CustomType is CustomObject template))
+ valueDict[prop].Value = MasterRepository.Project.CustomObjectRepositories[template].GetByID(coInstance.ID);
+ else
+ valueDict[prop].Value = ResolveByType(model.GetType(), model.ID);
+ }
+ }
+ }
+
+ public override void FromJson(JsonObject json)
+ {
+ base.FromJson(json);
+
+ this.Template = ((CustomTableInstance?)ParentTable)?.Template;
+ foreach (var prop in valueDict.Keys)
+ {
+ if (!prop.DataType?.IsVisualOnly ?? false)
+ valueDict[prop].Value = prop.ValueFromJson(json[prop.Column]);
+ }
+ }
+
+ public override JsonObject ToJson()
+ {
+ var customObjectJson = base.ToJson();
+
+ foreach (var prop in valueDict.Keys)
+ {
+ if (!prop.DataType?.IsVisualOnly ?? false)
+ customObjectJson.Add(prop.Column, prop.ValueToJson(valueDict[prop].Value));
+ }
+
+ return customObjectJson;
+ }
+ }
+}
diff --git a/eos/Models/Tables/TableItem.cs b/eos/Models/Tables/TableItem.cs
index aaf67da..f0a5ecf 100644
--- a/eos/Models/Tables/TableItem.cs
+++ b/eos/Models/Tables/TableItem.cs
@@ -1,4 +1,5 @@
-using System;
+using Eos.Repositories;
+using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
@@ -38,7 +39,8 @@ public virtual void FromJson(JsonObject json)
public virtual JsonObject ToJson()
{
var item = new JsonObject();
- item.Add("SourceLabel", this.SourceLabel);
+ if (this.SourceLabel != "")
+ item.Add("SourceLabel", this.SourceLabel);
return item;
}
@@ -59,6 +61,11 @@ public virtual bool IsValid()
return true;
}
+ protected BaseModel? ResolveByType(Type modelType, Guid id)
+ {
+ return MasterRepository.Standard.GetByID(modelType, id) ?? MasterRepository.Project.GetByID(modelType, id);
+ }
+
public void NotifyPropertyChanged([CallerMemberName] string propertyName = "") // TODOX: protected // !
{
if (PropertyChanged != null)
diff --git a/eos/Repositories/EosProject.cs b/eos/Repositories/EosProject.cs
index 371ee98..cdefbf1 100644
--- a/eos/Repositories/EosProject.cs
+++ b/eos/Repositories/EosProject.cs
@@ -758,6 +758,7 @@ public void CreateBackup()
AddZipEntry(zip, ProjectFolder + Constants.CustomEnumsFilename, Constants.CustomEnumsFilename);
AddZipEntry(zip, ProjectFolder + Constants.CustomObjectsFilename, Constants.CustomObjectsFilename);
+ AddZipEntry(zip, ProjectFolder + Constants.CustomTablesFilename, Constants.CustomTablesFilename);
AddZipEntry(zip, ProjectFolder + Constants.CustomDynamicTablesFilename, Constants.CustomDynamicTablesFilename);
foreach (var template in CustomObjects)
@@ -766,11 +767,17 @@ public void CreateBackup()
AddZipEntry(zip, ProjectFolder + template.ResourceName + ".json", template.ResourceName + ".json");
}
+ foreach (var template in CustomTables)
+ {
+ if (template != null)
+ AddZipEntry(zip, ProjectFolder + template.FileName + ".json", template.FileName + ".json");
+ }
+
foreach (var template in CustomDynamicTables)
{
if (template != null)
{
- AddZipEntry(zip, ProjectFolder + template.ResourceName + ".json", template.ResourceName + ".json");
+ AddZipEntry(zip, ProjectFolder + template.FileName + ".json", template.FileName + ".json");
}
}
}
@@ -791,10 +798,12 @@ public void Load(string projectFilename)
{
CustomEnums.LoadFromFile(ProjectFolder + Constants.CustomEnumsFilename);
CustomObjects.LoadFromFile(ProjectFolder + Constants.CustomObjectsFilename);
+ CustomTables.LoadFromFile(ProjectFolder + Constants.CustomTablesFilename);
CustomDynamicTables.LoadFromFile(ProjectFolder + Constants.CustomDynamicTablesFilename);
CustomEnums.ResolveReferences();
CustomObjects.ResolveReferences();
+ CustomTables.ResolveReferences();
CustomDynamicTables.ResolveReferences();
foreach (var customObj in CustomObjects)
@@ -803,6 +812,12 @@ public void Load(string projectFilename)
CustomObjectRepositories.AddRepository(customObj);
}
+ foreach (var customTable in CustomTables)
+ {
+ if (customTable != null)
+ CustomTableRepositories.AddRepository(customTable);
+ }
+
foreach (var customDynTable in CustomDynamicTables)
{
if (customDynTable != null)
@@ -864,10 +879,16 @@ public void Load(string projectFilename)
CustomObjectRepositories[template].LoadFromFile(ProjectFolder + template.ResourceName + ".json");
}
+ foreach (var template in CustomTables)
+ {
+ if (template != null)
+ CustomTableRepositories[template].LoadFromFile(ProjectFolder + template.FileName + ".json");
+ }
+
foreach (var template in CustomDynamicTables)
{
if (template != null)
- CustomDynamicTableRepositories[template].LoadFromFile(ProjectFolder + template.ResourceName + ".json");
+ CustomDynamicTableRepositories[template].LoadFromFile(ProjectFolder + template.FileName + ".json");
}
Races.ResolveReferences();
@@ -925,6 +946,12 @@ public void Load(string projectFilename)
CustomObjectRepositories[template].ResolveReferences();
}
+ foreach (var template in CustomTables)
+ {
+ if (template != null)
+ CustomTableRepositories[template].ResolveReferences();
+ }
+
foreach (var template in CustomDynamicTables)
{
if (template != null)
@@ -1052,6 +1079,7 @@ public void Save()
CustomEnums.SaveToFile(ProjectFolder + Constants.CustomEnumsFilename, Settings.CustomData.FormatJson);
CustomObjects.SaveToFile(ProjectFolder + Constants.CustomObjectsFilename, Settings.CustomData.FormatJson);
+ CustomTables.SaveToFile(ProjectFolder + Constants.CustomTablesFilename, Settings.CustomData.FormatJson);
CustomDynamicTables.SaveToFile(ProjectFolder + Constants.CustomDynamicTablesFilename, Settings.CustomData.FormatJson);
foreach (var template in CustomObjects)
@@ -1060,10 +1088,16 @@ public void Save()
CustomObjectRepositories[template].SaveToFile(ProjectFolder + template.ResourceName + ".json", Settings.CustomData.FormatJson);
}
+ foreach (var template in CustomTables)
+ {
+ if (template != null)
+ CustomTableRepositories[template].SaveToFile(ProjectFolder + template.FileName + ".json", Settings.CustomData.FormatJson);
+ }
+
foreach (var template in CustomDynamicTables)
{
if (template != null)
- CustomDynamicTableRepositories[template].SaveToFile(ProjectFolder + template.ResourceName + ".json", Settings.CustomData.FormatJson);
+ CustomDynamicTableRepositories[template].SaveToFile(ProjectFolder + template.FileName + ".json", Settings.CustomData.FormatJson);
}
}
catch (Exception e)
diff --git a/eos/Repositories/MasterRepository.cs b/eos/Repositories/MasterRepository.cs
index 288f61b..c0f7bfe 100644
--- a/eos/Repositories/MasterRepository.cs
+++ b/eos/Repositories/MasterRepository.cs
@@ -86,6 +86,7 @@ public static class MasterRepository
// Custom Datatypes
private static readonly VirtualModelRepository customEnumVirtualRepository;
private static readonly VirtualModelRepository customObjectVirtualRepository;
+ private static readonly VirtualModelRepository customTableVirtualRepository;
private static readonly VirtualModelRepository customDynamicTableVirtualRepository;
static MasterRepository()
@@ -182,6 +183,7 @@ static MasterRepository()
// Custom Datatypes
customEnumVirtualRepository = new VirtualModelRepository(standardCategory.CustomEnums, project.CustomEnums);
customObjectVirtualRepository = new VirtualModelRepository(standardCategory.CustomObjects, project.CustomObjects);
+ customTableVirtualRepository = new VirtualModelRepository(standardCategory.CustomTables, project.CustomTables);
customDynamicTableVirtualRepository = new VirtualModelRepository(standardCategory.CustomDynamicTables, project.CustomDynamicTables);
InitDefaultDataTypes();
@@ -321,6 +323,10 @@ private static void InitDefaultDataTypes()
if (customObject != null)
return customObject.DataTypeDefinition;
+ var customTable = Project.CustomTables.GetByID(id);
+ if (customTable != null)
+ return customTable.DataTypeDefinition;
+
var customDynTable = Project.CustomDynamicTables.GetByID(id);
if (customDynTable != null)
return customDynTable.DataTypeDefinition;
@@ -420,6 +426,7 @@ public static void Add(BaseModel model)
// Custom Datatypes
public static VirtualModelRepository CustomEnums { get { return customEnumVirtualRepository; } }
public static VirtualModelRepository CustomObjects { get { return customObjectVirtualRepository; } }
+ public static VirtualModelRepository CustomTables { get { return customTableVirtualRepository; } }
public static VirtualModelRepository CustomDynamicTables { get { return customDynamicTableVirtualRepository; } }
public static IEnumerable DataTypes
@@ -428,8 +435,9 @@ public static IEnumerable DataTypes
{
var enumTypes = CustomEnums.Select(ce => ce?.DataTypeDefinition);
var objectTypes = CustomObjects.Select(co => co?.DataTypeDefinition);
+ var tableTypes = CustomTables.Select(ct => ct?.DataTypeDefinition);
var dynTableTypes = CustomDynamicTables.Select(cdt => cdt?.DataTypeDefinition);
- return defaultDataTypeList.Concat(enumTypes).Concat(objectTypes).Concat(dynTableTypes);
+ return defaultDataTypeList.Concat(enumTypes).Concat(objectTypes).Concat(tableTypes).Concat(dynTableTypes);
}
}
diff --git a/eos/Repositories/Repository.cs b/eos/Repositories/Repository.cs
index 995321d..b63bcc2 100644
--- a/eos/Repositories/Repository.cs
+++ b/eos/Repositories/Repository.cs
@@ -83,7 +83,8 @@ protected void RaiseCollectionChanged(NotifyCollectionChangedEventArgs e)
private void Item_PropertyChanged(object? sender, PropertyChangedEventArgs e)
{
- RaiseCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
+ // Works better without.. But why did I have it in in the first place? It used to fix *something*...
+ //RaiseCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
}
protected virtual void Changed()
diff --git a/eos/Repositories/RepositoryCollection.cs b/eos/Repositories/RepositoryCollection.cs
index 1804d7d..7904d6d 100644
--- a/eos/Repositories/RepositoryCollection.cs
+++ b/eos/Repositories/RepositoryCollection.cs
@@ -62,6 +62,32 @@ public void Clear()
}
}
+ public class CustomTableRepositoryCollection
+ {
+ private Dictionary> repositoryDict = new Dictionary>();
+
+ public ModelRepository this[CustomTable index] => AddRepository(index);
+
+ public ModelRepository AddRepository(CustomTable customDynamicTable)
+ {
+ if (!repositoryDict.TryGetValue(customDynamicTable, out var repo))
+ {
+ repo = RepositoryFactory.Create(false);
+ //repo.CollectionChanged += (_, _) => NotifyPropertyChanged(nameof(CustomObjectInstances)); // TODO: ?
+ repositoryDict.Add(customDynamicTable, repo);
+ }
+
+ return repo;
+ }
+
+ public void Clear()
+ {
+ foreach (var repo in repositoryDict.Values)
+ repo.Clear();
+ repositoryDict.Clear();
+ }
+ }
+
public class RepositoryCollection : INotifyPropertyChanged
{
private readonly bool isReadonly;
@@ -121,15 +147,17 @@ public class RepositoryCollection : INotifyPropertyChanged
// Custom Datatypes
private readonly ModelRepository customEnumRepository;
private readonly ModelRepository customObjectRepository;
+ private readonly ModelRepository customTableRepository;
private readonly ModelRepository customDynamicTableRepository;
private readonly CustomObjectRepositoryCollection customObjectRepositoryCollection = new CustomObjectRepositoryCollection();
+ private readonly CustomTableRepositoryCollection customTableRepositoryCollection = new CustomTableRepositoryCollection();
private readonly CustomDynamicTableRepositoryCollection customDynamicTableRepositoryCollection = new CustomDynamicTableRepositoryCollection();
private void InitRepository(out ModelRepository repository, string propertyName) where T : BaseModel, new()
{
repository = RepositoryFactory.Create(isReadonly);
- repository.CollectionChanged += (_, _) => NotifyPropertyChanged(propertyName);
+ repository.CollectionChanged += (_, _) => Task.Delay(5).ContinueWith(t => NotifyPropertyChanged(propertyName));// Delay, because otherwise bindings won't update immediately
repositoryDict.Add(typeof(T), repository);
}
@@ -190,6 +218,7 @@ public RepositoryCollection(bool isReadonly)
// Custom Datatypes
InitRepository(out customEnumRepository, nameof(CustomEnums));
InitRepository(out customObjectRepository, nameof(CustomObjects));
+ InitRepository(out customTableRepository, nameof(CustomTables));
InitRepository(out customDynamicTableRepository, nameof(CustomDynamicTables));
}
@@ -245,9 +274,11 @@ public RepositoryCollection(bool isReadonly)
// Custom Datatypes
public ModelRepository CustomEnums { get { return customEnumRepository; } }
public ModelRepository CustomObjects { get { return customObjectRepository; } }
+ public ModelRepository CustomTables { get { return customTableRepository; } }
public ModelRepository CustomDynamicTables { get { return customDynamicTableRepository; } }
public CustomObjectRepositoryCollection CustomObjectRepositories { get { return customObjectRepositoryCollection; } }
+ public CustomTableRepositoryCollection CustomTableRepositories { get { return customTableRepositoryCollection; } }
public CustomDynamicTableRepositoryCollection CustomDynamicTableRepositories { get { return customDynamicTableRepositoryCollection; } }
public IEnumerable AllRepositories => repositoryDict.Values;
@@ -268,7 +299,16 @@ public BaseModel New(Type modelType)
public void Add(BaseModel model)
{
- if (model is CustomDynamicTableInstance cdti)
+ if (model is CustomTableInstance cti)
+ {
+ if (cti.Template != null)
+ {
+ if (cti.Index == null)
+ cti.Index = CustomTableRepositories[cti.Template].GetNextFreeIndex();
+ CustomTableRepositories[cti.Template].Add(cti);
+ }
+ }
+ else if(model is CustomDynamicTableInstance cdti)
{
if (cdti.Template != null)
{
@@ -307,7 +347,12 @@ public void Add(BaseModel model)
public void Delete(BaseModel model)
{
- if (model is CustomDynamicTableInstance cdti)
+ if (model is CustomTableInstance cti)
+ {
+ if (cti.Template != null)
+ CustomTableRepositories[cti.Template].Remove(cti);
+ }
+ else if (model is CustomDynamicTableInstance cdti)
{
if (cdti.Template != null)
CustomDynamicTableRepositories[cdti.Template].Remove(cdti);
@@ -342,7 +387,13 @@ public bool HasOverride(BaseModel model)
public int? GetBase2DAIndex(BaseModel model, bool returnCustomDataIndex = true)
{
- if (model is CustomDynamicTableInstance cdti)
+ if (model is CustomTableInstance cti)
+ {
+ if (cti.Template != null)
+ return CustomTableRepositories[cti.Template].GetBase2DAIndex(model, returnCustomDataIndex);
+ return -1;
+ }
+ else if (model is CustomDynamicTableInstance cdti)
{
if (cdti.Template != null)
return CustomDynamicTableRepositories[cdti.Template].GetBase2DAIndex(model, returnCustomDataIndex);
@@ -416,9 +467,11 @@ public void Clear()
// Custom Datatypes
CustomEnums.Clear();
CustomObjects.Clear();
+ CustomTables.Clear();
CustomDynamicTables.Clear();
CustomObjectRepositories.Clear();
+ CustomTableRepositories.Clear();
CustomDynamicTableRepositories.Clear();
}
diff --git a/eos/Services/CustomDataExport.cs b/eos/Services/CustomDataExport.cs
index e069486..90f6b2d 100644
--- a/eos/Services/CustomDataExport.cs
+++ b/eos/Services/CustomDataExport.cs
@@ -3541,6 +3541,63 @@ private void ExportCustomObjects(EosProject project)
}
}
+ private void ExportCustomTables(EosProject project)
+ {
+ foreach (var template in project.CustomTables)
+ {
+ if (template == null) continue;
+
+ var repo = project.CustomTableRepositories[template];
+ if (repo.Count == 0) return;
+
+ var columns = new List();
+ var columnLower = new List();
+ foreach (var prop in template.Items)
+ {
+ if ((prop == null) || (prop.DataType?.IsVisualOnly ?? false)) continue;
+ columns.Add(prop.Column);
+ columnLower.Add(prop.DataType?.ID.Equals(new Guid("e4897c44-4117-45d4-b3fc-37b82fd88247")) ?? false);
+ }
+
+ foreach (var instance in repo)
+ {
+ if (instance == null) continue;
+
+ Log.Info("Exporting 2DA: \"{0}\"", Path.GetFullPath(project.Settings.Export.TwoDAFolder + instance.Name.ToLower() + ".2da"));
+
+ var custom2da = new TwoDimensionalArrayFile();
+ custom2da.New(columns.ToArray());
+
+ if (project.Settings.Export.LowercaseFilenames)
+ {
+ for (int i = 0; i < columns.Count; i++)
+ {
+ if (columnLower[i])
+ custom2da.Columns.SetLowercase(columns[i].Trim());
+ }
+ }
+
+ foreach (var item in instance.Items)
+ {
+ if (item != null)
+ {
+ var rec = custom2da.AddRecord();
+ foreach (var value in item.Values)
+ {
+ if ((!value.Property.DataType?.IsVisualOnly ?? false) && (value.Property.DataType?.To2DA != null))
+ rec.Set(value.Property.Column, value.Property.DataType?.To2DA(value.Value, project.Settings.Export.LowercaseFilenames, GetTLKIndex));
+ }
+ }
+ }
+
+ var filename = project.Settings.Export.TwoDAFolder + instance.Name.ToLower() + ".2da";
+ custom2da.Save(filename, project.Settings.Export.Compress2DA);
+
+ AddHAKResource(instance.Name.ToLower(), NWNResourceType.TWODA, filename);
+ }
+ }
+ }
+
private void ExportCustomDynamicTables(EosProject project)
{
foreach (var template in project.CustomDynamicTables)
@@ -3554,6 +3611,8 @@ private void ExportCustomDynamicTables(EosProject project)
{
if (instance == null) continue;
+ Log.Info("Exporting 2DA: \"{0}\"", Path.GetFullPath(project.Settings.Export.TwoDAFolder + instance.Name.ToLower() + ".2da"));
+
var columns = new List();
var custColumns = new List
{
@@ -4096,6 +4155,7 @@ public void Export(EosProject project)
ExportDamageTypeGroups(project);
ExportCustomObjects(project);
+ ExportCustomTables(project);
ExportCustomDynamicTables(project);
ExportIncludeFile(project);
diff --git a/eos/Types/Constants.cs b/eos/Types/Constants.cs
index ee6c6e2..e9258c5 100644
--- a/eos/Types/Constants.cs
+++ b/eos/Types/Constants.cs
@@ -79,6 +79,7 @@ public static class Constants
public static readonly String CustomEnumsFilename;
public static readonly String CustomObjectsFilename;
+ public static readonly String CustomTablesFilename;
public static readonly String CustomDynamicTablesFilename;
public static readonly String IconResourcesFolder;
@@ -212,6 +213,7 @@ static Constants()
CustomEnumsFilename = "customenums.json";
CustomObjectsFilename = "customobjects.json";
+ CustomTablesFilename = "customtables.json";
CustomDynamicTablesFilename = "customdyntables.json";
IconResourcesFolder = @"icons" + Path.DirectorySeparatorChar;