benjajaja / ratatui-image

Ratatui widget for rendering image graphics in terminals that support it
https://crates.io/crates/ratatui-image
MIT License
117 stars 16 forks source link

Sixel image rendered on the last line of terminal causes a scroll, messes up the whole screen #57

Open benjajaja opened 1 week ago

benjajaja commented 1 week ago

There is DECSDM, but this causes the image to be rendered at 0,0 no matter what, and the implementations also seem to be wildly different.

No idea how to fix it other than not rendering in the last line of the terminal.

j4james commented 1 week ago

In theory it should be possible to render a Sixel image on the last line, but you need to limit the height to a multiple of 6 that will fit in the cell height. For example, if your cell height is 20px, you can fit an 18px high Sixel image in that space, but anything more than that is going to round up to a height of 24px, which will trigger a scroll.

So if you really want to fill the last line, you'd have to start your image a couple of rows up, so you can use a height that's both a multiple of 6, and a multiple of the cell height. For example, with a cell height of 20px, you can output a 60px image, with the first 40px being transparent. That would exactly span the bottom 3 rows, and shouldn't trigger a scroll.

In practice, though, many terminals incorrectly position the text cursor below the image, so they will still trigger a scroll even when the image fits. That's a terminal bug though, and it's worth noting that those terminals will potentially not even be able to fill the second last line of the screen without scrolling.

As for DECSDM, I know some apps/libraries have used that specifically for writing to the last line. But as you've noted, it forces the image to start at 0,0, so you have to add a lot of padding to get the image in the correct position. And again that depends on the terminal supporting transparency.

You should also be aware that DECSDM isn't universally supported, and for a long time many terminals implemented it backwards, because some of the DEC documentation had it backwards. I think most have corrected that by now, but it's possible there may be some that still have it backwards.