move ncurses render helpers into mr4th layer

main
Allen Webster 2026-05-18 11:05:33 -07:00
parent f4fdf28994
commit 03920a32d8
3 changed files with 148 additions and 144 deletions

View File

@ -1,151 +1,12 @@
#include "mr4th/mr4th_base.h"
#include "mr4th/mr4th_stdio.h"
#include "mr4th/mr4th_prng.h"
#include <ncurses.h>
#include "bfr.main.h"
#include "mr4th/mr4th_ncurses.h"
#include "mr4th/mr4th_base.c"
#include "mr4th/mr4th_stdio.c"
#include "mr4th/mr4th_prng.c"
MR4TH_SYMBOL NCRS_Bfr
ncrs_bfr_alloc(Arena *arena, U32 w, U32 h){
NCRS_Bfr result = { w, h };
result.chr = push_array(arena, U8, w*h);
result.color = push_array(arena, U8, w*h);
result.clip.x1 = w;
result.clip.y1 = h;
return(result);
}
MR4TH_SYMBOL void
ncrs_bfr_clip_clear(NCRS_Bfr *bfr){
bfr->clip.x0 = 0;
bfr->clip.y0 = 0;
bfr->clip.x1 = bfr->w;
bfr->clip.y1 = bfr->h;
}
MR4TH_SYMBOL void
ncrs_bfr_clip(NCRS_Bfr *bfr, RectS32 rect){
bfr->clip.x0 = ClampBot(0, rect.x0);
bfr->clip.y0 = ClampBot(0, rect.y0);
bfr->clip.x1 = ClampTop(rect.x1, bfr->w);
bfr->clip.y1 = ClampTop(rect.y1, bfr->h);
}
MR4TH_SYMBOL void
ncrs_bfr_fill_rect(NCRS_Bfr *bfr, RectS32 rect, U8 chr, U8 color){
S32 x0 = ClampBot(rect.x0, bfr->clip.x0);
S32 x1 = ClampTop(rect.x1, bfr->clip.x1);
S32 y0 = ClampBot(rect.y0, bfr->clip.y0);
S32 y1 = ClampTop(rect.y1, bfr->clip.y1);
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_outline_rect(NCRS_Bfr *bfr, RectS32 rect, U8 chr, U8 color){
S32 x0 = ClampBot(rect.x0, bfr->clip.x0);
S32 x1 = ClampTop(rect.x1, bfr->clip.x1);
S32 y0 = ClampBot(rect.y0, bfr->clip.y0);
S32 y1 = ClampTop(rect.y1, bfr->clip.y1);
// top
if (bfr->clip.y0 <= rect.y0 && rect.y0 < bfr->clip.y1){
S32 iyb = rect.y0*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// bottom
if (bfr->clip.y0 < rect.y1 && rect.y1 <= bfr->clip.y1){
S32 iyb = (rect.y1 - 1)*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// left
if (bfr->clip.x0 <= rect.x0 && rect.x0 < bfr->clip.x1){
S32 ix = rect.x0;
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// right
if (bfr->clip.x0 < rect.x1 && rect.x1 <= bfr->clip.x1){
S32 ix = rect.x1 - 1;
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_write(NCRS_Bfr *bfr, S32 x, S32 y, String8 str, U8 color){
if (str.size > 0 &&
bfr->clip.x0 < x + str.size && x < bfr->clip.x1 &&
bfr->clip.y0 <= y && y < bfr->clip.y1){
S32 iyb = y*bfr->w;
S32 x1 = ClampTop(x + str.size, bfr->clip.x1);
S32 xskip = ClampBot(0, bfr->clip.x0 - x);
for (U32 xi = x + xskip, i = xskip; xi < x1; xi += 1, i += 1){
bfr->chr[iyb + xi] = str.str[i];
bfr->color[iyb + xi] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_point(NCRS_Bfr *bfr, S32 x, S32 y, U8 chr, U8 color){
if (bfr->clip.x0 <= x && x < bfr->clip.x1 &&
bfr->clip.y0 <= y && y < bfr->clip.y1){
bfr->chr[y*bfr->w + x] = chr;
bfr->color[y*bfr->w + x] = color;
}
}
MR4TH_SYMBOL void
ncrs_bfr_to_window(NCRS_Bfr *bfr, WINDOW *window){
S32 w = 0;
S32 h = 0;
getmaxyx(window, h, w);
S32 x1 = ClampTop(bfr->w, w);
S32 y1 = ClampTop(bfr->h, h);
for (U32 iy = 0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
wmove(window, iy, 0);
for (U32 ix = 0; ix < x1; ix += 1){
S16 color = (S16)bfr->color[iyb + ix];
if (color != 0){
attron(COLOR_PAIR(color));
}
waddch(window, bfr->chr[iyb + ix]);
attroff(COLOR_PAIR(color));
}
}
wrefresh(window);
}
#include "mr4th/mr4th_ncurses.c"
int main(){
ArenaTemp scratch = arena_get_scratch(0, 0);

141
src/mr4th/mr4th_ncurses.c Normal file
View File

@ -0,0 +1,141 @@
/******************************************************************************
* NCRS Functions *
******************************************************************************/
MR4TH_SYMBOL NCRS_Bfr
ncrs_bfr_alloc(Arena *arena, U32 w, U32 h){
NCRS_Bfr result = { w, h };
result.chr = push_array(arena, U8, w*h);
result.color = push_array(arena, U8, w*h);
result.clip.x1 = w;
result.clip.y1 = h;
return(result);
}
MR4TH_SYMBOL void
ncrs_bfr_clip_clear(NCRS_Bfr *bfr){
bfr->clip.x0 = 0;
bfr->clip.y0 = 0;
bfr->clip.x1 = bfr->w;
bfr->clip.y1 = bfr->h;
}
MR4TH_SYMBOL void
ncrs_bfr_clip(NCRS_Bfr *bfr, RectS32 rect){
bfr->clip.x0 = ClampBot(0, rect.x0);
bfr->clip.y0 = ClampBot(0, rect.y0);
bfr->clip.x1 = ClampTop(rect.x1, bfr->w);
bfr->clip.y1 = ClampTop(rect.y1, bfr->h);
}
MR4TH_SYMBOL void
ncrs_bfr_fill_rect(NCRS_Bfr *bfr, RectS32 rect, U8 chr, U8 color){
S32 x0 = ClampBot(rect.x0, bfr->clip.x0);
S32 x1 = ClampTop(rect.x1, bfr->clip.x1);
S32 y0 = ClampBot(rect.y0, bfr->clip.y0);
S32 y1 = ClampTop(rect.y1, bfr->clip.y1);
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_outline_rect(NCRS_Bfr *bfr, RectS32 rect, U8 chr, U8 color){
S32 x0 = ClampBot(rect.x0, bfr->clip.x0);
S32 x1 = ClampTop(rect.x1, bfr->clip.x1);
S32 y0 = ClampBot(rect.y0, bfr->clip.y0);
S32 y1 = ClampTop(rect.y1, bfr->clip.y1);
// top
if (bfr->clip.y0 <= rect.y0 && rect.y0 < bfr->clip.y1){
S32 iyb = rect.y0*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// bottom
if (bfr->clip.y0 < rect.y1 && rect.y1 <= bfr->clip.y1){
S32 iyb = (rect.y1 - 1)*bfr->w;
for (S32 ix = x0; ix < x1; ix += 1){
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// left
if (bfr->clip.x0 <= rect.x0 && rect.x0 < bfr->clip.x1){
S32 ix = rect.x0;
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
// right
if (bfr->clip.x0 < rect.x1 && rect.x1 <= bfr->clip.x1){
S32 ix = rect.x1 - 1;
for (S32 iy = y0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
bfr->chr[iyb + ix] = chr;
bfr->color[iyb + ix] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_write(NCRS_Bfr *bfr, S32 x, S32 y, String8 str, U8 color){
if (str.size > 0 &&
bfr->clip.x0 < x + str.size && x < bfr->clip.x1 &&
bfr->clip.y0 <= y && y < bfr->clip.y1){
S32 iyb = y*bfr->w;
S32 x1 = ClampTop(x + str.size, bfr->clip.x1);
S32 xskip = ClampBot(0, bfr->clip.x0 - x);
for (U32 xi = x + xskip, i = xskip; xi < x1; xi += 1, i += 1){
bfr->chr[iyb + xi] = str.str[i];
bfr->color[iyb + xi] = color;
}
}
}
MR4TH_SYMBOL void
ncrs_bfr_point(NCRS_Bfr *bfr, S32 x, S32 y, U8 chr, U8 color){
if (bfr->clip.x0 <= x && x < bfr->clip.x1 &&
bfr->clip.y0 <= y && y < bfr->clip.y1){
bfr->chr[y*bfr->w + x] = chr;
bfr->color[y*bfr->w + x] = color;
}
}
MR4TH_SYMBOL void
ncrs_bfr_to_window(NCRS_Bfr *bfr, WINDOW *window){
S32 w = 0;
S32 h = 0;
getmaxyx(window, h, w);
S32 x1 = ClampTop(bfr->w, w);
S32 y1 = ClampTop(bfr->h, h);
for (U32 iy = 0; iy < y1; iy += 1){
S32 iyb = iy*bfr->w;
wmove(window, iy, 0);
for (U32 ix = 0; ix < x1; ix += 1){
S16 color = (S16)bfr->color[iyb + ix];
if (color != 0){
attron(COLOR_PAIR(color));
}
waddch(window, bfr->chr[iyb + ix]);
attroff(COLOR_PAIR(color));
}
}
wrefresh(window);
}

View File

@ -1,5 +1,7 @@
#ifndef BFR_MAIN_H
#define BFR_MAIN_H
#ifndef MR4TH_NCURSES_H
#define MR4TH_NCURSES_H
#include <ncurses.h>
/******************************************************************************
* NCRS Types *
@ -56,4 +58,4 @@ MR4TH_SYMBOL void ncrs_bfr_point(NCRS_Bfr *bfr, S32 x, S32 y, U8 chr, U8 color);
MR4TH_SYMBOL void ncrs_bfr_to_window(NCRS_Bfr *bfr, WINDOW *w);
#endif //BFR_MAIN_H
#endif //MR4TH_NCURSES_H