Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Now moves cursor vertically for sixel newlines even if there is no sixel #825

Merged
merged 3 commits into from
Sep 22, 2022

Conversation

Utkarsh-khambra
Copy link
Collaborator

fixes #822

To test this use this script. Since the script requires cell height to be 20px, you can change font size to be 11 in default config with monospace font family.
Screenshot from 2022-09-20 22-53-58

@github-actions github-actions bot added test Unit tests VT: Backend Virtual Terminal Backend (libterminal API) labels Sep 20, 2022
@christianparpart
Copy link
Member

Many thanks!

@Utkarsh-khambra with that, I don't think we do not need the configuration option images.sixel_cursor_conformance (bool) anymore as I was clearly misunderstanding/misreading/missing some of the Sixel documentation back in the days. I think it's save to completely get rid of that config option. ;)

@github-actions github-actions bot added the frontend Contour Terminal Emulator (GUI frontend) label Sep 20, 2022
src/terminal/SixelParser.cpp Outdated Show resolved Hide resolved
src/terminal/SixelParser_test.cpp Outdated Show resolved Hide resolved
moveCursorTo(_topLeft.line + unbox<int>(linesToBeRendered) - 1, _topLeft.column);
moveCursorTo(_topLeft.line + unbox<int>(linesToBeRendered), _topLeft.column);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

from this test

Test of the text cursor position after a Sixel image is output.
On a genuine VT340, after an image is output, the text cursor position is
set to the same row as the top of the final sixel line (regardless of
whether anything is output on that line). The column position remains
unchanged, i.e. it should align with the left of the image.

@christianparpart this change should place the ansi cursor to last sixel row, right?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

that is how i read it. any objections, @jerch?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If that's the case I think this is ready to merge.

Copy link

@jerch jerch Sep 21, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think "top of final sixel line" here means to clip the text cursor into the text row, wherever the first of the 6 pixel lines (last sixel band) ended up above. So its not the last line (sixth pixel line), but the first one determining it. Note that this has a weird consequence, if the last sixel band is not perfectly mapped on text line borders, possibly cutting off lower pixel rows, or not trigger scrolling at the end of the screen.
My impl still uses the last pixel line for this, but I prolly will change that.

Edit: Added another question, whether my assumption about the first pixel line is correct, here: jerch/xterm-addon-image#37 (comment)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So that means you may overwrite pixels in the last sixel line, if you print text just after drawing a sixel image.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes thats how I understand it so far. But lets see if it gets confirmed...

Copy link

@hackerb9 hackerb9 Sep 22, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The VT340 definitely does overwrite pixels in the last sixel line, but the cases which trigger it happen very rarely as long as a text newline is sent after the sixel image. Here is an image from some of the testing I had done to figure out where the text cursor would be positioned based on line endings (only NL, only GNL, or neither).
Test of Graphics NL and Text NL after sixel images of different height

First, I should state that it seems like the intention was for Sixel images to not include a GLF at the end, but for there to be a text LF after the image if text or another image is going to be written. As @j4james pointed out to me, this allows one to show a full screen sixel image without causing scrolling.

Second, when only LF is used at the end of the sixel data, 90% of the time there will be no overwrite. In actual practice, the glitch is much rarer than 10%. That is because image heights are often divisible by ten or a power of two or the character cell height, none of which can trigger what I call the VT340 text cursor glitch.

Personally, I think it is a programming mistake in the VT340 firmware since I cannot see anything in the documentation that would tip off an application developer to expect that behaviour. And, there does not appear to be any point to it.

I am not sure how to emulate it, but you can predict it on the VT340. For a sixel image of height $h$, let $a=(h-1)\bmod6$ and $b=(h-1)\bmod20$, then, the text will overlap the image when $a&gt;b$.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@hackerb9 If you want to see some serious overlap, try this:

echo -e '\eP1q#"60;1#1!360~\e\\'

@Utkarsh-khambra
Copy link
Collaborator Author

Utkarsh-khambra commented Sep 22, 2022

Thanks everybody for helping me in this. I got it to output similar image for this test as well, only discrepancy I see is with horizontal alignment but I am pretty sure this is because contour has 9px wide cells for my testing config.
Screenshot from 2022-09-22 12-51-54

Copy link
Member

