From 3f72c39fb0e95d45d15bde64661040e920574a85 Mon Sep 17 00:00:00 2001 From: aqua Date: Tue, 23 Apr 2024 11:22:02 +0300 Subject: Ported to qt6 --- lib/bookmarks/formats/ffjson.cpp | 7 +- lib/bookmarks/formats/xbel.cpp | 17 ++-- lib/downloads/downloadswidget.cpp | 2 +- lib/downloads/downloadswidget.h | 4 +- lib/downloads/widgets/downloaditemwidget.cpp | 27 ++--- lib/downloads/widgets/downloaditemwidget.h | 10 +- linux/.config | 111 +++++++++++++++++++++ linux/firejail/poi.profile | 48 ++++----- linux/makepkg/PKGBUILD | 58 +++++------ meson.build | 23 +++-- src/main.cpp | 2 + src/mainwindow/menubar.cpp | 5 +- src/mainwindow/widgets/searchform.cpp | 4 +- src/util.cpp | 2 +- src/webengine/webpage.cpp | 4 +- src/webengine/webpage.h | 4 +- src/webengine/webprofilemanager.cpp | 1 + src/webengine/webviewcontextmenu.cpp | 97 +----------------- .../packagefiles/SingleApplication/meson.build | 38 +++++++ .../SingleApplication/meson_options.txt | 1 + subprojects/singleapplication.wrap | 10 +- 21 files changed, 269 insertions(+), 206 deletions(-) create mode 100644 linux/.config create mode 100644 subprojects/packagefiles/SingleApplication/meson.build create mode 100644 subprojects/packagefiles/SingleApplication/meson_options.txt diff --git a/lib/bookmarks/formats/ffjson.cpp b/lib/bookmarks/formats/ffjson.cpp index f9e0866..f95d0d8 100644 --- a/lib/bookmarks/formats/ffjson.cpp +++ b/lib/bookmarks/formats/ffjson.cpp @@ -8,11 +8,12 @@ #include "ffjson.h" #include "bookmarkitem.h" +#include +#include +#include +#include #include #include -#include -#include -#include inline auto asDate(const QJsonValue &v) { diff --git a/lib/bookmarks/formats/xbel.cpp b/lib/bookmarks/formats/xbel.cpp index 7ff79a9..a0a553f 100644 --- a/lib/bookmarks/formats/xbel.cpp +++ b/lib/bookmarks/formats/xbel.cpp @@ -15,28 +15,28 @@ inline void readChildElements(QXmlStreamReader &reader, BookmarkItem *parent) { while(reader.readNextStartElement()) { - if(reader.name() == "title") { + if(reader.name() == QLatin1String("title")) { parent->setData(BookmarkItem::Title, reader.readElementText()); - } else if(reader.name() == "dateAdded") { + } else if(reader.name() == QLatin1String("dateAdded")) { parent->setData(BookmarkItem::DateAdded, QDateTime::fromString(reader.readElementText(), Qt::RFC2822Date)); - } else if(reader.name() == "lastModified") { + } else if(reader.name() == QLatin1String("lastModified")) { parent->setData(BookmarkItem::LastModified, QDateTime::fromString(reader.readElementText(), Qt::RFC2822Date)); - } else if(reader.name() == "tags") { + } else if(reader.name() == QLatin1String("tags")) { parent->setData(BookmarkItem::Tags, reader.readElementText().split(";")); - } else if(reader.name() == "description") { + } else if(reader.name() == QLatin1String("description")) { parent->setData(BookmarkItem::Description, reader.readElementText()); - } else if(reader.name() == "folder") { + } else if(reader.name() == QLatin1String("folder")) { auto *item = new BookmarkItem({}, BookmarkItem::Folder, parent); item->setExpanded(!(reader.attributes().value("folded") == QLatin1String("yes"))); parent->appendChild(item); readChildElements(reader, item); - } else if(reader.name() == "bookmark") { + } else if(reader.name() == QLatin1String("bookmark")) { auto *item = new BookmarkItem({}, BookmarkItem::Bookmark, parent); item->setData(BookmarkItem::Href, reader.attributes().value("href").toString()); parent->appendChild(item); @@ -53,7 +53,8 @@ void Xbel::read(QIODevice *device, BookmarkItem *item) QXmlStreamReader qXmlStreamReader(device); if(qXmlStreamReader.readNextStartElement()) { - if(!(qXmlStreamReader.name() == "xbel" && qXmlStreamReader.attributes().value("version") == "1.0")) { + if(!(qXmlStreamReader.name() == QLatin1String("xbel") + && qXmlStreamReader.attributes().value("version") == QLatin1String("1.0"))) { return; } diff --git a/lib/downloads/downloadswidget.cpp b/lib/downloads/downloadswidget.cpp index 02ed08a..2f192e9 100644 --- a/lib/downloads/downloadswidget.cpp +++ b/lib/downloads/downloadswidget.cpp @@ -28,7 +28,7 @@ DownloadsWidget::~DownloadsWidget() delete ui; } -void DownloadsWidget::addDownload(QWebEngineDownloadItem *item) +void DownloadsWidget::addDownload(QWebEngineDownloadRequest *item) { const QString filepath = QFileDialog::getSaveFileName(this, tr("Save File"), m_downloadPath + "/" + item->downloadFileName()); diff --git a/lib/downloads/downloadswidget.h b/lib/downloads/downloadswidget.h index eb4ce57..d0aa2b4 100644 --- a/lib/downloads/downloadswidget.h +++ b/lib/downloads/downloadswidget.h @@ -10,7 +10,7 @@ #define SMOLBOTE_DOWNLOADDIALOG_H #include -#include +#include namespace Ui { @@ -26,7 +26,7 @@ public: ~DownloadsWidget() override; public slots: - void addDownload(QWebEngineDownloadItem *item); + void addDownload(QWebEngineDownloadRequest *item); private: Ui::DownloadDialog *ui; diff --git a/lib/downloads/widgets/downloaditemwidget.cpp b/lib/downloads/widgets/downloaditemwidget.cpp index e0c8a60..169ba6f 100644 --- a/lib/downloads/widgets/downloaditemwidget.cpp +++ b/lib/downloads/widgets/downloaditemwidget.cpp @@ -30,7 +30,7 @@ inline QString sizeString(qint64 size) return QString("%1 GB").arg(size / (1024 * 1024 * 1024)); } -DownloadItemWidget::DownloadItemWidget(QWebEngineDownloadItem *m_item, QWidget *parent) +DownloadItemWidget::DownloadItemWidget(QWebEngineDownloadRequest *m_item, QWidget *parent) : QWidget(parent) , ui(new Ui::DownloadItemForm) { @@ -51,11 +51,11 @@ DownloadItemWidget::DownloadItemWidget(QWebEngineDownloadItem *m_item, QWidget * ui->path_label->setText(QString("%1
%2").arg(item->downloadDirectory(), item->downloadFileName())); this->updateState(item->state()); - connect(item, &QWebEngineDownloadItem::stateChanged, this, &DownloadItemWidget::updateState); - connect(item, &QWebEngineDownloadItem::downloadProgress, this, &DownloadItemWidget::updateProgress); - connect(item, &QWebEngineDownloadItem::finished, this, &DownloadItemWidget::updateFinished); + connect(item, &QWebEngineDownloadRequest::stateChanged, this, &DownloadItemWidget::updateState); + connect(item, &QWebEngineDownloadRequest::receivedBytesChanged, this, &DownloadItemWidget::updateProgress); + connect(item, &QWebEngineDownloadRequest::isFinishedChanged, this, &DownloadItemWidget::updateFinished); - connect(ui->abort_toolButton, &QToolButton::clicked, item, &QWebEngineDownloadItem::cancel); + connect(ui->abort_toolButton, &QToolButton::clicked, item, &QWebEngineDownloadRequest::cancel); connect(ui->pause_toolButton, &QToolButton::clicked, item, [m_item](bool clicked) { clicked ? m_item->pause() : m_item->resume(); }); @@ -69,34 +69,34 @@ DownloadItemWidget::~DownloadItemWidget() delete ui; } -void DownloadItemWidget::updateState(QWebEngineDownloadItem::DownloadState state) +void DownloadItemWidget::updateState(QWebEngineDownloadRequest::DownloadState state) { switch(state) { - case QWebEngineDownloadItem::DownloadRequested: + case QWebEngineDownloadRequest::DownloadRequested: ui->status_label->setText(tr("Requested")); ui->pause_toolButton->setEnabled(true); ui->abort_toolButton->setEnabled(true); ui->open_toolButton->setEnabled(false); break; - case QWebEngineDownloadItem::DownloadInProgress: + case QWebEngineDownloadRequest::DownloadInProgress: ui->status_label->setText(tr("In progress")); ui->pause_toolButton->setEnabled(true); ui->abort_toolButton->setEnabled(true); ui->open_toolButton->setEnabled(false); break; - case QWebEngineDownloadItem::DownloadCompleted: + case QWebEngineDownloadRequest::DownloadCompleted: ui->status_label->setText(tr("Completed")); ui->pause_toolButton->setEnabled(false); ui->abort_toolButton->setEnabled(false); ui->open_toolButton->setEnabled(true); break; - case QWebEngineDownloadItem::DownloadCancelled: + case QWebEngineDownloadRequest::DownloadCancelled: ui->status_label->setText(tr("Cancelled")); ui->pause_toolButton->setEnabled(false); ui->abort_toolButton->setEnabled(false); ui->open_toolButton->setEnabled(false); break; - case QWebEngineDownloadItem::DownloadInterrupted: + case QWebEngineDownloadRequest::DownloadInterrupted: ui->status_label->setText(tr("Interrupted")); ui->pause_toolButton->setEnabled(false); ui->abort_toolButton->setEnabled(false); @@ -107,8 +107,11 @@ void DownloadItemWidget::updateState(QWebEngineDownloadItem::DownloadState state } } -void DownloadItemWidget::updateProgress(qint64 value, qint64 total) +void DownloadItemWidget::updateProgress() { + const auto value = item->receivedBytes(); + const auto total = item->totalBytes(); + ui->progressBar->setValue(static_cast((static_cast(value) / static_cast(total)) * 100)); ui->progressBar->setFormat(QString("%1 / %2").arg(sizeString(value), sizeString(total))); } diff --git a/lib/downloads/widgets/downloaditemwidget.h b/lib/downloads/widgets/downloaditemwidget.h index a1de175..5d540a3 100644 --- a/lib/downloads/widgets/downloaditemwidget.h +++ b/lib/downloads/widgets/downloaditemwidget.h @@ -9,7 +9,7 @@ #ifndef SMOLBOTE_DOWNLOADITEMFORM_H #define SMOLBOTE_DOWNLOADITEMFORM_H -#include +#include #include namespace Ui @@ -22,17 +22,17 @@ class DownloadItemWidget : public QWidget Q_OBJECT public: - explicit DownloadItemWidget(QWebEngineDownloadItem *m_item, QWidget *parent = 0); + explicit DownloadItemWidget(QWebEngineDownloadRequest *m_item, QWidget *parent = 0); ~DownloadItemWidget() override; private slots: - void updateState(QWebEngineDownloadItem::DownloadState state); - void updateProgress(qint64 value, qint64 total); + void updateState(QWebEngineDownloadRequest::DownloadState state); + void updateProgress(); void updateFinished(); private: Ui::DownloadItemForm *ui; - QWebEngineDownloadItem *item = nullptr; + QWebEngineDownloadRequest *item = nullptr; }; #endif // SMOLBOTE_DOWNLOADITEMFORM_H diff --git a/linux/.config b/linux/.config new file mode 100644 index 0000000..2fb8236 --- /dev/null +++ b/linux/.config @@ -0,0 +1,111 @@ + +# +# Application +# +CONFIG_POI_NAME="smolbote" +CONFIG_POI_ICON=":/icons/poi.svg" +CONFIG_POI_CFG_PATH="~/.config/smolbote/smolbote.cfg" +# end of Application + +# +# Keyboard shortcuts +# + +# +# Main Window shortcuts +# +CONFIG_shortcuts.session.save="Ctrl+S,S" +CONFIG_shortcuts.session.open="Ctrl+S,O" +CONFIG_shortcuts.window.newgroup="Ctrl+G" +CONFIG_shortcuts.window.newwindow="Ctrl+N" +CONFIG_shortcuts.window.about="F1" +CONFIG_shortcuts.window.quit="Ctrl+Q" +CONFIG_shortcuts.window.search="F3" +CONFIG_shortcuts.window.downloads.show="Ctrl+D" + +# +# Navigation Bar shortcuts +# +CONFIG_navigationbar.show="Ctrl+Shift+N" +CONFIG_shortcuts.navigation.back="Ctrl+Left" +CONFIG_shortcuts.navigation.backmenu="Ctrl+Down" +CONFIG_shortcuts.navigation.forward="Ctrl+Right" +CONFIG_shortcuts.navigation.forwardmenu="Ctrl+Up" +CONFIG_shortcuts.navigation.refresh="F5" +CONFIG_shortcuts.navigation.reload="Ctrl+F5" +CONFIG_shortcuts.navigation.home="Ctrl+Home" + +# +# Address Bar shortcuts +# +CONFIG_shortcuts.address.focus="F4" +CONFIG_shortcuts.address.menu="F2" + +# +# Subwindow shortcuts +# +CONFIG_shortcuts.subwindow.close="Ctrl+Shift+W" +CONFIG_shortcuts.subwindow.fullscreen="F11" +CONFIG_shortcuts.subwindow.newtab="Ctrl+T" +CONFIG_shortcuts.subwindow.closetab="Ctrl+W" +CONFIG_shortcuts.subwindow.restoretab="Ctrl+Shift+T" +CONFIG_shortcuts.subwindow.tableft="Ctrl+O" +CONFIG_shortcuts.subwindow.movetableft="Ctrl+Shift+O" +CONFIG_shortcuts.subwindow.tabright="Ctrl+P" +CONFIG_shortcuts.subwindow.movetabright="Ctrl+Shift+P" +# end of Keyboard shortcuts + +# +# Main Window +# +CONFIG_mainwindow.title="smolbote" +CONFIG_mainwindow.width=1280 +CONFIG_mainwindow.height=720 +# end of Main Window + +# +# Bookmarks +# +CONFIG_bookmarks.path="~/.config/smolbote/bookmarks.xbel" +CONFIG_shortcuts.window.bookmarks.show="Ctrl+B" +CONFIG_bookmarks.toolbar.show="Ctrl+Shift+B" +# CONFIG_bookmarks.toolbar.movable is not set +# CONFIG_bookmarks.toolbar.visible is not set +# end of Bookmarks + +# +# Profile Settings +# +CONFIG_profile.path="~/.config/smolbote/profiles.d" +CONFIG_profile.default="default" +CONFIG_profile.search="https://duckduckgo.com/?q=%1&ia=web" +CONFIG_profile.homepage="about:blank" +CONFIG_profile.newtab="about:blank" +# end of Profile Settings + +CONFIG_USEPLUGINS=y + +# +# Plugin Settings +# +CONFIG_PLUGINS_PATH="~/.config/smolbote/plugins.d" +# CONFIG_PLUGINS_SIGNATURE_IGNORED is not set +CONFIG_PLUGINS_SIGNATURE_CHECKED=y +# CONFIG_PLUGINS_SIGNATURE_ENFORCED is not set +CONFIG_PLUGINS_SIGNATURE_HASH="SHA256" +# end of Plugin Settings + +# +# Default paths +# +CONFIG_filter.path="~/.config/smolbote/hosts.d" +CONFIG_downloads.path="~/Downloads" +CONFIG_session.path="~/.config/smolbote/session.d" +# CONFIG_USEPLASMA is not set +# CONFIG_USEBREAKPAD is not set + +# +# Workarounds +# +CONFIG_QTBUG_65223=y +# end of Workarounds diff --git a/linux/firejail/poi.profile b/linux/firejail/poi.profile index a7d3005..1a644d7 100644 --- a/linux/firejail/poi.profile +++ b/linux/firejail/poi.profile @@ -1,21 +1,22 @@ # Firejail profile for poi # This file is overwritten after every install/update # Persistent local customizations -include /etc/firejail/poi.local +include poi.local # Persistent global definitions -include /etc/firejail/globals.local +include globals.local # noblacklist: exclude from blacklist noblacklist ${HOME}/.cache/smolbote noblacklist ${HOME}/.config/smolbote noblacklist ${HOME}/.local/share/smolbote -include /etc/firejail/disable-common.inc -include /etc/firejail/disable-devel.inc -include /etc/firejail/disable-interpreters.inc -include /etc/firejail/disable-passwdmgr.inc -include /etc/firejail/disable-programs.inc -include /etc/firejail/disable-xdg.inc +include disable-common.inc +include disable-devel.inc +include disable-exec.inc +include disable-interpreters.inc +include disable-passwdmgr.inc +include disable-programs.inc +include disable-xdg.inc mkdir ${HOME}/.cache/smolbote mkdir ${HOME}/.config/smolbote @@ -25,7 +26,7 @@ whitelist ${DOWNLOADS} whitelist ${HOME}/.cache/smolbote whitelist ${HOME}/.config/smolbote whitelist ${HOME}/.local/share/smolbote -include /etc/firejail/whitelist-common.inc +include whitelist-common.inc ## caps.drop all - Removes the ability to call programs usually run only by root. Ex - chown, setuid @@ -43,7 +44,9 @@ caps.drop all netfilter ## nodbus - Disable access to dbus. -nodbus +#nodbus +dbus-user none +dbus-system none ## nodvd - Disable access to optical disk drives. nodvd @@ -60,6 +63,9 @@ noroot ## notv - Disable access to DVB TV devices. notv +## nou2f - Disable access to U2F devices. +nou2f + # novideo - Disable access to video devices. novideo @@ -67,20 +73,16 @@ novideo protocol unix,inet,inet6,netlink ## seccomp - Blacklists a large swath of syscalls from being accessible. -#seccomp -## Use seccomp.drop for now as seccomp is broken with many programs. -seccomp.drop @clock,@cpu-emulation,@module,@obsolete,@privileged,@raw-io,@reboot,@resources,@swap,ptrace -# QtWebEngine require chroot syscall on AMD CPUS and/or ATI Graphics for some bizarre reason -# Use the following seccomp.drop instead on such systems. -#seccomp.drop @clock,@cpu-emulation,@module,@obsolete,@raw-io,@reboot,@resources,@swap,ptrace,mount,umount2,pivot_root +# QtWebEngine requires chroot syscall on AMD and ATI Graphics for some bizarre reason +seccomp !name_to_handle_at,!chroot ## shell - Run the program directly, without a user shell. # breaks secondary instances when using join-or-start after shell=none -#shell none +shell none ## tracelog - Log all viloations to syslog. -# tracelog segfaults QtWebEngine on AMD CPUS and/or ATI Graphics for some bizarre reason -tracelog +# tracelog segfaults QtWebEngine on AMD and ATI Graphics for some bizarre reason +#tracelog ## disable-mnt - Deny access to /mnt, /media, /run/mount, and /run/media disable-mnt @@ -88,7 +90,7 @@ disable-mnt ## private-bin - Creates a virtual /bin directory containing only temporary copies of the following executables. # bash required to launch from kde kickoff menu # breaks if installed to /usr/local -#private-bin bash,poi +private-bin bash,poi ## private-dev - Create a virtual /dev directory. Only dri, null, full, zero, tty, pts, ptmx, random, snd, urandom, video, log and shm devices are available. private-dev @@ -101,12 +103,6 @@ private-etc fonts,group,machine-id,resolv.conf # breaks SingleApplication without join-or-start set private-tmp - -## noexec - Prevent execution of files in the specified locations -noexec ${HOME} -noexec /tmp - - # join-or-start - Join the sandbox identified by name or start a new one join-or-start poi diff --git a/linux/makepkg/PKGBUILD b/linux/makepkg/PKGBUILD index 5bcf684..34d54ef 100644 --- a/linux/makepkg/PKGBUILD +++ b/linux/makepkg/PKGBUILD @@ -3,14 +3,16 @@ ## not-use flags # Enable plugin signing: _signPlugins=0 -# Enable breakpad integraton: -_enableBreakpad=0 +# test +_test=0 +_branch=devel +_optimized=0 # install prefix -_prefix='/usr/local' +_prefix='/usr' pkgname=smolbote-git pkgdesc='Yet another no-frills browser' -pkgver=0 +pkgver=r638.be627c1 pkgrel=1 url="https://neueland.iserlohn-fortress.net/gitea/smolbote" @@ -19,33 +21,46 @@ install="smolbote.install" arch=('x86_64' 'aarch64') license=('GPL3') -depends=('qt5-svg' 'qt5-webengine>=5.11.0' 'spdlog') -makedepends=('git' 'meson' 'python-kconfiglib' 'openssl' 'qt5-tools' 'scdoc' 'catch2') -if [ $_enableBreakpad == "1" ]; then - makedepends+=('breakpad-git') -fi +depends=('qt6-svg' 'qt6-webengine' 'spdlog' 'fmt') +makedepends=('git' 'meson' 'python-kconfiglib' 'openssl' 'qt6-tools' 'scdoc') optdepends=('firejail: launch a sandboxed instance') +# this isn't a hard requirement, simply a workaround as the build script +# sets some additional hardening flags that the default makepkg.conf +# will turn down +options=(!buildflags) + # use git+file:///path/to/your/repo to build from a local repo source=("git+https://neueland.iserlohn-fortress.net/cgit/smolbote" - "https://neueland.iserlohn-fortress.net/releases/SingleApplication-3.1.1a.tar.xz"{,.sig} + "https://github.com/itay-grudev/SingleApplication/archive/refs/tags/v3.5.1.tar.gz" "https://neueland.iserlohn-fortress.net/releases/args.hxx-6.2.2.tar.xz"{,.sig}) +if [ $_optimized == "1" ]; then + source+=(meson.build.diff) +fi b2sums=('SKIP' - 'cec3de8dbf252bfa6dc488e5a1440695f4dd3abffdf30948b7d1a3df3d9c85911e981c802ed5a882f1407315114529f4016e55c7d05fbbd1dafe5495b0a63f4a' - 'SKIP' + '924cef0b6aeb76aace3444f46141acb58c5f5019e1e09c78e1b1d973f1689283b5f5f7612dc58dc542fc04364197128f2f3f9e1a97b8b78e704fae5d995a8eca' '440e357006883fbf1b1a796051500a6b068858a35947cd1119767bed8e0a86a7db4aff16498934d7217c375fe643da03c22007e438f30899e247153f25c922b6' 'SKIP') -validgpgkeys=(BB1C090188E3E32B375C13FD095DE26BC16D2E98) # Aqua-sama +validpgpkeys=('BB1C090188E3E32B375C13FD095DE26BC16D2E98') prepare() { mkdir "$srcdir/smolbote/subprojects/packagecache/" - ln -s "$srcdir/SingleApplication-3.1.1a" "$srcdir/smolbote/subprojects/" + ln -s "$srcdir/SingleApplication-3.5.1" "$srcdir/smolbote/subprojects/" ln -s "$srcdir/args.hxx-6.2.2" "$srcdir/smolbote/subprojects/" cd $srcdir/smolbote + + if [ $_test == "1" ]; then + git checkout ${_branch} + fi + KCONFIG_CONFIG=linux/.config alldefconfig + +if [ $_optimized == "1" ]; then + patch -p1 -i ${srcdir}/meson.build.diff +fi } pkgver() { @@ -72,14 +87,8 @@ build() { -Dmanpage=true \ $srcdir/smolbote $srcdir/build - if [ $_enableBreakpad == "1" ]; then - msg2 "Enabling crashhandler" - meson configure -Ddebug=true -Dcrashhandler=enabled - KCONFIG_CONFIG=linux/.config setconfig USEBREAKPAD=y - fi - # Build - ninja -C $srcdir/build + ninja -C $srcdir/build "$MAKEFLAGS" } #check() { @@ -98,12 +107,5 @@ package() { msg2 "Signed $(basename $so)" done fi - - if [ $_enableBreakpad == "1" ]; then - msg "Installing debug symbols" - ninja -C $srcdir/build linux/poi.sym - install -dm644 $pkgdir/$_prefix/lib/smolbote/symbols/poi/$(head -n1 linux/poi.sym | awk '{ print $(NF-1) }') - install -m644 -t $pkgdir/$_prefix/lib/smolbote/symbols/poi/$(head -n1 linux/poi.sym | awk '{ print $(NF-1) }') $srcdir/build/linux/poi.sym - fi } diff --git a/meson.build b/meson.build index 1351796..6534910 100644 --- a/meson.build +++ b/meson.build @@ -2,7 +2,7 @@ project('smolbote', ['cpp'], version: '0.1.0', default_options: ['cpp_std=c++2a', 'warning_level=3'], license: 'GPL3', - meson_version: '>=0.55.0' + meson_version: '>=0.57.0' ) kconfig = import('keyval') @@ -11,7 +11,7 @@ kconf = kconfig.load(host_machine.system() + '/.config') cdata = configuration_data(kconf) version_h = vcs_tag( - command: [find_program('git').path(), 'describe', '--long', '--abbrev=40'], + command: [find_program('git').full_path(), 'describe', '--long', '--abbrev=40'], #fallback: defaults to meson.project_version(), input: 'include/version.h.in', output: 'version.h' @@ -75,25 +75,26 @@ add_project_arguments(cxx.get_supported_arguments([ ]), language: 'cpp') # Dependencies -mod_qt5 = import('qt5') -dep_qt5 = dependency('qt5', - modules: [ 'Core', 'Network', 'Widgets', 'Svg', 'WebEngine', 'WebEngineWidgets', 'Concurrent' ], +mod_qt5 = import('qt6') +dep_qt5 = dependency('qt6', + modules: [ 'Core', 'Network', 'Widgets', 'SvgWidgets', 'WebEngineCore', 'WebEngineWidgets', 'Concurrent' ], include_type: 'system' ) dep_spdlog = dependency('spdlog', fallback: ['spdlog', 'spdlog_dep'], version: '>=1.3.1') +dep_fmt = dependency('fmt') optional_deps = [] poi_cpp_args = [] -dep_breakpad = dependency('breakpad-client', include_type: 'system', required: get_option('crashhandler')) -dep_threads = dependency('threads', include_type: 'system', required: get_option('crashhandler')) +dep_breakpad = disabler() # dependency('breakpad-client', include_type: 'system', required: get_option('crashhandler')) +dep_threads = disabler() # dependency('threads', include_type: 'system', required: get_option('crashhandler')) if dep_breakpad.found() poi_cpp_args += '-DHAVE_BREAKPAD' endif dep_gtest = dependency('gtest', required: false, disabler: true) -dep_catch = dependency('catch2', required: true, fallback: ['catch2', 'catch2_dep'] ) +dep_catch = disabler() # dependency('catch2', required: true, fallback: ['catch2', 'catch2_dep'] ) dep_SingleApplication = dependency('singleapplication', fallback: [ 'singleapplication', 'SingleApplication_dep' ]) dep_args = dependency('args.hxx', fallback: [ 'args', 'args_dep' ]) @@ -122,10 +123,10 @@ subdir('test/firefox-bookmarks-json-parser') ssconfig = poi_sourceset.apply(cdata) poi_exe = executable(get_option('poi'), - cpp_args: ['-DQAPPLICATION_CLASS=QApplication', poi_cpp_args], + cpp_args: ['-DQAPPLICATION_CLASS=QApplication', '-DSPDLOG_FMT_EXTERNAL=1', poi_cpp_args], sources: [ssconfig.sources()], include_directories: [ plugininterfaces_include, include_directories('src') ], - dependencies: [ dep_qt5, dep_spdlog, dep_SingleApplication, dep_args, optional_deps, dep_bookmarks, dep_configuration, dep_downloads, dep_pluginloader, dep_urlfilter, ssconfig.dependencies(), lib_session_formats ], + dependencies: [ dep_qt5, dep_spdlog, dep_fmt, dep_SingleApplication, dep_args, optional_deps, dep_bookmarks, dep_configuration, dep_downloads, dep_pluginloader, dep_urlfilter, ssconfig.dependencies(), lib_session_formats ], install: true, ) @@ -137,6 +138,6 @@ subdir(host_machine.system()) cppcheck = find_program('cppcheck', required: false) if cppcheck.found() run_target('cppcheck', - command: [cppcheck, '--enable=all', '--project=' + meson.build_root() / 'compile_commands.json'] + command: [cppcheck, '--enable=all', '--project=' + meson.project_build_root() / 'compile_commands.json'] ) endif diff --git a/src/main.cpp b/src/main.cpp index dad1f73..aa08236 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -106,6 +106,7 @@ int main(int argc, char **argv) Configuration conf; if(conf.value("usebreakpad").value()) { + /* FIXME CrashHandler::Context ctx( conf.value("path.crashdump").value(), conf.value("path.crashhandler").value()); @@ -115,6 +116,7 @@ int main(int argc, char **argv) } else { spdlog::warn("Failed to install breakpad crash handler: {}", ctx.dumppath); } + */ } // load plugins diff --git a/src/mainwindow/menubar.cpp b/src/mainwindow/menubar.cpp index 5fc039a..e557d50 100644 --- a/src/mainwindow/menubar.cpp +++ b/src/mainwindow/menubar.cpp @@ -329,10 +329,7 @@ MenuBar::MenuBar(QMenu *appMenu, MainWindow *parent) auto *printer = new QPrinter(QPrinterInfo::defaultPrinter()); QPrintDialog dlg(printer, parent); if(dlg.exec() == QDialog::Accepted) { - parent->currentView()->page()->print(printer, [printer](bool success) { - Q_UNUSED(success); - delete printer; - }); + parent->currentView()->print(printer); } } }); diff --git a/src/mainwindow/widgets/searchform.cpp b/src/mainwindow/widgets/searchform.cpp index e10933b..af54f5c 100644 --- a/src/mainwindow/widgets/searchform.cpp +++ b/src/mainwindow/widgets/searchform.cpp @@ -10,6 +10,7 @@ #include "ui_searchform.h" #include #include +#include #include SearchForm::SearchForm(QWidget *parent) @@ -26,7 +27,8 @@ SearchForm::SearchForm(QWidget *parent) QWebEnginePage::FindFlags searchFlags; searchFlags.setFlag(QWebEnginePage::FindCaseSensitively, ui->caseSensitivity_checkBox->isChecked()); searchFlags.setFlag(QWebEnginePage::FindBackward, ui->reverseSearch_checkBox->isChecked()); - m_view->findText(ui->lineEdit->text(), searchFlags, [this](bool found) { + m_view->findText(ui->lineEdit->text(), searchFlags, [this](const QWebEngineFindTextResult &result) { + const bool found = result.numberOfMatches() > 0; ui->result_label->setVisible(!found); }); } diff --git a/src/util.cpp b/src/util.cpp index fe74175..3061c96 100644 --- a/src/util.cpp +++ b/src/util.cpp @@ -62,7 +62,7 @@ QIcon Util::icon(QStyle::StandardPixmap id) { return QIcon::fromTheme("go-home", qApp->style()->standardIcon(id)); default: - spdlog::warn("FIXME: unhandled StandardPixmap {}", id); + spdlog::warn("FIXME: unhandled StandardPixmap"); return qApp->style()->standardIcon(id); } } diff --git a/src/webengine/webpage.cpp b/src/webengine/webpage.cpp index b2b19b5..f8a8f7f 100644 --- a/src/webengine/webpage.cpp +++ b/src/webengine/webpage.cpp @@ -62,6 +62,7 @@ WebPage::WebPage(QWebEngineProfile *profile, QObject *parent) connect(this, &QWebEnginePage::featurePermissionRequested, this, &WebPage::featurePermissionDialog); connect(this, &QWebEnginePage::renderProcessTerminated, this, &WebPage::renderProcessCrashed); + connect(this, &QWebEnginePage::certificateError, this, &WebPage::certificateError); } bool WebPage::certificateError(const QWebEngineCertificateError &certificateError) @@ -77,9 +78,8 @@ bool WebPage::certificateError(const QWebEngineCertificateError &certificateErro messageBox.setText(tr("An SSL error has occurred on %1").arg(certificateError.url().toString())); messageBox.setInformativeText(tr("

