Visitar URL original
atlas: measure ligature overhang against the glyph's own advance by conr2d · Pull Request #20905 · microsoft/terminal · GitHub
Skip to content

atlas: measure ligature overhang against the glyph's own advance - #20905

Open
Jeeyong Um (conr2d) wants to merge 1 commit into
microsoft:mainfrom
conr2d:fix/wide-glyph-overhang-color
Open

Jeeyong Um (conr2d) wants to merge 1 commit into
microsoft:mainfrom
conr2d:fix/wide-glyph-overhang-color

Conversation

@conr2d

Copy link
Copy Markdown

Summary of the Pull Request

AtlasEngine's cell-wise ligature coloring now measures overhang against the advance a glyph is drawn with, instead of against a single cell. Wide (2-column) glyphs no longer take the next cell's foreground where their italic slant overhangs it.

References and Relevant Issues

Closes #20890. Related: #19033, #16585.

Detailed Description of the Pull Request / Additional comments

_drawGlyph decided overlapSplit once per glyph, from its ink bounds against fixed thresholds: -cellSize.x/2 and font.advanceWidth + cellSize.x/2. font.advanceWidth is the advance of '0', so for a 2-column glyph the right threshold sat in the middle of its own second column. Every CJK glyph was therefore classified as a ligature. Upright that's invisible, because both columns share a color. Italic ink crossing into a third column, though, was painted in that column's color.

Whether a glyph acts as a ligature depends on the advance it's drawn with, and that's a property of its placement, not of the glyph. So the decision is now split along that line:

  • _drawGlyph (cached per glyph) only marks glyphs that can be a ligature: at least a cell wide, and only when liga isn't disabled. The two _ligatureOverhangTrigger* members become a single bool _ligatureOverlapSplit.
  • _drawText passes the glyph's advance range [advanceLeft, advanceRight) to _drawTextOverlapSplit.
  • _drawTextOverlapSplit colors each segment from the column underneath it, but only within the columns the glyph covers. That range is its advance, widened to wherever the ink overhangs the advance by at least half a cell, which is what a ligature such as an arrow drawn back over a - looks like. Smaller overhangs, such as an italic slant, clamp to the nearest column inside the range and keep their own color.

Existing cases, as I understand them:

  • single-glyph ligatures like != with a 2-column advance are still split per column;
  • the && padding-glyph case still takes the first column's color, now through the widened range rather than a special case;
  • line renditions keep the existing columnAdvance handling;
  • with liga disabled, nothing is split, as before.

For wide glyphs the function still runs (as it did, since they were all flagged), and finds a single color.

Validation Steps Performed

None. I have not built or run this. Per Leonard Hecker (@lhecker)'s request on #20890, validation is left to the maintainer. The repro script is in #20890.

AI disclosure: the investigation in #20890 and this change were written with Claude (Anthropic) at my direction. Leonard Hecker (@lhecker) asked for an LLM-authored PR on #20890 and permitted it there.

PR Checklist

Wide glyphs were all classified as ligatures, because the overhang
thresholds were computed from a single cell (the advance of '0'). Their
italic slant overhanging into the next column was then painted in that
column's foreground.

The ligature decision now happens where a glyph is drawn, against the
advance it is drawn with. The glyph cache only records whether a glyph
can be a ligature at all. Ink that overhangs its advance by less than
half a cell keeps the color of the nearest column it covers.

Closes microsoft#20890
@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines:
There may be pipelines that require an authorized user to comment /azp run to run.

@conr2d

Copy link
Copy Markdown
Author

@microsoft-github-policy-service agree

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Italic CJK (wide) glyphs take the next cell's foreground where they overhang: ligature-split threshold uses a 1-cell width

1 participant