Ignore:
Timestamp:
Aug 2, 2010, 9:27:30 PM (15 years ago)
Author:
Dmitry A. Kuminov
Message:

trunk: Merged in qt 4.6.3 sources from branches/vendor/nokia/qt.

Location:
trunk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk

  • trunk/src/gui/text/qtextlayout.cpp

    r651 r769  
    9090            align = Qt::AlignRight;
    9191        if (align & Qt::AlignRight)
    92             x = line.width - (line.textWidth + leadingSpaceWidth(eng, line));
     92            x = line.width - (line.textAdvance + leadingSpaceWidth(eng, line));
    9393        else if (align & Qt::AlignHCenter)
    94             x = (line.width - line.textWidth)/2;
     94            x = (line.width - line.textAdvance)/2;
    9595    }
    9696    return x;
     
    13321332    const QScriptLine &sl = d->lines[line];
    13331333
    1334     const qreal x = position.x() + l.cursorToX(cursorPosition);
     1334    qreal x = position.x() + l.cursorToX(cursorPosition);
    13351335
    13361336    int itm = d->findItem(cursorPosition - 1);
     
    13511351    if (toggleAntialiasing)
    13521352        p->setRenderHint(QPainter::Antialiasing);
     1353#if defined(QT_MAC_USE_COCOA)
     1354    // Always draw the cursor aligned to pixel boundary.
     1355    x = qRound(x);
     1356#endif
    13531357    p->fillRect(QRectF(x, y, qreal(width), (base + descent + 1).toReal()), p->pen().brush());
    13541358    if (toggleAntialiasing)
     
    16411645    struct LineBreakHelper
    16421646    {
    1643         LineBreakHelper() : glyphCount(0), maxGlyphs(0), manualWrap(false) {}
     1647        LineBreakHelper()
     1648            : glyphCount(0), maxGlyphs(0), currentPosition(0), fontEngine(0), logClusters(0),
     1649              manualWrap(false)
     1650        {
     1651        }
     1652
    16441653
    16451654        QScriptLine tmpData;
    16461655        QScriptLine spaceData;
    16471656
     1657        QGlyphLayout glyphs;
     1658
    16481659        int glyphCount;
    16491660        int maxGlyphs;
     1661        int currentPosition;
    16501662
    16511663        QFixed minw;
    16521664        QFixed softHyphenWidth;
    16531665        QFixed rightBearing;
     1666        QFixed minimumRightBearing;
     1667
     1668        QFontEngine *fontEngine;
     1669        const unsigned short *logClusters;
    16541670
    16551671        bool manualWrap;
    16561672
    16571673        bool checkFullOtherwiseExtend(QScriptLine &line);
     1674
     1675        QFixed calculateNewWidth(const QScriptLine &line) const {
     1676            return line.textWidth + tmpData.textWidth + spaceData.textWidth + softHyphenWidth
     1677                    - qMin(rightBearing, QFixed());
     1678        }
     1679
     1680        inline glyph_t currentGlyph() const
     1681        {
     1682            Q_ASSERT(currentPosition > 0);
     1683            return glyphs.glyphs[logClusters[currentPosition - 1]];
     1684        }
     1685
     1686        inline void adjustRightBearing()
     1687        {
     1688            if (currentPosition <= 0)
     1689                return;
     1690
     1691            qreal rb;
     1692            fontEngine->getGlyphBearings(currentGlyph(), 0, &rb);
     1693            rightBearing = qMin(QFixed(), QFixed::fromReal(rb));
     1694        }
     1695
     1696        inline void resetRightBearing()
     1697        {
     1698            rightBearing = QFixed(1); // Any positive number is defined as invalid since only
     1699                                      // negative right bearings are interesting to us.
     1700        }
    16581701    };
    16591702
     
    16621705    LB_DEBUG("possible break width %f, spacew=%f", tmpData.textWidth.toReal(), spaceData.textWidth.toReal());
    16631706
    1664     QFixed newWidth = line.textWidth + tmpData.textWidth + spaceData.textWidth + softHyphenWidth + rightBearing;
     1707    QFixed newWidth = calculateNewWidth(line);
    16651708    if (line.length && !manualWrap && (newWidth > line.width || glyphCount > maxGlyphs))
    16661709        return true;
     
    17381781
    17391782    const HB_CharAttributes *attributes = eng->attributes();
    1740     int pos = line.from;
     1783    lbh.currentPosition = line.from;
    17411784    int end = 0;
    1742     QGlyphLayout glyphs;
    1743     const unsigned short *logClusters = eng->layoutData->logClustersPtr;
     1785    lbh.logClusters = eng->layoutData->logClustersPtr;
    17441786
    17451787    while (newItem < eng->layoutData->items.size()) {
    1746         lbh.rightBearing = 0;
     1788        lbh.resetRightBearing();
    17471789        lbh.softHyphenWidth = 0;
    17481790        if (newItem != item) {
     
    17521794                eng->shape(item);
    17531795                attributes = eng->attributes();
    1754                 logClusters = eng->layoutData->logClustersPtr;
     1796                lbh.logClusters = eng->layoutData->logClustersPtr;
    17551797            }
    1756             pos = qMax(line.from, current.position);
     1798            lbh.currentPosition = qMax(line.from, current.position);
    17571799            end = current.position + eng->length(item);
    1758             glyphs = eng->shapedGlyphs(&current);
     1800            lbh.glyphs = eng->shapedGlyphs(&current);
    17591801        }
    17601802        const QScriptItem &current = eng->layoutData->items[item];
     1803        QFontEngine *fontEngine = eng->fontEngine(current);
     1804        if (lbh.fontEngine != fontEngine) {
     1805            lbh.fontEngine = fontEngine;
     1806            lbh.minimumRightBearing = qMin(QFixed(),
     1807                                           QFixed::fromReal(fontEngine->minRightBearing()));
     1808        }
    17611809
    17621810        lbh.tmpData.leading = qMax(lbh.tmpData.leading + lbh.tmpData.ascent,
     
    17881836                line.setDefaultHeight(eng);
    17891837            if (eng->option.flags() & QTextOption::ShowLineAndParagraphSeparators) {
    1790                 addNextCluster(pos, end, lbh.tmpData, lbh.glyphCount,
    1791                                current, logClusters, glyphs);
     1838                addNextCluster(lbh.currentPosition, end, lbh.tmpData, lbh.glyphCount,
     1839                               current, lbh.logClusters, lbh.glyphs);
    17921840            } else {
    17931841                lbh.tmpData.length++;
     
    18081856            if (lbh.checkFullOtherwiseExtend(line))
    18091857                goto found;
    1810         } else if (attributes[pos].whiteSpace) {
    1811             while (pos < end && attributes[pos].whiteSpace)
    1812                 addNextCluster(pos, end, lbh.spaceData, lbh.glyphCount,
    1813                                current, logClusters, glyphs);
     1858        } else if (attributes[lbh.currentPosition].whiteSpace) {
     1859            while (lbh.currentPosition < end && attributes[lbh.currentPosition].whiteSpace)
     1860                addNextCluster(lbh.currentPosition, end, lbh.spaceData, lbh.glyphCount,
     1861                               current, lbh.logClusters, lbh.glyphs);
    18141862
    18151863            if (!lbh.manualWrap && lbh.spaceData.textWidth > line.width) {
     
    18201868            bool sb_or_ws = false;
    18211869            do {
    1822                 addNextCluster(pos, end, lbh.tmpData, lbh.glyphCount,
    1823                                current, logClusters, glyphs);
    1824 
    1825                 if (attributes[pos].whiteSpace || attributes[pos-1].lineBreakType != HB_NoBreak) {
     1870                addNextCluster(lbh.currentPosition, end, lbh.tmpData, lbh.glyphCount,
     1871                               current, lbh.logClusters, lbh.glyphs);
     1872
     1873                if (attributes[lbh.currentPosition].whiteSpace || attributes[lbh.currentPosition-1].lineBreakType != HB_NoBreak) {
    18261874                    sb_or_ws = true;
    18271875                    break;
    1828                 } else if (breakany && attributes[pos].charStop) {
     1876                } else if (breakany && attributes[lbh.currentPosition].charStop) {
    18291877                    break;
    18301878                }
    1831             } while (pos < end);
     1879            } while (lbh.currentPosition < end);
    18321880            lbh.minw = qMax(lbh.tmpData.textWidth, lbh.minw);
    18331881
    1834             if (pos && attributes[pos - 1].lineBreakType == HB_SoftHyphen) {
     1882            if (lbh.currentPosition && attributes[lbh.currentPosition - 1].lineBreakType == HB_SoftHyphen) {
    18351883                // if we are splitting up a word because of
    18361884                // a soft hyphen then we ...
     
    18501898                //
    18511899                if (line.length)
    1852                     lbh.softHyphenWidth = glyphs.advances_x[logClusters[pos - 1]];
     1900                    lbh.softHyphenWidth = lbh.glyphs.advances_x[lbh.logClusters[lbh.currentPosition - 1]];
    18531901                else if (breakany)
    1854                     lbh.tmpData.textWidth += glyphs.advances_x[logClusters[pos - 1]];
     1902                    lbh.tmpData.textWidth += lbh.glyphs.advances_x[lbh.logClusters[lbh.currentPosition - 1]];
    18551903            }
    18561904
     
    18591907            // of the advance of the glyph, the bearing will be negative. We flip the sign
    18601908            // for the code to be more readable. Logic borrowed from qfontmetrics.cpp.
    1861             if (pos) {
    1862                 QFontEngine *fontEngine = eng->fontEngine(current);
    1863                 glyph_t glyph = glyphs.glyphs[logClusters[pos - 1]];
    1864                 glyph_metrics_t gi = fontEngine->boundingBox(glyph);
    1865                 if (gi.isValid())
    1866                     lbh.rightBearing = qMax(QFixed(), -(gi.xoff - gi.x - gi.width));
     1909            // We ignore the right bearing if the minimum negative bearing is too little to
     1910            // expand the text beyond the edge.
     1911            if (sb_or_ws|breakany) {
     1912                if (lbh.calculateNewWidth(line) + lbh.minimumRightBearing > line.width)
     1913                    lbh.adjustRightBearing();
     1914                if (lbh.checkFullOtherwiseExtend(line)) {
     1915                    if (!breakany) {
     1916                        line.textWidth += lbh.softHyphenWidth;
     1917                    }
     1918
     1919                    goto found;
     1920                }
    18671921            }
    1868 
    1869             if ((sb_or_ws|breakany) && lbh.checkFullOtherwiseExtend(line)) {
    1870                 if (!breakany) {
    1871                     line.textWidth += lbh.softHyphenWidth;
    1872                 }
    1873 
    1874                 line.textWidth += lbh.rightBearing;
    1875 
    1876                 goto found;
    1877             }
    1878         }
    1879         if (pos == end)
     1922        }
     1923        if (lbh.currentPosition == end)
    18801924            newItem = item + 1;
    18811925    }
    18821926    LB_DEBUG("reached end of line");
    18831927    lbh.checkFullOtherwiseExtend(line);
    1884     line.textWidth += lbh.rightBearing;
    1885 
    18861928found:       
     1929    if (lbh.rightBearing > 0) // If right bearing has not yet been adjusted
     1930        lbh.adjustRightBearing();
     1931    line.textAdvance = line.textWidth;
     1932    line.textWidth -= qMin(QFixed(), lbh.rightBearing);
     1933
    18871934    if (line.length == 0) {
    18881935        LB_DEBUG("no break available in line, adding temp: length %d, width %f, space: length %d, width %f",
Note: See TracChangeset for help on using the changeset viewer.