[Libreoffice-commits] .: 3 commits - configure.in vcl/generic vcl/inc vcl/source

Norbert Thiebaud nthiebaud at kemper.freedesktop.org
Sun Mar 4 19:20:28 PST 2012


 configure.in                         |    8 -
 vcl/generic/glyphs/gcach_layout.cxx  |    4 
 vcl/generic/print/genpspgraphics.cxx |    3 
 vcl/inc/sallayout.hxx                |    5 
 vcl/source/gdi/pdfwriter_impl.cxx    |    1 
 vcl/source/gdi/sallayout.cxx         |  267 ++++++++++++++---------------------
 6 files changed, 125 insertions(+), 163 deletions(-)

New commits:
commit 2ea4964b2e81a25125eec7ce3eb0b06b3883edf0
Author: Norbert Thiebaud <nthiebaud at gmail.com>
Date:   Sun Mar 4 19:30:04 2012 -0600

    help GlyphItems vector to be sized correctly up-front

diff --git a/vcl/generic/glyphs/gcach_layout.cxx b/vcl/generic/glyphs/gcach_layout.cxx
index 5f92f48..ef03aa3 100644
--- a/vcl/generic/glyphs/gcach_layout.cxx
+++ b/vcl/generic/glyphs/gcach_layout.cxx
@@ -106,6 +106,8 @@ bool ServerFontLayoutEngine::operator()( ServerFontLayout& rLayout, ImplLayoutAr
     int nGlyphWidth = 0;
     GlyphItem aPrevItem;
     bool bRightToLeft;
+
+    rLayout.Reserve(rArgs.mnLength);
     for( int nCharPos = -1; rArgs.GetNextPos( &nCharPos, &bRightToLeft ); )
     {
         sal_UCS4 cChar = rArgs.mpStr[ nCharPos ];
@@ -409,6 +411,8 @@ bool IcuLayoutEngine::operator()( ServerFontLayout& rLayout, ImplLayoutArgs& rAr
     // allocate temporary arrays, note: round to even
     int nGlyphCapacity = (3 * (rArgs.mnEndCharPos - rArgs.mnMinCharPos ) | 15) + 1;
 
+    rLayout.Reserve(nGlyphCapacity);
+
     struct IcuPosition{ float fX, fY; };
     const int nAllocSize = sizeof(LEGlyphID) + sizeof(le_int32) + sizeof(IcuPosition);
     LEGlyphID* pIcuGlyphs = (LEGlyphID*)alloca( (nGlyphCapacity * nAllocSize) + sizeof(IcuPosition) );
diff --git a/vcl/generic/print/genpspgraphics.cxx b/vcl/generic/print/genpspgraphics.cxx
index b806c1d..29c0610 100644
--- a/vcl/generic/print/genpspgraphics.cxx
+++ b/vcl/generic/print/genpspgraphics.cxx
@@ -616,6 +616,9 @@ bool PspFontLayout::LayoutText( ImplLayoutArgs& rArgs )
     Point aNewPos( 0, 0 );
     GlyphItem aPrevItem;
     rtl_TextEncoding aFontEnc = mrPrinterGfx.GetFontMgr().getFontEncoding( mnFontID );
+
+    Reserve(rArgs.mnLength);
+
     for(;;)
     {
         bool bRightToLeft;
diff --git a/vcl/inc/sallayout.hxx b/vcl/inc/sallayout.hxx
index a9a30d0..85c04f0 100644
--- a/vcl/inc/sallayout.hxx
+++ b/vcl/inc/sallayout.hxx
@@ -345,6 +345,7 @@ class VCL_PLUGIN_PUBLIC GenericSalLayout : public SalLayout
 public:
     // used by layout engines
     void            AppendGlyph( const GlyphItem& );
+    void            Reserve(int size) { m_GlyphItems.reserve(size + 1); }
     virtual void    AdjustLayout( ImplLayoutArgs& );
     virtual void    ApplyDXArray( ImplLayoutArgs& );
     virtual void    Justify( long nNewWidth );
diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx
index 3820d81..603104f 100644
--- a/vcl/source/gdi/pdfwriter_impl.cxx
+++ b/vcl/source/gdi/pdfwriter_impl.cxx
@@ -2364,6 +2364,7 @@ bool PDFSalLayout::LayoutText( ImplLayoutArgs& rArgs )
 
     Point aNewPos( 0, 0 );
     bool bRightToLeft;
+    Reserve(rArgs.mnLength);
     for( int nCharPos = -1; rArgs.GetNextPos( &nCharPos, &bRightToLeft ); )
     {
         // TODO: handle unicode surrogates
commit 6bb68cae7c31918eff8386d5b52be0759386bb60
Author: Norbert Thiebaud <nthiebaud at gmail.com>
Date:   Sun Mar 4 07:34:14 2012 -0600

    GenericSalLayout: manage the collection of GlyphItem with a vector.
    
    There was a TODO to replace a manually managed array of Glyphs
    to use std::list
    
    a GlyphItem is 36 bytes long. the colleciton of GlyphItems is
    mostly used in a sequential access. random insert/delete are fairly rare.
    using std::list would increase the size by at least 8 to 16 bytes per
    element (depending on the size of void*) (25 to 50% overhead)
    and would greatly degrade data locality for most iterations loops.
    so std::vector seems more appropriate here.

diff --git a/vcl/inc/sallayout.hxx b/vcl/inc/sallayout.hxx
index 51a6415..a9a30d0 100644
--- a/vcl/inc/sallayout.hxx
+++ b/vcl/inc/sallayout.hxx
@@ -374,9 +374,7 @@ protected:
     bool            GetCharWidths( sal_Int32* pCharWidths ) const;
 
 private:
-    GlyphItem*      mpGlyphItems;   // TODO: change to GlyphList
-    int             mnGlyphCount;
-    int             mnGlyphCapacity;
+    GlyphVector     m_GlyphItems;
     mutable Point   maBasePoint;
 
     // enforce proper copy semantic
diff --git a/vcl/source/gdi/sallayout.cxx b/vcl/source/gdi/sallayout.cxx
index 95118bf..3ca646d 100644
--- a/vcl/source/gdi/sallayout.cxx
+++ b/vcl/source/gdi/sallayout.cxx
@@ -797,37 +797,18 @@ const ImplFontData* SalLayout::GetFallbackFontData( sal_GlyphId /*nGlyphId*/ ) c
 // =======================================================================
 
 GenericSalLayout::GenericSalLayout()
-:   mpGlyphItems(0),
-    mnGlyphCount(0),
-    mnGlyphCapacity(0)
 {}
 
 // -----------------------------------------------------------------------
 
 GenericSalLayout::~GenericSalLayout()
-{
-    delete[] mpGlyphItems;
-}
+{}
 
 // -----------------------------------------------------------------------
 
 void GenericSalLayout::AppendGlyph( const GlyphItem& rGlyphItem )
 {
-    // TODO: use std::list<GlyphItem>
-    if( mnGlyphCount >= mnGlyphCapacity )
-    {
-        mnGlyphCapacity += 16 + 3 * mnGlyphCount;
-        GlyphItem* pNewGI = new GlyphItem[ mnGlyphCapacity ];
-        if( mpGlyphItems )
-        {
-            for( int i = 0; i < mnGlyphCount; ++i )
-                pNewGI[ i ] = mpGlyphItems[ i ];
-            delete[] mpGlyphItems;
-        }
-        mpGlyphItems = pNewGI;
-    }
-
-    mpGlyphItems[ mnGlyphCount++ ] = rGlyphItem;
+    m_GlyphItems.push_back(rGlyphItem);
 }
 
 // -----------------------------------------------------------------------
@@ -840,8 +821,7 @@ bool GenericSalLayout::GetCharWidths( sal_Int32* pCharWidths ) const
         pCharWidths[n] = 0;
 
     // determine cluster extents
-    const GlyphItem* const pEnd = mpGlyphItems + mnGlyphCount;
-    for( const GlyphItem* pG = mpGlyphItems; pG < pEnd; ++pG )
+    for( GlyphVector::const_iterator pG = m_GlyphItems.begin(), end = m_GlyphItems.end(); pG != end ; ++pG)
     {
         // use cluster start to get char index
         if( !pG->IsClusterStart() )
@@ -861,7 +841,7 @@ bool GenericSalLayout::GetCharWidths( sal_Int32* pCharWidths ) const
         // calculate right x-position for this glyph cluster
         // break if no more glyphs in layout
         // break at next glyph cluster start
-        while( (pG+1 < pEnd) && !pG[1].IsClusterStart() )
+        while( (pG+1 < end) && !pG[1].IsClusterStart() )
         {
             // advance to next glyph in cluster
             ++pG;
@@ -883,7 +863,7 @@ bool GenericSalLayout::GetCharWidths( sal_Int32* pCharWidths ) const
         // rightmost cluster edge is the leftmost edge of next cluster
         // for clusters that do not have x-sorted glyphs
         // TODO: avoid recalculation of left bound in next cluster iteration
-        for( const GlyphItem* pN = pG; ++pN < pEnd; )
+        for( GlyphVector::const_iterator pN = pG; ++pN < end; )
         {
             if( pN->IsClusterStart() )
                 break;
@@ -924,15 +904,14 @@ long GenericSalLayout::FillDXArray( sal_Int32* pCharWidths ) const
 // the text width is the maximum logical extent of all glyphs
 long GenericSalLayout::GetTextWidth() const
 {
-    if( mnGlyphCount <= 0 )
+    if( m_GlyphItems.empty() )
         return 0;
 
     // initialize the extent
     long nMinPos = 0;
     long nMaxPos = 0;
 
-    const GlyphItem* pG = mpGlyphItems;
-    for( int i = mnGlyphCount; --i >= 0; ++pG )
+    for( GlyphVector::const_iterator pG = m_GlyphItems.begin(), end = m_GlyphItems.end(); pG != end ; ++pG )
     {
         // update the text extent with the glyph extent
         long nXPos = pG->maLinearPos.X();
@@ -963,106 +942,106 @@ void GenericSalLayout::AdjustLayout( ImplLayoutArgs& rArgs )
 
 void GenericSalLayout::ApplyDXArray( ImplLayoutArgs& rArgs )
 {
-    if( mnGlyphCount <= 0 )
+    if( m_GlyphItems.empty())
         return;
 
     // determine cluster boundaries and x base offset
     const int nCharCount = rArgs.mnEndCharPos - rArgs.mnMinCharPos;
     int* pLogCluster = (int*)alloca( nCharCount * sizeof(int) );
-    int i, n;
+    size_t i;
+    int n,p;
     long nBasePointX = -1;
     if( mnLayoutFlags & SAL_LAYOUT_FOR_FALLBACK )
         nBasePointX = 0;
-    for( i = 0; i < nCharCount; ++i )
-        pLogCluster[ i ] = -1;
-    GlyphItem* pG = mpGlyphItems;
-    for( i = 0; i < mnGlyphCount; ++i, ++pG )
+    for(p = 0; p < nCharCount; ++p )
+        pLogCluster[ p ] = -1;
+
+    for( i = 0; i < m_GlyphItems.size(); ++i)
     {
-        n = pG->mnCharPos - rArgs.mnMinCharPos;
+        n = m_GlyphItems[i].mnCharPos - rArgs.mnMinCharPos;
         if( (n < 0) || (nCharCount <= n) )
             continue;
         if( pLogCluster[ n ] < 0 )
             pLogCluster[ n ] = i;
         if( nBasePointX < 0 )
-            nBasePointX = pG->maLinearPos.X();
+            nBasePointX = m_GlyphItems[i].maLinearPos.X();
     }
     // retarget unresolved pLogCluster[n] to a glyph inside the cluster
     // TODO: better do it while the deleted-glyph markers are still there
     for( n = 0; n < nCharCount; ++n )
-        if( (i = pLogCluster[0]) >= 0 )
+        if( (p = pLogCluster[0]) >= 0 )
             break;
     if( n >= nCharCount )
         return;
     for( n = 0; n < nCharCount; ++n )
     {
         if( pLogCluster[ n ] < 0 )
-            pLogCluster[ n ] = i;
+            pLogCluster[ n ] = p;
         else
-            i = pLogCluster[ n ];
+            p = pLogCluster[ n ];
     }
 
     // calculate adjusted cluster widths
-    sal_Int32* pNewGlyphWidths = (sal_Int32*)alloca( mnGlyphCount * sizeof(long) );
-    for( i = 0; i < mnGlyphCount; ++i )
+    sal_Int32* pNewGlyphWidths = (sal_Int32*)alloca( m_GlyphItems.size() * sizeof(long) );
+    for( i = 0; i < m_GlyphItems.size(); ++i )
         pNewGlyphWidths[ i ] = 0;
 
     bool bRTL;
-    for( int nCharPos = i = -1; rArgs.GetNextPos( &nCharPos, &bRTL ); )
+    for( int nCharPos = p = -1; rArgs.GetNextPos( &nCharPos, &bRTL ); )
     {
         n = nCharPos - rArgs.mnMinCharPos;
         if( (n < 0) || (nCharCount <= n) )  continue;
 
         if( pLogCluster[ n ] >= 0 )
-            i = pLogCluster[ n ];
-        if( i >= 0 )
+            p = pLogCluster[ n ];
+        if( p >= 0 )
         {
             long nDelta = rArgs.mpDXArray[ n ] ;
             if( n > 0 )
                 nDelta -= rArgs.mpDXArray[ n-1 ];
-            pNewGlyphWidths[ i ] += nDelta * mnUnitsPerPixel;
+            pNewGlyphWidths[ p ] += nDelta * mnUnitsPerPixel;
         }
     }
 
     // move cluster positions using the adjusted widths
     long nDelta = 0;
     long nNewPos = 0;
-    pG = mpGlyphItems;
-    for( i = 0; i < mnGlyphCount; ++i, ++pG )
+    for( i = 0; i < m_GlyphItems.size(); ++i)
     {
-        if( pG->IsClusterStart() )
+        if( m_GlyphItems[i].IsClusterStart() )
         {
             // calculate original and adjusted cluster width
-            int nOldClusterWidth = pG->mnNewWidth;
+            int nOldClusterWidth = m_GlyphItems[i].mnNewWidth;
             int nNewClusterWidth = pNewGlyphWidths[i];
-            GlyphItem* pClusterG = pG + 1;
-            for( int j = i; ++j < mnGlyphCount; ++pClusterG )
+            size_t j;
+            for( j = i; ++j < m_GlyphItems.size(); )
             {
-                if( pClusterG->IsClusterStart() )
+                if( m_GlyphItems[j].IsClusterStart() )
                     break;
-                if( !pClusterG->IsDiacritic() ) // #i99367# ignore diacritics
-                    nOldClusterWidth += pClusterG->mnNewWidth;
+                if( !m_GlyphItems[j].IsDiacritic() ) // #i99367# ignore diacritics
+                    nOldClusterWidth += m_GlyphItems[j].mnNewWidth;
                 nNewClusterWidth += pNewGlyphWidths[j];
             }
             const int nDiff = nNewClusterWidth - nOldClusterWidth;
 
             // adjust cluster glyph widths and positions
-            nDelta = nBasePointX + (nNewPos - pG->maLinearPos.X());
-            if( !pG->IsRTLGlyph() )
+            nDelta = nBasePointX + (nNewPos - m_GlyphItems[i].maLinearPos.X());
+            if( !m_GlyphItems[i].IsRTLGlyph() )
             {
                 // for LTR case extend rightmost glyph in cluster
-                pClusterG[-1].mnNewWidth += nDiff;
+                m_GlyphItems[j - 1].mnNewWidth += nDiff;
             }
             else
             {
                 // right align cluster in new space for RTL case
-                pG->mnNewWidth += nDiff;
+                m_GlyphItems[i].mnNewWidth += nDiff;
                 nDelta += nDiff;
             }
 
             nNewPos += nNewClusterWidth;
         }
 
-        pG->maLinearPos.X() += nDelta;
+        m_GlyphItems[i].maLinearPos.X() += nDelta;
     }
 }
 
@@ -1075,14 +1054,18 @@ void GenericSalLayout::Justify( long nNewWidth )
     if( !nOldWidth || nNewWidth==nOldWidth )
         return;
 
+    if(m_GlyphItems.empty())
+    {
+        return;
+    }
     // find rightmost glyph, it won't get stretched
-    GlyphItem* pGRight = mpGlyphItems + mnGlyphCount - 1;
-
+    GlyphVector::iterator pGRight = m_GlyphItems.begin();
+    pGRight += m_GlyphItems.size() - 1;
+    GlyphVector::iterator pG;
     // count stretchable glyphs
-    GlyphItem* pG;
     int nStretchable = 0;
     int nMaxGlyphWidth = 0;
-    for( pG = mpGlyphItems; pG < pGRight; ++pG )
+    for(pG = m_GlyphItems.begin(); pG != pGRight; ++pG)
     {
         if( !pG->IsDiacritic() )
             ++nStretchable;
@@ -1105,7 +1088,7 @@ void GenericSalLayout::Justify( long nNewWidth )
     {
         // expand width by distributing space between glyphs evenly
         int nDeltaSum = 0;
-        for( pG = mpGlyphItems; pG < pGRight; ++pG )
+        for( pG = m_GlyphItems.begin(); pG != pGRight; ++pG )
         {
             // move glyph to justified position
             pG->maLinearPos.X() += nDeltaSum;
@@ -1125,14 +1108,17 @@ void GenericSalLayout::Justify( long nNewWidth )
     {
         // squeeze width by moving glyphs proportionally
         double fSqueeze = (double)nNewWidth / nOldWidth;
-        for( pG = mpGlyphItems; ++pG < pGRight;)
+        if(m_GlyphItems.size() > 1)
         {
-            int nX = pG->maLinearPos.X() - maBasePoint.X();
-            nX = (int)(nX * fSqueeze);
-            pG->maLinearPos.X() = nX + maBasePoint.X();
+            for( pG = m_GlyphItems.begin(); ++pG != pGRight;)
+            {
+                int nX = pG->maLinearPos.X() - maBasePoint.X();
+                nX = (int)(nX * fSqueeze);
+                pG->maLinearPos.X() = nX + maBasePoint.X();
+            }
         }
         // adjust glyph widths to new positions
-        for( pG = mpGlyphItems; pG < pGRight; ++pG )
+        for( pG = m_GlyphItems.begin(); pG != pGRight; ++pG )
             pG->mnNewWidth = pG[1].maLinearPos.X() - pG[0].maLinearPos.X();
     }
 }
@@ -1143,8 +1129,7 @@ void GenericSalLayout::ApplyAsianKerning( const sal_Unicode* pStr, int nLength )
 {
     long nOffset = 0;
 
-    GlyphItem* pGEnd = mpGlyphItems + mnGlyphCount;
-    for( GlyphItem* pG = mpGlyphItems; pG < pGEnd; ++pG )
+    for( GlyphVector::iterator pG = m_GlyphItems.begin(), pGEnd = m_GlyphItems.end(); pG != pGEnd; ++pG )
     {
         const int n = pG->mnCharPos;
         if( n < nLength - 1)
@@ -1191,83 +1176,42 @@ void GenericSalLayout::KashidaJustify( long nKashidaIndex, int nKashidaWidth )
         return;
 
     // calculate max number of needed kashidas
-    const GlyphItem* pG1 = mpGlyphItems;
-    int nKashidaCount = 0, i;
-    for( i = 0; i < mnGlyphCount; ++i, ++pG1 )
+    int nKashidaCount = 0;
+    for( GlyphVector::iterator pG = m_GlyphItems.begin(), pGEnd = m_GlyphItems.end(); pG != pGEnd; ++pG )
     {
         // only inject kashidas in RTL contexts
-        if( !pG1->IsRTLGlyph() )
+        if( !pG->IsRTLGlyph() )
             continue;
         // no kashida-injection for blank justified expansion either
-        if( IsSpacingGlyph( pG1->mnGlyphIndex ) )
+        if( IsSpacingGlyph( pG->mnGlyphIndex ) )
             continue;
 
         // calculate gap, ignore if too small
-        const int nGapWidth = pG1->mnNewWidth - pG1->mnOrigWidth;
+        int nGapWidth = pG->mnNewWidth - pG->mnOrigWidth;
         // worst case is one kashida even for mini-gaps
-        if( 3 * nGapWidth >= nKashidaWidth )
-            nKashidaCount += 1 + (nGapWidth / nKashidaWidth);
-    }
-
-    if( !nKashidaCount )
-        return;
-
-    // reallocate glyph array for additional kashidas
-    // TODO: reuse array if additional glyphs would fit
-    mnGlyphCapacity = mnGlyphCount + nKashidaCount;
-    GlyphItem* pNewGlyphItems = new GlyphItem[ mnGlyphCapacity ];
-    GlyphItem* pG2 = pNewGlyphItems;
-    pG1 = mpGlyphItems;
-    for( i = mnGlyphCount; --i >= 0; ++pG1, ++pG2 )
-    {
-        // default action is to copy array element
-        *pG2 = *pG1;
-
-        // only inject kashida in RTL contexts
-        if( !pG1->IsRTLGlyph() )
-            continue;
-        // no kashida-injection for blank justified expansion either
-        if( IsSpacingGlyph( pG1->mnGlyphIndex ) )
+        if( 3 * nGapWidth < nKashidaWidth )
             continue;
 
-        // calculate gap, skip if too small
-        int nGapWidth = pG1->mnNewWidth - pG1->mnOrigWidth;
-        if( 3*nGapWidth < nKashidaWidth )
-            continue;
-
-        // fill gap with kashidas
         nKashidaCount = 0;
-        Point aPos = pG1->maLinearPos;
+        Point aPos = pG->maLinearPos;
         aPos.X() -= nGapWidth; // cluster is already right aligned
-        for(; nGapWidth > 0; nGapWidth -= nKashidaWidth, ++nKashidaCount )
+        GlyphVector::iterator pG2 = pG;
+        for(; nGapWidth > nKashidaWidth; nGapWidth -= nKashidaWidth, ++nKashidaCount )
         {
-            *(pG2++) = GlyphItem( pG1->mnCharPos, nKashidaIndex, aPos,
-                GlyphItem::IS_IN_CLUSTER|GlyphItem::IS_RTL_GLYPH, nKashidaWidth );
+            pG2 = m_GlyphItems.insert(pG2, GlyphItem( pG->mnCharPos, nKashidaIndex, aPos,
+                                                      GlyphItem::IS_IN_CLUSTER|GlyphItem::IS_RTL_GLYPH, nKashidaWidth ));
             aPos.X() += nKashidaWidth;
         }
 
         // fixup rightmost kashida for gap remainder
-        if( nGapWidth < 0 )
+        if( nGapWidth > 0 )
         {
+            pG2 = m_GlyphItems.insert(pG2, GlyphItem( pG->mnCharPos, nKashidaIndex, aPos,
+                                                      GlyphItem::IS_IN_CLUSTER|GlyphItem::IS_RTL_GLYPH, nKashidaCount ? nGapWidth : nGapWidth/2 ));
             aPos.X() += nGapWidth;
-            if( nKashidaCount <= 1 )
-                nGapWidth /= 2;               // for small gap move kashida to middle
-            pG2[-1].mnNewWidth += nGapWidth;  // adjust kashida width to gap width
-            pG2[-1].maLinearPos.X() += nGapWidth;
         }
-
-        // when kashidas were inserted move the original cluster
-        // to the right and shrink it to it's original width
-        *pG2 = *pG1;
-        pG2->maLinearPos.X() = aPos.X();
-        pG2->mnNewWidth = pG2->mnOrigWidth;
-     }
-
-    // use the new glyph array
-    DBG_ASSERT( mnGlyphCapacity >= pG2-pNewGlyphItems, "KashidaJustify overflow" );
-    delete[] mpGlyphItems;
-    mpGlyphItems = pNewGlyphItems;
-    mnGlyphCount = pG2 - pNewGlyphItems;
+        pG = pG2;
+    }
 }
 
 // -----------------------------------------------------------------------
@@ -1281,8 +1225,7 @@ void GenericSalLayout::GetCaretPositions( int nMaxIndex, sal_Int32* pCaretXArray
         pCaretXArray[ i ] = nXPos;
 
     // calculate caret positions using glyph array
-    const GlyphItem* pG = mpGlyphItems;
-    for( i = mnGlyphCount; --i >= 0; ++pG )
+    for( GlyphVector::const_iterator pG = m_GlyphItems.begin(), pGEnd = m_GlyphItems.end(); pG != pGEnd; ++pG )
     {
         nXPos = pG->maLinearPos.X();
         long nXRight = nXPos + pG->mnOrigWidth;
@@ -1329,10 +1272,12 @@ int GenericSalLayout::GetTextBreak( long nMaxWidth, long nCharExtra, int nFactor
 int GenericSalLayout::GetNextGlyphs( int nLen, sal_GlyphId* pGlyphs, Point& rPos,
     int& nStart, sal_Int32* pGlyphAdvAry, int* pCharPosAry ) const
 {
-    const GlyphItem* pG = mpGlyphItems + nStart;
+    GlyphVector::const_iterator pG = m_GlyphItems.begin();
+    GlyphVector::const_iterator pGEnd = m_GlyphItems.end();
+    pG += nStart;
 
     // find next glyph in substring
-    for(; nStart < mnGlyphCount; ++nStart, ++pG )
+    for(; pG != pGEnd; ++nStart, ++pG )
     {
         int n = pG->mnCharPos;
         if( (mnMinCharPos <= n) && (n < mnEndCharPos) )
@@ -1340,7 +1285,7 @@ int GenericSalLayout::GetNextGlyphs( int nLen, sal_GlyphId* pGlyphs, Point& rPos
     }
 
     // return zero if no more glyph found
-    if( nStart >= mnGlyphCount )
+    if( nStart >= (int)m_GlyphItems.size() )
         return 0;
 
     // calculate absolute position in pixel units
@@ -1361,7 +1306,7 @@ int GenericSalLayout::GetNextGlyphs( int nLen, sal_GlyphId* pGlyphs, Point& rPos
             *pGlyphAdvAry = pG->mnNewWidth;
 
         // break at end of glyph list
-        if( ++nStart >= mnGlyphCount )
+        if( ++nStart >= (int)m_GlyphItems.size() )
             break;
         // break when enough glyphs
         if( nCount >= nLen )
@@ -1410,10 +1355,12 @@ int GenericSalLayout::GetNextGlyphs( int nLen, sal_GlyphId* pGlyphs, Point& rPos
 
 void GenericSalLayout::MoveGlyph( int nStart, long nNewXPos )
 {
-    if( nStart >= mnGlyphCount )
+    if( nStart >= (int)m_GlyphItems.size() )
         return;
 
-    GlyphItem* pG = mpGlyphItems + nStart;
+    GlyphVector::iterator pG = m_GlyphItems.begin();
+    pG += nStart;
+
     // the nNewXPos argument determines the new cell position
     // as RTL-glyphs are right justified in their cell
     // the cell position needs to be adjusted to the glyph position
@@ -1424,9 +1371,10 @@ void GenericSalLayout::MoveGlyph( int nStart, long nNewXPos )
     // adjust all following glyph positions if needed
     if( nXDelta != 0 )
     {
-        GlyphItem* const pGEnd = mpGlyphItems + mnGlyphCount;
-        for(; pG < pGEnd; ++pG )
+        for( GlyphVector::iterator pGEnd = m_GlyphItems.end(); pG != pGEnd; ++pG )
+        {
             pG->maLinearPos.X() += nXDelta;
+        }
     }
 }
 
@@ -1434,9 +1382,11 @@ void GenericSalLayout::MoveGlyph( int nStart, long nNewXPos )
 
 void GenericSalLayout::DropGlyph( int nStart )
 {
-    if( nStart >= mnGlyphCount )
+    if( nStart >= (int)m_GlyphItems.size())
         return;
-    GlyphItem* pG = mpGlyphItems + nStart;
+
+    GlyphVector::iterator pG = m_GlyphItems.begin();
+    pG += nStart;
     pG->mnGlyphIndex = GF_DROPPED;
     pG->mnCharPos = -1;
 }
@@ -1448,18 +1398,19 @@ void GenericSalLayout::Simplify( bool bIsBase )
     const sal_GlyphId nDropMarker = bIsBase ? GF_DROPPED : 0;
 
     // remove dropped glyphs inplace
-    GlyphItem* pGDst = mpGlyphItems;
-    const GlyphItem* pGSrc = mpGlyphItems;
-    const GlyphItem* pGEnd = mpGlyphItems + mnGlyphCount;
-    for(; pGSrc < pGEnd; ++pGSrc )
+    size_t j = 0;
+    for(size_t i = 0; i < m_GlyphItems.size(); i++ )
     {
-        if( pGSrc->mnGlyphIndex == nDropMarker )
+        if( m_GlyphItems[i].mnGlyphIndex == nDropMarker )
             continue;
-        if( pGDst != pGSrc )
-            *pGDst = *pGSrc;
-        ++pGDst;
+
+        if( i != j )
+        {
+            m_GlyphItems[j] = m_GlyphItems[i];
+        }
+        j += 1;
     }
-    mnGlyphCount = pGDst - mpGlyphItems;
+    m_GlyphItems.erase(m_GlyphItems.begin() + j, m_GlyphItems.end());
 }
 
 // -----------------------------------------------------------------------
@@ -1469,27 +1420,25 @@ void GenericSalLayout::SortGlyphItems()
 {
     // move cluster components behind their cluster start (especially for RTL)
     // using insertion sort because the glyph items are "almost sorted"
-    const GlyphItem* const pGEnd = mpGlyphItems + mnGlyphCount;
-    for( GlyphItem* pG = mpGlyphItems; pG < pGEnd; ++pG )
+
+    for( GlyphVector::iterator pG = m_GlyphItems.begin(), pGEnd = m_GlyphItems.end(); pG != pGEnd; ++pG )
     {
         // find a cluster starting with a diacritic
         if( !pG->IsDiacritic() )
             continue;
         if( !pG->IsClusterStart() )
             continue;
-        for( GlyphItem* pBaseGlyph = pG; ++pBaseGlyph < pGEnd; )
+        for( GlyphVector::iterator pBaseGlyph = pG; ++pBaseGlyph != pGEnd; )
         {
             // find the base glyph matching to the misplaced diacritic
-               if( pBaseGlyph->IsClusterStart() )
-                   break;
-               if( pBaseGlyph->IsDiacritic() )
-                   continue;
+            if( pBaseGlyph->IsClusterStart() )
+                break;
+            if( pBaseGlyph->IsDiacritic() )
+                continue;
 
             // found the matching base glyph
             // => this base glyph becomes the new cluster start
-            const GlyphItem aDiacritic = *pG;
-            *pG = *pBaseGlyph;
-            *pBaseGlyph = aDiacritic;
+            iter_swap(pG, pBaseGlyph);
 
             // update glyph flags of swapped glyphitems
             pG->mnFlags &= ~GlyphItem::IS_IN_CLUSTER;
commit 43f3b1fb5bca9909a6ca2102b80dc3291e038f2f
Author: Norbert Thiebaud <nthiebaud at gmail.com>
Date:   Sun Mar 4 07:20:12 2012 -0600

    build internal cairo if not with_system_cairo but enable_librsvg != NO

diff --git a/configure.in b/configure.in
index 3df3a8f..f0ac6a0 100644
--- a/configure.in
+++ b/configure.in
@@ -9866,9 +9866,15 @@ else
         if test "$ENABLE_LIBRSVG" != NO -o -z "$ENABLE_DIRECTX"; then
             BUILD_TYPE="$BUILD_TYPE CAIRO"
         fi
-    else 
+    else
         if test "$enable_cairo_canvas" = "yes"; then
             BUILD_TYPE="$BUILD_TYPE CAIRO"
+        else
+            if test "$with_system_cairo" != "yes" ; then
+                if test "$ENABLE_LIBRSVG" != NO ; then
+                    BUILD_TYPE="$BUILD_TYPE CAIRO"
+                fi
+            fi
         fi
     fi
 fi


More information about the Libreoffice-commits mailing list