add auxiliary vector to TAM #1440

This commit is contained in:
nick black 2021-04-25 00:27:47 -04:00 committed by Nick Black
parent 3e0783593d
commit dd85c7042b
6 changed files with 84 additions and 78 deletions

View File

@ -143,6 +143,13 @@ typedef enum {
SPRIXCELL_ANNIHILATED, // this cell has been wiped (all trans) SPRIXCELL_ANNIHILATED, // this cell has been wiped (all trans)
} sprixcell_e; } sprixcell_e;
// a TAM entry is a sprixcell_e state plus a possible auxiliary vector for
// reconstruction of annihilated cells, valid only for SPRIXCELL_ANNIHILATED.
typedef struct tament {
sprixcell_e state;
uint8_t auxvector; // palette entries for sixel, alphas for kitty
} tament;
// a sprixel represents a bitmap, using whatever local protocol is available. // a sprixel represents a bitmap, using whatever local protocol is available.
// there is a list of sprixels per ncpile. there ought never be very many // there is a list of sprixels per ncpile. there ought never be very many
// associated with a context (a dozen or so at max). with the kitty protocol, // associated with a context (a dozen or so at max). with the kitty protocol,
@ -215,7 +222,7 @@ typedef struct ncplane {
struct ncplane* boundto;// plane to which we are bound (ourself for roots) struct ncplane* boundto;// plane to which we are bound (ourself for roots)
sprixel* sprite; // pointer into the sprixel cache sprixel* sprite; // pointer into the sprixel cache
sprixcell_e* tacache; // transparency-annihilation sprite matrix tament* tam; // transparency-annihilation sprite matrix
void* userptr; // slot for the user to stick some opaque pointer void* userptr; // slot for the user to stick some opaque pointer
int (*resizecb)(struct ncplane*); // callback after parent is resized int (*resizecb)(struct ncplane*); // callback after parent is resized
@ -931,7 +938,6 @@ int kitty_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell);
void sprixel_free(sprixel* s); void sprixel_free(sprixel* s);
void sprixel_hide(sprixel* s); void sprixel_hide(sprixel* s);
int sprite_draw(const notcurses* n, const ncpile *p, sprixel* s, FILE* out);
int kitty_draw(const notcurses* n, const ncpile *p, sprixel* s, FILE* out); int kitty_draw(const notcurses* n, const ncpile *p, sprixel* s, FILE* out);
int sixel_draw(const notcurses* n, const ncpile *p, sprixel* s, FILE* out); int sixel_draw(const notcurses* n, const ncpile *p, sprixel* s, FILE* out);
// dimy and dimx are cell geometry, not pixel. // dimy and dimx are cell geometry, not pixel.
@ -964,6 +970,13 @@ sprite_destroy(const notcurses* nc, const ncpile* p, FILE* out, sprixel* s){
return nc->tcache.pixel_destroy(nc, p, out, s); return nc->tcache.pixel_destroy(nc, p, out, s);
} }
// precondition: s->invalidated is SPRIXEL_INVALIDATED or SPRIXEL_MOVED.
static inline int
sprite_draw(const notcurses* n, const ncpile* p, sprixel* s, FILE* out){
//sprixel_debug(stderr, s);
return n->tcache.pixel_draw(n, p, s, out);
}
static inline int static inline int
sprite_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell){ sprite_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell){
return nc->tcache.pixel_rebuild(nc, s, ycell, xcell); return nc->tcache.pixel_rebuild(nc, s, ycell, xcell);
@ -986,26 +999,26 @@ clamp_to_sixelmax(const tinfo* t, int* y, int* x){
// cannot be SPRIXCELL_OPAQUE. this postprocesses the TAM, flipping any // cannot be SPRIXCELL_OPAQUE. this postprocesses the TAM, flipping any
// such sprixcells to SPRIXCELL_MIXED. // such sprixcells to SPRIXCELL_MIXED.
static inline void static inline void
scrub_tam_boundaries(sprixcell_e* tam, int leny, int lenx, int cdimy, int cdimx){ scrub_tam_boundaries(tament* tam, int leny, int lenx, int cdimy, int cdimx){
// any sprixcells which don't cover the full cell underneath them cannot // any sprixcells which don't cover the full cell underneath them cannot
// be SPRIXCELL_OPAQUE // be SPRIXCELL_OPAQUE
const int cols = (lenx + cdimx - 1) / cdimx; const int cols = (lenx + cdimx - 1) / cdimx;
if(lenx % cdimx){ if(lenx % cdimx){
for(int y = 0 ; y < (leny + cdimy - 1) / cdimy ; ++y){ for(int y = 0 ; y < (leny + cdimy - 1) / cdimy ; ++y){
if(tam[y * cols + cols - 1] == SPRIXCELL_OPAQUE_KITTY){ if(tam[y * cols + cols - 1].state == SPRIXCELL_OPAQUE_KITTY){
tam[y * cols + cols - 1] = SPRIXCELL_MIXED_KITTY; tam[y * cols + cols - 1].state = SPRIXCELL_MIXED_KITTY;
}else if(tam[y * cols + cols - 1] == SPRIXCELL_OPAQUE_SIXEL){ }else if(tam[y * cols + cols - 1].state == SPRIXCELL_OPAQUE_SIXEL){
tam[y * cols + cols - 1] = SPRIXCELL_MIXED_SIXEL; tam[y * cols + cols - 1].state = SPRIXCELL_MIXED_SIXEL;
} }
} }
} }
if(leny % cdimy){ if(leny % cdimy){
const int y = (leny + cdimy - 1) / cdimy - 1; const int y = (leny + cdimy - 1) / cdimy - 1;
for(int x = 0 ; x < cols ; ++x){ for(int x = 0 ; x < cols ; ++x){
if(tam[y * cols + x] == SPRIXCELL_OPAQUE_KITTY){ if(tam[y * cols + x].state == SPRIXCELL_OPAQUE_KITTY){
tam[y * cols + x] = SPRIXCELL_MIXED_KITTY; tam[y * cols + x].state = SPRIXCELL_MIXED_KITTY;
}else if(tam[y * cols + x] == SPRIXCELL_OPAQUE_SIXEL){ }else if(tam[y * cols + x].state == SPRIXCELL_OPAQUE_SIXEL){
tam[y * cols + x] = SPRIXCELL_MIXED_SIXEL; tam[y * cols + x].state = SPRIXCELL_MIXED_SIXEL;
} }
} }
} }
@ -1022,7 +1035,7 @@ sprixel_state(const sprixel* s, int y, int x){
assert(localy < s->dimy); assert(localy < s->dimy);
assert(localx >= 0); assert(localx >= 0);
assert(localx < s->dimx); assert(localx < s->dimx);
return s->n->tacache[localy * s->dimx + localx]; return s->n->tam[localy * s->dimx + localx].state;
} }
// is sprixel backend kitty (only valid after calling setup_kitty_bitmaps())? // is sprixel backend kitty (only valid after calling setup_kitty_bitmaps())?
@ -1426,7 +1439,7 @@ egc_rtl(const char* egc, int* bytes){
static inline int static inline int
plane_blit_sixel(sprixel* spx, char* s, int bytes, int rows, int cols, plane_blit_sixel(sprixel* spx, char* s, int bytes, int rows, int cols,
int placey, int placex, int leny, int lenx, int placey, int placex, int leny, int lenx,
int parse_start, sprixcell_e* tacache){ int parse_start, tament* tam){
if(sprixel_load(spx, s, bytes, placey, placex, leny, lenx, parse_start)){ if(sprixel_load(spx, s, bytes, placey, placex, leny, lenx, parse_start)){
return -1; return -1;
} }
@ -1442,11 +1455,11 @@ plane_blit_sixel(sprixel* spx, char* s, int bytes, int rows, int cols,
} }
} }
if(n){ if(n){
//fprintf(stderr, "TACACHE WAS: %p NOW: %p size: %d/%d\n", n->tacache, tacache, rows, cols); //fprintf(stderr, "TAM WAS: %p NOW: %p size: %d/%d\n", n->tam, tam, rows, cols);
if(n->tacache != tacache){ if(n->tam != tam){
free(n->tacache); free(n->tam);
} }
n->tacache = tacache; n->tam = tam;
n->sprite = spx; n->sprite = spx;
} }
return 0; return 0;

View File

@ -162,7 +162,7 @@ int kitty_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell){
} }
int kitty_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){ int kitty_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){
if(s->n->tacache[s->dimx * ycell + xcell] == SPRIXCELL_ANNIHILATED){ if(s->n->tam[s->dimx * ycell + xcell].state == SPRIXCELL_ANNIHILATED){
//fprintf(stderr, "CACHED WIPE %d %d/%d\n", s->id, ycell, xcell); //fprintf(stderr, "CACHED WIPE %d %d/%d\n", s->id, ycell, xcell);
return 0; // already annihilated, needn't draw glyph in kitty return 0; // already annihilated, needn't draw glyph in kitty
} }
@ -246,7 +246,7 @@ int kitty_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){
static int static int
write_kitty_data(FILE* fp, int linesize, int leny, int lenx, write_kitty_data(FILE* fp, int linesize, int leny, int lenx,
int cols, const uint32_t* data, int cdimy, int cdimx, int cols, const uint32_t* data, int cdimy, int cdimx,
int sprixelid, sprixcell_e* tacache, int* parse_start, int sprixelid, tament* tam, int* parse_start,
uint32_t transcolor){ uint32_t transcolor){
if(linesize % sizeof(*data)){ if(linesize % sizeof(*data)){
fclose(fp); fclose(fp);
@ -289,21 +289,21 @@ write_kitty_data(FILE* fp, int linesize, int leny, int lenx,
int ycell = y / cdimy; int ycell = y / cdimy;
int tyx = xcell + ycell * cols; int tyx = xcell + ycell * cols;
//fprintf(stderr, "Tyx: %d y: %d (%d) * %d x: %d (%d)\n", tyx, y, y / cdimy, cols, x, x / cdimx); //fprintf(stderr, "Tyx: %d y: %d (%d) * %d x: %d (%d)\n", tyx, y, y / cdimy, cols, x, x / cdimx);
if(tacache[tyx] == SPRIXCELL_ANNIHILATED){ if(tam[tyx].state == SPRIXCELL_ANNIHILATED){
wipe[e] = 1; wipe[e] = 1;
}else{ }else{
wipe[e] = 0; wipe[e] = 0;
if(rgba_trans_p(source[e], transcolor)){ if(rgba_trans_p(source[e], transcolor)){
if(x % cdimx == 0 && y % cdimy == 0){ if(x % cdimx == 0 && y % cdimy == 0){
tacache[tyx] = SPRIXCELL_TRANSPARENT; tam[tyx].state = SPRIXCELL_TRANSPARENT;
}else if(tacache[tyx] == SPRIXCELL_OPAQUE_KITTY){ }else if(tam[tyx].state == SPRIXCELL_OPAQUE_KITTY){
tacache[tyx] = SPRIXCELL_MIXED_KITTY; tam[tyx].state = SPRIXCELL_MIXED_KITTY;
} }
}else{ }else{
if(x % cdimx == 0 && y % cdimy == 0){ if(x % cdimx == 0 && y % cdimy == 0){
tacache[tyx] = SPRIXCELL_OPAQUE_KITTY; tam[tyx].state = SPRIXCELL_OPAQUE_KITTY;
}else if(tacache[tyx] == SPRIXCELL_TRANSPARENT){ }else if(tam[tyx].state == SPRIXCELL_TRANSPARENT){
tacache[tyx] = SPRIXCELL_MIXED_KITTY; tam[tyx].state = SPRIXCELL_MIXED_KITTY;
} }
} }
} }
@ -319,7 +319,7 @@ write_kitty_data(FILE* fp, int linesize, int leny, int lenx,
if(fclose(fp) == EOF){ if(fclose(fp) == EOF){
return -1; return -1;
} }
scrub_tam_boundaries(tacache, leny, lenx, cdimy, cdimx); scrub_tam_boundaries(tam, leny, lenx, cdimy, cdimx);
return 0; return 0;
} }
#undef RGBA_MAXLEN #undef RGBA_MAXLEN
@ -336,43 +336,43 @@ int kitty_blit(ncplane* n, int linesize, const void* data,
if(fp == NULL){ if(fp == NULL){
return -1; return -1;
} }
sprixcell_e* tacache = NULL; tament* tam = NULL;
bool reuse = false; bool reuse = false;
// if we have a sprixel attached to this plane, see if we can reuse it // if we have a sprixel attached to this plane, see if we can reuse it
// (we need the same dimensions) and thus immediately apply its T-A table. // (we need the same dimensions) and thus immediately apply its T-A table.
if(n->tacache){ if(n->tam){
if(n->leny == rows && n->lenx == cols){ if(n->leny == rows && n->lenx == cols){
tacache = n->tacache; tam = n->tam;
reuse = true; reuse = true;
} }
} }
int parse_start = 0; int parse_start = 0;
if(!reuse){ if(!reuse){
tacache = malloc(sizeof(*tacache) * rows * cols); tam = malloc(sizeof(*tam) * rows * cols);
if(tacache == NULL){ if(tam == NULL){
fclose(fp); fclose(fp);
free(buf); free(buf);
return -1; return -1;
} }
memset(tacache, 0, sizeof(*tacache) * rows * cols); memset(tam, 0, sizeof(*tam) * rows * cols);
} }
// closes fp on all paths // closes fp on all paths
if(write_kitty_data(fp, linesize, leny, lenx, cols, data, if(write_kitty_data(fp, linesize, leny, lenx, cols, data,
bargs->u.pixel.celldimy, bargs->u.pixel.celldimx, bargs->u.pixel.celldimy, bargs->u.pixel.celldimx,
bargs->u.pixel.spx->id, tacache, &parse_start, bargs->u.pixel.spx->id, tam, &parse_start,
bargs->transcolor)){ bargs->transcolor)){
if(!reuse){ if(!reuse){
free(tacache); free(tam);
} }
free(buf); free(buf);
return -1; return -1;
} }
// take ownership of |buf| and |tacache| on success // take ownership of |buf| and |tam| on success
if(plane_blit_sixel(bargs->u.pixel.spx, buf, size, rows, cols, if(plane_blit_sixel(bargs->u.pixel.spx, buf, size, rows, cols,
bargs->placey, bargs->placex, bargs->placey, bargs->placex,
leny, lenx, parse_start, tacache) < 0){ leny, lenx, parse_start, tam) < 0){
if(!reuse){ if(!reuse){
free(tacache); free(tam);
} }
free(buf); free(buf);
return -1; return -1;

View File

@ -269,7 +269,7 @@ void free_plane(ncplane* p){
if(p->sprite){ if(p->sprite){
sprixel_hide(p->sprite); sprixel_hide(p->sprite);
} }
free(p->tacache); free(p->tam);
egcpool_dump(&p->pool); egcpool_dump(&p->pool);
free(p->name); free(p->name);
free(p->fb); free(p->fb);
@ -381,7 +381,7 @@ ncplane* ncplane_new_internal(notcurses* nc, ncplane* n,
p->name = strdup(nopts->name ? nopts->name : ""); p->name = strdup(nopts->name ? nopts->name : "");
p->halign = NCALIGN_UNALIGNED; p->halign = NCALIGN_UNALIGNED;
p->valign = NCALIGN_UNALIGNED; p->valign = NCALIGN_UNALIGNED;
p->tacache = NULL; p->tam = NULL;
if(!n){ // new root/standard plane if(!n){ // new root/standard plane
p->absy = nopts->y; p->absy = nopts->y;
p->absx = nopts->x; p->absx = nopts->x;

View File

@ -158,7 +158,7 @@ update_deets(uint32_t rgb, cdetails* deets){
static inline int static inline int
extract_color_table(const uint32_t* data, int linesize, int cols, extract_color_table(const uint32_t* data, int linesize, int cols,
int leny, int lenx, sixeltable* stab, int leny, int lenx, sixeltable* stab,
sprixcell_e* tacache, const blitterargs* bargs){ tament* tam, const blitterargs* bargs){
const int begx = bargs->begx; const int begx = bargs->begx;
const int begy = bargs->begy; const int begy = bargs->begy;
const int cdimy = bargs->u.pixel.celldimy; const int cdimy = bargs->u.pixel.celldimy;
@ -170,23 +170,23 @@ extract_color_table(const uint32_t* data, int linesize, int cols,
for(int sy = visy ; sy < (begy + leny) && sy < visy + 6 ; ++sy){ // offset within sprixel for(int sy = visy ; sy < (begy + leny) && sy < visy + 6 ; ++sy){ // offset within sprixel
const uint32_t* rgb = (data + (linesize / 4 * sy) + visx); const uint32_t* rgb = (data + (linesize / 4 * sy) + visx);
int txyidx = (sy / cdimy) * cols + (visx / cdimx); int txyidx = (sy / cdimy) * cols + (visx / cdimx);
if(tacache[txyidx] == SPRIXCELL_ANNIHILATED){ if(tam[txyidx].state == SPRIXCELL_ANNIHILATED){
//fprintf(stderr, "TRANS SKIP %d %d %d %d (cell: %d %d)\n", visy, visx, sy, txyidx, sy / cdimy, visx / cdimx); //fprintf(stderr, "TRANS SKIP %d %d %d %d (cell: %d %d)\n", visy, visx, sy, txyidx, sy / cdimy, visx / cdimx);
continue; continue;
} }
if(rgba_trans_p(*rgb, bargs->transcolor)){ if(rgba_trans_p(*rgb, bargs->transcolor)){
if(sy % cdimy == 0 && visx % cdimx == 0){ if(sy % cdimy == 0 && visx % cdimx == 0){
tacache[txyidx] = SPRIXCELL_TRANSPARENT; tam[txyidx].state = SPRIXCELL_TRANSPARENT;
}else if(tacache[txyidx] == SPRIXCELL_OPAQUE_SIXEL){ }else if(tam[txyidx].state == SPRIXCELL_OPAQUE_SIXEL){
tacache[txyidx] = SPRIXCELL_MIXED_SIXEL; tam[txyidx].state = SPRIXCELL_MIXED_SIXEL;
} }
stab->p2 = SIXEL_P2_TRANS; // even one forces P2=1 stab->p2 = SIXEL_P2_TRANS; // even one forces P2=1
continue; continue;
}else{ }else{
if(sy % cdimy == 0 && visx % cdimx == 0){ if(sy % cdimy == 0 && visx % cdimx == 0){
tacache[txyidx] = SPRIXCELL_OPAQUE_SIXEL; tam[txyidx].state = SPRIXCELL_OPAQUE_SIXEL;
}else if(tacache[txyidx] == SPRIXCELL_TRANSPARENT){ }else if(tam[txyidx].state == SPRIXCELL_TRANSPARENT){
tacache[txyidx] = SPRIXCELL_MIXED_SIXEL; tam[txyidx].state = SPRIXCELL_MIXED_SIXEL;
} }
} }
unsigned char comps[RGBSIZE]; unsigned char comps[RGBSIZE];
@ -417,7 +417,7 @@ write_sixel_data(FILE* fp, int leny, int lenx, const sixeltable* stab, int* pars
// A pixel block is indicated by setting cell_pixels_p(). // A pixel block is indicated by setting cell_pixels_p().
static inline int static inline int
sixel_blit_inner(int leny, int lenx, const sixeltable* stab, int rows, int cols, sixel_blit_inner(int leny, int lenx, const sixeltable* stab, int rows, int cols,
const blitterargs* bargs, sprixcell_e* tacache){ const blitterargs* bargs, tament* tam){
char* buf = NULL; char* buf = NULL;
size_t size = 0; size_t size = 0;
FILE* fp = open_memstream(&buf, &size); FILE* fp = open_memstream(&buf, &size);
@ -431,12 +431,12 @@ sixel_blit_inner(int leny, int lenx, const sixeltable* stab, int rows, int cols,
free(buf); free(buf);
return -1; return -1;
} }
scrub_tam_boundaries(tacache, leny, lenx, bargs->u.pixel.celldimy, scrub_tam_boundaries(tam, leny, lenx, bargs->u.pixel.celldimy,
bargs->u.pixel.celldimx); bargs->u.pixel.celldimx);
// take ownership of buf on success // take ownership of buf on success
if(plane_blit_sixel(bargs->u.pixel.spx, buf, size, rows, cols, if(plane_blit_sixel(bargs->u.pixel.spx, buf, size, rows, cols,
bargs->placey, bargs->placex, bargs->placey, bargs->placex,
leny, lenx, parse_start, tacache) < 0){ leny, lenx, parse_start, tam) < 0){
free(buf); free(buf);
return -1; return -1;
} }
@ -476,28 +476,28 @@ int sixel_blit(ncplane* n, int linesize, const void* data,
memset(stable.deets, 0, sizeof(*stable.deets) * colorregs); memset(stable.deets, 0, sizeof(*stable.deets) * colorregs);
int cols = bargs->u.pixel.spx->dimx; int cols = bargs->u.pixel.spx->dimx;
int rows = bargs->u.pixel.spx->dimy; int rows = bargs->u.pixel.spx->dimy;
sprixcell_e* tacache = NULL; tament* tam = NULL;
bool reuse = false; bool reuse = false;
// if we have a sprixel attached to this plane, see if we can reuse it // if we have a sprixel attached to this plane, see if we can reuse it
// (we need the same dimensions) and thus immediately apply its T-A table. // (we need the same dimensions) and thus immediately apply its T-A table.
if(n->tacache){ if(n->tam){
//fprintf(stderr, "IT'S A REUSE %d %d %d %d\n", n->tacachey, rows, n->tacachex, cols); //fprintf(stderr, "IT'S A REUSE %d %d\n", rows, cols);
if(n->leny == rows && n->lenx == cols){ if(n->leny == rows && n->lenx == cols){
tacache = n->tacache; tam = n->tam;
reuse = true; reuse = true;
} }
} }
if(!reuse){ if(!reuse){
tacache = malloc(sizeof(*tacache) * rows * cols); tam = malloc(sizeof(*tam) * rows * cols);
if(tacache == NULL){ if(tam == NULL){
return -1; return -1;
} }
memset(tacache, 0, sizeof(*tacache) * rows * cols); memset(tam, 0, sizeof(*tam) * rows * cols);
} }
if(extract_color_table(data, linesize, cols, leny, lenx, if(extract_color_table(data, linesize, cols, leny, lenx,
&stable, tacache, bargs)){ &stable, tam, bargs)){
if(!reuse){ if(!reuse){
free(tacache); free(tam);
} }
free(stable.table); free(stable.table);
free(stable.data); free(stable.data);
@ -505,7 +505,7 @@ int sixel_blit(ncplane* n, int linesize, const void* data,
return -1; return -1;
} }
refine_color_table(data, linesize, bargs->begy, bargs->begx, leny, lenx, &stable); refine_color_table(data, linesize, bargs->begy, bargs->begx, leny, lenx, &stable);
int r = sixel_blit_inner(leny, lenx, &stable, rows, cols, bargs, tacache); int r = sixel_blit_inner(leny, lenx, &stable, rows, cols, bargs, tam);
free(stable.data); free(stable.data);
free(stable.deets); free(stable.deets);
free(stable.table); free(stable.table);
@ -546,7 +546,7 @@ deepclean_output(FILE* fp, const sprixel* s, int y, int *x, int rle,
unsigned char mask = 0; unsigned char mask = 0;
for(int yi = y ; yi < y + 6 ; ++yi){ for(int yi = y ; yi < y + 6 ; ++yi){
const int tidx = (yi / s->cellpxy) * s->dimx + (xi / s->cellpxx); const int tidx = (yi / s->cellpxy) * s->dimx + (xi / s->cellpxx);
const bool nihil = (s->n->tacache[tidx] == SPRIXCELL_ANNIHILATED); const bool nihil = (s->n->tam[tidx].state == SPRIXCELL_ANNIHILATED);
if(!nihil){ if(!nihil){
mask |= (1u << (yi - y)); mask |= (1u << (yi - y));
} }
@ -759,7 +759,7 @@ int sixel_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell){
// redrawn, it's redrawn using P2=1. // redrawn, it's redrawn using P2=1.
int sixel_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){ int sixel_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){
(void)nc; (void)nc;
if(s->n->tacache[s->dimx * ycell + xcell] == SPRIXCELL_ANNIHILATED){ if(s->n->tam[s->dimx * ycell + xcell].state == SPRIXCELL_ANNIHILATED){
//fprintf(stderr, "CACHED WIPE %d %d/%d\n", s->id, ycell, xcell); //fprintf(stderr, "CACHED WIPE %d %d/%d\n", s->id, ycell, xcell);
return 1; // already annihilated FIXME but 0 breaks things return 1; // already annihilated FIXME but 0 breaks things
} }

View File

@ -14,7 +14,7 @@ sprixel_debug(FILE* out, const sprixel* s){
int idx = 0; int idx = 0;
for(int y = 0 ; y < s->dimy ; ++y){ for(int y = 0 ; y < s->dimy ; ++y){
for(int x = 0 ; x < s->dimx ; ++x){ for(int x = 0 ; x < s->dimx ; ++x){
fprintf(out, "%d", s->n->tacache[idx]); fprintf(out, "%d", s->n->tam[idx].state);
++idx; ++idx;
} }
fprintf(out, "\n"); fprintf(out, "\n");
@ -85,9 +85,9 @@ void sprixel_invalidate(sprixel* s, int y, int x){
if(s->invalidated != SPRIXEL_HIDE && s->n){ if(s->invalidated != SPRIXEL_HIDE && s->n){
int localy = y - s->n->absy; int localy = y - s->n->absy;
int localx = x - s->n->absx; int localx = x - s->n->absx;
//fprintf(stderr, "INVALIDATING AT %d/%d (%d/%d) TAM: %d\n", y, x, localy, localx, s->n->tacache[localy * s->dimx + localx]); //fprintf(stderr, "INVALIDATING AT %d/%d (%d/%d) TAM: %d\n", y, x, localy, localx, s->n->tam[localy * s->dimx + localx].state);
if(s->n->tacache[localy * s->dimx + localx] != SPRIXCELL_TRANSPARENT && if(s->n->tam[localy * s->dimx + localx].state != SPRIXCELL_TRANSPARENT &&
s->n->tacache[localy * s->dimx + localx] != SPRIXCELL_ANNIHILATED){ s->n->tam[localy * s->dimx + localx].state != SPRIXCELL_ANNIHILATED){
s->invalidated = SPRIXEL_INVALIDATED; s->invalidated = SPRIXEL_INVALIDATED;
} }
} }
@ -156,19 +156,12 @@ int sprite_wipe(const notcurses* nc, sprixel* s, int ycell, int xcell){
if(s->invalidated == SPRIXEL_HIDE){ // no need to do work if we're killing it if(s->invalidated == SPRIXEL_HIDE){ // no need to do work if we're killing it
return 0; return 0;
} }
//fprintf(stderr, "ANNIHILATED %p %d\n", s->n->tacache, s->dimx * ycell + xcell); //fprintf(stderr, "ANNIHILATED %p %d\n", s->n->tam, s->dimx * ycell + xcell);
int r = nc->tcache.pixel_cell_wipe(nc, s, ycell, xcell); int r = nc->tcache.pixel_cell_wipe(nc, s, ycell, xcell);
//fprintf(stderr, "WIPED %d %d/%d ret=%d\n", s->id, ycell, xcell, r); //fprintf(stderr, "WIPED %d %d/%d ret=%d\n", s->id, ycell, xcell, r);
// mark the cell as annihilated whether we actually scrubbed it or not, // mark the cell as annihilated whether we actually scrubbed it or not,
// so that we use this fact should we move to another frame // so that we use this fact should we move to another frame
s->n->tacache[s->dimx * ycell + xcell] = SPRIXCELL_ANNIHILATED; s->n->tam[s->dimx * ycell + xcell].state = SPRIXCELL_ANNIHILATED;
return r;
}
// precondition: s->invalidated is SPRIXEL_INVALIDATED or SPRIXEL_MOVED.
int sprite_draw(const notcurses* n, const ncpile* p, sprixel* s, FILE* out){
//sprixel_debug(stderr, s);
int r = n->tcache.pixel_draw(n, p, s, out);
return r; return r;
} }

View File

@ -419,13 +419,13 @@ TEST_CASE("Bitmaps") {
REQUIRE(s); REQUIRE(s);
CHECK(s->dimy == dimy); CHECK(s->dimy == dimy);
CHECK(s->dimx == dimx); CHECK(s->dimx == dimx);
const auto tam = n->tacache; const auto tam = n->tam;
for(int i = 0 ; i < s->dimy * s->dimx ; ++i){ for(int i = 0 ; i < s->dimy * s->dimx ; ++i){
int py = (i / dimx) * nc_->tcache.cellpixy; int py = (i / dimx) * nc_->tcache.cellpixy;
int px = (i % dimx) * nc_->tcache.cellpixx; int px = (i % dimx) * nc_->tcache.cellpixx;
// cells with a transparent pixel ought be SPRIXCELL_MIXED; // cells with a transparent pixel ought be SPRIXCELL_MIXED;
// cells without one ought be SPRIXCELL_OPAQUE. // cells without one ought be SPRIXCELL_OPAQUE.
sprixcell_e state = tam[(i / dimx) + (i % dimx)]; sprixcell_e state = tam[(i / dimx) + (i % dimx)].state;
if(i % 2){ if(i % 2){
if(state == SPRIXCELL_MIXED_SIXEL){ if(state == SPRIXCELL_MIXED_SIXEL){
state = SPRIXCELL_MIXED_KITTY; state = SPRIXCELL_MIXED_KITTY;