summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.cmake.conf2
-rw-r--r--CHROMIUM_VERSION2
-rw-r--r--cmake/Functions.cmake45
-rw-r--r--coin/module_config.yaml6
-rw-r--r--conanfile.py36
-rw-r--r--configure.cmake1
-rw-r--r--dependencies.yaml8
-rw-r--r--examples/webenginewidgets/simplebrowser/browserwindow.cpp8
-rw-r--r--examples/webenginewidgets/simplebrowser/tabwidget.cpp4
m---------src/3rdparty0
-rw-r--r--src/CMakeLists.txt20
-rw-r--r--src/core/CMakeLists.txt4
-rw-r--r--src/core/api/configure.cmake3
-rw-r--r--src/core/api/qtwebenginecoreglobal.cpp5
-rw-r--r--src/core/api/qwebengineprofile.cpp2
-rw-r--r--src/core/browser_accessibility_qt.cpp13
-rw-r--r--src/core/chromium_overrides.cpp17
-rw-r--r--src/core/content_browser_client_qt.cpp4
-rw-r--r--src/core/content_client_qt.cpp53
-rw-r--r--src/core/doc/snippets/qtwebenginecore_build_snippet.qdoc2
-rw-r--r--src/core/doc/src/qtwebengine-deploying.qdoc7
-rw-r--r--src/core/doc/src/qtwebengine-platform-notes.qdoc9
-rw-r--r--src/core/doc/src/qwebenginesettings_lgpl.qdoc3
-rw-r--r--src/core/favicon_driver_qt.cpp8
-rw-r--r--src/core/file_picker_controller.cpp4
-rw-r--r--src/core/media_capture_devices_dispatcher.cpp2
-rw-r--r--src/core/native_web_keyboard_event_qt.cpp21
-rw-r--r--src/core/net/custom_url_loader_factory.cpp20
-rw-r--r--src/core/net/proxying_url_loader_factory_qt.cpp19
-rw-r--r--src/core/net/qrc_url_scheme_handler.cpp5
-rw-r--r--src/core/net/system_network_context_manager.cpp10
-rw-r--r--src/core/ozone/gl_surface_egl_qt.cpp6
-rw-r--r--src/core/ozone/gl_surface_glx_qt.cpp12
-rw-r--r--src/core/ozone/gl_surface_qt.cpp6
-rw-r--r--src/core/ozone/gl_surface_qt.h8
-rw-r--r--src/core/profile_adapter.cpp21
-rw-r--r--src/core/profile_adapter.h4
-rw-r--r--src/core/web_engine_context.cpp15
-rw-r--r--src/core/web_engine_library_info.cpp176
-rw-r--r--src/core/web_engine_library_info.h3
-rw-r--r--src/gn/CMakeLists.txt1
-rw-r--r--src/pdf/configure.cmake1
-rw-r--r--src/pdf/doc/qtpdf.qdocconf1
-rw-r--r--src/webenginequick/api/qquickwebengineprofile.cpp2
-rw-r--r--src/webenginequick/api/qquickwebenginesingleton.cpp3
-rw-r--r--src/webenginequick/doc/snippets/qtwebengine_build_snippet.qdoc2
-rw-r--r--src/webenginewidgets/api/qwebengineview.cpp4
-rw-r--r--src/webenginewidgets/doc/snippets/qtwebenginewidgets_build_snippet.qdoc2
-rw-r--r--src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp4
-rw-r--r--tests/auto/core/qwebengineurlrequestinterceptor/tst_qwebengineurlrequestinterceptor.cpp2
-rw-r--r--tests/auto/pdf/qpdfdocument/tst_qpdfdocument.cpp2
-rw-r--r--tests/auto/quick/CMakeLists.txt5
-rw-r--r--tests/auto/quick/qmltests/data/tst_favicon.qml32
-rw-r--r--tests/auto/widgets/favicon/tst_favicon.cpp37
-rw-r--r--tests/auto/widgets/proxypac/CMakeLists.txt22
-rw-r--r--tests/auto/widgets/proxypac/proxy.pac2
-rw-r--r--tests/auto/widgets/proxypac/tst_proxypac.cpp14
-rw-r--r--tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp65
-rw-r--r--tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp59
-rw-r--r--tests/auto/widgets/touchinput/tst_touchinput.cpp20
60 files changed, 693 insertions, 181 deletions
diff --git a/.cmake.conf b/.cmake.conf
index 8aab1909f..391d9ba0c 100644
--- a/.cmake.conf
+++ b/.cmake.conf
@@ -1,3 +1,3 @@
-set(QT_REPO_MODULE_VERSION "6.3.1")
+set(QT_REPO_MODULE_VERSION "6.3.3")
set(QT_REPO_MODULE_PRERELEASE_VERSION_SEGMENT "alpha1")
set(QT_SUPPORTED_MIN_CMAKE_VERSION_FOR_BUILDING_WEBENGINE "3.19")
diff --git a/CHROMIUM_VERSION b/CHROMIUM_VERSION
index 2ec45229b..91e8e4401 100644
--- a/CHROMIUM_VERSION
+++ b/CHROMIUM_VERSION
@@ -1,3 +1,3 @@
Based on Chromium version: 94.0.4606.126
-Patched with security patches up to Chromium version: 99.0.4844.84
+Patched with security patches up to Chromium version: 104.0.5112.81
diff --git a/cmake/Functions.cmake b/cmake/Functions.cmake
index 89f4cdd39..a5209e260 100644
--- a/cmake/Functions.cmake
+++ b/cmake/Functions.cmake
@@ -300,7 +300,7 @@ function(get_install_config result)
set(${result} "Release" PARENT_SCOPE)
elseif("RelWithDebInfo" IN_LIST CMAKE_CONFIGURATION_TYPES)
set(${result} "RelWithDebInfo" PARENT_SCOPE)
- elseif("Debug" IN_LIST CMAKE_CONFIGURATION_TYPE)
+ elseif("Debug" IN_LIST CMAKE_CONFIGURATION_TYPES)
set(${result} "Debug" PARENT_SCOPE)
else()
# assume MinSizeRel ?
@@ -408,7 +408,18 @@ function(get_copy_of_response_file result target rsp)
add_dependencies(${cmakeTarget} ${cmakeTarget}_${rsp}_copy_${config})
endfunction()
-function(extend_cmake_target target buildDir completeStatic)
+function(add_archiver_options target buildDir completeStatic)
+ get_target_property(config ${target} CONFIG)
+ string(TOUPPER ${config} cfg)
+ get_target_property(ninjaTarget ${target} NINJA_TARGET)
+ get_target_property(cmakeTarget ${target} CMAKE_TARGET)
+ set(objects_out "${buildDir}/${cmakeTarget}_objects.o")
+ add_library(GnObject_${cmakeTarget}_${config} OBJECT IMPORTED GLOBAL)
+ target_link_libraries(${cmakeTarget} PRIVATE $<$<CONFIG:${config}>:GnObject_${cmakeTarget}_${config}>)
+ set_property(TARGET GnObject_${cmakeTarget}_${config} PROPERTY IMPORTED_OBJECTS_${cfg} ${objects_out})
+endfunction()
+
+function(add_linker_options target buildDir completeStatic)
get_target_property(config ${target} CONFIG)
get_target_property(ninjaTarget ${target} NINJA_TARGET)
get_target_property(cmakeTarget ${target} CMAKE_TARGET)
@@ -419,6 +430,10 @@ function(extend_cmake_target target buildDir completeStatic)
set(libs_rsp "${buildDir}/${ninjaTarget}_libs.rsp")
set_target_properties(${cmakeTarget} PROPERTIES STATIC_LIBRARY_OPTIONS "@${objects_rsp}")
if(LINUX)
+ get_gn_arch(cpu ${TEST_architecture_arch})
+ if(CMAKE_CROSSCOMPILING AND cpu STREQUAL "arm" AND ${config} STREQUAL "Debug")
+ target_link_options(${cmakeTarget} PRIVATE "LINKER:--long-plt")
+ endif()
target_link_options(${cmakeTarget} PRIVATE "$<$<CONFIG:${config}>:@${objects_rsp}>")
if(NOT completeStatic)
target_link_libraries(${cmakeTarget} PRIVATE
@@ -429,7 +444,6 @@ function(extend_cmake_target target buildDir completeStatic)
target_link_libraries(${cmakeTarget} PRIVATE
"$<1:-Wl,--no-fatal-warnings $<$<CONFIG:${config}>:@${libs_rsp}> -Wl,--no-fatal-warnings>"
)
-
endif()
if(MACOS)
target_link_options(${cmakeTarget} PRIVATE "$<$<CONFIG:${config}>:@${objects_rsp}>")
@@ -440,6 +454,7 @@ function(extend_cmake_target target buildDir completeStatic)
endif()
if(WIN32)
get_copy_of_response_file(objects_rsp ${target} objects)
+ target_link_options(${cmakeTarget} PRIVATE /DELAYLOAD:mf.dll /DELAYLOAD:mfplat.dll /DELAYLOAD:mfreadwrite.dll)
target_link_options(${cmakeTarget} PRIVATE "$<$<CONFIG:${config}>:@${objects_rsp}>")
if(NOT completeStatic)
get_copy_of_response_file(archives_rsp ${target} archives)
@@ -452,7 +467,7 @@ function(extend_cmake_target target buildDir completeStatic)
endif()
endfunction()
-function(add_rsp_command target buildDir completeStatic)
+function(add_intermediate_archive target buildDir completeStatic)
get_target_property(config ${target} CONFIG)
get_target_property(arch ${target} ARCH)
get_target_property(ninjaTarget ${target} NINJA_TARGET)
@@ -493,13 +508,15 @@ function(add_rsp_command target buildDir completeStatic)
)
endfunction()
-function(add_ios_rsp_command target buildDir completeStatic)
+function(add_intermediate_object target buildDir completeStatic)
get_target_property(config ${target} CONFIG)
get_target_property(arch ${target} ARCH)
get_target_property(ninjaTarget ${target} NINJA_TARGET)
get_target_property(cmakeTarget ${target} CMAKE_TARGET)
string(TOUPPER ${config} cfg)
- get_ios_target_triple_and_sysroot(args ${arch})
+ if(IOS)
+ get_ios_target_triple_and_sysroot(args ${arch})
+ endif()
set(objects_rsp "${buildDir}/${ninjaTarget}_objects.rsp")
set(objects_out "${buildDir}/${cmakeTarget}_objects.o")
add_custom_command(
@@ -628,8 +645,10 @@ function(get_v8_arch result targetArch hostArch)
set(${result} "mipsel" PARENT_SCOPE)
elseif(hostArch STREQUAL "mipsel64")
set(${result} "mipsel" PARENT_SCOPE)
+ elseif(hostArch IN_LIST list32)
+ set(${result} "${hostArch}" PARENT_SCOPE)
else()
- message(DEBUG "Unsupported architecture: ${hostArch}")
+ message(FATAL_ERROR "Unsupported architecture: ${hostArch}")
endif()
else()
# assume 64bit target which matches 64bit host
@@ -1081,11 +1100,17 @@ function(add_gn_build_aritfacts_to_target cmakeTarget ninjaTarget module buildDi
LINK_DEPENDS ${buildDir}/${config}/${arch}/${ninjaTarget}.stamp
)
if(QT_IS_MACOS_UNIVERSAL)
- add_rsp_command(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ add_intermediate_archive(${target} ${buildDir}/${config}/${arch} ${completeStatic})
elseif(IOS)
- add_ios_rsp_command(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ add_intermediate_object(${target} ${buildDir}/${config}/${arch} ${completeStatic})
else()
- extend_cmake_target(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ if(MACOS AND QT_FEATURE_static)
+ # mac archiver does not support @file notation, do intermediate object istead
+ add_intermediate_object(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ add_archiver_options(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ else()
+ add_linker_options(${target} ${buildDir}/${config}/${arch} ${completeStatic})
+ endif()
endif()
unset(target)
endforeach()
diff --git a/coin/module_config.yaml b/coin/module_config.yaml
index 01da49996..f1d69a277 100644
--- a/coin/module_config.yaml
+++ b/coin/module_config.yaml
@@ -4,6 +4,12 @@ accept_configuration:
property: features
not_contains_value: Disable
+machine_type:
+ Build:
+ cores: 8
+ Test:
+ cores: 4
+
instructions:
Build:
- type: EnvironmentVariable
diff --git a/conanfile.py b/conanfile.py
index 9e2685877..6cf05b5d3 100644
--- a/conanfile.py
+++ b/conanfile.py
@@ -33,10 +33,29 @@ from typing import Dict, Any
_qtwebengine_features = [
"qtpdf-build",
+ "qtpdf-quick-build",
+ "qtpdf-widgets-build",
"qtwebengine-build",
+ "qtwebengine-core-build",
"qtwebengine-quick-build",
"qtwebengine-widgets-build",
"webengine-developer-build",
+ "webengine-embedded-build",
+ "webengine-extensions",
+ "webengine-full-debug-info",
+ "webengine-jumbo-build",
+ "webengine-kerberos",
+ "webengine-native-spellchecker",
+ "webengine-pepper-plugins",
+ "webengine-printing-and-pdf",
+ "webengine-proprietary-codecs",
+ "webengine-sanitizer",
+ "webengine-spellchecker",
+ "webengine-webchannel",
+ "webengine-webrtc",
+ "webengine-webrtc-pipewire",
+ "system-webengine-ffmpeg",
+ "system-webengine-icu",
]
@@ -76,3 +95,20 @@ class QtWebEngine(ConanFile):
def get_qt_leaf_module_default_options(self) -> Dict[str, Any]:
"""Implements abstractmethod from qt-conan-common.QtLeafModule"""
return self._shared.convert_qt_features_to_default_conan_options(_qtwebengine_features)
+
+ def package_env_info(self) -> Dict[str, Any]:
+ """Implements abstractmethod from qt-conan-common.QtLeafModule"""
+ # this will be called only after a successful build
+ _f = lambda p: True
+ if tools.os_info.is_windows:
+ ptrn = "**/QtWebEngineProcess.exe"
+ elif tools.os_info.is_macos:
+ ptrn = "**/QtWebEngineProcess.app/**/QtWebEngineProcess"
+ _f = lambda p: not any(".dSYM" in item for item in p.parts)
+ else:
+ ptrn = "**/QtWebEngineProcess"
+ ret = [str(p) for p in Path(self.package_folder).rglob(ptrn) if p.is_file() and _f(p)]
+ if len(ret) != 1:
+ print("Expected to find one 'QtWebEngineProcess'. Found: {0}".format(ret))
+ return {"QTWEBENGINEPROCESS_PATH": ret.pop() if ret else ""}
+
diff --git a/configure.cmake b/configure.cmake
index 89f8cc07a..6124dd1dc 100644
--- a/configure.cmake
+++ b/configure.cmake
@@ -373,7 +373,6 @@ qt_feature("webengine-qt-libjpeg" PRIVATE
AND TARGET Qt::Gui
AND QT_FEATURE_jpeg
AND NOT QT_FEATURE_system_jpeg
- AND FALSE # FIXME requires qtbase dep update
)
qt_feature("webengine-system-harfbuzz" PRIVATE
LABEL "harfbuzz"
diff --git a/dependencies.yaml b/dependencies.yaml
index 57ebaa507..fe7bc5e2a 100644
--- a/dependencies.yaml
+++ b/dependencies.yaml
@@ -1,13 +1,13 @@
dependencies:
../qtdeclarative:
- ref: 5233b0630496130b89a1bbaeba7c6cd46ed879e4
+ ref: 17af1433bfab54091051fa2b336a4c0866d4cc14
required: true
../qtpositioning:
- ref: a27e2d1abaca86011ccfaf544b393b848eefadd2
+ ref: 263c64a5cf5ccb68cfb1ba3060a87b8aa43d099c
required: false
../qttools:
- ref: beb81aec75f5548136b24eb1412131063b2cefee
+ ref: e24042be0fd018e40b8746d8d8f311fab034df3e
required: false
../qtwebchannel:
- ref: 88f76a364df3818bcb4c397e6bd1abec96d75e34
+ ref: 2090e6b7e89c5b387b8233afbf71cc44d0442090
required: false
diff --git a/examples/webenginewidgets/simplebrowser/browserwindow.cpp b/examples/webenginewidgets/simplebrowser/browserwindow.cpp
index b9d746de7..a3c7bec48 100644
--- a/examples/webenginewidgets/simplebrowser/browserwindow.cpp
+++ b/examples/webenginewidgets/simplebrowser/browserwindow.cpp
@@ -153,7 +153,11 @@ QSize BrowserWindow::sizeHint() const
QMenu *BrowserWindow::createFileMenu(TabWidget *tabWidget)
{
QMenu *fileMenu = new QMenu(tr("&File"));
+#if QT_VERSION >= QT_VERSION_CHECK(6, 3, 0)
fileMenu->addAction(tr("&New Window"), QKeySequence::New, this, &BrowserWindow::handleNewWindowTriggered);
+#else
+ fileMenu->addAction(tr("&New Window"), this, &BrowserWindow::handleNewWindowTriggered, QKeySequence::New);
+#endif
fileMenu->addAction(tr("New &Incognito Window"), this, &BrowserWindow::handleNewIncognitoWindowTriggered);
QAction *newTabAction = new QAction(tr("New &Tab"), this);
@@ -164,7 +168,11 @@ QMenu *BrowserWindow::createFileMenu(TabWidget *tabWidget)
});
fileMenu->addAction(newTabAction);
+#if QT_VERSION >= QT_VERSION_CHECK(6, 3, 0)
fileMenu->addAction(tr("&Open File..."), QKeySequence::Open, this, &BrowserWindow::handleFileOpenTriggered);
+#else
+ fileMenu->addAction(tr("&Open File..."), this, &BrowserWindow::handleFileOpenTriggered, QKeySequence::Open);
+#endif
fileMenu->addSeparator();
QAction *closeTabAction = new QAction(tr("&Close Tab"), this);
diff --git a/examples/webenginewidgets/simplebrowser/tabwidget.cpp b/examples/webenginewidgets/simplebrowser/tabwidget.cpp
index 268ad9a34..044e456b7 100644
--- a/examples/webenginewidgets/simplebrowser/tabwidget.cpp
+++ b/examples/webenginewidgets/simplebrowser/tabwidget.cpp
@@ -115,7 +115,11 @@ void TabWidget::handleCurrentChanged(int index)
void TabWidget::handleContextMenuRequested(const QPoint &pos)
{
QMenu menu;
+#if QT_VERSION >= QT_VERSION_CHECK(6, 3, 0)
menu.addAction(tr("New &Tab"), QKeySequence::AddTab, this, &TabWidget::createTab);
+#else
+ menu.addAction(tr("New &Tab"), this, &TabWidget::createTab, QKeySequence::AddTab);
+#endif
int index = tabBar()->tabAt(pos);
if (index != -1) {
QAction *action = menu.addAction(tr("Clone Tab"));
diff --git a/src/3rdparty b/src/3rdparty
-Subproject 5cd4e9af5765778abc0380fc0fc6e06c43fcdfe
+Subproject cee5373e6119a7ee20ba5e941185f4a22104d46
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 921871bee..eef368ddb 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -144,6 +144,9 @@ if(NOT Gn_FOUND)
if(QT_FEATURE_qtpdf_build)
add_dependencies(run_pdf_GnReady gn)
endif()
+endif()
+
+if(NOT Gn_FOUND OR Gn_EXECUTABLE MATCHES "^${installDir}")
set(INSTALL_GN 1 CACHE INTERNAL "")
endif()
@@ -188,5 +191,22 @@ if((LINUX OR MACOS) AND INSTALL_GN)
CONFIGURATIONS ${installConfig}
RUNTIME DESTINATION "${INSTALL_LIBEXECDIR}"
)
+ if(NOT QT_WILL_INSTALL)
+ add_custom_target(copy-gn ALL DEPENDS
+ ${QT_BUILD_DIR}/${INSTALL_LIBEXECDIR}/gn
+ )
+ if(Gn_FOUND)
+ set(copyDep ${Gn_EXECUTABLE})
+ else()
+ set(copyDep gn)
+ endif()
+ add_custom_command(
+ OUTPUT ${QT_BUILD_DIR}/${INSTALL_LIBEXECDIR}/gn
+ COMMAND ${CMAKE_COMMAND} -E copy ${installDir}/bin/gn
+ ${QT_BUILD_DIR}/${INSTALL_LIBEXECDIR}
+ DEPENDS ${copyDep}
+ USES_TERMINAL
+ )
+ endif()
endif()
diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt
index 9fd27d877..9e6370260 100644
--- a/src/core/CMakeLists.txt
+++ b/src/core/CMakeLists.txt
@@ -303,6 +303,10 @@ foreach(arch ${archs})
CONDITION QT_FEATURE_webengine_printing_and_pdf
)
extend_gn_list(gnArgArg
+ ARGS use_cups
+ CONDITION QT_FEATURE_webengine_printing_and_pdf AND NOT WIN32
+ )
+ extend_gn_list(gnArgArg
ARGS enable_plugins
CONDITION QT_FEATURE_webengine_pepper_plugins
)
diff --git a/src/core/api/configure.cmake b/src/core/api/configure.cmake
index 375aee727..e2543cfac 100644
--- a/src/core/api/configure.cmake
+++ b/src/core/api/configure.cmake
@@ -81,7 +81,8 @@ qt_feature("webengine-printing-and-pdf" PRIVATE
LABEL "Printing and PDF"
PURPOSE "Provides printing and output to PDF."
AUTODETECT NOT QT_FEATURE_webengine_embedded_build
- CONDITION TARGET Qt::PrintSupport AND QT_FEATURE_printer AND (CUPS_FOUND OR NOT LINUX)
+ CONDITION TARGET Qt::PrintSupport AND QT_FEATURE_printer AND
+ (CUPS_FOUND OR WIN32)
)
qt_feature("webengine-webchannel" PUBLIC
SECTION "WebEngine"
diff --git a/src/core/api/qtwebenginecoreglobal.cpp b/src/core/api/qtwebenginecoreglobal.cpp
index 5215f7ce7..fc4e23963 100644
--- a/src/core/api/qtwebenginecoreglobal.cpp
+++ b/src/core/api/qtwebenginecoreglobal.cpp
@@ -233,7 +233,10 @@ static void initialize()
#if QT_CONFIG(opengl)
if (QCoreApplication::instance()) {
// On window/ANGLE, calling QtWebEngineQuick::initialize from DllMain will result in a crash.
- if (!qt_gl_global_share_context()) {
+ if (!qt_gl_global_share_context() &&
+ !(QCoreApplication::testAttribute(Qt::AA_ShareOpenGLContexts) &&
+ QQuickWindow::graphicsApi() == QSGRendererInterface::OpenGLRhi)
+ ) {
qWarning("Qt WebEngine seems to be initialized from a plugin. Please "
"set Qt::AA_ShareOpenGLContexts using QCoreApplication::setAttribute and "
"QSGRendererInterface::OpenGLRhi using QQuickWindow::setGraphicsApi "
diff --git a/src/core/api/qwebengineprofile.cpp b/src/core/api/qwebengineprofile.cpp
index 5e48f4dd1..85ae00501 100644
--- a/src/core/api/qwebengineprofile.cpp
+++ b/src/core/api/qwebengineprofile.cpp
@@ -183,6 +183,8 @@ QWebEngineProfilePrivate::~QWebEngineProfilePrivate()
if (m_profileAdapter != QtWebEngineCore::ProfileAdapter::defaultProfileAdapter())
delete m_profileAdapter;
+ else if (m_profileAdapter)
+ m_profileAdapter->releaseAllWebContentsAdapterClients();
delete m_settings;
}
diff --git a/src/core/browser_accessibility_qt.cpp b/src/core/browser_accessibility_qt.cpp
index 7b4a02647..b3f0c6fa2 100644
--- a/src/core/browser_accessibility_qt.cpp
+++ b/src/core/browser_accessibility_qt.cpp
@@ -802,12 +802,13 @@ void BrowserAccessibilityInterface::init()
{
if (m_id)
return;
- Q_ASSERT(parent());
- Q_ASSERT(parent()->object());
- m_object = new QObject(parent()->object());
- QString name = toQt(q->GetAuthorUniqueId());
- if (!name.isEmpty())
- m_object->setObjectName(name);
+
+ if (parent() && parent()->object()) {
+ m_object = new QObject(parent()->object());
+ QString name = toQt(q->GetAuthorUniqueId());
+ if (!name.isEmpty())
+ m_object->setObjectName(name);
+ }
m_id = QAccessible::registerAccessibleInterface(this);
}
diff --git a/src/core/chromium_overrides.cpp b/src/core/chromium_overrides.cpp
index 4be528f58..7a5ea3737 100644
--- a/src/core/chromium_overrides.cpp
+++ b/src/core/chromium_overrides.cpp
@@ -37,10 +37,11 @@
**
****************************************************************************/
+#include "type_conversion.h"
#include "ozone/gl_context_qt.h"
#include "qtwebenginecoreglobal_p.h"
#include "web_contents_view_qt.h"
-
+#include "web_engine_library_info.h"
#include "base/values.h"
#include "content/browser/renderer_host/render_widget_host_view_base.h"
#include "content/browser/web_contents/web_contents_impl.h"
@@ -92,14 +93,20 @@ WebContentsView* CreateWebContentsView(WebContentsImpl *web_contents,
return rv;
}
-#if defined(Q_OS_MACOS)
-std::string getQtPrefix()
+#if defined(OS_MAC)
+#if defined(QT_MAC_FRAMEWORK_BUILD)
+base::FilePath getSandboxPath()
+{
+ return WebEngineLibraryInfo::getPath(QT_FRAMEWORK_BUNDLE);
+}
+#else
+base::FilePath getSandboxPath()
{
const QString prefix = QLibraryInfo::location(QLibraryInfo::PrefixPath);
- return prefix.toStdString();
+ return QtWebEngineCore::toFilePath(prefix);
}
#endif
-
+#endif
} // namespace content
#if defined(USE_AURA) || defined(USE_OZONE)
diff --git a/src/core/content_browser_client_qt.cpp b/src/core/content_browser_client_qt.cpp
index 6201bab27..f6ecb31b4 100644
--- a/src/core/content_browser_client_qt.cpp
+++ b/src/core/content_browser_client_qt.cpp
@@ -823,10 +823,6 @@ static bool navigationThrottleCallback(content::WebContents *source,
if (params.is_external_protocol() && !profile->profileAdapter()->urlSchemeHandler(toQByteArray(params.url().scheme())))
return false;
- WebContentsViewQt *view = WebContentsViewQt::from(static_cast<content::WebContentsImpl *>(source)->GetView());
- if (!view->client())
- return false;
-
bool navigationAccepted = true;
WebContentsAdapterClient *client =
diff --git a/src/core/content_client_qt.cpp b/src/core/content_client_qt.cpp
index 90e604e7b..6f7a6c785 100644
--- a/src/core/content_client_qt.cpp
+++ b/src/core/content_client_qt.cpp
@@ -53,6 +53,7 @@
#include "extensions/common/constants.h"
#include "media/base/media_switches.h"
#include "media/base/video_codecs.h"
+#include "media/cdm/supported_audio_codecs.h"
#include "media/media_buildflags.h"
#include "ui/base/layout.h"
#include "ui/base/l10n/l10n_util.h"
@@ -250,15 +251,56 @@ static bool IsWidevineAvailable(base::FilePath *cdm_path,
}
}
#elif defined(Q_OS_LINUX)
- pluginPaths << QStringLiteral("/opt/google/chrome/libwidevinecdm.so") // Old Google Chrome
+ QList<QDir> potentialWidevineVersionDirs;
+
+ // Google Chrome widevine modules
+ QDir chromeWidevineDir(QDir::homePath() + "/.config/google-chrome/WidevineCdm");
+ if (chromeWidevineDir.exists())
+ potentialWidevineVersionDirs << chromeWidevineDir;
+
+ // Firefox widevine modules
+ QDir firefoxPotentialProfilesDir(QDir::homePath() + "/.mozilla/firefox");
+ if (firefoxPotentialProfilesDir.exists()) {
+ QFileInfoList firefoxProfileDirs = firefoxPotentialProfilesDir.entryInfoList(QDir::Dirs | QDir::NoDotAndDotDot, QDir::Name | QDir::Reversed);
+ for (const QFileInfo &info : firefoxProfileDirs) {
+ QDir widevinePluginsDir(info.absoluteFilePath() + "/gmp-widevinecdm");
+ if (widevinePluginsDir.exists())
+ potentialWidevineVersionDirs << widevinePluginsDir;
+ }
+ }
+
+ // Chromium widevine modules (might not work with proprietary codecs)
+ QDir chromiumWidevineDir(QDir::homePath() + "/.config/chromium/WidevineCdm");
+ if (chromiumWidevineDir.exists())
+ potentialWidevineVersionDirs << chromiumWidevineDir;
+
+ // Search for widewine versions
+ for (const QDir &dir : potentialWidevineVersionDirs) {
+ QFileInfoList widevineVersionDirs = dir.entryInfoList(QDir::Dirs | QDir::NoDotAndDotDot, QDir::Name | QDir::Reversed);
+ // ### alternatively look up in the manifest.json and take the path from there.
#if Q_PROCESSOR_WORDSIZE == 8
- << QStringLiteral("/opt/google/chrome/WidevineCdm/_platform_specific/linux_x64/libwidevinecdm.so")
+ const QString library = QLatin1String("/_platform_specific/linux_x64/libwidevinecdm.so");
#else
- << QStringLiteral("/opt/google/chrome/WidevineCdm/_platform_specific/linux_x86/libwidevinecdm.so")
+ const QString library = QLatin1String("/_platform_specific/linux_x86/libwidevinecdm.so");
#endif
- << QStringLiteral("/usr/lib/chromium/libwidevinecdm.so") // Arch
+ for (const QFileInfo &info : widevineVersionDirs) {
+ pluginPaths << info.absoluteFilePath() + "/libwidevinecdm.so";
+ pluginPaths << info.absoluteFilePath() + library;
+ }
+ }
+
+ // Fixed paths:
+ pluginPaths << QStringLiteral("/usr/lib/chromium/libwidevinecdm.so") // Arch
<< QStringLiteral("/usr/lib/chromium-browser/libwidevinecdm.so") // Ubuntu/neon
- << QStringLiteral("/usr/lib64/chromium/libwidevinecdm.so"); // OpenSUSE style
+ << QStringLiteral("/usr/lib64/chromium/libwidevinecdm.so") // OpenSUSE style
+#if Q_PROCESSOR_WORDSIZE == 8
+ << QStringLiteral("/usr/lib64/chromium-browser/WidevineCdm/_platform_specific/linux_x64/libwidevinecdm.so") // Gentoo
+ << QStringLiteral("/opt/google/chrome/WidevineCdm/_platform_specific/linux_x64/libwidevinecdm.so") // Old Google Chrome
+#else
+ << QStringLiteral("/usr/lib/chromium-browser/WidevineCdm/_platform_specific/linux_x86/libwidevinecdm.so") // Gentoo
+ << QStringLiteral("/opt/google/chrome/WidevineCdm/_platform_specific/linux_x86/libwidevinecdm.so") // Old Google Chrome
+#endif
+ << QStringLiteral("/opt/google/chrome/libwidevinecdm.so"); // Older Google Chrome
#endif
}
@@ -274,6 +316,7 @@ static bool IsWidevineAvailable(base::FilePath *cdm_path,
#if BUILDFLAG(USE_PROPRIETARY_CODECS)
capability->video_codecs.emplace(media::VideoCodec::kCodecH264, kAllProfiles);
#endif // BUILDFLAG(USE_PROPRIETARY_CODECS)
+ capability->audio_codecs = media::GetCdmSupportedAudioCodecs();
// Add the supported encryption schemes as if they came from the
// component manifest. This list must match the CDM that is being
diff --git a/src/core/doc/snippets/qtwebenginecore_build_snippet.qdoc b/src/core/doc/snippets/qtwebenginecore_build_snippet.qdoc
index 43421bafb..ba23c8887 100644
--- a/src/core/doc/snippets/qtwebenginecore_build_snippet.qdoc
+++ b/src/core/doc/snippets/qtwebenginecore_build_snippet.qdoc
@@ -35,6 +35,6 @@ QT += webenginecore
//! [1]
//! [2]
-find_package(Qt6 COMPONENTS WebEngineCore REQUIRED)
+find_package(Qt6 REQUIRED COMPONENTS WebEngineCore)
target_link_libraries(target PRIVATE Qt::WebEngineCore)
//! [2]
diff --git a/src/core/doc/src/qtwebengine-deploying.qdoc b/src/core/doc/src/qtwebengine-deploying.qdoc
index 7b9f3fd4a..505d38e62 100644
--- a/src/core/doc/src/qtwebengine-deploying.qdoc
+++ b/src/core/doc/src/qtwebengine-deploying.qdoc
@@ -129,8 +129,12 @@
\li On Linux and Windows: the \c resources directory in the directory
specified by QLibraryInfo::location(QLibraryInfo::DataPath)
\li On \macos: \c .app/Content/Resources
+ \li The application directory specified by QCoreApplication::applicationDirPath()
\endlist
+ Alternatively, a resources directory path can be set as a value of the
+ \c QTWEBENGINE_RESOURCES_PATH environment variable.
+
\section2 Translations
Locale data (such as \c en-US.pak) is searched form the following locations:
@@ -142,6 +146,9 @@
QLibraryInfo::location(QLibraryInfo::TranslationsPath)
\endlist
+ Alternatively, a locales directory path can be set as a value of the
+ \c QTWEBENGINE_LOCALES_PATH environment variable.
+
\section2 JavaScript Files in Qt Resource Files
If your WebEngine application is built using the Qt Quick Compiler, and the application ships
diff --git a/src/core/doc/src/qtwebengine-platform-notes.qdoc b/src/core/doc/src/qtwebengine-platform-notes.qdoc
index d13fb2471..7c8f4d472 100644
--- a/src/core/doc/src/qtwebengine-platform-notes.qdoc
+++ b/src/core/doc/src/qtwebengine-platform-notes.qdoc
@@ -35,7 +35,7 @@
Static builds are not supported.
- The requirements for building Qt 5 modules from source are listed separately for each supported
+ The requirements for building Qt modules from source are listed separately for each supported
platform:
\list
@@ -78,14 +78,15 @@
\QWE can only be built on 64-bit Windows, with a x64-bit toolchain.
For building \QWE for x86 applications, you need to configure
- and compile Qt with the Visual Studio 2017 x64 to x86 cross-compile
+ and compile Qt with the Visual Studio x64 to x86 cross-compile
toolchain. This toolchain can be set up on the command line by running
\c{vcvarsall.bat amd64_x86}.
+ \note It is not recommended to use tools form \c msys2 or \c cygwin to build \QWE as it may result in build errors.
+
\section2 Linux
On Linux, Clang or GCC version 9 or later is required.
- Supported QMake configurations are \c linux-g++, \c{linux-clang} and \c{linux-clang-libc++}
\QWE requires \c pkg-config to detect most of its dependencies. The
following \c pkg-config files are required:
@@ -219,7 +220,7 @@
Due to some limitations, the Linux QPA plugin almost always reports that accessibility should
be activated. On big HTML pages, this can cause a significant slowdown in rendering speed.
- Because of that, from Qt 5.9 onwards, \QWE accessibility support is disabled by default
+ Because of that, \QWE accessibility support is disabled by default
on Linux.
It can be re-enabled by setting the \c QTWEBENGINE_ENABLE_LINUX_ACCESSIBILITY environment
variable to a non-empty value.
diff --git a/src/core/doc/src/qwebenginesettings_lgpl.qdoc b/src/core/doc/src/qwebenginesettings_lgpl.qdoc
index 6a7f1f958..01965c7a3 100644
--- a/src/core/doc/src/qwebenginesettings_lgpl.qdoc
+++ b/src/core/doc/src/qwebenginesettings_lgpl.qdoc
@@ -97,7 +97,8 @@
Enables support for the HTML 5 local storage feature. Enabled by default.
\value LocalContentCanAccessRemoteUrls
Allows local origin documents to access remote resources that would normally be blocked.
- Disabled by default.
+ Disabled by default. Note DnsPrefetchEnabled below operates independently of this setting,
+ and can if enabled, cause remote accesses from local content.
\value XSSAuditingEnabled
Obsolete and has no effect.
\value SpatialNavigationEnabled
diff --git a/src/core/favicon_driver_qt.cpp b/src/core/favicon_driver_qt.cpp
index 73c79fc1f..be5f7267e 100644
--- a/src/core/favicon_driver_qt.cpp
+++ b/src/core/favicon_driver_qt.cpp
@@ -300,15 +300,15 @@ void FaviconDriverQt::DidStartNavigation(content::NavigationHandle *navigation_h
return;
m_faviconUrls.reset();
- m_completedHandlersCount = 0;
- m_latestFavicon = FaviconStatusQt();
if (!navigation_handle->IsSameDocument()) {
+ m_completedHandlersCount = 0;
+ m_latestFavicon = FaviconStatusQt();
m_documentOnLoadCompleted = false;
m_manifestUrl = GURL();
- }
- m_viewClient->iconChanged(QUrl());
+ m_viewClient->iconChanged(QUrl());
+ }
content::ReloadType reload_type = navigation_handle->GetReloadType();
if (reload_type == content::ReloadType::NONE || IsOffTheRecord())
diff --git a/src/core/file_picker_controller.cpp b/src/core/file_picker_controller.cpp
index 140cb7dba..a40aefe49 100644
--- a/src/core/file_picker_controller.cpp
+++ b/src/core/file_picker_controller.cpp
@@ -245,6 +245,10 @@ void FilePickerController::filesSelectedInChooser(const QStringList &filesList)
else
d_ptr->fileSystemAccessDialogListener->MultiFilesSelected(files, nullptr);
}
+
+ // release the fileSelectListener manually because it blocks fullscreen requests in chromium
+ // see QTBUG-106975
+ d_ptr->fileDialogListener.reset();
}
QStringList FilePickerController::acceptedMimeTypes() const
diff --git a/src/core/media_capture_devices_dispatcher.cpp b/src/core/media_capture_devices_dispatcher.cpp
index c976798ae..9a3295363 100644
--- a/src/core/media_capture_devices_dispatcher.cpp
+++ b/src/core/media_capture_devices_dispatcher.cpp
@@ -181,7 +181,7 @@ content::DesktopMediaID getDefaultScreenId()
GetMonitorsFunc getMonitors = reinterpret_cast<GetMonitorsFunc>(dlsym(RTLD_DEFAULT, "XRRGetMonitors"));
typedef void (*FreeMonitorsFunc)(XRRMonitorInfo*);
FreeMonitorsFunc freeMonitors = reinterpret_cast<FreeMonitorsFunc>(dlsym(RTLD_DEFAULT, "XRRFreeMonitors"));
- if (!getMonitors && !freeMonitors) {
+ if (!getMonitors || !freeMonitors) {
qWarning("Unable to link XRandR monitor functions.");
return content::DesktopMediaID(content::DesktopMediaID::TYPE_SCREEN, 0);
}
diff --git a/src/core/native_web_keyboard_event_qt.cpp b/src/core/native_web_keyboard_event_qt.cpp
index c90b3c9e8..9942ecf17 100644
--- a/src/core/native_web_keyboard_event_qt.cpp
+++ b/src/core/native_web_keyboard_event_qt.cpp
@@ -70,28 +70,31 @@ using blink::WebKeyboardEvent;
namespace content {
-NativeWebKeyboardEvent::NativeWebKeyboardEvent(blink::WebKeyboardEvent const&, gfx::NativeView)
- : os_event(0)
+NativeWebKeyboardEvent::NativeWebKeyboardEvent(const blink::WebKeyboardEvent &web_event, gfx::NativeView)
+ : WebKeyboardEvent(web_event)
+ , os_event(nullptr)
, skip_in_browser(false)
{
}
-NativeWebKeyboardEvent::NativeWebKeyboardEvent(blink::WebInputEvent::Type, int, base::TimeTicks)
- : os_event(0)
+NativeWebKeyboardEvent::NativeWebKeyboardEvent(blink::WebInputEvent::Type type, int modifiers,
+ base::TimeTicks timestamp)
+ : WebKeyboardEvent(type, modifiers, timestamp)
+ , os_event(nullptr)
, skip_in_browser(false)
{
}
NativeWebKeyboardEvent::NativeWebKeyboardEvent(gfx::NativeEvent native_event)
- : os_event(CopyEvent(native_event)),
- skip_in_browser(false)
+ : os_event(CopyEvent(native_event))
+ , skip_in_browser(false)
{
}
NativeWebKeyboardEvent::NativeWebKeyboardEvent(const NativeWebKeyboardEvent& other)
- : WebKeyboardEvent(other),
- os_event(CopyEvent(other.os_event)),
- skip_in_browser(other.skip_in_browser)
+ : WebKeyboardEvent(other)
+ , os_event(CopyEvent(other.os_event))
+ , skip_in_browser(other.skip_in_browser)
{
}
diff --git a/src/core/net/custom_url_loader_factory.cpp b/src/core/net/custom_url_loader_factory.cpp
index 6cb272b1c..892f21dac 100644
--- a/src/core/net/custom_url_loader_factory.cpp
+++ b/src/core/net/custom_url_loader_factory.cpp
@@ -326,15 +326,14 @@ private:
m_client->OnStartLoadingResponseBody(std::move(m_pipeConsumerHandle));
m_head = nullptr;
- if (readAvailableData()) // May delete this
- return;
-
m_watcher = std::make_unique<mojo::SimpleWatcher>(
- FROM_HERE, mojo::SimpleWatcher::ArmingPolicy::AUTOMATIC, m_taskRunner);
+ FROM_HERE, mojo::SimpleWatcher::ArmingPolicy::MANUAL, m_taskRunner);
m_watcher->Watch(m_pipeProducerHandle.get(), MOJO_HANDLE_SIGNAL_WRITABLE,
MOJO_WATCH_CONDITION_SATISFIED,
base::BindRepeating(&CustomURLLoader::notifyReadyWrite,
m_weakPtrFactory.GetWeakPtr()));
+
+ readAvailableData(); // May delete this
}
void notifyCanceled() override
{
@@ -402,8 +401,10 @@ private:
uint32_t bufferSize = 0;
MojoResult beginResult = m_pipeProducerHandle->BeginWriteData(
&buffer, &bufferSize, MOJO_BEGIN_WRITE_DATA_FLAG_NONE);
- if (beginResult == MOJO_RESULT_SHOULD_WAIT)
+ if (beginResult == MOJO_RESULT_SHOULD_WAIT) {
+ m_watcher->ArmOrNotify();
return false; // Wait for pipe watcher
+ }
if (beginResult != MOJO_RESULT_OK)
break;
if (m_maxBytesToRead > 0 && m_maxBytesToRead <= int64_t{std::numeric_limits<uint32_t>::max()})
@@ -415,13 +416,20 @@ private:
m_totalBytesRead += bytesRead;
m_client->OnTransferSizeUpdated(m_totalBytesRead);
- if (m_device->atEnd() || (m_maxBytesToRead > 0 && m_totalBytesRead >= m_maxBytesToRead)) {
+ const bool deviceAtEnd = m_device->atEnd();
+ if ((deviceAtEnd && !m_device->isSequential())
+ || (m_maxBytesToRead > 0 && m_totalBytesRead >= m_maxBytesToRead)) {
OnTransferComplete(MOJO_RESULT_OK);
return true; // Done with reading
}
if (readResult == 0)
return false; // Wait for readyRead
+ if (readResult < 0 && deviceAtEnd && m_device->isSequential()) {
+ // Failure on read, and sequential device claiming to be at end, so treat it as a successful end-of-data.
+ OnTransferComplete(MOJO_RESULT_OK);
+ return true; // Done with reading
+ }
if (readResult < 0)
break;
}
diff --git a/src/core/net/proxying_url_loader_factory_qt.cpp b/src/core/net/proxying_url_loader_factory_qt.cpp
index 39630cf2d..ba2051d60 100644
--- a/src/core/net/proxying_url_loader_factory_qt.cpp
+++ b/src/core/net/proxying_url_loader_factory_qt.cpp
@@ -280,10 +280,23 @@ void InterceptedRequest::Restart()
// Check if non-local access is allowed
if (!allow_remote_ && remote_access_) {
- target_client_->OnComplete(network::URLLoaderCompletionStatus(net::ERR_NETWORK_ACCESS_DENIED));
- delete this;
- return;
+ bool granted_special_access = false;
+ switch (ui::PageTransition(request_.transition_type)) {
+ case ui::PAGE_TRANSITION_LINK:
+ case ui::PAGE_TRANSITION_TYPED:
+ if (blink::mojom::ResourceType(request_.resource_type) == blink::mojom::ResourceType::kMainFrame && request_.has_user_gesture)
+ granted_special_access = true; // allow normal explicit navigation
+ break;
+ default:
+ break;
+ }
+ if (!granted_special_access) {
+ target_client_->OnComplete(network::URLLoaderCompletionStatus(net::ERR_NETWORK_ACCESS_DENIED));
+ delete this;
+ return;
+ }
}
+
// Check if local access is allowed
if (!allow_local_ && local_access_) {
bool granted_special_access = false;
diff --git a/src/core/net/qrc_url_scheme_handler.cpp b/src/core/net/qrc_url_scheme_handler.cpp
index 73bf24f1d..0a9943431 100644
--- a/src/core/net/qrc_url_scheme_handler.cpp
+++ b/src/core/net/qrc_url_scheme_handler.cpp
@@ -67,7 +67,10 @@ void QrcUrlSchemeHandler::requestStarted(QWebEngineUrlRequestJob *job)
QFileInfo fileInfo(*file);
QMimeDatabase mimeDatabase;
QMimeType mimeType = mimeDatabase.mimeTypeForFile(fileInfo);
- job->reply(mimeType.name().toUtf8(), file.take());
+ if (mimeType.name() == QStringLiteral("application/x-extension-html"))
+ job->reply("text/html", file.take());
+ else
+ job->reply(mimeType.name().toUtf8(), file.take());
}
} // namespace QtWebEngineCore
diff --git a/src/core/net/system_network_context_manager.cpp b/src/core/net/system_network_context_manager.cpp
index 962266d78..f6e7cb630 100644
--- a/src/core/net/system_network_context_manager.cpp
+++ b/src/core/net/system_network_context_manager.cpp
@@ -292,7 +292,15 @@ void SystemNetworkContextManager::ConfigureDefaultNetworkContextParams(network::
// respect prefs::kEnableReferrers from the appropriate pref store.
network_context_params->enable_referrers = false;
- network_context_params->proxy_resolver_factory = ChromeMojoProxyResolverFactory::CreateWithSelfOwnedReceiver();
+ const base::CommandLine& command_line =
+ *base::CommandLine::ForCurrentProcess();
+
+ if (command_line.HasSwitch(switches::kSingleProcess)) {
+ LOG(ERROR) << "Cannot use V8 Proxy resolver in single process mode.";
+ } else {
+ network_context_params->proxy_resolver_factory =
+ ChromeMojoProxyResolverFactory::CreateWithSelfOwnedReceiver();
+ }
// Use the SystemNetworkContextManager to populate and update SSL
// configuration. The SystemNetworkContextManager is owned by the
diff --git a/src/core/ozone/gl_surface_egl_qt.cpp b/src/core/ozone/gl_surface_egl_qt.cpp
index f7d162923..52ab53c38 100644
--- a/src/core/ozone/gl_surface_egl_qt.cpp
+++ b/src/core/ozone/gl_surface_egl_qt.cpp
@@ -144,12 +144,12 @@ void GLSurfaceEGL::ShutdownOneOff()
const char *GLSurfaceEGL::GetEGLClientExtensions()
{
- return GLSurfaceQt::g_client_extensions;
+ return GLSurfaceQt::g_client_extensions.c_str();
}
const char *GLSurfaceEGL::GetEGLExtensions()
{
- return GLSurfaceQt::g_extensions;
+ return GLSurfaceQt::g_extensions.c_str();
}
bool GLSurfaceEGL::HasEGLClientExtension(const char *name)
@@ -223,7 +223,7 @@ bool GLSurfaceEGLQt::InitializeOneOff()
g_client_extensions = eglQueryString(EGL_NO_DISPLAY, EGL_EXTENSIONS);
g_extensions = eglQueryString(g_display, EGL_EXTENSIONS);
- g_egl_surfaceless_context_supported = ExtensionsContain(g_extensions, "EGL_KHR_surfaceless_context");
+ g_egl_surfaceless_context_supported = ExtensionsContain(g_extensions.c_str(), "EGL_KHR_surfaceless_context");
if (g_egl_surfaceless_context_supported) {
scoped_refptr<GLSurface> surface = new GLSurfacelessQtEGL(gfx::Size(1, 1));
gl::GLContextAttribs attribs;
diff --git a/src/core/ozone/gl_surface_glx_qt.cpp b/src/core/ozone/gl_surface_glx_qt.cpp
index 5ccf5037a..79a084941 100644
--- a/src/core/ozone/gl_surface_glx_qt.cpp
+++ b/src/core/ozone/gl_surface_glx_qt.cpp
@@ -54,7 +54,7 @@ void GLSurfaceGLX::ShutdownOneOff()
bool GLSurfaceGLX::IsCreateContextSupported()
{
- return ExtensionsContain(GLSurfaceQt::g_extensions, "GLX_ARB_create_context");
+ return HasGLXExtension("GLX_ARB_create_context");
}
bool GLSurfaceGLX::IsCreateContextRobustnessSupported()
@@ -79,7 +79,7 @@ bool GLSurfaceGLX::IsCreateContextProfileSupported()
bool GLSurfaceGLX::IsCreateContextES2ProfileSupported()
{
- return ExtensionsContain(GLSurfaceQt::g_extensions, "GLX_ARB_create_context_es2_profile");
+ return HasGLXExtension("GLX_ARB_create_context_es2_profile");
}
bool GLSurfaceGLX::IsOMLSyncControlSupported()
@@ -89,12 +89,12 @@ bool GLSurfaceGLX::IsOMLSyncControlSupported()
bool GLSurfaceGLX::HasGLXExtension(const char *name)
{
- return ExtensionsContain(GLSurfaceQt::g_extensions, name);
+ return ExtensionsContain(GLSurfaceQt::g_extensions.c_str(), name);
}
bool GLSurfaceGLX::IsTextureFromPixmapSupported()
{
- return ExtensionsContain(GLSurfaceQt::g_extensions, "GLX_EXT_texture_from_pixmap");
+ return HasGLXExtension("GLX_EXT_texture_from_pixmap");
}
bool GLSurfaceGLX::IsRobustnessVideoMemoryPurgeSupported()
@@ -104,7 +104,7 @@ bool GLSurfaceGLX::IsRobustnessVideoMemoryPurgeSupported()
const char* GLSurfaceGLX::GetGLXExtensions()
{
- return GLSurfaceQt::g_extensions;
+ return GLSurfaceQt::g_extensions.c_str();
}
@@ -162,7 +162,7 @@ bool GLSurfaceGLXQt::InitializeExtensionSettingsOneOff()
Display* display = static_cast<Display*>(g_display);
GLSurfaceQt::g_extensions = glXQueryExtensionsString(display, 0);
- g_driver_glx.InitializeExtensionBindings(g_extensions);
+ g_driver_glx.InitializeExtensionBindings(g_extensions.c_str());
return true;
}
diff --git a/src/core/ozone/gl_surface_qt.cpp b/src/core/ozone/gl_surface_qt.cpp
index 8af3bd3c1..9bf16c960 100644
--- a/src/core/ozone/gl_surface_qt.cpp
+++ b/src/core/ozone/gl_surface_qt.cpp
@@ -64,8 +64,8 @@ namespace gl {
void *GLSurfaceQt::g_display = nullptr;
void *GLSurfaceQt::g_config = nullptr;
-const char *GLSurfaceQt::g_client_extensions = nullptr;
-const char *GLSurfaceQt::g_extensions = nullptr;
+std::string GLSurfaceQt::g_client_extensions;
+std::string GLSurfaceQt::g_extensions;
GLSurfaceQt::~GLSurfaceQt()
{
@@ -86,7 +86,7 @@ GLSurfaceQt::GLSurfaceQt(const gfx::Size& size)
bool GLSurfaceQt::HasEGLExtension(const char* name)
{
- return ExtensionsContain(g_extensions, name);
+ return ExtensionsContain(g_extensions.c_str(), name);
}
bool GLSurfaceQt::IsOffscreen()
diff --git a/src/core/ozone/gl_surface_qt.h b/src/core/ozone/gl_surface_qt.h
index 055b27875..8689c3a19 100644
--- a/src/core/ozone/gl_surface_qt.h
+++ b/src/core/ozone/gl_surface_qt.h
@@ -37,11 +37,11 @@
**
****************************************************************************/
-
-
#ifndef GL_SURFACE_QT_H_
#define GL_SURFACE_QT_H_
+#include <string>
+
#include "ui/gfx/geometry/size.h"
#include "ui/gl/gl_surface.h"
@@ -71,8 +71,8 @@ protected:
public:
static void* g_config;
static void* g_display;
- static const char* g_extensions;
- static const char* g_client_extensions;
+ static std::string g_extensions;
+ static std::string g_client_extensions;
private:
DISALLOW_COPY_AND_ASSIGN(GLSurfaceQt);
diff --git a/src/core/profile_adapter.cpp b/src/core/profile_adapter.cpp
index 6e902ff5a..8d2138867 100644
--- a/src/core/profile_adapter.cpp
+++ b/src/core/profile_adapter.cpp
@@ -39,7 +39,9 @@
#include "profile_adapter.h"
+#include "base/files/file_util.h"
#include "base/task/cancelable_task_tracker.h"
+#include "base/time/time_to_iso8601.h"
#include "components/favicon/core/favicon_service.h"
#include "components/history/content/browser/history_database_helper.h"
#include "components/history/core/browser/history_database_params.h"
@@ -48,9 +50,7 @@
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/browsing_data_remover.h"
#include "content/public/browser/download_manager.h"
-#include "content/public/browser/shared_cors_origin_access_list.h"
#include "content/public/browser/storage_partition.h"
-#include "services/network/public/cpp/cors/origin_access_list.h"
#include "services/network/public/mojom/network_context.mojom.h"
#include "url/url_util.h"
@@ -65,12 +65,8 @@
#include "renderer_host/user_resource_controller_host.h"
#include "type_conversion.h"
#include "visited_links_manager_qt.h"
-#include "web_engine_context.h"
#include "web_contents_adapter_client.h"
-
-#include "base/files/file_util.h"
-#include "base/time/time_to_iso8601.h"
-#include "components/keyed_service/content/browser_context_dependency_manager.h"
+#include "web_engine_context.h"
#if BUILDFLAG(ENABLE_EXTENSIONS)
#include "extensions/browser/extension_system.h"
@@ -120,9 +116,8 @@ ProfileAdapter::~ProfileAdapter()
{
m_cancelableTaskTracker->TryCancelAll();
m_profile->NotifyWillBeDestroyed();
- while (!m_webContentsAdapterClients.isEmpty()) {
- m_webContentsAdapterClients.first()->releaseProfile();
- }
+ releaseAllWebContentsAdapterClients();
+
WebEngineContext::current()->removeProfileAdapter(this);
if (m_downloadManagerDelegate) {
m_profile->GetDownloadManager()->Shutdown();
@@ -655,6 +650,12 @@ void ProfileAdapter::removeWebContentsAdapterClient(WebContentsAdapterClient *cl
m_webContentsAdapterClients.removeAll(client);
}
+void ProfileAdapter::releaseAllWebContentsAdapterClients()
+{
+ while (!m_webContentsAdapterClients.isEmpty())
+ m_webContentsAdapterClients.first()->releaseProfile();
+}
+
void ProfileAdapter::resetVisitedLinksManager()
{
m_visitedLinksManager.reset(new VisitedLinksManagerQt(m_profile.data(), persistVisitedLinks()));
diff --git a/src/core/profile_adapter.h b/src/core/profile_adapter.h
index 373d6e2a9..140891150 100644
--- a/src/core/profile_adapter.h
+++ b/src/core/profile_adapter.h
@@ -53,10 +53,11 @@
#include <QtWebEngineCore/private/qtwebenginecoreglobal_p.h>
-#include <QEnableSharedFromThis>
+#include <QHash>
#include <QList>
#include <QPointer>
#include <QScopedPointer>
+#include <QSharedPointer>
#include <QString>
#include <QtWebEngineCore/qwebengineclientcertificatestore.h>
@@ -137,6 +138,7 @@ public:
void addWebContentsAdapterClient(WebContentsAdapterClient *client);
void removeWebContentsAdapterClient(WebContentsAdapterClient *client);
+ void releaseAllWebContentsAdapterClients();
// KEEP IN SYNC with API or add mapping layer
enum HttpCacheType {
diff --git a/src/core/web_engine_context.cpp b/src/core/web_engine_context.cpp
index 9727efab1..e99726d7a 100644
--- a/src/core/web_engine_context.cpp
+++ b/src/core/web_engine_context.cpp
@@ -185,14 +185,21 @@ static bool usingSupportedSGBackend()
bool usingSoftwareDynamicGL()
{
+ const char openGlVar[] = "QT_OPENGL";
if (QCoreApplication::testAttribute(Qt::AA_UseSoftwareOpenGL))
return true;
+
+ if (qEnvironmentVariableIsSet(openGlVar)) {
+ const QByteArray requested = qgetenv(openGlVar);
+ if (requested == "software")
+ return true;
+ }
#if defined(Q_OS_WIN)
HMODULE handle = QNativeInterface::QWGLContext::openGLModuleHandle();
wchar_t path[MAX_PATH];
DWORD size = GetModuleFileName(handle, path, MAX_PATH);
QFileInfo openGLModule(QString::fromWCharArray(path, size));
- return !openGLModule.fileName().compare(QLatin1String("opengl32sw.dll"),Qt::CaseInsensitive);
+ return openGLModule.fileName().contains(QLatin1String("opengl32sw"),Qt::CaseInsensitive);
#else
return false;
#endif
@@ -250,7 +257,7 @@ static const char *getGLType(bool enableGLSoftwareRendering, bool disableGpu)
return glType;
}
#else
-static const char *getGLType(bool enableGLSoftwareRendering)
+static const char *getGLType(bool enableGLSoftwareRendering, bool disableGpu)
{
return gl::kGLImplementationDisabledName;
}
@@ -687,6 +694,8 @@ WebEngineContext::WebEngineContext()
parsedCommandLine->AppendSwitch(sandbox::policy::switches::kNoSandbox);
qInfo() << "Sandboxing disabled by user.";
}
+ // Do not try to be clever with device-scale-factor, it messes up scaling in accessibility for us
+ parsedCommandLine->AppendSwitchASCII(switches::kEnableUseZoomForDSF, "false");
parsedCommandLine->AppendSwitch(switches::kEnableThreadedCompositing);
@@ -918,7 +927,7 @@ const char *qWebEngineChromiumVersion() noexcept
}
const char *qWebEngineChromiumSecurityPatchVersion() noexcept
{
- return "99.0.4844.84"; // FIXME: Remember to update
+ return "104.0.5112.81"; // FIXME: Remember to update
}
QT_END_NAMESPACE
diff --git a/src/core/web_engine_library_info.cpp b/src/core/web_engine_library_info.cpp
index 8f580e53a..151918bd7 100644
--- a/src/core/web_engine_library_info.cpp
+++ b/src/core/web_engine_library_info.cpp
@@ -59,6 +59,7 @@
#include <QFileInfo>
#include <QLibraryInfo>
#include <QLocale>
+#include <QLoggingCategory>
#include <QStandardPaths>
#if defined(OS_WIN)
@@ -71,6 +72,8 @@
using namespace QtWebEngineCore;
+Q_LOGGING_CATEGORY(webEngineLibraryInfoLog, "qt.webengine.libraryinfo")
+
namespace {
QString fallbackDir() {
@@ -84,7 +87,7 @@ static inline CFBundleRef frameworkBundle()
return CFBundleGetBundleWithIdentifier(CFSTR("org.qt-project.QtWebEngineCore"));
}
-static QString getPath(CFBundleRef frameworkBundle)
+static QString getBundlePath(CFBundleRef frameworkBundle)
{
QString path;
// The following is a fix for QtWebEngineProcess crashes on OS X 10.7 and before.
@@ -109,11 +112,11 @@ static QString getResourcesPath(CFBundleRef frameworkBundle)
// We use it for the other OS X versions as well to make sure it works and because
// the directory structure should be the same.
if (qApp->applicationName() == QLatin1String(QTWEBENGINEPROCESS_NAME)) {
- path = getPath(frameworkBundle) % QLatin1String("/Resources");
+ path = getBundlePath(frameworkBundle) % QLatin1String("/Resources");
} else if (frameworkBundle) {
CFURLRef resourcesRelativeUrl = CFBundleCopyResourcesDirectoryURL(frameworkBundle);
CFStringRef resourcesRelativePath = CFURLCopyFileSystemPath(resourcesRelativeUrl, kCFURLPOSIXPathStyle);
- path = getPath(frameworkBundle) % QLatin1Char('/') % QString::fromCFString(resourcesRelativePath);
+ path = getBundlePath(frameworkBundle) % QLatin1Char('/') % QString::fromCFString(resourcesRelativePath);
CFRelease(resourcesRelativePath);
CFRelease(resourcesRelativeUrl);
}
@@ -166,7 +169,7 @@ QString subProcessPath()
candidatePaths << fromEnv;
} else {
#if defined(OS_MAC) && defined(QT_MAC_FRAMEWORK_BUILD)
- candidatePaths << getPath(frameworkBundle())
+ candidatePaths << getBundlePath(frameworkBundle())
% QStringLiteral("/Helpers/" QTWEBENGINEPROCESS_NAME ".app/Contents/MacOS/" QTWEBENGINEPROCESS_NAME);
#else
candidatePaths << QLibraryInfo::path(QLibraryInfo::LibraryExecutablesPath)
@@ -181,11 +184,25 @@ QString subProcessPath()
for (const QString &candidate : qAsConst(candidatePaths)) {
if (QFileInfo::exists(candidate)) {
processPath = candidate;
+ qCDebug(webEngineLibraryInfoLog, "Qt WebEngine process path: %s",
+ qPrintable(candidate));
break;
}
}
- if (processPath.isEmpty())
- qFatal("Could not find %s", processBinary.toUtf8().constData());
+ if (processPath.isEmpty()) {
+ QStringList errorMessage;
+ errorMessage.append(
+ QStringLiteral("The following paths were searched for Qt WebEngine Process:"));
+ for (const QString &candidate : qAsConst(candidatePaths))
+ errorMessage.append(QStringLiteral(" ") % candidate);
+ errorMessage.append(QStringLiteral("but could not find it."));
+ if (fromEnv.isEmpty()) {
+ errorMessage.append(
+ QStringLiteral("You may override the default search path by using "
+ "QTWEBENGINEPROCESS_PATH environment variable."));
+ }
+ qFatal("%s", qPrintable(errorMessage.join('\n')));
+ }
#if defined(OS_WIN)
base::CommandLine *parsedCommandLine = base::CommandLine::ForCurrentProcess();
@@ -203,23 +220,55 @@ QString subProcessPath()
QString localesPath()
{
- static bool initialized = false;
- static QString potentialLocalesPath =
-#if defined(OS_MAC) && defined(QT_MAC_FRAMEWORK_BUILD)
- getResourcesPath(frameworkBundle()) % QLatin1String("/qtwebengine_locales");
+ static QString potentialLocalesPath;
+ if (potentialLocalesPath.isEmpty()) {
+ QStringList candidatePaths;
+ const QString translationPakFilename =
+#if QT_VERSION >= QT_VERSION_CHECK(6, 3, 0)
+ QLatin1String(WebEngineLibraryInfo::getResolvedLocale() + ".pak");
#else
- QLibraryInfo::path(QLibraryInfo::TranslationsPath) % QDir::separator() % QLatin1String("qtwebengine_locales");
+ QLatin1String((WebEngineLibraryInfo::getResolvedLocale() + ".pak").c_str());
#endif
+ const QString fromEnv = qEnvironmentVariable("QTWEBENGINE_LOCALES_PATH");
+ if (!fromEnv.isEmpty()) {
+ // Only search in QTWEBENGINE_LOCALES_PATH if set
+ candidatePaths << fromEnv;
+ } else {
+#if defined(OS_MAC) && defined(QT_MAC_FRAMEWORK_BUILD)
+ candidatePaths << getResourcesPath(frameworkBundle()) % QDir::separator()
+ % QLatin1String("qtwebengine_locales");
+#endif
+ candidatePaths << QLibraryInfo::path(QLibraryInfo::TranslationsPath) % QDir::separator()
+ % QLatin1String("qtwebengine_locales");
+ candidatePaths << fallbackDir();
+ }
- if (!initialized) {
- initialized = true;
- if (!QFileInfo::exists(potentialLocalesPath)) {
- qWarning("Installed Qt WebEngine locales directory not found at location %s. Trying application directory...", qPrintable(potentialLocalesPath));
- potentialLocalesPath = QCoreApplication::applicationDirPath() % QDir::separator() % QLatin1String("qtwebengine_locales");
+ for (const QString &candidate : qAsConst(candidatePaths)) {
+ if (QFileInfo::exists(candidate % QDir::separator() % translationPakFilename)) {
+ potentialLocalesPath = candidate;
+ qCDebug(webEngineLibraryInfoLog, "Qt WebEngine locales path: %s",
+ qPrintable(candidate));
+ break;
+ }
}
- if (!QFileInfo::exists(potentialLocalesPath)) {
- qWarning("Qt WebEngine locales directory not found at location %s. Trying fallback directory... Translations MAY NOT not be correct.", qPrintable(potentialLocalesPath));
- potentialLocalesPath = fallbackDir();
+
+ if (potentialLocalesPath.isEmpty()) {
+ QStringList warningMessage;
+ warningMessage.append(
+ QStringLiteral("The following paths were searched for Qt WebEngine locales:"));
+ for (const QString &candidate : qAsConst(candidatePaths))
+ warningMessage.append(QStringLiteral(" ") % candidate);
+ warningMessage.append(
+ QStringLiteral(
+ "but could not find the translation file for the current locale: ")
+ % translationPakFilename);
+ if (fromEnv.isEmpty()) {
+ warningMessage.append(
+ QStringLiteral("You may override the default search paths by using "
+ "QTWEBENGINE_LOCALES_PATH environment variable."));
+ }
+ warningMessage.append(QStringLiteral("Translations WILL NOT be correct."));
+ qWarning("%s", qPrintable(warningMessage.join('\n')));
}
}
@@ -265,6 +314,8 @@ QString dictionariesPath()
for (const QString &candidate : qAsConst(candidatePaths)) {
if (QFileInfo::exists(candidate)) {
potentialDictionariesPath = candidate;
+ qCDebug(webEngineLibraryInfoLog, "Qt WebEngine dictionaries path: %s",
+ qPrintable(candidate));
break;
}
}
@@ -274,28 +325,49 @@ QString dictionariesPath()
}
#endif // QT_CONFIG(webengine_spellchecker)
-QString resourcesDataPath()
+QString resourcesPath()
{
- static bool initialized = false;
- static QString potentialResourcesPath =
+ static QString potentialResourcesPath;
+ if (potentialResourcesPath.isEmpty()) {
+ QStringList candidatePaths;
+ const QString resourcesPakFilename = QLatin1String("qtwebengine_resources.pak");
+ const QString fromEnv = qEnvironmentVariable("QTWEBENGINE_RESOURCES_PATH");
+ if (!fromEnv.isEmpty()) {
+ // Only search in QTWEBENGINE_RESOURCES_PATH if set
+ candidatePaths << fromEnv;
+ } else {
#if defined(OS_MAC) && defined(QT_MAC_FRAMEWORK_BUILD)
- getResourcesPath(frameworkBundle());
-#else
- QLibraryInfo::path(QLibraryInfo::DataPath) % QLatin1String("/resources");
+ candidatePaths << getResourcesPath(frameworkBundle());
#endif
- if (!initialized) {
- initialized = true;
- if (!QFileInfo::exists(potentialResourcesPath % QLatin1String("/qtwebengine_resources.pak"))) {
- qWarning("Qt WebEngine resources not found at %s. Trying parent directory...", qPrintable(potentialResourcesPath));
- potentialResourcesPath = QLibraryInfo::path(QLibraryInfo::DataPath);
+ candidatePaths << QLibraryInfo::path(QLibraryInfo::DataPath) % QDir::separator()
+ % QLatin1String("resources");
+ candidatePaths << QLibraryInfo::path(QLibraryInfo::DataPath);
+ candidatePaths << QCoreApplication::applicationDirPath();
+ candidatePaths << fallbackDir();
}
- if (!QFileInfo::exists(potentialResourcesPath % QLatin1String("/qtwebengine_resources.pak"))) {
- qWarning("Qt WebEngine resources not found at %s. Trying application directory...", qPrintable(potentialResourcesPath));
- potentialResourcesPath = QCoreApplication::applicationDirPath();
+
+ for (const QString &candidate : qAsConst(candidatePaths)) {
+ if (QFileInfo::exists(candidate % QDir::separator() % resourcesPakFilename)) {
+ potentialResourcesPath = candidate;
+ qCDebug(webEngineLibraryInfoLog, "Qt WebEngine resources path: %s",
+ qPrintable(candidate));
+ break;
+ }
}
- if (!QFileInfo::exists(potentialResourcesPath % QLatin1String("/qtwebengine_resources.pak"))) {
- qWarning("Qt WebEngine resources not found at %s. Trying fallback directory... The application MAY NOT work.", qPrintable(potentialResourcesPath));
- potentialResourcesPath = fallbackDir();
+
+ if (potentialResourcesPath.isEmpty()) {
+ QStringList errorMessage;
+ errorMessage.append(QStringLiteral(
+ "The following paths were searched for Qt WebEngine resources:"));
+ for (const QString &candidate : qAsConst(candidatePaths))
+ errorMessage.append(QStringLiteral(" ") % candidate);
+ errorMessage.append(QStringLiteral("but could not find any."));
+ if (fromEnv.isEmpty()) {
+ errorMessage.append(
+ QStringLiteral("You may override the default search paths by using "
+ "QTWEBENGINE_RESOURCES_PATH environment variable."));
+ }
+ qFatal("%s", qPrintable(errorMessage.join('\n')));
}
}
@@ -308,13 +380,17 @@ base::FilePath WebEngineLibraryInfo::getPath(int key)
QString directory;
switch (key) {
case QT_RESOURCES_PAK:
- return toFilePath(resourcesDataPath() % QLatin1String("/qtwebengine_resources.pak"));
+ return toFilePath(resourcesPath() % QLatin1String("/qtwebengine_resources.pak"));
case QT_RESOURCES_100P_PAK:
- return toFilePath(resourcesDataPath() % QLatin1String("/qtwebengine_resources_100p.pak"));
+ return toFilePath(resourcesPath() % QLatin1String("/qtwebengine_resources_100p.pak"));
case QT_RESOURCES_200P_PAK:
- return toFilePath(resourcesDataPath() % QLatin1String("/qtwebengine_resources_200p.pak"));
+ return toFilePath(resourcesPath() % QLatin1String("/qtwebengine_resources_200p.pak"));
case QT_RESOURCES_DEVTOOLS_PAK:
- return toFilePath(resourcesDataPath() % QLatin1String("/qtwebengine_devtools_resources.pak"));
+ return toFilePath(resourcesPath() % QLatin1String("/qtwebengine_devtools_resources.pak"));
+#if defined(OS_MAC) && defined(QT_MAC_FRAMEWORK_BUILD)
+ case QT_FRAMEWORK_BUNDLE:
+ return toFilePath(getBundlePath(frameworkBundle()));
+#endif
case base::FILE_EXE:
case content::CHILD_PROCESS_EXE:
return toFilePath(subProcessPath());
@@ -330,7 +406,7 @@ base::FilePath WebEngineLibraryInfo::getPath(int key)
directory = QStandardPaths::writableLocation(QStandardPaths::DesktopLocation);
break;
case base::DIR_QT_LIBRARY_DATA:
- return toFilePath(resourcesDataPath());
+ return toFilePath(resourcesPath());
case ui::DIR_LOCALES:
return toFilePath(localesPath());
#if QT_CONFIG(webengine_spellchecker)
@@ -355,14 +431,16 @@ std::u16string WebEngineLibraryInfo::getApplicationName()
std::string WebEngineLibraryInfo::getResolvedLocale()
{
base::CommandLine *parsedCommandLine = base::CommandLine::ForCurrentProcess();
- if (parsedCommandLine->HasSwitch(switches::kLang)) {
- return parsedCommandLine->GetSwitchValueASCII(switches::kLang);
- } else {
- const QString &locale = QLocale().bcp47Name();
- std::string resolvedLocale;
- if (l10n_util::CheckAndResolveLocale(locale.toStdString(), &resolvedLocale))
- return resolvedLocale;
- }
+ std::string locale;
+ if (parsedCommandLine->HasSwitch(switches::kLang))
+ locale = parsedCommandLine->GetSwitchValueASCII(switches::kLang);
+ else
+ locale = QLocale().bcp47Name().toStdString();
+
+ std::string resolvedLocale;
+ if (l10n_util::CheckAndResolveLocale(locale, &resolvedLocale))
+ return resolvedLocale;
+
return "en-US";
}
diff --git a/src/core/web_engine_library_info.h b/src/core/web_engine_library_info.h
index 2926365bf..10542a99e 100644
--- a/src/core/web_engine_library_info.h
+++ b/src/core/web_engine_library_info.h
@@ -48,7 +48,8 @@ enum {
QT_RESOURCES_PAK = 5000,
QT_RESOURCES_100P_PAK = 5001,
QT_RESOURCES_200P_PAK = 5002,
- QT_RESOURCES_DEVTOOLS_PAK = 5003
+ QT_RESOURCES_DEVTOOLS_PAK = 5003,
+ QT_FRAMEWORK_BUNDLE = 5004
};
class WebEngineLibraryInfo {
diff --git a/src/gn/CMakeLists.txt b/src/gn/CMakeLists.txt
index a76d1dcee..37665465d 100644
--- a/src/gn/CMakeLists.txt
+++ b/src/gn/CMakeLists.txt
@@ -36,6 +36,7 @@ add_custom_command(
--cc ${CMAKE_C_COMPILER}
--cxx ${CMAKE_CXX_COMPILER}
--ld ${CMAKE_CXX_COMPILER}
+ --ar ${CMAKE_AR}
--qt-version "${QT_REPO_MODULE_VERSION}.qtwebengine.qt.io"
$<$<PLATFORM_ID:Darwin>:--isysroot>
$<$<PLATFORM_ID:Darwin>:${CMAKE_OSX_SYSROOT}>
diff --git a/src/pdf/configure.cmake b/src/pdf/configure.cmake
index a252d7da6..8d1a07183 100644
--- a/src/pdf/configure.cmake
+++ b/src/pdf/configure.cmake
@@ -1,6 +1,7 @@
qt_feature("pdf-v8" PRIVATE
LABEL "Support V8"
PURPOSE "Enables javascript support."
+ AUTODETECT FALSE
CONDITION NOT IOS
)
qt_feature("pdf-xfa" PRIVATE
diff --git a/src/pdf/doc/qtpdf.qdocconf b/src/pdf/doc/qtpdf.qdocconf
index 24f7d8b51..85d0a7c4d 100644
--- a/src/pdf/doc/qtpdf.qdocconf
+++ b/src/pdf/doc/qtpdf.qdocconf
@@ -1,4 +1,5 @@
include($QT_INSTALL_DOCS/global/qt-module-defaults.qdocconf)
+include($QT_INSTALL_DOCS/config/exampleurl-qtwebengine.qdocconf)
project = QtPdf
description = Qt Pdf Reference Documentation
diff --git a/src/webenginequick/api/qquickwebengineprofile.cpp b/src/webenginequick/api/qquickwebengineprofile.cpp
index ec7365064..63e2b84fe 100644
--- a/src/webenginequick/api/qquickwebengineprofile.cpp
+++ b/src/webenginequick/api/qquickwebengineprofile.cpp
@@ -181,6 +181,8 @@ QQuickWebEngineProfilePrivate::~QQuickWebEngineProfilePrivate()
if (m_profileAdapter != QtWebEngineCore::ProfileAdapter::defaultProfileAdapter())
delete m_profileAdapter;
+ else if (m_profileAdapter)
+ m_profileAdapter->releaseAllWebContentsAdapterClients();
}
void QQuickWebEngineProfilePrivate::addWebContentsAdapterClient(QtWebEngineCore::WebContentsAdapterClient *adapter)
diff --git a/src/webenginequick/api/qquickwebenginesingleton.cpp b/src/webenginequick/api/qquickwebenginesingleton.cpp
index 6c4e6fb68..bffa923de 100644
--- a/src/webenginequick/api/qquickwebenginesingleton.cpp
+++ b/src/webenginequick/api/qquickwebenginesingleton.cpp
@@ -117,6 +117,7 @@ QWebEngineScript QQuickWebEngineSingleton::script() const
return QWebEngineScript();
}
+QT_END_NAMESPACE
+
#include "moc_qquickwebenginesingleton_p.cpp"
-QT_END_NAMESPACE
diff --git a/src/webenginequick/doc/snippets/qtwebengine_build_snippet.qdoc b/src/webenginequick/doc/snippets/qtwebengine_build_snippet.qdoc
index b21efbdf9..ac3526540 100644
--- a/src/webenginequick/doc/snippets/qtwebengine_build_snippet.qdoc
+++ b/src/webenginequick/doc/snippets/qtwebengine_build_snippet.qdoc
@@ -35,6 +35,6 @@ QT += webenginequick
//! [1]
//! [2]
-find_package(Qt6 COMPONENTS WebEngineQuick REQUIRED)
+find_package(Qt6 REQUIRED COMPONENTS WebEngineQuick)
target_link_libraries(target PRIVATE Qt::WebEngineQuick)
//! [2]
diff --git a/src/webenginewidgets/api/qwebengineview.cpp b/src/webenginewidgets/api/qwebengineview.cpp
index 6a22a887e..0ed67edab 100644
--- a/src/webenginewidgets/api/qwebengineview.cpp
+++ b/src/webenginewidgets/api/qwebengineview.cpp
@@ -267,6 +267,10 @@ void QWebEngineViewPrivate::showColorDialog(
QColorDialog::connect(dialog, SIGNAL(colorSelected(QColor)), dialog, SLOT(deleteLater()));
QColorDialog::connect(dialog, SIGNAL(rejected()), dialog, SLOT(deleteLater()));
+#if defined(Q_OS_MACOS)
+ dialog->setOption(QColorDialog::DontUseNativeDialog);
+#endif
+
dialog->open();
#else
Q_UNUSED(controller);
diff --git a/src/webenginewidgets/doc/snippets/qtwebenginewidgets_build_snippet.qdoc b/src/webenginewidgets/doc/snippets/qtwebenginewidgets_build_snippet.qdoc
index f48932eae..e598f7746 100644
--- a/src/webenginewidgets/doc/snippets/qtwebenginewidgets_build_snippet.qdoc
+++ b/src/webenginewidgets/doc/snippets/qtwebenginewidgets_build_snippet.qdoc
@@ -35,6 +35,6 @@ QT += webenginewidgets
//! [1]
//! [2]
-find_package(Qt6 COMPONENTS WebEngineWidgets REQUIRED)
+find_package(Qt6 REQUIRED COMPONENTS WebEngineWidgets)
target_link_libraries(target PRIVATE Qt::WebEngineWidgets)
//! [2]
diff --git a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp
index 986c1e650..ef2549bb5 100644
--- a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp
+++ b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp
@@ -282,6 +282,10 @@ void RenderWidgetHostViewQtDelegateWidget::show()
// want to show anything else than popups as top-level.
if (parent() || m_isPopup) {
QQuickWidget::show();
+
+ QWebEngineView *view = static_cast<QWebEngineView *>(parent());
+ if (view && view->isWindow())
+ update();
}
}
diff --git a/tests/auto/core/qwebengineurlrequestinterceptor/tst_qwebengineurlrequestinterceptor.cpp b/tests/auto/core/qwebengineurlrequestinterceptor/tst_qwebengineurlrequestinterceptor.cpp
index 14d045613..614d05d75 100644
--- a/tests/auto/core/qwebengineurlrequestinterceptor/tst_qwebengineurlrequestinterceptor.cpp
+++ b/tests/auto/core/qwebengineurlrequestinterceptor/tst_qwebengineurlrequestinterceptor.cpp
@@ -727,7 +727,7 @@ void tst_QWebEngineUrlRequestInterceptor::jsServiceWorker()
server.setResourceDirs({ QDir(QT_TESTCASE_SOURCEDIR).canonicalPath() + "/resources" });
QVERIFY(server.start());
- QWebEngineProfile profile(QStringLiteral("Test"));
+ QWebEngineProfile profile;
std::unique_ptr<ConsolePage> page;
page.reset(new ConsolePage(&profile));
TestRequestInterceptor interceptor(/* intercept */ false);
diff --git a/tests/auto/pdf/qpdfdocument/tst_qpdfdocument.cpp b/tests/auto/pdf/qpdfdocument/tst_qpdfdocument.cpp
index a0f73bb88..a77906d9b 100644
--- a/tests/auto/pdf/qpdfdocument/tst_qpdfdocument.cpp
+++ b/tests/auto/pdf/qpdfdocument/tst_qpdfdocument.cpp
@@ -89,7 +89,7 @@ struct TemporaryPdf: public QTemporaryFile
};
-TemporaryPdf::TemporaryPdf()
+TemporaryPdf::TemporaryPdf():QTemporaryFile(QStringLiteral("qpdfdocument"))
{
open();
pageLayout = QPageLayout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF());
diff --git a/tests/auto/quick/CMakeLists.txt b/tests/auto/quick/CMakeLists.txt
index d44d67d38..48a83e7de 100644
--- a/tests/auto/quick/CMakeLists.txt
+++ b/tests/auto/quick/CMakeLists.txt
@@ -2,7 +2,10 @@ add_subdirectory(dialogs)
add_subdirectory(publicapi)
add_subdirectory(qquickwebenginedefaultsurfaceformat)
add_subdirectory(qtbug-70248)
-add_subdirectory(uidelegates)
+# Re-enable if QTBUG-101744 and QTBUG-103354 have been fixed.
+if(NOT MACOS)
+ add_subdirectory(uidelegates)
+endif()
add_subdirectory(inspectorserver)
add_subdirectory(qmltests)
add_subdirectory(qquickwebengineview)
diff --git a/tests/auto/quick/qmltests/data/tst_favicon.qml b/tests/auto/quick/qmltests/data/tst_favicon.qml
index 79c835c70..ce4a2aa3c 100644
--- a/tests/auto/quick/qmltests/data/tst_favicon.qml
+++ b/tests/auto/quick/qmltests/data/tst_favicon.qml
@@ -165,6 +165,38 @@ TestWebEngineView {
compare(iconUrl, Qt.resolvedUrl("icons/qt32.ico"))
}
+ function test_faviconLoadPushState_data() {
+ return [
+ { tag: "OTR", profile: defaultProfile },
+ { tag: "non-OTR", profile: nonOTRProfile },
+ ];
+ }
+
+ function test_faviconLoadPushState(row) {
+ webEngineView.profile = row.profile;
+ compare(iconChangedSpy.count, 0);
+
+ var iconUrl;
+
+ webEngineView.url = Qt.resolvedUrl("favicon.html");
+ verify(webEngineView.waitForLoadSucceeded());
+ tryCompare(iconChangedSpy, "count", 1);
+ iconUrl = removeFaviconProviderPrefix(webEngineView.icon);
+ compare(iconUrl, Qt.resolvedUrl("icons/favicon.png"));
+
+ iconChangedSpy.clear();
+
+ // pushState() is a same document navigation and should not reset or
+ // update favicon.
+ compare(webEngineView.history.items.rowCount(), 1);
+ runJavaScript("history.pushState('', '')");
+ tryVerify(function() { return webEngineView.history.items.rowCount() === 2; });
+
+ // Favicon change is not expected.
+ compare(iconChangedSpy.count, 0);
+ iconUrl = removeFaviconProviderPrefix(webEngineView.icon);
+ compare(iconUrl, Qt.resolvedUrl("icons/favicon.png"));
+ }
function test_noFavicon_data() {
return [
diff --git a/tests/auto/widgets/favicon/tst_favicon.cpp b/tests/auto/widgets/favicon/tst_favicon.cpp
index d8b4803c0..6b5ae3c02 100644
--- a/tests/auto/widgets/favicon/tst_favicon.cpp
+++ b/tests/auto/widgets/favicon/tst_favicon.cpp
@@ -29,6 +29,7 @@
#include <QtTest/QtTest>
#include <util.h>
+#include <QWebEngineHistory>
#include <QWebEnginePage>
#include <QWebEngineProfile>
#include <QWebEngineSettings>
@@ -49,6 +50,7 @@ private Q_SLOTS:
void faviconLoadFromResources();
void faviconLoadEncodedUrl();
void faviconLoadAfterHistoryNavigation();
+ void faviconLoadPushState();
void noFavicon();
void aboutBlank();
void unavailableFavicon();
@@ -222,6 +224,41 @@ void tst_Favicon::faviconLoadAfterHistoryNavigation()
QCOMPARE(m_page->iconUrl(), QUrl("qrc:/resources/icons/qtmulti.ico"));
}
+void tst_Favicon::faviconLoadPushState()
+{
+ 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_WITH_TIMEOUT(loadFinishedSpy.count(), 1, 30000);
+ 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());
+
+ iconUrlChangedSpy.clear();
+ iconChangedSpy.clear();
+
+ // pushState() is a same document navigation and should not reset or
+ // update favicon.
+ QCOMPARE(m_page->history()->count(), 1);
+ evaluateJavaScriptSync(m_page, "history.pushState('', '')");
+ QTRY_COMPARE(m_page->history()->count(), 2);
+
+ // Favicon change is not expected.
+ QCOMPARE(iconUrlChangedSpy.count(), 0);
+ QCOMPARE(iconChangedSpy.count(), 0);
+ QCOMPARE(m_page->iconUrl(), QUrl("qrc:/resources/icons/qt32.ico"));
+}
+
void tst_Favicon::noFavicon()
{
if (!QDir(QDir(QT_TESTCASE_SOURCEDIR).canonicalPath()).exists())
diff --git a/tests/auto/widgets/proxypac/CMakeLists.txt b/tests/auto/widgets/proxypac/CMakeLists.txt
index 1dd2c8bec..d3ddfd0c5 100644
--- a/tests/auto/widgets/proxypac/CMakeLists.txt
+++ b/tests/auto/widgets/proxypac/CMakeLists.txt
@@ -21,6 +21,22 @@ set_tests_properties(tst_proxypac_file PROPERTIES
ENVIRONMENT QTWEBENGINE_CHROMIUM_FLAGS=${fileEnvArg}
)
+if(NOT (LINUX AND CMAKE_CROSSCOMPILING))
+ set(fileEnvArg "--single-process ${fileEnvArg}")
+
+ qt_internal_add_test(tst_proxypac_single_process
+ SOURCES
+ tst_proxypac.cpp
+ LIBRARIES
+ Qt::WebEngineCore
+ Test::HttpServer
+ )
+
+ set_tests_properties(tst_proxypac_single_process PROPERTIES
+ ENVIRONMENT QTWEBENGINE_CHROMIUM_FLAGS=${fileEnvArg}
+ )
+endif()
+
qt_internal_add_test(tst_proxypac_qrc
SOURCES
tst_proxypac.cpp
@@ -40,8 +56,6 @@ set_tests_properties(tst_proxypac_qrc PROPERTIES
)
qt_internal_add_resource(tst_proxypac_qrc "proxypac"
- PREFIX
- "/"
- FILES
- "proxy.pac"
+ PREFIX "/"
+ FILES "proxy.pac"
)
diff --git a/tests/auto/widgets/proxypac/proxy.pac b/tests/auto/widgets/proxypac/proxy.pac
index 1d29847b9..966c37ba5 100644
--- a/tests/auto/widgets/proxypac/proxy.pac
+++ b/tests/auto/widgets/proxypac/proxy.pac
@@ -2,6 +2,6 @@ function FindProxyForURL(url, host)
{
if (shExpMatch(host, "*.proxy1.com")) return "PROXY localhost:5551";
if (shExpMatch(host, "*.proxy2.com")) return "PROXY localhost:5552";
- return "PROXY proxy.url:8080";
+ return "DIRECT";
}
diff --git a/tests/auto/widgets/proxypac/tst_proxypac.cpp b/tests/auto/widgets/proxypac/tst_proxypac.cpp
index 223c995e0..0b218aef9 100644
--- a/tests/auto/widgets/proxypac/tst_proxypac.cpp
+++ b/tests/auto/widgets/proxypac/tst_proxypac.cpp
@@ -33,7 +33,6 @@
#include <QWebEnginePage>
#include <QNetworkProxy>
-
class tst_ProxyPac : public QObject {
Q_OBJECT
public:
@@ -64,11 +63,20 @@ void tst_ProxyPac::proxypac()
QWebEngineProfile profile;
QWebEnginePage page(&profile);
+
+ const bool v8_proxy_resolver_enabled = !fromEnv.contains("--single-process");
page.load(QUrl("http://test.proxy1.com"));
- QTRY_COMPARE(proxySpy1.count() >= 1, true);
+ QTRY_COMPARE(proxySpy1.count() >= 1, v8_proxy_resolver_enabled);
QVERIFY(proxySpy2.count() == 0);
page.load(QUrl("http://test.proxy2.com"));
- QTRY_COMPARE(proxySpy2.count() >= 1 , true);
+ QTRY_COMPARE(proxySpy2.count() >= 1, v8_proxy_resolver_enabled);
+
+ // check for crash
+ QSignalSpy spyFinished(&page, &QWebEnginePage::loadFinished);
+ page.load(QUrl("https://contribute.qt-project.org"));
+
+ QTRY_VERIFY_WITH_TIMEOUT(!spyFinished.isEmpty(), 100000);
+
}
#include "tst_proxypac.moc"
diff --git a/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp b/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
index 227f33c17..32f866810 100644
--- a/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
+++ b/tests/auto/widgets/qwebenginepage/tst_qwebenginepage.cpp
@@ -257,6 +257,8 @@ private Q_SLOTS:
void testChooseFilesParameters();
void fileSystemAccessDialog();
+ void localToRemoteNavigation();
+
private:
static QPoint elementCenter(QWebEnginePage *page, const QString &id);
static bool isFalseJavaScriptResult(QWebEnginePage *page, const QString &javaScript);
@@ -328,6 +330,14 @@ void tst_QWebEnginePage::initTestCase()
QWebEngineUrlScheme echo("echo");
echo.setSyntax(QWebEngineUrlScheme::Syntax::Path);
QWebEngineUrlScheme::registerScheme(echo);
+
+ QWebEngineUrlScheme local("local");
+ local.setFlags(QWebEngineUrlScheme::LocalScheme);
+ QWebEngineUrlScheme::registerScheme(local);
+
+ QWebEngineUrlScheme remote("remote");
+ remote.setFlags(QWebEngineUrlScheme::CorsEnabled);
+ QWebEngineUrlScheme::registerScheme(remote);
}
void tst_QWebEnginePage::cleanupTestCase()
@@ -5010,6 +5020,61 @@ void tst_QWebEnginePage::isSafeRedirect()
spy.clear();
}
+class LocalRemoteUrlSchemeHandler : public QWebEngineUrlSchemeHandler
+{
+public:
+ LocalRemoteUrlSchemeHandler(QObject *parent = nullptr)
+ : QWebEngineUrlSchemeHandler(parent)
+ {
+ }
+ ~LocalRemoteUrlSchemeHandler() = default;
+
+ void requestStarted(QWebEngineUrlRequestJob *job) override
+ {
+ QBuffer *buffer = new QBuffer(job);
+ buffer->setData("<html><body><a href='remote://test.html' id='link'>Click link</a></body></html>");
+ job->reply("text/html", buffer);
+ loaded = true;
+ }
+ bool loaded = false;
+};
+
+void tst_QWebEnginePage::localToRemoteNavigation()
+{
+ LocalRemoteUrlSchemeHandler local;
+ LocalRemoteUrlSchemeHandler remote;
+ QWebEngineProfile profile;
+ profile.installUrlSchemeHandler("local", &local);
+ profile.installUrlSchemeHandler("remote", &remote);
+
+ QWebEnginePage page(&profile);
+ QSignalSpy loadSpy(&page, SIGNAL(loadFinished(bool)));
+ QWebEngineView view;
+ view.resize(640, 480);
+ view.show();
+ view.setPage(&page);
+ page.setUrl(QUrl("local://test.html"));
+ QVERIFY(QTest::qWaitForWindowExposed(&view));
+ QTRY_COMPARE_WITH_TIMEOUT(loadSpy.count(), 1, 20000);
+ QVERIFY(local.loaded);
+
+ // Should navigate:
+ QTest::mouseClick(view.focusProxy(), Qt::LeftButton, {}, elementCenter(&page, "link"));
+ QTRY_COMPARE_WITH_TIMEOUT(loadSpy.count(), 2, 20000);
+ QVERIFY(remote.loaded);
+ local.loaded = false;
+ remote.loaded = false;
+
+ page.setUrl(QUrl("local://test.html"));
+ QTRY_COMPARE_WITH_TIMEOUT(loadSpy.count(), 3, 20000);
+ QVERIFY(local.loaded && !remote.loaded);
+
+ // Should not navigate:
+ page.runJavaScript(QStringLiteral("document.getElementById(\"link\").click()"));
+ QTest::qWait(500);
+ QVERIFY(!remote.loaded);
+}
+
static QByteArrayList params = {QByteArrayLiteral("--use-fake-device-for-media-stream")};
W_QTEST_MAIN(tst_QWebEnginePage, params)
diff --git a/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp b/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
index c09f3b51a..ee4f5990e 100644
--- a/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
+++ b/tests/auto/widgets/qwebengineprofile/tst_qwebengineprofile.cpp
@@ -66,6 +66,7 @@ private Q_SLOTS:
void urlSchemeHandlerFailRequest();
void urlSchemeHandlerFailOnRead();
void urlSchemeHandlerStreaming();
+ void urlSchemeHandlerStreaming2();
void urlSchemeHandlerRequestHeaders();
void urlSchemeHandlerInstallation();
void urlSchemeHandlerXhrStatus();
@@ -289,10 +290,12 @@ public:
QList<QPointer<QBuffer>> m_buffers;
};
-class StreamingIODevice : public QIODevice {
+// an evil version constantly claiming to be at end, similar to QNetworkReply
+class StreamingIODeviceBasic : public QIODevice
+{
Q_OBJECT
public:
- StreamingIODevice(QObject *parent) : QIODevice(parent), m_bytesRead(0), m_bytesAvailable(0)
+ StreamingIODeviceBasic(QObject *parent) : QIODevice(parent), m_bytesRead(0), m_bytesAvailable(0)
{
setOpenMode(QIODevice::ReadOnly);
m_timer.start(100, this);
@@ -303,12 +306,11 @@ public:
const std::lock_guard<QRecursiveMutex> lock(m_mutex);
return m_bytesAvailable;
}
- bool atEnd() const override
+protected:
+ bool internalAtEnd() const
{
- const std::lock_guard<QRecursiveMutex> lock(m_mutex);
return (m_data.size() >= 1000 && m_bytesRead >= 1000);
}
-protected:
void timerEvent(QTimerEvent *) override
{
const std::lock_guard<QRecursiveMutex> lock(m_mutex);
@@ -329,7 +331,7 @@ protected:
memcpy(data, m_data.constData() + m_bytesRead, len);
m_bytesAvailable -= len;
m_bytesRead += len;
- } else if (atEnd())
+ } else if (internalAtEnd())
return -1;
return len;
@@ -339,14 +341,26 @@ protected:
return 0;
}
-private:
mutable QRecursiveMutex m_mutex;
+private:
QByteArray m_data;
QBasicTimer m_timer;
int m_bytesRead;
int m_bytesAvailable;
};
+// A nicer version implementing atEnd
+class StreamingIODevice : public StreamingIODeviceBasic
+{
+public:
+ StreamingIODevice(QObject *parent) : StreamingIODeviceBasic(parent) {}
+ bool atEnd() const override
+ {
+ const std::lock_guard<QRecursiveMutex> lock(m_mutex);
+ return internalAtEnd();
+ }
+};
+
class StreamingUrlSchemeHandler : public QWebEngineUrlSchemeHandler
{
public:
@@ -361,6 +375,20 @@ public:
}
};
+class StreamingUrlSchemeHandler2 : public QWebEngineUrlSchemeHandler
+{
+public:
+ StreamingUrlSchemeHandler2(QObject *parent = nullptr)
+ : QWebEngineUrlSchemeHandler(parent)
+ {
+ }
+
+ void requestStarted(QWebEngineUrlRequestJob *job) override
+ {
+ job->reply("text/plain;charset=utf-8", new StreamingIODeviceBasic(job));
+ }
+};
+
void tst_QWebEngineProfile::urlSchemeHandlers()
{
RedirectingUrlSchemeHandler lettertoHandler;
@@ -502,6 +530,23 @@ void tst_QWebEngineProfile::urlSchemeHandlerStreaming()
QCOMPARE(toPlainTextSync(view.page()), QString::fromLatin1(result));
}
+void tst_QWebEngineProfile::urlSchemeHandlerStreaming2()
+{
+ StreamingUrlSchemeHandler2 handler;
+ QWebEngineProfile profile;
+ profile.installUrlSchemeHandler("stream", &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("stream://whatever")));
+ view.show();
+ QTRY_COMPARE_WITH_TIMEOUT(loadFinishedSpy.count(), 1, 30000);
+ QByteArray result;
+ result.append(1000, 'c');
+ QCOMPARE(toPlainTextSync(view.page()), QString::fromLatin1(result));
+}
+
class ExtraHeaderInterceptor : public QWebEngineUrlRequestInterceptor
{
public:
diff --git a/tests/auto/widgets/touchinput/tst_touchinput.cpp b/tests/auto/widgets/touchinput/tst_touchinput.cpp
index 957f3e74c..e3ee9f933 100644
--- a/tests/auto/widgets/touchinput/tst_touchinput.cpp
+++ b/tests/auto/widgets/touchinput/tst_touchinput.cpp
@@ -81,17 +81,17 @@ private:
auto target = view.focusProxy();
QPoint p(target->width() / 2, target->height() / 4 * (down ? 3 : 1));
- QTest::touchEvent(target, s_touchDevice).press(42, p, target);
+ QTest::touchEvent(target, s_touchDevice).press(1, p, target);
QSignalSpy spy(view.page(), &QWebEnginePage::scrollPositionChanged);
for (int i = 0; i < 3; ++i) {
down ? p -= QPoint(5, 15) : p += QPoint(5, 15);
QTest::qWait(100); // too fast and events are recognized as fling gesture
- QTest::touchEvent(target, s_touchDevice).move(42, p, target);
+ QTest::touchEvent(target, s_touchDevice).move(1, p, target);
spy.wait();
}
- QTest::touchEvent(target, s_touchDevice).release(42, p, target);
+ QTest::touchEvent(target, s_touchDevice).release(1, p, target);
}
void gesturePinch(bool zoomIn, bool tapOneByOne = false) {
@@ -100,10 +100,10 @@ private:
auto t1 = p - QPoint(zoomIn ? 50 : 150, 10), t2 = p + QPoint(zoomIn ? 50 : 150, 10);
if (tapOneByOne) {
- QTest::touchEvent(target, s_touchDevice).press(42, t1, target);
- QTest::touchEvent(target, s_touchDevice).stationary(42).press(24, t2, target);
+ QTest::touchEvent(target, s_touchDevice).press(0, t1, target);
+ QTest::touchEvent(target, s_touchDevice).stationary(0).press(1, t2, target);
} else {
- QTest::touchEvent(target, s_touchDevice).press(42, t1, target).press(24, t2, target);
+ QTest::touchEvent(target, s_touchDevice).press(0, t1, target).press(1, t2, target);
}
for (int i = 0; i < 3; ++i) {
@@ -115,14 +115,14 @@ private:
t2 -= QPoint(35, 5);
}
QTest::qWait(100); // too fast and events are recognized as fling gesture
- QTest::touchEvent(target, s_touchDevice).move(24, t1, target).move(42, t2, target);
+ QTest::touchEvent(target, s_touchDevice).move(1, t1, target).move(0, t2, target);
}
if (tapOneByOne) {
- QTest::touchEvent(target, s_touchDevice).stationary(42).release(24, t2, target);
- QTest::touchEvent(target, s_touchDevice).release(42, t1, target);
+ QTest::touchEvent(target, s_touchDevice).stationary(0).release(1, t2, target);
+ QTest::touchEvent(target, s_touchDevice).release(0, t1, target);
} else {
- QTest::touchEvent(target, s_touchDevice).release(42, t1, target).release(24, t2, target);
+ QTest::touchEvent(target, s_touchDevice).release(0, t1, target).release(1, t2, target);
}
}