%1

" "

This error %2 be overridden.

") - .arg(certificateError.errorDescription(), + .arg(certificateError.description(), certificateError.isOverridable() ? tr("can") : tr("cannot"))); - messageBox.setDetailedText(tr("Error code: %1").arg(certificateError.error())); if(certificateError.isOverridable()) { messageBox.setStandardButtons(QMessageBox::Ignore | QMessageBox::Abort); diff --git a/src/webengine/webpage.h b/src/webengine/webpage.h index 91ae4f3..bd7d54c 100644 --- a/src/webengine/webpage.h +++ b/src/webengine/webpage.h @@ -19,12 +19,10 @@ public: WebPage(QWebEngineProfile *profile, QObject *parent = nullptr); ~WebPage() override = default; -protected: - bool certificateError(const QWebEngineCertificateError &certificateError) override; - protected slots: void featurePermissionDialog(const QUrl &securityOrigin, QWebEnginePage::Feature feature); void renderProcessCrashed(QWebEnginePage::RenderProcessTerminationStatus terminationStatus, int exitCode); + bool certificateError(const QWebEngineCertificateError &certificateError); }; #endif // SMOLBOTE_WEBPAGE_H diff --git a/src/webengine/webprofilemanager.cpp b/src/webengine/webprofilemanager.cpp index 5cc83f8..9ae2960 100644 --- a/src/webengine/webprofilemanager.cpp +++ b/src/webengine/webprofilemanager.cpp @@ -8,6 +8,7 @@ #include "webprofilemanager.h" #include "webprofile.h" +#include static WebProfileManager *s_instance = nullptr; diff --git a/src/webengine/webviewcontextmenu.cpp b/src/webengine/webviewcontextmenu.cpp index ea5e8c6..0de3b9f 100644 --- a/src/webengine/webviewcontextmenu.cpp +++ b/src/webengine/webviewcontextmenu.cpp @@ -17,7 +17,7 @@ #include #include #include -#include +#include #include #include @@ -94,100 +94,7 @@ WebViewContextMenu::WebViewContextMenu(WebView *view) this->addAction(navButtons); this->addSeparator(); - const auto ctxdata = view->page()->contextMenuData(); - - if(ctxdata.mediaType() == QWebEngineContextMenuData::MediaTypeNone) { - auto *backMenu = this->addMenu(tr("Back")); - if(!view->history()->canGoBack()) { - backMenu->setEnabled(false); - } else { - connect(backMenu, &QMenu::aboutToShow, view, [view, backMenu]() { - backMenu->clear(); - const auto backItems = view->history()->backItems(10); - for(const QWebEngineHistoryItem &item : backItems) { - backMenu->addAction(historyAction(view, item)); - } - }); - } - - auto *forwardMenu = this->addMenu(tr("Forward")); - if(!view->history()->canGoForward()) { - forwardMenu->setEnabled(false); - } else { - connect(forwardMenu, &QMenu::aboutToShow, view, [view, forwardMenu]() { - forwardMenu->clear(); - const auto forwardItems = view->history()->forwardItems(10); - for(const QWebEngineHistoryItem &item : forwardItems) { - forwardMenu->addAction(historyAction(view, item)); - } - }); - } - - connect(this->addAction(tr("Reload")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::Reload); - }); - connect(this->addAction(tr("Reload and bypass Cache")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::ReloadAndBypassCache); - }); - - this->addSeparator(); - - connect(this->addAction(tr("Select All")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::SelectAll); - }); - connect(this->addAction(tr("Clear Selection")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::Unselect); - }); - connect(this->addAction(tr("Copy to clipboard")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::Copy); - }); - - } else if(ctxdata.mediaType() == QWebEngineContextMenuData::MediaTypeImage) { - connect(this->addAction(tr("Copy image to clipboard")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::CopyImageToClipboard); - }); - connect(this->addAction(tr("Copy image URL to clipboard")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::CopyImageUrlToClipboard); - }); - if(!ctxdata.mediaUrl().isEmpty()) { - if(view->url() != ctxdata.mediaUrl()) { - connect(this->addAction(tr("Open image")), &QAction::triggered, view, [view, ctxdata]() { - view->load(ctxdata.mediaUrl()); - }); - connect(this->addAction(tr("Open image in new tab")), &QAction::triggered, view, [view, ctxdata]() { - view->createWindow(QWebEnginePage::WebBrowserTab)->load(ctxdata.mediaUrl()); - }); - } - connect(this->addAction(tr("Save image")), &QAction::triggered, view, [view, ctxdata]() { - view->page()->download(ctxdata.mediaUrl()); - }); - } - - } else { - addMenu(view->page()->createStandardContextMenu()); - } - - if(!ctxdata.linkUrl().isEmpty()) { - this->addSeparator(); - connect(this->addAction(tr("Open link in new tab")), &QAction::triggered, view, [view, ctxdata]() { - view->createWindow(QWebEnginePage::WebBrowserTab)->load(ctxdata.linkUrl()); - }); - - auto *newTabMenu = this->addMenu(tr("Open link in new tab with profile")); - profileMenu(newTabMenu, [view, ctxdata](WebProfile *profile) { - auto *v = view->createWindow(QWebEnginePage::WebBrowserTab); - v->setProfile(profile); - v->load(ctxdata.linkUrl()); - }); - - connect(this->addAction(tr("Open link in new window")), &QAction::triggered, view, [view, ctxdata]() { - view->createWindow(QWebEnginePage::WebBrowserWindow)->load(ctxdata.linkUrl()); - }); - - connect(this->addAction(tr("Copy link address")), &QAction::triggered, view, [view]() { - view->page()->triggerAction(QWebEnginePage::CopyLinkToClipboard); - }); - } + addMenu(view->createStandardContextMenu()); // zoom widget { diff --git a/subprojects/packagefiles/SingleApplication/meson.build b/subprojects/packagefiles/SingleApplication/meson.build new file mode 100644 index 0000000..4a583cd --- /dev/null +++ b/subprojects/packagefiles/SingleApplication/meson.build @@ -0,0 +1,38 @@ +project('SingleApplication', ['cpp'], + version: '3.5.1', + default_options: ['cpp_std=c++2a', 'warning_level=3'], + license: 'MIT', +) + +mod_qt5 = import('qt6') +dep_qt5 = dependency('qt6', modules: [ 'Core', 'Network', 'Gui', 'Widgets' ], include_type: 'system') + +SingleApplication_inc = include_directories('.') + +SingleApplication_moc = mod_qt5.preprocess( + moc_headers: [ 'singleapplication.h', 'singleapplication_p.h'], + moc_extra_arguments: ['-DQAPPLICATION_CLASS=QApplication'], + dependencies: dep_qt5 +) + +SingleApplication_lib = static_library('SingleApplication', + [ 'singleapplication.cpp', 'singleapplication_p.cpp', SingleApplication_moc ], + include_directories: SingleApplication_inc, + cpp_args: '-DQAPPLICATION_CLASS=QApplication', + dependencies: dep_qt5 +) + +SingleApplication_dep = declare_dependency( + include_directories: SingleApplication_inc, + link_with: SingleApplication_lib +).as_system('system') + +# On windows, SingleApplication needs to be linked against advapi32. This is +# done by adding 'advapi32' to cpp_winlibs, where it should be by default. + +if get_option('examples') + subdir('examples/basic') + subdir('examples/calculator') + subdir('examples/sending_arguments') +endif + diff --git a/subprojects/packagefiles/SingleApplication/meson_options.txt b/subprojects/packagefiles/SingleApplication/meson_options.txt new file mode 100644 index 0000000..21e68e0 --- /dev/null +++ b/subprojects/packagefiles/SingleApplication/meson_options.txt @@ -0,0 +1 @@ +option('examples', description: 'Build examples', type: 'boolean', value: false) diff --git a/subprojects/singleapplication.wrap b/subprojects/singleapplication.wrap index ac817db..52d0f62 100644 --- a/subprojects/singleapplication.wrap +++ b/subprojects/singleapplication.wrap @@ -1,6 +1,8 @@ [wrap-file] -directory = SingleApplication-3.1.1a +directory = SingleApplication-3.5.1 -source_url = https://neueland.iserlohn-fortress.net/releases/SingleApplication-3.1.1a.tar.xz -source_filename = SingleApplication-3.1.1a.tar.xz -source_hash = df21800c9f3b254048ed34f6cfe96e5a540dc8ab4533b327a6982a6030f77080 +source_url = https://github.com/itay-grudev/SingleApplication/archive/refs/tags/v3.5.1.tar.gz +source_filename = SingleApplication-3.5.1.tar.gz +source_hash = d2f02d94887bd8ffbf2a1a4bbc83293f4393dfbfa34f746ac627ea6ca18415ac + +patch_directory = SingleApplication -- cgit v1.2.1