diff --git a/src/lib/internal.h b/src/lib/internal.h index d9b5a7475..a5ad4c77c 100644 --- a/src/lib/internal.h +++ b/src/lib/internal.h @@ -462,7 +462,7 @@ typedef struct tinfo { // this means dialing down their alpha to 0 (in equivalent space). int (*pixel_wipe)(sprixel* s, int y, int x); // perform the inverse of pixel_wipe, restoring an annihilated sprixcell. - int (*pixel_rebuild)(sprixel* s, int y, int x, const uint8_t* auxvec); + int (*pixel_rebuild)(sprixel* s, int y, int x, uint8_t* auxvec); int (*pixel_remove)(int id, FILE* out); // kitty only, issue actual delete command int (*pixel_init)(int fd); // called when support is detected int (*pixel_draw)(const struct notcurses* n, const struct ncpile* p, sprixel* s, FILE* out); @@ -939,8 +939,8 @@ int sixel_wipe(sprixel* s, int ycell, int xcell); // throughout to 0. the same trick doesn't work on sixel, but there we // can just print directly over the bitmap. int kitty_wipe(sprixel* s, int ycell, int xcell); -int sixel_rebuild(sprixel* s, int ycell, int xcell, const uint8_t* auxvec); -int kitty_rebuild(sprixel* s, int ycell, int xcell, const uint8_t* auxvec); +int sixel_rebuild(sprixel* s, int ycell, int xcell, uint8_t* auxvec); +int kitty_rebuild(sprixel* s, int ycell, int xcell, uint8_t* auxvec); void sprixel_free(sprixel* s); void sprixel_hide(sprixel* s); @@ -991,17 +991,16 @@ sprite_draw(const notcurses* n, const ncpile* p, sprixel* s, FILE* out){ static inline int sprite_rebuild(const notcurses* nc, sprixel* s, int ycell, int xcell){ int ret = 0; - uint8_t* auxvec = s->n->tam[s->dimx * ycell + xcell].auxvector; // special case the transition back to SPRIXCELL_TRANSPARENT; this can be // done in O(1), since the actual glyph needn't change. if(s->n->tam[s->dimx * ycell + xcell].state == SPRIXCELL_ANNIHILATED_TRANS){ s->n->tam[s->dimx * ycell + xcell].state = SPRIXCELL_TRANSPARENT; }else if(s->n->tam[s->dimx * ycell + xcell].state == SPRIXCELL_ANNIHILATED){ + uint8_t* auxvec = s->n->tam[s->dimx * ycell + xcell].auxvector; // sets the new state itself ret = nc->tcache.pixel_rebuild(s, ycell, xcell, auxvec); } s->n->tam[s->dimx * ycell + xcell].auxvector = NULL; - free(auxvec); return ret; } diff --git a/src/lib/kitty.c b/src/lib/kitty.c index decdd7542..43a380571 100644 --- a/src/lib/kitty.c +++ b/src/lib/kitty.c @@ -264,7 +264,7 @@ kitty_restore(char* triplet, int skip, int max, int pleft, #define RGBA_MAXLEN 768 // 768 base64-encoded pixels in 4096 bytes // restore an annihilated sprixcell by copying the alpha values from the // auxiliary vector back into the actual data. we then free the auxvector. -int kitty_rebuild(sprixel* s, int ycell, int xcell, const uint8_t* auxvec){ +int kitty_rebuild(sprixel* s, int ycell, int xcell, uint8_t* auxvec){ const int totalpixels = s->pixy * s->pixx; const int xpixels = s->cellpxx; const int ypixels = s->cellpxy; @@ -314,6 +314,7 @@ int kitty_rebuild(sprixel* s, int ycell, int xcell, const uint8_t* auxvec){ //fprintf(stderr, "CLEARED ROW, TARGY: %d\n", targy - 1); if(--targy == 0){ s->n->tam[s->dimx * ycell + xcell].state = state; + free(auxvec); return 0; } thisrow = targx; diff --git a/src/lib/render.c b/src/lib/render.c index 85e0d13c5..0dc8a1566 100644 --- a/src/lib/render.c +++ b/src/lib/render.c @@ -169,7 +169,7 @@ paint_sprixel(ncplane* p, struct crender* rvec, int starty, int startx, // if sprite_wipe_cell() fails, we presumably do not have the // ability to wipe, and must reprint the character if(sprite_wipe(nc, p->sprite, y, x)){ - //fprintf(stderr, "damaging due to wipe [%s] %d/%d\n", nccell_extended_gcluster(crender->p, &crender->c), y, x); +//fprintf(stderr, "damaging due to wipe [%s] %d/%d\n", nccell_extended_gcluster(crender->p, &crender->c), y, x); crender->s.damaged = 1; } crender->s.p_beats_sprixel = 1; diff --git a/src/lib/sixel.c b/src/lib/sixel.c index d8988a639..f9b06013d 100644 --- a/src/lib/sixel.c +++ b/src/lib/sixel.c @@ -546,6 +546,7 @@ deepclean_output(FILE* fp, const sprixel* s, int y, int *x, int rle, unsigned char mask = 0; for(int yi = y ; yi < y + 6 ; ++yi){ const int tidx = (yi / s->cellpxy) * s->dimx + (xi / s->cellpxx); + // FIXME need to make auxvec here const bool nihil = (s->n->tam[tidx].state == SPRIXCELL_ANNIHILATED) || (s->n->tam[tidx].state == SPRIXCELL_ANNIHILATED_TRANS); if(!nihil){ @@ -713,8 +714,8 @@ err: int sixel_draw(const notcurses* n, const ncpile* p, sprixel* s, FILE* out){ (void)n; - // if we've wiped any cells, we need actually wipe them out now, or else - // we'll get flicker when we move to the new location + // if we've wiped or rebuilt any cells, effect those changes now, or else + // we'll get flicker when we move to the new location. if(s->wipes_outstanding){ if(sixel_deepclean(s)){ return -1; @@ -747,8 +748,9 @@ int sixel_init(int fd){ return tty_emit("\e[?80;8452h", fd); } -int sixel_rebuild(sprixel* s, int ycell, int xcell, const uint8_t* auxvec){ - (void)s; +// only called for cells in SPRIXCELL_ANNIHILATED +int sixel_rebuild(sprixel* s, int ycell, int xcell, uint8_t* auxvec){ + s->wipes_outstanding = true; (void)ycell; (void)xcell; (void)auxvec;