From 20eb1af118aaaff680f709dcd3a7ac8431ec50a5 Mon Sep 17 00:00:00 2001 From: Ryan Oldenburg Date: Thu, 6 May 2021 13:40:31 -0500 Subject: [PATCH] selection rects, better initial y --- src/pixie/fonts.nim | 14 ++++++++++++-- tests/fonts/diffs/lines2.png | Bin 0 -> 6665 bytes tests/fonts/masters/lines2.png | Bin 0 -> 3476 bytes tests/fonts/rendered/lines2.png | Bin 0 -> 7910 bytes tests/test_fonts.nim | 20 ++++++++++++++++++++ 5 files changed, 32 insertions(+), 2 deletions(-) create mode 100644 tests/fonts/diffs/lines2.png create mode 100644 tests/fonts/masters/lines2.png create mode 100644 tests/fonts/rendered/lines2.png diff --git a/src/pixie/fonts.nim b/src/pixie/fonts.nim index 2b5302a..b53d63a 100644 --- a/src/pixie/fonts.nim +++ b/src/pixie/fonts.nim @@ -157,16 +157,25 @@ proc typeset*( result += font.typeface.getAdvance(runes[i]) result *= font.scale + var fontUnitInitialY = font.typeface.ascent + font.typeface.lineGap / 2 + if lineHeight != font.defaultLineHeight: + fontUnitInitialY += ( + (lineHeight / font.scale) - + (font.typeface.ascent - font.typeface.descent + font.typeface.lineGap) + ) / 2 + let initialY = round(fontUnitInitialY * font.scale) + var at: Vec2 prevCanWrap: int - at.y = round((font.typeface.ascent + font.typeface.lineGap / 2) * font.scale) - at.y += (lineheight - font.defaultLineHeight) / 2 + at.y = initialY for i, rune in result.runes: if rune == LF: + let advance = font.typeface.getAdvance(SP) * font.scale result.positions[i] = at at.x = 0 at.y += lineHeight + result.selectionRects[i] = rect(at.x, at.y - initialY, advance, lineHeight) prevCanWrap = 0 else: if rune.canWrap(): @@ -185,6 +194,7 @@ proc typeset*( at.x += advance(font, result.runes, j, kerning) result.positions[i] = at + result.selectionRects[i] = rect(at.x, at.y - initialY, advance, lineHeight) at.x += advance iterator paths*(arrangement: Arrangement): Path = diff --git a/tests/fonts/diffs/lines2.png b/tests/fonts/diffs/lines2.png new file mode 100644 index 0000000000000000000000000000000000000000..bc3a8f339b35043b4a31836d22f4bab78feace81 GIT binary patch literal 6665 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 literal 0 HcmV?d00001 diff --git a/tests/fonts/masters/lines2.png b/tests/fonts/masters/lines2.png new file mode 100644 index 0000000000000000000000000000000000000000..0b1308c07056d40a648ca05d0c946cdef9e9273c GIT binary patch literal 3476 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