diff options
author | Khaled Hosny <khaled@aliftype.com> | 2022-08-12 02:12:04 +0200 |
---|---|---|
committer | Caolán McNamara <caolanm@redhat.com> | 2022-08-14 21:11:52 +0200 |
commit | 5e2b7a656024b621bdeeb6efd977331191b66d9d (patch) | |
tree | c81dc99f67ff3ab67aa8d305c5da7a1d308ad504 /vcl/source/outdev | |
parent | 72e56537d4bb9411229346da977d1d669ccfca9a (diff) |
Streamline Kashida validation logic
We are asked to validate the position *after* which Kashida will be
inserted, but HarfBuzz will tell us which glyph we can insert Kashida
*before*. So align both by passing down the position before and after
and make the loop iterating over glyph items a lot simpler.
As a bonus, the new code allow Kashida insertion across layout change in
both sides, old code allowed it only at the start of the layout.
Change-Id: I9f632610b92c0f4c512e50456bf7d207175f17ac
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/138168
Tested-by: Jenkins
Reviewed-by: Caolán McNamara <caolanm@redhat.com>
Diffstat (limited to 'vcl/source/outdev')
-rw-r--r-- | vcl/source/outdev/font.cxx | 26 |
1 files changed, 21 insertions, 5 deletions
diff --git a/vcl/source/outdev/font.cxx b/vcl/source/outdev/font.cxx index 071056e83690..8bae1c719e37 100644 --- a/vcl/source/outdev/font.cxx +++ b/vcl/source/outdev/font.cxx @@ -48,6 +48,8 @@ #include <salgdi.hxx> #include <svdata.hxx> +#include <unicode/uchar.h> + #include <strings.hrc> void OutputDevice::SetFont( const vcl::Font& rNewFont ) @@ -1311,14 +1313,28 @@ sal_Int32 OutputDevice::ValidateKashidas ( const OUString& rTxt, std::unique_ptr<SalLayout> pSalLayout = ImplLayout( rTxt, nIdx, nLen ); if( !pSalLayout ) return 0; + + auto nEnd = nIdx + nLen - 1; sal_Int32 nDropped = 0; for( int i = 0; i < nKashCount; ++i ) { - if( !pSalLayout->IsKashidaPosValid( pKashidaPos[ i ] )) - { - pKashidaPosDropped[ nDropped ] = pKashidaPos [ i ]; - ++nDropped; - } + auto nPos = pKashidaPos[i]; + auto nNextPos = nPos + 1; + + // Skip combining marks to find the next character after this position. + while (nNextPos <= nEnd && + u_getIntPropertyValue(rTxt[nNextPos], UCHAR_JOINING_TYPE) == U_JT_TRANSPARENT) + nNextPos++; + + // This is the start or end of the layout, it would happen if we + // changed the text styling in the middle of a word. Since we don’t do + // apply OpenType features across different layouts, this can’t be an + // invalid place to insert Kashida. + if (nPos == nIdx || nNextPos >= nEnd) + continue; + + if (!pSalLayout->IsKashidaPosValid(nPos, nNextPos)) + pKashidaPosDropped[nDropped++] = nPos; } return nDropped; } |