diff --git a/imgui.ini b/imgui.ini index 5c0aa5e..d39c017 100644 --- a/imgui.ini +++ b/imgui.ini @@ -8,7 +8,7 @@ Size=1152,1414 [Window][main] Pos=0,0 -Size=1775,680 +Size=1777,680 [Window][Hex View] Pos=91,62 diff --git a/src/app_state.h b/src/app_state.h index 2097d3f..8ad1b05 100644 --- a/src/app_state.h +++ b/src/app_state.h @@ -1,9 +1,18 @@ +struct Delta_Time_Accum { + f32 *base; + u16 count; + u16 max; + u16 start; +}; + struct App_State { Window_Data win_data; User_Input user_input; RNTuple_Info rntinfo; Viewer_Settings vsettings; + Delta_Time_Accum delta_time_accum; + FILE *inspected_file; u8 *inspected_fmem; u64 inspected_file_size; diff --git a/src/mainloop.cpp b/src/mainloop.cpp index 3b4c1b6..da8ca09 100644 --- a/src/mainloop.cpp +++ b/src/mainloop.cpp @@ -1,3 +1,37 @@ +internal +void glfw_error_callback(i32 error, const char *description) { + fprintf(stderr, "GLFW error %d: %s\n", error, description); +} + +internal +GLFWwindow *init_glfw(i32 desired_win_width, i32 desired_win_height) +{ + glfwSetErrorCallback(glfw_error_callback); + glfwInit(); + glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4); + // glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); + glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); + glfwWindowHint(GLFW_DOUBLEBUFFER, GLFW_TRUE); + glfwWindowHint(GLFW_RESIZABLE, GLFW_TRUE); + glfwWindowHint(GLFW_DECORATED, GLFW_TRUE); + glfwWindowHint(GLFW_DEPTH_BITS, 32); +#ifndef NDEBUG + glfwWindowHint(GLFW_OPENGL_DEBUG_CONTEXT, true); +#endif + + GLFWwindow *window = glfwCreateWindow( + desired_win_width, desired_win_height, + "RNTuple Viewer", + nullptr, + nullptr + ); + + glfwMakeContextCurrent(window); + //glfwSetFramebufferSizeCallback(window, resize_keep_ratio); + + return window; +} + internal void monitor_key(GLFWwindow *window, u16 *key_state, i32 glfw_key, Input_Key haru_key) { u16& state = key_state[haru_key]; @@ -25,15 +59,19 @@ void monitor_mouse_btn(GLFWwindow *window, u16 *mouse_btn_state, i32 glfw_btn, M internal void run_main_loop(GLFWwindow *window, Arena *arena, App_State &app) { - f32 delta_time; + f32 delta_time_ms; chr::time_point last_saved_time = chr::high_resolution_clock::now(); + + app.delta_time_accum.max = 100; + app.delta_time_accum.base = arena_push_array(arena, app.delta_time_accum.max); b8 running = true; while (running) { chr::time_point frame_start = chr::high_resolution_clock::now(); u64 time_since_prev_frame_us = chr::duration_cast(frame_start - last_saved_time).count(); - delta_time = time_since_prev_frame_us * 0.000'001f; + delta_time_ms = time_since_prev_frame_us * 0.001f; last_saved_time = frame_start; + accum_dt_ms(app.delta_time_accum, delta_time_ms); glfwPollEvents(); @@ -92,7 +130,7 @@ void run_main_loop(GLFWwindow *window, Arena *arena, App_State &app) monitor_mouse_btn(window, mouse_btn_state, GLFW_MOUSE_BUTTON_RIGHT, MOUSE_BTN_RIGHT); } - update_and_render(arena, app, delta_time); + update_and_render(arena, app, delta_time_ms); ImGui::Render(); ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); diff --git a/src/render.cpp b/src/render.cpp index 5d32aa3..bc19d25 100644 --- a/src/render.cpp +++ b/src/render.cpp @@ -1,12 +1,36 @@ +internal +void accum_dt_ms(Delta_Time_Accum &accum, f32 dt) +{ + if (accum.count < accum.max) { + assert(accum.start == 0); + accum.base[accum.count++] = dt; + } else { + accum.base[accum.start++] = dt; + if (accum.start == accum.max) + accum.start = 0; + } +} + +internal +f32 calc_avg_dt_ms(const Delta_Time_Accum &accum) +{ + f32 res = 0; + for (u16 idx = 0; idx < accum.count; ++idx) + res += accum.base[idx]; + if (accum.count) res /= accum.count; + return res; +} + internal u32 mem_edit_bg_color_fn(const u8 *data, u64 off, const void *user_data) { const App_State *app = reinterpret_cast(user_data); + const RNTuple_Info &rinfo = app->rntinfo; - #define COL(c) (ImColor((c)[0], (c)[1], (c)[2])) - if (app->rntinfo.header.start <= off && off <= app->rntinfo.header.end()) return COL(app->vsettings.col_header); - if (app->rntinfo.footer.start <= off && off <= app->rntinfo.footer.end()) return COL(app->vsettings.col_footer); - #undef COL +#define COL(c) (ImColor((c)[0], (c)[1], (c)[2])) + if (rinfo.header.start <= off && off <= rinfo.header.end()) return COL(app->vsettings.col_header); + if (rinfo.footer.start <= off && off <= rinfo.footer.end()) return COL(app->vsettings.col_footer); +#undef COL return IM_COL32(0, 0, 0, 0); } @@ -23,6 +47,7 @@ MemoryEditor make_memory_editor(const App_State &app) return mem_edit; } +internal Viewer_Settings make_viewer_settings() { Viewer_Settings settings {}; @@ -34,9 +59,9 @@ Viewer_Settings make_viewer_settings() } internal -void update_and_render(Arena *arena, App_State &app, f32 delta_time) +void update_and_render(Arena *arena, App_State &app, f32 delta_time_ms) { - (void)delta_time; + (void)delta_time_ms; ImGui::SetNextWindowPos({ 0, 0 }); ImGui::SetNextWindowSize({ (f32)app.win_data.width, (f32)app.win_data.height }); @@ -55,10 +80,28 @@ void update_and_render(Arena *arena, App_State &app, f32 delta_time) const auto main_win_flags = ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoDecoration; if (ImGui::Begin("main", nullptr, main_win_flags)) { - ImGui::Text("Inspecting RNTuple '%s' (%s)", app.ntpl_name, - (const char *)rntuple_description(scratch.arena, app.rntinfo.anchor)); + + String8 ntpl_desc = rntuple_description(scratch.arena, app.rntinfo.anchor); + ImGui::Text("Inspecting RNTuple '%s' (%s)", app.ntpl_name, ntpl_desc.c()); + + // Draw avg delta time + { + ImGui::SameLine(); + + f32 avg_dt = calc_avg_dt_ms(app.delta_time_accum); + String8 dt_txt = push_str8f(scratch.arena, "avg dt: %.1f", avg_dt); + + f32 pos_x = (ImGui::GetCursorPosX() + ImGui::GetColumnWidth() - ImGui::CalcTextSize(dt_txt.c()).x + - ImGui::GetScrollX() - 2 * ImGui::GetStyle().ItemSpacing.x); + if (pos_x > ImGui::GetCursorPosX()) + ImGui::SetCursorPosX(pos_x); + + ImGui::Text("%s", dt_txt.c()); + } + ImGui::Separator(); + // Draw main content { static MemoryEditor mem_edit = make_memory_editor(app); ImGui::BeginTable("Hex View", 2); diff --git a/src/rntviewer.cpp b/src/rntviewer.cpp index 72de955..0759ce4 100644 --- a/src/rntviewer.cpp +++ b/src/rntviewer.cpp @@ -55,40 +55,6 @@ b8 init_imgui(GLFWwindow* window) { return true; } -internal -void glfw_error_callback(i32 error, const char *description) { - fprintf(stderr, "GLFW error %d: %s\n", error, description); -} - -internal -GLFWwindow* init_glfw(i32 desired_win_width, i32 desired_win_height) -{ - glfwSetErrorCallback(glfw_error_callback); - glfwInit(); - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4); - // glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); - glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); - glfwWindowHint(GLFW_DOUBLEBUFFER, GLFW_TRUE); - glfwWindowHint(GLFW_RESIZABLE, GLFW_TRUE); - glfwWindowHint(GLFW_DECORATED, GLFW_TRUE); - glfwWindowHint(GLFW_DEPTH_BITS, 32); -#ifndef NDEBUG - glfwWindowHint(GLFW_OPENGL_DEBUG_CONTEXT, true); -#endif - - GLFWwindow *window = glfwCreateWindow( - desired_win_width, desired_win_height, - "RNTuple Viewer", - nullptr, - nullptr - ); - - glfwMakeContextCurrent(window); - //glfwSetFramebufferSizeCallback(window, resize_keep_ratio); - - return window; -} - internal void app_cleanup(App_State &app) { diff --git a/src/str.h b/src/str.h index 7246132..fd81c54 100644 --- a/src/str.h +++ b/src/str.h @@ -2,9 +2,7 @@ struct String8 { u8* str; u64 size; - operator const char *() const { - return (const char *)str; - } + const char *c() const { return reinterpret_cast(str); } }; #define str8(s) String8((u8*)(s), sizeof(s) - 1)