summaryrefslogtreecommitdiffstats
path: root/tests/auto/widgets
diff options
context:
space:
mode:
Diffstat (limited to 'tests/auto/widgets')
-rw-r--r--tests/auto/widgets/positionplugin/plugin.cpp112
-rw-r--r--tests/auto/widgets/positionplugin/plugin.json9
-rw-r--r--tests/auto/widgets/positionplugin/positionplugin.pro13
-rw-r--r--tests/auto/widgets/qwebengineaccessibility/tst_qwebengineaccessibility.cpp12
-rw-r--r--tests/auto/widgets/qwebenginedefaultsurfaceformat/tst_qwebenginedefaultsurfaceformat.cpp3
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/qwebenginefaviconmanager.pro1
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-misc.html11
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-multi.html9
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-shortcut.html10
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-single.html9
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-touch.html10
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-unavailable.html9
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt144.pngbin0 -> 8315 bytes
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt32.icobin0 -> 4286 bytes
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qtmulti.icobin0 -> 22382 bytes
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/resources/test1.html1
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.cpp478
-rw-r--r--tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.qrc14
-rw-r--r--tests/auto/widgets/qwebengineinspector/tst_qwebengineinspector.cpp45
-rw-r--r--tests/auto/widgets/qwebenginepage/BLACKLIST6
-rw-r--r--tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp216
-rw-r--r--tests/auto/widgets/qwebengineprofile/BLACKLIST5
-rw-r--r--tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp155
-rw-r--r--tests/auto/widgets/qwebenginescript/tst_qwebenginescript.cpp93
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/dict/en-US.aff5
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/dict/en-US.dic11
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/qwebenginespellcheck.pro22
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/resources/index.html36
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.cpp178
-rw-r--r--tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.qrc5
-rw-r--r--tests/auto/widgets/qwebengineview/resources/basic_printing_page.html8
-rw-r--r--tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp4
-rw-r--r--tests/auto/widgets/qwebengineview/tst_qwebengineview.qrc15
-rw-r--r--tests/auto/widgets/resources/qwebchannel.js408
-rw-r--r--tests/auto/widgets/resources/tests.qrc5
-rw-r--r--tests/auto/widgets/tests.pri1
-rw-r--r--tests/auto/widgets/util.h53
-rw-r--r--tests/auto/widgets/widgets.pro7
38 files changed, 1613 insertions, 366 deletions
diff --git a/tests/auto/widgets/positionplugin/plugin.cpp b/tests/auto/widgets/positionplugin/plugin.cpp
deleted file mode 100644
index 74d30469d..000000000
--- a/tests/auto/widgets/positionplugin/plugin.cpp
+++ /dev/null
@@ -1,112 +0,0 @@
-/****************************************************************************
-**
-** Copyright (C) 2015 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
-**
-** This file is part of the test suite of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:LGPL21$
-** Commercial License Usage
-** Licensees holding valid commercial Qt licenses may use this file in
-** accordance with the commercial license agreement provided with the
-** Software or, alternatively, in accordance with the terms contained in
-** a written agreement between you and The Qt Company. For licensing terms
-** and conditions see http://www.qt.io/terms-conditions. For further
-** information use the contact form at http://www.qt.io/contact-us.
-**
-** GNU Lesser General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU Lesser
-** General Public License version 2.1 or version 3 as published by the Free
-** Software Foundation and appearing in the file LICENSE.LGPLv21 and
-** LICENSE.LGPLv3 included in the packaging of this file. Please review the
-** following information to ensure the GNU Lesser General Public License
-** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
-**
-** As a special exception, The Qt Company gives you certain additional
-** rights. These rights are described in The Qt Company LGPL Exception
-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
-
-#include <QtPositioning/qgeopositioninfosource.h>
-#include <QtPositioning/qgeopositioninfosourcefactory.h>
-#include <QObject>
-#include <QtPlugin>
-
-class DummySource : public QGeoPositionInfoSource
-{
- Q_OBJECT
-
-public:
- DummySource(QObject *parent=0);
-
- void startUpdates() {}
- void stopUpdates() {}
- void requestUpdate(int) {}
-
- QGeoPositionInfo lastKnownPosition(bool fromSatellitePositioningMethodsOnly) const;
- PositioningMethods supportedPositioningMethods() const;
-
- int minimumUpdateInterval() const;
- Error error() const;
-};
-
-DummySource::DummySource(QObject *parent) :
- QGeoPositionInfoSource(parent)
-{
-}
-
-QGeoPositionInfoSource::Error DummySource::error() const
-{
- return QGeoPositionInfoSource::NoError;
-}
-
-int DummySource::minimumUpdateInterval() const
-{
- return 1000;
-}
-
-QGeoPositionInfo DummySource::lastKnownPosition(bool fromSatellitePositioningMethodsOnly) const
-{
- Q_UNUSED(fromSatellitePositioningMethodsOnly);
- return QGeoPositionInfo(QGeoCoordinate(54.186824, 12.087262), QDateTime::currentDateTime());
-}
-
-QGeoPositionInfoSource::PositioningMethods DummySource::supportedPositioningMethods() const
-{
- return QGeoPositionInfoSource::AllPositioningMethods;
-}
-
-
-class QGeoPositionInfoSourceFactoryTest : public QObject, public QGeoPositionInfoSourceFactory
-{
- Q_OBJECT
- Q_PLUGIN_METADATA(IID "org.qt-project.qt.position.sourcefactory/5.0"
- FILE "plugin.json")
- Q_INTERFACES(QGeoPositionInfoSourceFactory)
-
-public:
- QGeoPositionInfoSource *positionInfoSource(QObject *parent);
- QGeoSatelliteInfoSource *satelliteInfoSource(QObject *parent);
- QGeoAreaMonitorSource *areaMonitor(QObject *parent);
-};
-
-QGeoPositionInfoSource *QGeoPositionInfoSourceFactoryTest::positionInfoSource(QObject *parent)
-{
- return new DummySource(parent);
-}
-
-QGeoSatelliteInfoSource *QGeoPositionInfoSourceFactoryTest::satelliteInfoSource(QObject *)
-{
- return 0;
-}
-
-QGeoAreaMonitorSource *QGeoPositionInfoSourceFactoryTest::areaMonitor(QObject* )
-{
- return 0;
-}
-
-#include "plugin.moc"
diff --git a/tests/auto/widgets/positionplugin/plugin.json b/tests/auto/widgets/positionplugin/plugin.json
deleted file mode 100644
index 68acaded3..000000000
--- a/tests/auto/widgets/positionplugin/plugin.json
+++ /dev/null
@@ -1,9 +0,0 @@
-{
- "Keys": ["test.source"],
- "Provider": "test.source",
- "Position": true,
- "Satellite": false,
- "Monitor": false,
- "Priority": 0,
- "Testable": true
-}
diff --git a/tests/auto/widgets/positionplugin/positionplugin.pro b/tests/auto/widgets/positionplugin/positionplugin.pro
deleted file mode 100644
index 6f2e736c6..000000000
--- a/tests/auto/widgets/positionplugin/positionplugin.pro
+++ /dev/null
@@ -1,13 +0,0 @@
-TARGET = qtwebengine_positioning_testplugin
-
-QT += positioning
-
-SOURCES += plugin.cpp
-
-OTHER_FILES += \
- plugin.json
-
-PLUGIN_TYPE = position
-PLUGIN_CLASS_NAME = TestPositionPlugin
-PLUGIN_EXTENDS = -
-load(qt_plugin)
diff --git a/tests/auto/widgets/qwebengineaccessibility/tst_qwebengineaccessibility.cpp b/tests/auto/widgets/qwebengineaccessibility/tst_qwebengineaccessibility.cpp
index 016c4f98c..63ca25396 100644
--- a/tests/auto/widgets/qwebengineaccessibility/tst_qwebengineaccessibility.cpp
+++ b/tests/auto/widgets/qwebengineaccessibility/tst_qwebengineaccessibility.cpp
@@ -112,9 +112,9 @@ void tst_QWebEngineView::hierarchy()
QCOMPARE(text->parent(), grouping);
QCOMPARE(grouping->indexOfChild(text), 0);
QCOMPARE(text->childCount(), 0);
- QCOMPARE(text->text(QAccessible::Name), QString());
+ QCOMPARE(text->text(QAccessible::Name), QStringLiteral("Hello world"));
QCOMPARE(text->text(QAccessible::Description), QString());
- QCOMPARE(text->text(QAccessible::Value), QStringLiteral("Hello world"));
+ QCOMPARE(text->text(QAccessible::Value), QString());
QAccessibleInterface *input = grouping->child(1);
QCOMPARE(input->role(), QAccessible::EditableText);
@@ -182,9 +182,9 @@ void tst_QWebEngineView::text()
QAccessibleInterface *grouping2 = document->child(1);
QAccessibleInterface *label1 = grouping2->child(0);
QCOMPARE(label1->role(), QAccessible::StaticText);
- QCOMPARE(label1->text(QAccessible::Name), QString());
+ QCOMPARE(label1->text(QAccessible::Name), QStringLiteral("Enter your name here:"));
QCOMPARE(label1->text(QAccessible::Description), QString());
- QCOMPARE(label1->text(QAccessible::Value), QStringLiteral("Enter your name here:"));
+ QCOMPARE(label1->text(QAccessible::Value), QString());
QAccessibleInterface *grouping3 = document->child(2);
QAccessibleInterface *input2 = grouping3->child(0);
QCOMPARE(input2->role(), QAccessible::EditableText);
@@ -194,9 +194,9 @@ void tst_QWebEngineView::text()
QAccessibleInterface *grouping4 = document->child(3);
QAccessibleInterface *label2 = grouping4->child(0);
QCOMPARE(label2->role(), QAccessible::StaticText);
- QCOMPARE(label2->text(QAccessible::Name), QString());
+ QCOMPARE(label2->text(QAccessible::Name), QStringLiteral("Provide both first and last name."));
QCOMPARE(label2->text(QAccessible::Description), QString());
- QCOMPARE(label2->text(QAccessible::Value), QStringLiteral("Provide both first and last name."));
+ QCOMPARE(label2->text(QAccessible::Value), QString());
// Good day! [edit]
QAccessibleInterface *grouping5 = document->child(4);
diff --git a/tests/auto/widgets/qwebenginedefaultsurfaceformat/tst_qwebenginedefaultsurfaceformat.cpp b/tests/auto/widgets/qwebenginedefaultsurfaceformat/tst_qwebenginedefaultsurfaceformat.cpp
index e42a8a75e..3757a7842 100644
--- a/tests/auto/widgets/qwebenginedefaultsurfaceformat/tst_qwebenginedefaultsurfaceformat.cpp
+++ b/tests/auto/widgets/qwebenginedefaultsurfaceformat/tst_qwebenginedefaultsurfaceformat.cpp
@@ -51,6 +51,9 @@ private Q_SLOTS:
void tst_QWebEngineDefaultSurfaceFormat::customDefaultSurfaceFormat()
{
+#if defined(Q_OS_WIN)
+ QSKIP("Crashes on Windows");
+#endif
// Setting a new default QSurfaceFormat with a core OpenGL profile before
// app instantiation should succeed, without abort() being called.
int argc = 1;
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/qwebenginefaviconmanager.pro b/tests/auto/widgets/qwebenginefaviconmanager/qwebenginefaviconmanager.pro
new file mode 100644
index 000000000..e99c7f493
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/qwebenginefaviconmanager.pro
@@ -0,0 +1 @@
+include(../tests.pri)
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-misc.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-misc.html
new file mode 100644
index 000000000..9e788bdf4
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-misc.html
@@ -0,0 +1,11 @@
+<html>
+ <head>
+ <title>Favicon Test</title>
+ <link rel="shortcut icon" href="icons/qt32.ico" />
+ <link rel="apple-touch-icon" href="icons/qt144.png" />
+ <link rel="shortcut icon" href="icons/unavailable.ico" />
+ </head>
+ <body>
+ <h1>Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-multi.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-multi.html
new file mode 100644
index 000000000..cc5f3fd66
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-multi.html
@@ -0,0 +1,9 @@
+<html>
+ <head>
+ <title>Multi-sized Favicon Test</title>
+ <link rel="shortcut icon" sizes="16x16 32x23 64x64" href="icons/qtmulti.ico" />
+ </head>
+ <body>
+ <h1>Multi-sized Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-shortcut.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-shortcut.html
new file mode 100644
index 000000000..786cdb816
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-shortcut.html
@@ -0,0 +1,10 @@
+<html>
+ <head>
+ <title>Favicon Test</title>
+ <link rel="shortcut icon" href="icons/qt32.ico" />
+ <link rel="shortcut icon" href="icons/qt144.png" />
+ </head>
+ <body>
+ <h1>Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-single.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-single.html
new file mode 100644
index 000000000..eb4675c75
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-single.html
@@ -0,0 +1,9 @@
+<html>
+ <head>
+ <title>Favicon Test</title>
+ <link rel="shortcut icon" href="icons/qt32.ico" />
+ </head>
+ <body>
+ <h1>Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-touch.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-touch.html
new file mode 100644
index 000000000..271783434
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-touch.html
@@ -0,0 +1,10 @@
+<html>
+ <head>
+ <title>Favicon Test</title>
+ <link rel="apple-touch-icon" href="icons/qt32.ico" />
+ <link rel="apple-touch-icon" href="icons/qt144.png" />
+ </head>
+ <body>
+ <h1>Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-unavailable.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-unavailable.html
new file mode 100644
index 000000000..c45664294
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/favicon-unavailable.html
@@ -0,0 +1,9 @@
+<html>
+ <head>
+ <title>Favicon Test</title>
+ <link rel="shortcut icon" href="icons/unavailable.ico" />
+ </head>
+ <body>
+ <h1>Favicon Test</h1>
+ </body>
+</html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt144.png b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt144.png
new file mode 100644
index 000000000..050b1e066
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt144.png
Binary files differ
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt32.ico b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt32.ico
new file mode 100644
index 000000000..2f6fcb5bc
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qt32.ico
Binary files differ
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qtmulti.ico b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qtmulti.ico
new file mode 100644
index 000000000..81e5a22e8
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/icons/qtmulti.ico
Binary files differ
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/resources/test1.html b/tests/auto/widgets/qwebenginefaviconmanager/resources/test1.html
new file mode 100644
index 000000000..b323f966e
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/resources/test1.html
@@ -0,0 +1 @@
+<html><body><p>Some text 1</p></body></html>
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.cpp b/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.cpp
new file mode 100644
index 000000000..38311cad2
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.cpp
@@ -0,0 +1,478 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtWebEngine module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <QtTest/QtTest>
+#include "../util.h"
+
+#include <qwebenginepage.h>
+#include <qwebenginesettings.h>
+#include <qwebengineview.h>
+
+
+class tst_QWebEngineFaviconManager : public QObject {
+ Q_OBJECT
+
+public Q_SLOTS:
+ void init();
+ void initTestCase();
+ void cleanupTestCase();
+ void cleanup();
+
+private Q_SLOTS:
+ void faviconLoad();
+ void faviconLoadFromResources();
+ void faviconLoadEncodedUrl();
+ void noFavicon();
+ void aboutBlank();
+ void unavailableFavicon();
+ void errorPageEnabled();
+ void errorPageDisabled();
+ void bestFavicon();
+ void touchIcon();
+ void multiIcon();
+ void candidateIcon();
+ void downloadIconsDisabled_data();
+ void downloadIconsDisabled();
+ void downloadTouchIconsEnabled_data();
+ void downloadTouchIconsEnabled();
+
+private:
+ QWebEngineView *m_view;
+ QWebEnginePage *m_page;
+};
+
+
+void tst_QWebEngineFaviconManager::init()
+{
+ m_view = new QWebEngineView();
+ m_page = m_view->page();
+}
+
+
+void tst_QWebEngineFaviconManager::initTestCase()
+{
+}
+
+void tst_QWebEngineFaviconManager::cleanupTestCase()
+{
+}
+
+
+void tst_QWebEngineFaviconManager::cleanup()
+{
+ delete m_view;
+}
+
+void tst_QWebEngineFaviconManager::faviconLoad()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-single.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ QUrl iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(iconUrl, m_page->iconUrl());
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qt32.ico")));
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QCOMPARE(icon.availableSizes().count(), 1);
+ QSize iconSize = icon.availableSizes().first();
+ QCOMPARE(iconSize, QSize(32, 32));
+}
+
+void tst_QWebEngineFaviconManager::faviconLoadFromResources()
+{
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url("qrc:/resources/favicon-single.html");
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ QUrl iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(iconUrl, m_page->iconUrl());
+ QCOMPARE(iconUrl, QUrl("qrc:/resources/icons/qt32.ico"));
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QCOMPARE(icon.availableSizes().count(), 1);
+ QSize iconSize = icon.availableSizes().first();
+ QCOMPARE(iconSize, QSize(32, 32));
+}
+
+void tst_QWebEngineFaviconManager::faviconLoadEncodedUrl()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QString urlString = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-single.html")).toString();
+ QUrl url(urlString + QLatin1String("?favicon=load should work with#whitespace!"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ QUrl iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(m_page->iconUrl(), iconUrl);
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qt32.ico")));
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QCOMPARE(icon.availableSizes().count(), 1);
+ QSize iconSize = icon.availableSizes().first();
+ QCOMPARE(iconSize, QSize(32, 32));
+}
+
+void tst_QWebEngineFaviconManager::noFavicon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/test1.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::aboutBlank()
+{
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url("about:blank");
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::unavailableFavicon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-unavailable.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::errorPageEnabled()
+{
+ m_page->settings()->setAttribute(QWebEngineSettings::ErrorPageEnabled, true);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url("invalid://url");
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::errorPageDisabled()
+{
+ m_page->settings()->setAttribute(QWebEngineSettings::ErrorPageEnabled, false);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url("invalid://url");
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::bestFavicon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url, iconUrl;
+ QIcon icon;
+ QSize iconSize;
+
+ url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-misc.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(iconUrl, m_page->iconUrl());
+ // Touch icon is ignored
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qt32.ico")));
+
+ icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QCOMPARE(icon.availableSizes().count(), 1);
+ iconSize = icon.availableSizes().first();
+ QCOMPARE(iconSize, QSize(32, 32));
+
+ loadFinishedSpy.clear();
+ iconUrlChangedSpy.clear();
+ iconChangedSpy.clear();
+
+ url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-shortcut.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_VERIFY(iconUrlChangedSpy.count() >= 1);
+ QTRY_VERIFY(iconChangedSpy.count() >= 1);
+
+ iconUrl = iconUrlChangedSpy.last().at(0).toString();
+
+ // If the icon URL is empty we have to wait for
+ // the second iconChanged signal that propagates the expected URL
+ if (iconUrl.isEmpty()) {
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 2);
+ QTRY_COMPARE(iconChangedSpy.count(), 2);
+ iconUrl = iconUrlChangedSpy.last().at(0).toString();
+ }
+
+ QCOMPARE(iconUrl, m_page->iconUrl());
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qt144.png")));
+
+ icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QVERIFY(icon.availableSizes().count() >= 1);
+ QVERIFY(icon.availableSizes().contains(QSize(144, 144)));
+}
+
+void tst_QWebEngineFaviconManager::touchIcon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-touch.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::multiIcon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-multi.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ QUrl iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(m_page->iconUrl(), iconUrl);
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qtmulti.ico")));
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+ QCOMPARE(icon.availableSizes().count(), 3);
+ QVERIFY(icon.availableSizes().contains(QSize(16, 16)));
+ QVERIFY(icon.availableSizes().contains(QSize(32, 32)));
+ QVERIFY(icon.availableSizes().contains(QSize(64, 64)));
+}
+
+void tst_QWebEngineFaviconManager::candidateIcon()
+{
+ if (!QDir(TESTS_SOURCE_DIR).exists())
+ W_QSKIP(QString("This test requires access to resources found in '%1'").arg(TESTS_SOURCE_DIR).toLatin1().constData(), SkipAll);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ QUrl url = QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/favicon-shortcut.html"));
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ QUrl iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(m_page->iconUrl(), iconUrl);
+ QCOMPARE(iconUrl, QUrl::fromLocalFile(TESTS_SOURCE_DIR + QLatin1String("qwebenginefaviconmanager/resources/icons/qt144.png")));
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+ QCOMPARE(icon.availableSizes().count(), 2);
+ QVERIFY(icon.availableSizes().contains(QSize(32, 32)));
+ QVERIFY(icon.availableSizes().contains(QSize(144, 144)));
+}
+
+void tst_QWebEngineFaviconManager::downloadIconsDisabled_data()
+{
+ QTest::addColumn<QUrl>("url");
+ QTest::newRow("misc") << QUrl("qrc:/resources/favicon-misc.html");
+ QTest::newRow("shortcut") << QUrl("qrc:/resources/favicon-shortcut.html");
+ QTest::newRow("single") << QUrl("qrc:/resources/favicon-single.html");
+ QTest::newRow("touch") << QUrl("qrc:/resources/favicon-touch.html");
+ QTest::newRow("unavailable") << QUrl("qrc:/resources/favicon-unavailable.html");
+}
+
+void tst_QWebEngineFaviconManager::downloadIconsDisabled()
+{
+ QFETCH(QUrl, url);
+
+ m_page->settings()->setAttribute(QWebEngineSettings::AutoLoadIconsForPage, false);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+
+ QVERIFY(m_page->iconUrl().isEmpty());
+ QVERIFY(m_page->icon().isNull());
+}
+
+void tst_QWebEngineFaviconManager::downloadTouchIconsEnabled_data()
+{
+ QTest::addColumn<QUrl>("url");
+ QTest::addColumn<QUrl>("expectedIconUrl");
+ QTest::addColumn<QSize>("expectedIconSize");
+ QTest::newRow("misc") << QUrl("qrc:/resources/favicon-misc.html") << QUrl("qrc:/resources/icons/qt144.png") << QSize(144, 144);
+ QTest::newRow("shortcut") << QUrl("qrc:/resources/favicon-shortcut.html") << QUrl("qrc:/resources/icons/qt144.png") << QSize(144, 144);
+ QTest::newRow("single") << QUrl("qrc:/resources/favicon-single.html") << QUrl("qrc:/resources/icons/qt32.ico") << QSize(32, 32);
+ QTest::newRow("touch") << QUrl("qrc:/resources/favicon-touch.html") << QUrl("qrc:/resources/icons/qt144.png") << QSize(144, 144);
+}
+
+void tst_QWebEngineFaviconManager::downloadTouchIconsEnabled()
+{
+ QFETCH(QUrl, url);
+ QFETCH(QUrl, expectedIconUrl);
+ QFETCH(QSize, expectedIconSize);
+
+ m_page->settings()->setAttribute(QWebEngineSettings::TouchIconsEnabled, true);
+
+ QSignalSpy loadFinishedSpy(m_page, SIGNAL(loadFinished(bool)));
+ QSignalSpy iconUrlChangedSpy(m_page, SIGNAL(iconUrlChanged(QUrl)));
+ QSignalSpy iconChangedSpy(m_page, SIGNAL(iconChanged(QIcon)));
+
+ m_page->load(url);
+
+ QTRY_COMPARE(loadFinishedSpy.count(), 1);
+ QTRY_COMPARE(iconUrlChangedSpy.count(), 1);
+ QTRY_COMPARE(iconChangedSpy.count(), 1);
+
+ const QUrl &iconUrl = iconUrlChangedSpy.at(0).at(0).toString();
+ QCOMPARE(m_page->iconUrl(), iconUrl);
+ QCOMPARE(iconUrl, expectedIconUrl);
+
+ const QIcon &icon = m_page->icon();
+ QVERIFY(!icon.isNull());
+
+ QVERIFY(icon.availableSizes().count() >= 1);
+ QVERIFY(icon.availableSizes().contains(expectedIconSize));
+}
+
+QTEST_MAIN(tst_QWebEngineFaviconManager)
+
+#include "tst_qwebenginefaviconmanager.moc"
diff --git a/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.qrc b/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.qrc
new file mode 100644
index 000000000..a352f8a83
--- /dev/null
+++ b/tests/auto/widgets/qwebenginefaviconmanager/tst_qwebenginefaviconmanager.qrc
@@ -0,0 +1,14 @@
+<!DOCTYPE RCC><RCC version="1.0">
+<qresource>
+ <file>resources/favicon-misc.html</file>
+ <file>resources/favicon-multi.html</file>
+ <file>resources/favicon-shortcut.html</file>
+ <file>resources/favicon-single.html</file>
+ <file>resources/favicon-touch.html</file>
+ <file>resources/favicon-unavailable.html</file>
+ <file>resources/icons/qt144.png</file>
+ <file>resources/icons/qt32.ico</file>
+ <file>resources/icons/qtmulti.ico</file>
+ <file>resources/test1.html</file>
+</qresource>
+</RCC>
diff --git a/tests/auto/widgets/qwebengineinspector/tst_qwebengineinspector.cpp b/tests/auto/widgets/qwebengineinspector/tst_qwebengineinspector.cpp
index 8d7e41f0f..000214b9a 100644
--- a/tests/auto/widgets/qwebengineinspector/tst_qwebengineinspector.cpp
+++ b/tests/auto/widgets/qwebengineinspector/tst_qwebengineinspector.cpp
@@ -1,21 +1,30 @@
-/*
- Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License as published by the Free Software Foundation; either
- version 2 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtWebEngine module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
#include <QtTest/QtTest>
diff --git a/tests/auto/widgets/qwebenginepage/BLACKLIST b/tests/auto/widgets/qwebenginepage/BLACKLIST
index 045783c94..2b9453b0e 100644
--- a/tests/auto/widgets/qwebenginepage/BLACKLIST
+++ b/tests/auto/widgets/qwebenginepage/BLACKLIST
@@ -1,8 +1,8 @@
[comboBoxPopupPositionAfterMove]
linux
-[geolocationRequestJS]
-*
-
[macCopyUnicodeToClipboard]
osx
+
+[getUserMediaRequest]
+*
diff --git a/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp b/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
index ede50e63f..518713b51 100644
--- a/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
+++ b/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
@@ -1,5 +1,5 @@
/*
- Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
+ Copyright (C) 2016 The Qt Company Ltd.
Copyright (C) 2009 Girish Ramakrishnan <girish@forwardbias.in>
Copyright (C) 2010 Holger Hans Peter Freyther
@@ -20,6 +20,7 @@
*/
#include "../util.h"
+#include <QByteArray>
#include <QClipboard>
#include <QDir>
#include <QGraphicsWidget>
@@ -216,7 +217,6 @@ private Q_SLOTS:
void hitTestContent();
void baseUrl_data();
void baseUrl();
- void renderHints();
void scrollPosition();
void scrollToAnchor();
void scrollbarsOff();
@@ -241,6 +241,8 @@ private Q_SLOTS:
void setZoomFactor();
void mouseButtonTranslation();
+ void printToPdf();
+
private:
static QPoint elementCenter(QWebEnginePage *page, const QString &id);
@@ -421,9 +423,14 @@ void tst_QWebEnginePage::geolocationRequestJS()
W_QSKIP("Geolocation is not supported.", SkipSingle);
}
- evaluateJavaScriptSync(newPage, "var errorCode = 0; function error(err) { errorCode = err.code; } function success(pos) { } navigator.geolocation.getCurrentPosition(success, error)");
+ evaluateJavaScriptSync(newPage, "var errorCode = 0; var done = false; function error(err) { errorCode = err.code; done = true; } function success(pos) { done = true; } navigator.geolocation.getCurrentPosition(success, error)");
+
+ QTRY_VERIFY(evaluateJavaScriptSync(newPage, "done").toBool());
+ int result = evaluateJavaScriptSync(newPage, "errorCode").toInt();
+ if (result == 2)
+ QEXPECT_FAIL("", "No location service available.", Continue);
+ QCOMPARE(result, errorCode);
- QTRY_COMPARE(evaluateJavaScriptSync(newPage, "errorCode").toInt(), errorCode);
delete view;
}
@@ -2886,6 +2893,9 @@ void tst_QWebEnginePage::testJSPrompt()
{
JSPromptPage page;
bool res;
+ QSignalSpy loadSpy(&page, SIGNAL(loadFinished(bool)));
+ page.setHtml(QStringLiteral("<html><body></body></html>"));
+ QTRY_COMPARE(loadSpy.count(), 1);
// OK + QString()
res = evaluateJavaScriptSync(&page,
@@ -3398,9 +3408,9 @@ void tst_QWebEnginePage::loadSignalsOrder()
QFETCH(QUrl, url);
QWebEnginePage page;
SpyForLoadSignalsOrder loadSpy(&page);
- waitForSignal(&loadSpy, SIGNAL(started()));
+ waitForSignal(&loadSpy, SIGNAL(started()), 500);
page.load(url);
- QTRY_VERIFY(loadSpy.isFinished());
+ QTRY_VERIFY_WITH_TIMEOUT(loadSpy.isFinished(), 500);
}
void tst_QWebEnginePage::undoActionHaveCustomText()
@@ -4209,167 +4219,30 @@ void tst_QWebEnginePage::baseUrl()
QCOMPARE(baseUrlSync(m_page), baseUrl);
}
-class DummyPaintEngine: public QPaintEngine {
-public:
-
- DummyPaintEngine()
- : QPaintEngine(QPaintEngine::AllFeatures)
- , renderHints(0)
- {
- }
-
- bool begin(QPaintDevice*)
- {
- setActive(true);
- return true;
- }
-
- bool end()
- {
- setActive(false);
- return false;
- }
-
- void updateState(const QPaintEngineState& state)
- {
- renderHints = state.renderHints();
- }
-
- void drawPath(const QPainterPath&) { }
- void drawPixmap(const QRectF&, const QPixmap&, const QRectF&) { }
-
- QPaintEngine::Type type() const
- {
- return static_cast<QPaintEngine::Type>(QPaintEngine::User + 2);
- }
-
- QPainter::RenderHints renderHints;
-};
-
-class DummyPaintDevice: public QPaintDevice {
-public:
- DummyPaintDevice()
- : QPaintDevice()
- , m_engine(new DummyPaintEngine)
- {
- }
-
- ~DummyPaintDevice()
- {
- delete m_engine;
- }
-
- QPaintEngine* paintEngine() const
- {
- return m_engine;
- }
-
- QPainter::RenderHints renderHints() const
- {
- return m_engine->renderHints;
- }
-
-protected:
- int metric(PaintDeviceMetric metric) const;
-
-private:
- DummyPaintEngine* m_engine;
- friend class DummyPaintEngine;
-};
-
-
-int DummyPaintDevice::metric(PaintDeviceMetric metric) const
-{
- switch (metric) {
- case PdmWidth:
- return 400;
- break;
-
- case PdmHeight:
- return 200;
- break;
-
- case PdmNumColors:
- return INT_MAX;
- break;
-
- case PdmDepth:
- return 32;
- break;
-
- default:
- break;
- }
- return 0;
-}
-
-void tst_QWebEnginePage::renderHints()
-{
-#if !defined(QWEBENGINEPAGE_RENDER)
- QSKIP("QWEBENGINEPAGE_RENDER");
-#else
- QString html("<html><body><p>Hello, world!</p></body></html>");
-
- QWebEnginePage page;
- page.setHtml(html);
- page.setViewportSize(page.contentsSize());
-
- // We will call frame->render and trap the paint engine state changes
- // to ensure that GraphicsContext does not clobber the render hints.
- DummyPaintDevice buffer;
- QPainter painter(&buffer);
-
- painter.setRenderHint(QPainter::TextAntialiasing, false);
- page.render(&painter);
- QVERIFY(!(buffer.renderHints() & QPainter::TextAntialiasing));
- QVERIFY(!(buffer.renderHints() & QPainter::SmoothPixmapTransform));
- QVERIFY(!(buffer.renderHints() & QPainter::HighQualityAntialiasing));
-
- painter.setRenderHint(QPainter::TextAntialiasing, true);
- page.render(&painter);
- QVERIFY(buffer.renderHints() & QPainter::TextAntialiasing);
- QVERIFY(!(buffer.renderHints() & QPainter::SmoothPixmapTransform));
- QVERIFY(!(buffer.renderHints() & QPainter::HighQualityAntialiasing));
-
- painter.setRenderHint(QPainter::SmoothPixmapTransform, true);
- page.render(&painter);
- QVERIFY(buffer.renderHints() & QPainter::TextAntialiasing);
- QVERIFY(buffer.renderHints() & QPainter::SmoothPixmapTransform);
- QVERIFY(!(buffer.renderHints() & QPainter::HighQualityAntialiasing));
-
- painter.setRenderHint(QPainter::HighQualityAntialiasing, true);
- page.render(&painter);
- QVERIFY(buffer.renderHints() & QPainter::TextAntialiasing);
- QVERIFY(buffer.renderHints() & QPainter::SmoothPixmapTransform);
- QVERIFY(buffer.renderHints() & QPainter::HighQualityAntialiasing);
-#endif
-}
-
void tst_QWebEnginePage::scrollPosition()
{
-#if !defined(QWEBENGINEPAGE_EVALUATEJAVASCRIPT)
- QSKIP("QWEBENGINEPAGE_EVALUATEJAVASCRIPT");
-#else
// enlarged image in a small viewport, to provoke the scrollbars to appear
QString html("<html><body><img src='qrc:/image.png' height=500 width=500/></body></html>");
- QWebEnginePage page;
- page.setViewportSize(QSize(200, 200));
+ QWebEngineView view;
+ view.setFixedSize(200,200);
+ view.show();
- page.setHtml(html);
- page.setScrollBarPolicy(Qt::Vertical, Qt::ScrollBarAlwaysOff);
- page.setScrollBarPolicy(Qt::Horizontal, Qt::ScrollBarAlwaysOff);
+ QTest::qWaitForWindowExposed(&view);
+
+ QSignalSpy loadSpy(view.page(), SIGNAL(loadFinished(bool)));
+ view.setHtml(html);
+ QTRY_COMPARE(loadSpy.count(), 1);
// try to set the scroll offset programmatically
- page.setScrollPosition(QPoint(23, 29));
- QCOMPARE(page.scrollPosition().x(), 23);
- QCOMPARE(page.scrollPosition().y(), 29);
+ view.page()->runJavaScript("window.scrollTo(23, 29);");
+ QTRY_COMPARE(view.page()->scrollPosition().x(), qreal(23));
+ QCOMPARE(view.page()->scrollPosition().y(), qreal(29));
- int x = page.evaluateJavaScript("window.scrollX").toInt();
- int y = page.evaluateJavaScript("window.scrollY").toInt();
+ int x = evaluateJavaScriptSync(view.page(), "window.scrollX").toInt();
+ int y = evaluateJavaScriptSync(view.page(), "window.scrollY").toInt();
QCOMPARE(x, 23);
QCOMPARE(y, 29);
-#endif
}
void tst_QWebEnginePage::scrollToAnchor()
@@ -5053,6 +4926,37 @@ void tst_QWebEnginePage::setZoomFactor()
delete page;
}
+void tst_QWebEnginePage::printToPdf()
+{
+ QTemporaryDir tempDir(QDir::tempPath() + "/tst_qwebengineview-XXXXXX");
+ QVERIFY(tempDir.isValid());
+ QWebEnginePage page;
+ QSignalSpy spy(&page, SIGNAL(loadFinished(bool)));
+ page.load(QUrl("qrc:///resources/basic_printing_page.html"));
+ QTRY_VERIFY(spy.count() == 1);
+
+ QPageLayout layout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF(0.0, 0.0, 0.0, 0.0));
+ QString path = tempDir.path() + "/print_1_success.pdf";
+ page.printToPdf(path, layout);
+ QTRY_VERIFY(QFile::exists(path));
+
+#if !defined(Q_OS_WIN)
+ path = tempDir.path() + "/print_//2_failed.pdf";
+#else
+ path = tempDir.path() + "/print_|2_failed.pdf";
+#endif
+ page.printToPdf(path, QPageLayout());
+ QTRY_VERIFY(!QFile::exists(path));
+
+ CallbackSpy<QByteArray> successfulSpy;
+ page.printToPdf(successfulSpy.ref(), layout);
+ QVERIFY(successfulSpy.waitForResult().length() > 0);
+
+ CallbackSpy<QByteArray> failedInvalidLayoutSpy;
+ page.printToPdf(failedInvalidLayoutSpy.ref(), QPageLayout());
+ QCOMPARE(failedInvalidLayoutSpy.waitForResult().length(), 0);
+}
+
void tst_QWebEnginePage::mouseButtonTranslation()
{
QWebEngineView *view = new QWebEngineView;
diff --git a/tests/auto/widgets/qwebengineprofile/BLACKLIST b/tests/auto/widgets/qwebengineprofile/BLACKLIST
new file mode 100644
index 000000000..fc1c957dd
--- /dev/null
+++ b/tests/auto/widgets/qwebengineprofile/BLACKLIST
@@ -0,0 +1,5 @@
+[clearDataFromCache]
+*
+[disableCache]
+*
+
diff --git a/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp b/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
index 23a56a9cb..579a0f776 100644
--- a/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
+++ b/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
@@ -1,34 +1,26 @@
/****************************************************************************
**
-** Copyright (C) 2015 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the QtWebEngine module of the Qt Toolkit.
**
-** $QT_BEGIN_LICENSE:LGPL$
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
-** and conditions see http://www.qt.io/terms-conditions. For further
-** information use the contact form at http://www.qt.io/contact-us.
-**
-** GNU Lesser General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU Lesser
-** General Public License version 3 as published by the Free Software
-** Foundation and appearing in the file LICENSE.LGPLv3 included in the
-** packaging of this file. Please review the following information to
-** ensure the GNU Lesser General Public License version 3 requirements
-** will be met: https://www.gnu.org/licenses/lgpl.html.
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
-** General Public License version 2.0 or later as published by the Free
-** Software Foundation and appearing in the file LICENSE.GPL included in
-** the packaging of this file. Please review the following information to
-** ensure the GNU General Public License version 2.0 requirements will be
-** met: http://www.gnu.org/licenses/gpl-2.0.html.
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
@@ -40,6 +32,7 @@
#include <QtWebEngineCore/qwebengineurlrequestjob.h>
#include <QtWebEngineCore/qwebengineurlschemehandler.h>
#include <QtWebEngineWidgets/qwebengineprofile.h>
+#include <QtWebEngineWidgets/qwebenginepage.h>
#include <QtWebEngineWidgets/qwebenginesettings.h>
#include <QtWebEngineWidgets/qwebengineview.h>
#include <QtWebEngineWidgets/qwebenginedownloaditem.h>
@@ -51,8 +44,11 @@ class tst_QWebEngineProfile : public QObject
private Q_SLOTS:
void defaultProfile();
void profileConstructors();
+ void clearDataFromCache();
+ void disableCache();
void urlSchemeHandlers();
void urlSchemeHandlerFailRequest();
+ void urlSchemeHandlerFailOnRead();
void customUserAgent();
void httpAcceptLanguage();
void downloadItem();
@@ -80,7 +76,77 @@ void tst_QWebEngineProfile::profileConstructors()
QCOMPARE(diskProfile.httpCacheType(), QWebEngineProfile::DiskHttpCache);
QCOMPARE(otrProfile.persistentCookiesPolicy(), QWebEngineProfile::NoPersistentCookies);
QCOMPARE(diskProfile.persistentCookiesPolicy(), QWebEngineProfile::AllowPersistentCookies);
+}
+
+void tst_QWebEngineProfile::clearDataFromCache()
+{
+ QWebEnginePage page;
+
+ QDir cacheDir("./tst_QWebEngineProfile_cacheDir");
+ cacheDir.makeAbsolute();
+ if (cacheDir.exists())
+ cacheDir.removeRecursively();
+ cacheDir.mkpath(cacheDir.path());
+
+ QWebEngineProfile *profile = page.profile();
+ profile->setCachePath(cacheDir.path());
+ profile->setHttpCacheType(QWebEngineProfile::DiskHttpCache);
+
+ QSignalSpy loadFinishedSpy(&page, SIGNAL(loadFinished(bool)));
+ page.load(QUrl("http://qt-project.org"));
+ if (!loadFinishedSpy.wait(10000) || !loadFinishedSpy.at(0).at(0).toBool())
+ QSKIP("Couldn't load page from network, skipping test.");
+
+ cacheDir.refresh();
+ QVERIFY(cacheDir.entryList().contains("Cache"));
+ cacheDir.cd("./Cache");
+ int filesBeforeClear = cacheDir.entryList().count();
+
+ QFileSystemWatcher fileSystemWatcher;
+ fileSystemWatcher.addPath(cacheDir.path());
+ QSignalSpy directoryChangedSpy(&fileSystemWatcher, SIGNAL(directoryChanged(const QString &)));
+
+ // It deletes most of the files, but not all of them.
+ profile->clearHttpCache();
+ QTest::qWait(1000);
+ QTRY_VERIFY(directoryChangedSpy.count() > 0);
+
+ cacheDir.refresh();
+ QVERIFY(filesBeforeClear > cacheDir.entryList().count());
+ cacheDir.removeRecursively();
+}
+
+void tst_QWebEngineProfile::disableCache()
+{
+ QWebEnginePage page;
+ QDir cacheDir("./tst_QWebEngineProfile_cacheDir");
+ if (cacheDir.exists())
+ cacheDir.removeRecursively();
+ cacheDir.mkpath(cacheDir.path());
+
+ QWebEngineProfile *profile = page.profile();
+ profile->setCachePath(cacheDir.path());
+ QVERIFY(!cacheDir.entryList().contains("Cache"));
+
+ profile->setHttpCacheType(QWebEngineProfile::NoCache);
+ QSignalSpy loadFinishedSpy(&page, SIGNAL(loadFinished(bool)));
+ page.load(QUrl("http://qt-project.org"));
+ if (!loadFinishedSpy.wait(10000) || !loadFinishedSpy.at(0).at(0).toBool())
+ QSKIP("Couldn't load page from network, skipping test.");
+
+ cacheDir.refresh();
+ QVERIFY(!cacheDir.entryList().contains("Cache"));
+
+ profile->setHttpCacheType(QWebEngineProfile::DiskHttpCache);
+ page.load(QUrl("http://qt-project.org"));
+ if (!loadFinishedSpy.wait(10000) || !loadFinishedSpy.at(1).at(0).toBool())
+ QSKIP("Couldn't load page from network, skipping test.");
+
+ cacheDir.refresh();
+ QVERIFY(cacheDir.entryList().contains("Cache"));
+
+ cacheDir.removeRecursively();
}
class RedirectingUrlSchemeHandler : public QWebEngineUrlSchemeHandler
@@ -174,10 +240,47 @@ class FailingUrlSchemeHandler : public QWebEngineUrlSchemeHandler
public:
void requestStarted(QWebEngineUrlRequestJob *job) override
{
- job->fail(QWebEngineUrlRequestJob::RequestFailed);
+ job->fail(QWebEngineUrlRequestJob::UrlInvalid);
+ }
+};
+
+class FailingIODevice : public QIODevice
+{
+public:
+ FailingIODevice(QWebEngineUrlRequestJob *job) : m_job(job)
+ {
+ }
+
+ qint64 readData(char *, qint64) Q_DECL_OVERRIDE
+ {
+ m_job->fail(QWebEngineUrlRequestJob::RequestFailed);
+ return -1;
+ }
+ qint64 writeData(const char *, qint64) Q_DECL_OVERRIDE
+ {
+ m_job->fail(QWebEngineUrlRequestJob::RequestFailed);
+ return -1;
+ }
+ void close() Q_DECL_OVERRIDE
+ {
+ QIODevice::close();
+ deleteLater();
+ }
+
+private:
+ QWebEngineUrlRequestJob *m_job;
+};
+
+class FailOnReadUrlSchemeHandler : public QWebEngineUrlSchemeHandler
+{
+public:
+ void requestStarted(QWebEngineUrlRequestJob *job) override
+ {
+ job->reply(QByteArrayLiteral("text/plain"), new FailingIODevice(job));
}
};
+
void tst_QWebEngineProfile::urlSchemeHandlerFailRequest()
{
FailingUrlSchemeHandler handler;
@@ -192,6 +295,20 @@ void tst_QWebEngineProfile::urlSchemeHandlerFailRequest()
QCOMPARE(toPlainTextSync(view.page()), QString());
}
+void tst_QWebEngineProfile::urlSchemeHandlerFailOnRead()
+{
+ FailOnReadUrlSchemeHandler handler;
+ QWebEngineProfile profile;
+ profile.installUrlSchemeHandler("foo", &handler);
+ QWebEngineView view;
+ QSignalSpy loadFinishedSpy(&view, SIGNAL(loadFinished(bool)));
+ view.setPage(new QWebEnginePage(&profile, &view));
+ view.settings()->setAttribute(QWebEngineSettings::ErrorPageEnabled, false);
+ view.load(QUrl(QStringLiteral("foo://bar")));
+ QVERIFY(loadFinishedSpy.wait());
+ QCOMPARE(toPlainTextSync(view.page()), QString());
+}
+
void tst_QWebEngineProfile::customUserAgent()
{
QString defaultUserAgent = QWebEngineProfile::defaultProfile()->httpUserAgent();
diff --git a/tests/auto/widgets/qwebenginescript/tst_qwebenginescript.cpp b/tests/auto/widgets/qwebenginescript/tst_qwebenginescript.cpp
index 53762f54c..d5ecd8841 100644
--- a/tests/auto/widgets/qwebenginescript/tst_qwebenginescript.cpp
+++ b/tests/auto/widgets/qwebenginescript/tst_qwebenginescript.cpp
@@ -24,6 +24,7 @@
#include <qwebenginescriptcollection.h>
#include <qwebengineview.h>
#include "../util.h"
+#include <QWebChannel>
class tst_QWebEngineScript: public QObject {
Q_OBJECT
@@ -34,7 +35,9 @@ private Q_SLOTS:
void injectionPoint_data();
void scriptWorld();
void scriptModifications();
-
+ void webChannel_data();
+ void webChannel();
+ void noTransportWithoutWebChannel();
};
void tst_QWebEngineScript::domEditing()
@@ -115,12 +118,14 @@ void tst_QWebEngineScript::scriptWorld()
page.load(QUrl("about:blank"));
waitForSignal(&page, SIGNAL(loadFinished(bool)));
QCOMPARE(evaluateJavaScriptSync(&page, "typeof(userScriptTest) != \"undefined\" && userScriptTest == 1;"), QVariant::fromValue(true));
+ QCOMPARE(evaluateJavaScriptSyncInWorld(&page, "typeof(userScriptTest) == \"undefined\"", QWebEngineScript::ApplicationWorld), QVariant::fromValue(true));
script.setWorldId(QWebEngineScript::ApplicationWorld);
page.scripts().clear();
page.scripts().insert(script);
page.load(QUrl("about:blank"));
waitForSignal(&page, SIGNAL(loadFinished(bool)));
QCOMPARE(evaluateJavaScriptSync(&page, "typeof(userScriptTest) == \"undefined\""), QVariant::fromValue(true));
+ QCOMPARE(evaluateJavaScriptSyncInWorld(&page, "typeof(userScriptTest) != \"undefined\" && userScriptTest == 1;", QWebEngineScript::ApplicationWorld), QVariant::fromValue(true));
}
void tst_QWebEngineScript::scriptModifications()
@@ -148,6 +153,92 @@ void tst_QWebEngineScript::scriptModifications()
QVERIFY(page.scripts().count() == 0);
}
+class TestObject : public QObject
+{
+ Q_OBJECT
+ Q_PROPERTY(QString text READ text WRITE setText NOTIFY textChanged)
+public:
+ TestObject(QObject *parent = 0) : QObject(parent) { }
+
+ void setText(const QString &text)
+ {
+ if (text == m_text)
+ return;
+ m_text = text;
+ emit textChanged(text);
+ }
+
+ QString text() const { return m_text; }
+
+signals:
+ void textChanged(const QString &text);
+
+private:
+ QString m_text;
+};
+
+
+void tst_QWebEngineScript::webChannel_data()
+{
+ QTest::addColumn<int>("worldId");
+ QTest::addColumn<bool>("reloadFirst");
+ QTest::newRow("MainWorld") << static_cast<int>(QWebEngineScript::MainWorld) << false;
+ QTest::newRow("ApplicationWorld") << static_cast<int>(QWebEngineScript::ApplicationWorld) << false;
+ QTest::newRow("MainWorldWithReload") << static_cast<int>(QWebEngineScript::MainWorld) << true;
+ QTest::newRow("ApplicationWorldWithReload") << static_cast<int>(QWebEngineScript::ApplicationWorld) << true;
+}
+
+void tst_QWebEngineScript::webChannel()
+{
+ QFETCH(int, worldId);
+ QFETCH(bool, reloadFirst);
+ QWebEnginePage page;
+ TestObject testObject;
+ QScopedPointer<QWebChannel> channel(new QWebChannel(this));
+ channel->registerObject(QStringLiteral("object"), &testObject);
+ page.setWebChannel(channel.data(), worldId);
+
+ QFile qwebchanneljs(":/qwebchannel.js");
+ QVERIFY(qwebchanneljs.exists());
+ qwebchanneljs.open(QFile::ReadOnly);
+ QByteArray scriptSrc = qwebchanneljs.readAll();
+ qwebchanneljs.close();
+ QWebEngineScript script;
+ script.setInjectionPoint(QWebEngineScript::DocumentCreation);
+ script.setWorldId(worldId);
+ script.setSourceCode(QString::fromLatin1(scriptSrc));
+ page.scripts().insert(script);
+ page.setHtml(QStringLiteral("<html><body></body></html>"));
+ waitForSignal(&page, SIGNAL(loadFinished(bool)));
+ if (reloadFirst) {
+ // Check that the transport is also reinstalled on navigation
+ page.triggerAction(QWebEnginePage::Reload);
+ waitForSignal(&page, SIGNAL(loadFinished(bool)));
+ }
+ page.runJavaScript(QLatin1String(
+ "new QWebChannel(qt.webChannelTransport,"
+ " function(channel) {"
+ " channel.objects.object.text = 'test';"
+ " }"
+ ");"), worldId);
+ waitForSignal(&testObject, SIGNAL(textChanged(QString)));
+ QCOMPARE(testObject.text(), QStringLiteral("test"));
+
+ if (worldId != QWebEngineScript::MainWorld)
+ QCOMPARE(evaluateJavaScriptSync(&page, "qt.webChannelTransport"), QVariant(QVariant::Invalid));
+}
+
+void tst_QWebEngineScript::noTransportWithoutWebChannel()
+{
+ QWebEnginePage page;
+ page.setHtml(QStringLiteral("<html><body></body></html>"));
+
+ QCOMPARE(evaluateJavaScriptSync(&page, "qt.webChannelTransport"), QVariant(QVariant::Invalid));
+ page.triggerAction(QWebEnginePage::Reload);
+ waitForSignal(&page, SIGNAL(loadFinished(bool)));
+ QCOMPARE(evaluateJavaScriptSync(&page, "qt.webChannelTransport"), QVariant(QVariant::Invalid));
+}
+
QTEST_MAIN(tst_QWebEngineScript)
#include "tst_qwebenginescript.moc"
diff --git a/tests/auto/widgets/qwebenginespellcheck/dict/en-US.aff b/tests/auto/widgets/qwebenginespellcheck/dict/en-US.aff
new file mode 100644
index 000000000..ff8185771
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/dict/en-US.aff
@@ -0,0 +1,5 @@
+SET UTF-8
+TRY esianrtolcdugmphbyfvkwzqESIANRTOLCDUGMPHBYFVKWZQ
+
+PFX Q Y 1
+PFX Q 0 q .
diff --git a/tests/auto/widgets/qwebenginespellcheck/dict/en-US.dic b/tests/auto/widgets/qwebenginespellcheck/dict/en-US.dic
new file mode 100644
index 000000000..3d4ecdfa4
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/dict/en-US.dic
@@ -0,0 +1,11 @@
+10
+he/Q
+I/Q
+it/Q
+love/Q
+loves/Q
+qt/Q
+she/Q
+they/Q
+we/Q
+you/Q
diff --git a/tests/auto/widgets/qwebenginespellcheck/qwebenginespellcheck.pro b/tests/auto/widgets/qwebenginespellcheck/qwebenginespellcheck.pro
new file mode 100644
index 000000000..437aad937
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/qwebenginespellcheck.pro
@@ -0,0 +1,22 @@
+include(../tests.pri)
+
+DISTFILES += \
+ dict/en-US.dic \
+ dict/en-US.aff
+
+qtPrepareTool(CONVERT_TOOL, qwebengine_convert_dict)
+
+debug_and_release {
+ CONFIG(debug, debug|release): DICTIONARIES_DIR = debug/qtwebengine_dictionaries
+ else: DICTIONARIES_DIR = release/qtwebengine_dictionaries
+} else {
+ DICTIONARIES_DIR = qtwebengine_dictionaries
+}
+
+dict.files = $$PWD/dict/en-US.dic
+dictoolbuild.input = dict.files
+dictoolbuild.output = $${DICTIONARIES_DIR}/${QMAKE_FILE_BASE}.bdic
+dictoolbuild.commands = $${CONVERT_TOOL} ${QMAKE_FILE_IN} ${QMAKE_FILE_OUT}
+dictoolbuild.name = Build ${QMAKE_FILE_IN_BASE}
+dictoolbuild.CONFIG = no_link target_predeps
+QMAKE_EXTRA_COMPILERS += dictoolbuild
diff --git a/tests/auto/widgets/qwebenginespellcheck/resources/index.html b/tests/auto/widgets/qwebenginespellcheck/resources/index.html
new file mode 100644
index 000000000..520979244
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/resources/index.html
@@ -0,0 +1,36 @@
+<html>
+ <head>
+ <script type="text/javascript">
+ function makeEditable()
+ {
+ document.getElementsByClassName('textarea')[0].contentEditable = true;
+ }
+
+ function text()
+ {
+ return document.getElementsByClassName('textarea')[0].innerHTML;
+ }
+
+ function findWordPosition(text,word)
+ {
+ var divElement = document.getElementsByClassName('textarea')[0];
+ divElement.innerHTML = text;
+ var regex = new RegExp(word,'g');
+ divElement.innerHTML = divElement.innerHTML.replace(regex, '<span id="word">' + word + '</span>');
+ var spanElement = document.getElementById('word');
+ var rect = spanElement.getBoundingClientRect();
+ var array = new Array();
+ array.push(rect.left);
+ array.push(rect.top);
+ array.push(rect.right - rect.left);
+ array.push(rect.bottom - rect.top);
+ divElement.innerHTML = "";
+ return array;
+ }
+ </script>
+ </head>
+ <body>
+ <div class="textarea" style="width:300px; height:200px; border: 1px solid #ccc"></div>
+ </body>
+</html>
+
diff --git a/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.cpp b/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.cpp
new file mode 100644
index 000000000..2dfe3305d
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.cpp
@@ -0,0 +1,178 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtWebEngine module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "util.h"
+#include <QtTest/QtTest>
+#include <QtWebEngineWidgets/qwebenginecontextmenudata.h>
+#include <QtWebEngineWidgets/qwebengineprofile.h>
+#include <QtWebEngineWidgets/qwebenginepage.h>
+#include <QtWebEngineWidgets/qwebengineview.h>
+
+class WebView : public QWebEngineView
+{
+ Q_OBJECT
+public:
+ void activateMenu(const QPoint &position)
+ {
+ QTest::mouseMove(focusWidget(), position);
+ QTest::mousePress(focusWidget(), Qt::RightButton, 0, position);
+ QContextMenuEvent evcont(QContextMenuEvent::Mouse, position, mapToGlobal(position));
+ event(&evcont);
+ }
+
+ const QWebEngineContextMenuData& data()
+ {
+ return m_data;
+ }
+
+signals:
+ void menuReady();
+
+protected:
+ void contextMenuEvent(QContextMenuEvent *)
+ {
+ m_data = page()->contextMenuData();
+ emit menuReady();
+ }
+private:
+ QWebEngineContextMenuData m_data;
+};
+
+class tst_QWebEngineSpellcheck : public QObject
+{
+ Q_OBJECT
+
+private Q_SLOTS:
+ void init();
+ void cleanup();
+ void initTestCase();
+ void spellCheckLanguage();
+ void spellCheckEnabled();
+ void spellcheck();
+
+private:
+ void load();
+ WebView *m_view;
+};
+
+void tst_QWebEngineSpellcheck::initTestCase()
+{
+ QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
+ QVERIFY(profile);
+ QVERIFY(!profile->isSpellCheckEnabled());
+ QVERIFY(profile->spellCheckLanguage().isEmpty());
+}
+
+void tst_QWebEngineSpellcheck::init()
+{
+ QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
+ profile->setSpellCheckEnabled(false);
+ profile->setSpellCheckLanguage(QString::null);
+ m_view = new WebView();
+}
+
+void tst_QWebEngineSpellcheck::load()
+{
+ m_view->page()->load(QUrl("qrc:///resources/index.html"));
+ m_view->show();
+ waitForSignal(m_view->page(), SIGNAL(loadFinished(bool)));
+}
+
+void tst_QWebEngineSpellcheck::cleanup()
+{
+ delete m_view;
+}
+
+void tst_QWebEngineSpellcheck::spellCheckLanguage()
+{
+ QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
+ QVERIFY(profile);
+ profile->setSpellCheckLanguage("en-US");
+ QVERIFY(profile->spellCheckLanguage() == "en-US");
+}
+
+void tst_QWebEngineSpellcheck::spellCheckEnabled()
+{
+ QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
+ QVERIFY(profile);
+ profile->setSpellCheckEnabled(true);
+ QVERIFY(profile->isSpellCheckEnabled());
+}
+
+void tst_QWebEngineSpellcheck::spellcheck()
+{
+ QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
+ QVERIFY(profile);
+ profile->setSpellCheckLanguage("en-US");
+ profile->setSpellCheckEnabled(true);
+ load();
+
+ // make textarea editable
+ evaluateJavaScriptSync(m_view->page(), "makeEditable();");
+
+ // calcuate position of misspelled word
+ QVariantList list = evaluateJavaScriptSync(m_view->page(), "findWordPosition('I lovee Qt ....','lovee');").toList();
+ QRect rect(list[0].value<int>(),list[1].value<int>(),list[2].value<int>(),list[3].value<int>());
+
+ //type text, spellchecker needs time
+ QTest::mouseMove(m_view->focusWidget(), QPoint(20,20));
+ QTest::mousePress(m_view->focusWidget(), Qt::LeftButton, 0, QPoint(20,20));
+ QString text("I lovee Qt ....");
+ for (int i = 0; i < text.length(); i++) {
+ QTest::keyClicks(m_view->focusWidget(), text.at(i));
+ QTest::qWait(60);
+ }
+
+ // make sure text is there
+ QString result = evaluateJavaScriptSync(m_view->page(), "text();").toString();
+ QVERIFY(result == text);
+
+ // open menu on misspelled word
+ m_view->activateMenu(rect.center());
+ waitForSignal(m_view, SIGNAL(menuReady()));
+
+ // check if menu is valid
+ QVERIFY(m_view->data().isValid());
+ QVERIFY(m_view->data().isContentEditable());
+
+ // check misspelled word
+ QVERIFY(m_view->data().misspelledWord() == "lovee");
+
+ // check suggestions
+ QStringList expected {"love", "loves"};
+ QVERIFY(m_view->data().spellCheckerSuggestions() == expected);
+
+ // check replace word
+ m_view->page()->replaceMisspelledWord("love");
+ text = "I love Qt ....";
+ result = evaluateJavaScriptSync(m_view->page(), "text();").toString();
+ QVERIFY(result == text);
+}
+
+QTEST_MAIN(tst_QWebEngineSpellcheck)
+#include "tst_qwebenginespellcheck.moc"
diff --git a/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.qrc b/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.qrc
new file mode 100644
index 000000000..505b932c7
--- /dev/null
+++ b/tests/auto/widgets/qwebenginespellcheck/tst_qwebenginespellcheck.qrc
@@ -0,0 +1,5 @@
+<RCC>
+ <qresource prefix="/">
+ <file>resources/index.html</file>
+ </qresource>
+</RCC>
diff --git a/tests/auto/widgets/qwebengineview/resources/basic_printing_page.html b/tests/auto/widgets/qwebengineview/resources/basic_printing_page.html
new file mode 100644
index 000000000..0c6ff379f
--- /dev/null
+++ b/tests/auto/widgets/qwebengineview/resources/basic_printing_page.html
@@ -0,0 +1,8 @@
+<html>
+<head>
+<title> Basic Printing Page </title>
+</head>
+<body>
+<h1>Hello Paper World</h1>
+</body>
+</html>
diff --git a/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp b/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
index e66bf18cd..afb53ba20 100644
--- a/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
+++ b/tests/auto/widgets/qwebengineview/tst_qwebengineview.cpp
@@ -1,5 +1,5 @@
/*
- Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies)
+ Copyright (C) 2016 The Qt Company Ltd.
Copyright (C) 2009 Torch Mobile Inc.
Copyright (C) 2009 Girish Ramakrishnan <girish@forwardbias.in>
@@ -23,12 +23,14 @@
#include "../util.h"
#include <qpainter.h>
+#include <qpagelayout.h>
#include <qwebengineview.h>
#include <qwebenginepage.h>
#include <qwebenginesettings.h>
#include <qnetworkrequest.h>
#include <qdiriterator.h>
#include <qstackedlayout.h>
+#include <qtemporarydir.h>
#define VERIFY_INPUTMETHOD_HINTS(actual, expect) \
QVERIFY(actual == expect);
diff --git a/tests/auto/widgets/qwebengineview/tst_qwebengineview.qrc b/tests/auto/widgets/qwebengineview/tst_qwebengineview.qrc
index 6685a8086..b32b533c2 100644
--- a/tests/auto/widgets/qwebengineview/tst_qwebengineview.qrc
+++ b/tests/auto/widgets/qwebengineview/tst_qwebengineview.qrc
@@ -1,8 +1,9 @@
-<!DOCTYPE RCC><RCC version="1.0">
-<qresource>
- <file>resources/index.html</file>
- <file>resources/frame_a.html</file>
- <file>resources/input_types.html</file>
- <file>resources/scrolltest_page.html</file>
-</qresource>
+<RCC>
+ <qresource prefix="/">
+ <file>resources/index.html</file>
+ <file>resources/frame_a.html</file>
+ <file>resources/input_types.html</file>
+ <file>resources/scrolltest_page.html</file>
+ <file>resources/basic_printing_page.html</file>
+ </qresource>
</RCC>
diff --git a/tests/auto/widgets/resources/qwebchannel.js b/tests/auto/widgets/resources/qwebchannel.js
new file mode 100644
index 000000000..1da8f5496
--- /dev/null
+++ b/tests/auto/widgets/resources/qwebchannel.js
@@ -0,0 +1,408 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2014 Klarälvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author Milian Wolff <milian.wolff@kdab.com>
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtWebChannel module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+"use strict";
+
+var QWebChannelMessageTypes = {
+ signal: 1,
+ propertyUpdate: 2,
+ init: 3,
+ idle: 4,
+ debug: 5,
+ invokeMethod: 6,
+ connectToSignal: 7,
+ disconnectFromSignal: 8,
+ setProperty: 9,
+ response: 10,
+};
+
+var QWebChannel = function(transport, initCallback)
+{
+ if (typeof transport !== "object" || typeof transport.send !== "function") {
+ console.error("The QWebChannel expects a transport object with a send function and onmessage callback property." +
+ " Given is: transport: " + typeof(transport) + ", transport.send: " + typeof(transport.send));
+ return;
+ }
+
+ var channel = this;
+ this.transport = transport;
+
+ this.send = function(data)
+ {
+ if (typeof(data) !== "string") {
+ data = JSON.stringify(data);
+ }
+ channel.transport.send(data);
+ }
+
+ this.transport.onmessage = function(message)
+ {
+ var data = message.data;
+ if (typeof data === "string") {
+ data = JSON.parse(data);
+ }
+ switch (data.type) {
+ case QWebChannelMessageTypes.signal:
+ channel.handleSignal(data);
+ break;
+ case QWebChannelMessageTypes.response:
+ channel.handleResponse(data);
+ break;
+ case QWebChannelMessageTypes.propertyUpdate:
+ channel.handlePropertyUpdate(data);
+ break;
+ default:
+ console.error("invalid message received:", message.data);
+ break;
+ }
+ }
+
+ this.execCallbacks = {};
+ this.execId = 0;
+ this.exec = function(data, callback)
+ {
+ if (!callback) {
+ // if no callback is given, send directly
+ channel.send(data);
+ return;
+ }
+ if (channel.execId === Number.MAX_VALUE) {
+ // wrap
+ channel.execId = Number.MIN_VALUE;
+ }
+ if (data.hasOwnProperty("id")) {
+ console.error("Cannot exec message with property id: " + JSON.stringify(data));
+ return;
+ }
+ data.id = channel.execId++;
+ channel.execCallbacks[data.id] = callback;
+ channel.send(data);
+ };
+
+ this.objects = {};
+
+ this.handleSignal = function(message)
+ {
+ var object = channel.objects[message.object];
+ if (object) {
+ object.signalEmitted(message.signal, message.args);
+ } else {
+ console.warn("Unhandled signal: " + message.object + "::" + message.signal);
+ }
+ }
+
+ this.handleResponse = function(message)
+ {
+ if (!message.hasOwnProperty("id")) {
+ console.error("Invalid response message received: ", JSON.stringify(message));
+ return;
+ }
+ channel.execCallbacks[message.id](message.data);
+ delete channel.execCallbacks[message.id];
+ }
+
+ this.handlePropertyUpdate = function(message)
+ {
+ for (var i in message.data) {
+ var data = message.data[i];
+ var object = channel.objects[data.object];
+ if (object) {
+ object.propertyUpdate(data.signals, data.properties);
+ } else {
+ console.warn("Unhandled property update: " + data.object + "::" + data.signal);
+ }
+ }
+ channel.exec({type: QWebChannelMessageTypes.idle});
+ }
+
+ this.debug = function(message)
+ {
+ channel.send({type: QWebChannelMessageTypes.debug, data: message});
+ };
+
+ channel.exec({type: QWebChannelMessageTypes.init}, function(data) {
+ for (var objectName in data) {
+ var object = new QObject(objectName, data[objectName], channel);
+ }
+ // now unwrap properties, which might reference other registered objects
+ for (var objectName in channel.objects) {
+ channel.objects[objectName].unwrapProperties();
+ }
+ if (initCallback) {
+ initCallback(channel);
+ }
+ channel.exec({type: QWebChannelMessageTypes.idle});
+ });
+};
+
+function QObject(name, data, webChannel)
+{
+ this.__id__ = name;
+ webChannel.objects[name] = this;
+
+ // List of callbacks that get invoked upon signal emission
+ this.__objectSignals__ = {};
+
+ // Cache of all properties, updated when a notify signal is emitted
+ this.__propertyCache__ = {};
+
+ var object = this;
+
+ // ----------------------------------------------------------------------
+
+ this.unwrapQObject = function(response)
+ {
+ if (response instanceof Array) {
+ // support list of objects
+ var ret = new Array(response.length);
+ for (var i = 0; i < response.length; ++i) {
+ ret[i] = object.unwrapQObject(response[i]);
+ }
+ return ret;
+ }
+ if (!response
+ || !response["__QObject*__"]
+ || response.id === undefined) {
+ return response;
+ }
+
+ var objectId = response.id;
+ if (webChannel.objects[objectId])
+ return webChannel.objects[objectId];
+
+ if (!response.data) {
+ console.error("Cannot unwrap unknown QObject " + objectId + " without data.");
+ return;
+ }
+
+ var qObject = new QObject( objectId, response.data, webChannel );
+ qObject.destroyed.connect(function() {
+ if (webChannel.objects[objectId] === qObject) {
+ delete webChannel.objects[objectId];
+ // reset the now deleted QObject to an empty {} object
+ // just assigning {} though would not have the desired effect, but the
+ // below also ensures all external references will see the empty map
+ // NOTE: this detour is necessary to workaround QTBUG-40021
+ var propertyNames = [];
+ for (var propertyName in qObject) {
+ propertyNames.push(propertyName);
+ }
+ for (var idx in propertyNames) {
+ delete qObject[propertyNames[idx]];
+ }
+ }
+ });
+ // here we are already initialized, and thus must directly unwrap the properties
+ qObject.unwrapProperties();
+ return qObject;
+ }
+
+ this.unwrapProperties = function()
+ {
+ for (var propertyIdx in object.__propertyCache__) {
+ object.__propertyCache__[propertyIdx] = object.unwrapQObject(object.__propertyCache__[propertyIdx]);
+ }
+ }
+
+ function addSignal(signalData, isPropertyNotifySignal)
+ {
+ var signalName = signalData[0];
+ var signalIndex = signalData[1];
+ object[signalName] = {
+ connect: function(callback) {
+ if (typeof(callback) !== "function") {
+ console.error("Bad callback given to connect to signal " + signalName);
+ return;
+ }
+
+ object.__objectSignals__[signalIndex] = object.__objectSignals__[signalIndex] || [];
+ object.__objectSignals__[signalIndex].push(callback);
+
+ if (!isPropertyNotifySignal && signalName !== "destroyed") {
+ // only required for "pure" signals, handled separately for properties in propertyUpdate
+ // also note that we always get notified about the destroyed signal
+ webChannel.exec({
+ type: QWebChannelMessageTypes.connectToSignal,
+ object: object.__id__,
+ signal: signalIndex
+ });
+ }
+ },
+ disconnect: function(callback) {
+ if (typeof(callback) !== "function") {
+ console.error("Bad callback given to disconnect from signal " + signalName);
+ return;
+ }
+ object.__objectSignals__[signalIndex] = object.__objectSignals__[signalIndex] || [];
+ var idx = object.__objectSignals__[signalIndex].indexOf(callback);
+ if (idx === -1) {
+ console.error("Cannot find connection of signal " + signalName + " to " + callback.name);
+ return;
+ }
+ object.__objectSignals__[signalIndex].splice(idx, 1);
+ if (!isPropertyNotifySignal && object.__objectSignals__[signalIndex].length === 0) {
+ // only required for "pure" signals, handled separately for properties in propertyUpdate
+ webChannel.exec({
+ type: QWebChannelMessageTypes.disconnectFromSignal,
+ object: object.__id__,
+ signal: signalIndex
+ });
+ }
+ }
+ };
+ }
+
+ /**
+ * Invokes all callbacks for the given signalname. Also works for property notify callbacks.
+ */
+ function invokeSignalCallbacks(signalName, signalArgs)
+ {
+ var connections = object.__objectSignals__[signalName];
+ if (connections) {
+ connections.forEach(function(callback) {
+ callback.apply(callback, signalArgs);
+ });
+ }
+ }
+
+ this.propertyUpdate = function(signals, propertyMap)
+ {
+ // update property cache
+ for (var propertyIndex in propertyMap) {
+ var propertyValue = propertyMap[propertyIndex];
+ object.__propertyCache__[propertyIndex] = propertyValue;
+ }
+
+ for (var signalName in signals) {
+ // Invoke all callbacks, as signalEmitted() does not. This ensures the
+ // property cache is updated before the callbacks are invoked.
+ invokeSignalCallbacks(signalName, signals[signalName]);
+ }
+ }
+
+ this.signalEmitted = function(signalName, signalArgs)
+ {
+ invokeSignalCallbacks(signalName, signalArgs);
+ }
+
+ function addMethod(methodData)
+ {
+ var methodName = methodData[0];
+ var methodIdx = methodData[1];
+ object[methodName] = function() {
+ var args = [];
+ var callback;
+ for (var i = 0; i < arguments.length; ++i) {
+ if (typeof arguments[i] === "function")
+ callback = arguments[i];
+ else
+ args.push(arguments[i]);
+ }
+
+ webChannel.exec({
+ "type": QWebChannelMessageTypes.invokeMethod,
+ "object": object.__id__,
+ "method": methodIdx,
+ "args": args
+ }, function(response) {
+ if (response !== undefined) {
+ var result = object.unwrapQObject(response);
+ if (callback) {
+ (callback)(result);
+ }
+ }
+ });
+ };
+ }
+
+ function bindGetterSetter(propertyInfo)
+ {
+ var propertyIndex = propertyInfo[0];
+ var propertyName = propertyInfo[1];
+ var notifySignalData = propertyInfo[2];
+ // initialize property cache with current value
+ // NOTE: if this is an object, it is not directly unwrapped as it might
+ // reference other QObject that we do not know yet
+ object.__propertyCache__[propertyIndex] = propertyInfo[3];
+
+ if (notifySignalData) {
+ if (notifySignalData[0] === 1) {
+ // signal name is optimized away, reconstruct the actual name
+ notifySignalData[0] = propertyName + "Changed";
+ }
+ addSignal(notifySignalData, true);
+ }
+
+ Object.defineProperty(object, propertyName, {
+ configurable: true,
+ get: function () {
+ var propertyValue = object.__propertyCache__[propertyIndex];
+ if (propertyValue === undefined) {
+ // This shouldn't happen
+ console.warn("Undefined value in property cache for property \"" + propertyName + "\" in object " + object.__id__);
+ }
+
+ return propertyValue;
+ },
+ set: function(value) {
+ if (value === undefined) {
+ console.warn("Property setter for " + propertyName + " called with undefined value!");
+ return;
+ }
+ object.__propertyCache__[propertyIndex] = value;
+ webChannel.exec({
+ "type": QWebChannelMessageTypes.setProperty,
+ "object": object.__id__,
+ "property": propertyIndex,
+ "value": value
+ });
+ }
+ });
+
+ }
+
+ // ----------------------------------------------------------------------
+
+ data.methods.forEach(addMethod);
+
+ data.properties.forEach(bindGetterSetter);
+
+ data.signals.forEach(function(signal) { addSignal(signal, false); });
+
+ for (var name in data.enums) {
+ object[name] = data.enums[name];
+ }
+}
+
+//required for use with nodejs
+if (typeof module === 'object') {
+ module.exports = {
+ QWebChannel: QWebChannel
+ };
+}
diff --git a/tests/auto/widgets/resources/tests.qrc b/tests/auto/widgets/resources/tests.qrc
new file mode 100644
index 000000000..5e9df2873
--- /dev/null
+++ b/tests/auto/widgets/resources/tests.qrc
@@ -0,0 +1,5 @@
+<RCC>
+ <qresource prefix="/">
+ <file>qwebchannel.js</file>
+ </qresource>
+</RCC>
diff --git a/tests/auto/widgets/tests.pri b/tests/auto/widgets/tests.pri
index 8a62ce2a6..ca19a9496 100644
--- a/tests/auto/widgets/tests.pri
+++ b/tests/auto/widgets/tests.pri
@@ -9,6 +9,7 @@ TARGET = tst_$$TARGET
SOURCES += $${TARGET}.cpp
INCLUDEPATH += $$PWD
+RESOURCES += ../resources/tests.qrc
exists($$_PRO_FILE_PWD_/$${TARGET}.qrc): RESOURCES += $${TARGET}.qrc
QT += testlib network webenginewidgets widgets
diff --git a/tests/auto/widgets/util.h b/tests/auto/widgets/util.h
index 2b485fc0f..770579f1f 100644
--- a/tests/auto/widgets/util.h
+++ b/tests/auto/widgets/util.h
@@ -1,21 +1,31 @@
-/*
- Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies)
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License as published by the Free Software Foundation; either
- version 2 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtWebEngine module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
// Functions and macros that really need to be in QTestLib
#if 0
@@ -156,6 +166,13 @@ static inline QVariant evaluateJavaScriptSync(QWebEnginePage *page, const QStrin
return spy.waitForResult();
}
+static inline QVariant evaluateJavaScriptSyncInWorld(QWebEnginePage *page, const QString &script, int worldId)
+{
+ CallbackSpy<QVariant> spy;
+ page->runJavaScript(script, worldId, spy.ref());
+ return spy.waitForResult();
+}
+
static inline QUrl baseUrlSync(QWebEnginePage *page)
{
CallbackSpy<QVariant> spy;
diff --git a/tests/auto/widgets/widgets.pro b/tests/auto/widgets/widgets.pro
index 3220b1379..2f5416701 100644
--- a/tests/auto/widgets/widgets.pro
+++ b/tests/auto/widgets/widgets.pro
@@ -3,6 +3,7 @@ TEMPLATE = subdirs
SUBDIRS += \
qwebengineaccessibility \
qwebenginedefaultsurfaceformat \
+ qwebenginefaviconmanager \
qwebenginepage \
qwebenginehistory \
qwebenginehistoryinterface \
@@ -12,7 +13,7 @@ SUBDIRS += \
qwebenginesettings \
qwebengineview
-qtHaveModule(positioning) {
- SUBDIRS += positionplugin
- qwebenginepage.depends = positionplugin
+# QTBUG-53135, osx does not use hunspell
+!contains(WEBENGINE_CONFIG, no_spellcheck):!osx:!cross_compile {
+ SUBDIRS += qwebenginespellcheck
}