pub const Impl = struct { allocator: std.mem.Allocator, device: *gpu.GPUDevice = undefined, drawData: [*c]ig.DrawData = undefined, rendererDebug: bool = true, context: *ig.Context = undefined, beginCount: u32 = 0, pub var NeonObjectTable: core.EngineObjectVTable = core.EngineObjectVTable.from(@This(), "imgui.BackendImpl"); pub const Settings = struct { x: u32 = 0, }; // renderer plugin pub fn create(allocator: std.mem.Allocator) !*@This() { const self = try allocator.create(@This()); self.* = .{ .allocator = allocator, }; return self; } const ImguiArgs = struct { imguiIni: []const u8 = "imgui.ini" }; pub fn setup(self: *@This()) !void { core.graphics_log("imgui startup", .{}); self.device = rend.context().device; try rend.registerRendererObject(@This(), self); const args = try core.ParseArgs(ImguiArgs); c.Imgui_SDL3_Init(@ptrCast(platform.getInstance().window), @ptrCast(self.device)); ig.getIO().?.ini_file_name = @ptrCast(args.imguiIni.ptr); ig.loadIniSettingsFromDisk(@ptrCast(args.imguiIni.ptr)); try platform.getInstance().addSDLProcessFunction(processSDLEvents); core.engine_log("using imgui ini: {s}", .{args.imguiIni}); self.context = ig.getCurrentContext().?; self.setupBeginCount(); } pub fn setupBeginCount(self: *@This()) void { ig.setBeginCount(&self.beginCount); } pub fn processSDLEvents(event: *sdl3.Event) void { if (platform.getInstance().enableImguiEvents) { c.Imgui_SDL3_ProcessEvent(@ptrCast(event)); } } pub fn onPreDraw(p: *anyopaque, cmd: *gpu.GPUCommandBuffer) void { const self: *@This() = @ptrCast(@alignCast(p)); platform.context().imguiMouseConsumed = ig.isWindowHovered(.{ .any_window = true }); const count = self.beginCount; while (self.beginCount > 0) { ig.end(); } if (count > 0) { _ = ig.begin("error", null, .{}); ig.textf("IMGUI ERORR", .{}); core.engine_logs("error"); ig.end(); } ig.render(); if (platform.getInstance().imguiVisible) { self.drawData = ig.getDrawData(); c.Imgui_SDL3_PrepareRender(@ptrCast(self.drawData), @ptrCast(cmd)); } } pub fn postRender(p: *anyopaque, cmd: *gpu.GPUCommandBuffer) void { const self: *@This() = @ptrCast(@alignCast(p)); if (platform.getInstance().imguiVisible) { //const renderpass = cmd.beginGPURenderPass(color_target_infos: [*c]const GPUColorTargetInfo, num_color_targets: u32, depth_stencil_target_info: [*c]const GPUDepthStencilTargetInfo); var targetInfo: gpu.GPUColorTargetInfo = std.mem.zeroes(gpu.GPUColorTargetInfo); targetInfo.texture = rend.context().state.swapchainTargetTexture.?; targetInfo.clear_color = .{ .r = 0.0, .g = 0.0, .b = 0.0, .a = 0.0 }; targetInfo.load_op = .loadopLoad; targetInfo.store_op = .storeopStore; const renderpass = cmd.beginGPURenderPass(&targetInfo, 1, null); c.ImGui_SDLGPU3_RenderDrawData( @ptrCast(self.drawData), @ptrCast(cmd), @ptrCast(renderpass), ); renderpass.endGPURenderPass(); } } pub fn preTick(self: *@This(), dt: f64) core.EngineDataEventError!void { _ = self; c.Imgui_SDL3_NewFrame(); c.igNewFrame(); _ = ig.dockSpaceOverViewport(ig.getMainViewport(), .{ .passthru_central_node = true }, null); _ = dt; } // renderer plugin pub fn destroy(self: *@This()) void { self.allocator.destroy(self); } }; const c = @import("cimgui").c; const ig = @import("cimgui"); const sdl3 = @import("sdl3"); const gpu = sdl3.gpu; const rend = @import("rend"); const platform = @import("platform"); const std = @import("std"); const core = @import("core");