Added script inspector tooltips support via Tooltip attribute #95
|
@ -67,6 +67,11 @@ namespace SHADE
|
|||
ImGui::Separator();
|
||||
}
|
||||
|
||||
bool SHEditorUI::IsItemHovered()
|
||||
{
|
||||
return ImGui::IsItemHovered();
|
||||
}
|
||||
|
||||
bool SHEditorUI::BeginMenu(const std::string& label)
|
||||
{
|
||||
return ImGui::BeginMenu(label.data());
|
||||
|
@ -82,6 +87,16 @@ namespace SHADE
|
|||
ImGui::EndMenu();
|
||||
}
|
||||
|
||||
void SHEditorUI::BeginTooltip()
|
||||
{
|
||||
ImGui::BeginTooltip();
|
||||
}
|
||||
|
||||
void SHEditorUI::EndTooltip()
|
||||
{
|
||||
ImGui::EndTooltip();
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------------------------------------*/
|
||||
/* ImGui Wrapper Functions - Pop Ups */
|
||||
/*-----------------------------------------------------------------------------------*/
|
||||
|
@ -135,24 +150,30 @@ namespace SHADE
|
|||
return ImGui::Selectable(std::format("{} {}", icon, label).data());
|
||||
}
|
||||
|
||||
bool SHEditorUI::InputCheckbox(const std::string& label, bool& value)
|
||||
bool SHEditorUI::InputCheckbox(const std::string& label, bool& value, bool* isHovered)
|
||||
{
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
return ImGui::Checkbox("#", &value);
|
||||
}
|
||||
bool SHEditorUI::InputInt(const std::string& label, int& value)
|
||||
bool SHEditorUI::InputInt(const std::string& label, int& value, bool* isHovered)
|
||||
{
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
return ImGui::InputInt("#", &value,
|
||||
1, 10,
|
||||
ImGuiInputTextFlags_EnterReturnsTrue);
|
||||
}
|
||||
bool SHEditorUI::InputUnsignedInt(const std::string& label, unsigned int& value)
|
||||
bool SHEditorUI::InputUnsignedInt(const std::string& label, unsigned int& value, bool* isHovered)
|
||||
{
|
||||
int signedVal = static_cast<int>(value);
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
const bool CHANGED = InputInt("#", signedVal);
|
||||
if (CHANGED)
|
||||
|
@ -162,35 +183,43 @@ namespace SHADE
|
|||
}
|
||||
return CHANGED;
|
||||
}
|
||||
bool SHEditorUI::InputFloat(const std::string& label, float& value)
|
||||
bool SHEditorUI::InputFloat(const std::string& label, float& value, bool* isHovered)
|
||||
{
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
return ImGui::InputFloat("#", &value,
|
||||
0.1f, 1.0f, "%.3f",
|
||||
ImGuiInputTextFlags_EnterReturnsTrue);
|
||||
}
|
||||
bool SHEditorUI::InputDouble(const std::string& label, double& value)
|
||||
bool SHEditorUI::InputDouble(const std::string& label, double& value, bool* isHovered)
|
||||
{
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
return ImGui::InputDouble("#", &value,
|
||||
0.1, 1.0, "%.3f",
|
||||
ImGuiInputTextFlags_EnterReturnsTrue);
|
||||
}
|
||||
bool SHEditorUI::InputAngle(const std::string& label, double& value)
|
||||
bool SHEditorUI::InputAngle(const std::string& label, double& value, bool* isHovered)
|
||||
{
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
return ImGui::InputDouble("#", &value,
|
||||
1.0, 45.0, "%.3f",
|
||||
ImGuiInputTextFlags_EnterReturnsTrue);
|
||||
}
|
||||
|
||||
bool SHEditorUI::InputSlider(const std::string& label, double min, double max, double& value)
|
||||
bool SHEditorUI::InputSlider(const std::string& label, double min, double max, double& value, bool* isHovered)
|
||||
{
|
||||
float val = static_cast<float>(value);
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
const bool CHANGED = ImGui::SliderFloat("#", &val,
|
||||
static_cast<float>(min), static_cast<float>(max), "%.3f",
|
||||
|
@ -204,22 +233,24 @@ namespace SHADE
|
|||
return CHANGED;
|
||||
}
|
||||
|
||||
bool SHEditorUI::InputVec2(const std::string& label, SHVec2& value)
|
||||
bool SHEditorUI::InputVec2(const std::string& label, SHVec2& value, bool* isHovered)
|
||||
{
|
||||
static const std::vector<std::string> COMPONENT_LABELS = { "X", "Y" };
|
||||
return SHEditorWidgets::DragN<float, 2>(label, COMPONENT_LABELS, { &value.x, &value.y });
|
||||
return SHEditorWidgets::DragN<float, 2>(label, COMPONENT_LABELS, { &value.x, &value.y }, 0.1f, "%.3f", float{}, float{}, 0, isHovered);
|
||||
}
|
||||
bool SHEditorUI::InputVec3(const std::string& label, SHVec3& value, float speed)
|
||||
bool SHEditorUI::InputVec3(const std::string& label, SHVec3& value, bool* isHovered, float speed)
|
||||
{
|
||||
static const std::vector<std::string> COMPONENT_LABELS = { "X", "Y", "Z"};
|
||||
return SHEditorWidgets::DragN<float, 3>(label, COMPONENT_LABELS, { &value.x, &value.y, &value.z }, speed, "%.3f");
|
||||
return SHEditorWidgets::DragN<float, 3>(label, COMPONENT_LABELS, { &value.x, &value.y, &value.z }, speed, "%.3f", float{}, float{}, 0, isHovered);
|
||||
}
|
||||
|
||||
bool SHEditorUI::InputTextField(const std::string& label, std::string& value)
|
||||
bool SHEditorUI::InputTextField(const std::string& label, std::string& value, bool* isHovered)
|
||||
{
|
||||
std::array<char, TEXT_FIELD_MAX_LENGTH> buffer = { '\0' };
|
||||
strcpy_s(buffer.data(), TEXT_FIELD_MAX_LENGTH, value.c_str());
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
const bool CHANGED = ImGui::InputText("#", &buffer[0], TEXT_FIELD_MAX_LENGTH);
|
||||
if (CHANGED)
|
||||
|
@ -229,13 +260,15 @@ namespace SHADE
|
|||
return CHANGED;
|
||||
}
|
||||
|
||||
bool SHEditorUI::InputEnumCombo(const std::string& label, int& v, const std::vector<std::string>& enumNames)
|
||||
bool SHEditorUI::InputEnumCombo(const std::string& label, int& v, const std::vector<std::string>& enumNames, bool* isHovered)
|
||||
{
|
||||
// Clamp input value
|
||||
const std::string& INITIAL_NAME = v >= static_cast<int>(enumNames.size()) ? "Unknown" : enumNames[v];
|
||||
bool b = false;
|
||||
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
if (ImGui::BeginCombo("#", INITIAL_NAME.c_str(), ImGuiComboFlags_None))
|
||||
{
|
||||
|
|
|
@ -90,12 +90,19 @@ namespace SHADE
|
|||
static void SameLine();
|
||||
static void Separator();
|
||||
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* ImGui Wrapper Functions - Queries */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
static bool IsItemHovered();
|
||||
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* ImGui Wrapper Functions - Menu */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
static bool BeginMenu(const std::string& label);
|
||||
static bool BeginMenu(const std::string& label, const char* icon);
|
||||
static void EndMenu();
|
||||
static void BeginTooltip();
|
||||
static void EndTooltip();
|
||||
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* ImGui Wrapper Functions - Pop Ups */
|
||||
|
@ -165,8 +172,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputCheckbox(const std::string& label, bool& value);
|
||||
static bool InputCheckbox(const std::string& label, bool& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a integer field widget for integer input.
|
||||
/// <br/>
|
||||
|
@ -174,8 +182,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputInt(const std::string& label, int& value);
|
||||
static bool InputInt(const std::string& label, int& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a integer field widget for unsigned integer input.
|
||||
/// <br/>
|
||||
|
@ -186,8 +195,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputUnsignedInt(const std::string& label, unsigned int& value);
|
||||
static bool InputUnsignedInt(const std::string& label, unsigned int& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a decimal field widget for single precision float input.
|
||||
/// <br/>
|
||||
|
@ -195,8 +205,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputFloat(const std::string& label, float& value);
|
||||
static bool InputFloat(const std::string& label, float& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a decimal field widget for double precision float input.
|
||||
/// <br/>
|
||||
|
@ -204,8 +215,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputDouble(const std::string& label, double& value);
|
||||
static bool InputDouble(const std::string& label, double& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a decimal field widget for double input with increments of higher
|
||||
/// steps meant for angle variables.
|
||||
|
@ -214,8 +226,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputAngle(const std::string& label, double& value);
|
||||
static bool InputAngle(const std::string& label, double& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a double slider field widget for double input.
|
||||
/// <br/>
|
||||
|
@ -225,8 +238,9 @@ namespace SHADE
|
|||
/// <param name="min">Minimum value of the slider.</param>
|
||||
/// <param name="max">Maximum value of the slider.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputSlider(const std::string& label, double min, double max, double& value);
|
||||
static bool InputSlider(const std::string& label, double min, double max, double& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a 2x double field widget for Vector2 input.
|
||||
/// <br/>
|
||||
|
@ -234,8 +248,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputVec2(const std::string& label, SHVec2& value);
|
||||
static bool InputVec2(const std::string& label, SHVec2& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a 3x double field widget for Vector3 input.
|
||||
/// <br/>
|
||||
|
@ -243,8 +258,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputVec3(const std::string& label, SHVec3& value, float speed = 0.1f);
|
||||
static bool InputVec3(const std::string& label, SHVec3& value, bool* isHovered = nullptr, float speed = 0.1f);
|
||||
/// <summary>
|
||||
/// Creates a text field widget for string input.
|
||||
/// <br/>
|
||||
|
@ -252,8 +268,9 @@ namespace SHADE
|
|||
/// </summary>
|
||||
/// <param name="label">Label used to identify this widget.</param>
|
||||
/// <param name="value">Reference to the variable to store the result.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>True if the value was changed.</returns>
|
||||
static bool InputTextField(const std::string& label, std::string& value);
|
||||
static bool InputTextField(const std::string& label, std::string& value, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a combo box for enumeration input.
|
||||
/// </summary>
|
||||
|
@ -264,17 +281,19 @@ namespace SHADE
|
|||
/// <param name="toStrFn">
|
||||
/// Conversion function from the type of enum to C-style string.
|
||||
/// </param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>Whether the value was modified.</returns>
|
||||
template<typename Enum>
|
||||
static bool InputEnumCombo(const std::string& label, Enum& v, int maxVal, std::function<const char*(Enum)> toStrFn);
|
||||
static bool InputEnumCombo(const std::string& label, Enum& v, int maxVal, std::function<const char*(Enum)> toStrFn, bool* isHovered = nullptr);
|
||||
/// <summary>
|
||||
/// Creates a combo box for enumeration input using a specified list of names.
|
||||
/// </summary>
|
||||
/// <param name="label">The name of the input.</param>
|
||||
/// <param name="v">The reference to the value to modify.</param>
|
||||
/// <param name="enumNames">Vector of names for each enumeration value.</param>
|
||||
/// <param name="isHovered>If set, stores the hover state of this widget.</param>
|
||||
/// <returns>Whether the value was modified.</returns>
|
||||
static bool InputEnumCombo(const std::string& label, int& v, const std::vector<std::string>& enumNames);
|
||||
static bool InputEnumCombo(const std::string& label, int& v, const std::vector<std::string>& enumNames, bool* isHovered = nullptr);
|
||||
|
||||
|
||||
private:
|
||||
|
|
|
@ -20,7 +20,7 @@ namespace SHADE
|
|||
/* ImGui Wrapper Functions - Widgets */
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
template<typename Enum>
|
||||
inline bool SHEditorUI::InputEnumCombo(const std::string& label, Enum& v, int maxVal, std::function<const char* (Enum)> toStrFn)
|
||||
inline bool SHEditorUI::InputEnumCombo(const std::string& label, Enum& v, int maxVal, std::function<const char* (Enum)> toStrFn, bool* isHovered)
|
||||
{
|
||||
std::vector<Enum> values;
|
||||
for (int i = 0; i <= maxVal; ++i)
|
||||
|
@ -28,6 +28,11 @@ namespace SHADE
|
|||
values.emplace_back(static_cast<Enum>(i));
|
||||
}
|
||||
bool b = false;
|
||||
|
||||
ImGui::Text(label.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::SameLine();
|
||||
if (ImGui::BeginCombo(label.c_str(), toStrFn(v), ImGuiComboFlags_None))
|
||||
{
|
||||
for (int i = 0; i <= maxVal; ++i)
|
||||
|
|
|
@ -160,7 +160,7 @@ namespace SHADE
|
|||
template <typename T, std::size_t N>
|
||||
static bool DragN(const std::string& fieldLabel, std::vector<std::string>const& componentLabels,
|
||||
std::vector<T*> values, float speed = 0.1f, const char* displayFormat = "", T valueMin = T(), T valueMax = T(),
|
||||
ImGuiSliderFlags flags = 0)
|
||||
ImGuiSliderFlags flags = 0, bool* isHovered = nullptr)
|
||||
{
|
||||
const ImGuiWindow* const window = ImGui::GetCurrentWindow();
|
||||
if (window->SkipItems)
|
||||
|
@ -174,6 +174,8 @@ namespace SHADE
|
|||
ImGui::BeginColumns("DragVecCol", 2, ImGuiOldColumnFlags_NoBorder | ImGuiOldColumnFlags_NoResize);
|
||||
ImGui::SetColumnWidth(-1, 80.0f);
|
||||
ImGui::Text(fieldLabel.c_str());
|
||||
if (isHovered)
|
||||
*isHovered = ImGui::IsItemHovered();
|
||||
ImGui::NextColumn();
|
||||
for (std::size_t i = 0; i < N; ++i)
|
||||
{
|
||||
|
|
|
@ -115,7 +115,7 @@ namespace SHADE
|
|||
/*---------------------------------------------------------------------------------*/
|
||||
/* Script Serialisation Functions */
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
std::string SHScriptEngine::SerialiseScripts(const SHEntity& entity) const
|
||||
std::string SHScriptEngine::SerialiseScripts(EntityID entity) const
|
||||
{
|
||||
// Create buffer needed to store serialised script data
|
||||
constexpr int BUFFER_SIZE = 10240;
|
||||
|
@ -124,7 +124,7 @@ namespace SHADE
|
|||
|
||||
// Attempt to serialise the script
|
||||
std::string result;
|
||||
if (csScriptsSerialise(entity.GetEID(), buffer.get(), BUFFER_SIZE))
|
||||
if (csScriptsSerialise(entity, buffer.get(), BUFFER_SIZE))
|
||||
{
|
||||
result = std::string(buffer.get());
|
||||
}
|
||||
|
@ -140,9 +140,9 @@ namespace SHADE
|
|||
/*-----------------------------------------------------------------------------------*/
|
||||
/* Script Serialisation Functions */
|
||||
/*-----------------------------------------------------------------------------------*/
|
||||
void SHScriptEngine::DeserialiseScript(const SHEntity& entity, const std::string& yaml) const
|
||||
void SHScriptEngine::DeserialiseScript(EntityID entity, const std::string& yaml) const
|
||||
{
|
||||
csScriptDeserialise(entity.GetEID(), yaml.c_str());
|
||||
csScriptDeserialise(entity, yaml.c_str());
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------------------------------------*/
|
||||
|
|
|
@ -148,7 +148,7 @@ namespace SHADE
|
|||
/// <returns>
|
||||
/// String that represents the set of scripts attached to the specified Entity.
|
||||
/// </returns>
|
||||
std::string SerialiseScripts(const SHEntity& entity) const;
|
||||
std::string SerialiseScripts(EntityID entity) const;
|
||||
/// <summary>
|
||||
/// Loads the specified JSON string and creates a Script for the specified Entity
|
||||
/// based on the specified JSON string.
|
||||
|
@ -157,7 +157,7 @@ namespace SHADE
|
|||
/// <param name="yaml">
|
||||
/// The YAML string that represents the Script to load into the Entity.
|
||||
/// </param>
|
||||
void DeserialiseScript(const SHEntity& entity, const std::string& yaml) const;
|
||||
void DeserialiseScript(EntityID entity, const std::string& yaml) const;
|
||||
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* Script Editor Functions */
|
||||
|
|
|
@ -29,6 +29,7 @@ of DigiPen Institute of Technology is prohibited.
|
|||
#include "Editor/IconsMaterialDesign.h"
|
||||
#include "Editor/Command/SHCommandManager.h"
|
||||
#include "Editor/Command/SHCommand.hpp"
|
||||
#include "TooltipAttribute.hxx"
|
||||
|
||||
// Using Directives
|
||||
using namespace System;
|
||||
|
@ -48,17 +49,17 @@ using namespace System::Collections::Generic;
|
|||
/// <param name="MANAGED_TYPE">The managed type of the object to edit.</param>
|
||||
/// <param name="NATIVE_TYPE">The native type of the object to edit.</param>
|
||||
/// <param name="FUNC">The SHEditorUI:: function to use for editing.</param>
|
||||
#define RENDER_FIELD(MANAGED_TYPE, NATIVE_TYPE, FUNC) \
|
||||
(field->FieldType == MANAGED_TYPE::typeid) \
|
||||
{ \
|
||||
NATIVE_TYPE val = safe_cast<NATIVE_TYPE>(field->GetValue(object)); \
|
||||
NATIVE_TYPE oldVal = val; \
|
||||
if (SHEditorUI::FUNC(Convert::ToNative(field->Name), val)) \
|
||||
{ \
|
||||
field->SetValue(object, val); \
|
||||
registerUndoAction(object, field, val, oldVal); \
|
||||
} \
|
||||
} \
|
||||
#define RENDER_FIELD(MANAGED_TYPE, NATIVE_TYPE, FUNC) \
|
||||
(field->FieldType == MANAGED_TYPE::typeid) \
|
||||
{ \
|
||||
NATIVE_TYPE val = safe_cast<NATIVE_TYPE>(field->GetValue(object)); \
|
||||
NATIVE_TYPE oldVal = val; \
|
||||
if (SHEditorUI::FUNC(Convert::ToNative(field->Name), val, &isHovered))\
|
||||
{ \
|
||||
field->SetValue(object, val); \
|
||||
registerUndoAction(object, field, val, oldVal); \
|
||||
} \
|
||||
} \
|
||||
/// <summary>
|
||||
/// Macro expansion that is used in renderFieldInInspector() to check the type of a field
|
||||
/// named "field" against the specified type and if it matches, retrieves the value of
|
||||
|
@ -76,7 +77,7 @@ using namespace System::Collections::Generic;
|
|||
{ \
|
||||
NATIVE_TYPE val = Convert::ToNative(safe_cast<MANAGED_TYPE>(field->GetValue(object))); \
|
||||
NATIVE_TYPE oldVal = val; \
|
||||
if (SHEditorUI::FUNC(Convert::ToNative(field->Name), val)) \
|
||||
if (SHEditorUI::FUNC(Convert::ToNative(field->Name), val, &isHovered)) \
|
||||
{ \
|
||||
field->SetValue(object, Convert::ToCLI(val)); \
|
||||
registerUndoAction(object, field, Convert::ToCLI(val), Convert::ToCLI(oldVal)); \
|
||||
|
@ -196,6 +197,8 @@ namespace SHADE
|
|||
}
|
||||
void Editor::renderFieldInInspector(Reflection::FieldInfo^ field, Object^ object)
|
||||
{
|
||||
bool isHovered = false;
|
||||
|
||||
if RENDER_FIELD (Int16, int, InputInt)
|
||||
else if RENDER_FIELD (Int32, int, InputInt)
|
||||
else if RENDER_FIELD (Int64, int, InputInt)
|
||||
|
@ -244,6 +247,15 @@ namespace SHADE
|
|||
registerUndoAction(object, field, Convert::ToCLI(val), Convert::ToCLI(oldVal));
|
||||
}
|
||||
}
|
||||
|
||||
// Check if the field has a specific attribute
|
||||
TooltipAttribute^ toolTip = hasAttribute<TooltipAttribute^>(field);
|
||||
if (toolTip && isHovered)
|
||||
{
|
||||
SHEditorUI::BeginTooltip();
|
||||
SHEditorUI::Text(Convert::ToNative(toolTip->Description));
|
||||
SHEditorUI::EndTooltip();
|
||||
}
|
||||
}
|
||||
|
||||
void Editor::renderScriptContextMenu(Entity entity, Script^ script)
|
||||
|
@ -274,4 +286,24 @@ namespace SHADE
|
|||
SHCommandManager::RegisterCommand(std::reinterpret_pointer_cast<SHBaseCommand>(std::make_shared<SHCLICommand>()));
|
||||
}
|
||||
|
||||
generic<typename Attribute>
|
||||
Attribute Editor::hasAttribute(System::Reflection::FieldInfo^ field)
|
||||
{
|
||||
array<System::Object^>^ attributes = field->GetCustomAttributes(true);
|
||||
for each (System::Object^ attrib in attributes)
|
||||
{
|
||||
try
|
||||
{
|
||||
Attribute attribute = safe_cast<Attribute>(attrib);
|
||||
if (attribute != nullptr)
|
||||
return attribute;
|
||||
}
|
||||
catch (System::InvalidCastException^)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
}
|
||||
// Failed to find
|
||||
return Attribute{};
|
||||
}
|
||||
}
|
||||
|
|
|
@ -23,7 +23,7 @@ namespace SHADE
|
|||
/// <summary>
|
||||
/// Static class for Editor-related functions
|
||||
/// </summary>
|
||||
public ref class Editor abstract sealed
|
||||
private ref class Editor abstract sealed
|
||||
{
|
||||
public:
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
|
@ -48,7 +48,13 @@ namespace SHADE
|
|||
/*-----------------------------------------------------------------------------*/
|
||||
/* UndoRedoStack Functions */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/// <summary>
|
||||
/// Undoes the last script inspector change if there is any.
|
||||
/// </summary>
|
||||
static void Undo();
|
||||
/// <summary>
|
||||
/// Redoes the last script inspector change if there is any.
|
||||
/// </summary>
|
||||
static void Redo();
|
||||
|
||||
private:
|
||||
|
@ -86,5 +92,7 @@ namespace SHADE
|
|||
/// <param name="script">The Script to render the inspector for.</param>
|
||||
static void renderScriptContextMenu(Entity entity, Script^ script);
|
||||
static void registerUndoAction(System::Object^ object, System::Reflection::FieldInfo^ field, System::Object^ newData, System::Object^ oldData);
|
||||
generic<typename Attribute> where Attribute : System::Attribute
|
||||
static Attribute hasAttribute(System::Reflection::FieldInfo^ field);
|
||||
};
|
||||
}
|
||||
|
|
|
@ -1,27 +1,34 @@
|
|||
/************************************************************************************//*!
|
||||
\file SerializeFieldAttribute.cxx
|
||||
\file TooltipAttribute.cxx
|
||||
\author Tng Kah Wei, kahwei.tng, 390009620
|
||||
\par email: kahwei.tng\@digipen.edu
|
||||
\date Nov 5, 2021
|
||||
\brief Contains the definition of the functions of the managed SerializeField
|
||||
Attribute class.
|
||||
\date Oct 18, 2022
|
||||
\brief Contains the definition of the functions of the managed Tooltip Attribute
|
||||
class.
|
||||
|
||||
Note: This file is written in C++17/CLI.
|
||||
|
||||
Copyright (C) 2021 DigiPen Institute of Technology.
|
||||
Reproduction or disclosure of this file or its contents without the prior written consent
|
||||
|
||||
Copyright (C) 2022 DigiPen Institute of Technology.
|
||||
Reproduction or disclosure of this file or its contents without the prior written consent
|
||||
of DigiPen Institute of Technology is prohibited.
|
||||
*//*************************************************************************************/
|
||||
// Precompiled Headers
|
||||
#include "SHpch.h"
|
||||
// Primary Header
|
||||
#include "SerializeFieldAttribute.hxx"
|
||||
#include "TooltipAttribute.hxx"
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
/* Properties */
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
System::String^ TooltipAttribute::Description::get()
|
||||
{
|
||||
return desc;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
/* Constructors */
|
||||
/*---------------------------------------------------------------------------------*/
|
||||
SerializeField::SerializeField()
|
||||
TooltipAttribute::TooltipAttribute(System::String^ description)
|
||||
: desc { description }
|
||||
{}
|
||||
}
|
|
@ -0,0 +1,53 @@
|
|||
/************************************************************************************//*!
|
||||
\file TooltipAttribute.hxx
|
||||
\author Tng Kah Wei, kahwei.tng, 390009620
|
||||
\par email: kahwei.tng\@digipen.edu
|
||||
\date Oct 18, 2022
|
||||
\brief Contains the definition of the managed Tooltip Attribute class with
|
||||
the declaration of functions for working with it.
|
||||
|
||||
Note: This file is written in C++17/CLI.
|
||||
|
||||
Copyright (C) 2022 DigiPen Institute of Technology.
|
||||
Reproduction or disclosure of this file or its contents without the prior written consent
|
||||
of DigiPen Institute of Technology is prohibited.
|
||||
*//*************************************************************************************/
|
||||
#pragma once
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
/// <summary>
|
||||
/// Simple attribute to mark that a field in a Script should be serialised.
|
||||
/// </summary>
|
||||
[System::AttributeUsage(System::AttributeTargets::Field)]
|
||||
public ref class TooltipAttribute : public System::Attribute
|
||||
{
|
||||
public:
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* Properties */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/// <summary>
|
||||
/// Description that is to be shown in the Tooltip.
|
||||
/// </summary>
|
||||
property System::String^ Description
|
||||
{
|
||||
System::String^ get();
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* Constructors */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/// <summary>
|
||||
/// Constructor for a Tooltip attribute that fills in the description.
|
||||
/// </summary>
|
||||
/// <param name="description">Text to be shown when a field is hovered.</param>
|
||||
TooltipAttribute(System::String^ description);
|
||||
|
||||
private:
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* Data Members */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
System::String^ desc;
|
||||
};
|
||||
}
|
||||
|
|
@ -21,15 +21,6 @@ namespace SHADE
|
|||
/// </summary>
|
||||
[System::AttributeUsage(System::AttributeTargets::Field)]
|
||||
public ref class SerializeField : public System::Attribute
|
||||
{
|
||||
public:
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/* Constructors */
|
||||
/*-----------------------------------------------------------------------------*/
|
||||
/// <summary>
|
||||
/// Default Constructor
|
||||
/// </summary>
|
||||
SerializeField();
|
||||
};
|
||||
{};
|
||||
}
|
||||
|
||||
|
|
|
@ -3,8 +3,12 @@ using System;
|
|||
|
||||
public class RaccoonShowcase : Script
|
||||
{
|
||||
public double RotateSpeed = 1.0;
|
||||
public Vector3 ScaleSpeed = new Vector3(1.0, 1.0, 0.0);
|
||||
[SerializeField]
|
||||
[Tooltip("Speed of the rotation in radians per second.")]
|
||||
private double RotateSpeed = 1.0;
|
||||
[SerializeField]
|
||||
[Tooltip("Speed of the scaling in radians per second around each axis.")]
|
||||
private Vector3 ScaleSpeed = new Vector3(1.0, 1.0, 0.0);
|
||||
private Transform Transform;
|
||||
private double rotation = 0.0;
|
||||
private Vector3 scale = Vector3.Zero;
|
||||
|
|
|
@ -3,7 +3,9 @@ using System;
|
|||
|
||||
public class RaccoonSpin : Script
|
||||
{
|
||||
public double RotateSpeed = 1.0;
|
||||
[SerializeField]
|
||||
[Tooltip("Speed of the rotation in radians per second.")]
|
||||
private double RotateSpeed = 1.0;
|
||||
private double rotation = 0.0;
|
||||
private Transform Transform;
|
||||
public RaccoonSpin(GameObject gameObj) : base(gameObj) { }
|
||||
|
|
Loading…
Reference in New Issue