From de8000f5960101d287ad0c838df3a1cf2bb59679 Mon Sep 17 00:00:00 2001
From: peony <peony@email.com>
Date: Sun, 13 Oct 2024 23:15:10 +0200
Subject: [PATCH] Fixed software renderer; added vline,hline,trirect

---
 sysdata/libraries/render/src/lib.hb           |  3 +
 sysdata/libraries/render/src/software.hb      | 58 ++++++++++++-
 .../src/examples/tactical_screen.hb           | 83 +++++++++++++++++++
 sysdata/programs/render_example/src/main.hb   |  2 +-
 sysdata/programs/tetris/src/main.hb           | 25 ++++--
 sysdata/system_config.toml                    |  4 +-
 6 files changed, 165 insertions(+), 10 deletions(-)
 create mode 100644 sysdata/programs/render_example/src/examples/tactical_screen.hb

diff --git a/sysdata/libraries/render/src/lib.hb b/sysdata/libraries/render/src/lib.hb
index 5c0baed..7300319 100644
--- a/sysdata/libraries/render/src/lib.hb
+++ b/sysdata/libraries/render/src/lib.hb
@@ -30,7 +30,10 @@ light_cyan := mode.light_cyan
 put_pixel := mode.put_pixel
 put_rect := mode.put_rect
 put_filled_rect := mode.put_filled_rect
+put_trirect := mode.put_trirect
 put_line := mode.put_line
+put_vline := mode.put_vline
+put_hline := mode.put_hline
 clear := mode.clear
 put_img := mode.put_img
 
