From aade06e6000d1d0bf2e65761d0316695501c64a0 Mon Sep 17 00:00:00 2001 From: Nathan Christopher McRae Date: Mon, 19 Jun 2023 22:42:26 -0700 Subject: [PATCH] Add docmap struct We want to have an array of docmaps, one for each file and be able to iterate through them. That way the layout can be done in a single function. --- src/main.zig | 474 +++++++++++++++++++++++++++++---------------------- 1 file changed, 270 insertions(+), 204 deletions(-) diff --git a/src/main.zig b/src/main.zig index f641c99..7ec45fc 100644 --- a/src/main.zig +++ b/src/main.zig @@ -1,204 +1,270 @@ -const std = @import("std"); - -const c = @cImport({ - @cInclude("SDL.h"); - @cInclude("SDL_ttf.h"); -}); - -const assert = @import("std").debug.assert; - -pub fn main() !void { - const window_width = 300; - const window_height = 500; - const column_width = 100; - - if (c.SDL_Init(c.SDL_INIT_VIDEO) != 0) { - c.SDL_Log("Unable to initialize SDL: %s", c.SDL_GetError()); - return error.SDLInitializationFailed; - } - defer c.SDL_Quit(); - - const screen = c.SDL_CreateWindow("Document Map Viewer", c.SDL_WINDOWPOS_UNDEFINED, c.SDL_WINDOWPOS_UNDEFINED, window_width, window_height, c.SDL_WINDOW_OPENGL) orelse - { - c.SDL_Log("Unable to create window: %s", c.SDL_GetError()); - return error.SDLInitializationFailed; - }; - defer c.SDL_DestroyWindow(screen); - - const renderer = c.SDL_CreateRenderer(screen, -1, 0) orelse { - c.SDL_Log("Unable to create renderer: %s", c.SDL_GetError()); - return error.SDLInitializationFailed; - }; - defer c.SDL_DestroyRenderer(renderer); - - const source_code = @embedFile("GapProbeScan.cs"); - const file_name = "GapProbeScan.cs"; - - const color_result: c_int = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); - if (color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", color_result); - return error.SDLInitializationFailed; - } - - // https://github.com/cirosantilli/cpp-cheat/blob/e52ed4b838e2697d8f44ab5bef3e7a170705d48e/sdl/ttf.c - const ttf_init_result: c_int = c.TTF_Init(); - if (ttf_init_result != 0) { - c.SDL_Log("Unable to init TTF: %d", ttf_init_result); - return error.TTFInitializationFailed; - } - defer c.TTF_Quit(); - - const text_color: c.SDL_Color = c.SDL_Color { - .r = 0, - .g = 0, - .b = 0, - .a = 255 - }; - - // TODO: can we embed this file? - const font: ?*c.TTF_Font = c.TTF_OpenFont("FreeSans.ttf", 24); - if (font == null) { - const err = c.TTF_GetError(); - c.SDL_Log("Unable to load font: %s", err); - return error.TTFFontLoadFailed; - } - - const surface: [*c]c.SDL_Surface = c.TTF_RenderText_Solid(font, file_name, text_color); - if (surface == null) { - c.SDL_Log("Unable to render text"); - return error.RenderTextFailed; - } - defer c.SDL_FreeSurface(surface); - - const texture: ?*c.SDL_Texture = c.SDL_CreateTextureFromSurface(renderer, surface); - if (texture == null) { - c.SDL_Log("Unable to create texture from surface"); - return error.CreateTextureFailed; - } - defer c.SDL_DestroyTexture(texture); - - const rect = c.SDL_Rect { - .x = 0, - .y = 0, - .w = surface.*.w, - .h = surface.*.h, - }; - - // const surface = c.SDL_GetWindowSurface(screen); - - var quit = false; - while (!quit) { - var event: c.SDL_Event = undefined; - while (c.SDL_PollEvent(&event) != 0) { - switch (event.@"type") { - c.SDL_QUIT => { - quit = true; - }, - else => {}, - } - } - - const initial_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); - if (initial_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", initial_color_result); - return error.SDLInitializationFailed; - } - - var x: c_int = 0; - while (x < window_width) : (x += 1) { - var y: c_int = 0; - while (y < window_height) : (y += 1) { - const draw_result = c.SDL_RenderDrawPoint(renderer, x, y); - if (draw_result != 0) { - c.SDL_Log("Unable to draw point: %d", draw_result); - return error.SDLDrawingFailed; - } - } - } - - var i: usize = 0; - var column: c_int = 0; - x = 0; - var y: c_int = surface.*.h; - // white: false, black: true - var color: bool = false; - while (i < source_code.len) : (i += 1) { - if (source_code[i] == 10) { - y += 1; - if (y > window_height) { - y = 0; - column += 1; - // std.debug.print("Column: {any}, x: {any}\n", .{column, column*column_width}); - } - x = column * column_width; - - continue; - } - - if (source_code[i] == 32 and color) { - color = false; - const white_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); - if (white_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", white_color_result); - return error.SDLInitializationFailed; - } - } else if (source_code[i] != 32 and !color) { - color = true; - const black_color_result = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); - if (black_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", black_color_result); - return error.SDLInitializationFailed; - } - } - - if (x < (column + 1) * column_width) { - const draw_result = c.SDL_RenderDrawPoint(renderer, x, y); - if (draw_result != 0) { - c.SDL_Log("Unable to draw point: %d", draw_result); - return error.SDLDrawingFailed; - } - } else { - const red_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 0, 0, 255); - if (red_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", red_color_result); - return error.SDLInitializationFailed; - } - - const draw_result = c.SDL_RenderDrawPoint(renderer, (column + 1) * column_width - 1, y); - if (draw_result != 0) { - c.SDL_Log("Unable to draw point: %d", draw_result); - return error.SDLDrawingFailed; - } - - if (!color) { - const white_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); - if (white_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", white_color_result); - return error.SDLInitializationFailed; - } - } else { - const black_color_result = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); - if (black_color_result != 0) { - c.SDL_Log("Unable to set draw color: %d", black_color_result); - return error.SDLInitializationFailed; - } - } - } - - x += 1; - } - - // Display text - if (c.SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255) != 0) { - c.SDL_Log("Unable to set draw color"); - } - - if (c.SDL_RenderCopy(renderer, texture, null, &rect) != 0) { - c.SDL_Log("Unable to render copy"); - } - - c.SDL_RenderPresent(renderer); - - c.SDL_Delay(17); - } -} +const std = @import("std"); + +const c = @cImport({ + @cInclude("SDL.h"); + @cInclude("SDL_ttf.h"); +}); + +const assert = @import("std").debug.assert; + +const DrawnText = struct { + surface: [*c]c.SDL_Surface, + texture: ?*c.SDL_Texture, + rect: c.SDL_Rect, +}; + +const FileDocMap = struct { + title_text: DrawnText, + contents: []u8, +}; + +pub fn main() !void { + var gpa = std.heap.GeneralPurposeAllocator(.{}){}; + defer { + if(gpa.deinit()) { + std.debug.print("Allocator leak\n", .{}); + } + } + + const allocator = gpa.allocator(); + + const window_width = 300; + const window_height = 500; + const column_width = 100; + + if (c.SDL_Init(c.SDL_INIT_VIDEO) != 0) { + c.SDL_Log("Unable to initialize SDL: %s", c.SDL_GetError()); + return error.SDLInitializationFailed; + } + defer c.SDL_Quit(); + + const screen = c.SDL_CreateWindow("Document Map Viewer", c.SDL_WINDOWPOS_UNDEFINED, c.SDL_WINDOWPOS_UNDEFINED, window_width, window_height, c.SDL_WINDOW_OPENGL) orelse + { + c.SDL_Log("Unable to create window: %s", c.SDL_GetError()); + return error.SDLInitializationFailed; + }; + defer c.SDL_DestroyWindow(screen); + + const renderer = c.SDL_CreateRenderer(screen, -1, 0) orelse { + c.SDL_Log("Unable to create renderer: %s", c.SDL_GetError()); + return error.SDLInitializationFailed; + }; + defer c.SDL_DestroyRenderer(renderer); + + // Turn on anti-aliasing + // :( doesn't seem to work + const aa_result = c.SDL_SetHint(c.SDL_HINT_RENDER_SCALE_QUALITY, "1"); + if (aa_result != c.SDL_TRUE) { + c.SDL_Log("Unable to set anti-aliasing: %d", c.SDL_GetError()); + return error.SDLInitializationFailed; + } + + // https://github.com/cirosantilli/cpp-cheat/blob/e52ed4b838e2697d8f44ab5bef3e7a170705d48e/sdl/ttf.c + const ttf_init_result: c_int = c.TTF_Init(); + if (ttf_init_result != 0) { + c.SDL_Log("Unable to init TTF: %d", ttf_init_result); + return error.TTFInitializationFailed; + } + defer c.TTF_Quit(); + + const text_color: c.SDL_Color = c.SDL_Color { + .r = 0, + .g = 0, + .b = 0, + .a = 255 + }; + + // TODO: can we embed this file? + const font: ?*c.TTF_Font = c.TTF_OpenFont("FreeSans.ttf", 12); + if (font == null) { + const err = c.TTF_GetError(); + c.SDL_Log("Unable to load font: %s", err); + return error.TTFFontLoadFailed; + } + + var file_paths = std.ArrayList([]const u8).init(allocator); + defer file_paths.deinit(); + try file_paths.append("GapProbeScan.cs"); + try file_paths.append("src/main.zig"); + // const file_name = "GapProbeScan.cs"; + // const source_code = @embedFile(file_name); + + var file_docmaps = std.ArrayList(FileDocMap).init(allocator); + defer file_docmaps.deinit(); + + for (file_paths.items) |path| { + const surface: [*c]c.SDL_Surface = c.TTF_RenderText_Solid(font, @ptrCast([*c]const u8, path), text_color); + if (surface == null) { + c.SDL_Log("Unable to render text"); + return error.RenderTextFailed; + } + + const texture: ?*c.SDL_Texture = c.SDL_CreateTextureFromSurface(renderer, surface); + if (texture == null) { + c.SDL_Log("Unable to create texture from surface"); + return error.CreateTextureFailed; + } + + var rect = c.SDL_Rect { + .x = 0, + .y = 0, + .w = surface.*.w, + .h = surface.*.h, + }; + + const file = try std.fs.cwd().openFile(path, .{ }); + defer file.close(); + + const stat = try file.stat(); + var buffer = try allocator.alloc(u8, stat.size); + + const bytes_read = try file.readAll(buffer); + if (bytes_read != stat.size) { + std.debug.print("bytes_read: {any}, stat.size: {any}\n", .{ + bytes_read, + stat.size, + }); + return error.FileReadError; + } + + var docmap = FileDocMap { + .title_text = DrawnText { + .surface = surface, + .texture = texture, + .rect = rect, + }, + .contents = buffer, + }; + + try file_docmaps.append(docmap); + } + defer { + for (file_docmaps.items) |docmap| { + c.SDL_FreeSurface(docmap.title_text.surface); + c.SDL_DestroyTexture(docmap.title_text.texture); + allocator.free(docmap.contents); + } + } + + const color_result: c_int = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); + if (color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", color_result); + return error.SDLInitializationFailed; + } + + // const surface = c.SDL_GetWindowSurface(screen); + + var quit = false; + while (!quit) { + var event: c.SDL_Event = undefined; + while (c.SDL_PollEvent(&event) != 0) { + switch (event.@"type") { + c.SDL_QUIT => { + quit = true; + }, + else => {}, + } + } + + const initial_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); + if (initial_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", initial_color_result); + return error.SDLInitializationFailed; + } + + var x: c_int = 0; + while (x < window_width) : (x += 1) { + var y: c_int = 0; + while (y < window_height) : (y += 1) { + const draw_result = c.SDL_RenderDrawPoint(renderer, x, y); + if (draw_result != 0) { + c.SDL_Log("Unable to draw point: %d", draw_result); + return error.SDLDrawingFailed; + } + } + } + + var i: usize = 0; + var column: c_int = 0; + x = 0; + var y: c_int = file_docmaps.items[0].title_text.rect.h; + // white: false, black: true + var color: bool = false; + while (i < file_docmaps.items[0].contents.len) : (i += 1) { + if (file_docmaps.items[0].contents[i] == 10) { + y += 1; + if (y > window_height) { + y = 0; + column += 1; + // std.debug.print("Column: {any}, x: {any}\n", .{column, column*column_width}); + } + x = column * column_width; + + continue; + } + + if (file_docmaps.items[0].contents[i] == 32 and color) { + color = false; + const white_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); + if (white_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", white_color_result); + return error.SDLInitializationFailed; + } + } else if (file_docmaps.items[0].contents[i] != 32 and !color) { + color = true; + const black_color_result = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); + if (black_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", black_color_result); + return error.SDLInitializationFailed; + } + } + + if (x < (column + 1) * column_width) { + const draw_result = c.SDL_RenderDrawPoint(renderer, x, y); + if (draw_result != 0) { + c.SDL_Log("Unable to draw point: %d", draw_result); + return error.SDLDrawingFailed; + } + } else { + const red_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 0, 0, 255); + if (red_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", red_color_result); + return error.SDLInitializationFailed; + } + + const draw_result = c.SDL_RenderDrawPoint(renderer, (column + 1) * column_width - 1, y); + if (draw_result != 0) { + c.SDL_Log("Unable to draw point: %d", draw_result); + return error.SDLDrawingFailed; + } + + if (!color) { + const white_color_result = c.SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); + if (white_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", white_color_result); + return error.SDLInitializationFailed; + } + } else { + const black_color_result = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); + if (black_color_result != 0) { + c.SDL_Log("Unable to set draw color: %d", black_color_result); + return error.SDLInitializationFailed; + } + } + } + + x += 1; + } + + const text = file_docmaps.items[0].title_text; + + // Display text + if (c.SDL_RenderCopy(renderer, text.texture, null, &(text.rect)) != 0) { + c.SDL_Log("Unable to render copy"); + } + + c.SDL_RenderPresent(renderer); + + c.SDL_Delay(17); + } +}