widgets(terminal): send a redraw event

This commit is contained in:
Tim Culverhouse 2024-06-12 19:29:19 -05:00
parent 8f4ca5b830
commit f230f0c30a
2 changed files with 16 additions and 1 deletions

View file

@ -56,17 +56,21 @@ pub fn main() !void {
defer vt.deinit(); defer vt.deinit();
try vt.spawn(); try vt.spawn();
var redraw: bool = false;
while (true) { while (true) {
std.time.sleep(8 * std.time.ns_per_ms); std.time.sleep(8 * std.time.ns_per_ms);
// try vt events first // try vt events first
while (vt.tryEvent()) |event| { while (vt.tryEvent()) |event| {
redraw = true;
switch (event) { switch (event) {
.bell => {}, .bell => {},
.title_change => {}, .title_change => {},
.exited => return, .exited => return,
.redraw => {},
} }
} }
while (loop.tryEvent()) |event| { while (loop.tryEvent()) |event| {
redraw = true;
switch (event) { switch (event) {
.key_press => |key| { .key_press => |key| {
if (key.matches('c', .{ .ctrl = true })) return; if (key.matches('c', .{ .ctrl = true })) return;
@ -77,6 +81,8 @@ pub fn main() !void {
}, },
} }
} }
if (!redraw) continue;
redraw = false;
const win = vx.window(); const win = vx.window();
win.hideCursor(); win.hideCursor();

View file

@ -18,6 +18,7 @@ const key = @import("key.zig");
pub const Event = union(enum) { pub const Event = union(enum) {
exited, exited,
redraw,
bell, bell,
title_change, title_change,
}; };
@ -66,6 +67,8 @@ back_screen_alt: Screen,
// only applies to primary screen // only applies to primary screen
scroll_offset: usize = 0, scroll_offset: usize = 0,
back_mutex: std.Thread.Mutex = .{}, back_mutex: std.Thread.Mutex = .{},
// dirty is protected by back_mutex. Only access this field when you hold that mutex
dirty: bool = false,
unicode: *const vaxis.Unicode, unicode: *const vaxis.Unicode,
should_quit: bool = false, should_quit: bool = false,
@ -192,8 +195,10 @@ pub fn draw(self: *Terminal, win: vaxis.Window) !void {
defer self.back_mutex.unlock(); defer self.back_mutex.unlock();
// We keep this as a separate condition so we don't deadlock by obtaining the lock but not // We keep this as a separate condition so we don't deadlock by obtaining the lock but not
// having sync // having sync
if (!self.mode.sync) if (!self.mode.sync) {
try self.back_screen.copyTo(&self.front_screen); try self.back_screen.copyTo(&self.front_screen);
self.dirty = false;
}
} }
var row: usize = 0; var row: usize = 0;
@ -261,6 +266,10 @@ fn run(self: *Terminal) !void {
self.back_mutex.lock(); self.back_mutex.lock();
defer self.back_mutex.unlock(); defer self.back_mutex.unlock();
defer if (!self.dirty and self.event_queue.tryPush(.redraw)) {
self.dirty = true;
};
switch (event) { switch (event) {
.print => |str| { .print => |str| {
var iter = grapheme.Iterator.init(str, &self.unicode.grapheme_data); var iter = grapheme.Iterator.init(str, &self.unicode.grapheme_data);