From 1cc58fdf174656a52603af00cb40478066c5abd4 Mon Sep 17 00:00:00 2001 From: Eskil Abrahamsen Blomfeldt Date: Wed, 1 Jun 2011 09:45:55 +0200 Subject: Make QSGTextNode back-end for QML's TextInput and TextEdit Use the general QSGTextNode class as back-end for all text elements in QML to make all text elements look the same and use the same text rasterization back-end. This requires a few rewrites in the text node to support e.g. selections. Crashes seen with threaded renderer in TextEdit and TextInput on Mac are also fixed by this. Reviewed-by: Jiang Jiang Task-number: QTBUG-18019, QTBUG-20017 Change-Id: I4207faf180c83422e5f8b726741321af395bd724 Reviewed-on: http://codereview.qt.nokia.com/2865 Reviewed-by: Eskil Abrahamsen Blomfeldt --- .../declarative/qsgtextinput/tst_qsgtextinput.cpp | 99 ++++++++++++++++++++-- 1 file changed, 93 insertions(+), 6 deletions(-) (limited to 'tests/auto/declarative/qsgtextinput/tst_qsgtextinput.cpp') diff --git a/tests/auto/declarative/qsgtextinput/tst_qsgtextinput.cpp b/tests/auto/declarative/qsgtextinput/tst_qsgtextinput.cpp index 93e8ad21fd..744717cd80 100644 --- a/tests/auto/declarative/qsgtextinput/tst_qsgtextinput.cpp +++ b/tests/auto/declarative/qsgtextinput/tst_qsgtextinput.cpp @@ -51,7 +51,9 @@ #include #include #include +#include #include +#include #ifdef Q_OS_SYMBIAN // In Symbian OS test data is located in applications private dir @@ -59,6 +61,7 @@ #endif Q_DECLARE_METATYPE(QSGTextInput::SelectionMode) +DEFINE_BOOL_CONFIG_OPTION(qmlDisableDistanceField, QML_DISABLE_DISTANCEFIELD) QString createExpectedFileIfNotFound(const QString& filebasename, const QImage& actual) { @@ -221,11 +224,38 @@ void tst_qsgtextinput::width() delete textinputObject; } + bool requiresUnhintedMetrics = !qmlDisableDistanceField(); + for (int i = 0; i < standard.size(); i++) { QFont f; - QFontMetricsF fm(f); - qreal metricWidth = fm.width(standard.at(i)); + qreal metricWidth = 0.0; + if (requiresUnhintedMetrics) { + QString s = standard.at(i); + s.replace(QLatin1Char('\n'), QChar::LineSeparator); + + QTextLayout layout(s); + layout.setFlags(Qt::TextExpandTabs | Qt::TextShowMnemonic); + { + QTextOption option; + option.setUseDesignMetrics(true); + layout.setTextOption(option); + } + + layout.beginLayout(); + forever { + QTextLine line = layout.createLine(); + if (!line.isValid()) + break; + } + + layout.endLayout(); + + metricWidth = ceil(layout.boundingRect().width()); + } else { + QFontMetricsF fm(f); + metricWidth = fm.width(standard.at(i)); + } QString componentStr = "import QtQuick 2.0\nTextInput { text: \"" + standard.at(i) + "\" }"; QDeclarativeComponent textinputComponent(&engine); @@ -1048,7 +1078,6 @@ void tst_qsgtextinput::horizontalAlignment() void tst_qsgtextinput::horizontalAlignment_RightToLeft() { - QSKIP("QTBUG-20017", SkipAll); QSGView canvas(QUrl::fromLocalFile(SRCDIR "/data/horizontalAlignment_RightToLeft.qml")); QSGTextInput *textInput = canvas.rootObject()->findChild("text"); QVERIFY(textInput != 0); @@ -1161,7 +1190,45 @@ void tst_qsgtextinput::positionAt() QFontMetrics fm(textinputObject->font()); int pos = textinputObject->positionAt(textinputObject->width()/2); - int diff = abs(int(fm.width(textinputObject->text()) - (fm.width(textinputObject->text().left(pos))+textinputObject->width()/2))); + int textWidth = 0; + int textLeftWidth = 0; + if (!qmlDisableDistanceField()) { + { + QTextLayout layout(textinputObject->text().left(pos)); + + { + QTextOption option; + option.setUseDesignMetrics(true); + layout.setTextOption(option); + } + + layout.beginLayout(); + QTextLine line = layout.createLine(); + layout.endLayout(); + + textLeftWidth = ceil(line.horizontalAdvance()); + } + { + QTextLayout layout(textinputObject->text()); + + { + QTextOption option; + option.setUseDesignMetrics(true); + layout.setTextOption(option); + } + + layout.beginLayout(); + QTextLine line = layout.createLine(); + layout.endLayout(); + + textWidth = ceil(line.horizontalAdvance()); + } + } else { + textWidth = fm.width(textinputObject->text()); + textLeftWidth = fm.width(textinputObject->text().left(pos)); + } + + int diff = abs(textWidth - (textLeftWidth+textinputObject->width()/2)); // some tollerance for different fonts. #ifdef Q_OS_LINUX @@ -1177,7 +1244,28 @@ void tst_qsgtextinput::positionAt() // Check without autoscroll... textinputObject->setAutoScroll(false); pos = textinputObject->positionAt(textinputObject->width()/2); - diff = abs(int(fm.width(textinputObject->text().left(pos))-textinputObject->width()/2)); + + if (!qmlDisableDistanceField()) { + { + QTextLayout layout(textinputObject->text().left(pos)); + + { + QTextOption option; + option.setUseDesignMetrics(true); + layout.setTextOption(option); + } + + layout.beginLayout(); + QTextLine line = layout.createLine(); + layout.endLayout(); + + textLeftWidth = ceil(line.horizontalAdvance()); + } + } else { + textLeftWidth = fm.width(textinputObject->text().left(pos)); + } + + diff = abs(int(textLeftWidth-textinputObject->width()/2)); // some tollerance for different fonts. #ifdef Q_OS_LINUX @@ -1442,7 +1530,6 @@ void tst_qsgtextinput::navigation() void tst_qsgtextinput::navigation_RTL() { - QSKIP("QTBUG-20017", SkipAll); QSGView canvas(QUrl::fromLocalFile(SRCDIR "/data/navigation.qml")); canvas.show(); canvas.setFocus(); -- cgit v1.2.3