QTextDocument: add setLayoutEnabled()

This allows to set up everything first - without paying for layouting
at every step - and only then trigger layouting.

Same performance behavior as setTextWidth(0), but this is a more
explicit/readable API.

Change-Id: I044dbd8b1301b1c97a92f9a29ccde2baf27a7665
Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
This commit is contained in:
David Faure 2022-04-29 16:35:34 +02:00 committed by Volker Hilsheimer
parent e5a5c099af
commit 1e938c348b
4 changed files with 59 additions and 1 deletions

View File

@ -634,6 +634,41 @@ bool QTextDocument::useDesignMetrics() const
return d->defaultTextOption.useDesignMetrics();
}
/*!
\property QTextDocument::layoutEnabled
\since 6.4
\brief whether QTextDocument should recalculate the layout after every change
If this property is set to true, any change triggers a laying out of the
document, which makes everything work as expected, but takes time.
Temporarily disabling the layout process can save time when making multiple changes
(not just text content, but also default font, default text option....)
so that the document is only laid out once in the end. This can be useful when the
text width or page size isn't yet known, for instance.
By default, this property is \c true.
\sa setTextWidth
*/
void QTextDocument::setLayoutEnabled(bool b)
{
Q_D(QTextDocument);
if (d->layoutEnabled == b)
return;
d->layoutEnabled = b;
if (b && d->lout)
d->lout->documentChanged(0, 0, d->length());
}
bool QTextDocument::isLayoutEnabled() const
{
Q_D(const QTextDocument);
return d->layoutEnabled;
}
/*!
\since 4.2

View File

@ -62,6 +62,7 @@ class Q_GUI_EXPORT QTextDocument : public QObject
Q_PROPERTY(QSizeF pageSize READ pageSize WRITE setPageSize)
Q_PROPERTY(QFont defaultFont READ defaultFont WRITE setDefaultFont)
Q_PROPERTY(bool useDesignMetrics READ useDesignMetrics WRITE setUseDesignMetrics)
Q_PROPERTY(bool layoutEnabled READ isLayoutEnabled WRITE setLayoutEnabled)
Q_PROPERTY(QSizeF size READ size)
Q_PROPERTY(qreal textWidth READ textWidth WRITE setTextWidth)
Q_PROPERTY(int blockCount READ blockCount)
@ -218,6 +219,9 @@ public:
void setUseDesignMetrics(bool b);
bool useDesignMetrics() const;
void setLayoutEnabled(bool b);
bool isLayoutEnabled() const;
void drawContents(QPainter *painter, const QRectF &rect = QRectF());
void setTextWidth(qreal width);

View File

@ -294,7 +294,7 @@ public:
// Only test the width for 0:
// * setTextWidth(x) leads to height -1, which is valid
// * the default page size of (-1, -1) means size determined from contents, this is valid too
bool canLayout() const { return !qIsNull(pageSize.width()); }
bool canLayout() const { return layoutEnabled && !qIsNull(pageSize.width()); }
private:
QTextDocumentPrivate(const QTextDocumentPrivate& m);
@ -342,6 +342,7 @@ private:
public:
bool inContentsChange;
bool layoutEnabled = true;
QTextOption defaultTextOption;
Qt::CursorMoveStyle defaultCursorMoveStyle;
#ifndef QT_NO_CSSPARSER

View File

@ -35,6 +35,7 @@ private slots:
void translate();
void createTextItem();
void createTextItemZeroWidth();
void createTextItemNoLayouting();
};
tst_QGraphicsItem::tst_QGraphicsItem()
@ -235,5 +236,22 @@ void tst_QGraphicsItem::createTextItemZeroWidth()
}
}
void tst_QGraphicsItem::createTextItemNoLayouting()
{
// Ensure QFontDatabase loaded the font beforehand
QFontInfo(qApp->font()).family();
const QString text = "This is some text";
QBENCHMARK {
QGraphicsTextItem item;
item.document()->setLayoutEnabled(false);
// Prepare everything
item.setPlainText(text);
QTextOption option = item.document()->defaultTextOption();
option.setAlignment(Qt::AlignHCenter);
item.document()->setDefaultTextOption(option);
// And (in a real app) enable layouting here
}
}
QTEST_MAIN(tst_QGraphicsItem)
#include "tst_qgraphicsitem.moc"