vcl/source/outdev/text.cxx | 97 ++++++++++++++++++--------------------------- 1 file changed, 39 insertions(+), 58 deletions(-)
New commits: commit 88ce6625a03d33d714a2e26d9c41a7fa15b363a5 Author: Mike Kaganski <mike.kagan...@collabora.com> AuthorDate: Fri Mar 1 16:00:40 2024 +0600 Commit: Mike Kaganski <mike.kagan...@collabora.com> CommitDate: Fri Mar 1 22:38:01 2024 +0100 Fix nIndex / nLen passed to mpAlphaVDev->DrawCtrlText The corrected values along with original text make no sense Change-Id: Id84728e7d23d8780c4e7b7a76091470a82206efd Reviewed-on: https://gerrit.libreoffice.org/c/core/+/164184 Reviewed-by: Noel Grandin <noel.gran...@collabora.co.uk> Tested-by: Jenkins Reviewed-by: Mike Kaganski <mike.kagan...@collabora.com> diff --git a/vcl/source/outdev/text.cxx b/vcl/source/outdev/text.cxx index 158cb20ce93c..80fb2b94bd40 100644 --- a/vcl/source/outdev/text.cxx +++ b/vcl/source/outdev/text.cxx @@ -1758,17 +1758,12 @@ tools::Rectangle OutputDevice::GetTextRect( const tools::Rectangle& rRect, } void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, - sal_Int32 nIndex, sal_Int32 nLen, + const sal_Int32 nIndex, const sal_Int32 nLen, DrawTextFlags nStyle, std::vector< tools::Rectangle >* pVector, OUString* pDisplayText, const SalLayoutGlyphs* pGlyphs ) { assert(!is_double_buffered_window()); - if( (nLen < 0) || (nIndex + nLen >= rStr.getLength())) - { - nLen = rStr.getLength() - nIndex; - } - if ( !IsDeviceOutputNecessary() || (nIndex >= rStr.getLength()) ) return; @@ -1782,12 +1777,12 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, if ( mbOutputClipped ) return; - if( nIndex >= rStr.getLength() ) - return; - - if( (nLen < 0) || (nIndex + nLen >= rStr.getLength())) + // nIndex and nLen must go to mpAlphaVDev->DrawCtrlText unchanged + sal_Int32 nCorrectedIndex = nIndex; + sal_Int32 nCorrectedLen = nLen; + if ((nCorrectedLen < 0) || (nCorrectedIndex + nCorrectedLen >= rStr.getLength())) { - nLen = rStr.getLength() - nIndex; + nCorrectedLen = rStr.getLength() - nCorrectedIndex; } sal_Int32 nMnemonicPos = -1; @@ -1797,33 +1792,33 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, const OUString aStr = removeMnemonicFromString(rStr, nMnemonicPos); // Strip mnemonics always if (nMnemonicPos != -1) { - if (nMnemonicPos < nIndex) + if (nMnemonicPos < nCorrectedIndex) { - --nIndex; + --nCorrectedIndex; } else { - if (nMnemonicPos < (nIndex + nLen)) - --nLen; + if (nMnemonicPos < (nCorrectedIndex + nCorrectedLen)) + --nCorrectedLen; } if (nStyle & DrawTextFlags::Mnemonic && !pVector && !(GetSettings().GetStyleSettings().GetOptions() & StyleSettingsOptions::NoMnemonics)) { - SAL_WARN_IF( nMnemonicPos >= (nIndex+nLen), "vcl", "Mnemonic underline marker after last character" ); + SAL_WARN_IF( nMnemonicPos >= (nCorrectedIndex+nCorrectedLen), "vcl", "Mnemonic underline marker after last character" ); bool bInvalidPos = false; - if( nMnemonicPos >= nLen ) + if (nMnemonicPos >= nCorrectedLen) { // may occur in BiDi-Strings: the '~' is sometimes found behind the last char // due to some strange BiDi text editors // -> place the underline behind the string to indicate a failure bInvalidPos = true; - nMnemonicPos = nLen-1; + nMnemonicPos = nCorrectedLen - 1; } KernArray aDXArray; - GetTextArray(aStr, &aDXArray, nIndex, nLen, true, nullptr, pGlyphs); - sal_Int32 nPos = nMnemonicPos - nIndex; + GetTextArray(aStr, &aDXArray, nCorrectedIndex, nCorrectedLen, true, nullptr, pGlyphs); + sal_Int32 nPos = nMnemonicPos - nCorrectedIndex; sal_Int32 lc_x1 = nPos ? aDXArray[nPos - 1] : 0; sal_Int32 lc_x2 = aDXArray[nPos]; nMnemonicWidth = std::abs(lc_x1 - lc_x2); @@ -1871,7 +1866,7 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, SetTextColor( GetSettings().GetStyleSettings().GetDisableColor() ); } - DrawText(rPos, aStr, nIndex, nLen, pVector, pDisplayText, pGlyphs); + DrawText(rPos, aStr, nCorrectedIndex, nCorrectedLen, pVector, pDisplayText, pGlyphs); if (nMnemonicPos != -1) ImplDrawMnemonicLine(nMnemonicX, nMnemonicY, nMnemonicWidth); commit 4d39b88283d02eb44fe4cb8f3e4ec153ebf96a13 Author: Mike Kaganski <mike.kagan...@collabora.com> AuthorDate: Fri Mar 1 14:42:05 2024 +0600 Commit: Mike Kaganski <mike.kagan...@collabora.com> CommitDate: Fri Mar 1 22:37:49 2024 +0100 tdf#159976: make sure to always strip mnemonics in DrawCtrlText Note how GetCtrlTextWidth does that unconditionally. Also unify the code paths for disabled vs. enabled controls; this makes DrawText also use pGlyphs for disabled controls, similar to what was implemented for enabled controls in commit d70bf1c4caf37f38166b5f1facc08264cd203f92 (vcl: less text layout calls in Menu, 2018-09-05). Change-Id: I8fb6686012fb218dd4ae5536ad1cfeb69471e741 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/164180 Tested-by: Jenkins Reviewed-by: Mike Kaganski <mike.kagan...@collabora.com> diff --git a/vcl/source/outdev/text.cxx b/vcl/source/outdev/text.cxx index 2b4ada08e8cd..158cb20ce93c 100644 --- a/vcl/source/outdev/text.cxx +++ b/vcl/source/outdev/text.cxx @@ -1789,27 +1789,27 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, { nLen = rStr.getLength() - nIndex; } - OUString aStr = rStr; sal_Int32 nMnemonicPos = -1; tools::Long nMnemonicX = 0; tools::Long nMnemonicY = 0; tools::Long nMnemonicWidth = 0; - if ( (nStyle & DrawTextFlags::Mnemonic) && nLen > 1 ) + const OUString aStr = removeMnemonicFromString(rStr, nMnemonicPos); // Strip mnemonics always + if (nMnemonicPos != -1) { - aStr = removeMnemonicFromString( aStr, nMnemonicPos ); - if ( nMnemonicPos != -1 ) + if (nMnemonicPos < nIndex) { - if( nMnemonicPos < nIndex ) - { - --nIndex; - } - else - { - if( nMnemonicPos < (nIndex+nLen) ) - --nLen; - SAL_WARN_IF( nMnemonicPos >= (nIndex+nLen), "vcl", "Mnemonic underline marker after last character" ); - } + --nIndex; + } + else + { + if (nMnemonicPos < (nIndex + nLen)) + --nLen; + } + if (nStyle & DrawTextFlags::Mnemonic && !pVector + && !(GetSettings().GetStyleSettings().GetOptions() & StyleSettingsOptions::NoMnemonics)) + { + SAL_WARN_IF( nMnemonicPos >= (nIndex+nLen), "vcl", "Mnemonic underline marker after last character" ); bool bInvalidPos = false; if( nMnemonicPos >= nLen ) @@ -1837,13 +1837,14 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, nMnemonicX = mnOutOffX + aTempPos.X(); nMnemonicY = mnOutOffY + aTempPos.Y(); } + else + nMnemonicPos = -1; // Reset - we don't show the mnemonic } + std::optional<Color> oOldTextColor; + std::optional<Color> oOldTextFillColor; if ( nStyle & DrawTextFlags::Disable && ! pVector ) { - Color aOldTextColor; - Color aOldTextFillColor; - bool bRestoreFillColor; bool bHighContrastBlack = false; bool bHighContrastWhite = false; const StyleSettings& rStyleSettings( GetSettings().GetStyleSettings() ); @@ -1858,14 +1859,9 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, } } - aOldTextColor = GetTextColor(); + oOldTextColor = GetTextColor(); if ( IsTextFillColor() ) - { - bRestoreFillColor = true; - aOldTextFillColor = GetTextFillColor(); - } - else - bRestoreFillColor = false; + oOldTextFillColor = GetTextFillColor(); if( bHighContrastBlack ) SetTextColor( COL_GREEN ); @@ -1873,27 +1869,17 @@ void OutputDevice::DrawCtrlText( const Point& rPos, const OUString& rStr, SetTextColor( COL_LIGHTGREEN ); else SetTextColor( GetSettings().GetStyleSettings().GetDisableColor() ); - - DrawText( rPos, aStr, nIndex, nLen, pVector, pDisplayText ); - if (!(GetSettings().GetStyleSettings().GetOptions() & StyleSettingsOptions::NoMnemonics)) - { - if ( nMnemonicPos != -1 ) - ImplDrawMnemonicLine( nMnemonicX, nMnemonicY, nMnemonicWidth ); - } - SetTextColor( aOldTextColor ); - if ( bRestoreFillColor ) - SetTextFillColor( aOldTextFillColor ); - } - else - { - DrawText( rPos, aStr, nIndex, nLen, pVector, pDisplayText, pGlyphs ); - if ( !(GetSettings().GetStyleSettings().GetOptions() & StyleSettingsOptions::NoMnemonics) && !pVector ) - { - if ( nMnemonicPos != -1 ) - ImplDrawMnemonicLine( nMnemonicX, nMnemonicY, nMnemonicWidth ); - } } + DrawText(rPos, aStr, nIndex, nLen, pVector, pDisplayText, pGlyphs); + if (nMnemonicPos != -1) + ImplDrawMnemonicLine(nMnemonicX, nMnemonicY, nMnemonicWidth); + + if (oOldTextColor) + SetTextColor( *oOldTextColor ); + if (oOldTextFillColor) + SetTextFillColor(*oOldTextFillColor); + if( mpAlphaVDev ) mpAlphaVDev->DrawCtrlText( rPos, rStr, nIndex, nLen, nStyle, pVector, pDisplayText ); }