From 987a85da27c3f40b28513f74029303fd08c19459 Mon Sep 17 00:00:00 2001 From: Daniel Hammer Date: Fri, 20 Feb 2026 00:48:51 +0100 Subject: [PATCH] feat: rudimentary userspace desktop environment --- kernel/src/Api/Syscall.cpp | 196 ++++- kernel/src/Api/Syscall.hpp | 16 +- kernel/src/Sched/Scheduler.cpp | 36 + kernel/src/Sched/Scheduler.hpp | 22 + kernel/src/Timekeeping/ApicTimer.cpp | 6 +- programs/GNUmakefile | 15 +- programs/include/Api/Syscall.hpp | 15 + programs/include/gui/desktop.hpp | 55 ++ programs/include/gui/draw.hpp | 239 +++++ programs/include/gui/font.hpp | 63 ++ programs/include/gui/framebuffer.hpp | 196 +++++ programs/include/gui/gui.hpp | 92 ++ programs/include/gui/svg.hpp | 972 +++++++++++++++++++++ programs/include/gui/terminal.hpp | 526 +++++++++++ programs/include/gui/widgets.hpp | 354 ++++++++ programs/include/gui/window.hpp | 78 ++ programs/include/zenith/syscall.h | 23 + programs/obj/hello/main.o | Bin 9168 -> 9568 bytes programs/obj/shell/main.o | Bin 121376 -> 135952 bytes programs/src/desktop/Makefile | 86 ++ programs/src/desktop/font_data.cpp | 783 +++++++++++++++++ programs/src/desktop/main.cpp | 1208 ++++++++++++++++++++++++++ programs/src/desktop/obj/font_data.o | Bin 0 -> 13744 bytes programs/src/desktop/obj/main.o | Bin 0 -> 788080 bytes programs/src/init/main.cpp | 7 +- scripts/copy_icons.sh | 48 + 26 files changed, 5027 insertions(+), 9 deletions(-) create mode 100644 programs/include/gui/desktop.hpp create mode 100644 programs/include/gui/draw.hpp create mode 100644 programs/include/gui/font.hpp create mode 100644 programs/include/gui/framebuffer.hpp create mode 100644 programs/include/gui/gui.hpp create mode 100644 programs/include/gui/svg.hpp create mode 100644 programs/include/gui/terminal.hpp create mode 100644 programs/include/gui/widgets.hpp create mode 100644 programs/include/gui/window.hpp create mode 100644 programs/src/desktop/Makefile create mode 100644 programs/src/desktop/font_data.cpp create mode 100644 programs/src/desktop/main.cpp create mode 100644 programs/src/desktop/obj/font_data.o create mode 100644 programs/src/desktop/obj/main.o create mode 100755 scripts/copy_icons.sh diff --git a/kernel/src/Api/Syscall.cpp b/kernel/src/Api/Syscall.cpp index c406057..73df553 100644 --- a/kernel/src/Api/Syscall.cpp +++ b/kernel/src/Api/Syscall.cpp @@ -17,6 +17,7 @@ #include #include #include +#include #include #include #include @@ -53,11 +54,53 @@ namespace Zenith { return Sched::GetCurrentPid(); } + static void RingWrite(uint8_t* buf, uint32_t& head, uint32_t /*tail*/, uint32_t size, uint8_t byte) { + buf[head] = byte; + head = (head + 1) % size; + } + + static int RingRead(uint8_t* buf, uint32_t& head, uint32_t& tail, uint32_t size, uint8_t* out, int maxLen) { + int count = 0; + while (tail != head && count < maxLen) { + out[count++] = buf[tail]; + tail = (tail + 1) % size; + } + return count; + } + + // Find the process that owns the I/O ring buffers for a redirected process. + // If proc owns buffers itself (spawned via spawn_redir), returns proc. + // If proc inherited redirection (spawned via spawn from a redirected parent), + // follows parentPid to find the buffer owner. + static Sched::Process* GetRedirTarget(Sched::Process* proc) { + if (!proc || !proc->redirected) return nullptr; + if (proc->outBuf) return proc; // owns buffers + return Sched::GetProcessByPid(proc->parentPid); + } + static void Sys_Print(const char* text) { + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target && target->outBuf) { + for (int i = 0; text[i]; i++) { + RingWrite(target->outBuf, target->outHead, target->outTail, Sched::Process::IoBufSize, (uint8_t)text[i]); + } + return; + } + } Kt::Print(text); } static void Sys_Putchar(char c) { + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target && target->outBuf) { + RingWrite(target->outBuf, target->outHead, target->outTail, Sched::Process::IoBufSize, (uint8_t)c); + return; + } + } Kt::Putchar(c); } @@ -162,11 +205,29 @@ namespace Zenith { } static bool Sys_IsKeyAvailable() { + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target) return target->keyHead != target->keyTail; + } return Drivers::PS2::Keyboard::IsKeyAvailable(); } static void Sys_GetKey(KeyEvent* outEvent) { if (outEvent == nullptr) return; + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target) { + // Wait for key in target's keyBuf ring + while (target->keyHead == target->keyTail) { + Sched::Schedule(); + } + *outEvent = target->keyBuf[target->keyTail]; + target->keyTail = (target->keyTail + 1) % 64; + return; + } + } auto k = Drivers::PS2::Keyboard::GetKey(); outEvent->scancode = k.Scancode; outEvent->ascii = k.Ascii; @@ -177,6 +238,19 @@ namespace Zenith { } static char Sys_GetChar() { + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target && target->inBuf) { + // Wait for data in target's inBuf ring + while (target->inTail == target->inHead) { + Sched::Schedule(); // yield until parent writes + } + uint8_t c = target->inBuf[target->inTail]; + target->inTail = (target->inTail + 1) % Sched::Process::IoBufSize; + return (char)c; + } + } return Drivers::PS2::Keyboard::GetChar(); } @@ -249,7 +323,26 @@ namespace Zenith { } static int Sys_Spawn(const char* path, const char* args) { - return Sched::Spawn(path, args); + auto* parent = Sched::GetCurrentProcessPtr(); + int childPid = Sched::Spawn(path, args); + if (childPid < 0) return childPid; + + // Inherit I/O redirection: if the parent is redirected, the child + // is marked redirected too. It stores a parentPid pointing to the + // process that owns the actual ring buffers (the one spawned via + // spawn_redir). The child does NOT get its own buffers — Sys_Print + // et al. look up the buffer owner at write time. + if (parent && parent->redirected) { + auto* child = Sched::GetProcessByPid(childPid); + if (child) { + child->redirected = true; + // Point to the buffer owner: if parent owns buffers, target parent; + // if parent itself inherited, follow the chain. + child->parentPid = parent->outBuf ? parent->pid : parent->parentPid; + } + } + + return childPid; } static int Sys_GetArgs(char* buf, uint64_t maxLen) { @@ -264,6 +357,14 @@ namespace Zenith { } static uint64_t Sys_TermSize() { + // If the process is redirected to a GUI terminal, return those dimensions + auto* proc = Sched::GetCurrentProcessPtr(); + if (proc && proc->redirected) { + auto* target = GetRedirTarget(proc); + if (target && target->termCols > 0 && target->termRows > 0) { + return ((uint64_t)target->termRows << 32) | ((uint64_t)target->termCols & 0xFFFFFFFF); + } + } size_t cols = 0, rows = 0; flanterm_get_dimensions(Kt::ctx, &cols, &rows); return (rows << 32) | (cols & 0xFFFFFFFF); @@ -429,6 +530,81 @@ namespace Zenith { return (int64_t)len; } + // ---- Mouse syscalls ---- + + static void Sys_MouseState(MouseState* out) { + if (out == nullptr) return; + auto state = Drivers::PS2::Mouse::GetMouseState(); + out->x = state.X; + out->y = state.Y; + out->scrollDelta = state.ScrollDelta; + out->buttons = state.Buttons; + } + + static void Sys_SetMouseBounds(int32_t maxX, int32_t maxY) { + Drivers::PS2::Mouse::SetBounds(maxX, maxY); + } + + // ---- I/O redirection syscalls ---- + + static int Sys_SpawnRedir(const char* path, const char* args) { + int childPid = Sched::Spawn(path, args); + if (childPid < 0) return -1; + + auto* child = Sched::GetProcessByPid(childPid); + if (child == nullptr) return -1; + + // Allocate ring buffers + void* outPage = Memory::g_pfa->AllocateZeroed(); + void* inPage = Memory::g_pfa->AllocateZeroed(); + if (!outPage || !inPage) return -1; + + child->outBuf = (uint8_t*)outPage; + child->inBuf = (uint8_t*)inPage; + child->outHead = 0; + child->outTail = 0; + child->inHead = 0; + child->inTail = 0; + child->keyHead = 0; + child->keyTail = 0; + child->redirected = true; + child->parentPid = Sched::GetCurrentPid(); + + return childPid; + } + + static int Sys_ChildIoRead(int childPid, char* buf, int maxLen) { + auto* child = Sched::GetProcessByPid(childPid); + if (child == nullptr || !child->redirected || !child->outBuf) return -1; + return RingRead(child->outBuf, child->outHead, child->outTail, Sched::Process::IoBufSize, (uint8_t*)buf, maxLen); + } + + static int Sys_ChildIoWrite(int childPid, const char* data, int len) { + auto* child = Sched::GetProcessByPid(childPid); + if (child == nullptr || !child->redirected || !child->inBuf) return -1; + for (int i = 0; i < len; i++) { + RingWrite(child->inBuf, child->inHead, child->inTail, Sched::Process::IoBufSize, (uint8_t)data[i]); + } + return len; + } + + static int Sys_ChildIoWriteKey(int childPid, const KeyEvent* key) { + if (key == nullptr) return -1; + auto* child = Sched::GetProcessByPid(childPid); + if (child == nullptr || !child->redirected) return -1; + child->keyBuf[child->keyHead] = *key; + child->keyHead = (child->keyHead + 1) % 64; + return 0; + } + + static int Sys_ChildIoSetTermsz(int childPid, int cols, int rows) { + auto* child = Sched::GetProcessByPid(childPid); + if (child == nullptr || !child->redirected) return -1; + child->termCols = cols; + child->termRows = rows; + return 0; + } + // ---- Dispatch ---- extern "C" int64_t SyscallDispatch(SyscallFrame* frame) { @@ -551,6 +727,22 @@ namespace Zenith { return Sys_GetRandom((uint8_t*)frame->arg1, frame->arg2); case SYS_KLOG: return Kt::ReadKernelLog((char*)frame->arg1, frame->arg2); + case SYS_MOUSESTATE: + Sys_MouseState((MouseState*)frame->arg1); + return 0; + case SYS_SETMOUSEBOUNDS: + Sys_SetMouseBounds((int32_t)frame->arg1, (int32_t)frame->arg2); + return 0; + case SYS_SPAWN_REDIR: + return (int64_t)Sys_SpawnRedir((const char*)frame->arg1, (const char*)frame->arg2); + case SYS_CHILDIO_READ: + return (int64_t)Sys_ChildIoRead((int)frame->arg1, (char*)frame->arg2, (int)frame->arg3); + case SYS_CHILDIO_WRITE: + return (int64_t)Sys_ChildIoWrite((int)frame->arg1, (const char*)frame->arg2, (int)frame->arg3); + case SYS_CHILDIO_WRITEKEY: + return (int64_t)Sys_ChildIoWriteKey((int)frame->arg1, (const KeyEvent*)frame->arg2); + case SYS_CHILDIO_SETTERMSZ: + return (int64_t)Sys_ChildIoSetTermsz((int)frame->arg1, (int)frame->arg2, (int)frame->arg3); default: return -1; } @@ -577,7 +769,7 @@ namespace Zenith { Hal::WriteMSR(Hal::IA32_FMASK, 0x200); Kt::KernelLogStream(Kt::OK, "Syscall") << "SYSCALL/SYSRET initialized (LSTAR=" - << kcp::hex << (uint64_t)SyscallEntry << kcp::dec << ", 47 syscalls)"; + << kcp::hex << (uint64_t)SyscallEntry << kcp::dec << ", 53 syscalls)"; } } diff --git a/kernel/src/Api/Syscall.hpp b/kernel/src/Api/Syscall.hpp index 14aadbe..13e9026 100644 --- a/kernel/src/Api/Syscall.hpp +++ b/kernel/src/Api/Syscall.hpp @@ -57,7 +57,14 @@ namespace Zenith { static constexpr uint64_t SYS_TERMSCALE = 43; static constexpr uint64_t SYS_RESOLVE = 44; static constexpr uint64_t SYS_GETRANDOM = 45; - static constexpr uint64_t SYS_KLOG = 46; + static constexpr uint64_t SYS_KLOG = 46; + static constexpr uint64_t SYS_MOUSESTATE = 47; + static constexpr uint64_t SYS_SETMOUSEBOUNDS = 48; + static constexpr uint64_t SYS_SPAWN_REDIR = 49; + static constexpr uint64_t SYS_CHILDIO_READ = 50; + static constexpr uint64_t SYS_CHILDIO_WRITE = 51; + static constexpr uint64_t SYS_CHILDIO_WRITEKEY = 52; + static constexpr uint64_t SYS_CHILDIO_SETTERMSZ = 53; static constexpr int SOCK_TCP = 1; static constexpr int SOCK_UDP = 2; @@ -104,6 +111,13 @@ namespace Zenith { bool alt; }; + struct MouseState { + int32_t x; + int32_t y; + int32_t scrollDelta; + uint8_t buttons; + }; + // Stack frame pushed by SyscallEntry.asm struct SyscallFrame { uint64_t r15, r14, r13, r12, rbp, rbx; // callee-saved diff --git a/kernel/src/Sched/Scheduler.cpp b/kernel/src/Sched/Scheduler.cpp index 865b58a..7b2de94 100644 --- a/kernel/src/Sched/Scheduler.cpp +++ b/kernel/src/Sched/Scheduler.cpp @@ -76,6 +76,18 @@ namespace Sched { processTable[i].userStackTop = 0; processTable[i].heapNext = 0; processTable[i].args[0] = '\0'; + processTable[i].redirected = false; + processTable[i].parentPid = -1; + processTable[i].outBuf = nullptr; + processTable[i].outHead = 0; + processTable[i].outTail = 0; + processTable[i].inBuf = nullptr; + processTable[i].inHead = 0; + processTable[i].inTail = 0; + processTable[i].keyHead = 0; + processTable[i].keyTail = 0; + processTable[i].termCols = 0; + processTable[i].termRows = 0; } currentPid = -1; @@ -199,6 +211,19 @@ namespace Sched { proc.args[i] = '\0'; } + proc.redirected = false; + proc.parentPid = -1; + proc.outBuf = nullptr; + proc.outHead = 0; + proc.outTail = 0; + proc.inBuf = nullptr; + proc.inHead = 0; + proc.inTail = 0; + proc.keyHead = 0; + proc.keyTail = 0; + proc.termCols = 0; + proc.termRows = 0; + return proc.pid; } @@ -326,4 +351,15 @@ namespace Sched { return false; } + Process* GetProcessByPid(int pid) { + for (int i = 0; i < MaxProcesses; i++) { + if (processTable[i].pid == pid && + (processTable[i].state == ProcessState::Ready || + processTable[i].state == ProcessState::Running)) { + return &processTable[i]; + } + } + return nullptr; + } + } diff --git a/kernel/src/Sched/Scheduler.hpp b/kernel/src/Sched/Scheduler.hpp index d617953..04b35d9 100644 --- a/kernel/src/Sched/Scheduler.hpp +++ b/kernel/src/Sched/Scheduler.hpp @@ -6,6 +6,7 @@ #pragma once #include +#include namespace Sched { @@ -39,6 +40,24 @@ namespace Sched { uint64_t userStackTop; // User-space stack top uint64_t heapNext; // Simple bump allocator for user heap char args[256]; // Command-line arguments (set by parent via Spawn) + + // I/O redirection for GUI terminal + bool redirected = false; + int parentPid = -1; + uint8_t* outBuf = nullptr; // 4KB ring: child writes (print/putchar), parent reads + uint32_t outHead = 0; + uint32_t outTail = 0; + uint8_t* inBuf = nullptr; // 4KB ring: parent writes, child reads (getchar) + uint32_t inHead = 0; + uint32_t inTail = 0; + Zenith::KeyEvent keyBuf[64]; // parent injects, child reads (getkey/iskeyavailable) + uint32_t keyHead = 0; + uint32_t keyTail = 0; + static constexpr uint32_t IoBufSize = 4096; + + // GUI terminal dimensions (set by desktop, read by SYS_TERMSIZE) + int termCols = 0; + int termRows = 0; }; void Initialize(); @@ -60,4 +79,7 @@ namespace Sched { // Check if a process is still alive (Ready or Running) bool IsAlive(int pid); + // Find a process by PID (returns nullptr if not found or not alive) + Process* GetProcessByPid(int pid); + } diff --git a/kernel/src/Timekeeping/ApicTimer.cpp b/kernel/src/Timekeeping/ApicTimer.cpp index 3ccb57e..70e7350 100644 --- a/kernel/src/Timekeeping/ApicTimer.cpp +++ b/kernel/src/Timekeeping/ApicTimer.cpp @@ -149,7 +149,11 @@ namespace Timekeeping { void Sleep(uint64_t ms) { uint64_t target = g_tickCount + ms; while (g_tickCount < target) { - asm volatile("hlt"); + // Yield to other processes instead of hlt. Using hlt here causes + // a deadlock: if the timer ISR preempts us during hlt and context- + // switches away (via Tick → Schedule), EOI is never sent, so no + // more timer interrupts fire and any process doing hlt freezes. + Sched::Schedule(); } } }; diff --git a/programs/GNUmakefile b/programs/GNUmakefile index 7505807..0d8ecc1 100644 --- a/programs/GNUmakefile +++ b/programs/GNUmakefile @@ -57,7 +57,7 @@ BINDIR := bin PROGRAMS := $(notdir $(wildcard src/*)) # Programs with custom Makefiles (built separately). -CUSTOM_BUILDS := doom fetch wiki +CUSTOM_BUILDS := doom fetch wiki desktop SYSTEM_PROGRAMS := $(filter-out $(CUSTOM_BUILDS),$(PROGRAMS)) # Build targets: system programs go to bin/os/, games are handled separately. @@ -82,9 +82,9 @@ CA_CERTS := $(BINDIR)/etc/ca-certificates.crt # Home directory placeholder. HOMEKEEP := $(BINDIR)/home/.keep -.PHONY: all clean doom fetch wiki bearssl libc +.PHONY: all clean doom fetch wiki desktop icons bearssl libc -all: bearssl libc $(TARGETS) fetch wiki doom $(GAME_DATA) $(MANDST) $(WWWDST) $(CA_CERTS) $(HOMEKEEP) +all: bearssl libc $(TARGETS) fetch wiki doom desktop icons $(GAME_DATA) $(MANDST) $(WWWDST) $(CA_CERTS) $(HOMEKEEP) # Build BearSSL static library. bearssl: @@ -102,6 +102,14 @@ fetch: bearssl libc wiki: bearssl libc $(MAKE) -C src/wiki +# Build desktop via its own Makefile. +desktop: + $(MAKE) -C src/desktop + +# Copy SVG icons for the desktop into bin/icons/. +icons: + ../scripts/copy_icons.sh + # Build doom via its own Makefile. doom: $(MAKE) -C src/doom @@ -143,3 +151,4 @@ clean: $(MAKE) -C lib/libc clean $(MAKE) -C src/fetch clean $(MAKE) -C src/doom clean + $(MAKE) -C src/desktop clean diff --git a/programs/include/Api/Syscall.hpp b/programs/include/Api/Syscall.hpp index 9c00699..7ff7a20 100644 --- a/programs/include/Api/Syscall.hpp +++ b/programs/include/Api/Syscall.hpp @@ -57,6 +57,14 @@ namespace Zenith { static constexpr uint64_t SYS_TERMSCALE = 43; static constexpr uint64_t SYS_RESOLVE = 44; static constexpr uint64_t SYS_GETRANDOM = 45; + static constexpr uint64_t SYS_KLOG = 46; + static constexpr uint64_t SYS_MOUSESTATE = 47; + static constexpr uint64_t SYS_SETMOUSEBOUNDS = 48; + static constexpr uint64_t SYS_SPAWN_REDIR = 49; + static constexpr uint64_t SYS_CHILDIO_READ = 50; + static constexpr uint64_t SYS_CHILDIO_WRITE = 51; + static constexpr uint64_t SYS_CHILDIO_WRITEKEY = 52; + static constexpr uint64_t SYS_CHILDIO_SETTERMSZ = 53; static constexpr int SOCK_TCP = 1; static constexpr int SOCK_UDP = 2; @@ -103,4 +111,11 @@ namespace Zenith { bool alt; }; + struct MouseState { + int32_t x; + int32_t y; + int32_t scrollDelta; + uint8_t buttons; + }; + } diff --git a/programs/include/gui/desktop.hpp b/programs/include/gui/desktop.hpp new file mode 100644 index 0000000..809bf3c --- /dev/null +++ b/programs/include/gui/desktop.hpp @@ -0,0 +1,55 @@ +/* + * desktop.hpp + * ZenithOS desktop state and compositor declarations + * Copyright (c) 2026 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/framebuffer.hpp" +#include "gui/svg.hpp" +#include "gui/window.hpp" +#include "gui/widgets.hpp" +#include "gui/terminal.hpp" +#include + +namespace gui { + +static constexpr int MAX_WINDOWS = 8; +static constexpr int PANEL_HEIGHT = 32; + +struct DesktopState { + Framebuffer fb; + Window windows[MAX_WINDOWS]; + int window_count; + int focused_window; + + Zenith::MouseState mouse; + uint8_t prev_buttons; + + bool app_menu_open; + + SvgIcon icon_terminal; + SvgIcon icon_filemanager; + SvgIcon icon_sysinfo; + SvgIcon icon_appmenu; + SvgIcon icon_folder; + SvgIcon icon_file; + SvgIcon icon_computer; + + int screen_w, screen_h; +}; + +// Forward declarations - implemented in main.cpp +void desktop_init(DesktopState* ds); +void desktop_run(DesktopState* ds); +void desktop_compose(DesktopState* ds); +int desktop_create_window(DesktopState* ds, const char* title, int x, int y, int w, int h); +void desktop_close_window(DesktopState* ds, int idx); +void desktop_raise_window(DesktopState* ds, int idx); +void desktop_draw_panel(DesktopState* ds); +void desktop_draw_window(DesktopState* ds, int idx); +void desktop_handle_mouse(DesktopState* ds); +void desktop_handle_keyboard(DesktopState* ds, const Zenith::KeyEvent& key); + +} // namespace gui diff --git a/programs/include/gui/draw.hpp b/programs/include/gui/draw.hpp new file mode 100644 index 0000000..1362ed6 --- /dev/null +++ b/programs/include/gui/draw.hpp @@ -0,0 +1,239 @@ +/* + * draw.hpp + * ZenithOS drawing primitives (lines, circles, rounded rects, cursor) + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/framebuffer.hpp" + +namespace gui { + +// Fast horizontal line +inline void draw_hline(Framebuffer& fb, int x, int y, int w, Color c) { + for (int i = 0; i < w; i++) fb.put_pixel(x + i, y, c); +} + +// Fast vertical line +inline void draw_vline(Framebuffer& fb, int x, int y, int h, Color c) { + for (int i = 0; i < h; i++) fb.put_pixel(x, y + i, c); +} + +// Rectangle outline +inline void draw_rect(Framebuffer& fb, int x, int y, int w, int h, Color c) { + draw_hline(fb, x, y, w, c); + draw_hline(fb, x, y + h - 1, w, c); + draw_vline(fb, x, y, h, c); + draw_vline(fb, x + w - 1, y, h, c); +} + +// Filled rounded rectangle using corner circles +inline void fill_rounded_rect(Framebuffer& fb, int x, int y, int w, int h, int radius, Color c) { + if (radius <= 0) { + fb.fill_rect(x, y, w, h, c); + return; + } + + // Clamp radius to half the smaller dimension + int max_r = gui_min(w / 2, h / 2); + if (radius > max_r) radius = max_r; + + // Fill the center rectangle + fb.fill_rect(x + radius, y, w - 2 * radius, h, c); + // Fill the left and right strips (excluding corners) + fb.fill_rect(x, y + radius, radius, h - 2 * radius, c); + fb.fill_rect(x + w - radius, y + radius, radius, h - 2 * radius, c); + + // Draw the four rounded corners using midpoint circle + int cx_tl = x + radius; + int cy_tl = y + radius; + int cx_tr = x + w - radius - 1; + int cy_tr = y + radius; + int cx_bl = x + radius; + int cy_bl = y + h - radius - 1; + int cx_br = x + w - radius - 1; + int cy_br = y + h - radius - 1; + + int px = 0; + int py = radius; + int d = 1 - radius; + + while (px <= py) { + // Top-left corner + draw_hline(fb, cx_tl - py, cy_tl - px, py - radius + radius, c); + draw_hline(fb, cx_tl - px, cy_tl - py, px, c); + + // Top-right corner + draw_hline(fb, cx_tr + 1, cy_tr - px, py, c); + draw_hline(fb, cx_tr + 1, cy_tr - py, px, c); + + // Bottom-left corner + draw_hline(fb, cx_bl - py, cy_bl + px, py, c); + draw_hline(fb, cx_bl - px, cy_bl + py, px, c); + + // Bottom-right corner + draw_hline(fb, cx_br + 1, cy_br + px, py, c); + draw_hline(fb, cx_br + 1, cy_br + py, px, c); + + if (d < 0) { + d += 2 * px + 3; + } else { + d += 2 * (px - py) + 5; + py--; + } + px++; + } +} + +// Filled circle (midpoint algorithm) +inline void fill_circle(Framebuffer& fb, int cx, int cy, int r, Color c) { + if (r <= 0) return; + + int x = 0; + int y = r; + int d = 1 - r; + + // Draw initial horizontal lines + draw_hline(fb, cx - r, cy, 2 * r + 1, c); + + while (x < y) { + if (d < 0) { + d += 2 * x + 3; + } else { + d += 2 * (x - y) + 5; + y--; + draw_hline(fb, cx - x, cy + y + 1, 2 * x + 1, c); + draw_hline(fb, cx - x, cy - y - 1, 2 * x + 1, c); + } + x++; + draw_hline(fb, cx - y, cy + x, 2 * y + 1, c); + draw_hline(fb, cx - y, cy - x, 2 * y + 1, c); + } +} + +// Circle outline (midpoint algorithm) +inline void draw_circle(Framebuffer& fb, int cx, int cy, int r, Color c) { + if (r <= 0) { + fb.put_pixel(cx, cy, c); + return; + } + + int x = 0; + int y = r; + int d = 1 - r; + + while (x <= y) { + fb.put_pixel(cx + x, cy + y, c); + fb.put_pixel(cx - x, cy + y, c); + fb.put_pixel(cx + x, cy - y, c); + fb.put_pixel(cx - x, cy - y, c); + fb.put_pixel(cx + y, cy + x, c); + fb.put_pixel(cx - y, cy + x, c); + fb.put_pixel(cx + y, cy - x, c); + fb.put_pixel(cx - y, cy - x, c); + + if (d < 0) { + d += 2 * x + 3; + } else { + d += 2 * (x - y) + 5; + y--; + } + x++; + } +} + +// Bresenham line drawing +inline void draw_line(Framebuffer& fb, int x0, int y0, int x1, int y1, Color c) { + int dx = gui_abs(x1 - x0); + int dy = gui_abs(y1 - y0); + int sx = x0 < x1 ? 1 : -1; + int sy = y0 < y1 ? 1 : -1; + int err = dx - dy; + + for (;;) { + fb.put_pixel(x0, y0, c); + if (x0 == x1 && y0 == y1) break; + int e2 = 2 * err; + if (e2 > -dy) { + err -= dy; + x0 += sx; + } + if (e2 < dx) { + err += dx; + y0 += sy; + } + } +} + +// Drop shadow: offset darker rectangles below/right +inline void draw_shadow(Framebuffer& fb, int x, int y, int w, int h, int offset, Color shadow_color) { + // Bottom shadow strip + fb.fill_rect_alpha(x + offset, y + h, w, offset, shadow_color); + // Right shadow strip + fb.fill_rect_alpha(x + w, y + offset, offset, h, shadow_color); + // Corner + fb.fill_rect_alpha(x + w, y + h, offset, offset, shadow_color); +} + +// 16x16 mouse cursor bitmaps +// Outline (black, where design has '1') +static constexpr uint16_t cursor_outline[16] = { + 0x8000, // 1000000000000000 + 0xC000, // 1100000000000000 + 0xA000, // 1010000000000000 + 0x9000, // 1001000000000000 + 0x8800, // 1000100000000000 + 0x8400, // 1000010000000000 + 0x8200, // 1000001000000000 + 0x8100, // 1000000100000000 + 0x8080, // 1000000010000000 + 0x8040, // 1000000001000000 + 0x8780, // 1000011110000000 (changed: row 10 = 1 2 2 2 2 2 1 1 1 1) + 0x9200, // 1001001000000000 (row 11 = 1 2 2 1 2 2 1) + 0xA900, // 1010100100000000 (row 12 = 1 2 1 0 1 2 2 1) + 0xC900, // 1100100100000000 (row 13 = 1 1 0 0 1 2 2 1) + 0x8480, // 1000010010000000 (row 14 = 1 0 0 0 0 1 2 2 1) + 0x0700, // 0000011100000000 (row 15 = 0 0 0 0 0 1 1 1) +}; + +// Fill (white, where design has '2') +static constexpr uint16_t cursor_fill[16] = { + 0x0000, // row 0: no fill + 0x0000, // row 1: no fill + 0x4000, // row 2: 0100000000000000 + 0x6000, // row 3: 0110000000000000 + 0x7000, // row 4: 0111000000000000 + 0x7800, // row 5: 0111100000000000 + 0x7C00, // row 6: 0111110000000000 + 0x7E00, // row 7: 0111111000000000 + 0x7F00, // row 8: 0111111100000000 + 0x7F80, // row 9: 0111111110000000 + 0x7800, // row 10: 0111100000000000 (fill only in positions 1-5) + 0x6C00, // row 11: 0110110000000000 (fill at positions 1,2 and 4,5) + 0x4600, // row 12: 0100011000000000 (fill at position 1 and 5,6) + 0x0600, // row 13: 0000011000000000 (fill at positions 5,6) + 0x0300, // row 14: 0000001100000000 (fill at positions 6,7) + 0x0000, // row 15: no fill +}; + +// Draw the mouse cursor at (x, y) +inline void draw_cursor(Framebuffer& fb, int x, int y) { + Color black = colors::BLACK; + Color white = colors::WHITE; + + for (int row = 0; row < 16; row++) { + uint16_t outline = cursor_outline[row]; + uint16_t fill = cursor_fill[row]; + for (int col = 0; col < 16; col++) { + uint16_t mask = (uint16_t)(0x8000 >> col); + if (outline & mask) { + fb.put_pixel(x + col, y + row, black); + } else if (fill & mask) { + fb.put_pixel(x + col, y + row, white); + } + } + } +} + +} // namespace gui diff --git a/programs/include/gui/font.hpp b/programs/include/gui/font.hpp new file mode 100644 index 0000000..11c5f6a --- /dev/null +++ b/programs/include/gui/font.hpp @@ -0,0 +1,63 @@ +/* + * font.hpp + * ZenithOS 8x16 VGA bitmap font rendering + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/framebuffer.hpp" + +namespace gui { + +static constexpr int FONT_WIDTH = 8; +static constexpr int FONT_HEIGHT = 16; + +// Defined in font_data.cpp +extern const uint8_t font_data[256 * 16]; + +inline void draw_char(Framebuffer& fb, int x, int y, char c, Color fg) { + const uint8_t* glyph = &font_data[(unsigned char)c * FONT_HEIGHT]; + for (int row = 0; row < FONT_HEIGHT; row++) { + uint8_t bits = glyph[row]; + for (int col = 0; col < FONT_WIDTH; col++) { + if (bits & (0x80 >> col)) { + fb.put_pixel(x + col, y + row, fg); + } + } + } +} + +inline void draw_char_bg(Framebuffer& fb, int x, int y, char c, Color fg, Color bg) { + const uint8_t* glyph = &font_data[(unsigned char)c * FONT_HEIGHT]; + for (int row = 0; row < FONT_HEIGHT; row++) { + uint8_t bits = glyph[row]; + for (int col = 0; col < FONT_WIDTH; col++) { + if (bits & (0x80 >> col)) { + fb.put_pixel(x + col, y + row, fg); + } else { + fb.put_pixel(x + col, y + row, bg); + } + } + } +} + +inline void draw_text(Framebuffer& fb, int x, int y, const char* text, Color fg) { + for (int i = 0; text[i]; i++) { + draw_char(fb, x + i * FONT_WIDTH, y, text[i], fg); + } +} + +inline void draw_text_bg(Framebuffer& fb, int x, int y, const char* text, Color fg, Color bg) { + for (int i = 0; text[i]; i++) { + draw_char_bg(fb, x + i * FONT_WIDTH, y, text[i], fg, bg); + } +} + +inline int text_width(const char* text) { + int len = 0; + while (text[len]) len++; + return len * FONT_WIDTH; +} + +} // namespace gui diff --git a/programs/include/gui/framebuffer.hpp b/programs/include/gui/framebuffer.hpp new file mode 100644 index 0000000..6ae1619 --- /dev/null +++ b/programs/include/gui/framebuffer.hpp @@ -0,0 +1,196 @@ +/* + * framebuffer.hpp + * ZenithOS double-buffered framebuffer abstraction + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include +#include +#include "gui/gui.hpp" + +namespace gui { + +class Framebuffer { + uint32_t* hw_fb; + uint32_t* back_buf; + int fb_width; + int fb_height; + int fb_pitch; // in bytes + +public: + Framebuffer() : hw_fb(nullptr), back_buf(nullptr), fb_width(0), fb_height(0), fb_pitch(0) { + Zenith::FbInfo info; + zenith::fb_info(&info); + + fb_width = (int)info.width; + fb_height = (int)info.height; + fb_pitch = (int)info.pitch; + + hw_fb = (uint32_t*)zenith::fb_map(); + back_buf = (uint32_t*)zenith::alloc((uint64_t)fb_height * fb_pitch); + } + + int width() const { return fb_width; } + int height() const { return fb_height; } + int pitch() const { return fb_pitch; } + + uint32_t* buffer() { return back_buf; } + + inline void put_pixel(int x, int y, Color c) { + if (x < 0 || x >= fb_width || y < 0 || y >= fb_height) return; + uint32_t* row = (uint32_t*)((uint8_t*)back_buf + y * fb_pitch); + row[x] = c.to_pixel(); + } + + inline void put_pixel_alpha(int x, int y, Color c) { + if (x < 0 || x >= fb_width || y < 0 || y >= fb_height) return; + if (c.a == 0) return; + if (c.a == 255) { + put_pixel(x, y, c); + return; + } + + uint32_t* row = (uint32_t*)((uint8_t*)back_buf + y * fb_pitch); + uint32_t dst = row[x]; + + uint8_t dr = (dst >> 16) & 0xFF; + uint8_t dg = (dst >> 8) & 0xFF; + uint8_t db = dst & 0xFF; + + uint32_t a = c.a; + uint32_t inv_a = 255 - a; + + // Fast alpha blend: out = (src * alpha + dst * (255 - alpha) + 128) / 255 + // Approximation: (x + 1 + (x >> 8)) >> 8 for division by 255 + uint32_t rr = a * c.r + inv_a * dr; + uint32_t gg = a * c.g + inv_a * dg; + uint32_t bb = a * c.b + inv_a * db; + + rr = (rr + 1 + (rr >> 8)) >> 8; + gg = (gg + 1 + (gg >> 8)) >> 8; + bb = (bb + 1 + (bb >> 8)) >> 8; + + row[x] = (0xFF000000) | (rr << 16) | (gg << 8) | bb; + } + + inline void fill_rect(int x, int y, int w, int h, Color c) { + // Clip to screen bounds + int x0 = x < 0 ? 0 : x; + int y0 = y < 0 ? 0 : y; + int x1 = (x + w) > fb_width ? fb_width : (x + w); + int y1 = (y + h) > fb_height ? fb_height : (y + h); + + if (x0 >= x1 || y0 >= y1) return; + + uint32_t pixel = c.to_pixel(); + int clipped_w = x1 - x0; + + for (int row = y0; row < y1; row++) { + uint32_t* dst = (uint32_t*)((uint8_t*)back_buf + row * fb_pitch) + x0; + for (int col = 0; col < clipped_w; col++) { + dst[col] = pixel; + } + } + } + + inline void fill_rect_alpha(int x, int y, int w, int h, Color c) { + if (c.a == 0) return; + if (c.a == 255) { + fill_rect(x, y, w, h, c); + return; + } + + int x0 = x < 0 ? 0 : x; + int y0 = y < 0 ? 0 : y; + int x1 = (x + w) > fb_width ? fb_width : (x + w); + int y1 = (y + h) > fb_height ? fb_height : (y + h); + + if (x0 >= x1 || y0 >= y1) return; + + uint32_t a = c.a; + uint32_t inv_a = 255 - a; + uint32_t src_r = a * c.r; + uint32_t src_g = a * c.g; + uint32_t src_b = a * c.b; + + for (int row = y0; row < y1; row++) { + uint32_t* dst = (uint32_t*)((uint8_t*)back_buf + row * fb_pitch) + x0; + for (int col = 0; col < x1 - x0; col++) { + uint32_t d = dst[col]; + uint32_t dr = (d >> 16) & 0xFF; + uint32_t dg = (d >> 8) & 0xFF; + uint32_t db = d & 0xFF; + + uint32_t rr = src_r + inv_a * dr; + uint32_t gg = src_g + inv_a * dg; + uint32_t bb = src_b + inv_a * db; + + rr = (rr + 1 + (rr >> 8)) >> 8; + gg = (gg + 1 + (gg >> 8)) >> 8; + bb = (bb + 1 + (bb >> 8)) >> 8; + + dst[col] = (0xFF000000) | (rr << 16) | (gg << 8) | bb; + } + } + } + + inline void blit(int x, int y, int w, int h, const uint32_t* pixels) { + for (int row = 0; row < h; row++) { + int dy = y + row; + if (dy < 0 || dy >= fb_height) continue; + for (int col = 0; col < w; col++) { + int dx = x + col; + if (dx < 0 || dx >= fb_width) continue; + uint32_t* dst_row = (uint32_t*)((uint8_t*)back_buf + dy * fb_pitch); + dst_row[dx] = pixels[row * w + col]; + } + } + } + + inline void blit_alpha(int x, int y, int w, int h, const uint32_t* pixels) { + for (int row = 0; row < h; row++) { + int dy = y + row; + if (dy < 0 || dy >= fb_height) continue; + for (int col = 0; col < w; col++) { + int dx = x + col; + if (dx < 0 || dx >= fb_width) continue; + + uint32_t src = pixels[row * w + col]; + uint8_t sa = (src >> 24) & 0xFF; + if (sa == 0) continue; + + uint8_t sr = (src >> 16) & 0xFF; + uint8_t sg = (src >> 8) & 0xFF; + uint8_t sb = src & 0xFF; + + if (sa == 255) { + uint32_t* dst_row = (uint32_t*)((uint8_t*)back_buf + dy * fb_pitch); + dst_row[dx] = src; + continue; + } + + Color sc = {sr, sg, sb, sa}; + put_pixel_alpha(dx, dy, sc); + } + } + } + + inline void clear(Color c) { + fill_rect(0, 0, fb_width, fb_height, c); + } + + inline void flip() { + // Copy back buffer to hardware framebuffer, row by row (pitch may differ) + int row_pixels = fb_width; + for (int y = 0; y < fb_height; y++) { + uint32_t* src = (uint32_t*)((uint8_t*)back_buf + y * fb_pitch); + uint32_t* dst = (uint32_t*)((uint8_t*)hw_fb + y * fb_pitch); + for (int x = 0; x < row_pixels; x++) { + dst[x] = src[x]; + } + } + } +}; + +} // namespace gui diff --git a/programs/include/gui/gui.hpp b/programs/include/gui/gui.hpp new file mode 100644 index 0000000..492159d --- /dev/null +++ b/programs/include/gui/gui.hpp @@ -0,0 +1,92 @@ +/* + * gui.hpp + * ZenithOS core GUI types and utilities + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include + +namespace gui { + +// 16.16 fixed-point type +using fixed_t = int32_t; + +static constexpr int FIXED_SHIFT = 16; + +inline fixed_t int_to_fixed(int v) { return v << FIXED_SHIFT; } +inline int fixed_to_int(fixed_t v) { return v >> FIXED_SHIFT; } +inline fixed_t fixed_mul(fixed_t a, fixed_t b) { return (int32_t)(((int64_t)a * b) >> FIXED_SHIFT); } +inline fixed_t fixed_div(fixed_t a, fixed_t b) { return (int32_t)(((int64_t)a << FIXED_SHIFT) / b); } +inline fixed_t fixed_from_parts(int whole, int frac_num, int frac_den) { + return int_to_fixed(whole) + (int32_t)(((int64_t)frac_num << FIXED_SHIFT) / frac_den); +} + +struct Color { + uint8_t r, g, b, a; + + static Color from_rgb(uint8_t r, uint8_t g, uint8_t b) { return {r, g, b, 255}; } + static Color from_rgba(uint8_t r, uint8_t g, uint8_t b, uint8_t a) { return {r, g, b, a}; } + static Color from_hex(uint32_t hex) { + return {(uint8_t)((hex >> 16) & 0xFF), (uint8_t)((hex >> 8) & 0xFF), (uint8_t)(hex & 0xFF), 255}; + } + + uint32_t to_pixel() const { return ((uint32_t)a << 24) | ((uint32_t)r << 16) | ((uint32_t)g << 8) | b; } +}; + +// Named colors for the desktop theme +namespace colors { + static constexpr Color DESKTOP_BG = {0xE0, 0xE0, 0xE0, 0xFF}; + static constexpr Color PANEL_BG = {0x2B, 0x3E, 0x50, 0xFF}; + static constexpr Color TITLEBAR_BG = {0xF5, 0xF5, 0xF5, 0xFF}; + static constexpr Color WINDOW_BG = {0xFF, 0xFF, 0xFF, 0xFF}; + static constexpr Color BORDER = {0xCC, 0xCC, 0xCC, 0xFF}; + static constexpr Color TEXT_COLOR = {0x33, 0x33, 0x33, 0xFF}; + static constexpr Color PANEL_TEXT = {0xFF, 0xFF, 0xFF, 0xFF}; + static constexpr Color ACCENT = {0x36, 0x7B, 0xF0, 0xFF}; + static constexpr Color CLOSE_BTN = {0xFF, 0x5F, 0x57, 0xFF}; + static constexpr Color MAX_BTN = {0x28, 0xCA, 0x42, 0xFF}; + static constexpr Color MIN_BTN = {0xFF, 0xBD, 0x2E, 0xFF}; + static constexpr Color SHADOW = {0x00, 0x00, 0x00, 0x40}; + static constexpr Color TRANSPARENT = {0x00, 0x00, 0x00, 0x00}; + static constexpr Color BLACK = {0x00, 0x00, 0x00, 0xFF}; + static constexpr Color WHITE = {0xFF, 0xFF, 0xFF, 0xFF}; + static constexpr Color ICON_COLOR = {0x5C, 0x61, 0x6C, 0xFF}; + static constexpr Color SCROLLBAR_BG = {0xF0, 0xF0, 0xF0, 0xFF}; + static constexpr Color SCROLLBAR_FG = {0xC0, 0xC0, 0xC0, 0xFF}; + static constexpr Color MENU_BG = {0xFF, 0xFF, 0xFF, 0xFF}; + static constexpr Color MENU_HOVER = {0xE8, 0xF0, 0xFE, 0xFF}; + static constexpr Color TERM_BG = {0x2D, 0x2D, 0x2D, 0xFF}; + static constexpr Color TERM_FG = {0xCC, 0xCC, 0xCC, 0xFF}; +} + +struct Point { + int x, y; +}; + +struct Rect { + int x, y, w, h; + + bool contains(int px, int py) const { + return px >= x && px < x + w && py >= y && py < y + h; + } + + Rect intersect(const Rect& other) const { + int rx = x > other.x ? x : other.x; + int ry = y > other.y ? y : other.y; + int rx2 = (x + w) < (other.x + other.w) ? (x + w) : (other.x + other.w); + int ry2 = (y + h) < (other.y + other.h) ? (y + h) : (other.y + other.h); + if (rx2 <= rx || ry2 <= ry) return {0, 0, 0, 0}; + return {rx, ry, rx2 - rx, ry2 - ry}; + } + + bool empty() const { return w <= 0 || h <= 0; } +}; + +// Simple inline utility functions +inline int gui_min(int a, int b) { return a < b ? a : b; } +inline int gui_max(int a, int b) { return a > b ? a : b; } +inline int gui_abs(int a) { return a < 0 ? -a : a; } +inline int gui_clamp(int v, int lo, int hi) { return v < lo ? lo : (v > hi ? hi : v); } + +} // namespace gui diff --git a/programs/include/gui/svg.hpp b/programs/include/gui/svg.hpp new file mode 100644 index 0000000..0c10b0b --- /dev/null +++ b/programs/include/gui/svg.hpp @@ -0,0 +1,972 @@ +/* + * svg.hpp + * ZenithOS SVG icon parser and scanline rasterizer + * Handles the Flat-Remix symbolic icon subset (path, circle, rect) + * All math uses 16.16 fixed-point -- NO floating point. + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include + +namespace gui { + +// --------------------------------------------------------------------------- +// SVG icon result +// --------------------------------------------------------------------------- +struct SvgIcon { + uint32_t* pixels; // ARGB pixel data (heap-allocated) + int width; + int height; +}; + +// --------------------------------------------------------------------------- +// Edge used by the scanline rasterizer +// --------------------------------------------------------------------------- +struct SvgEdge { + fixed_t x0, y0, x1, y1; +}; + +// --------------------------------------------------------------------------- +// Constants +// --------------------------------------------------------------------------- +static constexpr int SVG_MAX_EDGES = 4096; +static constexpr int SVG_MAX_PATH_LEN = 4096; +static constexpr int SVG_MAX_FILE_SIZE = 32768; +static constexpr int SVG_BEZIER_STEPS = 8; + +// --------------------------------------------------------------------------- +// Fixed-point number parser (NO floating point) +// Parses strings like "3.25", "-0.5", ".1115", "16" +// Returns the number of characters consumed. +// --------------------------------------------------------------------------- +inline int svg_parse_fixed(const char* s, fixed_t* out) { + const char* p = s; + bool neg = false; + + if (*p == '-') { neg = true; ++p; } + else if (*p == '+') { ++p; } + + // Integer part + int32_t integer = 0; + while (*p >= '0' && *p <= '9') { + integer = integer * 10 + (*p - '0'); + ++p; + } + + // Fractional part + int32_t frac = 0; + int32_t frac_div = 1; + if (*p == '.') { + ++p; + while (*p >= '0' && *p <= '9') { + if (frac_div < 100000) { // prevent overflow + frac = frac * 10 + (*p - '0'); + frac_div *= 10; + } + ++p; + } + } + + fixed_t val = int_to_fixed(integer); + if (frac_div > 1) { + val += (int32_t)(((int64_t)frac << 16) / frac_div); + } + + if (neg) val = -val; + *out = val; + return (int)(p - s); +} + +// --------------------------------------------------------------------------- +// String helpers (no stdlib) +// --------------------------------------------------------------------------- +inline bool svg_char_is_ws(char c) { + return c == ' ' || c == '\t' || c == '\n' || c == '\r'; +} + +inline bool svg_char_is_sep(char c) { + return svg_char_is_ws(c) || c == ','; +} + +inline bool svg_char_is_num_start(char c) { + return (c >= '0' && c <= '9') || c == '-' || c == '+' || c == '.'; +} + +inline bool svg_char_is_cmd(char c) { + return (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z'); +} + +inline int svg_strlen(const char* s) { + int n = 0; + while (s[n]) ++n; + return n; +} + +inline bool svg_strncmp(const char* a, const char* b, int n) { + for (int i = 0; i < n; ++i) + if (a[i] != b[i]) return false; + return true; +} + +inline void svg_memset(void* dst, uint8_t val, int n) { + auto* d = (uint8_t*)dst; + for (int i = 0; i < n; ++i) d[i] = val; +} + +inline void svg_memcpy(void* dst, const void* src, int n) { + auto* d = (uint8_t*)dst; + auto* s = (const uint8_t*)src; + for (int i = 0; i < n; ++i) d[i] = s[i]; +} + +// --------------------------------------------------------------------------- +// Mini XML attribute extraction +// --------------------------------------------------------------------------- + +// Find the next occurrence of needle in haystack (haystack has length hLen). +// Returns pointer to start of match, or nullptr. +inline const char* svg_strstr(const char* haystack, int hLen, const char* needle) { + int nLen = svg_strlen(needle); + if (nLen == 0 || nLen > hLen) return nullptr; + for (int i = 0; i <= hLen - nLen; ++i) { + if (svg_strncmp(haystack + i, needle, nLen)) + return haystack + i; + } + return nullptr; +} + +// Check if a character can be part of an XML attribute name +inline bool svg_char_is_attrname(char c) { + return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || + (c >= '0' && c <= '9') || c == '-' || c == '_' || c == ':'; +} + +// Extract the value of an XML attribute: attr="value" +// The attr string should include a leading space (e.g., " cx") to distinguish +// from substrings of other attribute names. +// Writes into buf (up to maxLen-1 chars), returns length or -1 if not found. +inline int svg_get_attr(const char* tag, int tagLen, const char* attr, char* buf, int maxLen) { + int attrLen = svg_strlen(attr); + const char* search_start = tag; + int search_len = tagLen; + + while (search_len > 0) { + const char* p = svg_strstr(search_start, search_len, attr); + if (!p) return -1; + + // Ensure this is the exact attribute name, not a prefix of another + // (e.g., " r" should not match " rx" or " ry") + const char* after_name = p + attrLen; + if (after_name < tag + tagLen && svg_char_is_attrname(*after_name)) { + // This is a prefix of a longer attribute name, skip and search again + search_start = after_name; + search_len = tagLen - (int)(search_start - tag); + continue; + } + + p = after_name; + // skip whitespace around '=' + while (p < tag + tagLen && svg_char_is_ws(*p)) ++p; + if (p >= tag + tagLen || *p != '=') return -1; + ++p; + while (p < tag + tagLen && svg_char_is_ws(*p)) ++p; + if (p >= tag + tagLen) return -1; + char quote = *p; + if (quote != '"' && quote != '\'') return -1; + ++p; + int len = 0; + while (p < tag + tagLen && *p != quote && len < maxLen - 1) { + buf[len++] = *p++; + } + buf[len] = '\0'; + return len; + } + return -1; +} + +// Parse an integer from a string (no sign, simple decimal). +inline int svg_parse_int(const char* s) { + int v = 0; + while (*s >= '0' && *s <= '9') { + v = v * 10 + (*s - '0'); + ++s; + } + return v; +} + +// Parse a hex color like "#5c616c" into a Color. +inline Color svg_parse_hex_color(const char* s) { + if (*s == '#') ++s; + auto hexval = [](char c) -> uint8_t { + if (c >= '0' && c <= '9') return c - '0'; + if (c >= 'a' && c <= 'f') return 10 + (c - 'a'); + if (c >= 'A' && c <= 'F') return 10 + (c - 'A'); + return 0; + }; + uint8_t r = (hexval(s[0]) << 4) | hexval(s[1]); + uint8_t g = (hexval(s[2]) << 4) | hexval(s[3]); + uint8_t b = (hexval(s[4]) << 4) | hexval(s[5]); + return Color::from_rgb(r, g, b); +} + +// --------------------------------------------------------------------------- +// Edge list builder +// --------------------------------------------------------------------------- +struct SvgEdgeList { + SvgEdge* edges; + int count; + int capacity; + + void init(int cap) { + edges = (SvgEdge*)zenith::alloc(cap * sizeof(SvgEdge)); + count = 0; + capacity = cap; + } + + void add(fixed_t x0, fixed_t y0, fixed_t x1, fixed_t y1) { + if (count >= capacity) return; + // skip horizontal edges (they don't contribute to scanline crossings) + if (y0 == y1) return; + edges[count++] = {x0, y0, x1, y1}; + } +}; + +// --------------------------------------------------------------------------- +// Bezier flattening (fixed-point) +// --------------------------------------------------------------------------- + +// Cubic bezier: add line segments approximating B(t) for t in [0,1] +inline void svg_flatten_cubic(SvgEdgeList& el, + fixed_t x0, fixed_t y0, + fixed_t x1, fixed_t y1, + fixed_t x2, fixed_t y2, + fixed_t x3, fixed_t y3) { + constexpr int N = SVG_BEZIER_STEPS; + fixed_t px = x0, py = y0; + for (int i = 1; i <= N; ++i) { + // t = i/N in 16.16: (i << 16) / N + fixed_t t = (int32_t)(((int64_t)i << 16) / N); + fixed_t omt = int_to_fixed(1) - t; // 1 - t + + // (1-t)^2 and t^2 + fixed_t omt2 = fixed_mul(omt, omt); + fixed_t t2 = fixed_mul(t, t); + + // (1-t)^3 and t^3 + fixed_t omt3 = fixed_mul(omt2, omt); + fixed_t t3 = fixed_mul(t2, t); + + // 3*(1-t)^2*t and 3*(1-t)*t^2 + fixed_t c1 = fixed_mul(omt2, t) * 3; + fixed_t c2 = fixed_mul(omt, t2) * 3; + + fixed_t nx = fixed_mul(omt3, x0) + fixed_mul(c1, x1) + fixed_mul(c2, x2) + fixed_mul(t3, x3); + fixed_t ny = fixed_mul(omt3, y0) + fixed_mul(c1, y1) + fixed_mul(c2, y2) + fixed_mul(t3, y3); + + el.add(px, py, nx, ny); + px = nx; + py = ny; + } +} + +// Quadratic bezier: add line segments approximating B(t) for t in [0,1] +inline void svg_flatten_quad(SvgEdgeList& el, + fixed_t x0, fixed_t y0, + fixed_t x1, fixed_t y1, + fixed_t x2, fixed_t y2) { + constexpr int N = SVG_BEZIER_STEPS; + fixed_t px = x0, py = y0; + for (int i = 1; i <= N; ++i) { + fixed_t t = (int32_t)(((int64_t)i << 16) / N); + fixed_t omt = int_to_fixed(1) - t; + + // (1-t)^2*P0 + 2*(1-t)*t*P1 + t^2*P2 + fixed_t omt2 = fixed_mul(omt, omt); + fixed_t t2 = fixed_mul(t, t); + fixed_t c1 = fixed_mul(omt, t) * 2; + + fixed_t nx = fixed_mul(omt2, x0) + fixed_mul(c1, x1) + fixed_mul(t2, x2); + fixed_t ny = fixed_mul(omt2, y0) + fixed_mul(c1, y1) + fixed_mul(t2, y2); + + el.add(px, py, nx, ny); + px = nx; + py = ny; + } +} + +// --------------------------------------------------------------------------- +// Circle to edges: approximate a circle as N line segments +// --------------------------------------------------------------------------- +inline void svg_circle_edges(SvgEdgeList& el, fixed_t cx, fixed_t cy, fixed_t r) { + // Approximate circle with 16 segments using a precomputed sin/cos table + // for angles 0, 22.5, 45, ... 337.5 degrees. + // sin/cos in 16.16 fixed-point for 16 evenly-spaced angles: + static const fixed_t cos16[16] = { + 65536, 60547, 46341, 25080, 0, -25080, -46341, -60547, + -65536, -60547, -46341, -25080, 0, 25080, 46341, 60547 + }; + static const fixed_t sin16[16] = { + 0, 25080, 46341, 60547, 65536, 60547, 46341, 25080, + 0, -25080, -46341, -60547, -65536, -60547, -46341, -25080 + }; + + fixed_t px = cx + fixed_mul(r, cos16[0]); + fixed_t py = cy + fixed_mul(r, sin16[0]); + for (int i = 1; i <= 16; ++i) { + int idx = i & 15; + fixed_t nx = cx + fixed_mul(r, cos16[idx]); + fixed_t ny = cy + fixed_mul(r, sin16[idx]); + el.add(px, py, nx, ny); + px = nx; + py = ny; + } +} + +// --------------------------------------------------------------------------- +// Rounded rect to edges +// --------------------------------------------------------------------------- +inline void svg_rect_edges(SvgEdgeList& el, fixed_t x, fixed_t y, fixed_t w, fixed_t h, + fixed_t rx, fixed_t ry) { + if (rx <= 0 && ry <= 0) { + // Simple rectangle: 4 edges + fixed_t x2 = x + w; + fixed_t y2 = y + h; + el.add(x, y, x2, y); // top + el.add(x2, y, x2, y2); // right + el.add(x2, y2, x, y2); // bottom + el.add(x, y2, x, y); // left + return; + } + + // Clamp radii + fixed_t half_w = w >> 1; + fixed_t half_h = h >> 1; + if (rx > half_w) rx = half_w; + if (ry > half_h) ry = half_h; + + // Quarter-circle corner with 4 segments per corner. + // cos/sin for 0, 22.5, 45, 67.5, 90 degrees (5 points, 4 segments): + static const fixed_t qcos[5] = { 65536, 60547, 46341, 25080, 0 }; + static const fixed_t qsin[5] = { 0, 25080, 46341, 60547, 65536 }; + + // Corners: top-right, bottom-right, bottom-left, top-left + // Each corner has a center and a quadrant direction for cos/sin application + struct Corner { fixed_t cx, cy; int sx, sy; }; + Corner corners[4] = { + { x + w - rx, y + ry, 1, -1 }, // top-right + { x + w - rx, y + h - ry, 1, 1 }, // bottom-right + { x + rx, y + h - ry, -1, 1 }, // bottom-left + { x + rx, y + ry, -1, -1 }, // top-left + }; + + for (int c = 0; c < 4; ++c) { + Corner& cn = corners[c]; + fixed_t px = cn.cx + fixed_mul(rx, qcos[0]) * cn.sx; + fixed_t py = cn.cy + fixed_mul(ry, qsin[0]) * cn.sy; + for (int i = 1; i <= 4; ++i) { + fixed_t nx = cn.cx + fixed_mul(rx, qcos[i]) * cn.sx; + fixed_t ny = cn.cy + fixed_mul(ry, qsin[i]) * cn.sy; + el.add(px, py, nx, ny); + px = nx; + py = ny; + } + } + + // Straight edges between corners + // Top edge: top-left corner end -> top-right corner start + el.add(x + rx, y, x + w - rx, y); + // Right edge: top-right corner end -> bottom-right corner start + el.add(x + w, y + ry, x + w, y + h - ry); + // Bottom edge: bottom-right corner end -> bottom-left corner start + el.add(x + w - rx, y + h, x + rx, y + h); + // Left edge: bottom-left corner end -> top-left corner start + el.add(x, y + h - ry, x, y + ry); +} + +// --------------------------------------------------------------------------- +// Path command parser: tokenize the 'd' attribute +// --------------------------------------------------------------------------- +struct SvgPathParser { + const char* data; + int len; + int pos; + + void init(const char* d, int l) { data = d; len = l; pos = 0; } + + void skip_separators() { + while (pos < len && svg_char_is_sep(data[pos])) ++pos; + } + + bool has_more() const { return pos < len; } + + // Peek at what's next: command letter, number, or end + bool next_is_number() { + skip_separators(); + if (pos >= len) return false; + return svg_char_is_num_start(data[pos]); + } + + char read_command() { + skip_separators(); + if (pos >= len) return '\0'; + if (svg_char_is_cmd(data[pos]) && data[pos] != 'e' && data[pos] != 'E') { + return data[pos++]; + } + return '\0'; + } + + fixed_t read_number() { + skip_separators(); + if (pos >= len) return 0; + fixed_t val = 0; + int consumed = svg_parse_fixed(data + pos, &val); + pos += consumed; + return val; + } +}; + +// --------------------------------------------------------------------------- +// Process an SVG path 'd' attribute into edges +// --------------------------------------------------------------------------- +inline void svg_path_to_edges(SvgEdgeList& el, const char* d, int dLen, + fixed_t scale_x, fixed_t scale_y, + fixed_t off_x, fixed_t off_y) { + SvgPathParser pp; + pp.init(d, dLen); + + fixed_t cur_x = 0, cur_y = 0; // current point + fixed_t start_x = 0, start_y = 0; // subpath start + fixed_t last_cx = 0, last_cy = 0; // last control point (for S/T) + char last_cmd = '\0'; + + auto scale_pt = [&](fixed_t x, fixed_t y, fixed_t* ox, fixed_t* oy) { + *ox = fixed_mul(x - off_x, scale_x); + *oy = fixed_mul(y - off_y, scale_y); + }; + + while (pp.has_more()) { + char cmd = '\0'; + + // Try reading a command letter + pp.skip_separators(); + if (pp.pos < pp.len && svg_char_is_cmd(pp.data[pp.pos]) && + pp.data[pp.pos] != 'e' && pp.data[pp.pos] != 'E') { + cmd = pp.data[pp.pos++]; + } else if (pp.next_is_number()) { + // Implicit repeat of last command + // After M, implicit repeat is L; after m, implicit repeat is l + if (last_cmd == 'M') cmd = 'L'; + else if (last_cmd == 'm') cmd = 'l'; + else cmd = last_cmd; + } else { + // Skip unknown character + if (pp.pos < pp.len) pp.pos++; + continue; + } + + if (cmd == '\0') break; + + switch (cmd) { + case 'M': { + fixed_t x = pp.read_number(); + fixed_t y = pp.read_number(); + cur_x = x; cur_y = y; + start_x = x; start_y = y; + last_cmd = 'M'; + break; + } + case 'm': { + fixed_t dx = pp.read_number(); + fixed_t dy = pp.read_number(); + cur_x += dx; cur_y += dy; + start_x = cur_x; start_y = cur_y; + last_cmd = 'm'; + break; + } + case 'L': { + fixed_t x = pp.read_number(); + fixed_t y = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x, y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_x = x; cur_y = y; + last_cmd = 'L'; + break; + } + case 'l': { + fixed_t dx = pp.read_number(); + fixed_t dy = pp.read_number(); + fixed_t nx = cur_x + dx, ny = cur_y + dy; + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(nx, ny, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_x = nx; cur_y = ny; + last_cmd = 'l'; + break; + } + case 'H': { + fixed_t x = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x, cur_y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_x = x; + last_cmd = 'H'; + break; + } + case 'h': { + fixed_t dx = pp.read_number(); + fixed_t nx = cur_x + dx; + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(nx, cur_y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_x = nx; + last_cmd = 'h'; + break; + } + case 'V': { + fixed_t y = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(cur_x, y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_y = y; + last_cmd = 'V'; + break; + } + case 'v': { + fixed_t dy = pp.read_number(); + fixed_t ny = cur_y + dy; + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(cur_x, ny, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_y = ny; + last_cmd = 'v'; + break; + } + case 'C': { + fixed_t x1 = pp.read_number(), y1 = pp.read_number(); + fixed_t x2 = pp.read_number(), y2 = pp.read_number(); + fixed_t x3 = pp.read_number(), y3 = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x1, y1, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + scale_pt(x3, y3, &sx3, &sy3); + svg_flatten_cubic(el, sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3); + last_cx = x2; last_cy = y2; + cur_x = x3; cur_y = y3; + last_cmd = 'C'; + break; + } + case 'c': { + fixed_t dx1 = pp.read_number(), dy1 = pp.read_number(); + fixed_t dx2 = pp.read_number(), dy2 = pp.read_number(); + fixed_t dx3 = pp.read_number(), dy3 = pp.read_number(); + fixed_t x1 = cur_x + dx1, y1 = cur_y + dy1; + fixed_t x2 = cur_x + dx2, y2 = cur_y + dy2; + fixed_t x3 = cur_x + dx3, y3 = cur_y + dy3; + fixed_t sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x1, y1, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + scale_pt(x3, y3, &sx3, &sy3); + svg_flatten_cubic(el, sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3); + last_cx = x2; last_cy = y2; + cur_x = x3; cur_y = y3; + last_cmd = 'c'; + break; + } + case 'S': { + // Smooth cubic: reflect last control point + fixed_t rcx = cur_x * 2 - last_cx; + fixed_t rcy = cur_y * 2 - last_cy; + if (last_cmd != 'C' && last_cmd != 'c' && last_cmd != 'S' && last_cmd != 's') { + rcx = cur_x; rcy = cur_y; + } + fixed_t x2 = pp.read_number(), y2 = pp.read_number(); + fixed_t x3 = pp.read_number(), y3 = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(rcx, rcy, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + scale_pt(x3, y3, &sx3, &sy3); + svg_flatten_cubic(el, sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3); + last_cx = x2; last_cy = y2; + cur_x = x3; cur_y = y3; + last_cmd = 'S'; + break; + } + case 's': { + fixed_t rcx = cur_x * 2 - last_cx; + fixed_t rcy = cur_y * 2 - last_cy; + if (last_cmd != 'C' && last_cmd != 'c' && last_cmd != 'S' && last_cmd != 's') { + rcx = cur_x; rcy = cur_y; + } + fixed_t dx2 = pp.read_number(), dy2 = pp.read_number(); + fixed_t dx3 = pp.read_number(), dy3 = pp.read_number(); + fixed_t x2 = cur_x + dx2, y2 = cur_y + dy2; + fixed_t x3 = cur_x + dx3, y3 = cur_y + dy3; + fixed_t sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(rcx, rcy, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + scale_pt(x3, y3, &sx3, &sy3); + svg_flatten_cubic(el, sx0, sy0, sx1, sy1, sx2, sy2, sx3, sy3); + last_cx = x2; last_cy = y2; + cur_x = x3; cur_y = y3; + last_cmd = 's'; + break; + } + case 'Q': { + fixed_t x1 = pp.read_number(), y1 = pp.read_number(); + fixed_t x2 = pp.read_number(), y2 = pp.read_number(); + fixed_t sx0, sy0, sx1, sy1, sx2, sy2; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x1, y1, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + svg_flatten_quad(el, sx0, sy0, sx1, sy1, sx2, sy2); + last_cx = x1; last_cy = y1; + cur_x = x2; cur_y = y2; + last_cmd = 'Q'; + break; + } + case 'q': { + fixed_t dx1 = pp.read_number(), dy1 = pp.read_number(); + fixed_t dx2 = pp.read_number(), dy2 = pp.read_number(); + fixed_t x1 = cur_x + dx1, y1 = cur_y + dy1; + fixed_t x2 = cur_x + dx2, y2 = cur_y + dy2; + fixed_t sx0, sy0, sx1, sy1, sx2, sy2; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x1, y1, &sx1, &sy1); + scale_pt(x2, y2, &sx2, &sy2); + svg_flatten_quad(el, sx0, sy0, sx1, sy1, sx2, sy2); + last_cx = x1; last_cy = y1; + cur_x = x2; cur_y = y2; + last_cmd = 'q'; + break; + } + case 'A': case 'a': { + // Arc command: consume parameters but approximate as a line + // (arcs are rare in these icons) + fixed_t rx = pp.read_number(); + fixed_t ry = pp.read_number(); + pp.read_number(); // x-rotation + pp.read_number(); // large-arc-flag + pp.read_number(); // sweep-flag + fixed_t x = pp.read_number(); + fixed_t y = pp.read_number(); + if (cmd == 'a') { x += cur_x; y += cur_y; } + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(x, y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + cur_x = x; cur_y = y; + last_cmd = cmd; + (void)rx; (void)ry; + break; + } + case 'Z': case 'z': { + if (cur_x != start_x || cur_y != start_y) { + fixed_t sx0, sy0, sx1, sy1; + scale_pt(cur_x, cur_y, &sx0, &sy0); + scale_pt(start_x, start_y, &sx1, &sy1); + el.add(sx0, sy0, sx1, sy1); + } + cur_x = start_x; cur_y = start_y; + last_cmd = 'Z'; + break; + } + default: + // Unknown command, skip + break; + } + } +} + +// --------------------------------------------------------------------------- +// Scanline rasterizer (even-odd fill rule) +// --------------------------------------------------------------------------- +inline void svg_rasterize(const SvgEdgeList& el, uint32_t* pixels, int w, int h, uint32_t fill) { + // Temporary array for x-intersections on each scanline + // Allocate enough for all edges (each edge can intersect at most once per scanline) + int maxIsect = el.count + 16; + fixed_t* isect = (fixed_t*)zenith::alloc(maxIsect * sizeof(fixed_t)); + + for (int y = 0; y < h; ++y) { + // Scanline center in fixed-point + fixed_t scanY = int_to_fixed(y) + (1 << 15); // y + 0.5 + + int isectCount = 0; + + // Find intersections with all edges + for (int i = 0; i < el.count; ++i) { + const SvgEdge& e = el.edges[i]; + fixed_t ey0 = e.y0, ey1 = e.y1; + + // Ensure ey0 <= ey1 for the range check + fixed_t emin = ey0 < ey1 ? ey0 : ey1; + fixed_t emax = ey0 > ey1 ? ey0 : ey1; + + // Does this edge cross scanY? + if (scanY < emin || scanY >= emax) continue; + + // Compute x at intersection: x = x0 + (scanY - y0) * (x1 - x0) / (y1 - y0) + fixed_t dy = ey1 - ey0; + if (dy == 0) continue; // horizontal, skip + fixed_t dx = e.x1 - e.x0; + fixed_t t_num = scanY - ey0; + // x_intersect = x0 + dx * t_num / dy + fixed_t x_int = e.x0 + (int32_t)(((int64_t)dx * t_num) / dy); + + if (isectCount < maxIsect) + isect[isectCount++] = x_int; + } + + // Sort intersections (simple insertion sort -- usually very few) + for (int i = 1; i < isectCount; ++i) { + fixed_t key = isect[i]; + int j = i - 1; + while (j >= 0 && isect[j] > key) { + isect[j + 1] = isect[j]; + --j; + } + isect[j + 1] = key; + } + + // Fill between pairs (even-odd rule) + for (int i = 0; i + 1 < isectCount; i += 2) { + int x0 = fixed_to_int(isect[i]); + int x1 = fixed_to_int(isect[i + 1]); + + // Clamp to pixel bounds + if (x0 < 0) x0 = 0; + if (x1 > w) x1 = w; + + for (int x = x0; x < x1; ++x) { + pixels[y * w + x] = fill; + } + } + } + + zenith::free(isect); +} + +// --------------------------------------------------------------------------- +// SVG document parser: extract paths, circles, rects and rasterize +// --------------------------------------------------------------------------- +inline SvgIcon svg_render(const char* svg_data, int svg_len, int target_w, int target_h, Color fill_color) { + SvgIcon icon; + icon.width = target_w; + icon.height = target_h; + icon.pixels = (uint32_t*)zenith::alloc(target_w * target_h * sizeof(uint32_t)); + // Clear to transparent + svg_memset(icon.pixels, 0, target_w * target_h * sizeof(uint32_t)); + + uint32_t fill_px = fill_color.to_pixel(); + + // Parse SVG dimensions: width and height + int svg_w = 16, svg_h = 16; + fixed_t vb_x = 0, vb_y = 0, vb_w = 0, vb_h = 0; + bool has_viewbox = false; + + // Find tag + int tag_offset = (int)(svg_tag - svg_data); + int tag_end = tag_offset; + while (tag_end < svg_len && svg_data[tag_end] != '>') ++tag_end; + int tag_len = tag_end - tag_offset + 1; + + char attr_buf[64]; + + // width + if (svg_get_attr(svg_tag, tag_len, " width", attr_buf, sizeof(attr_buf)) > 0) { + svg_w = svg_parse_int(attr_buf); + } + // height + if (svg_get_attr(svg_tag, tag_len, " height", attr_buf, sizeof(attr_buf)) > 0) { + svg_h = svg_parse_int(attr_buf); + } + // viewBox + if (svg_get_attr(svg_tag, tag_len, " viewBox", attr_buf, sizeof(attr_buf)) > 0) { + has_viewbox = true; + const char* vp = attr_buf; + int c; + c = svg_parse_fixed(vp, &vb_x); vp += c; while (*vp && svg_char_is_sep(*vp)) ++vp; + c = svg_parse_fixed(vp, &vb_y); vp += c; while (*vp && svg_char_is_sep(*vp)) ++vp; + c = svg_parse_fixed(vp, &vb_w); vp += c; while (*vp && svg_char_is_sep(*vp)) ++vp; + svg_parse_fixed(vp, &vb_h); + } + } + + if (!has_viewbox) { + vb_x = 0; + vb_y = 0; + vb_w = int_to_fixed(svg_w); + vb_h = int_to_fixed(svg_h); + } + + // Compute scale: pixel = (svg_coord - vb_origin) * target_size / vb_size + fixed_t scale_x = vb_w > 0 ? fixed_div(int_to_fixed(target_w), vb_w) : int_to_fixed(1); + fixed_t scale_y = vb_h > 0 ? fixed_div(int_to_fixed(target_h), vb_h) : int_to_fixed(1); + + // Edge list + SvgEdgeList el; + el.init(SVG_MAX_EDGES); + + // Scan for = end) break; + + int remaining = (int)(end - p); + + // Check for 5 && svg_strncmp(p, "' + int elem_len = (int)(elem_end - elem_start); + + // Extract d attribute + char d_buf[SVG_MAX_PATH_LEN]; + int d_len = svg_get_attr(elem_start, elem_len, " d", d_buf, SVG_MAX_PATH_LEN); + if (d_len > 0) { + svg_path_to_edges(el, d_buf, d_len, scale_x, scale_y, vb_x, vb_y); + } + + p = elem_end; + continue; + } + + // Check for 7 && svg_strncmp(p, " 0) + svg_parse_fixed(attr_buf, &cx); + if (svg_get_attr(elem_start, elem_len, " cy", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &cy); + if (svg_get_attr(elem_start, elem_len, " r", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &r); + + // Scale to target coordinates + fixed_t scx = fixed_mul(cx - vb_x, scale_x); + fixed_t scy = fixed_mul(cy - vb_y, scale_y); + fixed_t srx = fixed_mul(r, scale_x); + fixed_t sry = fixed_mul(r, scale_y); + // Use average of scaled radii + fixed_t sr = (srx + sry) >> 1; + + svg_circle_edges(el, scx, scy, sr); + + p = elem_end; + continue; + } + + // Check for 5 && svg_strncmp(p, " 0) + svg_parse_fixed(attr_buf, &rx_val); + if (svg_get_attr(elem_start, elem_len, " y", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &ry_val); + if (svg_get_attr(elem_start, elem_len, " width", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &rw); + if (svg_get_attr(elem_start, elem_len, " height", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &rh); + if (svg_get_attr(elem_start, elem_len, " rx", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &rrx); + if (svg_get_attr(elem_start, elem_len, " ry", attr_buf, sizeof(attr_buf)) > 0) + svg_parse_fixed(attr_buf, &rry); + + // Scale all to target pixel space + fixed_t sx = fixed_mul(rx_val - vb_x, scale_x); + fixed_t sy = fixed_mul(ry_val - vb_y, scale_y); + fixed_t sw = fixed_mul(rw, scale_x); + fixed_t sh = fixed_mul(rh, scale_y); + fixed_t srx = fixed_mul(rrx, scale_x); + fixed_t sry = fixed_mul(rry, scale_y); + + svg_rect_edges(el, sx, sy, sw, sh, srx, sry); + + p = elem_end; + continue; + } + + ++p; + } + + // Rasterize all accumulated edges + if (el.count > 0) { + svg_rasterize(el, icon.pixels, target_w, target_h, fill_px); + } + + zenith::free(el.edges); + return icon; +} + +// --------------------------------------------------------------------------- +// Load SVG from VFS and render +// --------------------------------------------------------------------------- +inline SvgIcon svg_load(const char* vfs_path, int target_w, int target_h, Color fill_color) { + int fd = zenith::open(vfs_path); + if (fd < 0) { + return {nullptr, 0, 0}; + } + + uint64_t size = zenith::getsize(fd); + if (size == 0 || size > SVG_MAX_FILE_SIZE) { + zenith::close(fd); + return {nullptr, 0, 0}; + } + + char* buf = (char*)zenith::alloc(size + 1); + zenith::read(fd, (uint8_t*)buf, 0, size); + zenith::close(fd); + buf[size] = '\0'; + + SvgIcon icon = svg_render(buf, (int)size, target_w, target_h, fill_color); + zenith::free(buf); + return icon; +} + +// --------------------------------------------------------------------------- +// Free icon pixel data +// --------------------------------------------------------------------------- +inline void svg_free(SvgIcon& icon) { + if (icon.pixels) zenith::free(icon.pixels); + icon.pixels = nullptr; + icon.width = 0; + icon.height = 0; +} + +} // namespace gui diff --git a/programs/include/gui/terminal.hpp b/programs/include/gui/terminal.hpp new file mode 100644 index 0000000..2f30b2a --- /dev/null +++ b/programs/include/gui/terminal.hpp @@ -0,0 +1,526 @@ +/* + * terminal.hpp + * ZenithOS terminal emulator with ANSI escape sequence support + * Copyright (c) 2026 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/font.hpp" +#include +#include +#include + +namespace gui { + +struct TermCell { + char ch; + Color fg; + Color bg; +}; + +static constexpr int TERM_MAX_SCROLLBACK = 500; + +struct TerminalState { + TermCell* cells; + TermCell* alt_cells; // alternate screen buffer + int cols, rows; + int cursor_x, cursor_y; + int saved_cursor_x, saved_cursor_y; // saved cursor for alternate screen + int scroll_top; + int total_rows; + int child_pid; + Color current_fg; + Color current_bg; + bool cursor_visible; + bool alt_screen_active; + bool reverse_video; + + enum { STATE_NORMAL, STATE_ESC, STATE_CSI } parse_state; + bool csi_private; // true if '?' was seen after CSI + int csi_params[8]; + int csi_param_count; + int csi_current_param; +}; + +// Standard ANSI color palette as ARGB pixels +static inline Color term_ansi_color(int idx) { + switch (idx) { + case 0: return Color::from_hex(0x000000); + case 1: return Color::from_hex(0xCC0000); + case 2: return Color::from_hex(0x4E9A06); + case 3: return Color::from_hex(0xC4A000); + case 4: return Color::from_hex(0x3465A4); + case 5: return Color::from_hex(0x75507B); + case 6: return Color::from_hex(0x06989A); + case 7: return Color::from_hex(0xD3D7CF); + case 8: return Color::from_hex(0x555753); + case 9: return Color::from_hex(0xEF2929); + case 10: return Color::from_hex(0x8AE234); + case 11: return Color::from_hex(0xFCE94F); + case 12: return Color::from_hex(0x729FCF); + case 13: return Color::from_hex(0xAD7FA8); + case 14: return Color::from_hex(0x34E2E2); + case 15: return Color::from_hex(0xEEEEEC); + default: return colors::TERM_FG; + } +} + +static inline void terminal_scroll_up(TerminalState* t) { + // Move all rows up by one + for (int r = 0; r < t->rows - 1; r++) { + for (int c = 0; c < t->cols; c++) { + t->cells[r * t->cols + c] = t->cells[(r + 1) * t->cols + c]; + } + } + // Clear last row + int last = t->rows - 1; + for (int c = 0; c < t->cols; c++) { + t->cells[last * t->cols + c] = {' ', t->current_fg, colors::TERM_BG}; + } +} + +static inline void terminal_init(TerminalState* t, int cols, int rows) { + t->cols = cols; + t->rows = rows; + t->cursor_x = 0; + t->cursor_y = 0; + t->saved_cursor_x = 0; + t->saved_cursor_y = 0; + t->scroll_top = 0; + t->total_rows = rows; + t->current_fg = colors::TERM_FG; + t->current_bg = colors::TERM_BG; + t->cursor_visible = true; + t->alt_screen_active = false; + t->reverse_video = false; + t->parse_state = TerminalState::STATE_NORMAL; + t->csi_private = false; + t->csi_param_count = 0; + t->csi_current_param = 0; + + int total_cells = cols * rows; + t->cells = (TermCell*)zenith::alloc(total_cells * sizeof(TermCell)); + t->alt_cells = (TermCell*)zenith::alloc(total_cells * sizeof(TermCell)); + for (int i = 0; i < total_cells; i++) { + t->cells[i] = {' ', colors::TERM_FG, colors::TERM_BG}; + t->alt_cells[i] = {' ', colors::TERM_FG, colors::TERM_BG}; + } + + t->child_pid = zenith::spawn_redir("0:/os/shell.elf"); + zenith::childio_settermsz(t->child_pid, cols, rows); +} + +static inline void terminal_put_char(TerminalState* t, char ch) { + if (t->cursor_x >= t->cols) { + t->cursor_x = 0; + t->cursor_y++; + } + if (t->cursor_y >= t->rows) { + terminal_scroll_up(t); + t->cursor_y = t->rows - 1; + } + int idx = t->cursor_y * t->cols + t->cursor_x; + t->cells[idx].ch = ch; + t->cells[idx].fg = t->current_fg; + t->cells[idx].bg = t->current_bg; + t->cursor_x++; +} + +static inline void terminal_enter_alt_screen(TerminalState* t) { + if (t->alt_screen_active) return; + t->alt_screen_active = true; + // Save cursor + t->saved_cursor_x = t->cursor_x; + t->saved_cursor_y = t->cursor_y; + // Swap buffers: save main screen to alt_cells, clear main + int total = t->cols * t->rows; + for (int i = 0; i < total; i++) { + t->alt_cells[i] = t->cells[i]; + t->cells[i] = {' ', colors::TERM_FG, colors::TERM_BG}; + } + t->cursor_x = 0; + t->cursor_y = 0; +} + +static inline void terminal_exit_alt_screen(TerminalState* t) { + if (!t->alt_screen_active) return; + t->alt_screen_active = false; + // Restore main screen from alt_cells + int total = t->cols * t->rows; + for (int i = 0; i < total; i++) { + t->cells[i] = t->alt_cells[i]; + } + // Restore cursor + t->cursor_x = t->saved_cursor_x; + t->cursor_y = t->saved_cursor_y; +} + +static inline void terminal_process_private_mode(TerminalState* t, char cmd) { + int p0 = t->csi_param_count > 0 ? t->csi_params[0] : 0; + + if (cmd == 'h') { + // Set private mode + if (p0 == 25) { + t->cursor_visible = true; + } else if (p0 == 1049) { + terminal_enter_alt_screen(t); + } + } else if (cmd == 'l') { + // Reset private mode + if (p0 == 25) { + t->cursor_visible = false; + } else if (p0 == 1049) { + terminal_exit_alt_screen(t); + } + } +} + +static inline void terminal_process_csi(TerminalState* t, char cmd) { + // Finalize current param + if (t->csi_param_count < 8) { + t->csi_params[t->csi_param_count] = t->csi_current_param; + t->csi_param_count++; + } + + // Handle private mode sequences (ESC[?...) + if (t->csi_private) { + terminal_process_private_mode(t, cmd); + return; + } + + int p0 = t->csi_param_count > 0 ? t->csi_params[0] : 0; + int p1 = t->csi_param_count > 1 ? t->csi_params[1] : 0; + + switch (cmd) { + case 'H': case 'f': { + // Cursor position: ESC[row;colH (1-based) + int row = (p0 > 0 ? p0 : 1) - 1; + int col = (p1 > 0 ? p1 : 1) - 1; + if (row < 0) row = 0; + if (row >= t->rows) row = t->rows - 1; + if (col < 0) col = 0; + if (col >= t->cols) col = t->cols - 1; + t->cursor_y = row; + t->cursor_x = col; + break; + } + case 'A': { + // Cursor up + int n = p0 > 0 ? p0 : 1; + t->cursor_y -= n; + if (t->cursor_y < 0) t->cursor_y = 0; + break; + } + case 'B': { + // Cursor down + int n = p0 > 0 ? p0 : 1; + t->cursor_y += n; + if (t->cursor_y >= t->rows) t->cursor_y = t->rows - 1; + break; + } + case 'C': { + // Cursor forward + int n = p0 > 0 ? p0 : 1; + t->cursor_x += n; + if (t->cursor_x >= t->cols) t->cursor_x = t->cols - 1; + break; + } + case 'D': { + // Cursor backward + int n = p0 > 0 ? p0 : 1; + t->cursor_x -= n; + if (t->cursor_x < 0) t->cursor_x = 0; + break; + } + case 'J': { + // Erase in display + if (p0 == 0) { + // Clear from cursor to end + for (int x = t->cursor_x; x < t->cols; x++) + t->cells[t->cursor_y * t->cols + x] = {' ', t->current_fg, colors::TERM_BG}; + for (int r = t->cursor_y + 1; r < t->rows; r++) + for (int c = 0; c < t->cols; c++) + t->cells[r * t->cols + c] = {' ', t->current_fg, colors::TERM_BG}; + } else if (p0 == 1) { + // Clear from start to cursor + for (int r = 0; r < t->cursor_y; r++) + for (int c = 0; c < t->cols; c++) + t->cells[r * t->cols + c] = {' ', t->current_fg, colors::TERM_BG}; + for (int x = 0; x <= t->cursor_x; x++) + t->cells[t->cursor_y * t->cols + x] = {' ', t->current_fg, colors::TERM_BG}; + } else if (p0 == 2) { + // Clear entire screen + for (int i = 0; i < t->rows * t->cols; i++) + t->cells[i] = {' ', t->current_fg, colors::TERM_BG}; + t->cursor_x = 0; + t->cursor_y = 0; + } + break; + } + case 'K': { + // Erase in line + int start = 0, end = t->cols; + if (p0 == 0) { start = t->cursor_x; end = t->cols; } + else if (p0 == 1) { start = 0; end = t->cursor_x + 1; } + else if (p0 == 2) { start = 0; end = t->cols; } + for (int x = start; x < end; x++) + t->cells[t->cursor_y * t->cols + x] = {' ', t->current_fg, colors::TERM_BG}; + break; + } + case 'm': { + // SGR - Set Graphics Rendition + for (int i = 0; i < t->csi_param_count; i++) { + int code = t->csi_params[i]; + if (code == 0) { + t->current_fg = colors::TERM_FG; + t->current_bg = colors::TERM_BG; + t->reverse_video = false; + } else if (code == 1) { + // Bold: map to bright version of current color + uint8_t r = t->current_fg.r; + uint8_t g = t->current_fg.g; + uint8_t b = t->current_fg.b; + int add = 50; + r = (r + add > 255) ? 255 : r + add; + g = (g + add > 255) ? 255 : g + add; + b = (b + add > 255) ? 255 : b + add; + t->current_fg = Color::from_rgb(r, g, b); + } else if (code == 2) { + // Dim: darken current fg color + t->current_fg.r = t->current_fg.r / 2; + t->current_fg.g = t->current_fg.g / 2; + t->current_fg.b = t->current_fg.b / 2; + } else if (code == 7) { + // Reverse video + if (!t->reverse_video) { + t->reverse_video = true; + Color tmp = t->current_fg; + t->current_fg = t->current_bg; + t->current_bg = tmp; + } + } else if (code == 27) { + // Reverse off + if (t->reverse_video) { + t->reverse_video = false; + Color tmp = t->current_fg; + t->current_fg = t->current_bg; + t->current_bg = tmp; + } + } else if (code >= 30 && code <= 37) { + t->current_fg = term_ansi_color(code - 30); + if (t->reverse_video) { + // In reverse mode, fg is displayed as bg + Color tmp = t->current_fg; + t->current_fg = t->current_bg; + t->current_bg = tmp; + } + } else if (code >= 40 && code <= 47) { + t->current_bg = term_ansi_color(code - 40); + } else if (code >= 90 && code <= 97) { + t->current_fg = term_ansi_color(code - 90 + 8); + } else if (code >= 100 && code <= 107) { + t->current_bg = term_ansi_color(code - 100 + 8); + } else if (code == 39) { + t->current_fg = colors::TERM_FG; + } else if (code == 49) { + t->current_bg = colors::TERM_BG; + } + } + if (t->csi_param_count == 0) { + // ESC[m with no params = reset + t->current_fg = colors::TERM_FG; + t->current_bg = colors::TERM_BG; + t->reverse_video = false; + } + break; + } + default: + break; + } +} + +static inline void terminal_feed(TerminalState* t, const char* data, int len) { + for (int i = 0; i < len; i++) { + char ch = data[i]; + + switch (t->parse_state) { + case TerminalState::STATE_NORMAL: + if (ch == '\033') { + t->parse_state = TerminalState::STATE_ESC; + } else if (ch == '\n') { + t->cursor_x = 0; // CR+LF: shell sends \n without \r + t->cursor_y++; + if (t->cursor_y >= t->rows) { + terminal_scroll_up(t); + t->cursor_y = t->rows - 1; + } + } else if (ch == '\r') { + t->cursor_x = 0; + } else if (ch == '\b') { + if (t->cursor_x > 0) t->cursor_x--; + } else if (ch == '\t') { + int next = (t->cursor_x + 8) & ~7; + if (next > t->cols) next = t->cols; + while (t->cursor_x < next) { + terminal_put_char(t, ' '); + } + } else if (ch >= 32 || ch < 0) { + // Printable character (also treat high-bit chars as printable) + terminal_put_char(t, ch); + } + break; + + case TerminalState::STATE_ESC: + if (ch == '[') { + t->parse_state = TerminalState::STATE_CSI; + t->csi_private = false; + t->csi_param_count = 0; + t->csi_current_param = 0; + for (int j = 0; j < 8; j++) t->csi_params[j] = 0; + } else if (ch == 'c') { + // Reset terminal + t->current_fg = colors::TERM_FG; + t->current_bg = colors::TERM_BG; + t->cursor_x = 0; + t->cursor_y = 0; + t->parse_state = TerminalState::STATE_NORMAL; + } else { + // Unknown ESC sequence, ignore + t->parse_state = TerminalState::STATE_NORMAL; + } + break; + + case TerminalState::STATE_CSI: + if (ch >= '0' && ch <= '9') { + t->csi_current_param = t->csi_current_param * 10 + (ch - '0'); + } else if (ch == ';') { + if (t->csi_param_count < 8) { + t->csi_params[t->csi_param_count] = t->csi_current_param; + t->csi_param_count++; + } + t->csi_current_param = 0; + } else if (ch == '?') { + t->csi_private = true; + } else if (ch >= 0x40 && ch <= 0x7E) { + // Final byte - execute command + terminal_process_csi(t, ch); + t->parse_state = TerminalState::STATE_NORMAL; + } else { + // Unknown, abort CSI + t->parse_state = TerminalState::STATE_NORMAL; + } + break; + } + } +} + +static inline void terminal_render(TerminalState* t, uint32_t* pixels, int pw, int ph) { + // Fill background + uint32_t bg_px = colors::TERM_BG.to_pixel(); + int total = pw * ph; + for (int i = 0; i < total; i++) { + pixels[i] = bg_px; + } + + // Render each visible cell + int visible_rows = ph / FONT_HEIGHT; + int visible_cols = pw / FONT_WIDTH; + if (visible_rows > t->rows) visible_rows = t->rows; + if (visible_cols > t->cols) visible_cols = t->cols; + + for (int r = 0; r < visible_rows; r++) { + for (int c = 0; c < visible_cols; c++) { + int idx = r * t->cols + c; + TermCell& cell = t->cells[idx]; + + int px = c * FONT_WIDTH; + int py = r * FONT_HEIGHT; + + uint32_t cell_bg = cell.bg.to_pixel(); + uint32_t cell_fg = cell.fg.to_pixel(); + + // Draw cell background + for (int fy = 0; fy < FONT_HEIGHT; fy++) { + int dy = py + fy; + if (dy >= ph) break; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + int dx = px + fx; + if (dx >= pw) break; + pixels[dy * pw + dx] = cell_bg; + } + } + + // Draw character glyph + if (cell.ch > 32 || cell.ch < 0) { + const uint8_t* glyph = &font_data[(unsigned char)cell.ch * FONT_HEIGHT]; + for (int fy = 0; fy < FONT_HEIGHT; fy++) { + int dy = py + fy; + if (dy >= ph) break; + uint8_t bits = glyph[fy]; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + if (bits & (0x80 >> fx)) { + int dx = px + fx; + if (dx >= pw) break; + pixels[dy * pw + dx] = cell_fg; + } + } + } + } + } + } + + // Draw cursor + if (t->cursor_visible && t->cursor_x < visible_cols && t->cursor_y < visible_rows) { + int cx = t->cursor_x * FONT_WIDTH; + int cy = t->cursor_y * FONT_HEIGHT; + uint32_t cursor_px = colors::WHITE.to_pixel(); + for (int fy = 0; fy < FONT_HEIGHT; fy++) { + int dy = cy + fy; + if (dy >= ph) break; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + int dx = cx + fx; + if (dx >= pw) break; + pixels[dy * pw + dx] = cursor_px; + } + } + // Draw character on top of cursor in black + if (t->cursor_y < t->rows && t->cursor_x < t->cols) { + int idx = t->cursor_y * t->cols + t->cursor_x; + char ch = t->cells[idx].ch; + if (ch > 32 || ch < 0) { + const uint8_t* glyph = &font_data[(unsigned char)ch * FONT_HEIGHT]; + uint32_t black_px = colors::BLACK.to_pixel(); + for (int fy = 0; fy < FONT_HEIGHT; fy++) { + int dy = cy + fy; + if (dy >= ph) break; + uint8_t bits = glyph[fy]; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + if (bits & (0x80 >> fx)) { + int dx = cx + fx; + if (dx >= pw) break; + pixels[dy * pw + dx] = black_px; + } + } + } + } + } + } +} + +static inline void terminal_handle_key(TerminalState* t, const Zenith::KeyEvent& key) { + if (t->child_pid > 0) { + zenith::childio_writekey(t->child_pid, &key); + } +} + +static inline void terminal_poll(TerminalState* t) { + if (t->child_pid <= 0) return; + char buf[512]; + int n = zenith::childio_read(t->child_pid, buf, sizeof(buf)); + if (n > 0) { + terminal_feed(t, buf, n); + } +} + +} // namespace gui diff --git a/programs/include/gui/widgets.hpp b/programs/include/gui/widgets.hpp new file mode 100644 index 0000000..121ebf8 --- /dev/null +++ b/programs/include/gui/widgets.hpp @@ -0,0 +1,354 @@ +/* + * widgets.hpp + * ZenithOS GUI widget toolkit (Label, Button, TextBox, Scrollbar) + * Copyright (c) 2025 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/framebuffer.hpp" +#include "gui/font.hpp" +#include "gui/draw.hpp" + +namespace gui { + +// ---- Mouse event ---- + +struct MouseEvent { + int x, y; + uint8_t buttons; + uint8_t prev_buttons; + int32_t scroll; + + bool left_held() const { return buttons & 0x01; } + bool right_held() const { return buttons & 0x02; } + bool middle_held() const { return buttons & 0x04; } + + bool left_pressed() const { return (buttons & 0x01) && !(prev_buttons & 0x01); } + bool left_released() const { return !(buttons & 0x01) && (prev_buttons & 0x01); } + bool right_pressed() const { return (buttons & 0x02) && !(prev_buttons & 0x02); } + bool right_released() const { return !(buttons & 0x02) && (prev_buttons & 0x02); } +}; + +// ---- Callback types ---- + +using ClickCallback = void (*)(void* userdata); + +// ---- Label ---- + +struct Label { + int x, y; + const char* text; + Color color; + + void draw(Framebuffer& fb) const { + if (text) { + draw_text(fb, x, y, text, color); + } + } +}; + +// ---- Button ---- + +struct Button { + Rect bounds; + const char* text; + Color bg; + Color fg; + Color hover_bg; + bool hovered; + bool pressed; + ClickCallback on_click; + void* userdata; + + void init(int x, int y, int w, int h, const char* label) { + bounds = {x, y, w, h}; + text = label; + bg = colors::ACCENT; + fg = colors::WHITE; + hover_bg = Color::from_rgb(0x2B, 0x6B, 0xE0); + hovered = false; + pressed = false; + on_click = nullptr; + userdata = nullptr; + } + + void draw(Framebuffer& fb) const { + Color bg_color = hovered ? hover_bg : bg; + fill_rounded_rect(fb, bounds.x, bounds.y, bounds.w, bounds.h, 4, bg_color); + // Center text + int tw = text_width(text); + int tx = bounds.x + (bounds.w - tw) / 2; + int ty = bounds.y + (bounds.h - FONT_HEIGHT) / 2; + draw_text(fb, tx, ty, text, fg); + } + + bool handle_mouse(const MouseEvent& ev) { + hovered = bounds.contains(ev.x, ev.y); + if (hovered && ev.left_pressed()) { + pressed = true; + } + if (pressed && ev.left_released()) { + pressed = false; + if (hovered && on_click) { + on_click(userdata); + return true; + } + } + if (!ev.left_held()) { + pressed = false; + } + return false; + } +}; + +// ---- IconButton (for panel/menu items with SVG icon + optional text) ---- + +struct IconButton { + Rect bounds; + const char* text; // optional label (can be nullptr) + uint32_t* icon_pixels; // icon pixel data (ARGB) + int icon_w, icon_h; + Color bg; + Color hover_bg; + Color text_color; + bool hovered; + bool pressed; + ClickCallback on_click; + void* userdata; + + void init(int x, int y, int w, int h) { + bounds = {x, y, w, h}; + text = nullptr; + icon_pixels = nullptr; + icon_w = 0; + icon_h = 0; + bg = {0, 0, 0, 0}; // transparent by default + hover_bg = colors::MENU_HOVER; + text_color = colors::TEXT_COLOR; + hovered = false; + pressed = false; + on_click = nullptr; + userdata = nullptr; + } + + void draw(Framebuffer& fb) const { + if (hovered) { + fill_rounded_rect(fb, bounds.x, bounds.y, bounds.w, bounds.h, 3, hover_bg); + } else if (bg.a > 0) { + fill_rounded_rect(fb, bounds.x, bounds.y, bounds.w, bounds.h, 3, bg); + } + + int content_x = bounds.x + 6; + + // Draw icon + if (icon_pixels && icon_w > 0 && icon_h > 0) { + int iy = bounds.y + (bounds.h - icon_h) / 2; + fb.blit_alpha(content_x, iy, icon_w, icon_h, icon_pixels); + content_x += icon_w + 6; + } + + // Draw text + if (text) { + int ty = bounds.y + (bounds.h - FONT_HEIGHT) / 2; + draw_text(fb, content_x, ty, text, text_color); + } + } + + bool handle_mouse(const MouseEvent& ev) { + hovered = bounds.contains(ev.x, ev.y); + if (hovered && ev.left_pressed()) { + pressed = true; + } + if (pressed && ev.left_released()) { + pressed = false; + if (hovered && on_click) { + on_click(userdata); + return true; + } + } + if (!ev.left_held()) { + pressed = false; + } + return false; + } +}; + +// ---- TextBox ---- + +struct TextBox { + Rect bounds; + char text[256]; + int cursor; + int text_len; + bool focused; + Color bg; + Color fg; + Color border_color; + Color cursor_color; + + void init(int x, int y, int w, int h) { + bounds = {x, y, w, h}; + text[0] = '\0'; + cursor = 0; + text_len = 0; + focused = false; + bg = colors::WHITE; + fg = colors::TEXT_COLOR; + border_color = colors::BORDER; + cursor_color = colors::ACCENT; + } + + void draw(Framebuffer& fb) const { + fb.fill_rect(bounds.x, bounds.y, bounds.w, bounds.h, bg); + draw_rect(fb, bounds.x, bounds.y, bounds.w, bounds.h, + focused ? cursor_color : border_color); + + // Draw text with 4px padding + int tx = bounds.x + 4; + int ty = bounds.y + (bounds.h - FONT_HEIGHT) / 2; + draw_text(fb, tx, ty, text, fg); + + // Draw cursor if focused + if (focused) { + int cx = tx + cursor * FONT_WIDTH; + draw_vline(fb, cx, ty, FONT_HEIGHT, cursor_color); + } + } + + void handle_mouse(const MouseEvent& ev) { + if (ev.left_pressed()) { + focused = bounds.contains(ev.x, ev.y); + } + } + + void handle_key(const Zenith::KeyEvent& key) { + if (!focused || !key.pressed) return; + + if (key.ascii == '\b' || key.scancode == 0x0E) { + // Backspace + if (cursor > 0) { + for (int i = cursor - 1; i < text_len - 1; i++) { + text[i] = text[i + 1]; + } + text_len--; + cursor--; + text[text_len] = '\0'; + } + } else if (key.ascii >= 32 && key.ascii < 127) { + // Printable character + if (text_len < 254) { + for (int i = text_len; i > cursor; i--) { + text[i] = text[i - 1]; + } + text[cursor] = key.ascii; + cursor++; + text_len++; + text[text_len] = '\0'; + } + } else if (key.scancode == 0x4B) { + // Left arrow + if (cursor > 0) cursor--; + } else if (key.scancode == 0x4D) { + // Right arrow + if (cursor < text_len) cursor++; + } + } +}; + +// ---- Scrollbar ---- + +struct Scrollbar { + Rect bounds; + int content_height; + int view_height; + int scroll_offset; + bool dragging; + int drag_start_y; + int drag_start_offset; + Color bg; + Color fg; + Color hover_fg; + bool hovered; + + void init(int x, int y, int w, int h) { + bounds = {x, y, w, h}; + content_height = 0; + view_height = h; + scroll_offset = 0; + dragging = false; + drag_start_y = 0; + drag_start_offset = 0; + bg = colors::SCROLLBAR_BG; + fg = colors::SCROLLBAR_FG; + hover_fg = Color::from_rgb(0xA0, 0xA0, 0xA0); + hovered = false; + } + + int thumb_height() const { + if (content_height <= view_height) return bounds.h; + int th = (view_height * bounds.h) / content_height; + return th < 20 ? 20 : th; + } + + int thumb_y() const { + if (content_height <= view_height) return bounds.y; + int range = bounds.h - thumb_height(); + int max_scroll = content_height - view_height; + if (max_scroll <= 0) return bounds.y; + return bounds.y + (scroll_offset * range) / max_scroll; + } + + int max_scroll() const { + int ms = content_height - view_height; + return ms > 0 ? ms : 0; + } + + void draw(Framebuffer& fb) const { + if (content_height <= view_height) return; // no scrollbar needed + + fb.fill_rect(bounds.x, bounds.y, bounds.w, bounds.h, bg); + int th = thumb_height(); + int ty = thumb_y(); + Color thumb_color = (hovered || dragging) ? hover_fg : fg; + fill_rounded_rect(fb, bounds.x + 1, ty, bounds.w - 2, th, 3, thumb_color); + } + + void handle_mouse(const MouseEvent& ev) { + if (content_height <= view_height) return; + + Rect thumb_rect = {bounds.x, thumb_y(), bounds.w, thumb_height()}; + hovered = thumb_rect.contains(ev.x, ev.y); + + if (hovered && ev.left_pressed()) { + dragging = true; + drag_start_y = ev.y; + drag_start_offset = scroll_offset; + } + + if (dragging && ev.left_held()) { + int dy = ev.y - drag_start_y; + int range = bounds.h - thumb_height(); + if (range > 0) { + int ms = max_scroll(); + scroll_offset = drag_start_offset + (dy * ms) / range; + if (scroll_offset < 0) scroll_offset = 0; + if (scroll_offset > ms) scroll_offset = ms; + } + } + + if (!ev.left_held()) { + dragging = false; + } + + // Handle scroll wheel + if (bounds.contains(ev.x, ev.y) && ev.scroll != 0) { + scroll_offset += ev.scroll * 20; + int ms = max_scroll(); + if (scroll_offset < 0) scroll_offset = 0; + if (scroll_offset > ms) scroll_offset = ms; + } + } +}; + +} // namespace gui diff --git a/programs/include/gui/window.hpp b/programs/include/gui/window.hpp new file mode 100644 index 0000000..67f42a4 --- /dev/null +++ b/programs/include/gui/window.hpp @@ -0,0 +1,78 @@ +/* + * window.hpp + * ZenithOS window management types + * Copyright (c) 2026 Daniel Hammer +*/ + +#pragma once +#include "gui/gui.hpp" +#include "gui/framebuffer.hpp" +#include "gui/widgets.hpp" +#include + +namespace gui { + +enum WindowState { WIN_NORMAL, WIN_MINIMIZED, WIN_MAXIMIZED, WIN_CLOSED }; + +static constexpr int TITLEBAR_HEIGHT = 30; +static constexpr int BORDER_WIDTH = 1; +static constexpr int SHADOW_SIZE = 3; +static constexpr int BTN_RADIUS = 6; +static constexpr int MAX_TITLE_LEN = 64; + +struct Window; +using WindowDrawCallback = void (*)(Window* win, Framebuffer& fb); +using WindowMouseCallback = void (*)(Window* win, MouseEvent& ev); +using WindowKeyCallback = void (*)(Window* win, const Zenith::KeyEvent& key); +using WindowCloseCallback = void (*)(Window* win); + +struct Window { + char title[MAX_TITLE_LEN]; + Rect frame; + WindowState state; + int z_order; + bool focused; + bool dirty; + + uint32_t* content; + int content_w, content_h; + + bool dragging; + int drag_offset_x, drag_offset_y; + + bool resizing; + + Rect saved_frame; + + WindowDrawCallback on_draw; + WindowMouseCallback on_mouse; + WindowKeyCallback on_key; + WindowCloseCallback on_close; + void* app_data; + + Rect titlebar_rect() const { + return {frame.x, frame.y, frame.w, TITLEBAR_HEIGHT}; + } + + Rect content_rect() const { + return {frame.x + BORDER_WIDTH, frame.y + TITLEBAR_HEIGHT, + frame.w - 2 * BORDER_WIDTH, frame.h - TITLEBAR_HEIGHT - BORDER_WIDTH}; + } + + Rect close_btn_rect() const { + int by = frame.y + (TITLEBAR_HEIGHT - BTN_RADIUS * 2) / 2; + return {frame.x + 12, by, BTN_RADIUS * 2, BTN_RADIUS * 2}; + } + + Rect min_btn_rect() const { + int by = frame.y + (TITLEBAR_HEIGHT - BTN_RADIUS * 2) / 2; + return {frame.x + 12 + 22, by, BTN_RADIUS * 2, BTN_RADIUS * 2}; + } + + Rect max_btn_rect() const { + int by = frame.y + (TITLEBAR_HEIGHT - BTN_RADIUS * 2) / 2; + return {frame.x + 12 + 44, by, BTN_RADIUS * 2, BTN_RADIUS * 2}; + } +}; + +} // namespace gui diff --git a/programs/include/zenith/syscall.h b/programs/include/zenith/syscall.h index a07486b..9aae5e4 100644 --- a/programs/include/zenith/syscall.h +++ b/programs/include/zenith/syscall.h @@ -256,4 +256,27 @@ namespace zenith { __builtin_unreachable(); } + // Mouse + inline void mouse_state(Zenith::MouseState* out) { syscall1(Zenith::SYS_MOUSESTATE, (uint64_t)out); } + inline void set_mouse_bounds(int32_t maxX, int32_t maxY) { + syscall2(Zenith::SYS_SETMOUSEBOUNDS, (uint64_t)maxX, (uint64_t)maxY); + } + + // I/O redirection + inline int spawn_redir(const char* path, const char* args = nullptr) { + return (int)syscall2(Zenith::SYS_SPAWN_REDIR, (uint64_t)path, (uint64_t)args); + } + inline int childio_read(int childPid, char* buf, int maxLen) { + return (int)syscall3(Zenith::SYS_CHILDIO_READ, (uint64_t)childPid, (uint64_t)buf, (uint64_t)maxLen); + } + inline int childio_write(int childPid, const char* data, int len) { + return (int)syscall3(Zenith::SYS_CHILDIO_WRITE, (uint64_t)childPid, (uint64_t)data, (uint64_t)len); + } + inline int childio_writekey(int childPid, const Zenith::KeyEvent* key) { + return (int)syscall2(Zenith::SYS_CHILDIO_WRITEKEY, (uint64_t)childPid, (uint64_t)key); + } + inline int childio_settermsz(int childPid, int cols, int rows) { + return (int)syscall3(Zenith::SYS_CHILDIO_SETTERMSZ, (uint64_t)childPid, (uint64_t)cols, (uint64_t)rows); + } + } diff --git a/programs/obj/hello/main.o b/programs/obj/hello/main.o index dcdbf6c95a526ed130725a66007d8576bc848915..bb43a93be400a134baeef3489426440ccf8f1e63 100644 GIT binary patch delta 2328 zcmZ9NUu@G=6vyxHw{~uw8|&8g`YUd2w<%D`+WiSbGP{+v(z>yhwF?ra+YAm@$=m`M z5?!i^Gy0-5C&7e3m_h?oWmTi>cbRmPa!C8s_)CFHbUP6y?5SWIPF zxvaqgaK_S-ZMHIIn-G&ZbZKah)>&UGfwnhGHWulj&vsbnN}%31$aXFX|YOYKXI_Qm1@k$7Ts zC>oBi(b37NBW>;5y+@}GPad3l`2dqHyA#8yXeu2}M3_4#m^a{^&lqW9zK` z9|U*Rb$==u-a9DLM&d&%OL92f7Yi5dR5Y!U?o131MpF6pswU0SKakj!cU0fh@(*f) zx-lzSD@SK>VK%YKn;(U+of|IIR>p>i`W?&&wHIT@h$vy$#0ZiFy&*>UjJDR`nH8JMqNJgwG>iCHzasiL>@&B@c)?0#}5(hG*4c zMP`3a!#$xcVdl+5eGz>1+^}G5FHr&Z)N}1DOx6dC0{To7pWCn~GNe#_kEq9BRj65{ z^F;jz?2dr;ErcE1=*A2M;`1)dIC#7Y>%T=*H}>Q{;Y>blIWVi)jZ?5J&bo+Ej}i4p z(40Je8EKHH-56z7YUZp#9wYt*7kJCL6u zoFO+~qFM8wMGl)>cI_8<+7&Rq#tz;f8Dj9Zi@WDA&t0NEVS&$Gty%_FT|6s4GIDsa zc=NCqF!ff#Gq~SQ_#o~hgzvySNy1+(7L{cqMA(GYzCw7hOva87ehDvd0$1|_57F-v z!Y45QdBy9+mtJI+AEi$*;4>KKT>C-I*C5Ba@mom>`9D#EwcLa&!t;*uybt#{&zetI z=9HdKqNfF)w#i$NR};Psxt(zH1L`W_j|ks(^lvHh9sgbC0=7L+5+E;m0I#x*@Sk9h z!L#Ng7$EA;7&T3}7f(4)_+Mr#317$Fe?fR-k-OO?B2;6*H()pTma9a4h{rDz-k)DI zx~%&1c35kCR=W;up03Ji_5aG)4VdwC>B(|f@PxEwxb5lDV;jNm4e1RPkP*w$MpzKb z?h05F%Uz-QLfUDV^!4b;$6>)2svMDx6vHMGbEs(Y>Jv5KZwl$(Z-9(gRyM$bSPBiW bCKhik_?ts|uN^YYp~_ng#n``LvBC2%U{3<% delta 2015 zcmZ9NYe*DP6vyYz?zp*ItJ|*LMlE;U#ooDExFI#VMUM?XsFm~})F?~}3$!T9Hlq*u zA<9k}h}4Iof(nWa5+zCqBB-dK7o|P0NJv6@sYG;V=ZtLU!p^ekWU4l5SYDAYBRAu39C@{>=(u z#a%lh*55;IL2CdMe_`H6x zcH9yVy^d;#{Ca@o&}DODf0PcZtE#H5zA?XGp?7zELtSnC)-7<~eiu3&dC=#0YAaj2 zX6edsMeNnY92T=U`&g_$r9ftGa82gXweeS$q-A<;G3?@}_w@^Tg$~6q`61b`*BjF~ zA4OhGc(ugT%3=gLrEoUwDTw_BQbr zLXDe8cB1zy@eX4rBZN;!y%lSkyL29UMXgHoW)W{C42xPe%(;Mg2hc7dya8=d8|pP;-xHY!FW4(PDg~x5Rr7 z`4_^kV?RF#KZaE#j5FWG?0X{Niwr%yOmnGMFjs(R_5e%gk!M(O5%FF?Zk`>p;wJ25 z4beA1jmTDrbO-T1Mtd*eAJINS_;lzM*&bjIoy6OY{4(KD?CmDur@_bb*jXs&Ty>*w zfM_zIg>$*b0v&u_)VP@>$%BQ=mp6`sBzXysVBu_>O??~cW)q%|#e;+|G4!$&g5fEg zRm7hg!KZSyHbJUiv`*}0JCv)OHO7_A(4z8aD^cd6(mX?Yb9#mV@^+#xMBYL80_5is zxJ|GE|MG?ojaImPl_;qq(t zPZNw(XRL78Unn1#1l@j3?svkNm`0pX6wu_7ENBwb!W8Hh)4Eg`3uwvfvW&o=5YEp2 E2iOtMFaQ7m diff --git a/programs/obj/shell/main.o b/programs/obj/shell/main.o index c92f767c6765edcf6be45da207b55b98902a868c..9cb6b0a77434462ea7915f143593d860af2566a4 100644 GIT binary patch literal 135952 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

