Add support for multiple VisibleIf attributes, and properly set up the VisibleIf entries for ImportMaterialsAsInstances and InstanceToImportAs.
This commit is contained in:
@@ -66,9 +66,9 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
public HeaderAttribute Header;
|
public HeaderAttribute Header;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The visible if attribute.
|
/// The visible if attributes.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public VisibleIfAttribute VisibleIf;
|
public VisibleIfAttribute[] VisibleIfs;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The read-only attribute usage flag.
|
/// The read-only attribute usage flag.
|
||||||
@@ -128,7 +128,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
CustomEditorAlias = (CustomEditorAliasAttribute)attributes.FirstOrDefault(x => x is CustomEditorAliasAttribute);
|
CustomEditorAlias = (CustomEditorAliasAttribute)attributes.FirstOrDefault(x => x is CustomEditorAliasAttribute);
|
||||||
Space = (SpaceAttribute)attributes.FirstOrDefault(x => x is SpaceAttribute);
|
Space = (SpaceAttribute)attributes.FirstOrDefault(x => x is SpaceAttribute);
|
||||||
Header = (HeaderAttribute)attributes.FirstOrDefault(x => x is HeaderAttribute);
|
Header = (HeaderAttribute)attributes.FirstOrDefault(x => x is HeaderAttribute);
|
||||||
VisibleIf = (VisibleIfAttribute)attributes.FirstOrDefault(x => x is VisibleIfAttribute);
|
VisibleIfs = attributes.OfType<VisibleIfAttribute>().ToArray();
|
||||||
IsReadOnly = attributes.FirstOrDefault(x => x is ReadOnlyAttribute) != null;
|
IsReadOnly = attributes.FirstOrDefault(x => x is ReadOnlyAttribute) != null;
|
||||||
ExpandGroups = attributes.FirstOrDefault(x => x is ExpandGroupsAttribute) != null;
|
ExpandGroups = attributes.FirstOrDefault(x => x is ExpandGroupsAttribute) != null;
|
||||||
|
|
||||||
@@ -210,17 +210,24 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
private struct VisibleIfCache
|
private struct VisibleIfCache
|
||||||
{
|
{
|
||||||
public ScriptMemberInfo Target;
|
public ScriptMemberInfo Target;
|
||||||
public ScriptMemberInfo Source;
|
public ScriptMemberInfo[] Sources;
|
||||||
public PropertiesListElement PropertiesList;
|
public PropertiesListElement PropertiesList;
|
||||||
public GroupElement Group;
|
public GroupElement Group;
|
||||||
public bool Invert;
|
public bool[] InversionList;
|
||||||
public int LabelIndex;
|
public int LabelIndex;
|
||||||
|
|
||||||
public bool GetValue(object instance)
|
public bool GetValue(object instance)
|
||||||
{
|
{
|
||||||
var value = (bool)Source.GetValue(instance);
|
bool value = true;
|
||||||
if (Invert)
|
|
||||||
value = !value;
|
for (int i = 0; i < Sources.Length; i++)
|
||||||
|
{
|
||||||
|
bool currentValue = (bool)Sources[i].GetValue(instance);
|
||||||
|
if (InversionList[i])
|
||||||
|
currentValue = !currentValue;
|
||||||
|
|
||||||
|
value = value && currentValue;
|
||||||
|
}
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -298,40 +305,48 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
return items;
|
return items;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ScriptMemberInfo GetVisibleIfSource(ScriptType type, VisibleIfAttribute visibleIf)
|
private static ScriptMemberInfo[] GetVisibleIfSources(ScriptType type, VisibleIfAttribute[] visibleIfs)
|
||||||
{
|
{
|
||||||
var property = type.GetProperty(visibleIf.MemberName, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static);
|
ScriptMemberInfo[] members = Array.Empty<ScriptMemberInfo>();
|
||||||
if (property != ScriptMemberInfo.Null)
|
|
||||||
|
for (int i = 0; i < visibleIfs.Length; i++)
|
||||||
{
|
{
|
||||||
if (!property.HasGet)
|
var property = type.GetProperty(visibleIfs[i].MemberName, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static);
|
||||||
|
if (property != ScriptMemberInfo.Null)
|
||||||
{
|
{
|
||||||
Debug.LogError("Invalid VisibleIf rule. Property has missing getter " + visibleIf.MemberName);
|
if (!property.HasGet)
|
||||||
return ScriptMemberInfo.Null;
|
{
|
||||||
|
Debug.LogError("Invalid VisibleIf rule. Property has missing getter " + visibleIfs[i].MemberName);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (property.ValueType.Type != typeof(bool))
|
||||||
|
{
|
||||||
|
Debug.LogError("Invalid VisibleIf rule. Property has to return bool type " + visibleIfs[i].MemberName);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
members = members.Append(property).ToArray();
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (property.ValueType.Type != typeof(bool))
|
var field = type.GetField(visibleIfs[i].MemberName, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static);
|
||||||
|
if (field != ScriptMemberInfo.Null)
|
||||||
{
|
{
|
||||||
Debug.LogError("Invalid VisibleIf rule. Property has to return bool type " + visibleIf.MemberName);
|
if (field.ValueType.Type != typeof(bool))
|
||||||
return ScriptMemberInfo.Null;
|
{
|
||||||
|
Debug.LogError("Invalid VisibleIf rule. Field has to be bool type " + visibleIfs[i].MemberName);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
members = members.Append(field).ToArray();
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
return property;
|
Debug.LogError("Invalid VisibleIf rule. Cannot find member " + visibleIfs[i].MemberName);
|
||||||
}
|
}
|
||||||
|
|
||||||
var field = type.GetField(visibleIf.MemberName, BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static);
|
return members;
|
||||||
if (field != ScriptMemberInfo.Null)
|
|
||||||
{
|
|
||||||
if (field.ValueType.Type != typeof(bool))
|
|
||||||
{
|
|
||||||
Debug.LogError("Invalid VisibleIf rule. Field has to be bool type " + visibleIf.MemberName);
|
|
||||||
return ScriptMemberInfo.Null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return field;
|
|
||||||
}
|
|
||||||
|
|
||||||
Debug.LogError("Invalid VisibleIf rule. Cannot find member " + visibleIf.MemberName);
|
|
||||||
return ScriptMemberInfo.Null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void GroupPanelCheckIfCanRevert(LayoutElementsContainer layout, ref bool canRevertReference, ref bool canRevertDefault)
|
private static void GroupPanelCheckIfCanRevert(LayoutElementsContainer layout, ref bool canRevertReference, ref bool canRevertDefault)
|
||||||
@@ -575,7 +590,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
protected virtual void SpawnProperty(LayoutElementsContainer itemLayout, ValueContainer itemValues, ItemInfo item)
|
protected virtual void SpawnProperty(LayoutElementsContainer itemLayout, ValueContainer itemValues, ItemInfo item)
|
||||||
{
|
{
|
||||||
int labelIndex = 0;
|
int labelIndex = 0;
|
||||||
if ((item.IsReadOnly || item.VisibleIf != null) &&
|
if ((item.IsReadOnly || item.VisibleIfs.Length > 0) &&
|
||||||
itemLayout.Children.Count > 0 &&
|
itemLayout.Children.Count > 0 &&
|
||||||
itemLayout.Children[itemLayout.Children.Count - 1] is PropertiesListElement propertiesListElement)
|
itemLayout.Children[itemLayout.Children.Count - 1] is PropertiesListElement propertiesListElement)
|
||||||
{
|
{
|
||||||
@@ -616,7 +631,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (item.VisibleIf != null && itemLayout.Children.Count > 0)
|
if (item.VisibleIfs.Length > 0 && itemLayout.Children.Count > 0)
|
||||||
{
|
{
|
||||||
PropertiesListElement list = null;
|
PropertiesListElement list = null;
|
||||||
GroupElement group = null;
|
GroupElement group = null;
|
||||||
@@ -628,8 +643,8 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
// Get source member used to check rule
|
// Get source member used to check rule
|
||||||
var sourceMember = GetVisibleIfSource(item.Info.DeclaringType, item.VisibleIf);
|
var sourceMembers = GetVisibleIfSources(item.Info.DeclaringType, item.VisibleIfs);
|
||||||
if (sourceMember == ScriptType.Null)
|
if (sourceMembers.Length == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// Resize cache
|
// Resize cache
|
||||||
@@ -645,11 +660,11 @@ namespace FlaxEditor.CustomEditors.Editors
|
|||||||
_visibleIfCaches[count] = new VisibleIfCache
|
_visibleIfCaches[count] = new VisibleIfCache
|
||||||
{
|
{
|
||||||
Target = item.Info,
|
Target = item.Info,
|
||||||
Source = sourceMember,
|
Sources = sourceMembers,
|
||||||
PropertiesList = list,
|
PropertiesList = list,
|
||||||
Group = group,
|
Group = group,
|
||||||
LabelIndex = labelIndex,
|
LabelIndex = labelIndex,
|
||||||
Invert = item.VisibleIf.Invert,
|
InversionList = item.VisibleIfs.Select((x, i) => x.Invert).ToArray(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,11 +5,11 @@ using System;
|
|||||||
namespace FlaxEngine
|
namespace FlaxEngine
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Shows property/field in the editor only if the specified member has a given value. Can be used to hide properties based on other properties (also private properties). The given member has to be bool type.
|
/// Shows property/field in the editor only if the specified member has a given value. Can be used to hide properties based on other properties (also private properties). The given member has to be bool type. Multiple VisibleIf attributes can be added for additional conditions to be met.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <seealso cref="System.Attribute" />
|
/// <seealso cref="System.Attribute" />
|
||||||
[Serializable]
|
[Serializable]
|
||||||
[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property)]
|
[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, AllowMultiple = true)]
|
||||||
public sealed class VisibleIfAttribute : Attribute
|
public sealed class VisibleIfAttribute : Attribute
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -260,10 +260,10 @@ public:
|
|||||||
API_FIELD(Attributes="EditorOrder(400), EditorDisplay(\"Materials\"), VisibleIf(nameof(ShowGeometry))")
|
API_FIELD(Attributes="EditorOrder(400), EditorDisplay(\"Materials\"), VisibleIf(nameof(ShowGeometry))")
|
||||||
bool ImportMaterials = true;
|
bool ImportMaterials = true;
|
||||||
// If checked, the importer will create the model's materials as instances of a base material.
|
// If checked, the importer will create the model's materials as instances of a base material.
|
||||||
API_FIELD(Attributes = "EditorOrder(401), EditorDisplay(\"Materials\"), VisibleIf(nameof(ImportMaterials))")
|
API_FIELD(Attributes = "EditorOrder(401), EditorDisplay(\"Materials\"), VisibleIf(nameof(ImportMaterials)), VisibleIf(nameof(ShowGeometry))")
|
||||||
bool ImportMaterialsAsInstances = false;
|
bool ImportMaterialsAsInstances = false;
|
||||||
// The material used as the base material that will be instanced as the imported model's material.
|
// The material used as the base material that will be instanced as the imported model's material.
|
||||||
API_FIELD(Attributes = "EditorOrder(402), EditorDisplay(\"Materials\"), VisibleIf(nameof(ImportMaterialsAsInstances))")
|
API_FIELD(Attributes = "EditorOrder(402), EditorDisplay(\"Materials\"), VisibleIf(nameof(ImportMaterialsAsInstances)), VisibleIf(nameof(ShowGeometry))")
|
||||||
AssetReference<MaterialBase> InstanceToImportAs;
|
AssetReference<MaterialBase> InstanceToImportAs;
|
||||||
// If checked, the importer will import texture files used by the model and any embedded texture resources.
|
// If checked, the importer will import texture files used by the model and any embedded texture resources.
|
||||||
API_FIELD(Attributes="EditorOrder(410), EditorDisplay(\"Materials\"), VisibleIf(nameof(ShowGeometry))")
|
API_FIELD(Attributes="EditorOrder(410), EditorDisplay(\"Materials\"), VisibleIf(nameof(ShowGeometry))")
|
||||||
|
|||||||
Reference in New Issue
Block a user