@christianparpart christianparpart left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @Utkarsh-khambra for your work, and thanks @jerch, @hackerb9 and @j4james for your very valuable feedback and the joined discussion over here. :-)

@christianparpart christianparpart merged commit aa3b8e0 into master Sep 22, 2022
@christianparpart christianparpart deleted the fix/822 branch September 22, 2022 08:37
@hackerb9
Copy link

hackerb9 commented Sep 23, 2022

Thanks everybody for helping me in this. I got it to output similar image for this test as well, only discrepancy I see is with horizontal alignment but I am pretty sure this is because contour has 9px wide cells for my testing config. Screenshot from 2022-09-22 12-51-54

Wow! I did not expect anybody would replicate that behaviour and I am impressed. I do think it is a firmware bug that a text newline is not always sufficient to separate sixels from text. I suggest new terminals, like Contour, may want to make precise bug-for-bug VT340 compatibility available but disabled by default.

By the way, now that you've duplicated the overlap glitch, how is it affected when the size of the font goes up? If I'm correct, anything taller than 10×20 will reduce the percentage of "bad" image sizes that cause overlap.

@Utkarsh-khambra
Copy link
Collaborator Author

may want to make precise bug-for-bug VT340 compatibility available but disabled by default.

That's a good suggestion.
Here are some tests that I did

Cell Height Overlap
15 No
17 No
18 No
23 No
25 No
27 Yes
28 Yes
30 No
31 No
33 No
35 No
36 No
38 No
40 Yes
41 Yes
43 No
44 No
46 No
48 No
49 No
51 No
53 No
54 No
56 No
57 No
58 No
61 No
62 No
64 No

@hackerb9
Copy link

may want to make precise bug-for-bug VT340 compatibility available but disabled by default.

That's a good suggestion. Here are some tests that I did [...]

That looks close, but not what I would have predicted. You're only testing image heights 84 and 96, right?

If we can extrapolate from the VT340 glitch, I would expect the overlap bug to occur when

$$ (h_i-1)\bmod6 > (h_i-1)\bmod h_c $$

where $h_i$ is the height of the image and $h_c$ is the height of the character cell. On a VT340, $h_c$ is fixed at $20$.

With that formula, a character cell of height 23 would have overlap and 28 would not. It's possible my formula is wrong.

But, I wouldn't spend too much time trying to extend this bug to modern terminals. It's not like there is any compatibility to worry about and it'll only cause application developers grief as they have to implement workarounds to not overlap images.

@j4james
Copy link

j4james commented Sep 23, 2022

The VT340's behavior may not be to your liking, but it's not a bug or a glitch. It actually serves a very useful purpose when you're working with images that you want to align on text boundaries.

For example, if you want to output an image that is exactly one text cell in height, you need to output 4 sixel bands (24px height) with the last 4 pixels being transparent. If you end that with a GNL, the text cursor is exactly below the image.

Similarly if you want an image two text cells in height, it's 7 sixel bands (42px height) with the last 2 pixels transparent. And for an image three text cells in height, it's exactly 6 sixel bands (60px height).

In every case the text cursor ends up exactly below the visible portion of the image, overwriting only the transparent pixels. And if you leave off the final GNL, you can get the text cursor on the bottom row of the image instead.

Example test cases:

echo -en '\eP9;1q#1!800~-!800~-!800~-!800B-\e\\'
echo -en '\eP9;1q#1!800~-!800~-!800~-!800~-!800~-!800~-!800N-\e\\'
echo -en '\eP9;1q#1!800~-!800~-!800~-!800~-!800~-!800~-!800~-!800~-!800~-!800~-\e\\'

Please do not try to "fix" sixel. If you don't like it, and feel the need to change the standard, rather put that effort into a new graphics protocol instead.

@hackerb9
Copy link

Please do not try to "fix" sixel. If you don't like it, and feel the need to change the standard, rather put that effort into a new graphics protocol instead.

I respectfully disagree with you, but I also see that one of us is misunderstanding the problem. It's probably me and I want to understand, so let's discus that on a new bug so as to not clutter up this one: hackerb9/vt340test#25.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
frontend Contour Terminal Emulator (GUI frontend) test Unit tests VT: Backend Virtual Terminal Backend (libterminal API)
Projects
None yet
Development

Successfully merging this pull request may close these issues.

no vertical cursor progression on GLFs (sixel)
5 participants