V^2zBYr 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 Utt9`({@ePO(f@_C0$mLKKU}+Lod5s; literal 121376 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 YJ?zz$tI>U;|8#pj0b~i?fUZXV2Z=vU7XSbN diff --git a/programs/src/desktop/Makefile b/programs/src/desktop/Makefile new file mode 100644 index 0000000..9921374 --- /dev/null +++ b/programs/src/desktop/Makefile @@ -0,0 +1,86 @@ +# Makefile for desktop (GUI desktop environment) on ZenithOS +# Copyright (c) 2025 Daniel Hammer + +MAKEFLAGS += -rR +.SUFFIXES: + +# ---- Toolchain ---- + +TOOLCHAIN_PREFIX := $(shell cd ../../.. && pwd)/toolchain/local/bin/x86_64-elf- +ifneq ($(wildcard $(TOOLCHAIN_PREFIX)gcc),) + CXX := $(TOOLCHAIN_PREFIX)g++ +else + CXX := g++ +endif + +# ---- Paths ---- + +PROG_INC := ../../include +LINK_LD := ../../link.ld +BINDIR := ../../bin +OBJDIR := obj + +# ---- Compiler flags ---- + +CXXFLAGS := \ + -std=gnu++20 \ + -g -O2 -pipe \ + -Wall \ + -Wextra \ + -Wno-unused-parameter \ + -Wno-unused-function \ + -nostdinc \ + -ffreestanding \ + -fno-stack-protector \ + -fno-stack-check \ + -fno-PIC \ + -fno-rtti \ + -fno-exceptions \ + -ffunction-sections \ + -fdata-sections \ + -m64 \ + -march=x86-64 \ + -mno-80387 \ + -mno-mmx \ + -mno-sse \ + -mno-sse2 \ + -mno-red-zone \ + -mcmodel=small \ + -I $(PROG_INC) \ + -isystem ../../../kernel/freestnd-c-hdrs/x86_64/include \ + -isystem ../../../kernel/freestnd-cxx-hdrs/x86_64/include + +# ---- Linker flags ---- + +LDFLAGS := \ + -nostdlib \ + -static \ + -Wl,--build-id=none \ + -Wl,--gc-sections \ + -Wl,-m,elf_x86_64 \ + -z max-page-size=0x1000 \ + -T $(LINK_LD) + +# ---- Source files ---- + +SRCS := main.cpp font_data.cpp +OBJS := $(addprefix $(OBJDIR)/,$(SRCS:.cpp=.o)) + +# ---- Target ---- + +TARGET := $(BINDIR)/os/desktop.elf + +.PHONY: all clean + +all: $(TARGET) + +$(TARGET): $(OBJS) $(LINK_LD) Makefile + mkdir -p $(BINDIR)/os + $(CXX) $(CXXFLAGS) $(LDFLAGS) $(OBJS) -o $@ + +$(OBJDIR)/%.o: %.cpp Makefile + mkdir -p $(OBJDIR) + $(CXX) $(CXXFLAGS) -c $< -o $@ + +clean: + rm -rf $(OBJDIR) $(TARGET) diff --git a/programs/src/desktop/font_data.cpp b/programs/src/desktop/font_data.cpp new file mode 100644 index 0000000..940f6e1 --- /dev/null +++ b/programs/src/desktop/font_data.cpp @@ -0,0 +1,783 @@ +/* + * font_data.cpp + * Standard VGA 8x16 bitmap font (Code Page 437) + * 256 characters, 16 bytes each (8 pixels wide, 1 bit per pixel, MSB left) + * Copyright (c) 2025 Daniel Hammer +*/ + +#include "gui/font.hpp" + +namespace gui { + +const uint8_t font_data[256 * 16] = { + // Character 0 (NUL) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 1 (smiley face) + 0x00, 0x00, 0x7E, 0x81, 0xA5, 0x81, 0x81, 0xBD, + 0x99, 0x81, 0x81, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 2 (inverse smiley) + 0x00, 0x00, 0x7E, 0xFF, 0xDB, 0xFF, 0xFF, 0xC3, + 0xE7, 0xFF, 0xFF, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 3 (heart) + 0x00, 0x00, 0x00, 0x00, 0x6C, 0xFE, 0xFE, 0xFE, + 0xFE, 0x7C, 0x38, 0x10, 0x00, 0x00, 0x00, 0x00, + // Character 4 (diamond) + 0x00, 0x00, 0x00, 0x00, 0x10, 0x38, 0x7C, 0xFE, + 0x7C, 0x38, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 5 (club) + 0x00, 0x00, 0x00, 0x18, 0x3C, 0x3C, 0xE7, 0xE7, + 0xE7, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 6 (spade) + 0x00, 0x00, 0x00, 0x18, 0x3C, 0x7E, 0xFF, 0xFF, + 0x7E, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 7 (bullet) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x3C, + 0x3C, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 8 (inverse bullet) + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xE7, 0xC3, + 0xC3, 0xE7, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + // Character 9 (circle) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x3C, 0x66, 0x42, + 0x42, 0x66, 0x3C, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 10 (inverse circle) + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC3, 0x99, 0xBD, + 0xBD, 0x99, 0xC3, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + // Character 11 (male sign) + 0x00, 0x00, 0x1E, 0x0E, 0x1A, 0x32, 0x78, 0xCC, + 0xCC, 0xCC, 0xCC, 0x78, 0x00, 0x00, 0x00, 0x00, + // Character 12 (female sign) + 0x00, 0x00, 0x3C, 0x66, 0x66, 0x66, 0x66, 0x3C, + 0x18, 0x7E, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 13 (note) + 0x00, 0x00, 0x3F, 0x33, 0x3F, 0x30, 0x30, 0x30, + 0x30, 0x70, 0xF0, 0xE0, 0x00, 0x00, 0x00, 0x00, + // Character 14 (double note) + 0x00, 0x00, 0x7F, 0x63, 0x7F, 0x63, 0x63, 0x63, + 0x63, 0x67, 0xE7, 0xE6, 0xC0, 0x00, 0x00, 0x00, + // Character 15 (sun) + 0x00, 0x00, 0x00, 0x18, 0x18, 0xDB, 0x3C, 0xE7, + 0x3C, 0xDB, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 16 (right triangle) + 0x00, 0x80, 0xC0, 0xE0, 0xF0, 0xF8, 0xFE, 0xF8, + 0xF0, 0xE0, 0xC0, 0x80, 0x00, 0x00, 0x00, 0x00, + // Character 17 (left triangle) + 0x00, 0x02, 0x06, 0x0E, 0x1E, 0x3E, 0xFE, 0x3E, + 0x1E, 0x0E, 0x06, 0x02, 0x00, 0x00, 0x00, 0x00, + // Character 18 (up-down arrow) + 0x00, 0x00, 0x18, 0x3C, 0x7E, 0x18, 0x18, 0x18, + 0x7E, 0x3C, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 19 (double exclamation) + 0x00, 0x00, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, + 0x66, 0x00, 0x66, 0x66, 0x00, 0x00, 0x00, 0x00, + // Character 20 (paragraph) + 0x00, 0x00, 0x7F, 0xDB, 0xDB, 0xDB, 0x7B, 0x1B, + 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00, 0x00, 0x00, + // Character 21 (section) + 0x00, 0x7C, 0xC6, 0x60, 0x38, 0x6C, 0xC6, 0xC6, + 0x6C, 0x38, 0x0C, 0xC6, 0x7C, 0x00, 0x00, 0x00, + // Character 22 (thick underscore) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0xFE, 0xFE, 0xFE, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 23 (up-down arrow underlined) + 0x00, 0x00, 0x18, 0x3C, 0x7E, 0x18, 0x18, 0x18, + 0x7E, 0x3C, 0x18, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 24 (up arrow) + 0x00, 0x00, 0x18, 0x3C, 0x7E, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 25 (down arrow) + 0x00, 0x00, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + 0x18, 0x7E, 0x3C, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 26 (right arrow) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0C, 0xFE, + 0x0C, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 27 (left arrow) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x60, 0xFE, + 0x60, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 28 (right angle) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0xC0, + 0xC0, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 29 (left-right arrow) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x24, 0x66, 0xFF, + 0x66, 0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 30 (up triangle) + 0x00, 0x00, 0x00, 0x00, 0x10, 0x38, 0x38, 0x7C, + 0x7C, 0xFE, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 31 (down triangle) + 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFE, 0x7C, 0x7C, + 0x38, 0x38, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 32 (space) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 33 '!' + 0x00, 0x00, 0x18, 0x3C, 0x3C, 0x3C, 0x18, 0x18, + 0x18, 0x00, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 34 '"' + 0x00, 0x66, 0x66, 0x66, 0x24, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 35 '#' + 0x00, 0x00, 0x00, 0x6C, 0x6C, 0xFE, 0x6C, 0x6C, + 0x6C, 0xFE, 0x6C, 0x6C, 0x00, 0x00, 0x00, 0x00, + // Character 36 '$' + 0x18, 0x18, 0x7C, 0xC6, 0xC2, 0xC0, 0x7C, 0x06, + 0x06, 0x86, 0xC6, 0x7C, 0x18, 0x18, 0x00, 0x00, + // Character 37 '%' + 0x00, 0x00, 0x00, 0x00, 0xC2, 0xC6, 0x0C, 0x18, + 0x30, 0x60, 0xC6, 0x86, 0x00, 0x00, 0x00, 0x00, + // Character 38 '&' + 0x00, 0x00, 0x38, 0x6C, 0x6C, 0x38, 0x76, 0xDC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 39 ''' + 0x00, 0x30, 0x30, 0x30, 0x60, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 40 '(' + 0x00, 0x00, 0x0C, 0x18, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x18, 0x0C, 0x00, 0x00, 0x00, 0x00, + // Character 41 ')' + 0x00, 0x00, 0x30, 0x18, 0x0C, 0x0C, 0x0C, 0x0C, + 0x0C, 0x0C, 0x18, 0x30, 0x00, 0x00, 0x00, 0x00, + // Character 42 '*' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x66, 0x3C, 0xFF, + 0x3C, 0x66, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 43 '+' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x7E, + 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 44 ',' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x18, 0x18, 0x18, 0x30, 0x00, 0x00, 0x00, + // Character 45 '-' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 46 '.' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 47 '/' + 0x00, 0x00, 0x00, 0x00, 0x02, 0x06, 0x0C, 0x18, + 0x30, 0x60, 0xC0, 0x80, 0x00, 0x00, 0x00, 0x00, + // Character 48 '0' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xCE, 0xDE, 0xF6, + 0xE6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 49 '1' + 0x00, 0x00, 0x18, 0x38, 0x78, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 50 '2' + 0x00, 0x00, 0x7C, 0xC6, 0x06, 0x0C, 0x18, 0x30, + 0x60, 0xC0, 0xC6, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 51 '3' + 0x00, 0x00, 0x7C, 0xC6, 0x06, 0x06, 0x3C, 0x06, + 0x06, 0x06, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 52 '4' + 0x00, 0x00, 0x0C, 0x1C, 0x3C, 0x6C, 0xCC, 0xFE, + 0x0C, 0x0C, 0x0C, 0x1E, 0x00, 0x00, 0x00, 0x00, + // Character 53 '5' + 0x00, 0x00, 0xFE, 0xC0, 0xC0, 0xC0, 0xFC, 0x06, + 0x06, 0x06, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 54 '6' + 0x00, 0x00, 0x38, 0x60, 0xC0, 0xC0, 0xFC, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 55 '7' + 0x00, 0x00, 0xFE, 0xC6, 0x06, 0x06, 0x0C, 0x18, + 0x30, 0x30, 0x30, 0x30, 0x00, 0x00, 0x00, 0x00, + // Character 56 '8' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0x7C, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 57 '9' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0x7E, 0x06, + 0x06, 0x06, 0x0C, 0x78, 0x00, 0x00, 0x00, 0x00, + // Character 58 ':' + 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x00, 0x00, + 0x00, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 59 ';' + 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x00, 0x00, + 0x00, 0x18, 0x18, 0x30, 0x00, 0x00, 0x00, 0x00, + // Character 60 '<' + 0x00, 0x00, 0x00, 0x06, 0x0C, 0x18, 0x30, 0x60, + 0x30, 0x18, 0x0C, 0x06, 0x00, 0x00, 0x00, 0x00, + // Character 61 '=' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7E, 0x00, 0x00, + 0x7E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 62 '>' + 0x00, 0x00, 0x00, 0x60, 0x30, 0x18, 0x0C, 0x06, + 0x0C, 0x18, 0x30, 0x60, 0x00, 0x00, 0x00, 0x00, + // Character 63 '?' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0x0C, 0x18, 0x18, + 0x18, 0x00, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 64 '@' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0xDE, 0xDE, + 0xDE, 0xDC, 0xC0, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 65 'A' + 0x00, 0x00, 0x10, 0x38, 0x6C, 0xC6, 0xC6, 0xFE, + 0xC6, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 66 'B' + 0x00, 0x00, 0xFC, 0x66, 0x66, 0x66, 0x7C, 0x66, + 0x66, 0x66, 0x66, 0xFC, 0x00, 0x00, 0x00, 0x00, + // Character 67 'C' + 0x00, 0x00, 0x3C, 0x66, 0xC2, 0xC0, 0xC0, 0xC0, + 0xC0, 0xC2, 0x66, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 68 'D' + 0x00, 0x00, 0xF8, 0x6C, 0x66, 0x66, 0x66, 0x66, + 0x66, 0x66, 0x6C, 0xF8, 0x00, 0x00, 0x00, 0x00, + // Character 69 'E' + 0x00, 0x00, 0xFE, 0x66, 0x62, 0x68, 0x78, 0x68, + 0x60, 0x62, 0x66, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 70 'F' + 0x00, 0x00, 0xFE, 0x66, 0x62, 0x68, 0x78, 0x68, + 0x60, 0x60, 0x60, 0xF0, 0x00, 0x00, 0x00, 0x00, + // Character 71 'G' + 0x00, 0x00, 0x3C, 0x66, 0xC2, 0xC0, 0xC0, 0xDE, + 0xC6, 0xC6, 0x66, 0x3A, 0x00, 0x00, 0x00, 0x00, + // Character 72 'H' + 0x00, 0x00, 0xC6, 0xC6, 0xC6, 0xC6, 0xFE, 0xC6, + 0xC6, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 73 'I' + 0x00, 0x00, 0x3C, 0x18, 0x18, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 74 'J' + 0x00, 0x00, 0x1E, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, + 0xCC, 0xCC, 0xCC, 0x78, 0x00, 0x00, 0x00, 0x00, + // Character 75 'K' + 0x00, 0x00, 0xE6, 0x66, 0x66, 0x6C, 0x78, 0x78, + 0x6C, 0x66, 0x66, 0xE6, 0x00, 0x00, 0x00, 0x00, + // Character 76 'L' + 0x00, 0x00, 0xF0, 0x60, 0x60, 0x60, 0x60, 0x60, + 0x60, 0x62, 0x66, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 77 'M' + 0x00, 0x00, 0xC6, 0xEE, 0xFE, 0xFE, 0xD6, 0xC6, + 0xC6, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 78 'N' + 0x00, 0x00, 0xC6, 0xE6, 0xF6, 0xFE, 0xDE, 0xCE, + 0xC6, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 79 'O' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 80 'P' + 0x00, 0x00, 0xFC, 0x66, 0x66, 0x66, 0x7C, 0x60, + 0x60, 0x60, 0x60, 0xF0, 0x00, 0x00, 0x00, 0x00, + // Character 81 'Q' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xD6, 0xDE, 0x7C, 0x0C, 0x0E, 0x00, 0x00, + // Character 82 'R' + 0x00, 0x00, 0xFC, 0x66, 0x66, 0x66, 0x7C, 0x6C, + 0x66, 0x66, 0x66, 0xE6, 0x00, 0x00, 0x00, 0x00, + // Character 83 'S' + 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0x60, 0x38, 0x0C, + 0x06, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 84 'T' + 0x00, 0x00, 0xFF, 0xDB, 0x99, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 85 'U' + 0x00, 0x00, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 86 'V' + 0x00, 0x00, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0x6C, 0x38, 0x10, 0x00, 0x00, 0x00, 0x00, + // Character 87 'W' + 0x00, 0x00, 0xC6, 0xC6, 0xC6, 0xC6, 0xD6, 0xD6, + 0xD6, 0xFE, 0xEE, 0x6C, 0x00, 0x00, 0x00, 0x00, + // Character 88 'X' + 0x00, 0x00, 0xC6, 0xC6, 0x6C, 0x7C, 0x38, 0x38, + 0x7C, 0x6C, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 89 'Y' + 0x00, 0x00, 0xC6, 0xC6, 0xC6, 0x6C, 0x38, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 90 'Z' + 0x00, 0x00, 0xFE, 0xC6, 0x86, 0x0C, 0x18, 0x30, + 0x60, 0xC2, 0xC6, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 91 '[' + 0x00, 0x00, 0x3C, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 92 '\' + 0x00, 0x00, 0x00, 0x80, 0xC0, 0xE0, 0x70, 0x38, + 0x1C, 0x0E, 0x06, 0x02, 0x00, 0x00, 0x00, 0x00, + // Character 93 ']' + 0x00, 0x00, 0x3C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, + 0x0C, 0x0C, 0x0C, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 94 '^' + 0x10, 0x38, 0x6C, 0xC6, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 95 '_' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0xFF, 0x00, 0x00, 0x00, + // Character 96 '`' + 0x30, 0x30, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 97 'a' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 98 'b' + 0x00, 0x00, 0xE0, 0x60, 0x60, 0x78, 0x6C, 0x66, + 0x66, 0x66, 0x66, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 99 'c' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C, 0xC6, 0xC0, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 100 'd' + 0x00, 0x00, 0x1C, 0x0C, 0x0C, 0x3C, 0x6C, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 101 'e' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C, 0xC6, 0xFE, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 102 'f' + 0x00, 0x00, 0x38, 0x6C, 0x64, 0x60, 0xF0, 0x60, + 0x60, 0x60, 0x60, 0xF0, 0x00, 0x00, 0x00, 0x00, + // Character 103 'g' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x7C, 0x0C, 0xCC, 0x78, 0x00, + // Character 104 'h' + 0x00, 0x00, 0xE0, 0x60, 0x60, 0x6C, 0x76, 0x66, + 0x66, 0x66, 0x66, 0xE6, 0x00, 0x00, 0x00, 0x00, + // Character 105 'i' + 0x00, 0x00, 0x18, 0x18, 0x00, 0x38, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 106 'j' + 0x00, 0x00, 0x06, 0x06, 0x00, 0x0E, 0x06, 0x06, + 0x06, 0x06, 0x06, 0x06, 0x66, 0x66, 0x3C, 0x00, + // Character 107 'k' + 0x00, 0x00, 0xE0, 0x60, 0x60, 0x66, 0x6C, 0x78, + 0x78, 0x6C, 0x66, 0xE6, 0x00, 0x00, 0x00, 0x00, + // Character 108 'l' + 0x00, 0x00, 0x38, 0x18, 0x18, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 109 'm' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xEC, 0xFE, 0xD6, + 0xD6, 0xD6, 0xD6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 110 'n' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xDC, 0x66, 0x66, + 0x66, 0x66, 0x66, 0x66, 0x00, 0x00, 0x00, 0x00, + // Character 111 'o' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 112 'p' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xDC, 0x66, 0x66, + 0x66, 0x66, 0x66, 0x7C, 0x60, 0x60, 0xF0, 0x00, + // Character 113 'q' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x7C, 0x0C, 0x0C, 0x1E, 0x00, + // Character 114 'r' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xDC, 0x76, 0x66, + 0x60, 0x60, 0x60, 0xF0, 0x00, 0x00, 0x00, 0x00, + // Character 115 's' + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C, 0xC6, 0x60, + 0x38, 0x0C, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 116 't' + 0x00, 0x00, 0x10, 0x30, 0x30, 0xFC, 0x30, 0x30, + 0x30, 0x30, 0x36, 0x1C, 0x00, 0x00, 0x00, 0x00, + // Character 117 'u' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xCC, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 118 'v' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xC6, 0xC6, 0xC6, + 0xC6, 0x6C, 0x38, 0x10, 0x00, 0x00, 0x00, 0x00, + // Character 119 'w' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xC6, 0xC6, 0xD6, + 0xD6, 0xD6, 0xFE, 0x6C, 0x00, 0x00, 0x00, 0x00, + // Character 120 'x' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xC6, 0x6C, 0x38, + 0x38, 0x38, 0x6C, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 121 'y' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7E, 0x06, 0x0C, 0xF8, 0x00, + // Character 122 'z' + 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xCC, 0x18, + 0x30, 0x60, 0xC6, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 123 '{' + 0x00, 0x00, 0x0E, 0x18, 0x18, 0x18, 0x70, 0x18, + 0x18, 0x18, 0x18, 0x0E, 0x00, 0x00, 0x00, 0x00, + // Character 124 '|' + 0x00, 0x00, 0x18, 0x18, 0x18, 0x18, 0x00, 0x18, + 0x18, 0x18, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 125 '}' + 0x00, 0x00, 0x70, 0x18, 0x18, 0x18, 0x0E, 0x18, + 0x18, 0x18, 0x18, 0x70, 0x00, 0x00, 0x00, 0x00, + // Character 126 '~' + 0x00, 0x00, 0x76, 0xDC, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 127 (DEL - block) + 0x00, 0x00, 0x00, 0x00, 0x10, 0x38, 0x6C, 0xC6, + 0xC6, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 128 (C cedilla) + 0x00, 0x00, 0x3C, 0x66, 0xC2, 0xC0, 0xC0, 0xC0, + 0xC2, 0x66, 0x3C, 0x0C, 0x06, 0x7C, 0x00, 0x00, + // Character 129 (u umlaut) + 0x00, 0x00, 0xCC, 0x00, 0x00, 0xCC, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 130 (e acute) + 0x00, 0x0C, 0x18, 0x30, 0x00, 0x7C, 0xC6, 0xFE, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 131 (a circumflex) + 0x00, 0x10, 0x38, 0x6C, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 132 (a umlaut) + 0x00, 0x00, 0xCC, 0x00, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 133 (a grave) + 0x00, 0x60, 0x30, 0x18, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 134 (a ring) + 0x00, 0x38, 0x6C, 0x38, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 135 (c cedilla) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C, 0xC6, 0xC0, + 0xC0, 0xC6, 0x7C, 0x0C, 0x06, 0x7C, 0x00, 0x00, + // Character 136 (e circumflex) + 0x00, 0x10, 0x38, 0x6C, 0x00, 0x7C, 0xC6, 0xFE, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 137 (e umlaut) + 0x00, 0x00, 0xC6, 0x00, 0x00, 0x7C, 0xC6, 0xFE, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 138 (e grave) + 0x00, 0x60, 0x30, 0x18, 0x00, 0x7C, 0xC6, 0xFE, + 0xC0, 0xC0, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 139 (i umlaut) + 0x00, 0x00, 0x66, 0x00, 0x00, 0x38, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 140 (i circumflex) + 0x00, 0x18, 0x3C, 0x66, 0x00, 0x38, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 141 (i grave) + 0x00, 0x60, 0x30, 0x18, 0x00, 0x38, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 142 (A umlaut) + 0x00, 0xC6, 0x00, 0x10, 0x38, 0x6C, 0xC6, 0xC6, + 0xFE, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 143 (A ring) + 0x38, 0x6C, 0x38, 0x10, 0x38, 0x6C, 0xC6, 0xC6, + 0xFE, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 144 (E acute) + 0x0C, 0x18, 0x00, 0xFE, 0x66, 0x62, 0x68, 0x78, + 0x68, 0x62, 0x66, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 145 (ae) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x6E, 0x3B, 0x1B, + 0x7E, 0xD8, 0xDC, 0x77, 0x00, 0x00, 0x00, 0x00, + // Character 146 (AE) + 0x00, 0x00, 0x3E, 0x6C, 0xCC, 0xCC, 0xFE, 0xCC, + 0xCC, 0xCC, 0xCC, 0xCE, 0x00, 0x00, 0x00, 0x00, + // Character 147 (o circumflex) + 0x00, 0x10, 0x38, 0x6C, 0x00, 0x7C, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 148 (o umlaut) + 0x00, 0x00, 0xC6, 0x00, 0x00, 0x7C, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 149 (o grave) + 0x00, 0x60, 0x30, 0x18, 0x00, 0x7C, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 150 (u circumflex) + 0x00, 0x30, 0x78, 0xCC, 0x00, 0xCC, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 151 (u grave) + 0x00, 0x60, 0x30, 0x18, 0x00, 0xCC, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 152 (y umlaut) + 0x00, 0x00, 0xC6, 0x00, 0x00, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7E, 0x06, 0x0C, 0x78, 0x00, + // Character 153 (O umlaut) + 0x00, 0xC6, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 154 (U umlaut) + 0x00, 0xC6, 0x00, 0xC6, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 155 (cent) + 0x00, 0x18, 0x18, 0x7C, 0xC6, 0xC0, 0xC0, 0xC0, + 0xC6, 0x7C, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 156 (pound) + 0x00, 0x38, 0x6C, 0x64, 0x60, 0xF0, 0x60, 0x60, + 0x60, 0x60, 0xE6, 0xFC, 0x00, 0x00, 0x00, 0x00, + // Character 157 (yen) + 0x00, 0x00, 0xC6, 0x6C, 0x38, 0x38, 0xFE, 0x38, + 0xFE, 0x38, 0x38, 0x38, 0x00, 0x00, 0x00, 0x00, + // Character 158 (Pt) + 0x00, 0xF8, 0xCC, 0xCC, 0xF8, 0xC4, 0xCC, 0xDE, + 0xCC, 0xCC, 0xCC, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 159 (f hook) + 0x00, 0x0E, 0x1B, 0x18, 0x18, 0x18, 0x7E, 0x18, + 0x18, 0x18, 0xD8, 0x70, 0x00, 0x00, 0x00, 0x00, + // Character 160 (a acute) + 0x00, 0x18, 0x30, 0x60, 0x00, 0x78, 0x0C, 0x7C, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 161 (i acute) + 0x00, 0x0C, 0x18, 0x30, 0x00, 0x38, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 162 (o acute) + 0x00, 0x18, 0x30, 0x60, 0x00, 0x7C, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 163 (u acute) + 0x00, 0x18, 0x30, 0x60, 0x00, 0xCC, 0xCC, 0xCC, + 0xCC, 0xCC, 0xCC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 164 (n tilde) + 0x00, 0x00, 0x76, 0xDC, 0x00, 0xDC, 0x66, 0x66, + 0x66, 0x66, 0x66, 0x66, 0x00, 0x00, 0x00, 0x00, + // Character 165 (N tilde) + 0x76, 0xDC, 0x00, 0xC6, 0xE6, 0xF6, 0xFE, 0xDE, + 0xCE, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 166 (feminine ordinal) + 0x00, 0x3C, 0x6C, 0x6C, 0x3E, 0x00, 0x7E, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 167 (masculine ordinal) + 0x00, 0x38, 0x6C, 0x6C, 0x38, 0x00, 0x7C, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 168 (inverted question) + 0x00, 0x00, 0x30, 0x30, 0x00, 0x30, 0x30, 0x60, + 0xC0, 0xC6, 0xC6, 0x7C, 0x00, 0x00, 0x00, 0x00, + // Character 169 (not left) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xC0, + 0xC0, 0xC0, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 170 (not right) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0x06, + 0x06, 0x06, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 171 (fraction 1/2) + 0x00, 0xC0, 0xC0, 0xC2, 0xC6, 0xCC, 0x18, 0x30, + 0x60, 0xDC, 0x86, 0x0C, 0x18, 0x3E, 0x00, 0x00, + // Character 172 (fraction 1/4) + 0x00, 0xC0, 0xC0, 0xC2, 0xC6, 0xCC, 0x18, 0x30, + 0x66, 0xCE, 0x9E, 0x3E, 0x06, 0x06, 0x00, 0x00, + // Character 173 (inverted exclamation) + 0x00, 0x00, 0x18, 0x18, 0x00, 0x18, 0x18, 0x18, + 0x3C, 0x3C, 0x3C, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 174 (double left angle) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x36, 0x6C, 0xD8, + 0x6C, 0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 175 (double right angle) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xD8, 0x6C, 0x36, + 0x6C, 0xD8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 176 (light shade) + 0x11, 0x44, 0x11, 0x44, 0x11, 0x44, 0x11, 0x44, + 0x11, 0x44, 0x11, 0x44, 0x11, 0x44, 0x11, 0x44, + // Character 177 (medium shade) + 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, + 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, + // Character 178 (dark shade) + 0xDD, 0x77, 0xDD, 0x77, 0xDD, 0x77, 0xDD, 0x77, + 0xDD, 0x77, 0xDD, 0x77, 0xDD, 0x77, 0xDD, 0x77, + // Character 179 (box vertical) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 180 (box vertical-left) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0xF8, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 181 (box double vertical-left single) + 0x18, 0x18, 0x18, 0x18, 0x18, 0xF8, 0x18, 0xF8, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 182 (box double vertical-left) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0xF6, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 183 (box double horizontal-down) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 184 (box double vertical-left single) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0x18, 0xF8, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 185 (box double vertical-left double) + 0x36, 0x36, 0x36, 0x36, 0x36, 0xF6, 0x06, 0xF6, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 186 (box double vertical) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 187 (box double down-left) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0x06, 0xF6, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 188 (box double up-left) + 0x36, 0x36, 0x36, 0x36, 0x36, 0xF6, 0x06, 0xFE, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 189 (box double up-right) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0xFE, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 190 (box horizontal-down) + 0x18, 0x18, 0x18, 0x18, 0x18, 0xF8, 0x18, 0xF8, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 191 (box down-left) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 192 (box up-right) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x1F, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 193 (box horizontal-up) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 194 (box horizontal-down) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 195 (box vertical-right) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x1F, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 196 (box horizontal) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 197 (box cross) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0xFF, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 198 (box single vert-right double) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x1F, 0x18, 0x1F, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 199 (box double vert-right) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x37, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 200 (box double up-right) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x37, 0x30, 0x3F, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 201 (box double down-right) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x3F, 0x30, 0x37, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 202 (box double horizontal-up) + 0x36, 0x36, 0x36, 0x36, 0x36, 0xF7, 0x00, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 203 (box double horizontal-down) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x00, 0xF7, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 204 (box double vertical-right) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x37, 0x30, 0x37, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 205 (box double horizontal) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x00, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 206 (box double cross) + 0x36, 0x36, 0x36, 0x36, 0x36, 0xF7, 0x00, 0xF7, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 207 (box single horiz-up double) + 0x18, 0x18, 0x18, 0x18, 0x18, 0xFF, 0x00, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 208 (box double horizontal-up single) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 209 (box single horiz-down double) + 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x00, 0xFF, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 210 (box double horizontal-down single) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 211 (box double up-right single) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x3F, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 212 (box single up-right double) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x1F, 0x18, 0x1F, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 213 (box single down-right double) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x1F, 0x18, 0x1F, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 214 (box double down-right single) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3F, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 215 (box double cross single) + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0xFF, + 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, + // Character 216 (box single cross double) + 0x18, 0x18, 0x18, 0x18, 0x18, 0xFF, 0x18, 0xFF, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 217 (box up-left) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0xF8, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 218 (box down-right) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1F, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 219 (full block) + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + // Character 220 (bottom half block) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + // Character 221 (left half block) + 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, + 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, + // Character 222 (right half block) + 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, + 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, + // Character 223 (top half block) + 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 224 (alpha) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, 0xDC, 0xD8, + 0xD8, 0xD8, 0xDC, 0x76, 0x00, 0x00, 0x00, 0x00, + // Character 225 (beta/sharp s) + 0x00, 0x00, 0x78, 0xCC, 0xCC, 0xCC, 0xD8, 0xCC, + 0xC6, 0xC6, 0xC6, 0xCC, 0x00, 0x00, 0x00, 0x00, + // Character 226 (gamma) + 0x00, 0x00, 0xFE, 0xC6, 0xC6, 0xC0, 0xC0, 0xC0, + 0xC0, 0xC0, 0xC0, 0xC0, 0x00, 0x00, 0x00, 0x00, + // Character 227 (pi) + 0x00, 0x00, 0x00, 0x00, 0xFE, 0x6C, 0x6C, 0x6C, + 0x6C, 0x6C, 0x6C, 0x6C, 0x00, 0x00, 0x00, 0x00, + // Character 228 (sigma uppercase) + 0x00, 0x00, 0x00, 0xFE, 0xC6, 0x60, 0x30, 0x18, + 0x30, 0x60, 0xC6, 0xFE, 0x00, 0x00, 0x00, 0x00, + // Character 229 (sigma lowercase) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x7E, 0xD8, 0xD8, + 0xD8, 0xD8, 0xD8, 0x70, 0x00, 0x00, 0x00, 0x00, + // Character 230 (mu) + 0x00, 0x00, 0x00, 0x00, 0x66, 0x66, 0x66, 0x66, + 0x66, 0x7C, 0x60, 0x60, 0xC0, 0x00, 0x00, 0x00, + // Character 231 (tau) + 0x00, 0x00, 0x00, 0x00, 0x76, 0xDC, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, + // Character 232 (phi uppercase) + 0x00, 0x00, 0x00, 0x7E, 0x18, 0x3C, 0x66, 0x66, + 0x66, 0x3C, 0x18, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 233 (theta) + 0x00, 0x00, 0x00, 0x38, 0x6C, 0xC6, 0xC6, 0xFE, + 0xC6, 0xC6, 0x6C, 0x38, 0x00, 0x00, 0x00, 0x00, + // Character 234 (omega) + 0x00, 0x00, 0x38, 0x6C, 0xC6, 0xC6, 0xC6, 0xC6, + 0x6C, 0x6C, 0x6C, 0xEE, 0x00, 0x00, 0x00, 0x00, + // Character 235 (delta) + 0x00, 0x00, 0x1E, 0x30, 0x18, 0x0C, 0x3E, 0x66, + 0x66, 0x66, 0x66, 0x3C, 0x00, 0x00, 0x00, 0x00, + // Character 236 (infinity) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, 0xDB, 0xDB, + 0xDB, 0x76, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 237 (phi lowercase) + 0x00, 0x00, 0x00, 0x02, 0x06, 0x7C, 0xCE, 0xDE, + 0xF6, 0xE6, 0x7C, 0xC0, 0x80, 0x00, 0x00, 0x00, + // Character 238 (epsilon) + 0x00, 0x00, 0x1C, 0x30, 0x60, 0x60, 0x7C, 0x60, + 0x60, 0x60, 0x30, 0x1C, 0x00, 0x00, 0x00, 0x00, + // Character 239 (intersection) + 0x00, 0x00, 0x00, 0x7C, 0xC6, 0xC6, 0xC6, 0xC6, + 0xC6, 0xC6, 0xC6, 0xC6, 0x00, 0x00, 0x00, 0x00, + // Character 240 (triple bar) + 0x00, 0x00, 0x00, 0x00, 0xFE, 0x00, 0x00, 0xFE, + 0x00, 0x00, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 241 (plus-minus) + 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x7E, 0x18, + 0x18, 0x00, 0x00, 0xFF, 0x00, 0x00, 0x00, 0x00, + // Character 242 (greater-equal) + 0x00, 0x00, 0x00, 0x30, 0x18, 0x0C, 0x06, 0x0C, + 0x18, 0x30, 0x00, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 243 (less-equal) + 0x00, 0x00, 0x00, 0x0C, 0x18, 0x30, 0x60, 0x30, + 0x18, 0x0C, 0x00, 0x7E, 0x00, 0x00, 0x00, 0x00, + // Character 244 (top integral) + 0x00, 0x00, 0x0E, 0x1B, 0x1B, 0x18, 0x18, 0x18, + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + // Character 245 (bottom integral) + 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, 0x18, + 0x18, 0xD8, 0xD8, 0xD8, 0x70, 0x00, 0x00, 0x00, + // Character 246 (division) + 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x00, 0x7E, + 0x00, 0x18, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 247 (approximately equal) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, 0xDC, 0x00, + 0x76, 0xDC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 248 (degree) + 0x00, 0x38, 0x6C, 0x6C, 0x38, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 249 (bullet operator) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, + 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 250 (middle dot) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 251 (square root) + 0x00, 0x0F, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0xEC, + 0x6C, 0x6C, 0x3C, 0x1C, 0x00, 0x00, 0x00, 0x00, + // Character 252 (superscript n) + 0x00, 0xD8, 0x6C, 0x6C, 0x6C, 0x6C, 0x6C, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 253 (superscript 2) + 0x00, 0x70, 0xD8, 0x30, 0x60, 0xC8, 0xF8, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 254 (filled square) + 0x00, 0x00, 0x00, 0x00, 0x7C, 0x7C, 0x7C, 0x7C, + 0x7C, 0x7C, 0x7C, 0x00, 0x00, 0x00, 0x00, 0x00, + // Character 255 (non-breaking space) + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, +}; + +} // namespace gui diff --git a/programs/src/desktop/main.cpp b/programs/src/desktop/main.cpp new file mode 100644 index 0000000..6ec9f33 --- /dev/null +++ b/programs/src/desktop/main.cpp @@ -0,0 +1,1208 @@ +/* + * main.cpp + * ZenithOS Desktop Environment - window manager, compositor, and applications + * Copyright (c) 2026 Daniel Hammer +*/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +// Placement new for freestanding environment +inline void* operator new(unsigned long, void* p) { return p; } + +using namespace gui; + +// ============================================================================ +// Minimal snprintf (copied from init/main.cpp pattern) +// ============================================================================ + +using va_list = __builtin_va_list; +#define va_start __builtin_va_start +#define va_end __builtin_va_end +#define va_arg __builtin_va_arg + +struct PfState { char* buf; int pos; int max; }; + +static void pf_putc(PfState* st, char c) { + if (st->pos < st->max) st->buf[st->pos] = c; + st->pos++; +} + +static void pf_putnum(PfState* st, unsigned long val, int base, int width, char pad, int neg) { + char tmp[24]; int i = 0; + const char* digits = "0123456789abcdef"; + if (val == 0) { tmp[i++] = '0'; } + else { while (val > 0) { tmp[i++] = digits[val % base]; val /= base; } } + int total = (neg ? 1 : 0) + i; + if (neg && pad == '0') pf_putc(st, '-'); + for (int w = total; w < width; w++) pf_putc(st, pad); + if (neg && pad != '0') pf_putc(st, '-'); + while (i > 0) pf_putc(st, tmp[--i]); +} + +static int snprintf(char* buf, int size, const char* fmt, ...) { + va_list ap; va_start(ap, fmt); + PfState st; st.buf = buf; st.pos = 0; st.max = size > 0 ? size - 1 : 0; + while (*fmt) { + if (*fmt != '%') { pf_putc(&st, *fmt++); continue; } + fmt++; + char pad = ' '; + if (*fmt == '0') { pad = '0'; fmt++; } + int width = 0; + while (*fmt >= '0' && *fmt <= '9') { width = width * 10 + (*fmt - '0'); fmt++; } + if (*fmt == 'l') fmt++; + switch (*fmt) { + case 'd': case 'i': { + long val = va_arg(ap, int); + int neg = 0; unsigned long uval; + if (val < 0) { neg = 1; uval = (unsigned long)(-val); } else uval = (unsigned long)val; + pf_putnum(&st, uval, 10, width, pad, neg); break; + } + case 'u': { unsigned val = va_arg(ap, unsigned); pf_putnum(&st, val, 10, width, pad, 0); break; } + case 'x': { unsigned val = va_arg(ap, unsigned); pf_putnum(&st, val, 16, width, pad, 0); break; } + case 's': { + const char* s = va_arg(ap, const char*); if (!s) s = "(null)"; + int slen = 0; while (s[slen]) slen++; + for (int w = slen; w < width; w++) pf_putc(&st, ' '); + for (int j = 0; j < slen; j++) pf_putc(&st, s[j]); + break; + } + case 'c': { char c = (char)va_arg(ap, int); pf_putc(&st, c); break; } + case '%': pf_putc(&st, '%'); break; + default: pf_putc(&st, '%'); pf_putc(&st, *fmt); break; + } + if (*fmt) fmt++; + } + if (size > 0) { if (st.pos < size) st.buf[st.pos] = '\0'; else st.buf[size - 1] = '\0'; } + va_end(ap); return st.pos; +} + +// ============================================================================ +// String helpers +// ============================================================================ + +static void str_append(char* dst, const char* src, int max) { + int len = zenith::slen(dst); + int i = 0; + while (src[i] && len < max - 1) { + dst[len++] = src[i++]; + } + dst[len] = '\0'; +} + +// ============================================================================ +// File Manager Application +// ============================================================================ + +struct FileManagerState { + char current_path[256]; + char entry_names[64][64]; + int entry_count; + int selected; + int scroll_offset; + bool is_dir[64]; +}; + +static void filemanager_read_dir(FileManagerState* fm) { + const char* names[64]; + fm->entry_count = zenith::readdir(fm->current_path, names, 64); + if (fm->entry_count < 0) fm->entry_count = 0; + for (int i = 0; i < fm->entry_count; i++) { + zenith::strncpy(fm->entry_names[i], names[i], 63); + // Heuristic: entries ending with '/' or without '.' are directories + int len = zenith::slen(fm->entry_names[i]); + if (len > 0 && fm->entry_names[i][len - 1] == '/') { + fm->is_dir[i] = true; + fm->entry_names[i][len - 1] = '\0'; // strip trailing slash + } else { + // Check if entry has an extension (has a dot) + bool has_dot = false; + for (int j = 0; j < len; j++) { + if (fm->entry_names[i][j] == '.') { has_dot = true; break; } + } + fm->is_dir[i] = !has_dot; + } + } + fm->selected = -1; + fm->scroll_offset = 0; +} + +static void filemanager_navigate(FileManagerState* fm, const char* name) { + // Build new path + int path_len = zenith::slen(fm->current_path); + if (path_len > 0 && fm->current_path[path_len - 1] != '/') { + str_append(fm->current_path, "/", 256); + } + str_append(fm->current_path, name, 256); + filemanager_read_dir(fm); +} + +static void filemanager_go_up(FileManagerState* fm) { + int len = zenith::slen(fm->current_path); + if (len <= 3) return; // "0:/" is root + + // Remove trailing slash if present + if (len > 0 && fm->current_path[len - 1] == '/') { + fm->current_path[len - 1] = '\0'; + len--; + } + + // Find last slash + int last_slash = -1; + for (int i = len - 1; i >= 0; i--) { + if (fm->current_path[i] == '/') { last_slash = i; break; } + } + if (last_slash >= 0) { + fm->current_path[last_slash + 1] = '\0'; + } + filemanager_read_dir(fm); +} + +static void filemanager_on_draw(Window* win, Framebuffer& fb) { + FileManagerState* fm = (FileManagerState*)win->app_data; + if (!fm) return; + + Rect cr = win->content_rect(); + int cw = cr.w; + int ch = cr.h; + + // Render to content buffer + uint32_t* pixels = win->content; + uint32_t bg_px = colors::WINDOW_BG.to_pixel(); + for (int i = 0; i < cw * ch; i++) pixels[i] = bg_px; + + // Draw path bar at top (24px tall, light gray background) + uint32_t pathbar_px = Color::from_rgb(0xF0, 0xF0, 0xF0).to_pixel(); + for (int y = 0; y < 24 && y < ch; y++) + for (int x = 0; x < cw; x++) + pixels[y * cw + x] = pathbar_px; + + // Draw path text + { + int tx = 8; + int ty = 4; + uint32_t fg_px = colors::TEXT_COLOR.to_pixel(); + for (int ci = 0; fm->current_path[ci] && tx + FONT_WIDTH <= cw; ci++) { + const uint8_t* glyph = &font_data[(unsigned char)fm->current_path[ci] * FONT_HEIGHT]; + for (int fy = 0; fy < FONT_HEIGHT && ty + fy < ch; fy++) { + uint8_t bits = glyph[fy]; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + if (bits & (0x80 >> fx)) { + int dx = tx + fx; + int dy = ty + fy; + if (dx < cw && dy < ch) + pixels[dy * cw + dx] = fg_px; + } + } + } + tx += FONT_WIDTH; + } + } + + // Draw separator line + uint32_t sep_px = colors::BORDER.to_pixel(); + if (24 < ch) { + for (int x = 0; x < cw; x++) + pixels[24 * cw + x] = sep_px; + } + + // Draw file entries + int item_height = 24; + int start_y = 26; + int visible_items = (ch - start_y) / item_height; + + for (int i = fm->scroll_offset; i < fm->entry_count && (i - fm->scroll_offset) < visible_items; i++) { + int iy = start_y + (i - fm->scroll_offset) * item_height; + if (iy + item_height > ch) break; + + // Highlight selected + if (i == fm->selected) { + uint32_t sel_px = colors::MENU_HOVER.to_pixel(); + for (int y = iy; y < iy + item_height && y < ch; y++) + for (int x = 0; x < cw; x++) + pixels[y * cw + x] = sel_px; + } + + // Draw icon placeholder (small colored square) + uint32_t icon_px; + if (fm->is_dir[i]) { + icon_px = Color::from_rgb(0xFF, 0xBD, 0x2E).to_pixel(); // folder yellow + } else { + icon_px = Color::from_rgb(0x90, 0x90, 0x90).to_pixel(); // file gray + } + int icon_x = 8; + int icon_y = iy + 4; + for (int dy = 0; dy < 16 && icon_y + dy < ch; dy++) + for (int dx = 0; dx < 16 && icon_x + dx < cw; dx++) + pixels[(icon_y + dy) * cw + (icon_x + dx)] = icon_px; + + // Draw entry name + int tx = 30; + int ty = iy + 4; + uint32_t text_px = colors::TEXT_COLOR.to_pixel(); + for (int ci = 0; fm->entry_names[i][ci] && tx + FONT_WIDTH <= cw; ci++) { + const uint8_t* glyph = &font_data[(unsigned char)fm->entry_names[i][ci] * FONT_HEIGHT]; + for (int fy = 0; fy < FONT_HEIGHT && ty + fy < ch; fy++) { + uint8_t bits = glyph[fy]; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + if (bits & (0x80 >> fx)) { + int dx = tx + fx; + int dy = ty + fy; + if (dx < cw && dy < ch) + pixels[dy * cw + dx] = text_px; + } + } + } + tx += FONT_WIDTH; + } + } +} + +static void filemanager_on_mouse(Window* win, MouseEvent& ev) { + FileManagerState* fm = (FileManagerState*)win->app_data; + if (!fm) return; + + Rect cr = win->content_rect(); + int local_y = ev.y - cr.y; + + if (ev.left_pressed()) { + int item_height = 24; + int start_y = 26; + int clicked_idx = fm->scroll_offset + (local_y - start_y) / item_height; + + if (local_y >= start_y && clicked_idx >= 0 && clicked_idx < fm->entry_count) { + if (fm->selected == clicked_idx) { + // Double-click: navigate into directory + if (fm->is_dir[clicked_idx]) { + filemanager_navigate(fm, fm->entry_names[clicked_idx]); + } + } else { + fm->selected = clicked_idx; + } + } + } + + // Scroll handling + if (ev.scroll != 0) { + fm->scroll_offset -= ev.scroll; + if (fm->scroll_offset < 0) fm->scroll_offset = 0; + int max_off = fm->entry_count - ((cr.h - 26) / 24); + if (max_off < 0) max_off = 0; + if (fm->scroll_offset > max_off) fm->scroll_offset = max_off; + } +} + +static void filemanager_on_key(Window* win, const Zenith::KeyEvent& key) { + FileManagerState* fm = (FileManagerState*)win->app_data; + if (!fm || !key.pressed) return; + + if (key.ascii == '\b' || key.scancode == 0x0E) { + filemanager_go_up(fm); + } else if (key.scancode == 0x48) { + // Up arrow + if (fm->selected > 0) fm->selected--; + } else if (key.scancode == 0x50) { + // Down arrow + if (fm->selected < fm->entry_count - 1) fm->selected++; + } else if (key.ascii == '\n' || key.ascii == '\r') { + if (fm->selected >= 0 && fm->selected < fm->entry_count) { + if (fm->is_dir[fm->selected]) { + filemanager_navigate(fm, fm->entry_names[fm->selected]); + } + } + } +} + +static void filemanager_on_close(Window* win) { + if (win->app_data) { + zenith::mfree(win->app_data); + win->app_data = nullptr; + } +} + +// ============================================================================ +// System Info Application +// ============================================================================ + +struct SysInfoState { + Zenith::SysInfo sys_info; + Zenith::NetCfg net_cfg; + uint64_t uptime_ms; +}; + +static void draw_text_to_pixels(uint32_t* pixels, int pw, int ph, + int tx, int ty, const char* text, uint32_t color_px) { + for (int i = 0; text[i] && tx + (i + 1) * FONT_WIDTH <= pw; i++) { + const uint8_t* glyph = &font_data[(unsigned char)text[i] * FONT_HEIGHT]; + int cx = tx + i * FONT_WIDTH; + for (int fy = 0; fy < FONT_HEIGHT && ty + fy < ph; fy++) { + uint8_t bits = glyph[fy]; + for (int fx = 0; fx < FONT_WIDTH; fx++) { + if (bits & (0x80 >> fx)) { + int dx = cx + fx; + int dy = ty + fy; + if (dx >= 0 && dx < pw && dy >= 0 && dy < ph) + pixels[dy * pw + dx] = color_px; + } + } + } + } +} + +static void sysinfo_on_draw(Window* win, Framebuffer& fb) { + SysInfoState* si = (SysInfoState*)win->app_data; + if (!si) return; + + // Refresh uptime + si->uptime_ms = zenith::get_milliseconds(); + + Rect cr = win->content_rect(); + int cw = cr.w; + int ch = cr.h; + uint32_t* pixels = win->content; + + // Fill background + uint32_t bg_px = colors::WINDOW_BG.to_pixel(); + for (int i = 0; i < cw * ch; i++) pixels[i] = bg_px; + + uint32_t text_px = colors::TEXT_COLOR.to_pixel(); + uint32_t accent_px = colors::ACCENT.to_pixel(); + int y = 16; + int x = 16; + char line[128]; + + // Title + draw_text_to_pixels(pixels, cw, ch, x, y, "System Information", accent_px); + y += FONT_HEIGHT + 12; + + // Separator + uint32_t sep_px = colors::BORDER.to_pixel(); + for (int sx = x; sx < cw - x && y < ch; sx++) + pixels[y * cw + sx] = sep_px; + y += 8; + + // OS Name + snprintf(line, sizeof(line), "OS: %s", si->sys_info.osName); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // OS Version + snprintf(line, sizeof(line), "Version: %s", si->sys_info.osVersion); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // API Version + snprintf(line, sizeof(line), "API: %d", (int)si->sys_info.apiVersion); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // Max Processes + snprintf(line, sizeof(line), "Max PIDs: %d", (int)si->sys_info.maxProcesses); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 12; + + // Uptime + int up_sec = (int)(si->uptime_ms / 1000); + int up_min = up_sec / 60; + int up_hr = up_min / 60; + snprintf(line, sizeof(line), "Uptime: %d:%02d:%02d", up_hr, up_min % 60, up_sec % 60); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 12; + + // Network section + draw_text_to_pixels(pixels, cw, ch, x, y, "Network", accent_px); + y += FONT_HEIGHT + 8; + + for (int sx = x; sx < cw - x && y < ch; sx++) + pixels[y * cw + sx] = sep_px; + y += 8; + + // IP Address + uint32_t ip = si->net_cfg.ipAddress; + snprintf(line, sizeof(line), "IP: %d.%d.%d.%d", + (int)(ip & 0xFF), (int)((ip >> 8) & 0xFF), + (int)((ip >> 16) & 0xFF), (int)((ip >> 24) & 0xFF)); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // Subnet + uint32_t mask = si->net_cfg.subnetMask; + snprintf(line, sizeof(line), "Subnet: %d.%d.%d.%d", + (int)(mask & 0xFF), (int)((mask >> 8) & 0xFF), + (int)((mask >> 16) & 0xFF), (int)((mask >> 24) & 0xFF)); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // Gateway + uint32_t gw = si->net_cfg.gateway; + snprintf(line, sizeof(line), "Gateway: %d.%d.%d.%d", + (int)(gw & 0xFF), (int)((gw >> 8) & 0xFF), + (int)((gw >> 16) & 0xFF), (int)((gw >> 24) & 0xFF)); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // DNS + uint32_t dns = si->net_cfg.dnsServer; + snprintf(line, sizeof(line), "DNS: %d.%d.%d.%d", + (int)(dns & 0xFF), (int)((dns >> 8) & 0xFF), + (int)((dns >> 16) & 0xFF), (int)((dns >> 24) & 0xFF)); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); + y += FONT_HEIGHT + 6; + + // MAC Address + snprintf(line, sizeof(line), "MAC: %02x:%02x:%02x:%02x:%02x:%02x", + (unsigned)si->net_cfg.macAddress[0], (unsigned)si->net_cfg.macAddress[1], + (unsigned)si->net_cfg.macAddress[2], (unsigned)si->net_cfg.macAddress[3], + (unsigned)si->net_cfg.macAddress[4], (unsigned)si->net_cfg.macAddress[5]); + draw_text_to_pixels(pixels, cw, ch, x, y, line, text_px); +} + +static void sysinfo_on_close(Window* win) { + if (win->app_data) { + zenith::mfree(win->app_data); + win->app_data = nullptr; + } +} + +// ============================================================================ +// Terminal Application +// ============================================================================ + +static void terminal_on_draw(Window* win, Framebuffer& fb) { + TerminalState* ts = (TerminalState*)win->app_data; + if (!ts) return; + + Rect cr = win->content_rect(); + terminal_render(ts, win->content, cr.w, cr.h); +} + +static void terminal_on_mouse(Window* win, MouseEvent& ev) { + // Terminal doesn't need mouse handling for now +} + +static void terminal_on_key(Window* win, const Zenith::KeyEvent& key) { + TerminalState* ts = (TerminalState*)win->app_data; + if (!ts) return; + terminal_handle_key(ts, key); +} + +static void terminal_on_close(Window* win) { + TerminalState* ts = (TerminalState*)win->app_data; + if (ts) { + if (ts->cells) zenith::mfree(ts->cells); + zenith::mfree(ts); + win->app_data = nullptr; + } +} + +// ============================================================================ +// Application Launchers +// ============================================================================ + +static DesktopState* g_desktop; + +static void open_terminal(DesktopState* ds) { + int idx = desktop_create_window(ds, "Terminal", 200, 80, 648, 480); + if (idx < 0) return; + + Window* win = &ds->windows[idx]; + Rect cr = win->content_rect(); + int cols = cr.w / FONT_WIDTH; + int rows = cr.h / FONT_HEIGHT; + + TerminalState* ts = (TerminalState*)zenith::malloc(sizeof(TerminalState)); + zenith::memset(ts, 0, sizeof(TerminalState)); + terminal_init(ts, cols, rows); + + win->app_data = ts; + win->on_draw = terminal_on_draw; + win->on_mouse = terminal_on_mouse; + win->on_key = terminal_on_key; + win->on_close = terminal_on_close; +} + +static void open_filemanager(DesktopState* ds) { + int idx = desktop_create_window(ds, "Files", 150, 120, 500, 400); + if (idx < 0) return; + + Window* win = &ds->windows[idx]; + FileManagerState* fm = (FileManagerState*)zenith::malloc(sizeof(FileManagerState)); + zenith::memset(fm, 0, sizeof(FileManagerState)); + zenith::strcpy(fm->current_path, "0:/"); + fm->selected = -1; + filemanager_read_dir(fm); + + win->app_data = fm; + win->on_draw = filemanager_on_draw; + win->on_mouse = filemanager_on_mouse; + win->on_key = filemanager_on_key; + win->on_close = filemanager_on_close; +} + +static void open_sysinfo(DesktopState* ds) { + int idx = desktop_create_window(ds, "System Info", 300, 100, 400, 380); + if (idx < 0) return; + + Window* win = &ds->windows[idx]; + SysInfoState* si = (SysInfoState*)zenith::malloc(sizeof(SysInfoState)); + zenith::memset(si, 0, sizeof(SysInfoState)); + zenith::get_info(&si->sys_info); + zenith::get_netcfg(&si->net_cfg); + si->uptime_ms = zenith::get_milliseconds(); + + win->app_data = si; + win->on_draw = sysinfo_on_draw; + win->on_mouse = nullptr; + win->on_key = nullptr; + win->on_close = sysinfo_on_close; +} + +// App menu click callbacks +static void on_click_terminal(void* ud) { + DesktopState* ds = (DesktopState*)ud; + open_terminal(ds); + ds->app_menu_open = false; +} + +static void on_click_filemanager(void* ud) { + DesktopState* ds = (DesktopState*)ud; + open_filemanager(ds); + ds->app_menu_open = false; +} + +static void on_click_sysinfo(void* ud) { + DesktopState* ds = (DesktopState*)ud; + open_sysinfo(ds); + ds->app_menu_open = false; +} + +// ============================================================================ +// Desktop Implementation +// ============================================================================ + +void gui::desktop_init(DesktopState* ds) { + ds->screen_w = ds->fb.width(); + ds->screen_h = ds->fb.height(); + + // Immediately clear the screen to hide flanterm boot text + ds->fb.clear(colors::DESKTOP_BG); + ds->fb.flip(); + + ds->window_count = 0; + ds->focused_window = -1; + ds->prev_buttons = 0; + ds->app_menu_open = false; + + zenith::memset(&ds->mouse, 0, sizeof(Zenith::MouseState)); + zenith::set_mouse_bounds(ds->screen_w - 1, ds->screen_h - 1); + + // Load SVG icons (filenames match those copied by scripts/copy_icons.sh) + ds->icon_terminal = svg_load("0:/icons/utilities-terminal-symbolic.svg", 20, 20, colors::ICON_COLOR); + ds->icon_filemanager = svg_load("0:/icons/system-file-manager-symbolic.svg", 20, 20, colors::ICON_COLOR); + ds->icon_sysinfo = svg_load("0:/icons/preferences-desktop-apps-symbolic.svg", 20, 20, colors::ICON_COLOR); + ds->icon_appmenu = svg_load("0:/icons/view-app-grid-symbolic.svg", 20, 20, colors::PANEL_TEXT); + ds->icon_folder = svg_load("0:/icons/folder-symbolic.svg", 16, 16, Color::from_rgb(0xFF, 0xBD, 0x2E)); + ds->icon_file = svg_load("0:/icons/text-x-generic-symbolic.svg", 16, 16, colors::ICON_COLOR); + ds->icon_computer = svg_load("0:/icons/computer-symbolic.svg", 20, 20, colors::ICON_COLOR); + + // Open initial terminal window + open_terminal(ds); +} + +int gui::desktop_create_window(DesktopState* ds, const char* title, int x, int y, int w, int h) { + if (ds->window_count >= MAX_WINDOWS) return -1; + + int idx = ds->window_count; + Window* win = &ds->windows[idx]; + zenith::memset(win, 0, sizeof(Window)); + + zenith::strncpy(win->title, title, MAX_TITLE_LEN); + win->frame = {x, y, w, h}; + win->state = WIN_NORMAL; + win->z_order = idx; + win->focused = true; + win->dirty = true; + win->dragging = false; + win->resizing = false; + win->saved_frame = win->frame; + + // Allocate content buffer + Rect cr = win->content_rect(); + win->content_w = cr.w; + win->content_h = cr.h; + int buf_size = cr.w * cr.h * 4; + win->content = (uint32_t*)zenith::alloc(buf_size); + zenith::memset(win->content, 0xFF, buf_size); + + win->on_draw = nullptr; + win->on_mouse = nullptr; + win->on_key = nullptr; + win->on_close = nullptr; + win->app_data = nullptr; + + // Unfocus previous window + if (ds->focused_window >= 0 && ds->focused_window < ds->window_count) { + ds->windows[ds->focused_window].focused = false; + } + ds->focused_window = idx; + ds->window_count++; + + return idx; +} + +void gui::desktop_close_window(DesktopState* ds, int idx) { + if (idx < 0 || idx >= ds->window_count) return; + + Window* win = &ds->windows[idx]; + if (win->on_close) win->on_close(win); + + // Free content buffer + if (win->content) { + zenith::free(win->content); + win->content = nullptr; + } + + // Shift remaining windows down + for (int i = idx; i < ds->window_count - 1; i++) { + ds->windows[i] = ds->windows[i + 1]; + } + ds->window_count--; + + // Fix focused window index + if (ds->focused_window == idx) { + ds->focused_window = ds->window_count > 0 ? ds->window_count - 1 : -1; + } else if (ds->focused_window > idx) { + ds->focused_window--; + } + + if (ds->focused_window >= 0 && ds->focused_window < ds->window_count) { + ds->windows[ds->focused_window].focused = true; + } +} + +void gui::desktop_raise_window(DesktopState* ds, int idx) { + if (idx < 0 || idx >= ds->window_count) return; + if (idx == ds->window_count - 1) { + // Already on top, just focus + if (ds->focused_window >= 0 && ds->focused_window < ds->window_count) + ds->windows[ds->focused_window].focused = false; + ds->focused_window = idx; + ds->windows[idx].focused = true; + return; + } + + // Unfocus current + if (ds->focused_window >= 0 && ds->focused_window < ds->window_count) { + ds->windows[ds->focused_window].focused = false; + } + + // Move window to end (top of stack) + Window tmp = ds->windows[idx]; + for (int i = idx; i < ds->window_count - 1; i++) { + ds->windows[i] = ds->windows[i + 1]; + } + ds->windows[ds->window_count - 1] = tmp; + + ds->focused_window = ds->window_count - 1; + ds->windows[ds->focused_window].focused = true; +} + +void gui::desktop_draw_window(DesktopState* ds, int idx) { + if (idx < 0 || idx >= ds->window_count) return; + Window* win = &ds->windows[idx]; + if (win->state == WIN_MINIMIZED || win->state == WIN_CLOSED) return; + + Framebuffer& fb = ds->fb; + int x = win->frame.x; + int y = win->frame.y; + int w = win->frame.w; + int h = win->frame.h; + + // Draw shadow + draw_shadow(fb, x, y, w, h, SHADOW_SIZE, colors::SHADOW); + + // Draw window body + fb.fill_rect(x, y, w, h, colors::WINDOW_BG); + + // Draw titlebar + Color tb_bg = win->focused ? colors::TITLEBAR_BG : Color::from_rgb(0xE8, 0xE8, 0xE8); + fb.fill_rect(x, y, w, TITLEBAR_HEIGHT, tb_bg); + + // Draw border + draw_rect(fb, x, y, w, h, colors::BORDER); + // Titlebar bottom separator + draw_hline(fb, x, y + TITLEBAR_HEIGHT - 1, w, colors::BORDER); + + // Draw window buttons (macOS style: close, minimize, maximize) + Rect close_r = win->close_btn_rect(); + Rect min_r = win->min_btn_rect(); + Rect max_r = win->max_btn_rect(); + + fill_circle(fb, close_r.x + BTN_RADIUS, close_r.y + BTN_RADIUS, BTN_RADIUS, colors::CLOSE_BTN); + fill_circle(fb, min_r.x + BTN_RADIUS, min_r.y + BTN_RADIUS, BTN_RADIUS, colors::MIN_BTN); + fill_circle(fb, max_r.x + BTN_RADIUS, max_r.y + BTN_RADIUS, BTN_RADIUS, colors::MAX_BTN); + + // Draw title text centered in titlebar (after buttons) + int title_x = x + 12 + 44 + BTN_RADIUS * 2 + 12; // after buttons + int title_y = y + (TITLEBAR_HEIGHT - FONT_HEIGHT) / 2; + int title_w = text_width(win->title); + // Center in remaining space + int remaining_w = w - (title_x - x) - 12; + if (remaining_w > title_w) { + title_x += (remaining_w - title_w) / 2; + } + draw_text(fb, title_x, title_y, win->title, colors::TEXT_COLOR); + + // Call app draw callback to render content + if (win->on_draw) { + win->on_draw(win, fb); + } + + // Blit content buffer to framebuffer + Rect cr = win->content_rect(); + if (win->content) { + fb.blit(cr.x, cr.y, cr.w, cr.h, win->content); + } +} + +void gui::desktop_draw_panel(DesktopState* ds) { + Framebuffer& fb = ds->fb; + int sw = ds->screen_w; + + // Panel background + fb.fill_rect(0, 0, sw, PANEL_HEIGHT, colors::PANEL_BG); + + // App menu button (left side) + int btn_x = 4; + int btn_y = 2; + int btn_w = 28; + int btn_h = 28; + + // Draw grid icon for app menu (3x3 dots) + if (ds->icon_appmenu.pixels) { + int ix = btn_x + (btn_w - ds->icon_appmenu.width) / 2; + int iy = btn_y + (btn_h - ds->icon_appmenu.height) / 2; + fb.blit_alpha(ix, iy, ds->icon_appmenu.width, ds->icon_appmenu.height, ds->icon_appmenu.pixels); + } else { + // Fallback: draw 3x3 grid of small squares + for (int gr = 0; gr < 3; gr++) { + for (int gc = 0; gc < 3; gc++) { + int dx = btn_x + 6 + gc * 6; + int dy = btn_y + 6 + gr * 6; + fb.fill_rect(dx, dy, 3, 3, colors::PANEL_TEXT); + } + } + } + + // Window indicator buttons (center area) + int indicator_x = 40; + for (int i = 0; i < ds->window_count; i++) { + Window* win = &ds->windows[i]; + if (win->state == WIN_CLOSED) continue; + + int tw = text_width(win->title); + int pad = 12; + int iw = tw + pad * 2; + if (iw > 150) iw = 150; + + Color btn_bg = (i == ds->focused_window) + ? Color::from_rgba(0xFF, 0xFF, 0xFF, 0x30) + : Color::from_rgba(0xFF, 0xFF, 0xFF, 0x10); + + fb.fill_rect_alpha(indicator_x, 4, iw, 24, btn_bg); + + // Truncate title if too long + char short_title[20]; + zenith::strncpy(short_title, win->title, 18); + + int tx = indicator_x + pad; + int ty = 4 + (24 - FONT_HEIGHT) / 2; + draw_text(fb, tx, ty, short_title, colors::PANEL_TEXT); + + indicator_x += iw + 4; + } + + // Clock (right side) + Zenith::DateTime dt; + zenith::gettime(&dt); + char clock_str[8]; + snprintf(clock_str, sizeof(clock_str), "%02d:%02d", (int)dt.Hour, (int)dt.Minute); + int clock_w = text_width(clock_str); + int clock_x = sw - clock_w - 12; + int clock_y = (PANEL_HEIGHT - FONT_HEIGHT) / 2; + draw_text(fb, clock_x, clock_y, clock_str, colors::PANEL_TEXT); +} + +static void desktop_draw_app_menu(DesktopState* ds) { + Framebuffer& fb = ds->fb; + + int menu_x = 4; + int menu_y = PANEL_HEIGHT + 2; + int menu_w = 200; + int item_h = 36; + int menu_h = item_h * 3 + 8; + + // Menu shadow + draw_shadow(fb, menu_x, menu_y, menu_w, menu_h, 4, colors::SHADOW); + + // Menu background + fb.fill_rect(menu_x, menu_y, menu_w, menu_h, colors::MENU_BG); + draw_rect(fb, menu_x, menu_y, menu_w, menu_h, colors::BORDER); + + // Menu items + struct MenuItem { + const char* label; + SvgIcon* icon; + }; + MenuItem items[3] = { + { "Terminal", &ds->icon_terminal }, + { "Files", &ds->icon_filemanager }, + { "System Info", &ds->icon_sysinfo } + }; + + int mx = ds->mouse.x; + int my = ds->mouse.y; + + for (int i = 0; i < 3; i++) { + int iy = menu_y + 4 + i * item_h; + Rect item_rect = {menu_x + 4, iy, menu_w - 8, item_h}; + + // Hover highlight + if (item_rect.contains(mx, my)) { + fill_rounded_rect(fb, item_rect.x, item_rect.y, item_rect.w, item_rect.h, 4, colors::MENU_HOVER); + } + + // Icon + int icon_x = item_rect.x + 8; + int icon_y = item_rect.y + (item_h - 20) / 2; + if (items[i].icon && items[i].icon->pixels) { + fb.blit_alpha(icon_x, icon_y, items[i].icon->width, items[i].icon->height, items[i].icon->pixels); + } + + // Label + int tx = icon_x + 28; + int ty = item_rect.y + (item_h - FONT_HEIGHT) / 2; + draw_text(fb, tx, ty, items[i].label, colors::TEXT_COLOR); + } +} + +void gui::desktop_compose(DesktopState* ds) { + Framebuffer& fb = ds->fb; + + // Desktop background + fb.clear(colors::DESKTOP_BG); + + // Draw windows from bottom to top (index 0 = bottom) + for (int i = 0; i < ds->window_count; i++) { + if (ds->windows[i].state != WIN_MINIMIZED && ds->windows[i].state != WIN_CLOSED) { + desktop_draw_window(ds, i); + } + } + + // Draw panel on top of everything + desktop_draw_panel(ds); + + // Draw app menu if open + if (ds->app_menu_open) { + desktop_draw_app_menu(ds); + } + + // Draw cursor last (on top of everything) + draw_cursor(fb, ds->mouse.x, ds->mouse.y); +} + +void gui::desktop_handle_mouse(DesktopState* ds) { + int mx = ds->mouse.x; + int my = ds->mouse.y; + uint8_t buttons = ds->mouse.buttons; + uint8_t prev = ds->prev_buttons; + bool left_pressed = (buttons & 0x01) && !(prev & 0x01); + bool left_held = (buttons & 0x01); + bool left_released = !(buttons & 0x01) && (prev & 0x01); + + // Build mouse event + MouseEvent ev; + ev.x = mx; + ev.y = my; + ev.buttons = buttons; + ev.prev_buttons = prev; + ev.scroll = ds->mouse.scrollDelta; + + // Check for ongoing window drags first + for (int i = 0; i < ds->window_count; i++) { + Window* win = &ds->windows[i]; + if (win->dragging) { + if (left_held) { + win->frame.x = mx - win->drag_offset_x; + win->frame.y = my - win->drag_offset_y; + // Clamp to screen + if (win->frame.x < -win->frame.w + 50) win->frame.x = -win->frame.w + 50; + if (win->frame.y < 0) win->frame.y = 0; + if (win->frame.x > ds->screen_w - 50) win->frame.x = ds->screen_w - 50; + if (win->frame.y > ds->screen_h - 50) win->frame.y = ds->screen_h - 50; + } + if (left_released) { + win->dragging = false; + } + return; + } + } + + // Handle app menu clicks + if (ds->app_menu_open && left_pressed) { + int menu_x = 4; + int menu_y = PANEL_HEIGHT + 2; + int menu_w = 200; + int item_h = 36; + int menu_h = item_h * 3 + 8; + Rect menu_rect = {menu_x, menu_y, menu_w, menu_h}; + + if (menu_rect.contains(mx, my)) { + // Which item was clicked? + int rel_y = my - menu_y - 4; + int item_idx = rel_y / item_h; + if (item_idx >= 0 && item_idx < 3) { + switch (item_idx) { + case 0: on_click_terminal(ds); break; + case 1: on_click_filemanager(ds); break; + case 2: on_click_sysinfo(ds); break; + } + } + return; + } else { + ds->app_menu_open = false; + // Fall through to handle click on other things + } + } + + // Panel click check + if (left_pressed && my < PANEL_HEIGHT) { + // App menu button + if (mx < 36) { + ds->app_menu_open = !ds->app_menu_open; + return; + } + + // Window indicator buttons + int indicator_x = 40; + for (int i = 0; i < ds->window_count; i++) { + Window* win = &ds->windows[i]; + if (win->state == WIN_CLOSED) continue; + + int tw = text_width(win->title); + int pad = 12; + int iw = tw + pad * 2; + if (iw > 150) iw = 150; + + Rect btn_rect = {indicator_x, 4, iw, 24}; + if (btn_rect.contains(mx, my)) { + if (win->state == WIN_MINIMIZED) { + win->state = WIN_NORMAL; + } + desktop_raise_window(ds, i); + return; + } + indicator_x += iw + 4; + } + return; + } + + // Window interaction: check from top (last) to bottom (first) + if (left_pressed) { + for (int i = ds->window_count - 1; i >= 0; i--) { + Window* win = &ds->windows[i]; + if (win->state == WIN_MINIMIZED || win->state == WIN_CLOSED) continue; + + // Check close button + Rect close_r = win->close_btn_rect(); + if (close_r.contains(mx, my)) { + desktop_close_window(ds, i); + return; + } + + // Check minimize button + Rect min_r = win->min_btn_rect(); + if (min_r.contains(mx, my)) { + win->state = WIN_MINIMIZED; + if (ds->focused_window == i) { + ds->focused_window = -1; + // Focus next visible window + for (int j = ds->window_count - 1; j >= 0; j--) { + if (ds->windows[j].state == WIN_NORMAL || ds->windows[j].state == WIN_MAXIMIZED) { + ds->focused_window = j; + ds->windows[j].focused = true; + break; + } + } + } + return; + } + + // Check maximize button + Rect max_r = win->max_btn_rect(); + if (max_r.contains(mx, my)) { + if (win->state == WIN_MAXIMIZED) { + // Restore + win->frame = win->saved_frame; + win->state = WIN_NORMAL; + } else { + // Maximize + win->saved_frame = win->frame; + win->frame = {0, PANEL_HEIGHT, ds->screen_w, ds->screen_h - PANEL_HEIGHT}; + win->state = WIN_MAXIMIZED; + } + // Reallocate content buffer for new size + Rect cr = win->content_rect(); + if (cr.w != win->content_w || cr.h != win->content_h) { + if (win->content) zenith::free(win->content); + win->content_w = cr.w; + win->content_h = cr.h; + win->content = (uint32_t*)zenith::alloc(cr.w * cr.h * 4); + zenith::memset(win->content, 0xFF, cr.w * cr.h * 4); + } + desktop_raise_window(ds, i); + return; + } + + // Check titlebar (start drag) + Rect tb = win->titlebar_rect(); + if (tb.contains(mx, my)) { + win->dragging = true; + win->drag_offset_x = mx - win->frame.x; + win->drag_offset_y = my - win->frame.y; + desktop_raise_window(ds, ds->window_count - 1 == i ? i : i); + // After raise, this window is at the end + // Need to update the reference since raise moved it + int new_idx = ds->window_count - 1; + ds->windows[new_idx].dragging = true; + ds->windows[new_idx].drag_offset_x = mx - ds->windows[new_idx].frame.x; + ds->windows[new_idx].drag_offset_y = my - ds->windows[new_idx].frame.y; + return; + } + + // Check content area + Rect cr = win->content_rect(); + if (cr.contains(mx, my)) { + desktop_raise_window(ds, i); + // Dispatch mouse event to app + int new_idx = ds->window_count - 1; + if (ds->windows[new_idx].on_mouse) { + ev.x = mx; + ev.y = my; + ds->windows[new_idx].on_mouse(&ds->windows[new_idx], ev); + } + return; + } + + // Check full frame (catches border clicks) + if (win->frame.contains(mx, my)) { + desktop_raise_window(ds, i); + return; + } + } + + // Clicked on desktop background - close app menu + ds->app_menu_open = false; + } + + // Handle scroll events on focused window + if (ev.scroll != 0 && ds->focused_window >= 0) { + Window* win = &ds->windows[ds->focused_window]; + Rect cr = win->content_rect(); + if (cr.contains(mx, my) && win->on_mouse) { + win->on_mouse(win, ev); + } + } +} + +void gui::desktop_handle_keyboard(DesktopState* ds, const Zenith::KeyEvent& key) { + if (!key.pressed) return; + + // Global shortcuts + if (key.ctrl && key.alt) { + if (key.ascii == 't' || key.ascii == 'T') { + open_terminal(ds); + return; + } + if (key.ascii == 'f' || key.ascii == 'F') { + open_filemanager(ds); + return; + } + if (key.ascii == 'i' || key.ascii == 'I') { + open_sysinfo(ds); + return; + } + } + + // Dispatch to focused window + if (ds->focused_window >= 0 && ds->focused_window < ds->window_count) { + Window* win = &ds->windows[ds->focused_window]; + if (win->on_key) { + win->on_key(win, key); + } + } +} + +void gui::desktop_run(DesktopState* ds) { + for (;;) { + // Poll mouse state + ds->prev_buttons = ds->mouse.buttons; + zenith::mouse_state(&ds->mouse); + + // Poll keyboard events + while (zenith::is_key_available()) { + Zenith::KeyEvent key; + zenith::getkey(&key); + desktop_handle_keyboard(ds, key); + } + + // Poll terminal I/O for all terminal windows + for (int i = 0; i < ds->window_count; i++) { + Window* win = &ds->windows[i]; + if (win->state == WIN_CLOSED) continue; + if (win->app_data && win->on_draw == terminal_on_draw) { + TerminalState* ts = (TerminalState*)win->app_data; + terminal_poll(ts); + } + } + + // Handle mouse events + desktop_handle_mouse(ds); + + // Compose and present + desktop_compose(ds); + ds->fb.flip(); + + // Target ~60fps + zenith::sleep_ms(16); + } +} + +// ============================================================================ +// Entry Point +// ============================================================================ + +extern "C" void _start() { + DesktopState* ds = (DesktopState*)zenith::malloc(sizeof(DesktopState)); + zenith::memset(ds, 0, sizeof(DesktopState)); + + // Placement-new the Framebuffer since it has a constructor + new (&ds->fb) Framebuffer(); + + g_desktop = ds; + + desktop_init(ds); + desktop_run(ds); + + zenith::exit(0); +} diff --git a/programs/src/desktop/obj/font_data.o b/programs/src/desktop/obj/font_data.o new file mode 100644 index 0000000000000000000000000000000000000000..ab24d2bf58eaeb3dfdea50d2b602781c681e713c GIT binary patch literal 13744 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 z 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%0A(~yXw$o!Ma!)J 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�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

