From e44b7859680675ed242b83424085ab32513c9681 Mon Sep 17 00:00:00 2001 From: chreden <4263940+chreden@users.noreply.github.com> Date: Sun, 24 Sep 2023 14:44:36 +0100 Subject: [PATCH] Add ImGui input controls for plugins (#1182) Add bindings for ImGui input functions. This will at least let plugins do some basic input instead of checkboxes and buttons. Rearrange files for the imgui project to `inc` and `src` - will probably do this for the rest of the projects at some point too. #1129 --- doc/lua/imgui.md | 194 ++++++++++++++- trview.app/Lua/Lua.cpp | 2 +- trview.lua.imgui/{ => inc}/trview.lua.imgui.h | 0 trview.lua.imgui/{ => src}/framework.h | 0 trview.lua.imgui/{ => src}/pch.cpp | 0 trview.lua.imgui/{ => src}/pch.h | 7 + trview.lua.imgui/src/tables.cpp | 133 ++++++++++ trview.lua.imgui/src/tables.h | 31 +++ .../{ => src}/trview.lua.imgui.cpp | 75 +----- .../src/trview.lua.imgui.input.cpp | 231 ++++++++++++++++++ trview.lua.imgui/src/trview.lua.imgui.input.h | 11 + trview.lua.imgui/trview.lua.imgui.vcxproj | 36 +-- .../trview.lua.imgui.vcxproj.filters | 46 ++-- 13 files changed, 654 insertions(+), 112 deletions(-) rename trview.lua.imgui/{ => inc}/trview.lua.imgui.h (100%) rename trview.lua.imgui/{ => src}/framework.h (100%) rename trview.lua.imgui/{ => src}/pch.cpp (100%) rename trview.lua.imgui/{ => src}/pch.h (73%) create mode 100644 trview.lua.imgui/src/tables.cpp create mode 100644 trview.lua.imgui/src/tables.h rename trview.lua.imgui/{ => src}/trview.lua.imgui.cpp (88%) create mode 100644 trview.lua.imgui/src/trview.lua.imgui.input.cpp create mode 100644 trview.lua.imgui/src/trview.lua.imgui.input.h diff --git a/doc/lua/imgui.md b/doc/lua/imgui.md index 336328356..13b01f8e1 100644 --- a/doc/lua/imgui.md +++ b/doc/lua/imgui.md @@ -13,10 +13,20 @@ The ImGui library allows plugins to render UI elements. | Button |`boolean result`|`{ string label, ImGuiButtonFlags flags }`|| | Checkbox | `boolean result, boolean checked` | `{ string label, boolean checked }` | Make a checkbox. The checked parameter indicates whether the checkbox is checked and the new state is in the second return value. | | End ||| End rendering a window | -| EndChild |||| +| EndChild ||| End a child window | | EndCombo |||| | EndTable |||| -| SameLine |||| +| InputDouble | `boolean result, number value` | `{ string label, number value, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputFloat | `boolean result, number value` | `{ string label, number value, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputFloat2 | `boolean result, number value1, number value2` | `{ string label, number value1, number value2, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputFloat3 | `boolean result, number value1, number value2, number value3` | `{ string label, number value1, number value2, number value3, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputFloat4 | `boolean result, number value1, number value2, number value3, number value4` | `{ string label, number value1, number value2, number value3, number value4, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputInt | `boolean result, number value` | `{ string label, number value, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputInt2 | `boolean result, number value1, number value2` | `{ string label, number value1, number value2 [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputInt3 | `boolean result, number value1, number value2, number value3` | `{ string label, number value1, number value2, number value3, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputInt4 | `boolean result, number value1, number value2, number value3, number value4` | `{ string label, number value1, number value2, number value3, number value4, [optional] number step, [optional] number step_fast, [optional] string format, [optional] InputTextFlags flags }` || +| InputText | `boolean result, string value` | `{ string label, string value, [optional] InputTextFlags flags }` || +| SameLine ||| Put the next element on the same line. | | Selectable |`boolean result`|`{ string label, boolean selected, ImGuiSelectableFlags flags }`|| | TableHeadersRow |||| | TableNextColumn |`boolean result`||| @@ -27,14 +37,182 @@ The ImGui library allows plugins to render UI elements. # Enumerations -## ImGuiWindowFlags +## WindowFlags -## ImGuiComboFlags +| Name | +| ---- | +| None | +| NoTitleBar | +| NoResize | +| NoMove | +| NoScrollbar | +| NoScrollWithMouse | +| NoCollapse | +| AlwaysAutoResize | +| NoBackground | +| NoSavedSettings | +| NoMouseInputs | +| MenuBar | +| HorizontalScrollbar | +| NoFocusOnAppearing | +| NoBringToFrontOnFocus | +| AlwaysVerticalScrollbar | +| AlwaysHorizontalScrollbar | +| AlwaysUseWindowPadding | +| NoNavInputs | +| NoNavFocus | +| UnsavedDocument | +| NoDocking | -## ImGuiSelectableFlags -## ImGuiTableColumnFlags +## ComboFlags -## ImGuiTableFlags +| Name | +| ---- | +| None | +| PopupAlignLeft | +| HeightSmall | +| HeightRegular | +| HeightLarge | +| HeightLargest | +| NoArrowButton | +| NoPreview | -## ImGuiButtonFlags +## SelectableFlags + +| Name | +| ---- | +| None | +| DontClosePopups | +| SpanAllColumns | +| AllowDoubleClick | +| Disabled | +| AllowItemOverlap | +| NoHoldingActiveID | +| SelectOnNav | +| SelectOnClick | +| SelectOnRelease | +| SpanAvailWidth | +| DrawHoveredWhenHeld | +| SetNavIdOnHover | +| NoPadWithHalfSpacing | + +## TableColumnFlags + +| Name | +| ---- | +| None | +| Disabled | +| DefaultHide | +| DefaultSort | +| WidthStretch | +| WidthFixed | +| NoResize | +| NoReorder | +| NoHide | +| NoClip | +| NoSort | +| NoSortAscending | +| NoSortDescending | +| NoHeaderLabel | +| NoHeaderWidth | +| PreferSortAscending | +| PreferSortDescending | +| IndentEnable | +| IndentDisable | +| IsEnabled | +| IsVisible | +| IsSorted | +| IsHovered | + +## TableFlags + +| Name | Notes | +| ---- | ----- | +| None || +| Resizable || +| Reorderable || +| Hideable || +| Sortable | Not yet implemented | +| NoSavedSettings || +| ContextMenuInBody || +| RowBg || +| BordersInnerH || +| BordersOuterH || +| BordersInnerV || +| BordersOuterV || +| BordersH || +| BordersV || +| BordersInner || +| BordersOuter || +| Borders || +| NoBordersInBody || +| NoBordersInBodyUntilResize || +| SizingFixedFit || +| SizingFixedSame || +| SizingStretchProp || +| SizingStretchSame || +| NoHostExtendX || +| NoHostExtendY || +| NoKeepColumnsVisible || +| PreciseWidths || +| NoClip || +| PadOuterX || +| NoPadOuterX || +| NoPadInnerX || +| ScrollX || +| ScrollY || +| SortMulti | Not yet implemented | +| SortTristate | Not yet implemented | + +## InputTextFlags + +| Name | Notes | +| ---- | ----- | +| None || +| CharsDecimal || +| CharsHexadecimal || +| CharsUppercase || +| CharsNoBlank || +| AutoSelectAll || +| EnterReturnsTrue || +| CallbackCompletion | Not yet implemented | +| CallbackHistory | Not yet implemented | +| CallbackAlways | Not yet implemented | +| CallbackCharFilter | Not yet implemented | +| AllowTabInput || +| CtrlEnterForNewLine || +| NoHorizontalScroll || +| AlwaysOverwrite || +| ReadOnly || +| Password || +| NoUndoRedo || +| CharsScientific || +| CallbackResize | Not yet implemented | +| CallbackEdit | Not yet implemented | + +## ButtonFlags + +| Name | +| ---- | +| None | +| MouseButtonLeft | +| MouseButtonRight | +| MouseButtonMiddle | +| PressedOnClick | +| PressedOnClickRelease | +| PressedOnClickReleaseAnywhere | +| PressedOnRelease | +| PressedOnDoubleClick | +| PressedOnDragDropHold | +| Repeat | +| FlattenChildren | +| AllowItemOverlap | +| DontClosePopups | +| AlignTextBaseLine | +| NoKeyModifiers | +| NoHoldingActiveId | +| NoNavFocus | +| NoHoveredOnFocus | +| PressedOnMask_ | +| PressedOnDefault_ | diff --git a/trview.app/Lua/Lua.cpp b/trview.app/Lua/Lua.cpp index fafb75630..3c6505c4d 100644 --- a/trview.app/Lua/Lua.cpp +++ b/trview.app/Lua/Lua.cpp @@ -2,7 +2,7 @@ #include #include "trview/trview.h" #include -#include +#include #include "Route/Lua_Waypoint.h" namespace trview diff --git a/trview.lua.imgui/trview.lua.imgui.h b/trview.lua.imgui/inc/trview.lua.imgui.h similarity index 100% rename from trview.lua.imgui/trview.lua.imgui.h rename to trview.lua.imgui/inc/trview.lua.imgui.h diff --git a/trview.lua.imgui/framework.h b/trview.lua.imgui/src/framework.h similarity index 100% rename from trview.lua.imgui/framework.h rename to trview.lua.imgui/src/framework.h diff --git a/trview.lua.imgui/pch.cpp b/trview.lua.imgui/src/pch.cpp similarity index 100% rename from trview.lua.imgui/pch.cpp rename to trview.lua.imgui/src/pch.cpp diff --git a/trview.lua.imgui/pch.h b/trview.lua.imgui/src/pch.h similarity index 73% rename from trview.lua.imgui/pch.h rename to trview.lua.imgui/src/pch.h index 885d5d62e..3b4688df2 100644 --- a/trview.lua.imgui/pch.h +++ b/trview.lua.imgui/src/pch.h @@ -10,4 +10,11 @@ // add headers that you want to pre-compile here #include "framework.h" +#include +#include + +#include +#include +#include + #endif //PCH_H diff --git a/trview.lua.imgui/src/tables.cpp b/trview.lua.imgui/src/tables.cpp new file mode 100644 index 000000000..778dc30bb --- /dev/null +++ b/trview.lua.imgui/src/tables.cpp @@ -0,0 +1,133 @@ +#include "pch.h" +#include "tables.h" + +namespace trview +{ + namespace lua + { + double get_double(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + luaL_checktype(L, -1, LUA_TNUMBER); + double value = lua_tonumber(L, -1); + lua_pop(L, 1); + return value; + } + + float get_float(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + luaL_checktype(L, -1, LUA_TNUMBER); + float value = lua_tonumber(L, -1); + lua_pop(L, 1); + return value; + } + + int get_integer(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + luaL_checktype(L, -1, LUA_TNUMBER); + int value = lua_tointeger(L, -1); + lua_pop(L, 1); + return value; + } + + std::optional get_optional_double(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + if (lua_isnil(L, -1)) + { + lua_pop(L, 1); + return std::nullopt; + } + luaL_checktype(L, -1, LUA_TNUMBER); + double value = lua_tonumber(L, -1); + lua_pop(L, 1); + return value; + } + + std::optional get_optional_float(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + if (lua_isnil(L, -1)) + { + lua_pop(L, 1); + return std::nullopt; + } + luaL_checktype(L, -1, LUA_TNUMBER); + float value = lua_tonumber(L, -1); + lua_pop(L, 1); + return value; + } + + std::optional get_optional_integer(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + if (lua_isnil(L, -1)) + { + lua_pop(L, 1); + return std::nullopt; + } + luaL_checktype(L, -1, LUA_TNUMBER); + int value = lua_tointeger(L, -1); + lua_pop(L, 1); + return value; + } + + std::optional get_optional_string(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + if (lua_isnil(L, -1)) + { + lua_pop(L, 1); + return std::nullopt; + } + luaL_checktype(L, -1, LUA_TSTRING); + std::string value = lua_tostring(L, -1); + lua_pop(L, 1); + return value; + } + + std::string get_string(lua_State* L, int index, const std::string& name) + { + luaL_checktype(L, index, LUA_TTABLE); + lua_getfield(L, index, name.c_str()); + luaL_checktype(L, -1, LUA_TSTRING); + std::string value = lua_tostring(L, -1); + lua_pop(L, 1); + return value; + } + + void set_enum(lua_State* L, const std::string& name, int index, const std::vector& values) + { + if (index < 0) + { + index += lua_gettop(L) + 1; + } + + lua_newtable(L); + for (const auto& v : values) + { + set_integer(L, -1, v.name.c_str(), v.value); + } + lua_setfield(L, index, name.c_str()); + } + + void set_integer(lua_State* L, int index, const std::string& name, int value) + { + if (index < 0) + { + index += lua_gettop(L) + 1; + } + lua_pushinteger(L, value); + lua_setfield(L, index, name.c_str()); + } + } +} diff --git a/trview.lua.imgui/src/tables.h b/trview.lua.imgui/src/tables.h new file mode 100644 index 000000000..a885f2b2d --- /dev/null +++ b/trview.lua.imgui/src/tables.h @@ -0,0 +1,31 @@ +#pragma once + +#include +#include +#include + +struct lua_State; + +namespace trview +{ + namespace lua + { + double get_double(lua_State* L, int index, const std::string& name); + float get_float(lua_State* L, int index, const std::string& name); + int get_integer(lua_State* L, int index, const std::string& name); + std::optional get_optional_double(lua_State* L, int index, const std::string& name); + std::optional get_optional_float(lua_State* L, int index, const std::string& name); + std::optional get_optional_integer(lua_State* L, int index, const std::string& name); + std::optional get_optional_string(lua_State* L, int index, const std::string& name); + std::string get_string(lua_State* L, int index, const std::string& name); + + struct EnumValue + { + std::string name; + int value; + }; + + void set_enum(lua_State* L, const std::string& name, int index, const std::vector& values); + void set_integer(lua_State* L, int index, const std::string& name, int value); + } +} diff --git a/trview.lua.imgui/trview.lua.imgui.cpp b/trview.lua.imgui/src/trview.lua.imgui.cpp similarity index 88% rename from trview.lua.imgui/trview.lua.imgui.cpp rename to trview.lua.imgui/src/trview.lua.imgui.cpp index 88763a846..e97476a75 100644 --- a/trview.lua.imgui/trview.lua.imgui.cpp +++ b/trview.lua.imgui/src/trview.lua.imgui.cpp @@ -3,14 +3,15 @@ #include "pch.h" #include "framework.h" -#include "trview.lua.imgui.h" +#include "../inc/trview.lua.imgui.h" -#include -#include #include #include #include +#include "trview.lua.imgui.input.h" +#include "tables.h" + namespace trview { namespace lua @@ -49,72 +50,6 @@ namespace trview return value; } - std::optional get_optional_integer(lua_State* L, int index, const std::string& name) - { - luaL_checktype(L, index, LUA_TTABLE); - lua_getfield(L, index, name.c_str()); - if (lua_isnil(L, -1)) - { - lua_pop(L, 1); - return std::nullopt; - } - luaL_checktype(L, -1, LUA_TNUMBER); - int value = lua_tointeger(L, -1); - lua_pop(L, 1); - return value; - } - - int get_integer(lua_State* L, int index, const std::string& name) - { - luaL_checktype(L, index, LUA_TTABLE); - lua_getfield(L, index, name.c_str()); - luaL_checktype(L, -1, LUA_TNUMBER); - int value = lua_tointeger(L, -1); - lua_pop(L, 1); - return value; - } - - std::string get_string(lua_State* L, int index, const std::string& name) - { - luaL_checktype(L, index, LUA_TTABLE); - lua_getfield(L, index, name.c_str()); - luaL_checktype(L, -1, LUA_TSTRING); - std::string value = lua_tostring(L, -1); - lua_pop(L, 1); - return value; - } - - void set_integer(lua_State* L, int index, const std::string& name, int value) - { - if (index < 0) - { - index += lua_gettop(L) + 1; - } - lua_pushinteger(L, value); - lua_setfield(L, index, name.c_str()); - } - - struct EnumValue - { - std::string name; - int value; - }; - - void set_enum(lua_State* L, const std::string& name, int index, const std::vector& values) - { - if (index < 0) - { - index += lua_gettop(L) + 1; - } - - lua_newtable(L); - for (const auto& v : values) - { - set_integer(L, -1, v.name.c_str(), v.value); - } - lua_setfield(L, index, name.c_str()); - } - int begin(lua_State* L) { const auto name = get_string(L, 1, "name"); @@ -460,6 +395,8 @@ namespace trview lua_pushcfunction(L, same_line); lua_setfield(L, -2, "SameLine"); + register_input(L); + lua_setglobal(L, "ImGui"); } } diff --git a/trview.lua.imgui/src/trview.lua.imgui.input.cpp b/trview.lua.imgui/src/trview.lua.imgui.input.cpp new file mode 100644 index 000000000..89caba62e --- /dev/null +++ b/trview.lua.imgui/src/trview.lua.imgui.input.cpp @@ -0,0 +1,231 @@ +#include "pch.h" +#include "trview.lua.imgui.input.h" +#include "tables.h" + +namespace trview +{ + namespace lua + { + namespace + { + int input_double(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + double out = get_double(L, 1, "value"); + const auto step = get_optional_double(L, 1, "step"); + const auto step_fast = get_optional_double(L, 1, "step_fast"); + const auto format = get_optional_string(L, 1, "format"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputDouble(label.c_str(), &out, step.value_or(0.0), step_fast.value_or(0.0), format.value_or("%.6f").c_str(), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushnumber(L, result); + lua_pushnumber(L, out); + return 2; + } + + int input_float(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + float out = get_float(L, 1, "value"); + const auto step = get_optional_float(L, 1, "step"); + const auto step_fast = get_optional_float(L, 1, "step_fast"); + const auto format = get_optional_string(L, 1, "format"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputFloat(label.c_str(), &out, step.value_or(0.0f), step_fast.value_or(0.0f), format.value_or("%.3f").c_str(), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushnumber(L, out); + return 2; + } + + int input_float2(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + float values[2] + { + get_float(L, 1, "value1"), + get_float(L, 1, "value2") + }; + const auto format = get_optional_string(L, 1, "format"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputFloat2(label.c_str(), values, format.value_or("%.3f").c_str(), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushnumber(L, values[0]); + lua_pushnumber(L, values[1]); + return 3; + } + + int input_float3(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + float values[3] + { + get_float(L, 1, "value1"), + get_float(L, 1, "value2"), + get_float(L, 1, "value3") + }; + const auto format = get_optional_string(L, 1, "format"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputFloat3(label.c_str(), values, format.value_or("%.3f").c_str(), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushnumber(L, values[0]); + lua_pushnumber(L, values[1]); + lua_pushnumber(L, values[2]); + return 4; + } + + int input_float4(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + float values[4] + { + get_float(L, 1, "value1"), + get_float(L, 1, "value2"), + get_float(L, 1, "value3"), + get_float(L, 1, "value4") + }; + const auto format = get_optional_string(L, 1, "format"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputFloat4(label.c_str(), values, format.value_or("%.3f").c_str(), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushnumber(L, values[0]); + lua_pushnumber(L, values[1]); + lua_pushnumber(L, values[2]); + lua_pushnumber(L, values[3]); + return 5; + } + + int input_int(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + int value = get_integer(L, 1, "value"); + const auto step = get_optional_integer(L, 1, "step"); + const auto step_fast = get_optional_integer(L, 1, "step_fast"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputInt(label.c_str(), &value, step.value_or(1), step_fast.value_or(100), flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushinteger(L, value); + return 2; + } + + int input_int2(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + int values[2] + { + get_integer(L, 1, "value1"), + get_integer(L, 1, "value2") + }; + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputInt2(label.c_str(), values, flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushinteger(L, values[0]); + lua_pushinteger(L, values[1]); + return 3; + } + + int input_int3(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + int values[3] + { + get_integer(L, 1, "value1"), + get_integer(L, 1, "value2"), + get_integer(L, 1, "value3") + }; + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputInt3(label.c_str(), values, flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushinteger(L, values[0]); + lua_pushinteger(L, values[1]); + lua_pushinteger(L, values[2]); + return 4; + } + + int input_int4(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + int values[4] + { + get_integer(L, 1, "value1"), + get_integer(L, 1, "value2"), + get_integer(L, 1, "value3"), + get_integer(L, 1, "value4") + }; + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputInt4(label.c_str(), values, flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushinteger(L, values[0]); + lua_pushinteger(L, values[1]); + lua_pushinteger(L, values[2]); + lua_pushinteger(L, values[3]); + return 5; + } + + int input_scalar(lua_State* L) + { + return luaL_error(L, "input_scalar not yet implemented"); + } + + int input_scalarN(lua_State* L) + { + return luaL_error(L, "input_scalarN not yet implemented"); + } + + int input_text(lua_State* L) + { + const auto label = get_string(L, 1, "label"); + std::string out = get_string(L, 1, "value"); + const auto flags = get_optional_integer(L, 1, "flags"); + bool result = ImGui::InputText(label.c_str(), &out, flags.value_or(ImGuiInputTextFlags_None)); + lua_pushboolean(L, result); + lua_pushstring(L, out.c_str()); + return 2; + } + } + + void register_input(lua_State* L) + { + // Callbacks are not yet implemented. + set_enum(L, "InputTextFlags", -1, + { + { "None", ImGuiInputTextFlags_None }, + { "CharsDecimal", ImGuiInputTextFlags_CharsDecimal }, + { "CharsHexadecimal", ImGuiInputTextFlags_CharsHexadecimal }, + { "CharsUppercase", ImGuiInputTextFlags_CharsUppercase }, + { "CharsNoBlank", ImGuiInputTextFlags_CharsNoBlank }, + { "AutoSelectAll", ImGuiInputTextFlags_AutoSelectAll }, + { "EnterReturnsTrue", ImGuiInputTextFlags_EnterReturnsTrue }, + { "CallbackCompletion", ImGuiInputTextFlags_CallbackCompletion }, + { "CallbackHistory", ImGuiInputTextFlags_CallbackHistory }, + { "CallbackAlways", ImGuiInputTextFlags_CallbackAlways }, + { "CallbackCharFilter", ImGuiInputTextFlags_CallbackCharFilter }, + { "AllowTabInput", ImGuiInputTextFlags_AllowTabInput }, + { "CtrlEnterForNewLine", ImGuiInputTextFlags_CtrlEnterForNewLine }, + { "NoHorizontalScroll", ImGuiInputTextFlags_NoHorizontalScroll }, + { "AlwaysOverwrite", ImGuiInputTextFlags_AlwaysOverwrite }, + { "ReadOnly", ImGuiInputTextFlags_ReadOnly }, + { "Password", ImGuiInputTextFlags_Password }, + { "NoUndoRedo", ImGuiInputTextFlags_NoUndoRedo }, + { "CharsScientific", ImGuiInputTextFlags_CharsScientific }, + { "CallbackResize", ImGuiInputTextFlags_CallbackResize }, + { "CallbackEdit", ImGuiInputTextFlags_CallbackEdit } + }); + + constexpr luaL_Reg funcs[] = { + { "InputDouble", input_double }, + { "InputFloat", input_float }, + { "InputFloat2", input_float2 }, + { "InputFloat3", input_float3 }, + { "InputFloat4", input_float4 }, + { "InputInt", input_int }, + { "InputInt2", input_int2 }, + { "InputInt3", input_int3 }, + { "InputInt4", input_int4 }, + // { "InputScalar", input_scalar }, + // { "InputScalarN", input_scalarN }, + { "InputText", input_text }, + { nullptr, nullptr } + }; + luaL_setfuncs(L, funcs, 0); + } + } +} diff --git a/trview.lua.imgui/src/trview.lua.imgui.input.h b/trview.lua.imgui/src/trview.lua.imgui.input.h new file mode 100644 index 000000000..7c95eea94 --- /dev/null +++ b/trview.lua.imgui/src/trview.lua.imgui.input.h @@ -0,0 +1,11 @@ +#pragma once + +struct lua_State; + +namespace trview +{ + namespace lua + { + void register_input(lua_State* L); + } +} \ No newline at end of file diff --git a/trview.lua.imgui/trview.lua.imgui.vcxproj b/trview.lua.imgui/trview.lua.imgui.vcxproj index d2b9be855..a4572625d 100644 --- a/trview.lua.imgui/trview.lua.imgui.vcxproj +++ b/trview.lua.imgui/trview.lua.imgui.vcxproj @@ -18,6 +18,28 @@ x64 + + + + + + + + + + Create + Create + Create + Create + pch.h + pch.h + pch.h + pch.h + + + + + 16.0 Win32Proj @@ -154,20 +176,6 @@ true - - - - - - - - Create - Create - Create - Create - - - diff --git a/trview.lua.imgui/trview.lua.imgui.vcxproj.filters b/trview.lua.imgui/trview.lua.imgui.vcxproj.filters index b8084fe58..53df7601a 100644 --- a/trview.lua.imgui/trview.lua.imgui.vcxproj.filters +++ b/trview.lua.imgui/trview.lua.imgui.vcxproj.filters @@ -1,36 +1,42 @@  - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx + + {34b2a761-9128-4221-845c-6fb9cca75b1e} - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms + + {ea9d3c34-8bae-4bde-89e0-2b115958af28} - - Header Files + + inc + + + src + + + src - - Header Files + + src - - Header Files + + src - - Source Files + + src + + + src + + + src - - Source Files + + src \ No newline at end of file