diff --git a/src/gui/text/qtextengine.cpp b/src/gui/text/qtextengine.cpp index 3b50376504..f569c6e795 100644 --- a/src/gui/text/qtextengine.cpp +++ b/src/gui/text/qtextengine.cpp @@ -2058,6 +2058,9 @@ QFontEngine *QTextEngine::fontEngine(const QScriptItem &si, QFixed *ascent, QFix font = font.resolve(fnt); } engine = font.d->engineForScript(script); + if (engine) + engine->ref.ref(); + QTextCharFormat::VerticalAlignment valign = f.verticalAlignment(); if (valign == QTextCharFormat::AlignSuperScript || valign == QTextCharFormat::AlignSubScript) { if (font.pointSize() != -1) @@ -2065,16 +2068,14 @@ QFontEngine *QTextEngine::fontEngine(const QScriptItem &si, QFixed *ascent, QFix else font.setPixelSize((font.pixelSize() * 2) / 3); scaledEngine = font.d->engineForScript(script); + if (scaledEngine) + scaledEngine->ref.ref(); } - if (engine) - engine->ref.ref(); if (feCache.prevFontEngine) releaseCachedFontEngine(feCache.prevFontEngine); feCache.prevFontEngine = engine; - if (scaledEngine) - scaledEngine->ref.ref(); if (feCache.prevScaledFontEngine) releaseCachedFontEngine(feCache.prevScaledFontEngine); feCache.prevScaledFontEngine = scaledEngine; diff --git a/tests/auto/gui/text/qtextlayout/tst_qtextlayout.cpp b/tests/auto/gui/text/qtextlayout/tst_qtextlayout.cpp index e778232461..84d58191c0 100644 --- a/tests/auto/gui/text/qtextlayout/tst_qtextlayout.cpp +++ b/tests/auto/gui/text/qtextlayout/tst_qtextlayout.cpp @@ -143,6 +143,7 @@ private slots: void cursorInNonStopChars(); void nbsp(); void noModificationOfInputString(); + void superscriptCrash_qtbug53911(); private: QFont testFont; @@ -2209,5 +2210,61 @@ void tst_QTextLayout::noModificationOfInputString() } } +void tst_QTextLayout::superscriptCrash_qtbug53911() +{ + static int fontSizes = 64; + static QString layoutText = "THIS IS SOME EXAMPLE TEXT THIS IS SOME EXAMPLE TEXT"; + + QList textLayouts; + for (int i = 0; i < fontSizes; ++i) { + for (int j = 0; j < 4; ++j) { + QTextLayout* newTextLayout = new QTextLayout(); + newTextLayout->setText(layoutText); + QList formatRanges; + QTextLayout::FormatRange formatRange; + + formatRange.format.setFont(QFont()); + formatRange.format.setFontPointSize(i + 5); + + switch (j) { + case 0: + formatRange.format.setFontWeight(QFont::Normal); + formatRange.format.setFontItalic(false); + break; + case 1: + formatRange.format.setFontWeight(QFont::Bold); + formatRange.format.setFontItalic(false); + break; + case 2: + formatRange.format.setFontWeight(QFont::Bold); + formatRange.format.setFontItalic(true); + break; + case 3: + formatRange.format.setFontWeight(QFont::Normal); + formatRange.format.setFontItalic(true); + break; + } + + formatRange.format.setVerticalAlignment( QTextCharFormat::AlignSuperScript); + + formatRange.start = 0; + formatRange.length = layoutText.size(); + formatRanges << formatRange; + newTextLayout->setAdditionalFormats(formatRanges); + + textLayouts.push_front(newTextLayout); + } + } + + // This loop would crash before fix for QTBUG-53911 + foreach (QTextLayout *textLayout, textLayouts) { + textLayout->beginLayout(); + while (textLayout->createLine().isValid()); + textLayout->endLayout(); + } + + qDeleteAll(textLayouts); +} + QTEST_MAIN(tst_QTextLayout) #include "tst_qtextlayout.moc"