From 23700154de28de62b200fd1e1f503e618166573e Mon Sep 17 00:00:00 2001 From: Taeyeon Mori Date: Fri, 1 Nov 2024 17:52:10 +0100 Subject: [PATCH] feat: Add Qt 6 support (#209) * qt6: webengine(quick) module no longer required Relevant componets were moved to webenginecore * qt6: QWebEngineDownloadRequest QWebEngineDownloadItem was renamed to QWebEngineDownloadRequest and the downloadProgress signal was split into receivedBytesChanged and totalBytesChanged signals * qt6: QWebEnginePage::view() polyfill QWebEnginePage was moved to the webenginecore module in Qt6. As such, it cannot reference QWidget from the widgets module. QWebEnginePage::view() was replaced by QWebEngineView::forPage() from the webenginewidgets module. * qt6: QWebEnginePage::certificateError() is now a signal QWebEnginePage::certificateError() was changed from an overridable method to a signal in Qt6. The response actions are now methods on the QWebEngineCertificateError object. For some reason, said object is passed as const reference and must be const_cast before applying a resolution. * qt6: QWebEngineContextMenuRequest QWebEngineContextMenuData was renamed to QWebEngineContextMenuRequest in Qt6. The related methods were moved from QWebEnginePage (which moved to the webenginecore module) to QWebEngineView. * qt6: QWebEngineSettings::defaultSettings() removal QWebEngineSettings::defaultSettings() was removed in Qt6, use QWebEngineProfile::defaultProfile()->settings() insteadd. * qt6: QStandardPaths::DataLocation removal QStandardPaths::DataLocation was already deprecated in Qt5 and removed in Qt6. It was an alias for QStandardPaths::AppLocalDataLocation. * qt6: QDesktopWidget removal QDesktopWidget (and QApplication::desktop()) was removed in Qt6 * qt6: Use QString::fromUtf8() instead of QTextCodec QTextCodec was removed (movec to core5compat) in Qt6. * qt6: QGeoPositionInfoSource::updateTimeout removal The QGeoPositionInfoSource::updateTimeout signal was removed in Qt6, with it's functionality taken over by the QGeoPositionInfoSource::errorOccured signal. * qt6: QDateTime::toTime_t() removal QDateTime::toTime_t() was already deprecated and replaced with QDateTime::toSecsSinceEpoch() in Qt5. It was removed in Qt6. * qt6: Fix some deprecation warnings --- src/WhatsApp.pro | 4 +++- src/automatictheme.cpp | 8 ++++++-- src/downloadmanagerwidget.h | 10 ++++++---- src/downloadwidget.cpp | 8 +++++++- src/downloadwidget.h | 9 ++++++--- src/main.cpp | 21 +++++++++++++-------- src/mainwindow.cpp | 19 +++++++++---------- src/mainwindow.h | 1 - src/notificationpopup.h | 10 +++------- src/utils.cpp | 2 +- src/webenginepage.cpp | 29 ++++++++++++++++++++++++++--- src/webenginepage.h | 17 ++++++++++++++++- src/webview.cpp | 19 ++++++++++++++++--- src/widgets/MoreApps/moreapps.cpp | 6 +++--- 14 files changed, 115 insertions(+), 48 deletions(-) diff --git a/src/WhatsApp.pro b/src/WhatsApp.pro index 881963a..5d5ed16 100644 --- a/src/WhatsApp.pro +++ b/src/WhatsApp.pro @@ -23,7 +23,9 @@ equals(QMAKE_HOST.arch, aarch64) { # Uncomment if you need specific linker flags as well #QMAKE_LFLAGS += $$QMAKE_LDFLAGS -QT += core gui webengine webenginewidgets positioning +QT += core gui webenginewidgets positioning + +lessThan(QT_MAJOR_VERSION, 6): QT += webengine CONFIG += c++17 diff --git a/src/automatictheme.cpp b/src/automatictheme.cpp index 9b1f3e7..a4d9fc5 100644 --- a/src/automatictheme.cpp +++ b/src/automatictheme.cpp @@ -47,7 +47,11 @@ AutomaticTheme::AutomaticTheme(QWidget *parent) ui->refresh->setEnabled(false); } }); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(m_gPosInfoSrc, &QGeoPositionInfoSource::errorOccurred, this, [=]() { +#else connect(m_gPosInfoSrc, &QGeoPositionInfoSource::updateTimeout, this, [=]() { +#endif if (!SettingsManager::instance().settings().value("sunrise").isValid() || !SettingsManager::instance().settings().value("sunset").isValid()) { if (ui->refresh->isEnabled()) @@ -77,9 +81,9 @@ void AutomaticTheme::on_refresh_clicked() { if (geoCor.isValid()) { Sunclock sun(this->m_latitube, this->m_longitude, this->m_hourOffset); m_sunrise.setSecsSinceEpoch( - sun.sunrise(QDateTime::currentDateTimeUtc().toTime_t())); + sun.sunrise(QDateTime::currentDateTimeUtc().toSecsSinceEpoch())); m_sunset.setSecsSinceEpoch( - sun.sunset(QDateTime::currentDateTimeUtc().toTime_t())); + sun.sunset(QDateTime::currentDateTimeUtc().toSecsSinceEpoch())); ui->sunrise->setTime(m_sunrise.time()); ui->sunset->setTime(m_sunset.time()); diff --git a/src/downloadmanagerwidget.h b/src/downloadmanagerwidget.h index 8367041..b5b88cb 100644 --- a/src/downloadmanagerwidget.h +++ b/src/downloadmanagerwidget.h @@ -57,12 +57,14 @@ #include #include -#include #include -QT_BEGIN_NAMESPACE -class QWebEngineDownloadItem; -QT_END_NAMESPACE +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +using QWebEngineDownloadItem = QWebEngineDownloadRequest; +#else +#include +#endif class DownloadWidget; diff --git a/src/downloadwidget.cpp b/src/downloadwidget.cpp index bdc974d..82e555a 100644 --- a/src/downloadwidget.cpp +++ b/src/downloadwidget.cpp @@ -4,7 +4,6 @@ #include #include #include -#include DownloadWidget::DownloadWidget(QWebEngineDownloadItem *download, QWidget *parent) @@ -38,8 +37,15 @@ DownloadWidget::DownloadWidget(QWebEngineDownloadItem *download, emit removeClicked(this); }); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(m_download, &QWebEngineDownloadItem::receivedBytesChanged, this, + &DownloadWidget::updateWidget); + connect(m_download, &QWebEngineDownloadItem::totalBytesChanged, this, + &DownloadWidget::updateWidget); +#else connect(m_download, &QWebEngineDownloadItem::downloadProgress, this, &DownloadWidget::updateWidget); +#endif connect(m_download, &QWebEngineDownloadItem::stateChanged, this, &DownloadWidget::updateWidget); diff --git a/src/downloadwidget.h b/src/downloadwidget.h index 4417cb4..9607fac 100644 --- a/src/downloadwidget.h +++ b/src/downloadwidget.h @@ -58,9 +58,12 @@ #include #include -QT_BEGIN_NAMESPACE -class QWebEngineDownloadItem; -QT_END_NAMESPACE +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +using QWebEngineDownloadItem = QWebEngineDownloadRequest; +#else +#include +#endif // Displays one ongoing or finished download (QWebEngineDownloadItem). class DownloadWidget final : public QFrame, public Ui::DownloadWidget { diff --git a/src/main.cpp b/src/main.cpp index 1d5efe9..65bfd7d 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -2,9 +2,14 @@ #include #include #include -#include #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +#else +#include +#endif + #include "common.h" #include "def.h" #include "mainwindow.h" @@ -13,7 +18,9 @@ int main(int argc, char *argv[]) { +#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0) QApplication::setAttribute(Qt::AA_EnableHighDpiScaling); +#endif #ifdef QT_DEBUG qputenv("QTWEBENGINE_CHROMIUM_FLAGS", @@ -136,12 +143,10 @@ int main(int argc, char *argv[]) { return 0; } - QWebEngineSettings::defaultSettings()->setAttribute( - QWebEngineSettings::DnsPrefetchEnabled, true); - QWebEngineSettings::defaultSettings()->setAttribute( - QWebEngineSettings::FullScreenSupportEnabled, true); - QWebEngineSettings::defaultSettings()->setAttribute( - QWebEngineSettings::JavascriptCanAccessClipboard, true); + QWebEngineSettings *websettings = QWebEngineProfile::defaultProfile()->settings(); + websettings->setAttribute(QWebEngineSettings::DnsPrefetchEnabled, true); + websettings->setAttribute(QWebEngineSettings::FullScreenSupportEnabled, true); + websettings->setAttribute(QWebEngineSettings::JavascriptCanAccessClipboard, true); MainWindow whatsie; @@ -153,7 +158,7 @@ int main(int argc, char *argv[]) { qInfo().noquote() << "Another instance with PID: " + QString::number(instanceId) + ", sent argument: " + message; - QString messageStr = QTextCodec::codecForMib(106)->toUnicode(message); + QString messageStr = QString::fromUtf8(message); QCommandLineParser p; p.addOptions(secondaryInstanceCLIOptions); diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp index 94dc414..ba66fcd 100644 --- a/src/mainwindow.cpp +++ b/src/mainwindow.cpp @@ -43,7 +43,7 @@ void MainWindow::restoreMainWindow() { SettingsManager::instance().settings().value("geometry").toByteArray()); QPoint pos = QCursor::pos(); auto localScreens = QGuiApplication::screens(); - for (auto screen : qAsConst(localScreens)) { + for (auto screen : std::as_const(localScreens)) { QRect screenRect = screen->geometry(); if (screenRect.contains(pos)) { this->move(screenRect.center() - this->rect().center()); @@ -244,7 +244,7 @@ void MainWindow::tryLogOut() { } void MainWindow::initSettingWidget() { - int screenNumber = qApp->desktop()->screenNumber(this); + int screenNumber = qApp->screens().indexOf(screen()); if (m_settingsWidget == nullptr) { m_settingsWidget = new SettingsWidget( this, screenNumber, m_webEngine->page()->profile()->cachePath(), @@ -451,8 +451,7 @@ void MainWindow::showSettings(bool isAskedByCLI) { if (!m_settingsWidget->isVisible()) { this->updateSettingsUserAgentWidget(); m_settingsWidget->refresh(); - int screenNumber = qApp->desktop()->screenNumber(this); - QRect screenRect = QGuiApplication::screens().at(screenNumber)->geometry(); + QRect screenRect = screen()->geometry(); if (!screenRect.contains(m_settingsWidget->pos())) { m_settingsWidget->move(screenRect.center() - m_settingsWidget->rect().center()); @@ -579,7 +578,7 @@ void MainWindow::notificationClicked() { void MainWindow::createActions() { m_openUrlAction = new QAction("New Chat", this); - m_openUrlAction->setShortcut(QKeySequence(Qt::Modifier::CTRL + Qt::Key_N)); + m_openUrlAction->setShortcut(QKeySequence(Qt::Modifier::CTRL | Qt::Key_N)); connect(m_openUrlAction, &QAction::triggered, this, &MainWindow::newChat); addAction(m_openUrlAction); @@ -594,7 +593,7 @@ void MainWindow::createActions() { addAction(m_minimizeAction); QShortcut *minimizeShortcut = new QShortcut( - QKeySequence(Qt::Modifier::CTRL + Qt::Key_W), this, SLOT(hide())); + QKeySequence(Qt::Modifier::CTRL | Qt::Key_W), this, SLOT(hide())); minimizeShortcut->setAutoRepeat(false); m_restoreAction = new QAction(tr("&Restore"), this); @@ -608,19 +607,19 @@ void MainWindow::createActions() { addAction(m_reloadAction); m_lockAction = new QAction(tr("Loc&k"), this); - m_lockAction->setShortcut(QKeySequence(Qt::Modifier::CTRL + Qt::Key_L)); + m_lockAction->setShortcut(QKeySequence(Qt::Modifier::CTRL | Qt::Key_L)); connect(m_lockAction, &QAction::triggered, this, &MainWindow::lockApp); addAction(m_lockAction); m_settingsAction = new QAction(tr("&Settings"), this); - m_settingsAction->setShortcut(QKeySequence(Qt::Modifier::CTRL + Qt::Key_P)); + m_settingsAction->setShortcut(QKeySequence(Qt::Modifier::CTRL | Qt::Key_P)); connect(m_settingsAction, &QAction::triggered, this, &MainWindow::showSettings); addAction(m_settingsAction); m_toggleThemeAction = new QAction(tr("&Toggle theme"), this); m_toggleThemeAction->setShortcut( - QKeySequence(Qt::Modifier::CTRL + Qt::Key_T)); + QKeySequence(Qt::Modifier::CTRL | Qt::Key_T)); connect(m_toggleThemeAction, &QAction::triggered, this, &MainWindow::toggleTheme); addAction(m_toggleThemeAction); @@ -629,7 +628,7 @@ void MainWindow::createActions() { connect(m_aboutAction, &QAction::triggered, this, &MainWindow::showAbout); m_quitAction = new QAction(tr("&Quit"), this); - m_quitAction->setShortcut(QKeySequence(Qt::Modifier::CTRL + Qt::Key_Q)); + m_quitAction->setShortcut(QKeySequence(Qt::Modifier::CTRL | Qt::Key_Q)); connect(m_quitAction, &QAction::triggered, this, &MainWindow::quitApp); addAction(m_quitAction); } diff --git a/src/mainwindow.h b/src/mainwindow.h index 7be6372..0603890 100644 --- a/src/mainwindow.h +++ b/src/mainwindow.h @@ -15,7 +15,6 @@ #include #include #include -#include #include #include #include diff --git a/src/notificationpopup.h b/src/notificationpopup.h index dc1277b..c9b2a54 100644 --- a/src/notificationpopup.h +++ b/src/notificationpopup.h @@ -6,14 +6,12 @@ #include #include -#include #include #include #include #include #include #include -#include #include #include #include @@ -131,13 +129,11 @@ protected slots: } void onClosed() { - auto x = this->pos().x(); - auto y = this->pos().y(); + auto pos = mapToGlobal(QPoint(0, 0)); QPropertyAnimation *a = new QPropertyAnimation(this, "pos"); a->setDuration(150); - a->setStartValue(QApplication::desktop()->mapToGlobal(QPoint(x, y))); - a->setEndValue(QApplication::desktop()->mapToGlobal( - QPoint(x, -(this->height() + 20)))); + a->setStartValue(pos); + a->setEndValue(QPoint(pos.x(), -(this->height() + 20))); a->setEasingCurve(QEasingCurve::Linear); connect(a, &QPropertyAnimation::finished, this, [=]() { diff --git a/src/utils.cpp b/src/utils.cpp index a2ebc00..e1b39f4 100644 --- a/src/utils.cpp +++ b/src/utils.cpp @@ -134,7 +134,7 @@ QString Utils::convertSectoDay(qint64 secs) { QString Utils::returnPath(QString pathname, QString standardLocation = QStandardPaths::writableLocation( - QStandardPaths::DataLocation)) { + QStandardPaths::AppLocalDataLocation)) { QChar sepe = QDir::separator(); QDir d(standardLocation + sepe + pathname); d.mkpath(standardLocation + sepe + pathname); diff --git a/src/webenginepage.cpp b/src/webenginepage.cpp index daa33f3..fca21f8 100644 --- a/src/webenginepage.cpp +++ b/src/webenginepage.cpp @@ -26,6 +26,11 @@ WebEnginePage::WebEnginePage(QWebEngineProfile *profile, QObject *parent) connect(this, &QWebEnginePage::selectClientCertificate, this, &WebEnginePage::handleSelectClientCertificate); #endif + +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(this, &QWebEnginePage::certificateError, this, + &WebEnginePage::handleCertificateError); +#endif } bool WebEnginePage::acceptNavigationRequest(const QUrl &url, @@ -196,7 +201,13 @@ QStringList WebEnginePage::chooseFiles(QWebEnginePage::FileSelectionMode mode, return selectedFiles; } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +void WebEnginePage::handleCertificateError(const QWebEngineCertificateError &error) { + QString description = error.description(); +#else bool WebEnginePage::certificateError(const QWebEngineCertificateError &error) { + QString description = error.errorDescription(); +#endif QWidget *mainWindow = view()->window(); if (error.isOverridable()) { QDialog dialog(mainWindow); @@ -209,14 +220,26 @@ bool WebEnginePage::certificateError(const QWebEngineCertificateError &error) { QIcon icon(mainWindow->style()->standardIcon(QStyle::SP_MessageBoxWarning, nullptr, mainWindow)); certificateDialog.m_iconLabel->setPixmap(icon.pixmap(32, 32)); - certificateDialog.m_errorLabel->setText(error.errorDescription()); + certificateDialog.m_errorLabel->setText(description); dialog.setWindowTitle(tr("Certificate Error")); - return dialog.exec() == QDialog::Accepted; + bool accepted = dialog.exec() == QDialog::Accepted; +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + auto handler = const_cast(error); + if (accepted) + handler.acceptCertificate(); + else + handler.rejectCertificate(); +#else + return accepted; +#endif } QMessageBox::critical(mainWindow, tr("Certificate Error"), - error.errorDescription()); + description); + +#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0) return false; +#endif } void WebEnginePage::handleAuthenticationRequired(const QUrl &requestUrl, diff --git a/src/webenginepage.h b/src/webenginepage.h index f9d8324..92eb8df 100644 --- a/src/webenginepage.h +++ b/src/webenginepage.h @@ -16,6 +16,10 @@ #include #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +#endif + #include "settingsmanager.h" #include "ui_certificateerrordialog.h" @@ -32,10 +36,21 @@ class WebEnginePage : public QWebEnginePage { QWebEnginePage::NavigationType type, bool isMainFrame) override; QWebEnginePage *createWindow(QWebEnginePage::WebWindowType type) override; - bool certificateError(const QWebEngineCertificateError &error) override; QStringList chooseFiles(FileSelectionMode mode, const QStringList &oldFiles, const QStringList &acceptedMimeTypes) override; +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + void handleCertificateError(const QWebEngineCertificateError &error); +#else + bool certificateError(const QWebEngineCertificateError &error) override; +#endif + +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + inline QWidget *view() { + return QWebEngineView::forPage(this); + } +#endif + public slots: void handleFeaturePermissionRequested(const QUrl &securityOrigin, QWebEnginePage::Feature feature); diff --git a/src/webview.cpp b/src/webview.cpp index 035fb4b..07e0605 100644 --- a/src/webview.cpp +++ b/src/webview.cpp @@ -2,10 +2,16 @@ #include #include -#include #include #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +using QWebEngineContextMenuData = QWebEngineContextMenuRequest; +#else +#include +#endif + WebView::WebView(QWidget *parent, QStringList dictionaries) : QWebEngineView(parent), m_dictionaries(dictionaries) { @@ -63,8 +69,11 @@ void WebView::wheelEvent(QWheelEvent *event) { } void WebView::contextMenuEvent(QContextMenuEvent *event) { - +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + auto menu = createStandardContextMenu(); +#else auto menu = page()->createStandardContextMenu(); +#endif menu->setAttribute(Qt::WA_DeleteOnClose, true); // hide reload, back, forward, savepage, copyimagelink menus foreach (auto *action, menu->actions()) { @@ -77,8 +86,12 @@ void WebView::contextMenuEvent(QContextMenuEvent *event) { } } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + const QWebEngineContextMenuRequest &data = *lastContextMenuRequest(); +#else const QWebEngineContextMenuData &data = page()->contextMenuData(); Q_ASSERT(data.isValid()); +#endif // allow context menu on image if (data.mediaType() == QWebEngineContextMenuData::MediaTypeImage) { @@ -107,7 +120,7 @@ void WebView::contextMenuEvent(QContextMenuEvent *event) { if (pageWebengineProfile->isSpellCheckEnabled()) { auto subMenu = menu->addMenu(tr("Select Language")); - for (const QString &dict : qAsConst(m_dictionaries)) { + for (const QString &dict : std::as_const(m_dictionaries)) { auto action = subMenu->addAction(dict); action->setCheckable(true); action->setChecked(languages.contains(dict)); diff --git a/src/widgets/MoreApps/moreapps.cpp b/src/widgets/MoreApps/moreapps.cpp index c333751..a32ae9e 100644 --- a/src/widgets/MoreApps/moreapps.cpp +++ b/src/widgets/MoreApps/moreapps.cpp @@ -104,7 +104,7 @@ QList MoreApps::prepareAppsToShow(const QByteArray &bytes) { } QJsonArray jsonArray = jsonResponse.object().value("results").toArray(); - foreach (const QJsonValue &val, jsonArray) { + for (const QJsonValue &val : jsonArray) { QJsonObject object = val.toObject(); // publisher @@ -127,7 +127,7 @@ QList MoreApps::prepareAppsToShow(const QByteArray &bytes) { QJsonArray mediaArr = object.value("snap").toObject().value("media").toArray(); QString iconUrl; - foreach (const QJsonValue &mediaItem, mediaArr) { + for (const QJsonValue &mediaItem : mediaArr) { if (mediaItem.toObject().value("type") == "icon") iconUrl = mediaItem.toObject().value("url").toString(); } @@ -252,7 +252,7 @@ void MoreApps::showApps() { if (mRemoteIconPreCaching) { // cache fallback icon setRemoteIcon(fallbackIconUrl, nullptr); - foreach (auto a, mAppList) { + for (auto &a : mAppList) { auto iconUrl = a.getIconUrl(); // qDebug() << "pre-caching icon for" << a.getName(); setRemoteIcon(iconUrl, nullptr);