mirror of
https://github.com/dankamongmen/notcurses
synced 2025-03-10 01:29:05 -04:00
Two unit tests on Sixel round trips, one with wipes #1580.
This commit is contained in:
parent
4cceb01acf
commit
ba6088578d
@ -26,9 +26,8 @@ fn main() -> NcResult<()> {
|
|||||||
|
|
||||||
// vframe.inflate(1)?; // this works
|
// vframe.inflate(1)?; // this works
|
||||||
|
|
||||||
vframe.resize(1, 1)?; // but it doesn't matter which values we put here
|
vframe.resize(6, 1)?;
|
||||||
|
|
||||||
// FIXME: render always gives an error
|
|
||||||
vframe.render(&mut nc, &voptions)?;
|
vframe.render(&mut nc, &voptions)?;
|
||||||
|
|
||||||
rsleep![&mut nc, 2];
|
rsleep![&mut nc, 2];
|
||||||
|
@ -946,10 +946,11 @@ sprixel* sprixel_by_id(const ncpile* n, uint32_t id);
|
|||||||
void sprixel_invalidate(sprixel* s, int y, int x);
|
void sprixel_invalidate(sprixel* s, int y, int x);
|
||||||
void sprixel_movefrom(sprixel* s, int y, int x);
|
void sprixel_movefrom(sprixel* s, int y, int x);
|
||||||
|
|
||||||
// is the sprixel backend kitty?
|
int sixel_blit(ncplane* nc, int linesize, const void* data,
|
||||||
static inline bool sprixel_kitty_p(const tinfo* t){
|
int leny, int lenx, const blitterargs* bargs);
|
||||||
return t->pixel_shutdown == kitty_shutdown;
|
|
||||||
}
|
int kitty_blit(ncplane* nc, int linesize, const void* data,
|
||||||
|
int leny, int lenx, const blitterargs* bargs);
|
||||||
|
|
||||||
static inline int
|
static inline int
|
||||||
sprite_destroy(const notcurses* nc, const ncpile* p, FILE* out, sprixel* s){
|
sprite_destroy(const notcurses* nc, const ncpile* p, FILE* out, sprixel* s){
|
||||||
@ -1008,6 +1009,12 @@ sprixel_state(const sprixel* s, int y, int x){
|
|||||||
return s->n->tacache[localy * s->dimx + localx];
|
return s->n->tacache[localy * s->dimx + localx];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// is sprixel backend kitty (only valid after calling setup_kitty_bitmaps())?
|
||||||
|
// FIXME kill this off, and use different states instead
|
||||||
|
static inline bool sprixel_kitty_p(const tinfo* t){
|
||||||
|
return t->pixel_shutdown == kitty_shutdown;
|
||||||
|
}
|
||||||
|
|
||||||
static inline void
|
static inline void
|
||||||
pool_release(egcpool* pool, nccell* c){
|
pool_release(egcpool* pool, nccell* c){
|
||||||
if(cell_extended_p(c)){
|
if(cell_extended_p(c)){
|
||||||
@ -1588,12 +1595,6 @@ ncdirect_bg_default_p(const struct ncdirect* nc){
|
|||||||
return channels_bg_default_p(ncdirect_channels(nc));
|
return channels_bg_default_p(ncdirect_channels(nc));
|
||||||
}
|
}
|
||||||
|
|
||||||
int sixel_blit(ncplane* nc, int linesize, const void* data,
|
|
||||||
int leny, int lenx, const blitterargs* bargs);
|
|
||||||
|
|
||||||
int kitty_blit(ncplane* nc, int linesize, const void* data,
|
|
||||||
int leny, int lenx, const blitterargs* bargs);
|
|
||||||
|
|
||||||
int term_fg_rgb8(bool RGBflag, const char* setaf, int colors, FILE* out,
|
int term_fg_rgb8(bool RGBflag, const char* setaf, int colors, FILE* out,
|
||||||
unsigned r, unsigned g, unsigned b);
|
unsigned r, unsigned g, unsigned b);
|
||||||
|
|
||||||
|
@ -1029,14 +1029,15 @@ rasterize_core(notcurses* nc, const ncpile* p, FILE* out, unsigned phase){
|
|||||||
//fprintf(stderr, "RAST %08x [%s] to %d/%d cols: %u %016lx\n", srccell->gcluster, pool_extended_gcluster(&nc->pool, srccell), y, x, srccell->width, srccell->channels);
|
//fprintf(stderr, "RAST %08x [%s] to %d/%d cols: %u %016lx\n", srccell->gcluster, pool_extended_gcluster(&nc->pool, srccell), y, x, srccell->width, srccell->channels);
|
||||||
// this is used to invalidate the sprixel in the first text round,
|
// this is used to invalidate the sprixel in the first text round,
|
||||||
// which is only necessary for sixel, not kitty.
|
// which is only necessary for sixel, not kitty.
|
||||||
if(rvec[damageidx].sprixel
|
if(rvec[damageidx].sprixel){
|
||||||
&& sprixel_state(rvec[damageidx].sprixel, y - nc->stdplane->absy, x - nc->stdplane->absx) != SPRIXCELL_TRANSPARENT
|
sprixcell_e scstate = sprixel_state(rvec[damageidx].sprixel, y - nc->stdplane->absy, x - nc->stdplane->absx);
|
||||||
&& sprixel_state(rvec[damageidx].sprixel, y - nc->stdplane->absy, x - nc->stdplane->absx) != SPRIXCELL_ANNIHILATED
|
if(scstate != SPRIXCELL_TRANSPARENT
|
||||||
&& !rvec[damageidx].s.p_beats_sprixel
|
&& scstate != SPRIXCELL_ANNIHILATED && !rvec[damageidx].s.p_beats_sprixel
|
||||||
&& !sprixel_kitty_p(&nc->tcache)){
|
&& !sprixel_kitty_p(&nc->tcache)){
|
||||||
//fprintf(stderr, "INVALIDATING at %d/%d (%u)\n", y, x, rvec[damageidx].s.p_beats_sprixel);
|
//fprintf(stderr, "INVALIDATING at %d/%d (%u)\n", y, x, rvec[damageidx].s.p_beats_sprixel);
|
||||||
|
|
||||||
sprixel_invalidate(rvec[damageidx].sprixel, y, x);
|
sprixel_invalidate(rvec[damageidx].sprixel, y, x);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if(term_putc(out, &nc->pool, srccell)){
|
if(term_putc(out, &nc->pool, srccell)){
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -2,6 +2,34 @@
|
|||||||
#include <ncurses.h> // needed for some definitions, see terminfo(3ncurses)
|
#include <ncurses.h> // needed for some definitions, see terminfo(3ncurses)
|
||||||
#include "internal.h"
|
#include "internal.h"
|
||||||
|
|
||||||
|
// we found Sixel support -- set up the API
|
||||||
|
static inline void
|
||||||
|
setup_sixel_bitmaps(tinfo* ti){
|
||||||
|
ti->bitmap_supported = true;
|
||||||
|
ti->color_registers = 256; // assumed default [shrug]
|
||||||
|
ti->pixel_init = sixel_init;
|
||||||
|
ti->pixel_draw = sixel_draw;
|
||||||
|
ti->sixel_maxx = 4096; // whee!
|
||||||
|
ti->sixel_maxy = 4096;
|
||||||
|
ti->pixel_remove = NULL;
|
||||||
|
ti->pixel_destroy = sixel_delete;
|
||||||
|
ti->pixel_cell_wipe = sixel_wipe;
|
||||||
|
ti->pixel_shutdown = sixel_shutdown;
|
||||||
|
ti->sprixel_height_factor = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
setup_kitty_bitmaps(tinfo* ti){
|
||||||
|
ti->pixel_cell_wipe = kitty_wipe;
|
||||||
|
ti->pixel_destroy = kitty_delete;
|
||||||
|
ti->pixel_init = kitty_init;
|
||||||
|
ti->pixel_remove = kitty_remove;
|
||||||
|
ti->pixel_draw = kitty_draw;
|
||||||
|
ti->pixel_shutdown = kitty_shutdown;
|
||||||
|
ti->sprixel_height_factor = 1;
|
||||||
|
set_pixel_blitter(kitty_blit);
|
||||||
|
}
|
||||||
|
|
||||||
static bool
|
static bool
|
||||||
query_rgb(void){
|
query_rgb(void){
|
||||||
bool rgb = tigetflag("RGB") == 1;
|
bool rgb = tigetflag("RGB") == 1;
|
||||||
@ -61,14 +89,7 @@ apply_term_heuristics(tinfo* ti, const char* termname){
|
|||||||
ti->quadrants = true;
|
ti->quadrants = true;
|
||||||
ti->pixel_query_done = true;
|
ti->pixel_query_done = true;
|
||||||
ti->bitmap_supported = true;
|
ti->bitmap_supported = true;
|
||||||
ti->pixel_cell_wipe = kitty_wipe;
|
setup_kitty_bitmaps(ti);
|
||||||
ti->pixel_destroy = kitty_delete;
|
|
||||||
ti->pixel_init = kitty_init;
|
|
||||||
ti->pixel_remove = kitty_remove;
|
|
||||||
ti->pixel_draw = kitty_draw;
|
|
||||||
ti->pixel_shutdown = kitty_shutdown;
|
|
||||||
ti->sprixel_height_factor = 1;
|
|
||||||
set_pixel_blitter(kitty_blit);
|
|
||||||
}else if(strstr(termname, "alacritty")){
|
}else if(strstr(termname, "alacritty")){
|
||||||
ti->alacritty_sixel_hack = true;
|
ti->alacritty_sixel_hack = true;
|
||||||
ti->quadrants = true;
|
ti->quadrants = true;
|
||||||
@ -334,22 +355,6 @@ query_sixel_details(tinfo* ti, int fd){
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// we found Sixel support -- set up the API
|
|
||||||
static void
|
|
||||||
setup_sixel(tinfo* ti){
|
|
||||||
ti->bitmap_supported = true;
|
|
||||||
ti->color_registers = 256; // assumed default [shrug]
|
|
||||||
ti->pixel_init = sixel_init;
|
|
||||||
ti->pixel_draw = sixel_draw;
|
|
||||||
ti->sixel_maxx = 4096; // whee!
|
|
||||||
ti->sixel_maxy = 4096;
|
|
||||||
ti->pixel_remove = NULL;
|
|
||||||
ti->pixel_destroy = sixel_delete;
|
|
||||||
ti->pixel_cell_wipe = sixel_wipe;
|
|
||||||
ti->pixel_shutdown = sixel_shutdown;
|
|
||||||
ti->sprixel_height_factor = 6;
|
|
||||||
}
|
|
||||||
|
|
||||||
// query for Sixel support
|
// query for Sixel support
|
||||||
static int
|
static int
|
||||||
query_sixel(tinfo* ti, int fd){
|
query_sixel(tinfo* ti, int fd){
|
||||||
@ -389,7 +394,7 @@ query_sixel(tinfo* ti, int fd){
|
|||||||
case WANT_SEMI:
|
case WANT_SEMI:
|
||||||
if(in == ';'){
|
if(in == ';'){
|
||||||
if(in4){
|
if(in4){
|
||||||
setup_sixel(ti);
|
setup_sixel_bitmaps(ti);
|
||||||
}
|
}
|
||||||
state = WANT_C4;
|
state = WANT_C4;
|
||||||
}else if(in == 'c'){
|
}else if(in == 'c'){
|
||||||
@ -404,7 +409,7 @@ query_sixel(tinfo* ti, int fd){
|
|||||||
// until graphics/ayosec is merged, alacritty doesn't actually
|
// until graphics/ayosec is merged, alacritty doesn't actually
|
||||||
// have sixel support. enable this then. FIXME
|
// have sixel support. enable this then. FIXME
|
||||||
/*if(ti->alacritty_sixel_hack){
|
/*if(ti->alacritty_sixel_hack){
|
||||||
setup_sixel(ti);
|
setup_sixel_bitmaps(ti);
|
||||||
}*/
|
}*/
|
||||||
state = DONE;
|
state = DONE;
|
||||||
}else if(in == ';'){
|
}else if(in == ';'){
|
||||||
|
@ -22,6 +22,30 @@ TEST_CASE("Bitmaps") {
|
|||||||
CHECK(nc_->tcache.bitmap_supported);
|
CHECK(nc_->tcache.bitmap_supported);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SUBCASE("SprixelResize") {
|
||||||
|
auto y = 10;
|
||||||
|
auto x = 10;
|
||||||
|
std::vector<uint32_t> v(x * y, htole(0xe61c28ff));
|
||||||
|
auto ncv = ncvisual_from_rgba(v.data(), y, sizeof(decltype(v)::value_type) * x, x);
|
||||||
|
REQUIRE(nullptr != ncv);
|
||||||
|
struct ncvisual_options vopts = {
|
||||||
|
.n = nullptr,
|
||||||
|
.scaling = NCSCALE_NONE,
|
||||||
|
.y = 0, .x = 0,
|
||||||
|
.begy = 0, .begx = 0,
|
||||||
|
.leny = 0, .lenx = 0,
|
||||||
|
.blitter = NCBLIT_PIXEL,
|
||||||
|
.flags = NCVISUAL_OPTION_NODEGRADE,
|
||||||
|
.transcolor = 0,
|
||||||
|
};
|
||||||
|
CHECK(0 == ncvisual_resize(ncv, 6, 1)); // FIXME get down to 1, 1
|
||||||
|
auto n = ncvisual_render(nc_, ncv, &vopts);
|
||||||
|
REQUIRE(nullptr != n);
|
||||||
|
auto s = n->sprite;
|
||||||
|
REQUIRE(nullptr != s);
|
||||||
|
ncvisual_destroy(ncv);
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef NOTCURSES_USE_MULTIMEDIA
|
#ifdef NOTCURSES_USE_MULTIMEDIA
|
||||||
SUBCASE("PixelRender") {
|
SUBCASE("PixelRender") {
|
||||||
auto ncv = ncvisual_from_file(find_data("worldmap.png"));
|
auto ncv = ncvisual_from_file(find_data("worldmap.png"));
|
||||||
|
@ -18,6 +18,7 @@ auto testing_notcurses() -> struct notcurses* {
|
|||||||
notcurses_options nopts{};
|
notcurses_options nopts{};
|
||||||
// FIXME get loglevel from command line. enabling it by default leads to
|
// FIXME get loglevel from command line. enabling it by default leads to
|
||||||
// more confusion than useful information, so leave it off by default.
|
// more confusion than useful information, so leave it off by default.
|
||||||
|
//nopts.loglevel = NCLOGLEVEL_TRACE;
|
||||||
nopts.flags = NCOPTION_SUPPRESS_BANNERS | NCOPTION_NO_ALTERNATE_SCREEN;
|
nopts.flags = NCOPTION_SUPPRESS_BANNERS | NCOPTION_NO_ALTERNATE_SCREEN;
|
||||||
auto nc = notcurses_init(&nopts, nullptr);
|
auto nc = notcurses_init(&nopts, nullptr);
|
||||||
return nc;
|
return nc;
|
||||||
@ -84,6 +85,11 @@ reset_terminal(){
|
|||||||
printf("%s", str);
|
printf("%s", str);
|
||||||
}
|
}
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
|
str = tigetstr("cnorm");
|
||||||
|
if(str != (char*)-1){
|
||||||
|
printf("%s", str);
|
||||||
|
}
|
||||||
|
fflush(stdout);
|
||||||
close(fd);
|
close(fd);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,141 @@
|
|||||||
#include "main.h"
|
#include "main.h"
|
||||||
#include "visual-details.h"
|
#include "visual-details.h"
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
// convert the sprixel at s having pixel dimensions dimyXdimx to an rgb(a)
|
||||||
|
// matrix for easier analysis. breaks on malformed sixels.
|
||||||
|
std::vector<uint32_t> sixel_to_rgb(const char* s, int dimy, int dimx) {
|
||||||
|
std::vector<uint32_t> bmap(dimy * dimx, 0x00000000ull);
|
||||||
|
std::vector<uint32_t> colors;
|
||||||
|
// first we skip the header
|
||||||
|
while(*s != '#'){
|
||||||
|
++s;
|
||||||
|
}
|
||||||
|
// now we build the color table (form: #Pc;Pu;Px;Py;Pz). data starts with
|
||||||
|
// a color spec lacking a semicolon.
|
||||||
|
enum {
|
||||||
|
STATE_WANT_HASH,
|
||||||
|
STATE_WANT_COLOR,
|
||||||
|
STATE_WANT_COLORSEMI,
|
||||||
|
STATE_WANT_COLORSPACE,
|
||||||
|
STATE_WANT_DATA,
|
||||||
|
} state = STATE_WANT_HASH;
|
||||||
|
unsigned color = 0;
|
||||||
|
unsigned x = 0;
|
||||||
|
unsigned y = 0;
|
||||||
|
unsigned rle = 1;
|
||||||
|
while(*s){
|
||||||
|
if(*s == '\e'){
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(state == STATE_WANT_HASH){
|
||||||
|
REQUIRE('#' == *s);
|
||||||
|
state = STATE_WANT_COLOR;
|
||||||
|
}else if(state == STATE_WANT_COLOR){
|
||||||
|
CHECK(isdigit(*s));
|
||||||
|
color = 0;
|
||||||
|
do{
|
||||||
|
color *= 10;
|
||||||
|
color += *s - '0';
|
||||||
|
++s;
|
||||||
|
}while(isdigit(*s));
|
||||||
|
//std::cerr << "Got color " << color << std::endl;
|
||||||
|
--s;
|
||||||
|
state = STATE_WANT_COLORSEMI;
|
||||||
|
}else if(state == STATE_WANT_COLORSEMI){
|
||||||
|
// if we get a semicolon, we're a colorspec, otherwise data
|
||||||
|
if(*s == ';'){
|
||||||
|
state = STATE_WANT_COLORSPACE;
|
||||||
|
}else{
|
||||||
|
state = STATE_WANT_DATA;
|
||||||
|
rle = 1;
|
||||||
|
}
|
||||||
|
}else if(state == STATE_WANT_COLORSPACE){
|
||||||
|
CHECK('2' == *(s++));
|
||||||
|
CHECK(';' == *(s++));
|
||||||
|
int r = 0;
|
||||||
|
do{
|
||||||
|
r *= 10;
|
||||||
|
r += *s - '0';
|
||||||
|
++s;
|
||||||
|
}while(isdigit(*s));
|
||||||
|
CHECK(';' == *(s++));
|
||||||
|
int g = 0;
|
||||||
|
do{
|
||||||
|
g *= 10;
|
||||||
|
g += *s - '0';
|
||||||
|
++s;
|
||||||
|
}while(isdigit(*s));
|
||||||
|
CHECK(';' == *(s++));
|
||||||
|
int b = 0;
|
||||||
|
do{
|
||||||
|
b *= 10;
|
||||||
|
b += *s - '0';
|
||||||
|
++s;
|
||||||
|
}while(isdigit(*s));
|
||||||
|
uint32_t rgb = 0xff000000 + (r << 16u) * 255 / 100 + (g << 8u) * 255 / 100 + b * 255 / 100;
|
||||||
|
//std::cerr << "Got color " << color << ": " << r << "/" << g << "/" << b << std::endl;
|
||||||
|
if(color >= colors.capacity()){
|
||||||
|
colors.resize(color + 1);
|
||||||
|
}
|
||||||
|
colors[color] = rgb;
|
||||||
|
state = STATE_WANT_HASH;
|
||||||
|
--s;
|
||||||
|
}
|
||||||
|
// read until we hit next colorspec
|
||||||
|
if(state == STATE_WANT_DATA){
|
||||||
|
//std::cerr << "Character " << *s << std::endl;
|
||||||
|
if(*s == '#'){
|
||||||
|
state = STATE_WANT_HASH;
|
||||||
|
--s;
|
||||||
|
}else if(*s == '!'){ // RLE
|
||||||
|
++s;
|
||||||
|
rle = 0;
|
||||||
|
do{
|
||||||
|
rle *= 10;
|
||||||
|
rle += *s - '0';
|
||||||
|
++s;
|
||||||
|
}while(isdigit(*s));
|
||||||
|
CHECK(2 < rle);
|
||||||
|
--s;
|
||||||
|
}else if(*s == '$'){
|
||||||
|
x = 0;
|
||||||
|
state = STATE_WANT_HASH;
|
||||||
|
}else if(*s == '-'){
|
||||||
|
x = 0;
|
||||||
|
y += 6;
|
||||||
|
state = STATE_WANT_HASH;
|
||||||
|
}else{
|
||||||
|
//std::cerr << "RLE: " << rle << " pos: " << y << "*" << x << std::endl;
|
||||||
|
for(unsigned xpos = x ; xpos < x + rle ; ++xpos){
|
||||||
|
for(unsigned ypos = y ; ypos < y + 6 ; ++ypos){
|
||||||
|
if((*s - 63) & (1u << (ypos - y))){
|
||||||
|
// ought be an empty pixel
|
||||||
|
CHECK(0x00000000ull == bmap[ypos * dimx + xpos]);
|
||||||
|
//std::cerr << *s << " BMAP[" << ypos << "][" << xpos << "] = " << std::hex << colors[color] << std::dec << std::endl;
|
||||||
|
bmap[ypos * dimx + xpos] = colors[color];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
x += rle;
|
||||||
|
rle = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
++s;
|
||||||
|
}
|
||||||
|
return bmap;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
void print_bmap(const std::vector<uint32_t> rgba, int pixy, int pixx){
|
||||||
|
for(int y = 0 ; y < pixy ; ++y){
|
||||||
|
for(int x = 0 ; x < pixx ; ++x){
|
||||||
|
std::cerr << "rgba[" << y << "][" << x << "] (" << y * x << "): " << std::hex << rgba[y * pixx + x] << std::dec << std::endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
TEST_CASE("Sixels") {
|
TEST_CASE("Sixels") {
|
||||||
auto nc_ = testing_notcurses();
|
auto nc_ = testing_notcurses();
|
||||||
@ -10,14 +145,36 @@ TEST_CASE("Sixels") {
|
|||||||
auto n_ = notcurses_stdplane(nc_);
|
auto n_ = notcurses_stdplane(nc_);
|
||||||
REQUIRE(n_);
|
REQUIRE(n_);
|
||||||
|
|
||||||
// FIXME force Sixel support
|
// this can only run with a Sixel backend
|
||||||
if(notcurses_check_pixel_support(nc_) <= 0){
|
if(notcurses_check_pixel_support(nc_) <= 0){
|
||||||
CHECK(0 == nc_->tcache.bitmap_supported);
|
return;
|
||||||
CHECK(!notcurses_stop(nc_));
|
}
|
||||||
|
if(nc_->tcache.color_registers <= 0){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef NOTCURSES_USE_MULTIMEDIA
|
#ifdef NOTCURSES_USE_MULTIMEDIA
|
||||||
|
SUBCASE("SixelRoundtrip") {
|
||||||
|
CHECK(1 == ncplane_set_base(n_, "&", 0, 0));
|
||||||
|
auto ncv = ncvisual_from_file(find_data("worldmap.png"));
|
||||||
|
REQUIRE(ncv);
|
||||||
|
struct ncvisual_options vopts{};
|
||||||
|
vopts.blitter = NCBLIT_PIXEL;
|
||||||
|
vopts.flags = NCVISUAL_OPTION_NODEGRADE;
|
||||||
|
auto newn = ncvisual_render(nc_, ncv, &vopts);
|
||||||
|
CHECK(newn);
|
||||||
|
CHECK(0 == notcurses_render(nc_));
|
||||||
|
auto rgb = sixel_to_rgb(newn->sprite->glyph, newn->sprite->pixy, newn->sprite->pixx);
|
||||||
|
for(int y = 0 ; y < newn->sprite->pixy ; ++y){
|
||||||
|
for(int x = 0 ; x < newn->sprite->pixx ; ++x){
|
||||||
|
//fprintf(stderr, "%03d/%03d NCV: %08x RGB: %08x\n", y, x, ncv->data[y * newn->sprite->pixx + x], rgb[y * newn->sprite->pixx + x]);
|
||||||
|
// FIXME
|
||||||
|
//CHECK(ncv->data[y * newn->sprite->pixx + x] == rgb[y * newn->sprite->pixx + x]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ncvisual_destroy(ncv);
|
||||||
|
}
|
||||||
|
|
||||||
SUBCASE("SixelBlit") {
|
SUBCASE("SixelBlit") {
|
||||||
CHECK(1 == ncplane_set_base(n_, "&", 0, 0));
|
CHECK(1 == ncplane_set_base(n_, "&", 0, 0));
|
||||||
auto ncv = ncvisual_from_file(find_data("natasha-blur.png"));
|
auto ncv = ncvisual_from_file(find_data("natasha-blur.png"));
|
||||||
@ -27,6 +184,8 @@ TEST_CASE("Sixels") {
|
|||||||
vopts.flags = NCVISUAL_OPTION_NODEGRADE;
|
vopts.flags = NCVISUAL_OPTION_NODEGRADE;
|
||||||
auto newn = ncvisual_render(nc_, ncv, &vopts);
|
auto newn = ncvisual_render(nc_, ncv, &vopts);
|
||||||
CHECK(newn);
|
CHECK(newn);
|
||||||
|
auto rgbold = sixel_to_rgb(newn->sprite->glyph, newn->sprite->pixy, newn->sprite->pixx);
|
||||||
|
//print_bmap(rgbold, newn->sprite->pixy, newn->sprite->pixx);
|
||||||
CHECK(0 == notcurses_render(nc_));
|
CHECK(0 == notcurses_render(nc_));
|
||||||
struct ncplane_options nopts = {
|
struct ncplane_options nopts = {
|
||||||
.y = ncplane_dim_y(newn) * 3 / 4,
|
.y = ncplane_dim_y(newn) * 3 / 4,
|
||||||
@ -43,12 +202,12 @@ TEST_CASE("Sixels") {
|
|||||||
uint64_t chan = CHANNELS_RGB_INITIALIZER(0, 0, 0, 0, 0, 0);
|
uint64_t chan = CHANNELS_RGB_INITIALIZER(0, 0, 0, 0, 0, 0);
|
||||||
CHECK(1 == ncplane_set_base(blockerplane, " ", 0, chan));
|
CHECK(1 == ncplane_set_base(blockerplane, " ", 0, chan));
|
||||||
CHECK(0 == notcurses_render(nc_));
|
CHECK(0 == notcurses_render(nc_));
|
||||||
sleep(2);
|
|
||||||
CHECK(1 == ncplane_set_base(n_, "%", 0, 0));
|
CHECK(1 == ncplane_set_base(n_, "%", 0, 0));
|
||||||
CHECK(0 == notcurses_render(nc_));
|
CHECK(0 == notcurses_render(nc_));
|
||||||
sleep(2);
|
|
||||||
// FIXME at this point currently, we get a degraded back of the orca
|
// FIXME at this point currently, we get a degraded back of the orca
|
||||||
// test via conversion back to image? unsure
|
// test via conversion back to image? unsure
|
||||||
|
auto rgbnew = sixel_to_rgb(newn->sprite->glyph, newn->sprite->pixy, newn->sprite->pixx);
|
||||||
|
//print_bmap(rgbnew, newn->sprite->pixy, newn->sprite->pixx);
|
||||||
CHECK(0 == ncplane_destroy(newn));
|
CHECK(0 == ncplane_destroy(newn));
|
||||||
CHECK(0 == ncplane_destroy(blockerplane));
|
CHECK(0 == ncplane_destroy(blockerplane));
|
||||||
ncvisual_destroy(ncv);
|
ncvisual_destroy(ncv);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user