diff --git a/sysdata/libraries/render/src/software.hb b/sysdata/libraries/render/src/software.hb
index a89057b..87b1bdb 100644
--- a/sysdata/libraries/render/src/software.hb
+++ b/sysdata/libraries/render/src/software.hb
@@ -119,7 +119,7 @@ sync := fn(): void {
 		bb := ctx.buf
 		fb := ctx.fb
 		boundary := bb + ctx.pixels
-		loop if bb == boundary break else {
+		loop if bb >= boundary break else {
 			*@as(^[Color; copy_pixels], @bitcast(fb)) = *@as(^[Color; copy_pixels], @bitcast(bb))
 			bb += copy_pixels
 			fb += copy_pixels
@@ -137,6 +137,9 @@ height := fn(): int {
 }
 
 screenidx := fn(x: int, y: int): int {
+	/*if x < 0 || y < 0 || x >= ctx.width || y >= ctx.height {
+		return -1
+	}*/
 	return x + ctx.width * y
 }
 
@@ -178,6 +181,27 @@ put_rect := fn(pos: Vec2(int), tr: Vec2(int), color: Color): void {
 	return
 }
 
+put_trirect := fn(pos: Vec2(int), size: Vec2(int), color0: Color, color1: Color): void {
+	step := Vec2(int).(1, 1)
+	if size.x < 0 {
+		step.x = -1
+	}
+	if size.y < 0 {
+		step.y = size.y / size.x
+	}
+
+	start_y := pos.y
+	target := pos + size
+
+	loop if pos.x == target.x break else {
+		put_vline(pos.x, pos.y, target.y, color0)
+		put_vline(pos.x, pos.y, start_y, color1)
+		pos += step
+	}
+
+	return
+}
+
 put_line_low := fn(p0: Vec2(int), p1: Vec2(int), color: Color): void {
 	dx := p1.x - p0.x
 	dy := p1.y - p0.y
@@ -243,6 +267,38 @@ put_line := fn(p0: Vec2(int), p1: Vec2(int), color: Color): void {
 	return
 }
 
+put_vline := fn(x: int, y0: int, y1: int, color: Color): void {
+	if y1 < y0 {
+		tmp := y0
+		y0 = y1
+		y1 = tmp
+	}
+	y := y0
+
+	loop if y == y1 break else {
+		*(ctx.buf + @inline(screenidx, x, y)) = color
+		y += 1
+	}
+
+	return
+}
+
+put_hline := fn(y: int, x0: int, x1: int, color: Color): void {
+	if x1 < x0 {
+		tmp := x0
+		x0 = x1
+		x1 = tmp
+	}
+	x := x0
+
+	loop if x == x1 break else {
+		*(ctx.buf + @inline(screenidx, x, y)) = color
+		x += 1
+	}
+
+	return
+}
+
 set_height := fn(new: int): void {
 	return
 }
diff --git a/sysdata/programs/render_example/src/examples/tactical_screen.hb b/sysdata/programs/render_example/src/examples/tactical_screen.hb
new file mode 100644
index 0000000..4f227de
--- /dev/null
+++ b/sysdata/programs/render_example/src/examples/tactical_screen.hb
@@ -0,0 +1,83 @@
+render := @use("../../../../libraries/render/src/lib.hb");
+.{math, random} := @use("../../../../libraries/stn/src/lib.hb")
+Vec2 := math.Vec2
+
+/* expected result:
+   a grid of green lines scrolling from the left top corner to the right bottom one
+   with a "target" randomly apperaing in one of them and a "seeker" "catching" it*/
+
+example := fn(): void {
+	render.init()
+
+	width := render.width()
+	height := render.height()
+	cell_size := 0
+	range := Vec2(int).(0, 0)
+	if width > height {
+		cell_size = width / 40
+		range = .(39, height / cell_size - 1)
+	} else {
+		cell_size = height / 40
+		range = .(width / cell_size - 1, 39)
+	}
+	width -= 1
+	height -= 1
+
+	scroll := 0
+	target := Vec2(int).(random.range(int, 0, range.x), random.range(int, 0, range.y))
+
+	halfcell := cell_size / 2
+	octcell := cell_size / 8
+	sevenoctcell := cell_size - octcell
+
+	seeker := Vec2(int).(random.range(int, 0, range.x), random.range(int, 0, range.y))
+
+	loop {
+		render.clear(render.black)
+
+		target_pixel_coord := target * .(cell_size, cell_size) + .(scroll, scroll)
+		render.put_trirect(target_pixel_coord, .(cell_size, cell_size), render.red, render.light_red)
+
+		render.put_hline(target_pixel_coord.y + halfcell, target_pixel_coord.x - octcell, target_pixel_coord.x - sevenoctcell, render.light_red)
+		render.put_hline(target_pixel_coord.y + halfcell, target_pixel_coord.x + cell_size + octcell, target_pixel_coord.x + cell_size + sevenoctcell, render.light_red)
+		render.put_vline(target_pixel_coord.x + halfcell, target_pixel_coord.y - octcell, target_pixel_coord.y - sevenoctcell, render.light_red)
+		render.put_vline(target_pixel_coord.x + halfcell, target_pixel_coord.y + cell_size + octcell, target_pixel_coord.y + cell_size + sevenoctcell, render.light_red)
+
+		x := scroll
+		loop if x > width break else {
+			render.put_vline(x, 0, height, .(0, 127, 0, 127))
+			x += cell_size
+		}
+
+		y := scroll
+		loop if y > height break else {
+			render.put_hline(y, 0, width, .(0, 127, 0, 127))
+			y += cell_size
+		}
+
+		render.put_hline(seeker.y * cell_size + halfcell + scroll, 0, width, render.light_green)
+		render.put_vline(seeker.x * cell_size + halfcell + scroll, 0, height, render.light_green)
+
+		render.sync()
+
+		if seeker.x < target.x {
+			seeker.x += 1
+		} else if seeker.x > target.x {
+			seeker.x -= 1
+		} else if seeker.y < target.y {
+			seeker.y += 1
+		} else if seeker.y > target.y {
+			seeker.y -= 1
+		} else {
+			target = .(random.range(int, 0, range.x), random.range(int, 0, range.y))
+		}
+
+		scroll += 1
+		if scroll > cell_size {
+			scroll = 0
+			target += .(1, 1)
+			seeker += .(1, 1)
+		}
+	}
+	return
+}
\ No newline at end of file
diff --git a/sysdata/programs/render_example/src/main.hb b/sysdata/programs/render_example/src/main.hb
index 35b2706..5d15c24 100644
--- a/sysdata/programs/render_example/src/main.hb
+++ b/sysdata/programs/render_example/src/main.hb
@@ -1,4 +1,4 @@
-.{example} := @use("./examples/amogus.hb")
+.{example} := @use("./examples/tactical_screen.hb")
 
 main := fn(): void {
 	@inline(example)
diff --git a/sysdata/programs/tetris/src/main.hb b/sysdata/programs/tetris/src/main.hb
index e61324b..65aebf3 100644
--- a/sysdata/programs/tetris/src/main.hb
+++ b/sysdata/programs/tetris/src/main.hb
@@ -1,14 +1,27 @@
-.{memory, log, string, buffer} := @use("../../../libraries/stn/src/lib.hb")
+.{memory, log, string, buffer, math} := @use("../../../libraries/stn/src/lib.hb")
+render := @use("../../../libraries/render/src/lib.hb")
+Color := render.Color
+Vec2 := math.Vec2
 
 main := fn(): void {
-	storage := @as(u8, 0)
+	input := @as(u8, 0)
 	output_buffer := memory.request_page(1)
 	input_buffer := buffer.search("XKeyboard\0")
+
+	render.init()
+
 	loop {
-		buffer.recv(input_buffer, &storage, 1)
-		if storage != 0 {
-			log.info(string.display_int(storage, output_buffer))
-			storage = 0
+		render.clear(render.black)
+		render.put_vline(100, 255, 128, Color.(255, 255, 255, 255))
+		render.put_hline(64, 100 - 64, 164, Color.(255, 255, 255, 255))
+		render.put_trirect(Vec2(int).(128, 128 + 256), Vec2(int).(256, -256), Color.(147, 147, 147, 255), Color.(107, 107, 107, 255))
+		render.put_filled_rect(Vec2(int).(128 + 32, 128 + 32), Vec2(int).(256 - 64, 256 - 64), Color.(127, 127, 127, 127))
+		render.sync()
+
+		buffer.recv(input_buffer, &input, 1)
+		if input != 0 {
+			log.info(string.display_int(input, output_buffer))
+			input = 0
 		}
 	}
 	return
diff --git a/sysdata/system_config.toml b/sysdata/system_config.toml
index e4bd86f..48aa105 100644
--- a/sysdata/system_config.toml
+++ b/sysdata/system_config.toml
@@ -3,7 +3,7 @@
 default_entry = 1
 timeout = 0
 verbose = false
-interface_resolution = "1024x768x24"
+interface_resolution = "1600x900x24"
 # interface_resolution = "640x480x32"
 # Terminal related settings
 term_wallpaper = "boot:///background.bmp"
@@ -16,7 +16,7 @@ protocol = "limine"
 kernel_path = "boot:///kernel_${ARCH}"
 kernel_cmdline = ""
 # resolution = "640x480x32"
-resolution = "1024x768x24"
+resolution = "1600x900x24"
 
 [boot.limine.ableos.modules]