The open source OpenXR runtime

st/gui: Refactor a few OpenGL drawing code into helper

+159 -59
+2
src/xrt/state_trackers/gui/CMakeLists.txt
··· 8 8 st_gui STATIC 9 9 gui_common.h 10 10 gui_imgui.h 11 + gui_ogl.c 12 + gui_ogl.h 11 13 gui_ogl_sink.c 12 14 gui_prober.c 13 15 gui_scene.cpp
+96
src/xrt/state_trackers/gui/gui_ogl.c
··· 1 + // Copyright 2019-2023, Collabora, Ltd. 2 + // SPDX-License-Identifier: BSL-1.0 3 + /*! 4 + * @file 5 + * @brief OpenGL helper functions for drawing GUI elements. 6 + * @author Jakob Bornecrantz <jakob@collabora.com> 7 + * @author Moses Turner <moses@collabora.com> 8 + * @ingroup gui 9 + */ 10 + 11 + #include "math/m_api.h" 12 + 13 + #include "gui_ogl.h" 14 + #include "gui_imgui.h" 15 + 16 + 17 + /* 18 + * 19 + * Helpers. 20 + * 21 + */ 22 + 23 + static void 24 + get_uvs(ImVec2 *uv0, ImVec2 *uv1, bool rotate_180, bool flip_y) 25 + { 26 + // Flip direction of y (x) if we are rotating. 27 + float u0 = rotate_180 ? 1.f : 0.f; 28 + float u1 = rotate_180 ? 0.f : 1.f; 29 + 30 + // Flip direction of v (y) if either flip_y or rotate_180 is true. 31 + float v0 = (rotate_180 ^ flip_y) ? 1.f : 0.f; 32 + float v1 = (rotate_180 ^ flip_y) ? 0.f : 1.f; 33 + 34 + // Note: We can't easily do 90 or 270-degree rotations: https://github.com/ocornut/imgui/issues/3267 35 + *uv0 = (ImVec2){u0, v0}; 36 + *uv1 = (ImVec2){u1, v1}; 37 + } 38 + 39 + 40 + /* 41 + * 42 + * 'Exported' functions. 43 + * 44 + */ 45 + 46 + void 47 + gui_ogl_draw_image(uint32_t width, uint32_t height, uint32_t tex_id, float scale, bool rotate_180, bool flip_y) 48 + { 49 + ImVec2 uv0, uv1; 50 + get_uvs(&uv0, &uv1, rotate_180, flip_y); 51 + 52 + // Need to go via ints to get integer steps. 53 + int w = (float)width * scale; 54 + int h = (float)height * scale; 55 + 56 + ImVec2 size = {(float)w, (float)h}; 57 + ImVec4 white = {1, 1, 1, 1}; 58 + ImVec4 black = {0, 0, 0, 1}; 59 + ImTextureID id = (ImTextureID)(intptr_t)tex_id; 60 + 61 + igImageBg(id, size, uv0, uv1, white, white, black); 62 + } 63 + 64 + void 65 + gui_ogl_draw_background(uint32_t width, uint32_t height, uint32_t tex_id, bool rotate_180, bool flip_y) 66 + { 67 + ImVec2 uv0, uv1; 68 + get_uvs(&uv0, &uv1, rotate_180, flip_y); 69 + 70 + const ImU32 white = 0xffffffff; 71 + ImTextureID id = (ImTextureID)(intptr_t)tex_id; 72 + 73 + ImGuiIO *io = igGetIO(); 74 + 75 + float in_w = (float)width; 76 + float in_h = (float)height; 77 + float out_w = io->DisplaySize.x; 78 + float out_h = io->DisplaySize.y; 79 + 80 + float scale_w = (float)out_w / in_w; // 128 / 1280 = 0.1 81 + float scale_h = (float)out_h / in_h; // 128 / 800 = 0.16 82 + 83 + float scale = MIN(scale_w, scale_h); // 0.1 84 + 85 + float inside_w = in_w * scale; 86 + float inside_h = in_h * scale; 87 + 88 + float translate_x = (out_w - inside_w) / 2; // Should be 0 for 1280x800 89 + float translate_y = (out_h - inside_h) / 2; // Should be (1280 - 800) / 2 = 240 90 + 91 + ImVec2 p_min = {translate_x, translate_y}; 92 + ImVec2 p_max = {translate_x + inside_w, translate_y + inside_h}; 93 + 94 + ImDrawList *bg = igGetBackgroundDrawList(); 95 + ImDrawList_AddImage(bg, id, p_min, p_max, uv0, uv1, white); 96 + }
+39
src/xrt/state_trackers/gui/gui_ogl.h
··· 1 + // Copyright 2019-2023, Collabora, Ltd. 2 + // SPDX-License-Identifier: BSL-1.0 3 + /*! 4 + * @file 5 + * @brief OpenGL helper functions for drawing GUI elements. 6 + * @author Jakob Bornecrantz <jakob@collabora.com> 7 + * @ingroup gui 8 + */ 9 + 10 + #pragma once 11 + 12 + #include "xrt/xrt_compiler.h" 13 + 14 + 15 + #ifdef __cplusplus 16 + extern "C" { 17 + #endif 18 + 19 + /*! 20 + * Draw the given textures as igImage, scale of 1.0f == 100%. 21 + * 22 + * @ingroup gui 23 + */ 24 + void 25 + gui_ogl_draw_image(uint32_t width, uint32_t height, uint32_t tex_id, float scale, bool rotate_180, bool flip_y); 26 + 27 + 28 + /*! 29 + * Draw the given texture to the background of the current OS window. 30 + * 31 + * @ingroup gui 32 + */ 33 + void 34 + gui_ogl_draw_background(uint32_t width, uint32_t height, uint32_t tex_id, bool rotate_180, bool flip_y); 35 + 36 + 37 + #ifdef __cplusplus 38 + } 39 + #endif
+8 -8
src/xrt/state_trackers/gui/gui_scene_calibrate.c
··· 27 27 28 28 #include "gui_common.h" 29 29 #include "gui_imgui.h" 30 + #include "gui_ogl.h" 30 31 31 32 #include <assert.h> 32 33 ··· 134 135 135 136 gui_ogl_sink_update(tex); 136 137 137 - int w = tex->w / (tex->half ? 2 : 1); 138 - int h = tex->h / (tex->half ? 2 : 1); 138 + gui_ogl_draw_image( // 139 + (uint32_t)tex->w, // width 140 + (uint32_t)tex->h, // height 141 + tex->id, // tex_id 142 + tex->half ? 0.5f : 1.0f, // scale 143 + false, // rotate_180 144 + false); // flip_y 139 145 140 - ImVec2 size = {(float)w, (float)h}; 141 - ImVec2 uv0 = {0, 0}; 142 - ImVec2 uv1 = {1, 1}; 143 - ImVec4 white = {1, 1, 1, 1}; 144 - ImTextureID id = (ImTextureID)(intptr_t)tex->id; 145 - igImage(id, size, uv0, uv1, white, white); 146 146 igText("Sequence %u", (uint32_t)tex->seq); 147 147 148 148 char temp[512];
+14 -51
src/xrt/state_trackers/gui/gui_window_record.c
··· 34 34 #include "gstreamer/gst_pipeline.h" 35 35 #endif 36 36 37 + #include "gui_ogl.h" 37 38 #include "gui_imgui.h" 38 39 #include "gui_common.h" 39 40 #include "gui_window_record.h" ··· 313 314 314 315 gui_ogl_sink_update(tex); 315 316 316 - ImVec2 uv0 = {0, 0}; 317 - ImVec2 uv1 = {1, 1}; 318 - 319 - // Note: We can't easily do 90 or 270-degree rotations: https://github.com/ocornut/imgui/issues/3267 320 - if (rw->texture.rotate_180) { 321 - uv0 = (ImVec2){1, 1}; 322 - uv1 = (ImVec2){0, 0}; 323 - } 324 - 325 - const ImU32 white = 0xffffffff; 326 - ImTextureID id = (ImTextureID)(intptr_t)tex->id; 327 - 328 - ImGuiIO *io = igGetIO(); 329 - 330 - // Shamelessly stolen from hg_model.cpp 331 - float in_w = tex->w; 332 - float in_h = tex->h; 333 - float out_w = io->DisplaySize.x; 334 - float out_h = io->DisplaySize.y; 335 - 336 - float scale_w = (float)out_w / in_w; // 128 / 1280 = 0.1 337 - float scale_h = (float)out_h / in_h; // 128 / 800 = 0.16 338 - 339 - float scale = MIN(scale_w, scale_h); // 0.1 340 - 341 - float inside_w = in_w * scale; 342 - float inside_h = in_h * scale; 343 - 344 - float translate_x = (out_w - inside_w) / 2; // Should be 0 for 1280x800 345 - float translate_y = (out_h - inside_h) / 2; // Should be (1280 - 800) / 2 = 240 346 - 347 - ImVec2 p_min = {translate_x, translate_y}; 348 - ImVec2 p_max = {translate_x + inside_w, translate_y + inside_h}; 349 - 350 - ImDrawList *bg = igGetBackgroundDrawList(); 351 - ImDrawList_AddImage(bg, id, p_min, p_max, uv0, uv1, white); 317 + gui_ogl_draw_background( // 318 + (uint32_t)tex->w, // width 319 + (uint32_t)tex->h, // height 320 + tex->id, // tex_id 321 + rw->texture.rotate_180, // rotate_180 322 + false); // flip_y 352 323 } 353 324 354 325 void ··· 363 334 364 335 struct gui_ogl_texture *tex = rw->texture.ogl; 365 336 366 - int w = tex->w * rw->texture.scale / 100.0f; 367 - int h = tex->h * rw->texture.scale / 100.0f; 368 - 369 - ImVec2 size = {(float)w, (float)h}; 370 - ImVec2 uv0 = {0, 0}; 371 - ImVec2 uv1 = {1, 1}; 372 - 373 - // Note: We can't easily do 90 or 270-degree rotations: https://github.com/ocornut/imgui/issues/3267 374 - if (rw->texture.rotate_180) { 375 - uv0 = (ImVec2){1, 1}; 376 - uv1 = (ImVec2){0, 0}; 377 - } 337 + gui_ogl_draw_image( // 338 + (uint32_t)tex->w, // width 339 + (uint32_t)tex->h, // height 340 + tex->id, // tex_id 341 + rw->texture.scale / 100.0f, // scale 342 + rw->texture.rotate_180, // rotate_180 343 + false); // flip_y 378 344 379 - ImVec4 white = {1, 1, 1, 1}; 380 - ImTextureID id = (ImTextureID)(intptr_t)tex->id; 381 - igImage(id, size, uv0, uv1, white, white); 382 345 383 346 #ifdef XRT_HAVE_GST 384 347 draw_gst(rw);