summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKirill Burtsev <kirill.burtsev@qt.io>2018-08-22 09:53:21 +0200
committerKirill Burtsev <kirill.burtsev@qt.io>2018-10-01 09:47:54 +0000
commit3257ab9ce01b01b667237fd6ad33512739db5b01 (patch)
treedc550c6276444f8077b69319987efd56c00001d4
parent774f8d3d8099286ee1202fb8b809b399b4632fb3 (diff)
Fix QWebEngineView changed properties emit on setPage
QWebEngineView now also emits url, title, icon and selection changes on setPage in the save way when url changes. Before, those updates were only forwarded from current page. Fixes: QTBUG-69300 Change-Id: If827205094423bc00064a123ddb143b6002d2e7c Reviewed-by: Kai Koehne <kai.koehne@qt.io>
-rw-r--r--src/webenginewidgets/api/qwebenginepage.cpp2
-rw-r--r--src/webenginewidgets/api/qwebengineview.cpp76
-rw-r--r--src/webenginewidgets/api/qwebengineview_p.h5
-rw-r--r--tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp96
4 files changed, 161 insertions, 18 deletions
diff --git a/src/webenginewidgets/api/qwebenginepage.cpp b/src/webenginewidgets/api/qwebenginepage.cpp
index 187565a76..fbb7c1f9e 100644
--- a/src/webenginewidgets/api/qwebenginepage.cpp
+++ b/src/webenginewidgets/api/qwebenginepage.cpp
@@ -902,7 +902,7 @@ QWebEnginePage::~QWebEnginePage()
Q_D(QWebEnginePage);
setDevToolsPage(nullptr);
d->adapter->stopFinding();
- QWebEngineViewPrivate::bind(nullptr, this, true);
+ QWebEngineViewPrivate::removePageFromView(this);
}
QWebEngineHistory *QWebEnginePage::history() const
diff --git a/src/webenginewidgets/api/qwebengineview.cpp b/src/webenginewidgets/api/qwebengineview.cpp
index aa51e5b0e..e6f9fcb49 100644
--- a/src/webenginewidgets/api/qwebengineview.cpp
+++ b/src/webenginewidgets/api/qwebengineview.cpp
@@ -55,33 +55,77 @@
QT_BEGIN_NAMESPACE
-void QWebEngineViewPrivate::bind(QWebEngineView *view, QWebEnginePage *page, bool pageBeingDeleted)
+void QWebEngineViewPrivate::notify(QWebEngineView *view, QWebEnginePage *oldPage, QWebEnginePage *newPage)
+{
+ Q_ASSERT(view);
+
+ auto oldUrl = oldPage ? oldPage->url() : QUrl();
+ auto newUrl = newPage ? newPage->url() : QUrl();
+ if (oldUrl != newUrl)
+ Q_EMIT view->urlChanged(newUrl);
+
+ auto oldTitle = oldPage ? oldPage->title() : QString();
+ auto newTitle = newPage ? newPage->title() : QString();
+ if (oldTitle != newTitle)
+ Q_EMIT view->titleChanged(newTitle);
+
+ auto oldIcon = oldPage ? oldPage->iconUrl() : QUrl();
+ auto newIcon = newPage ? newPage->iconUrl() : QUrl();
+ if (oldIcon != newIcon) {
+ Q_EMIT view->iconUrlChanged(newIcon);
+ Q_EMIT view->iconChanged(newPage ? newPage->icon() : QIcon());
+ }
+
+ if ((oldPage && oldPage->hasSelection()) || (newPage && newPage->hasSelection()))
+ Q_EMIT view->selectionChanged();
+}
+
+QWebEnginePage* QWebEngineViewPrivate::removeViewFromPage(QWebEngineView *view)
+{
+ Q_ASSERT(view);
+ QWebEnginePage *oldPage = view->d_func()->page;
+
+ if (oldPage) {
+ oldPage->disconnect(view);
+ oldPage->d_func()->view = nullptr;
+ if (oldPage->parent() != view)
+ oldPage->d_func()->adapter->reattachRWHV();
+ }
+ return oldPage;
+}
+
+void QWebEngineViewPrivate::removePageFromView(QWebEnginePage *page)
+{
+ Q_ASSERT(page);
+ if (QWebEngineView *oldView = page->d_func()->view) {
+ page->disconnect(oldView);
+ page->d_func()->view = nullptr;
+ oldView->d_func()->page = nullptr;
+ notify(oldView, page, nullptr);
+ }
+}
+
+void QWebEngineViewPrivate::bind(QWebEngineView *view, QWebEnginePage *page)
{
if (view && page == view->d_func()->page)
return;
if (page) {
// Un-bind page from its current view.
- if (QWebEngineView *oldView = page->d_func()->view) {
- page->disconnect(oldView);
- oldView->d_func()->page = nullptr;
- }
+ removePageFromView(page);
page->d_func()->view = view;
- if (!pageBeingDeleted)
- page->d_func()->adapter->reattachRWHV();
+ page->d_func()->adapter->reattachRWHV();
}
if (view) {
// Un-bind view from its current page.
- if (QWebEnginePage *oldPage = view->d_func()->page) {
- oldPage->disconnect(view);
- oldPage->d_func()->view = nullptr;
- if (oldPage->parent() == view)
- delete oldPage;
- else
- oldPage->d_func()->adapter->reattachRWHV();
- }
+ QWebEnginePage *oldPage = removeViewFromPage(view);
+
view->d_func()->page = page;
+ notify(view, oldPage, page);
+
+ if (oldPage && oldPage->parent() == view)
+ delete oldPage;
}
if (view && page) {
@@ -149,7 +193,7 @@ QWebEngineView::QWebEngineView(QWidget *parent)
QWebEngineView::~QWebEngineView()
{
- QWebEngineViewPrivate::bind(this, nullptr);
+ QWebEngineViewPrivate::removeViewFromPage(this);
}
QWebEnginePage* QWebEngineView::page() const
diff --git a/src/webenginewidgets/api/qwebengineview_p.h b/src/webenginewidgets/api/qwebengineview_p.h
index bfb44bec5..1845bfb60 100644
--- a/src/webenginewidgets/api/qwebengineview_p.h
+++ b/src/webenginewidgets/api/qwebengineview_p.h
@@ -65,7 +65,10 @@ public:
Q_DECLARE_PUBLIC(QWebEngineView)
QWebEngineView *q_ptr;
- static void bind(QWebEngineView *view, QWebEnginePage *page, bool pageBeingDeleted = false);
+ static void notify(QWebEngineView *view, QWebEnginePage *oldPage, QWebEnginePage *newPage);
+ static QWebEnginePage* removeViewFromPage(QWebEngineView *view);
+ static void removePageFromView(QWebEnginePage *page);
+ static void bind(QWebEngineView *view, QWebEnginePage *page);
QWebEngineViewPrivate();
diff --git a/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp b/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
index 57f5f6def..78677e459 100644
--- a/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
+++ b/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
@@ -134,6 +134,8 @@ private Q_SLOTS:
void renderHints();
void getWebKitVersion();
+ void changePage_data();
+ void changePage();
void reusePage_data();
void reusePage();
void microFocusCoordinates();
@@ -260,6 +262,100 @@ void tst_QWebEngineView::getWebKitVersion()
#endif
}
+void tst_QWebEngineView::changePage_data()
+{
+ QString html = "<html><head><title>%1</title>"
+ "<link rel='icon' href='file://" TESTS_SOURCE_DIR "/resources/image2.png'></head></html>";
+ QUrl urlFrom("data:text/html," + html.arg("TitleFrom"));
+ QUrl urlTo("data:text/html," + html.arg("TitleTo"));
+ QUrl nullPage("data:text/html,<html/>");
+ QTest::addColumn<QUrl>("urlFrom");
+ QTest::addColumn<QUrl>("urlTo");
+ QTest::addColumn<bool>("fromIsNullPage");
+ QTest::addColumn<bool>("toIsNullPage");
+ QTest::newRow("From empty page to url") << nullPage << urlTo << true << false;
+ QTest::newRow("From url to empty content page") << urlFrom << nullPage << false << true;
+ QTest::newRow("From one content to another") << urlFrom << urlTo << false << false;
+}
+
+void tst_QWebEngineView::changePage()
+{
+ QScopedPointer<QWebEngineView> view(new QWebEngineView); view->resize(640, 480); view->show();
+
+ QFETCH(QUrl, urlFrom);
+ QFETCH(QUrl, urlTo);
+ QFETCH(bool, fromIsNullPage);
+ QFETCH(bool, toIsNullPage);
+
+ QSignalSpy spyUrl(view.get(), &QWebEngineView::urlChanged);
+ QSignalSpy spyTitle(view.get(), &QWebEngineView::titleChanged);
+ QSignalSpy spyIconUrl(view.get(), &QWebEngineView::iconUrlChanged);
+ QSignalSpy spyIcon(view.get(), &QWebEngineView::iconChanged);
+
+ QScopedPointer<QWebEnginePage> pageFrom(new QWebEnginePage);
+ QSignalSpy pageFromLoadSpy(pageFrom.get(), &QWebEnginePage::loadFinished);
+ QSignalSpy pageFromIconLoadSpy(pageFrom.get(), &QWebEnginePage::iconChanged);
+ pageFrom->load(urlFrom);
+ QTRY_COMPARE(pageFromLoadSpy.count(), 1);
+ QCOMPARE(pageFromLoadSpy.last().value(0).toBool(), true);
+ if (!fromIsNullPage) {
+ QTRY_COMPARE(pageFromIconLoadSpy.count(), 1);
+ QVERIFY(!pageFromIconLoadSpy.last().value(0).isNull());
+ }
+
+ view->setPage(pageFrom.get());
+
+ QTRY_COMPARE(spyUrl.count(), 1);
+ QCOMPARE(spyUrl.last().value(0).toUrl(), pageFrom->url());
+ QTRY_COMPARE(spyTitle.count(), 1);
+ QCOMPARE(spyTitle.last().value(0).toString(), pageFrom->title());
+
+ QTRY_COMPARE(spyIconUrl.count(), fromIsNullPage ? 0 : 1);
+ QTRY_COMPARE(spyIcon.count(), fromIsNullPage ? 0 : 1);
+ if (!fromIsNullPage) {
+ QVERIFY(!pageFrom->iconUrl().isEmpty());
+ QCOMPARE(spyIconUrl.last().value(0).toUrl(), pageFrom->iconUrl());
+ QCOMPARE(spyIcon.last().value(0), QVariant::fromValue(pageFrom->icon()));
+ }
+
+ QScopedPointer<QWebEnginePage> pageTo(new QWebEnginePage);
+ QSignalSpy pageToLoadSpy(pageTo.get(), &QWebEnginePage::loadFinished);
+ QSignalSpy pageToIconLoadSpy(pageTo.get(), &QWebEnginePage::iconChanged);
+ pageTo->load(urlTo);
+ QTRY_COMPARE(pageToLoadSpy.count(), 1);
+ QCOMPARE(pageToLoadSpy.last().value(0).toBool(), true);
+ if (!toIsNullPage) {
+ QTRY_COMPARE(pageToIconLoadSpy.count(), 1);
+ QVERIFY(!pageToIconLoadSpy.last().value(0).isNull());
+ }
+
+ view->setPage(pageTo.get());
+
+ QTRY_COMPARE(spyUrl.count(), 2);
+ QCOMPARE(spyUrl.last().value(0).toUrl(), pageTo->url());
+ QTRY_COMPARE(spyTitle.count(), 2);
+ QCOMPARE(spyTitle.last().value(0).toString(), pageTo->title());
+
+ bool iconIsSame = fromIsNullPage == toIsNullPage;
+ int iconChangeNotifyCount = fromIsNullPage ? (iconIsSame ? 0 : 1) : (iconIsSame ? 1 : 2);
+
+ QTRY_COMPARE(spyIconUrl.count(), iconChangeNotifyCount);
+ QTRY_COMPARE(spyIcon.count(), iconChangeNotifyCount);
+ QCOMPARE(pageFrom->iconUrl() == pageTo->iconUrl(), iconIsSame);
+ if (!iconIsSame) {
+ QCOMPARE(spyIconUrl.last().value(0).toUrl(), pageTo->iconUrl());
+ QCOMPARE(spyIcon.last().value(0), QVariant::fromValue(pageTo->icon()));
+ }
+
+ // verify no emits on destroy with the same number of signals in spy
+ view.reset();
+ qApp->processEvents();
+ QTRY_COMPARE(spyUrl.count(), 2);
+ QTRY_COMPARE(spyTitle.count(), 2);
+ QTRY_COMPARE(spyIconUrl.count(), iconChangeNotifyCount);
+ QTRY_COMPARE(spyIcon.count(), iconChangeNotifyCount);
+}
+
void tst_QWebEngineView::reusePage_data()
{
QTest::addColumn<QString>("html");