QTextHtmlImporter: don't forget to appendBlock after block tag closed

If we see a closing tag that really demands a new block after it,
like </ul>, that needs to be done even if some ignorable whitespace
and "inline" tags come after it. Don't get distracted by those.

Also add a comment in QTextDocument::setHtml() to remind the reader that
HTML parsing is a two-pass algorithm.

Fixes: QTBUG-81662
Change-Id: If723c9d3c211a684725055a06bcf87be4e38923a
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Eskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io>
(cherry picked from commit 60aeeb0e92762d57c208e4212374d30be6490611)
Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
(cherry picked from commit f0713117d6d0b77c5903ffe9ce3a7d5317021691)
This commit is contained in:
Shawn Rutledge 2024-02-28 16:36:02 -07:00 committed by Qt Cherry-pick Bot
parent b8ed5def06
commit d91d5d3abe
3 changed files with 27 additions and 1 deletions

View File

@ -1267,6 +1267,8 @@ void QTextDocument::setHtml(const QString &html)
d->enableUndoRedo(false);
d->beginEditBlock();
d->clear();
// ctor calls parse() to build up QTextHtmlParser::nodes list
// then import() populates the QTextDocument from those
QTextHtmlImporter(this, html, QTextHtmlImporter::ImportToDocument).import();
d->endEditBlock();
d->enableUndoRedo(previousState);

View File

@ -488,7 +488,8 @@ void QTextHtmlImporter::import()
* means there was a tag closing in the input html
*/
if (currentNodeIdx > 0 && (currentNode->parent != currentNodeIdx - 1)) {
blockTagClosed = closeTag();
const bool lastBlockTagClosed = closeTag();
blockTagClosed = blockTagClosed || lastBlockTagClosed;
// visually collapse subsequent block tags, but if the element after the closed block tag
// is for example an inline element (!isBlock) we have to make sure we start a new paragraph by setting
// hasBlock to false.
@ -540,6 +541,7 @@ void QTextHtmlImporter::import()
appendBlock(block, currentNode->charFormat);
blockTagClosed = false;
hasBlock = true;
}

View File

@ -16,6 +16,8 @@
#include <qtextcursor.h>
using namespace Qt::StringLiterals;
QT_FORWARD_DECLARE_CLASS(QTextDocument)
class tst_QTextDocumentFragment : public QObject
@ -245,6 +247,7 @@ private slots:
void html_fromFirefox();
void html_emptyInlineInsideBlock();
void css_fontAndWordSpacing();
void html_brWithWhitespaceAfterList();
private:
inline void setHtml(const QString &html)
@ -4320,5 +4323,24 @@ void tst_QTextDocumentFragment::css_fontAndWordSpacing()
}
}
void tst_QTextDocumentFragment::html_brWithWhitespaceAfterList() // QTBUG-81662
{
setHtml(QString::fromLatin1("<ul><li>one</li><li>two</li></ul>\n <br/>\nhello"));
QCOMPARE(doc->blockCount(), 3);
QTextBlock block = doc->begin();
QVERIFY(block.textList());
block = block.next();
QVERIFY(block.textList());
block = block.next();
QCOMPARE(block.text(), u"\u2028hello"_s);
block = block.next();
QVERIFY(block.text().isEmpty());
}
QTEST_MAIN(tst_QTextDocumentFragment)
#include "tst_qtextdocumentfragment.moc"