1 /*
2 * Copyright (c) 2012-2016, Bruno Levy
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * * Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above copyright notice,
11 * this list of conditions and the following disclaimer in the documentation
12 * and/or other materials provided with the distribution.
13 * * Neither the name of the ALICE Project-Team nor the names of its
14 * contributors may be used to endorse or promote products derived from this
15 * software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
21 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 * POSSIBILITY OF SUCH DAMAGE.
28 *
29 * If you modify this software, you should include a notice giving the
30 * name of the person performing the modification, the date of modification,
31 * and the reason for such modification.
32 *
33 * Contact: Bruno Levy
34 *
35 * Bruno.Levy@inria.fr
36 * http://www.loria.fr/~levy
37 *
38 * ALICE Project
39 * LORIA, INRIA Lorraine,
40 * Campus Scientifique, BP 239
41 * 54506 VANDOEUVRE LES NANCY CEDEX
42 * FRANCE
43 *
44 */
45
46 #include <geogram_gfx/lua/lua_imgui.h>
47 #include <geogram_gfx/ImGui_ext/imgui_ext.h>
48 #include <geogram_gfx/ImGui_ext/icon_font.h>
49 #include <geogram/lua/lua_wrap.h>
50 #include <geogram/basic/string.h>
51 #include <geogram/basic/logger.h>
52 #include <map>
53
54 extern void LoadImguiBindings();
55 extern lua_State* lState;
56
57 namespace {
58 using namespace GEO;
59
60
wrapper_TextInput(lua_State * L)61 int wrapper_TextInput(lua_State* L) {
62
63 if(
64 lua_gettop(L) != 2 &&
65 lua_gettop(L) != 3
66 ) {
67 return luaL_error(
68 L, "'imgui.TextInput()' invalid number of arguments"
69 );
70 }
71
72 if(!lua_isstring(L,1)) {
73 return luaL_error(
74 L, "'imgui.TextInput()' argument 1 should be a string"
75 );
76 }
77
78 if(!lua_isstring(L,2)) {
79 return luaL_error(
80 L, "'imgui.TextInput()' argument 2 should be a string"
81 );
82 }
83
84 ImGuiInputTextFlags flags = 0;
85
86 if(lua_gettop(L) == 3) {
87 if(!lua_isnumber(L,3)) {
88 return luaL_error(
89 L, "'imgui.TextInput()' argument 3 should be a number"
90 );
91 }
92 flags = ImGuiInputTextFlags(lua_tonumber(L,3));
93 }
94
95 const char* label = lua_tostring(L,1);
96 const char* str = lua_tostring(L,2);
97 static char buff[geo_imgui_string_length];
98 strcpy(buff,str);
99 bool result = ImGui::InputText(
100 label, buff, geo_imgui_string_length, flags
101 );
102 lua_pushboolean(L,result);
103 lua_pushstring(L,buff);
104
105
106 return 2;
107 }
108
109
wrapper_Combo(lua_State * L)110 int wrapper_Combo(lua_State* L) {
111 if(lua_gettop(L) != 3) {
112 return luaL_error(
113 L, "'imgui.Combo()' invalid number of arguments"
114 );
115 }
116
117 if(!lua_isstring(L,1)) {
118 return luaL_error(
119 L, "'imgui.Combo()' argument should be a string"
120 );
121 }
122
123 if(!lua_isstring(L,2)) {
124 return luaL_error(
125 L, "'imgui.Combo()' argument should be a string"
126 );
127 }
128
129 if(!lua_isstring(L,3)) {
130 return luaL_error(
131 L, "'imgui.Combo()' argument should be a string"
132 );
133 }
134
135 const char* label = lua_tostring(L,1);
136 const char* current_item = lua_tostring(L,2);
137 const char* items = lua_tostring(L,3);
138
139 char* lua_items = (char*)alloca(strlen(items)+2);
140 strcpy(lua_items,items);
141 {
142 size_t n = strlen(lua_items);
143 lua_items[n] = ';';
144 lua_items[n+1] = '\0';
145 }
146
147 int lua_current_item=0;
148
149 const char* prev_item = lua_items;
150 int nb_items = 0;
151
152 char* p = lua_items;
153 while(*p != '\0') {
154 if(*p == ';') {
155 *p = '\0';
156 if(!strcmp(prev_item, current_item)) {
157 lua_current_item = nb_items;
158 }
159 prev_item = p+1;
160 ++nb_items;
161 }
162 ++p;
163 }
164 *p = '\0'; // Double '\0' to indicate end of item list to lua.
165
166 bool result = ImGui::Combo(label, &lua_current_item, lua_items);
167
168 current_item = lua_items;
169 while(lua_current_item > 0) {
170 while(*current_item) {
171 ++current_item;
172 }
173 ++current_item;
174 --lua_current_item;
175 }
176
177 lua_pushboolean(L, result);
178 lua_pushstring(L, current_item);
179
180 return 2;
181 }
182
wrapper_ColorEdit3WithPalette(lua_State * L)183 int wrapper_ColorEdit3WithPalette(
184 lua_State* L
185 ) {
186 if(lua_gettop(L) != 4) {
187 return luaL_error(
188 L, "'imgui.ColorEdit3WithPalette()' invalid number of arguments"
189 );
190 }
191
192 if(!lua_isstring(L,1)) {
193 return luaL_error(
194 L, "'imgui.ColorEdit3WithPalette()' argument 1 should be a string"
195 );
196 }
197
198 if(!lua_isnumber(L,2)) {
199 return luaL_error(
200 L, "'imgui.ColorEdit3WithPalette()' argument 2 should be a number"
201 );
202 }
203
204 if(!lua_isnumber(L,3)) {
205 return luaL_error(
206 L, "'imgui.ColorEdit3WithPalette()' argument 3 should be a number"
207 );
208 }
209
210 if(!lua_isnumber(L,4)) {
211 return luaL_error(
212 L, "'imgui.ColorEdit3WithPalette()' argument 4 should be a number"
213 );
214 }
215
216 const char* label = lua_tostring(L,1);
217
218 float rgb[3];
219 rgb[0] = float(lua_tonumber(L,2));
220 rgb[1] = float(lua_tonumber(L,3));
221 rgb[2] = float(lua_tonumber(L,4));
222
223 bool sel = ImGui::ColorEdit3WithPalette(
224 label, rgb
225 );
226
227 lua_pushboolean(L,sel);
228 lua_pushnumber(L,double(rgb[0]));
229 lua_pushnumber(L,double(rgb[1]));
230 lua_pushnumber(L,double(rgb[2]));
231
232 return 4;
233 }
234
wrapper_ColorEdit4WithPalette(lua_State * L)235 int wrapper_ColorEdit4WithPalette(
236 lua_State* L
237 ) {
238 if(lua_gettop(L) != 5) {
239 return luaL_error(
240 L, "'imgui.ColorEdit3WithPalette()' invalid number of arguments"
241 );
242 }
243
244 if(!lua_isstring(L,1)) {
245 return luaL_error(
246 L, "'imgui.ColorEdit3WithPalette()' argument 1 should be a string"
247 );
248 }
249
250 if(!lua_isnumber(L,2)) {
251 return luaL_error(
252 L, "'imgui.ColorEdit3WithPalette()' argument 2 should be a number"
253 );
254 }
255
256 if(!lua_isnumber(L,3)) {
257 return luaL_error(
258 L, "'imgui.ColorEdit3WithPalette()' argument 3 should be a number"
259 );
260 }
261
262 if(!lua_isnumber(L,4)) {
263 return luaL_error(
264 L, "'imgui.ColorEdit3WithPalette()' argument 4 should be a number"
265 );
266 }
267
268 if(!lua_isnumber(L,5)) {
269 return luaL_error(
270 L, "'imgui.ColorEdit3WithPalette()' argument 5 should be a number"
271 );
272 }
273
274 const char* label = lua_tostring(L,1);
275
276 float rgb[4];
277 rgb[0] = float(lua_tonumber(L,2));
278 rgb[1] = float(lua_tonumber(L,3));
279 rgb[2] = float(lua_tonumber(L,4));
280 rgb[3] = float(lua_tonumber(L,5));
281
282 bool sel = ImGui::ColorEdit4WithPalette(
283 label, rgb
284 );
285
286 lua_pushboolean(L,sel);
287 lua_pushnumber(L,double(rgb[0]));
288 lua_pushnumber(L,double(rgb[1]));
289 lua_pushnumber(L,double(rgb[2]));
290 lua_pushnumber(L,double(rgb[3]));
291
292 return 5;
293 }
294
295
wrapper_OpenFileDialog(lua_State * L)296 int wrapper_OpenFileDialog(
297 lua_State* L
298 ) {
299 if(lua_gettop(L) != 4) {
300 return luaL_error(
301 L, "'imgui.OpenFileDialog()' invalid number of arguments"
302 );
303 }
304
305 if(!lua_isstring(L,1)) {
306 return luaL_error(
307 L, "'imgui.OpenFileDialog()' argument 1 should be a string"
308 );
309 }
310
311 if(!lua_isstring(L,2)) {
312 return luaL_error(
313 L, "'imgui.OpenFileDialog()' argument 2 should be a string"
314 );
315 }
316
317 if(!lua_isstring(L,3)) {
318 return luaL_error(
319 L, "'imgui.OpenFileDialog()' argument 3 should be a string"
320 );
321 }
322
323 if(!lua_isnumber(L,4)) {
324 return luaL_error(
325 L, "'imgui.OpenFileDialog()' argument 4 should be a number"
326 );
327 }
328
329 const char* label = lua_tostring(L,1);
330 const char* extensions = lua_tostring(L,2);
331 const char* filename = lua_tostring(L,3);
332 ImGuiExtFileDialogFlags flags =
333 ImGuiExtFileDialogFlags(lua_tonumber(L,4));
334
335 ImGui::OpenFileDialog(label, extensions, filename, flags);
336
337 return 0;
338 }
339
wrapper_FileDialog(lua_State * L)340 int wrapper_FileDialog(
341 lua_State* L
342 ) {
343 if(lua_gettop(L) != 2) {
344 return luaL_error(
345 L, "'imgui.FileDialog()' invalid number of arguments"
346 );
347 }
348
349 if(!lua_isstring(L,1)) {
350 return luaL_error(
351 L, "'imgui.OpenFileDialog()' argument 1 should be a string"
352 );
353 }
354
355 if(!lua_isstring(L,2)) {
356 return luaL_error(
357 L, "'imgui.OpenFileDialog()' argument 2 should be a string"
358 );
359 }
360
361 const char* label = lua_tostring(L,1);
362 char filename[geo_imgui_string_length];
363
364 const char* filename_in = lua_tostring(L,2);
365 if(filename_in != nullptr) {
366 if(strlen(filename_in) > geo_imgui_string_length + 1) {
367 Logger::err("ImGui") << "Max file name length exceeded"
368 << std::endl;
369 return false;
370 }
371 strcpy(filename, filename_in);
372 } else {
373 filename[0] = '\0';
374 }
375
376 bool result =
377 ImGui::FileDialog(label, filename, geo_imgui_string_length);
378
379 lua_pushboolean(L,result);
380 lua_pushstring(L, result ? filename : filename_in);
381
382 return 2;
383 }
384
wrapper_SetNextWindowPos(lua_State * L)385 int wrapper_SetNextWindowPos(lua_State* L) {
386 if(
387 lua_gettop(L) != 2 &&
388 lua_gettop(L) != 3
389 ) {
390 return luaL_error(
391 L, "'imgui.SetNextWindowPos()' invalid number of arguments"
392 );
393 }
394
395 if(!lua_isnumber(L,1)) {
396 return luaL_error(
397 L, "'imgui.SetNextWindowPos()' argument 1 should be a number"
398 );
399 }
400
401 if(!lua_isnumber(L,2)) {
402 return luaL_error(
403 L, "'imgui.SetNextWindowPos()' argument 2 should be a number"
404 );
405 }
406
407 ImGuiCond cond = 0;
408 if(lua_gettop(L) == 3) {
409 if(!lua_isnumber(L,3)) {
410 return luaL_error(
411 L,
412 "'imgui.SetNextWindowPos()' argument 3 should be a number"
413 );
414 }
415 cond = ImGuiCond(lua_tonumber(L,3));
416 }
417
418
419 ImGui::SetNextWindowPos(
420 ImVec2(float(lua_tonumber(L,1)), float(lua_tonumber(L,2))),
421 cond
422 );
423
424 return 0;
425 }
426
wrapper_SetNextWindowSize(lua_State * L)427 int wrapper_SetNextWindowSize(lua_State* L) {
428 if(
429 lua_gettop(L) != 2 &&
430 lua_gettop(L) != 3
431 ) {
432 return luaL_error(
433 L, "'imgui.SetNextWindowSize()' invalid number of arguments"
434 );
435 }
436
437 if(!lua_isnumber(L,1)) {
438 return luaL_error(
439 L, "'imgui.SetNextWindowSize()' argument 1 should be a number"
440 );
441 }
442
443 if(!lua_isnumber(L,2)) {
444 return luaL_error(
445 L, "'imgui.SetNextWindowSize()' argument 2 should be a number"
446 );
447 }
448
449 ImGuiCond cond = 0;
450 if(lua_gettop(L) == 3) {
451 if(!lua_isnumber(L,3)) {
452 return luaL_error(
453 L,
454 "'imgui.SetNextWindowSize()' argument 3 should be a number"
455 );
456 }
457 cond = ImGuiCond(lua_tonumber(L,3));
458 }
459
460
461 ImGui::SetNextWindowSize(
462 ImVec2(float(lua_tonumber(L,1)), float(lua_tonumber(L,2))),
463 cond
464 );
465
466 return 0;
467 }
468
469
wrapper_IsItemHovered(lua_State * L)470 int wrapper_IsItemHovered(lua_State* L) {
471 if(lua_gettop(L) != 0) {
472 return luaL_error(
473 L, "'imgui.IsItemHovered()' invalid number of arguments"
474 );
475 }
476 lua_pushboolean(L,ImGui::IsItemHovered());
477 return 1;
478 }
479
wrapper_Text(lua_State * L)480 int wrapper_Text(lua_State* L) {
481 if(lua_gettop(L) < 1) {
482 return luaL_error(
483 L, "'imgui.Text()' invalid number of arguments"
484 );
485 }
486 const char* str = lua_tostring(L,1);
487 ImGui::Text("%s",str);
488 return 0;
489 }
490
wrapper_SetTooltip(lua_State * L)491 int wrapper_SetTooltip(lua_State* L) {
492 if(lua_gettop(L) != 1) {
493 return luaL_error(
494 L, "'imgui.SetTooltip()' invalid number of arguments"
495 );
496 }
497 const char* str = lua_tostring(L,1);
498 ImGui::SetTooltip("%s",str);
499 return 0;
500 }
501
wrapper_ShowStyleEditor(lua_State * L)502 int wrapper_ShowStyleEditor(lua_State* L) {
503 if(lua_gettop(L) != 0) {
504 return luaL_error(
505 L, "'imgui.ShowStyleEditor()' invalid number of arguments"
506 );
507 }
508 ImGui::ShowStyleEditor(nullptr);
509 return 0;
510 }
511
wrapper_PushFont(lua_State * L)512 int wrapper_PushFont(lua_State* L) {
513 if(lua_gettop(L) != 1) {
514 return luaL_error(
515 L, "'imgui.PushFont()' invalid number of arguments"
516 );
517 }
518 if(!lua_isinteger(L,1)) {
519 return luaL_error(
520 L, "'imgui.PushFont()' argument is not an integer"
521 );
522 }
523 int idx = int(lua_tointeger(L,1));
524 if(idx < 0 || idx >= ImGui::GetIO().Fonts->Fonts.size()) {
525 return luaL_error(
526 L, "'imgui.PushFont()' invalid font index"
527 );
528 }
529 ImGui::PushFont(ImGui::GetIO().Fonts->Fonts[idx]);
530 return 0;
531 }
532
wrapper_font_icon(lua_State * L)533 int wrapper_font_icon(lua_State* L) {
534 if(lua_gettop(L) != 1) {
535 return luaL_error(
536 L, "'imgui.font_icon()' invalid number of arguments"
537 );
538 }
539 if(!lua_isstring(L,1)) {
540 return luaL_error(
541 L, "'imgui.font_icon()' argument is not a string"
542 );
543 }
544 const char* K = lua_tostring(L,1);
545 wchar_t result[2];
546 result[0] = icon_wchar(K);
547 result[1] = '\0';
548 std::string result_str = String::wchar_to_UTF8(result);
549 lua_pushstring(L, result_str.c_str());
550 return 1;
551 }
552
wrapper_BeginTabBar(lua_State * L)553 int wrapper_BeginTabBar(lua_State* L) {
554 if(lua_gettop(L) != 1) {
555 return luaL_error(
556 L, "'imgui.BeginTabBar()' invalid number of arguments"
557 );
558 }
559 if(!lua_isstring(L,1)) {
560 return luaL_error(
561 L, "'imgui.BeinTabBar()' argument is not a string"
562 );
563 }
564 const char* K = lua_tostring(L,1);
565 ImGui::BeginTabBar(K);
566 return 0;
567 }
568
wrapper_BeginTabItem(lua_State * L)569 int wrapper_BeginTabItem(lua_State* L) {
570 if(lua_gettop(L) != 1) {
571 return luaL_error(
572 L, "'imgui.BeginTabItem()' invalid number of arguments"
573 );
574 }
575 if(!lua_isstring(L,1)) {
576 return luaL_error(
577 L, "'imgui.BeginTabItem()' argument is not a string"
578 );
579 }
580 const char* K = lua_tostring(L,1);
581 lua_pushboolean(L,ImGui::BeginTabItem(K));
582 return 1;
583 }
584
wrapper_SimpleButton(lua_State * L)585 int wrapper_SimpleButton(lua_State* L) {
586 if(lua_gettop(L) != 1) {
587 return luaL_error(
588 L, "'imgui.SimpleButton()' invalid number of arguments"
589 );
590 }
591 if(!lua_isstring(L,1)) {
592 return luaL_error(
593 L, "'imgui.SimpleButton()' argument is not a string"
594 );
595 }
596 const char* K = lua_tostring(L,1);
597 lua_pushboolean(L,ImGui::SimpleButton(K));
598 return 1;
599 }
600
wrapper_GetMousePos(lua_State * L)601 int wrapper_GetMousePos(lua_State* L) {
602 if(lua_gettop(L) != 0) {
603 return luaL_error(
604 L, "'imgui.GetMousePos()' invalid number of arguments"
605 );
606 }
607 lua_pushnumber(L,double(ImGui::GetIO().MousePos.x));
608 lua_pushnumber(L,double(ImGui::GetIO().MousePos.y));
609 return 2;
610 }
611
612 }
613
614 namespace GEO {
615
616 /**
617 * \brief Specialization of lua_push() for ImDrawList*
618 */
lua_push(lua_State * L,ImDrawList * x)619 template<> inline void lua_push(
620 lua_State* L, ImDrawList* x
621 ) {
622 lua_pushlightuserdata(L,(void*)x);
623 }
624
625 /**
626 * \brief lua_to specialization for ImDrawList*
627 */
628 template<> class lua_to<ImDrawList*> {
629 public:
lua_to(lua_State * L,int idx)630 lua_to(lua_State* L, int idx) {
631 x_ = (ImDrawList*)(lua_touserdata(L,idx));
632 }
can_convert(lua_State * L,int idx)633 static bool can_convert(lua_State* L, int idx) {
634 return lua_check_type(L, idx, my_lua_islightuserdata);
635 }
operator ImDrawList*() const636 operator ImDrawList*() const {
637 return x_;
638 }
639 private:
640 ImDrawList* x_;
641 };
642
643 }
644
645 // WIP: export all ImGuiDrawList functions to LUA
646
647 namespace ImGuiDrawAdapters {
648
649 // Needed by lua_bindwrapper because ImGui::GetBackgroundDrawList()
650 // takes an ImViewport (default = nullptr) as an argunemt.
GetBackgroundDrawList()651 static ImDrawList* GetBackgroundDrawList() {
652 return ImGui::GetBackgroundDrawList();
653 }
654
655 // Needed by lua_bindwrapper because ImGui::GetForegroundDrawList()
656 // takes an ImViewport (default = nullptr) as an argunemt.
GetForegroundDrawList()657 static ImDrawList* GetForegroundDrawList() {
658 return ImGui::GetForegroundDrawList();
659 }
660
PushClipRect(ImDrawList * list,float xmin,float ymin,float xmax,float ymax,bool intersect)661 static void PushClipRect(
662 ImDrawList* list,
663 float xmin, float ymin,
664 float xmax, float ymax,
665 bool intersect
666 ) {
667 list->PushClipRect(
668 ImVec2(xmin, ymin),
669 ImVec2(xmax, ymax),
670 intersect
671 );
672 }
673
PushClipRectFullScreen(ImDrawList * list)674 static void PushClipRectFullScreen(ImDrawList* list) {
675 list->PushClipRectFullScreen();
676 }
677
PopClipRect(ImDrawList * list)678 static void PopClipRect(ImDrawList* list) {
679 list->PopClipRect();
680 }
681
PushTextureID(ImDrawList * list,index_t id)682 static void PushTextureID(ImDrawList* list, index_t id) {
683 union {
684 ImTextureID im_texture_id;
685 index_t gl_texture_id;
686 };
687 gl_texture_id = id;
688 list->PushTextureID(im_texture_id);
689 }
690
PopTextureID(ImDrawList * list)691 static void PopTextureID(ImDrawList* list) {
692 list->PopClipRect();
693 }
694
AddLine(ImDrawList * list,float x1,float y1,float x2,float y2,Numeric::uint32 color,float thickness)695 static void AddLine(
696 ImDrawList* list, float x1, float y1, float x2, float y2,
697 Numeric::uint32 color, float thickness
698 ) {
699 list->AddLine(
700 ImVec2(x1,y1), ImVec2(x2,y2),
701 color, thickness
702 );
703 }
704
AddRect(ImDrawList * list,float x1,float y1,float x2,float y2,Numeric::uint32 color,float rounding,int rounding_corners,float thickness)705 static void AddRect(
706 ImDrawList* list,
707 float x1, float y1, float x2, float y2,
708 Numeric::uint32 color, float rounding, int rounding_corners,
709 float thickness
710 ) {
711 list->AddRect(
712 ImVec2(x1,y1), ImVec2(x2,y2), color, rounding,
713 ImDrawCornerFlags(rounding_corners), thickness
714 );
715 }
716
AddRectFilled(ImDrawList * list,float x1,float y1,float x2,float y2,Numeric::uint32 color,float rounding,int rounding_corners)717 static void AddRectFilled(
718 ImDrawList* list,
719 float x1, float y1, float x2, float y2,
720 Numeric::uint32 color, float rounding, int rounding_corners
721 ) {
722 list->AddRectFilled(
723 ImVec2(x1,y1), ImVec2(x2,y2), color, rounding,
724 ImDrawCornerFlags(rounding_corners)
725 );
726 }
727
AddRectFilledMultiColor(ImDrawList * list,float x1,float y1,float x2,float y2,Numeric::uint32 color1,Numeric::uint32 color2,Numeric::uint32 color3,Numeric::uint32 color4)728 static void AddRectFilledMultiColor(
729 ImDrawList* list,
730 float x1, float y1, float x2, float y2,
731 Numeric::uint32 color1, Numeric::uint32 color2,
732 Numeric::uint32 color3, Numeric::uint32 color4
733 ) {
734 list->AddRectFilledMultiColor(
735 ImVec2(x1,y1), ImVec2(x2,y2),
736 color1, color2, color3, color4
737 );
738 }
739
AddQuad(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,float x4,float y4,Numeric::uint32 color,float thickness)740 static void AddQuad(
741 ImDrawList* list,
742 float x1, float y1, float x2, float y2,
743 float x3, float y3, float x4, float y4,
744 Numeric::uint32 color,
745 float thickness
746 ) {
747 list->AddQuad(
748 ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), ImVec2(x4,y4),
749 color, thickness
750 );
751 }
752
AddQuadFilled(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,float x4,float y4,Numeric::uint32 color)753 static void AddQuadFilled(
754 ImDrawList* list, float x1, float y1, float x2, float y2,
755 float x3, float y3, float x4, float y4, Numeric::uint32 color
756 ) {
757 list->AddQuad(
758 ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), ImVec2(x4,y4), color
759 );
760 }
761
AddTriangle(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,Numeric::uint32 color,float thickness)762 static void AddTriangle(
763 ImDrawList* list, float x1, float y1, float x2, float y2,
764 float x3, float y3, Numeric::uint32 color, float thickness
765 ) {
766 list->AddTriangle(
767 ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), color, thickness
768 );
769 }
770
AddTriangleFilled(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,Numeric::uint32 color)771 static void AddTriangleFilled(
772 ImDrawList* list, float x1, float y1, float x2, float y2,
773 float x3, float y3, Numeric::uint32 color
774 ) {
775 list->AddTriangleFilled(ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), color);
776 }
777
AddCircle(ImDrawList * list,float x,float y,float radius,Numeric::uint32 color,int num_segments,float thickness)778 static void AddCircle(
779 ImDrawList* list, float x, float y, float radius, Numeric::uint32 color,
780 int num_segments, float thickness
781 ) {
782 list->AddCircle(ImVec2(x,y), radius, color, num_segments, thickness);
783 }
784
AddCircleFilled(ImDrawList * list,float x,float y,float radius,Numeric::uint32 color,int num_segments)785 static void AddCircleFilled(
786 ImDrawList* list, float x, float y, float radius, Numeric::uint32 color,
787 int num_segments
788 ) {
789 list->AddCircleFilled(ImVec2(x,y), radius, color, num_segments);
790 }
791
AddText(ImDrawList * list,float x,float y,index_t color,const char * text)792 static void AddText(
793 ImDrawList* list, float x, float y, index_t color, const char* text
794 ) {
795 list->AddText(ImVec2(x,y), color, text);
796 }
797
AddText2(ImDrawList * list,index_t font,float font_size,float x,float y,index_t color,const char * text)798 static void AddText2(
799 ImDrawList* list, index_t font, float font_size, float x, float y,
800 index_t color, const char* text
801 ) {
802 if(int(font) >= ImGui::GetIO().Fonts->Fonts.size()) {
803 return;
804 }
805 ImFont* imfont = ImGui::GetIO().Fonts->Fonts[int(font)];
806 list->AddText(imfont, font_size, ImVec2(x,y), color, text);
807 }
808
AddBezierCurve(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,float x4,float y4,index_t color,float thickness,int num_segments)809 static void AddBezierCurve(
810 ImDrawList* list, float x1, float y1, float x2, float y2,
811 float x3, float y3, float x4, float y4, index_t color,
812 float thickness, int num_segments
813 ) {
814 list->AddBezierCurve(
815 ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), ImVec2(x4,y4),
816 color, thickness, num_segments
817 );
818 }
819
AddImage(ImDrawList * list,index_t id,float x1,float y1,float x2,float y2,float u1,float v1,float u2,float v2,index_t color)820 static void AddImage(
821 ImDrawList* list, index_t id,
822 float x1, float y1, float x2, float y2,
823 float u1, float v1, float u2, float v2,
824 index_t color
825 ) {
826 union {
827 ImTextureID im_texture_id;
828 index_t gl_texture_id;
829 };
830 gl_texture_id = id;
831 list->AddImage(
832 im_texture_id,
833 ImVec2(x1,y1), ImVec2(x2,y2),
834 ImVec2(u1,v1), ImVec2(u2,v2),
835 color
836 );
837 }
838
AddImageRounded(ImDrawList * list,index_t id,float x1,float y1,float x2,float y2,float u1,float v1,float u2,float v2,index_t color,float rounding,int rounding_corners)839 static void AddImageRounded(
840 ImDrawList* list, index_t id,
841 float x1, float y1, float x2, float y2,
842 float u1, float v1, float u2, float v2,
843 index_t color, float rounding, int rounding_corners
844 ) {
845 union {
846 ImTextureID im_texture_id;
847 index_t gl_texture_id;
848 };
849 gl_texture_id = id;
850 list->AddImageRounded(
851 im_texture_id,
852 ImVec2(x1,y1), ImVec2(x2,y2),
853 ImVec2(u1,v1), ImVec2(u2,v2),
854 color, rounding, ImDrawCornerFlags(rounding_corners)
855 );
856 }
857
PathClear(ImDrawList * list)858 static void PathClear(ImDrawList* list) {
859 list->PathClear();
860 }
861
PathLineTo(ImDrawList * list,float x,float y)862 static void PathLineTo(ImDrawList* list, float x, float y) {
863 list->PathLineTo(ImVec2(x,y));
864 }
865
PathLineToMergeDuplicate(ImDrawList * list,float x,float y)866 static void PathLineToMergeDuplicate(ImDrawList* list, float x, float y) {
867 list->PathLineToMergeDuplicate(ImVec2(x,y));
868 }
869
PathFillConvex(ImDrawList * list,index_t color)870 static void PathFillConvex(ImDrawList* list, index_t color) {
871 list->PathFillConvex(color);
872 }
873
PathStroke(ImDrawList * list,index_t color,bool closed,float thickness)874 static void PathStroke(
875 ImDrawList* list, index_t color, bool closed, float thickness
876 ) {
877 list->PathStroke(color, closed, thickness);
878 }
879
PathArcTo(ImDrawList * list,float cx,float cy,float radius,float a1,float a2,int num_segments)880 static void PathArcTo(
881 ImDrawList* list, float cx, float cy, float radius, float a1, float a2,
882 int num_segments
883 ) {
884 list->PathArcTo(ImVec2(cx,cy), radius, a1, a2, num_segments);
885 }
886
PathArcToFast(ImDrawList * list,float cx,float cy,float radius,int a1,int a2)887 static void PathArcToFast(
888 ImDrawList* list, float cx, float cy, float radius, int a1, int a2
889 ) {
890 list->PathArcToFast(ImVec2(cx,cy), radius, a1, a2);
891 }
892
PathBezierCurveTo(ImDrawList * list,float x1,float y1,float x2,float y2,float x3,float y3,int num_segments)893 static void PathBezierCurveTo(
894 ImDrawList* list,
895 float x1, float y1, float x2, float y2, float x3, float y3,
896 int num_segments
897 ) {
898 list->PathBezierCurveTo(
899 ImVec2(x1,y1), ImVec2(x2,y2), ImVec2(x3,y3), num_segments
900 );
901 }
902
PathRect(ImDrawList * list,float x1,float y1,float x2,float y2,float rounding,int rounding_corners)903 static void PathRect(
904 ImDrawList* list,
905 float x1, float y1, float x2, float y2,
906 float rounding, int rounding_corners
907 ) {
908 list->PathRect(
909 ImVec2(x1,y1), ImVec2(x2,y2),
910 rounding, ImDrawCornerFlags(rounding_corners)
911 );
912 }
913 }
914
915
916 #define DECLARE_IMGUI_CONSTANT(C) \
917 lua_pushinteger(L,C); \
918 lua_setglobal(L,#C)
919
920
init_lua_imgui(lua_State * L)921 void init_lua_imgui(lua_State* L) {
922 lState = L;
923 LoadImguiBindings();
924
925 DECLARE_IMGUI_CONSTANT(ImGuiExtFileDialogFlags_Load);
926 DECLARE_IMGUI_CONSTANT(ImGuiExtFileDialogFlags_Save);
927 DECLARE_IMGUI_CONSTANT(ImGuiCond_Always);
928 DECLARE_IMGUI_CONSTANT(ImGuiCond_Once);
929 DECLARE_IMGUI_CONSTANT(ImGuiCond_FirstUseEver);
930 DECLARE_IMGUI_CONSTANT(ImGuiCond_Appearing);
931 DECLARE_IMGUI_CONSTANT(ImGuiSelectableFlags_AllowDoubleClick);
932
933 DECLARE_IMGUI_CONSTANT(ImGuiCol_Text);
934 DECLARE_IMGUI_CONSTANT(ImGuiCol_TextDisabled);
935 DECLARE_IMGUI_CONSTANT(ImGuiCol_WindowBg);
936 DECLARE_IMGUI_CONSTANT(ImGuiCol_ChildBg);
937 DECLARE_IMGUI_CONSTANT(ImGuiCol_PopupBg);
938 DECLARE_IMGUI_CONSTANT(ImGuiCol_Border);
939 DECLARE_IMGUI_CONSTANT(ImGuiCol_BorderShadow);
940 DECLARE_IMGUI_CONSTANT(ImGuiCol_FrameBg);
941 DECLARE_IMGUI_CONSTANT(ImGuiCol_FrameBgHovered);
942 DECLARE_IMGUI_CONSTANT(ImGuiCol_FrameBgActive);
943 DECLARE_IMGUI_CONSTANT(ImGuiCol_TitleBg);
944 DECLARE_IMGUI_CONSTANT(ImGuiCol_TitleBgActive);
945 DECLARE_IMGUI_CONSTANT(ImGuiCol_TitleBgCollapsed);
946 DECLARE_IMGUI_CONSTANT(ImGuiCol_MenuBarBg);
947 DECLARE_IMGUI_CONSTANT(ImGuiCol_ScrollbarBg);
948 DECLARE_IMGUI_CONSTANT(ImGuiCol_ScrollbarGrab);
949 DECLARE_IMGUI_CONSTANT(ImGuiCol_ScrollbarGrabHovered);
950 DECLARE_IMGUI_CONSTANT(ImGuiCol_ScrollbarGrabActive);
951 DECLARE_IMGUI_CONSTANT(ImGuiCol_CheckMark);
952 DECLARE_IMGUI_CONSTANT(ImGuiCol_SliderGrab);
953 DECLARE_IMGUI_CONSTANT(ImGuiCol_SliderGrabActive);
954 DECLARE_IMGUI_CONSTANT(ImGuiCol_Button);
955 DECLARE_IMGUI_CONSTANT(ImGuiCol_ButtonHovered);
956 DECLARE_IMGUI_CONSTANT(ImGuiCol_ButtonActive);
957 DECLARE_IMGUI_CONSTANT(ImGuiCol_Header);
958 DECLARE_IMGUI_CONSTANT(ImGuiCol_HeaderHovered);
959 DECLARE_IMGUI_CONSTANT(ImGuiCol_HeaderActive);
960 DECLARE_IMGUI_CONSTANT(ImGuiCol_Separator);
961 DECLARE_IMGUI_CONSTANT(ImGuiCol_SeparatorHovered);
962 DECLARE_IMGUI_CONSTANT(ImGuiCol_SeparatorActive);
963 DECLARE_IMGUI_CONSTANT(ImGuiCol_ResizeGrip);
964 DECLARE_IMGUI_CONSTANT(ImGuiCol_ResizeGripHovered);
965 DECLARE_IMGUI_CONSTANT(ImGuiCol_ResizeGripActive);
966 DECLARE_IMGUI_CONSTANT(ImGuiCol_Tab);
967 DECLARE_IMGUI_CONSTANT(ImGuiCol_TabHovered);
968 DECLARE_IMGUI_CONSTANT(ImGuiCol_TabActive);
969 DECLARE_IMGUI_CONSTANT(ImGuiCol_TabUnfocused);
970 DECLARE_IMGUI_CONSTANT(ImGuiCol_TabUnfocusedActive);
971 DECLARE_IMGUI_CONSTANT(ImGuiCol_DockingPreview);
972 DECLARE_IMGUI_CONSTANT(ImGuiCol_DockingEmptyBg);
973 DECLARE_IMGUI_CONSTANT(ImGuiCol_PlotLines);
974 DECLARE_IMGUI_CONSTANT(ImGuiCol_PlotLinesHovered);
975 DECLARE_IMGUI_CONSTANT(ImGuiCol_PlotHistogram);
976 DECLARE_IMGUI_CONSTANT(ImGuiCol_PlotHistogramHovered);
977 DECLARE_IMGUI_CONSTANT(ImGuiCol_TextSelectedBg);
978 DECLARE_IMGUI_CONSTANT(ImGuiCol_DragDropTarget);
979 DECLARE_IMGUI_CONSTANT(ImGuiCol_NavHighlight);
980 DECLARE_IMGUI_CONSTANT(ImGuiCol_NavWindowingHighlight);
981 DECLARE_IMGUI_CONSTANT(ImGuiCol_NavWindowingDimBg);
982 DECLARE_IMGUI_CONSTANT(ImGuiCol_ModalWindowDimBg);
983
984 lua_getglobal(L, "imgui");
985
986 lua_pushliteral(L,"TextInput");
987 lua_pushcfunction(L,wrapper_TextInput);
988 lua_settable(L,-3);
989
990 lua_pushliteral(L,"Combo");
991 lua_pushcfunction(L,wrapper_Combo);
992 lua_settable(L,-3);
993
994 lua_pushliteral(L,"ColorEdit3WithPalette");
995 lua_pushcfunction(L,wrapper_ColorEdit3WithPalette);
996 lua_settable(L,-3);
997
998 lua_pushliteral(L,"ColorEdit4WithPalette");
999 lua_pushcfunction(L,wrapper_ColorEdit4WithPalette);
1000 lua_settable(L,-3);
1001
1002 lua_pushliteral(L,"OpenFileDialog");
1003 lua_pushcfunction(L,wrapper_OpenFileDialog);
1004 lua_settable(L,-3);
1005
1006 lua_pushliteral(L,"FileDialog");
1007 lua_pushcfunction(L,wrapper_FileDialog);
1008 lua_settable(L,-3);
1009
1010 lua_pushliteral(L,"SetNextWindowPos");
1011 lua_pushcfunction(L,wrapper_SetNextWindowPos);
1012 lua_settable(L,-3);
1013
1014 lua_pushliteral(L,"SetNextWindowSize");
1015 lua_pushcfunction(L,wrapper_SetNextWindowSize);
1016 lua_settable(L,-3);
1017
1018 lua_pushliteral(L,"IsItemHovered");
1019 lua_pushcfunction(L,wrapper_IsItemHovered);
1020 lua_settable(L,-3);
1021
1022 lua_pushliteral(L,"Text");
1023 lua_pushcfunction(L,wrapper_Text);
1024 lua_settable(L,-3);
1025
1026 lua_pushliteral(L,"SetTooltip");
1027 lua_pushcfunction(L,wrapper_SetTooltip);
1028 lua_settable(L,-3);
1029
1030 lua_pushliteral(L,"ShowStyleEditor");
1031 lua_pushcfunction(L,wrapper_ShowStyleEditor);
1032 lua_settable(L,-3);
1033
1034 lua_pushliteral(L,"PushFont");
1035 lua_pushcfunction(L,wrapper_PushFont);
1036 lua_settable(L,-3);
1037
1038 lua_pushliteral(L,"font_icon");
1039 lua_pushcfunction(L,wrapper_font_icon);
1040 lua_settable(L,-3);
1041
1042 lua_pushliteral(L,"BeginTabBar");
1043 lua_pushcfunction(L,wrapper_BeginTabBar);
1044 lua_settable(L,-3);
1045
1046 lua_pushliteral(L,"BeginTabItem");
1047 lua_pushcfunction(L,wrapper_BeginTabItem);
1048 lua_settable(L,-3);
1049
1050 lua_pushliteral(L,"SimpleButton");
1051 lua_pushcfunction(L,wrapper_SimpleButton);
1052 lua_settable(L,-3);
1053
1054 lua_pushliteral(L,"GetMousePos");
1055 lua_pushcfunction(L,wrapper_GetMousePos);
1056 lua_settable(L,-3);
1057
1058 /*****************************************************************/
1059
1060 lua_bindwrapper(L,ImGui::GetWindowDrawList);
1061 lua_bindwrapper(L,ImGuiDrawAdapters::GetBackgroundDrawList);
1062 lua_bindwrapper(L,ImGuiDrawAdapters::GetForegroundDrawList);
1063
1064 lua_bindwrapper(L,ImGuiDrawAdapters::PushClipRect);
1065 lua_bindwrapper(L,ImGuiDrawAdapters::PushClipRectFullScreen);
1066 lua_bindwrapper(L,ImGuiDrawAdapters::PopClipRect);
1067
1068 lua_bindwrapper(L,ImGuiDrawAdapters::PushTextureID);
1069 lua_bindwrapper(L,ImGuiDrawAdapters::PopTextureID);
1070
1071 lua_bindwrapper(L,ImGuiDrawAdapters::AddLine);
1072 lua_bindwrapper(L,ImGuiDrawAdapters::AddRect);
1073 lua_bindwrapper(L,ImGuiDrawAdapters::AddRectFilled);
1074 lua_bindwrapper(L,ImGuiDrawAdapters::AddRectFilledMultiColor);
1075 lua_bindwrapper(L,ImGuiDrawAdapters::AddQuad);
1076 lua_bindwrapper(L,ImGuiDrawAdapters::AddQuadFilled);
1077 lua_bindwrapper(L,ImGuiDrawAdapters::AddTriangle);
1078 lua_bindwrapper(L,ImGuiDrawAdapters::AddTriangleFilled);
1079 lua_bindwrapper(L,ImGuiDrawAdapters::AddCircle);
1080 lua_bindwrapper(L,ImGuiDrawAdapters::AddCircleFilled);
1081 lua_bindwrapper(L,ImGuiDrawAdapters::AddText);
1082 lua_bindwrapper(L,ImGuiDrawAdapters::AddText2);
1083 lua_bindwrapper(L,ImGuiDrawAdapters::AddBezierCurve);
1084 lua_bindwrapper(L,ImGuiDrawAdapters::AddImage);
1085 lua_bindwrapper(L,ImGuiDrawAdapters::AddImageRounded);
1086 lua_bindwrapper(L,ImGuiDrawAdapters::PathClear);
1087 lua_bindwrapper(L,ImGuiDrawAdapters::PathLineTo);
1088 lua_bindwrapper(L,ImGuiDrawAdapters::PathLineToMergeDuplicate);
1089 lua_bindwrapper(L,ImGuiDrawAdapters::PathFillConvex);
1090 lua_bindwrapper(L,ImGuiDrawAdapters::PathStroke);
1091 lua_bindwrapper(L,ImGuiDrawAdapters::PathArcTo);
1092 lua_bindwrapper(L,ImGuiDrawAdapters::PathArcToFast);
1093 lua_bindwrapper(L,ImGuiDrawAdapters::PathBezierCurveTo);
1094 lua_bindwrapper(L,ImGuiDrawAdapters::PathRect);
1095
1096 lua_pop(L,1);
1097
1098 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_None);
1099 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_TopLeft);
1100 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_TopRight);
1101 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_BotLeft);
1102 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_BotRight);
1103 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_Top);
1104 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_Bot);
1105 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_Left);
1106 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_Right);
1107 DECLARE_IMGUI_CONSTANT(ImDrawCornerFlags_All);
1108
1109 }
1110
1111