{wgEF2SxaZ2+xV|{0N^B;jJPi?$1>@0hWarb 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 Y3z_Q+KK7ZPr95iukM_prF5LeA0q~SlQUCw| literal 0 HcmV?d00001 diff --git a/programs/src/init/main.cpp b/programs/src/init/main.cpp index 364f4e8..1329f01 100644 --- a/programs/src/init/main.cpp +++ b/programs/src/init/main.cpp @@ -153,8 +153,11 @@ extern "C" void _start() { // ---- Stage 1: Network configuration ---- run_service("0:/os/dhcp.elf", "dhcp"); - // ---- Stage 2: Interactive shell ---- - run_service("0:/os/shell.elf", "shell"); + // ---- Stage 2: Desktop environment (falls back to shell) ---- + if (!run_service("0:/os/desktop.elf", "desktop")) { + log_warn("Desktop failed, falling back to shell"); + run_service("0:/os/shell.elf", "shell"); + } log_warn("All services exited"); diff --git a/scripts/copy_icons.sh b/scripts/copy_icons.sh new file mode 100755 index 0000000..bb35f1d --- /dev/null +++ b/scripts/copy_icons.sh @@ -0,0 +1,48 @@ +#!/bin/bash +# copy_icons.sh - Copy selected SVG icons for the desktop environment +# Usage: ./scripts/copy_icons.sh (from project root or programs/ directory) + +set -e + +# Find project root relative to this script's location +SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)" +PROJECT_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)" + +ICON_SRC="$PROJECT_ROOT/programs/gui/icons/Flat-Remix-Blue-Light-darkPanel" +ICON_DST="$PROJECT_ROOT/programs/bin/icons" + +mkdir -p "$ICON_DST" + +# Selected icons for the desktop +ICONS=( + "actions/symbolic/view-app-grid-symbolic.svg" + "actions/symbolic/window-close-symbolic.svg" + "actions/symbolic/window-maximize-symbolic.svg" + "actions/symbolic/window-minimize-symbolic.svg" + "apps/symbolic/utilities-terminal-symbolic.svg" + "apps/symbolic/system-file-manager-symbolic.svg" + "apps/symbolic/preferences-desktop-apps-symbolic.svg" + "places/symbolic/folder-symbolic.svg" + "places/symbolic/folder-documents-symbolic.svg" + "places/symbolic/user-home-symbolic.svg" + "mimetypes/symbolic/text-x-generic-symbolic.svg" + "mimetypes/symbolic/application-x-executable-symbolic.svg" + "devices/symbolic/computer-symbolic.svg" + "devices/symbolic/network-wired-symbolic.svg" +) + +copied=0 +for icon in "${ICONS[@]}"; do + src="$ICON_SRC/$icon" + # Extract just the filename + name=$(basename "$icon") + dst="$ICON_DST/$name" + if [ -f "$src" ]; then + cp "$src" "$dst" + copied=$((copied + 1)) + else + echo "copy_icons: warning: $src not found" >&2 + fi +done + +echo "copy_icons: copied $copied icons to $ICON_DST"