QTextDocumentLayout: Account for topMargin when hit-testing
When TopMargin is set in TextBlock and the mouse click position is between Margin (the mouse is not on the textrect), the cursor will usually jump to the end. So topMargin should be considered when hitTest() calculates coordinates. Fixes: QTBUG-91774 Change-Id: I231377263855b9cd7152684203fc4ed2e9299bb9 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io> Reviewed-by: Tang Haixiang <tanghaixiang@uniontech.com> Reviewed-by: Eskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io> (cherry picked from commit 8aae49019d7386c1abd6cd32f7ccb68c264c0288)
This commit is contained in:
parent
16dcd2abe6
commit
b3bb20b8bc
@ -794,7 +794,7 @@ QTextDocumentLayoutPrivate::hitTest(const QTextBlock &bl, const QFixedPoint &poi
|
||||
textrect.translate(tl->position());
|
||||
qCDebug(lcHit) << " checking block" << bl.position() << "point=" << point.toPointF() << " tlrect" << textrect;
|
||||
*position = bl.position();
|
||||
if (point.y.toReal() < textrect.top()) {
|
||||
if (point.y.toReal() < textrect.top() - bl.blockFormat().topMargin()) {
|
||||
qCDebug(lcHit) << " before pos=" << *position;
|
||||
return PointBefore;
|
||||
} else if (point.y.toReal() > textrect.bottom()) {
|
||||
|
@ -33,6 +33,7 @@ private slots:
|
||||
void floatingTablePageBreak();
|
||||
void imageAtRightAlignedTab();
|
||||
void blockVisibility();
|
||||
void testHitTest();
|
||||
|
||||
void largeImage();
|
||||
|
||||
@ -380,5 +381,41 @@ void tst_QTextDocumentLayout::largeImage()
|
||||
}
|
||||
}
|
||||
|
||||
void tst_QTextDocumentLayout::testHitTest()
|
||||
{
|
||||
QTextDocument document;
|
||||
QTextCursor cur(&document);
|
||||
int topMargin = 20;
|
||||
|
||||
//insert 500 blocks into textedit
|
||||
for (int i = 0; i < 500; i++) {
|
||||
cur.insertBlock();
|
||||
cur.insertHtml(QString("block %1").arg(i));
|
||||
}
|
||||
|
||||
//randomly set half the blocks invisible
|
||||
QTextBlock blk=document.begin();
|
||||
for (int i = 0; i < 500; i++) {
|
||||
if (i % 7)
|
||||
blk.setVisible(0);
|
||||
blk = blk.next();
|
||||
}
|
||||
|
||||
//set margin for all blocks (not strictly necessary, but makes easier to click in between blocks)
|
||||
QTextBlockFormat blkfmt;
|
||||
blkfmt.setTopMargin(topMargin);
|
||||
cur.movePosition(QTextCursor::Start);
|
||||
cur.movePosition(QTextCursor::End, QTextCursor::KeepAnchor);
|
||||
cur.mergeBlockFormat(blkfmt);
|
||||
|
||||
for (int y = cur.selectionStart(); y < cur.selectionEnd(); y += 10) {
|
||||
QPoint mousePoint(1, y);
|
||||
int cursorPos = document.documentLayout()->hitTest(mousePoint, Qt::FuzzyHit);
|
||||
int positionY = document.findBlock(cursorPos).layout()->position().toPoint().y();
|
||||
//mousePoint is in the rect of the current Block
|
||||
QVERIFY(positionY - topMargin <= y);
|
||||
}
|
||||
}
|
||||
|
||||
QTEST_MAIN(tst_QTextDocumentLayout)
|
||||
#include "tst_qtextdocumentlayout.moc"
|
||||
|
Loading…
x
Reference in New Issue
Block a user