Show Buttons in entity editor

- ScriptEngine: Added HasCustomAttribute- extension method
- ScriptEngine: Added Application class
This commit is contained in:
Simon Lübeß
2023-12-12 13:38:29 +01:00
parent 13cb043cf4
commit e69e1b5526
12 changed files with 253 additions and 42 deletions
+39 -11
View File
@@ -24,11 +24,16 @@ internal class EntityEditor
public static bool ShowFieldInEditor(FieldInfo fieldInfo)
{
if (fieldInfo.IsPublic)
{
// Public fields are visible by default (No HideInEditorAttribute)
if (fieldInfo.HasCustomAttribute<HideInEditorAttribute>())
return false;
return true;
var showInEditorAttribute = fieldInfo.GetCustomAttribute<ShowInEditorAttribute>();
if (showInEditorAttribute != null)
}
// Private, protected and internal fields are hidden by default (No ShowInEditorAttribute)
if (fieldInfo.HasCustomAttribute<ShowInEditorAttribute>())
return true;
return false;
@@ -357,13 +362,9 @@ internal class EntityEditor
public static void ShowEditor(Type type, object reference)
{
T GetValue<T>(FieldInfo fieldInfo)
{
return default;
}
int i = 0;
// Iterate all fields
foreach (FieldInfo field in type.GetFields(BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public))
{
i++;
@@ -371,8 +372,6 @@ internal class EntityEditor
if (ShowFieldInEditor(field))
{
//Log.Info(field.Name);
object value = field.GetValue(reference);
IEnumerable<Attribute> attributes = field.GetCustomAttributes();
@@ -388,6 +387,35 @@ internal class EntityEditor
ImGui.PopID();
}
// Iterate all methods
foreach (MethodInfo method in type.GetMethods(BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public))
{
var showButton = method.GetCustomAttribute<ShowButtonAttribute>();
if (showButton == null)
continue;
if (Application.IsInEditMode && !showButton.Visibility.HasFlag(ButtonVisibility.InEditMode))
continue;
if (Application.IsInPlayMode && !showButton.Visibility.HasFlag(ButtonVisibility.InPlayMode))
continue;
i++;
ImGui.PushID(i);
if (method.GetParameters().Length > 0)
{
Log.Error($"Method {method.Name} cannot be executed from editor, because it expects arguments.");
}
else if (ImGui.Button(showButton.ButtonText))
{
method.Invoke(reference, null);
}
ImGui.PopID();
}
}
struct ListPayload
@@ -0,0 +1,11 @@
using System;
namespace GlitchyEngine.Editor;
/// <summary>
/// Specifies, that the field should not be visible in the editor.
/// </summary>
[AttributeUsage(AttributeTargets.Field)]
public sealed class HideInEditorAttribute : Attribute
{
}
+42
View File
@@ -0,0 +1,42 @@
using System;
namespace GlitchyEngine.Editor;
public enum ButtonVisibility
{
/// <summary>
/// The button will be visible in edit mode.
/// </summary>
InEditMode = 1,
/// <summary>
/// The button will be visible in play mode.
/// </summary>
InPlayMode = 2,
/// <summary>
/// The button will always be visible.
/// </summary>
Always = InEditMode | InPlayMode
}
/// <summary>
/// Specifies that a button will be shown in the editor that, when clicked, executes the method this attribute is attached to.
/// </summary>
[AttributeUsage(AttributeTargets.Method)]
public sealed class ShowButtonAttribute : Attribute
{
/// <summary>
/// The text on the button.
/// </summary>
public string ButtonText { get; private set; }
/// <summary>
/// Determines whether the button is visible in edit and/or play mode.
/// </summary>
public ButtonVisibility Visibility { get; set; } = ButtonVisibility.Always;
public ShowButtonAttribute(string buttonText)
{
ButtonText = buttonText;
}
}
+9 -4
View File
@@ -7,11 +7,16 @@ namespace GlitchyEngine.Editor;
* - this attribute also means that the Field is being serialized
* - Editor-Namespace wont be available for distribution builds of the game
*/
/// <summary>
/// Specifies that the field should be visible in the editor, regardless of it's code visibility (private, protected, etc...)
/// If this attribute is specified, the field will also be serialized.
/// </summary>
[AttributeUsage(AttributeTargets.Field)]
public sealed class ShowInEditorAttribute : Attribute
{
/// <summary>
/// The label with which the field will be shown in the editor.
/// If not specified, the fields name will be used.
/// </summary>
public string DisplayName { get; set; } = null;
public ShowInEditorAttribute()
{}
}
}