highgradient: degrade to gradient #700 #696

dankamongmen/slickgoose
nick black 4 years ago
parent 20322fe805
commit a10ba4dac6
No known key found for this signature in database
GPG Key ID: 5F43400C21CBFACC

@ -840,34 +840,34 @@ typedef enum {
// prior to notcurses_init(), you should not set this bit. Even if you are // prior to notcurses_init(), you should not set this bit. Even if you are
// invoking setlocale(), this behavior shouldn't be an issue unless you're // invoking setlocale(), this behavior shouldn't be an issue unless you're
// doing something weird (setting a locale not based on LANG). // doing something weird (setting a locale not based on LANG).
#define NCOPTION_INHIBIT_SETLOCALE 0x0001 #define NCOPTION_INHIBIT_SETLOCALE 0x0001ull
// Checking for Sixel support requires writing an escape, and then reading an // Checking for Sixel support requires writing an escape, and then reading an
// inline reply from the terminal. Since this can interact poorly with actual // inline reply from the terminal. Since this can interact poorly with actual
// user input, it's not done unless Sixel will actually be used. Set this flag // user input, it's not done unless Sixel will actually be used. Set this flag
// to unconditionally test for Sixel support in notcurses_init(). // to unconditionally test for Sixel support in notcurses_init().
#define NCOPTION_VERIFY_SIXEL 0x0002 #define NCOPTION_VERIFY_SIXEL 0x0002ull
// We typically install a signal handler for SIGWINCH that generates a resize // We typically install a signal handler for SIGWINCH that generates a resize
// event in the notcurses_getc() queue. Set to inhibit this handler. // event in the notcurses_getc() queue. Set to inhibit this handler.
#define NCOPTION_NO_WINCH_SIGHANDLER 0x0004 #define NCOPTION_NO_WINCH_SIGHANDLER 0x0004ull
// We typically install a signal handler for SIG{INT, SEGV, ABRT, QUIT} that // We typically install a signal handler for SIG{INT, SEGV, ABRT, QUIT} that
// restores the screen, and then calls the old signal handler. Set to inhibit // restores the screen, and then calls the old signal handler. Set to inhibit
// registration of these signal handlers. // registration of these signal handlers.
#define NCOPTION_NO_QUIT_SIGHANDLERS 0x0008 #define NCOPTION_NO_QUIT_SIGHANDLERS 0x0008ull
// By default, we hide the cursor if possible. This flag inhibits use of // By default, we hide the cursor if possible. This flag inhibits use of
// the civis capability, retaining the cursor. // the civis capability, retaining the cursor.
#define NCOPTION_RETAIN_CURSOR 0x0010 #define NCOPTION_RETAIN_CURSOR 0x0010ull
// Notcurses typically prints version info in notcurses_init() and performance // Notcurses typically prints version info in notcurses_init() and performance
// info in notcurses_stop(). This inhibits that output. // info in notcurses_stop(). This inhibits that output.
#define NCOPTION_SUPPRESS_BANNERS 0x0020 #define NCOPTION_SUPPRESS_BANNERS 0x0020ull
// If smcup/rmcup capabilities are indicated, notcurses defaults to making use // If smcup/rmcup capabilities are indicated, notcurses defaults to making use
// of the "alternate screen". This flag inhibits use of smcup/rmcup. // of the "alternate screen". This flag inhibits use of smcup/rmcup.
#define NCOPTION_NO_ALTERNATE_SCREEN 0x0040 #define NCOPTION_NO_ALTERNATE_SCREEN 0x0040ull
// Configuration for notcurses_init(). // Configuration for notcurses_init().
typedef struct notcurses_options { typedef struct notcurses_options {
@ -1717,6 +1717,11 @@ ncplane_highgradient_sized(struct ncplane* n, uint32_t ul, uint32_t ur,
return -1; return -1;
} }
int y, x; int y, x;
if(!notcurses_canutf8(ncplane_notcurses_const(n))){
// this works because the uin32_ts we pass in will be promoted to uint64_ts
// via extension, and the space will employ the background. mwahh!
return ncplane_gradient_sized(n, " ", 0, ul, ur, ll, lr, ylen, xlen);
}
ncplane_cursor_yx(n, &y, &x); ncplane_cursor_yx(n, &y, &x);
return ncplane_highgradient(n, ul, ur, ll, lr, y + ylen - 1, x + xlen - 1); return ncplane_highgradient(n, ul, ur, ll, lr, y + ylen - 1, x + xlen - 1);
} }
@ -2229,8 +2234,8 @@ API struct ncvisual* ncvisual_from_plane(const struct ncplane* n,
int begy, int begx, int begy, int begx,
int leny, int lenx); int leny, int lenx);
#define NCVISUAL_OPTION_NODEGRADE 0x0001 // fail rather than degrading #define NCVISUAL_OPTION_NODEGRADE 0x0001ull // fail rather than degrading
#define NCVISUAL_OPTION_BLEND 0x0002 // use CELL_ALPHA_BLEND with visual #define NCVISUAL_OPTION_BLEND 0x0002ull // use CELL_ALPHA_BLEND with visual
struct ncvisual_options { struct ncvisual_options {
// if no ncplane is provided, one will be created using the exact size // if no ncplane is provided, one will be created using the exact size
@ -2364,11 +2369,11 @@ API int ncblit_bgrx(const void* data, int linesize,
// is scrolling infinite (can one move down or up forever, or is an end // is scrolling infinite (can one move down or up forever, or is an end
// reached?). if true, 'circular' specifies how to handle the special case of // reached?). if true, 'circular' specifies how to handle the special case of
// an incompletely-filled reel. // an incompletely-filled reel.
#define NCREEL_OPTION_INFINITESCROLL 0x0001 #define NCREEL_OPTION_INFINITESCROLL 0x0001ull
// is navigation circular (does moving down from the last panel move to the // is navigation circular (does moving down from the last panel move to the
// first, and vice versa)? only meaningful when infinitescroll is true. if // first, and vice versa)? only meaningful when infinitescroll is true. if
// infinitescroll is false, this must be false. // infinitescroll is false, this must be false.
#define NCREEL_OPTION_CIRCULAR 0x0002 #define NCREEL_OPTION_CIRCULAR 0x0002ull
typedef struct ncreel_options { typedef struct ncreel_options {
// require this many rows and columns (including borders). otherwise, a // require this many rows and columns (including borders). otherwise, a
@ -2400,7 +2405,7 @@ typedef struct ncreel_options {
uint64_t tabletchan; // tablet border styling channel uint64_t tabletchan; // tablet border styling channel
uint64_t focusedchan;// focused tablet border styling channel uint64_t focusedchan;// focused tablet border styling channel
uint64_t bgchannel; // background colors uint64_t bgchannel; // background colors
unsigned flags; // bitfield over NCREEL_OPTION_* uint64_t flags; // bitfield over NCREEL_OPTION_*
} ncreel_options; } ncreel_options;
struct nctablet; struct nctablet;
@ -2637,7 +2642,7 @@ typedef struct ncselector_options {
uint64_t footchannels; // secondary and footer channels uint64_t footchannels; // secondary and footer channels
uint64_t boxchannels; // border channels uint64_t boxchannels; // border channels
uint64_t bgchannels; // background channels, used only in body uint64_t bgchannels; // background channels, used only in body
unsigned flags; // bitfield of NCSELECTOR_OPTION_* uint64_t flags; // bitfield of NCSELECTOR_OPTION_*
} ncselector_options; } ncselector_options;
API struct ncselector* ncselector_create(struct ncplane* n, int y, int x, API struct ncselector* ncselector_create(struct ncplane* n, int y, int x,
@ -2712,7 +2717,7 @@ typedef struct ncmultiselector_options {
uint64_t footchannels; // secondary and footer channels uint64_t footchannels; // secondary and footer channels
uint64_t boxchannels; // border channels uint64_t boxchannels; // border channels
uint64_t bgchannels; // background channels, used only in body uint64_t bgchannels; // background channels, used only in body
unsigned flags; // bitfield of NCMULTISELECTOR_OPTION_* uint64_t flags; // bitfield of NCMULTISELECTOR_OPTION_*
} ncmultiselector_options; } ncmultiselector_options;
API struct ncmultiselector* ncmultiselector_create(struct ncplane* n, int y, int x, API struct ncmultiselector* ncmultiselector_create(struct ncplane* n, int y, int x,
@ -2755,15 +2760,15 @@ struct ncmenu_section {
ncinput shortcut; // shortcut, will be underlined if present in name ncinput shortcut; // shortcut, will be underlined if present in name
}; };
#define NCMENU_OPTION_BOTTOM 0x0001 // bottom row (as opposed to top row) #define NCMENU_OPTION_BOTTOM 0x0001ull // bottom row (as opposed to top row)
#define NCMENU_OPTION_HIDING 0x0002 // hide the menu when not being used #define NCMENU_OPTION_HIDING 0x0002ull // hide the menu when not being used
typedef struct ncmenu_options { typedef struct ncmenu_options {
struct ncmenu_section* sections; // array of 'sectioncount' menu_sections struct ncmenu_section* sections; // array of 'sectioncount' menu_sections
int sectioncount; // must be positive int sectioncount; // must be positive
uint64_t headerchannels; // styling for header uint64_t headerchannels; // styling for header
uint64_t sectionchannels; // styling for sections uint64_t sectionchannels; // styling for sections
unsigned flags; // flag word of NCMENU_OPTION_* uint64_t flags; // flag word of NCMENU_OPTION_*
} ncmenu_options; } ncmenu_options;
// Create a menu with the specified options. Menus are currently bound to an // Create a menu with the specified options. Menus are currently bound to an
@ -2846,10 +2851,10 @@ API int ncmenu_destroy(struct ncmenu* n);
// //
// This options structure works for both the ncuplot (uint64_t) and ncdplot // This options structure works for both the ncuplot (uint64_t) and ncdplot
// (double) types. // (double) types.
#define NCPLOT_OPTION_LABELTICKSD 0x0001 // show labels for dependent axis #define NCPLOT_OPTION_LABELTICKSD 0x0001ull // show labels for dependent axis
#define NCPLOT_OPTION_EXPONENTIALD 0x0002 // exponential dependent axis #define NCPLOT_OPTION_EXPONENTIALD 0x0002ull // exponential dependent axis
#define NCPLOT_OPTION_VERTICALI 0x0004 // independent axis is vertical #define NCPLOT_OPTION_VERTICALI 0x0004ull // independent axis is vertical
#define NCPLOT_OPTION_NODEGRADE 0x0008 // fail rather than degrade blitter #define NCPLOT_OPTION_NODEGRADE 0x0008ull // fail rather than degrade blitter
typedef struct ncplot_options { typedef struct ncplot_options {
// channels for the maximum and minimum levels. linear interpolation will be // channels for the maximum and minimum levels. linear interpolation will be
@ -2864,7 +2869,7 @@ typedef struct ncplot_options {
// resolution, the independent variable would be the range [0..3600): 3600. // resolution, the independent variable would be the range [0..3600): 3600.
// if rangex is 0, it is dynamically set to the number of columns. // if rangex is 0, it is dynamically set to the number of columns.
int rangex; int rangex;
unsigned flags; // bitfield over NCPLOT_OPTION_* uint64_t flags; // bitfield over NCPLOT_OPTION_*
} ncplot_options; } ncplot_options;
// Use the provided plane 'n' for plotting according to the options 'opts'. // Use the provided plane 'n' for plotting according to the options 'opts'.
@ -2902,7 +2907,7 @@ typedef int(*ncfdplane_done_cb)(struct ncfdplane* n, int fderrno, void* curry);
typedef struct ncfdplane_options { typedef struct ncfdplane_options {
void* curry; // parameter provided to callbacks void* curry; // parameter provided to callbacks
bool follow; // keep reading after hitting end? (think tail -f) bool follow; // keep reading after hitting end? (think tail -f)
unsigned flags; // bitfield over NCOPTION_FDPLANE_* uint64_t flags; // bitfield over NCOPTION_FDPLANE_*
} ncfdplane_options; } ncfdplane_options;
// Create an ncfdplane around the fd 'fd'. Consider this function to take // Create an ncfdplane around the fd 'fd'. Consider this function to take
@ -2917,7 +2922,7 @@ API int ncfdplane_destroy(struct ncfdplane* n);
typedef struct ncsubproc_options { typedef struct ncsubproc_options {
void* curry; void* curry;
uint64_t restart_period; // restart this many seconds after an exit (watch) uint64_t restart_period; // restart this many seconds after an exit (watch)
unsigned flags; // bitfield over NCOPTION_SUBPROC_* uint64_t flags; // bitfield over NCOPTION_SUBPROC_*
} ncsubproc_options; } ncsubproc_options;
// see exec(2). p-types use $PATH. e-type passes environment vars. // see exec(2). p-types use $PATH. e-type passes environment vars.
@ -2944,8 +2949,8 @@ API int ncsubproc_destroy(struct ncsubproc* n);
// future compatability (provide 0 for no artificial bound). // future compatability (provide 0 for no artificial bound).
API int ncplane_qrcode(struct ncplane* n, int maxversion, const void* data, size_t len); API int ncplane_qrcode(struct ncplane* n, int maxversion, const void* data, size_t len);
#define NCREADER_OPTION_HORSCROLL 0x0001 #define NCREADER_OPTION_HORSCROLL 0x0001ull
#define NCREADER_OPTION_VERSCROLL 0x0002 #define NCREADER_OPTION_VERSCROLL 0x0002ull
typedef struct ncreader_options { typedef struct ncreader_options {
uint64_t tchannels; // channels used for input uint64_t tchannels; // channels used for input
@ -2955,7 +2960,7 @@ typedef struct ncreader_options {
char* egc; // egc used for empty space char* egc; // egc used for empty space
int physrows; int physrows;
int physcols; int physcols;
unsigned flags; // bitfield of NCREADER_OPTION_* uint64_t flags; // bitfield of NCREADER_OPTION_*
} ncreader_options; } ncreader_options;
// ncreaders provide freeform input in a (possibly multiline) region, // ncreaders provide freeform input in a (possibly multiline) region,

@ -102,7 +102,6 @@ rotate_visual(struct notcurses* nc, struct ncplane* n, int dy, int dx){
return failed ? -1 : 0; return failed ? -1 : 0;
} }
static const int VSCALE = 2;
static const int ITERMAX = 255; static const int ITERMAX = 255;
static int static int
@ -124,7 +123,7 @@ mandelbrot(int y, int x, int dy, int dx){
static int static int
mcell(uint32_t* c, int y, int x, int dy, int dx){ mcell(uint32_t* c, int y, int x, int dy, int dx){
int iter = mandelbrot(y, x, dy, dx); int iter = mandelbrot(y, x, dy, dx);
*c = (0xff << 24u) + ((255 - iter) << 16u) + ((255 - iter) << 8u) + (255 - iter); *c = ncpixel(255 - iter, 255 - iter, 255 - iter);
return 0; return 0;
} }
@ -145,7 +144,13 @@ int normal_demo(struct notcurses* nc){
ncplane_set_base_cell(nstd, &c); ncplane_set_base_cell(nstd, &c);
cell_release(nstd, &c); cell_release(nstd, &c);
struct ncplane* n = NULL; struct ncplane* n = NULL;
dy *= VSCALE; // double-block trick means both 2x resolution and even linecount yay struct ncvisual_options vopts = {
.n = nstd,
};
int yscale, xscale;
ncvisual_geom(nc, NULL, &vopts, NULL, NULL, &yscale, &xscale);
dy *= yscale;
dx *= xscale;
uint32_t* rgba = malloc(sizeof(*rgba) * dy * dx); uint32_t* rgba = malloc(sizeof(*rgba) * dy * dx);
if(!rgba){ if(!rgba){
goto err; goto err;
@ -154,10 +159,10 @@ int normal_demo(struct notcurses* nc){
rgba[off] = 0xff000000; rgba[off] = 0xff000000;
} }
int y; int y;
if(dy / VSCALE % 2){ if(dy / yscale % 2){
y = dy / VSCALE + 1; y = dy / yscale + 1;
for(int x = 0 ; x < dx ; ++x){ for(int x = 0 ; x < dx ; ++x){
if(mcell(offset(rgba, y, x, dx), y, x, dy / VSCALE, dx)){ if(mcell(offset(rgba, y, x, dx), y, x, dy / yscale, dx)){
goto err; goto err;
} }
} }
@ -173,11 +178,8 @@ int normal_demo(struct notcurses* nc){
goto err; goto err;
} }
} }
struct ncvisual_options vopts = { vopts.leny = dy;
.n = nstd, vopts.lenx = dx;
.leny = dy,
.lenx = dx,
};
if(ncblit_rgba(rgba, dx * sizeof(*rgba), &vopts) < 0){ if(ncblit_rgba(rgba, dx * sizeof(*rgba), &vopts) < 0){
goto err; goto err;
} }

@ -108,7 +108,9 @@ fill_chunk(struct ncplane* n, int idx){
channel_set_rgb(&ur, g, b, r); channel_set_rgb(&ur, g, b, r);
channel_set_rgb(&ll, b, r, g); channel_set_rgb(&ll, b, r, g);
int ret = 0; int ret = 0;
ret |= ncplane_highgradient_sized(n, ul, ur, ll, lr, maxy, maxx); if(ncplane_highgradient_sized(n, ul, ur, ll, lr, maxy, maxx) <= 0){
ret = -1;
}
ret |= ncplane_double_box(n, 0, channels, maxy - 1, maxx - 1, 0); ret |= ncplane_double_box(n, 0, channels, maxy - 1, maxx - 1, 0);
if(maxx >= 4 && maxy >= 3){ if(maxx >= 4 && maxy >= 3){
ret |= ncplane_cursor_move_yx(n, (maxy - 1) / 2, (maxx - 1) / 2); ret |= ncplane_cursor_move_yx(n, (maxy - 1) / 2, (maxx - 1) / 2);
@ -175,7 +177,9 @@ int sliding_puzzle_demo(struct notcurses* nc){
if(chunks[idx] == NULL){ if(chunks[idx] == NULL){
goto done; goto done;
} }
fill_chunk(chunks[idx], idx); if(fill_chunk(chunks[idx], idx)){
goto done;
}
} }
} }
// draw a box around the playing area // draw a box around the playing area
@ -183,7 +187,7 @@ int sliding_puzzle_demo(struct notcurses* nc){
goto done; goto done;
} }
DEMO_RENDER(nc); DEMO_RENDER(nc);
struct timespec ts = { .tv_sec = 0, .tv_nsec = 1000000000, }; struct timespec ts = { .tv_sec = 0, .tv_nsec = GIG, };
// fade out each of the chunks in succession // fade out each of the chunks in succession
/*for(cy = 0 ; cy < CHUNKS_VERT ; ++cy){ /*for(cy = 0 ; cy < CHUNKS_VERT ; ++cy){
for(cx = 0 ; cx < CHUNKS_HORZ ; ++cx){ for(cx = 0 ; cx < CHUNKS_HORZ ; ++cx){

@ -153,7 +153,8 @@ launch_pipe_process(int* pipe, int* pidfd){
pid_t p = -1; pid_t p = -1;
// on linux, we try to use the brand-new pidfd capability via clone3(). if // on linux, we try to use the brand-new pidfd capability via clone3(). if
// that fails, fall through to fork(), which is all we try to use on freebsd. // that fails, fall through to fork(), which is all we try to use on freebsd.
#ifdef __linux__ // FIXME clone3 is not yet supported on debian sparc64, as of 2020-06 anyway
#if (defined(__linux__) && !defined(__sparc__))
// FIXME introduced in linux 5.5 // FIXME introduced in linux 5.5
#ifndef CLONE_CLEAR_SIGHAND #ifndef CLONE_CLEAR_SIGHAND
#define CLONE_CLEAR_SIGHAND 0x100000000ULL #define CLONE_CLEAR_SIGHAND 0x100000000ULL

Loading…
Cancel
Save