From 84efd2ac5ff30c559ef614f8a7fdc347491f9476 Mon Sep 17 00:00:00 2001 From: Mitchell Hashimoto Date: Sun, 27 Nov 2022 14:08:15 -0800 Subject: [PATCH] font: use Canvas more, Canvas rect --- src/font/sprite/Box.zig | 8 ++++++-- src/font/sprite/Canvas.zig | 38 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 44 insertions(+), 2 deletions(-) diff --git a/src/font/sprite/Box.zig b/src/font/sprite/Box.zig index ee59a5bf8..fd182dbc2 100644 --- a/src/font/sprite/Box.zig +++ b/src/font/sprite/Box.zig @@ -66,7 +66,7 @@ pub fn renderGlyph( defer canvas.deinit(alloc); // Perform the actual drawing - try self.draw(alloc, canvas.image, cp); + try self.draw(alloc, &canvas, cp); // Write the drawing to the atlas const region = try canvas.writeAtlas(alloc, atlas); @@ -87,7 +87,11 @@ pub fn renderGlyph( }; } -fn draw(self: Box, alloc: Allocator, img: *pixman.Image, cp: u32) !void { +fn draw(self: Box, alloc: Allocator, canvas: *font.sprite.Canvas, cp: u32) !void { + // We currently just draw directly to the pixman image, we should + // abstract drawing more and switch to that eventually. + const img = canvas.image; + switch (cp) { 0x2500 => self.draw_light_horizontal(img), 0x2501 => self.draw_heavy_horizontal(img), diff --git a/src/font/sprite/Canvas.zig b/src/font/sprite/Canvas.zig index 520615d57..05ef1e5a1 100644 --- a/src/font/sprite/Canvas.zig +++ b/src/font/sprite/Canvas.zig @@ -8,9 +8,32 @@ const Allocator = std.mem.Allocator; const pixman = @import("pixman"); const Atlas = @import("../../Atlas.zig"); +/// The underlying image. image: *pixman.Image, + +/// The raw data buffer. data: []u32, +pub const Rect = struct { + x: u32, + y: u32, + width: u32, + height: u32, +}; + +/// We only use alpha-channel so a pixel can only be "on" or "off". +pub const Color = enum { + on, + off, + + fn pixmanColor(self: Color) pixman.Color { + return switch (self) { + .on => .{ .red = 0xFFFF, .green = 0xFFFF, .blue = 0xFFFF, .alpha = 0xFFFF }, + .off => .{ .red = 0, .green = 0, .blue = 0, .alpha = 0 }, + }; + } +}; + pub fn init(alloc: Allocator, width: u32, height: u32) !Canvas { // Determine the config for our image buffer. The images we draw // for boxes are always 8bpp @@ -91,3 +114,18 @@ pub fn writeAtlas(self: *Canvas, alloc: Allocator, atlas: *Atlas) !Atlas.Region return region; } + +/// Draw and fill a rectangle. This is the main primitive for drawing +/// lines as well (which are just generally skinny rectangles...) +pub fn rect(self: *Canvas, v: Rect, color: pixman.Color) void { + const boxes = &[_]pixman.Box32{ + .{ + .x1 = @intCast(i32, v.x), + .y1 = @intCast(i32, v.y), + .x2 = @intCast(i32, v.width), + .y2 = @intCast(i32, v.height), + }, + }; + + self.image.fillBoxes(.src, color.pixmanColor(), boxes) catch {}; +}