[Libreoffice-commits] .: vcl/source

Caolán McNamara caolan at kemper.freedesktop.org
Tue Mar 29 06:06:32 PDT 2011


 vcl/source/gdi/outdev3.cxx        |   46 ++++++++++++++++++++++++--------------
 vcl/source/gdi/pdfwriter_impl.cxx |   23 +++++++++++++++++++
 2 files changed, 53 insertions(+), 16 deletions(-)

New commits:
commit 53e2bdb610cb46b8a2482c742820e2dbe80bfc47
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Tue Mar 29 14:00:33 2011 +0100

    Resolves: rhbz#684580 'X' and '/' strike-through escapes range
    
    i.e. it bleeds outside the text it is supposed to affect.  See #i114076#,

diff --git a/vcl/source/gdi/outdev3.cxx b/vcl/source/gdi/outdev3.cxx
index 02febe3..d43c163 100644
--- a/vcl/source/gdi/outdev3.cxx
+++ b/vcl/source/gdi/outdev3.cxx
@@ -4005,6 +4005,11 @@ void OutputDevice::ImplDrawStrikeoutChar( long nBaseX, long nBaseY,
                                           FontStrikeout eStrikeout,
                                           Color aColor )
 {
+    //See qadevOOo/testdocs/StrikeThrough.odt for examples if you need
+    //to tweak this
+    if (!nWidth)
+        return;
+
     // PDF-export does its own strikeout drawing... why again?
     if( mpPDFWriter && mpPDFWriter->isBuiltinFont(mpFontEntry->maFontSelData.mpFontData) )
         return;
@@ -4017,35 +4022,23 @@ void OutputDevice::ImplDrawStrikeoutChar( long nBaseX, long nBaseY,
         cStrikeoutChar = 'X';
     static const int nTestStrLen = 4;
     static const int nMaxStrikeStrLen = 2048;
-    xub_Unicode aChars[ nMaxStrikeStrLen +1]; // +1 for valgrind...
+    xub_Unicode aChars[nMaxStrikeStrLen+1]; // +1 for valgrind...
     for( int i = 0; i < nTestStrLen; ++i)
         aChars[i] = cStrikeoutChar;
     const String aStrikeoutTest( aChars, nTestStrLen );
 
     // calculate approximation of strikeout atom size
-    long nStrikeoutWidth = nWidth;
+    long nStrikeoutWidth = 0;
     SalLayout* pLayout = ImplLayout( aStrikeoutTest, 0, nTestStrLen );
     if( pLayout )
     {
-        nStrikeoutWidth = (pLayout->GetTextWidth() +nTestStrLen/2) / (nTestStrLen * pLayout->GetUnitsPerPixel());        
+        nStrikeoutWidth = pLayout->GetTextWidth() / (nTestStrLen * pLayout->GetUnitsPerPixel());
         pLayout->Release();
     }
     if( nStrikeoutWidth <= 0 ) // sanity check
         return;
 
-    // calculate acceptable strikeout length
-    // allow the strikeout to be one pixel larger than the text it strikes out
-    long nMaxWidth = nStrikeoutWidth * 3 / 4;
-    if ( nMaxWidth < 2 )
-        nMaxWidth = 2;
-    nMaxWidth += nWidth + 1;
-
-    int nStrikeStrLen = (nMaxWidth - 1) / nStrikeoutWidth;
-    // if the text width is smaller than the strikeout text, then do not
-    // strike out at all. This case requires user interaction, e.g. adding
-    // a space to the text
-    if( nStrikeStrLen <= 0 )
-        return;
+    int nStrikeStrLen = (nWidth+(nStrikeoutWidth-1)) / nStrikeoutWidth;
     if( nStrikeStrLen > nMaxStrikeStrLen )
         nStrikeStrLen = nMaxStrikeStrLen;
 
@@ -4074,8 +4067,29 @@ void OutputDevice::ImplDrawStrikeoutChar( long nBaseX, long nBaseY,
     ImplInitTextColor();
 
     pLayout->DrawBase() = Point( nBaseX+mnTextOffX, nBaseY+mnTextOffY );
+
+    Rectangle aPixelRect;
+    aPixelRect.nLeft = nBaseX+mnTextOffX;
+    aPixelRect.nRight = aPixelRect.nLeft+nWidth;
+    aPixelRect.nBottom = nBaseY+mpFontEntry->maMetric.mnDescent;
+    aPixelRect.nTop = nBaseY-mpFontEntry->maMetric.mnAscent;
+
+    if (mpFontEntry->mnOrientation)
+    {
+        Polygon aPoly( aPixelRect );
+        aPoly.Rotate( Point(nBaseX+mnTextOffX, nBaseY+mnTextOffY), mpFontEntry->mnOrientation);
+        aPixelRect = aPoly.GetBoundRect();
+    }
+
+    Push( PUSH_CLIPREGION );
+    IntersectClipRegion( PixelToLogic(aPixelRect) );
+    if( mbInitClipRegion )
+        ImplInitClipRegion();
+
     pLayout->DrawText( *mpGraphics );
+
     pLayout->Release();
+    Pop();
 
     SetTextColor( aOldColor );
     ImplInitTextColor();
diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx
index 442a25d..485dad3 100644
--- a/vcl/source/gdi/pdfwriter_impl.cxx
+++ b/vcl/source/gdi/pdfwriter_impl.cxx
@@ -8264,6 +8264,9 @@ void PDFWriterImpl::drawStrikeoutLine( OStringBuffer& aLine, long nWidth, FontSt
 
 void PDFWriterImpl::drawStrikeoutChar( const Point& rPos, long nWidth, FontStrikeout eStrikeout )
 {
+    //See qadevOOo/testdocs/StrikeThrough.odt for examples if you need
+    //to tweak this
+
     String aStrikeoutChar = String::CreateFromAscii( eStrikeout == STRIKEOUT_SLASH ? "/" : "X" );
     String aStrikeout = aStrikeoutChar;
     while( m_pReferenceDevice->GetTextWidth( aStrikeout ) < nWidth )
@@ -8285,7 +8288,27 @@ void PDFWriterImpl::drawStrikeoutChar( const Point& rPos, long nWidth, FontStrik
     // strikeout string is left aligned non-CTL text
     sal_uLong nOrigTLM = m_pReferenceDevice->GetLayoutMode();
     m_pReferenceDevice->SetLayoutMode( TEXT_LAYOUT_BIDI_STRONG|TEXT_LAYOUT_COMPLEX_DISABLED );
+
+    push( PUSH_CLIPREGION );
+    FontMetric aRefDevFontMetric = m_pReferenceDevice->GetFontMetric();
+    Rectangle aRect;
+    aRect.nLeft = rPos.X();
+    aRect.nRight = aRect.nLeft+nWidth;
+    aRect.nBottom = rPos.Y()+aRefDevFontMetric.GetDescent();
+    aRect.nTop = rPos.Y()-aRefDevFontMetric.GetAscent();
+
+    ImplFontEntry* pFontEntry = m_pReferenceDevice->mpFontEntry;
+    if (pFontEntry->mnOrientation)
+    {
+        Polygon aPoly( aRect );
+        aPoly.Rotate( rPos, pFontEntry->mnOrientation);
+        aRect = aPoly.GetBoundRect();
+    }
+
+    intersectClipRegion( aRect );
     drawText( rPos, aStrikeout, 0, aStrikeout.Len(), false );
+    pop();
+
     m_pReferenceDevice->SetLayoutMode( nOrigTLM );
 
     if ( bShadow )


More information about the Libreoffice-commits mailing list