Wed, 01 Sep 2021 19:54:34 +0200
Merged with recent changes provided by Tobias.
--- a/docs/README.rst Sun Aug 29 19:19:31 2021 +0200 +++ b/docs/README.rst Wed Sep 01 19:54:34 2021 +0200 @@ -94,7 +94,9 @@ 1.3 Installation of Qt Tools via Qt online installer ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ In order to get the most out of eric7 it is recommended to install the Qt Tools -like ``Qt Designer`` or ``Qt Linguist``. The recommended way is this. +like ``Qt Designer`` or ``Qt Linguist``. If the above shown installation +variants are executed, these tools will be installed automatically. Otherwise +it is recommended to get them from th Qt web site by following these steps. 1. Download the Qt online installer from the Qt download site. @@ -145,7 +147,7 @@ 6. Completions/Calltips ----------------------- eric7 provides an interface to the QScintilla completion and call-tips -functionality. QScintilla2 comes with API files for Python and itself. PyQt4 +functionality. QScintilla2 comes with API files for Python and itself. PyQt6 and PyQt5 contain API files as well. These are installed by default. An API file for eric7 is installed in the same place, if installation variant 1 was chosen. @@ -222,6 +224,20 @@ This automatism can be overridden an a per project basis using the "User Properties" dialog. + pip + This is a tool to install additional Python packages from the Python + Package Index (PyPI). It is available from + <https://pypi.org/project/pip/> + + conda + This is another tool to install additional Python packages and manage + virtual environments. It is available from + <https://github.com/conda/conda> or <https://pypi.org/project/conda/> + + virtualenv + This is a tool to create Python virtual environments. It is available + from <https://pypi.org/project/virtualenv/> + coverage.py This is a tool to check Python code coverage. A slightly modified version is part of the eric7 distribution. The original version is @@ -364,7 +380,7 @@ 14. License ----------- -eric7 (and the others) is released under the conditions of the GPLv3. See +eric7 (and the eric7 tools) is released under the conditions of the GPLv3. See separate license file ``LICENSE.GPL3`` for more details. Third party software included in eric7 is released under their respective license and contained in the eric7 distribution for convenience.
--- a/eric7/EricNetwork/EricSslInfoWidget.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/EricNetwork/EricSslInfoWidget.py Wed Sep 01 19:54:34 2021 +0200 @@ -15,6 +15,7 @@ import Utilities +# FIXME: don't use QMenu class EricSslInfoWidget(QMenu): """ Class implementing a widget to show SSL certificate infos.
--- a/eric7/EricNetwork/EricTldExtractor.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/EricNetwork/EricTldExtractor.py Wed Sep 01 19:54:34 2021 +0200 @@ -320,7 +320,8 @@ file = QFile(dataFile) - if not file.open(QIODevice.OpenModeFlag.ReadOnly | QIODevice.OpenModeFlag.Text): + if not file.open(QIODevice.OpenModeFlag.ReadOnly | + QIODevice.OpenModeFlag.Text): return False seekToEndOfPrivateDomains = False @@ -479,7 +480,8 @@ file = QFile(testDataFileName) - if not file.open(QIODevice.OpenModeFlag.ReadOnly | QIODevice.OpenModeFlag.Text): + if not file.open(QIODevice.OpenModeFlag.ReadOnly | + QIODevice.OpenModeFlag.Text): return False testRegExp = re.compile(
--- a/eric7/Preferences/ConfigurationPages/WebBrowserPage.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/Preferences/ConfigurationPages/WebBrowserPage.py Wed Sep 01 19:54:34 2021 +0200 @@ -66,6 +66,10 @@ Preferences.getWebBrowser("ScreenCaptureEnabled")) self.webGLCheckBox.setChecked( Preferences.getWebBrowser("WebGLEnabled")) + self.accelerated2dCanvasCheckBox.setChecked( + Preferences.getWebBrowser("Accelerated2dCanvasEnabled")) + self.autoloadIconsCheckBox.setChecked( + Preferences.getWebBrowser("AutoLoadIconsForPage")) self.autoplayMediaCheckBox.setChecked( Preferences.getWebBrowser("PlaybackRequiresUserGesture")) self.webRtcPublicOnlyCheckBox.setChecked( @@ -144,8 +148,10 @@ idx = 5 self.expireHistory.setCurrentIndex(idx) - # FIXME: fix this issue - for language in range(2, QLocale.Language.LastLanguage + 1): + for language in QLocale.Language: + if language == QLocale.Language.C: + continue + countries = [ loc.country() for loc in QLocale.matchingLocales( @@ -158,7 +164,8 @@ QLocale.languageToString(language), language) self.languageCombo.model().sort(0) self.languageCombo.insertSeparator(0) - self.languageCombo.insertItem(0, QLocale.languageToString(0), 0) + self.languageCombo.insertItem( + 0, QLocale.languageToString(QLocale.Language.AnyLanguage), 0) index = self.languageCombo.findData( Preferences.getWebBrowser("SearchLanguage")) if index > -1: @@ -236,8 +243,14 @@ Preferences.setWebBrowser( "WebGLEnabled", self.webGLCheckBox.isChecked()) + Preferences.setWebBrowser( + "Accelerated2dCanvasEnabled", + self.accelerated2dCanvasCheckBox.isChecked()), Preferences.setWebBrowser( + "AutoLoadIconsForPage", + self.autoloadIconsCheckBox.isChecked()), + Preferences.setWebBrowser( "PlaybackRequiresUserGesture", self.autoplayMediaCheckBox.isChecked()) Preferences.setWebBrowser(
--- a/eric7/Preferences/ConfigurationPages/WebBrowserPage.ui Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/Preferences/ConfigurationPages/WebBrowserPage.ui Wed Sep 01 19:54:34 2021 +0200 @@ -7,7 +7,7 @@ <x>0</x> <y>0</y> <width>650</width> - <height>2084</height> + <height>1630</height> </rect> </property> <layout class="QVBoxLayout" name="verticalLayout_6"> @@ -128,6 +128,26 @@ </widget> </item> <item row="4" column="1"> + <widget class="QCheckBox" name="accelerated2dCanvasCheckBox"> + <property name="toolTip"> + <string>Select to enable support for accelerated 2D canvas using OpenGL</string> + </property> + <property name="text"> + <string>Enable Accelerated 2D Canvas</string> + </property> + </widget> + </item> + <item row="5" column="0"> + <widget class="QCheckBox" name="autoloadIconsCheckBox"> + <property name="toolTip"> + <string>Select to load web site icons automatically</string> + </property> + <property name="text"> + <string>Load Icons automatically</string> + </property> + </widget> + </item> + <item row="5" column="1"> <widget class="QCheckBox" name="autoplayMediaCheckBox"> <property name="toolTip"> <string>Select, to inhibit playback of media content until the user interacts with the page</string> @@ -137,7 +157,7 @@ </property> </widget> </item> - <item row="5" column="0"> + <item row="6" column="0"> <widget class="QCheckBox" name="webRtcPublicOnlyCheckBox"> <property name="toolTip"> <string>Select to limit WebRTC to public IP addresses only</string> @@ -147,7 +167,7 @@ </property> </widget> </item> - <item row="5" column="1"> + <item row="6" column="1"> <widget class="QCheckBox" name="dnsPrefetchCheckBox"> <property name="toolTip"> <string>Select to try to pre-fetch DNS entries to speed up browsing</string> @@ -1173,6 +1193,8 @@ <tabstop>fullscreenCheckBox</tabstop> <tabstop>screenCaptureCheckBox</tabstop> <tabstop>webGLCheckBox</tabstop> + <tabstop>accelerated2dCanvasCheckBox</tabstop> + <tabstop>autoloadIconsCheckBox</tabstop> <tabstop>autoplayMediaCheckBox</tabstop> <tabstop>webRtcPublicOnlyCheckBox</tabstop> <tabstop>dnsPrefetchCheckBox</tabstop>
--- a/eric7/Preferences/__init__.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/Preferences/__init__.py Wed Sep 01 19:54:34 2021 +0200 @@ -22,7 +22,6 @@ import shutil import json import sys -import contextlib from PyQt6.QtCore import ( QDir, QPoint, QLocale, QSettings, QFileInfo, QCoreApplication, QByteArray, @@ -1055,9 +1054,9 @@ if QWebEngineSettings is None: return -## webEngineSettings = QWebEngineSettings.defaultSettings() webEngineSettings = QWebEngineProfile.defaultProfile().settings() cls.webBrowserDefaults.update({ + # fonts "StandardFontFamily": webEngineSettings.fontFamily( QWebEngineSettings.FontFamily.StandardFont), "FixedFontFamily": webEngineSettings.fontFamily( @@ -1070,6 +1069,10 @@ QWebEngineSettings.FontFamily.CursiveFont), "FantasyFontFamily": webEngineSettings.fontFamily( QWebEngineSettings.FontFamily.FantasyFont), + "PictographFontFamily": webEngineSettings.fontFamily( + QWebEngineSettings.FontFamily.PictographFont), + + # font sizes "DefaultFontSize": webEngineSettings.fontSize( QWebEngineSettings.FontSize.DefaultFontSize), "DefaultFixedFontSize": webEngineSettings.fontSize( @@ -1078,6 +1081,11 @@ QWebEngineSettings.FontSize.MinimumFontSize), "MinimumLogicalFontSize": webEngineSettings.fontSize( QWebEngineSettings.FontSize.MinimumLogicalFontSize), + + # text encoding + "DefaultTextEncoding": webEngineSettings.defaultTextEncoding(), + + # web attributes "AutoLoadImages": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.AutoLoadImages), "JavaScriptEnabled": webEngineSettings.testAttribute( @@ -1086,34 +1094,35 @@ QWebEngineSettings.WebAttribute.JavascriptCanOpenWindows), "JavaScriptCanAccessClipboard": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.JavascriptCanAccessClipboard), - "PluginsEnabled": webEngineSettings.testAttribute( - QWebEngineSettings.WebAttribute.PluginsEnabled), + "LinksIncludedInFocusChain": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.LinksIncludedInFocusChain), "LocalStorageEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.LocalStorageEnabled), - "DefaultTextEncoding": webEngineSettings.defaultTextEncoding(), - "SpatialNavigationEnabled": webEngineSettings.testAttribute( - QWebEngineSettings.WebAttribute.SpatialNavigationEnabled), - "LinksIncludedInFocusChain": webEngineSettings.testAttribute( - QWebEngineSettings.WebAttribute.LinksIncludedInFocusChain), "LocalContentCanAccessRemoteUrls": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute .LocalContentCanAccessRemoteUrls), + "XSSAuditingEnabled": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.XSSAuditingEnabled), + "SpatialNavigationEnabled": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.SpatialNavigationEnabled), "LocalContentCanAccessFileUrls": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.LocalContentCanAccessFileUrls), - "XSSAuditingEnabled": webEngineSettings.testAttribute( - QWebEngineSettings.WebAttribute.XSSAuditingEnabled), "ScrollAnimatorEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.ScrollAnimatorEnabled), "ErrorPageEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.ErrorPageEnabled), + "PluginsEnabled": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.PluginsEnabled), "FullScreenSupportEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.FullScreenSupportEnabled), - "PictographFontFamily": webEngineSettings.fontFamily( - QWebEngineSettings.FontFamily.PictographFont), "ScreenCaptureEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.ScreenCaptureEnabled), "WebGLEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.WebGLEnabled), + "Accelerated2dCanvasEnabled": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.Accelerated2dCanvasEnabled), + "AutoLoadIconsForPage": webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.AutoLoadIconsForPage), "FocusOnNavigationEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.FocusOnNavigationEnabled), "PrintElementBackgrounds": webEngineSettings.testAttribute( @@ -1144,14 +1153,10 @@ "DnsPrefetchEnabled": webEngineSettings.testAttribute( QWebEngineSettings.WebAttribute.DnsPrefetchEnabled), + "PdfViewerEnabled": + webEngineSettings.testAttribute( + QWebEngineSettings.WebAttribute.PdfViewerEnabled), }) - with contextlib.suppress(AttributeError): - # Qt 5.13 - cls.webBrowserDefaults.update({ - "PdfViewerEnabled": - webEngineSettings.testAttribute( - QWebEngineSettings.WebAttribute.PdfViewerEnabled), - }) cls.webEngineSettingsIntitialized = True @@ -2784,7 +2789,7 @@ elif key in ["StartupBehavior", "HistoryLimit", "DownloadManagerRemovePolicy", "SyncType", "SyncFtpPort", "SyncFtpIdleTimeout", "SyncEncryptionKeyLength", - "SearchLanguage", "DefaultFontSize", "DefaultFixedFontSize", + "DefaultFontSize", "DefaultFixedFontSize", "MinimumFontSize", "MinimumLogicalFontSize", "DiskCacheSize", "AcceptCookies", "KeepCookiesUntil", "AdBlockUpdatePeriod", "TabManagerGroupByType", @@ -2826,6 +2831,7 @@ "WebRTCPublicInterfacesOnly", "DnsPrefetchEnabled", "VirusTotalEnabled", "VirusTotalSecure", "PdfViewerEnabled", "AlwaysRejectFaultyCertificates", + "Accelerated2dCanvasEnabled", "AutoLoadIconsForPage", ]: return toBool(prefClass.settings.value( "WebBrowser/" + key, prefClass.webBrowserDefaults[key]))
--- a/eric7/WebBrowser/AdBlock/AdBlockManager.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/AdBlock/AdBlockManager.py Wed Sep 01 19:54:34 2021 +0200 @@ -425,7 +425,7 @@ else: subscriptions = ( [self.__defaultSubscriptionUrlString] + - self.__additionalDefaultSubscriptionUrlStrings + + list(self.__additionalDefaultSubscriptionUrlStrings) + [self.__customSubscriptionUrlString] ) for subscription in subscriptions:
--- a/eric7/WebBrowser/AdBlock/AdBlockRule.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/AdBlock/AdBlockRule.py Wed Sep 01 19:54:34 2021 +0200 @@ -13,6 +13,8 @@ from PyQt6.QtCore import Qt from PyQt6.QtWebEngineCore import QWebEngineUrlRequestInfo +from EricNetwork import EricTldExtractor + def toSecondLevelDomain(url): """ @@ -23,7 +25,7 @@ @return name of second level domain @rtype str """ - topLevelDomain = url.topLevelDomain() + topLevelDomain = EricTldExtractor.instance().tld(url.host()) urlHost = url.host() if not topLevelDomain or not urlHost:
--- a/eric7/WebBrowser/AdBlock/AdBlockSubscription.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/AdBlock/AdBlockSubscription.py Wed Sep 01 19:54:34 2021 +0200 @@ -437,14 +437,14 @@ # ignore Third-party advertisers rules for performance # whitelist rules at the end will be used index = response.indexOf( - "!---------------------------" - "Third-party advertisers" - "---------------------------!") + b"!---------------------------" + b"Third-party advertisers" + b"---------------------------!") part1 = response.left(index) index = response.indexOf( - "!-----------------------" - "Whitelists to fix broken sites" - "------------------------!") + b"!-----------------------" + b"Whitelists to fix broken sites" + b"------------------------!") part2 = response.mid(index) f.write(part1) f.write(part2)
--- a/eric7/WebBrowser/Download/DownloadItem.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/Download/DownloadItem.py Wed Sep 01 19:54:34 2021 +0200 @@ -7,6 +7,7 @@ Module implementing a widget controlling a download. """ +import enum import os from PyQt6.QtCore import ( @@ -27,6 +28,15 @@ import Utilities.MimeTypes +class DownloadState(enum.Enum): + """ + Class implementing the various download states. + """ + Downloading = 0 + Successful = 1 + Cancelled = 2 + + class DownloadItem(QWidget, Ui_DownloadItem): """ Class implementing a widget controlling a download. @@ -39,11 +49,6 @@ downloadFinished = pyqtSignal(bool) progress = pyqtSignal(int, int) - # TODO: convert this to an enum - Downloading = 0 - DownloadSuccessful = 1 - DownloadCancelled = 2 - def __init__(self, downloadRequest=None, pageUrl=None, parent=None): """ Constructor @@ -71,7 +76,7 @@ self.openButton.setEnabled(False) self.openButton.setVisible(False) - self.__state = DownloadItem.Downloading + self.__state = DownloadState.Downloading icon = self.style().standardIcon(QStyle.StandardPixmap.SP_FileIcon) self.fileIcon.setPixmap(icon.pixmap(48, 48)) @@ -110,7 +115,8 @@ # attach to the download item object self.__url = self.__downloadRequest.url() - self.__downloadRequest.receivedBytesChanged.connect(self.__downloadProgress) + self.__downloadRequest.receivedBytesChanged.connect( + self.__downloadProgress) self.__downloadRequest.isFinishedChanged.connect(self.__finished) # reset info @@ -307,7 +313,7 @@ self.pauseButton.setEnabled(False) self.pauseButton.setVisible(False) self.setUpdatesEnabled(True) - self.__state = DownloadItem.DownloadCancelled + self.__state = DownloadState.Cancelled self.__downloadRequest.cancel() self.__setDateTime() self.downloadFinished.emit(False) @@ -463,7 +469,7 @@ @return flag indicating a download is in progress (boolean) """ - return self.__state == DownloadItem.Downloading + return self.__state == DownloadState.Downloading def downloadedSuccessfully(self): """ @@ -471,7 +477,7 @@ @return flag indicating a successful download (boolean) """ - return self.__state == DownloadItem.DownloadSuccessful + return self.__state == DownloadState.Successful def downloadCanceled(self): """ @@ -479,7 +485,7 @@ @return flag indicating a canceled download (boolean) """ - return self.__state == DownloadItem.DownloadCancelled + return self.__state == DownloadState.Cancelled def __finished(self): """ @@ -497,7 +503,7 @@ self.stopButton.setVisible(False) self.openButton.setEnabled(noError) self.openButton.setVisible(noError) - self.__state = DownloadItem.DownloadSuccessful + self.__state = DownloadState.Successful self.__updateInfoLabel() self.__setDateTime() @@ -588,9 +594,9 @@ self.openButton.setEnabled(data["Done"]) self.openButton.setVisible(data["Done"]) if data["Done"]: - self.__state = DownloadItem.DownloadSuccessful + self.__state = DownloadState.Successful else: - self.__state = DownloadItem.DownloadCancelled + self.__state = DownloadState.Cancelled self.progressBar.setVisible(False) self.__adjustSize()
--- a/eric7/WebBrowser/FeaturePermissions/FeaturePermissionManager.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/FeaturePermissions/FeaturePermissionManager.py Wed Sep 01 19:54:34 2021 +0200 @@ -7,8 +7,6 @@ Module implementing the feature permission manager object. """ -import contextlib - from PyQt6.QtCore import QObject from PyQt6.QtWidgets import QDialog from PyQt6.QtWebEngineCore import QWebEnginePage @@ -65,13 +63,11 @@ QWebEnginePage.PermissionPolicy.PermissionDeniedByUser: [], }, - } - with contextlib.suppress(AttributeError): - # this was re-added in Qt 5.13.0 - self.__featurePermissions[QWebEnginePage.Feature.Notifications] = { + QWebEnginePage.Feature.Notifications: { QWebEnginePage.PermissionPolicy.PermissionGrantedByUser: [], QWebEnginePage.PermissionPolicy.PermissionDeniedByUser: [], } + } self.__featurePermissionsKeys = { (QWebEnginePage.Feature.Geolocation, @@ -116,17 +112,13 @@ (QWebEnginePage.Feature.DesktopAudioVideoCapture, QWebEnginePage.PermissionPolicy.PermissionDeniedByUser): "DesktopAudioVideoCaptureDenied", + (QWebEnginePage.Feature.Notifications, + QWebEnginePage.PermissionPolicy.PermissionGrantedByUser): + "NotificationsGranted", + (QWebEnginePage.Feature.Notifications, + QWebEnginePage.PermissionPolicy.PermissionDeniedByUser): + "NotificationsDenied", } - with contextlib.suppress(AttributeError): - # this was re-added in Qt 5.13.0 - self.__featurePermissionsKeys.update({ - (QWebEnginePage.Feature.Notifications, - QWebEnginePage.PermissionPolicy.PermissionGrantedByUser): - "NotificationsGranted", - (QWebEnginePage.Feature.Notifications, - QWebEnginePage.PermissionPolicy.PermissionDeniedByUser): - "NotificationsDenied", - }) self.__loaded = False
--- a/eric7/WebBrowser/FeaturePermissions/FeaturePermissionsDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/FeaturePermissions/FeaturePermissionsDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -37,23 +37,21 @@ # add the various lists - if hasattr(QWebEnginePage, "Notifications"): - # this was re-added in Qt 5.13.0 - self.notifList = QTreeWidget() - self.notifList.setAlternatingRowColors(True) - self.notifList.setSelectionMode( - QAbstractItemView.SelectionMode.ExtendedSelection) - self.notifList.setRootIsDecorated(False) - self.notifList.setItemsExpandable(False) - self.notifList.setAllColumnsShowFocus(True) - self.notifList.setObjectName("notifList") - self.notifList.setSortingEnabled(True) - self.notifList.headerItem().setText(0, self.tr("Host")) - self.notifList.headerItem().setText(1, self.tr("Permission")) - self.tabWidget.addTab( - self.notifList, - UI.PixmapCache.getIcon("notification"), - self.tr("Notifications")) + self.notifList = QTreeWidget() + self.notifList.setAlternatingRowColors(True) + self.notifList.setSelectionMode( + QAbstractItemView.SelectionMode.ExtendedSelection) + self.notifList.setRootIsDecorated(False) + self.notifList.setItemsExpandable(False) + self.notifList.setAllColumnsShowFocus(True) + self.notifList.setObjectName("notifList") + self.notifList.setSortingEnabled(True) + self.notifList.headerItem().setText(0, self.tr("Host")) + self.notifList.headerItem().setText(1, self.tr("Permission")) + self.tabWidget.addTab( + self.notifList, + UI.PixmapCache.getIcon("notification"), + self.tr("Notifications")) self.geoList = QTreeWidget() self.geoList.setAlternatingRowColors(True) @@ -135,55 +133,47 @@ UI.PixmapCache.getIcon("mouse"), self.tr("Mouse Lock")) - if hasattr(QWebEnginePage, "DesktopVideoCapture"): - # these are shown as of Qt 5.10.0/PyQt 5.10.0 - self.deskVidList = QTreeWidget() - self.deskVidList.setAlternatingRowColors(True) - self.deskVidList.setSelectionMode( - QAbstractItemView.SelectionMode.ExtendedSelection) - self.deskVidList.setRootIsDecorated(False) - self.deskVidList.setItemsExpandable(False) - self.deskVidList.setAllColumnsShowFocus(True) - self.deskVidList.setObjectName("deskVidList") - self.deskVidList.setSortingEnabled(True) - self.deskVidList.headerItem().setText(0, self.tr("Host")) - self.deskVidList.headerItem().setText(1, self.tr("Permission")) - self.tabWidget.addTab( - self.deskVidList, - UI.PixmapCache.getIcon("desktopVideoCapture"), - self.tr("Desktop Video")) - - self.deskAudVidList = QTreeWidget() - self.deskAudVidList.setAlternatingRowColors(True) - self.deskAudVidList.setSelectionMode( - QAbstractItemView.SelectionMode.ExtendedSelection) - self.deskAudVidList.setRootIsDecorated(False) - self.deskAudVidList.setItemsExpandable(False) - self.deskAudVidList.setAllColumnsShowFocus(True) - self.deskAudVidList.setObjectName("deskAudVidList") - self.deskAudVidList.setSortingEnabled(True) - self.deskAudVidList.headerItem().setText(0, self.tr("Host")) - self.deskAudVidList.headerItem().setText(1, self.tr("Permission")) - self.tabWidget.addTab( - self.deskAudVidList, - UI.PixmapCache.getIcon("desktopAudioVideoCapture"), - self.tr("Desktop Audio && Video")) + self.deskVidList = QTreeWidget() + self.deskVidList.setAlternatingRowColors(True) + self.deskVidList.setSelectionMode( + QAbstractItemView.SelectionMode.ExtendedSelection) + self.deskVidList.setRootIsDecorated(False) + self.deskVidList.setItemsExpandable(False) + self.deskVidList.setAllColumnsShowFocus(True) + self.deskVidList.setObjectName("deskVidList") + self.deskVidList.setSortingEnabled(True) + self.deskVidList.headerItem().setText(0, self.tr("Host")) + self.deskVidList.headerItem().setText(1, self.tr("Permission")) + self.tabWidget.addTab( + self.deskVidList, + UI.PixmapCache.getIcon("desktopVideoCapture"), + self.tr("Desktop Video")) - if hasattr(QWebEnginePage, "Notifications"): - self.setTabOrder(self.tabWidget, self.notifList) - self.setTabOrder(self.notifList, self.geoList) - else: - self.setTabOrder(self.tabWidget, self.geoList) + self.deskAudVidList = QTreeWidget() + self.deskAudVidList.setAlternatingRowColors(True) + self.deskAudVidList.setSelectionMode( + QAbstractItemView.SelectionMode.ExtendedSelection) + self.deskAudVidList.setRootIsDecorated(False) + self.deskAudVidList.setItemsExpandable(False) + self.deskAudVidList.setAllColumnsShowFocus(True) + self.deskAudVidList.setObjectName("deskAudVidList") + self.deskAudVidList.setSortingEnabled(True) + self.deskAudVidList.headerItem().setText(0, self.tr("Host")) + self.deskAudVidList.headerItem().setText(1, self.tr("Permission")) + self.tabWidget.addTab( + self.deskAudVidList, + UI.PixmapCache.getIcon("desktopAudioVideoCapture"), + self.tr("Desktop Audio && Video")) + + self.setTabOrder(self.tabWidget, self.notifList) + self.setTabOrder(self.notifList, self.geoList) self.setTabOrder(self.geoList, self.micList) self.setTabOrder(self.micList, self.camList) self.setTabOrder(self.camList, self.micCamList) self.setTabOrder(self.micCamList, self.mouseLockList) - if hasattr(QWebEnginePage, "DesktopVideoCapture"): - self.setTabOrder(self.mouseLockList, self.deskVidList) - self.setTabOrder(self.deskVidList, self.deskAudVidList) - self.setTabOrder(self.deskAudVidList, self.removeButton) - else: - self.setTabOrder(self.mouseLockList, self.removeButton) + self.setTabOrder(self.mouseLockList, self.deskVidList) + self.setTabOrder(self.deskVidList, self.deskAudVidList) + self.setTabOrder(self.deskAudVidList, self.removeButton) self.setTabOrder(self.removeButton, self.removeAllButton) self.__permissionStrings = { @@ -199,18 +189,11 @@ QWebEnginePage.Feature.MediaVideoCapture: self.camList, QWebEnginePage.Feature.MediaAudioVideoCapture: self.micCamList, QWebEnginePage.Feature.MouseLock: self.mouseLockList, + QWebEnginePage.Feature.DesktopVideoCapture: self.deskVidList, + QWebEnginePage.Feature.DesktopAudioVideoCapture: + self.deskAudVidList, + QWebEnginePage.Feature.Notifications: self.notifList, } - if hasattr(QWebEnginePage, "DesktopVideoCapture"): - self.__permissionsLists.update({ - QWebEnginePage.Feature.DesktopVideoCapture: - self.deskVidList, - QWebEnginePage.Feature.DesktopAudioVideoCapture: - self.deskAudVidList, - }) - if hasattr(QWebEnginePage, "Notifications"): - self.__permissionsLists[QWebEnginePage.Feature.Notifications] = ( - self.notifList - ) for feature, permissionsList in self.__permissionsLists.items(): for permission in featurePermissions[feature]: @@ -281,7 +264,7 @@ while currentList.topLevelItemCount() > 0: itm = currentList.takeTopLevelItem(0) # __IGNORE_WARNING__ del itm - self.__updateGeoButtons() + self.__updateButtons() def getData(self): """
--- a/eric7/WebBrowser/Network/SslErrorExceptionsDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/Network/SslErrorExceptionsDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -31,50 +31,59 @@ self.setupUi(self) self.__errorDescriptions = { - QWebEngineCertificateError.Error.SslPinnedKeyNotInCertificateChain: + QWebEngineCertificateError.Type.SslPinnedKeyNotInCertificateChain: self.tr("The certificate did not match the built-in public" " keys pinned for the host name."), - QWebEngineCertificateError.Error.CertificateCommonNameInvalid: + QWebEngineCertificateError.Type.CertificateCommonNameInvalid: self.tr("The certificate's common name did not match the" " host name."), - QWebEngineCertificateError.Error.CertificateDateInvalid: + QWebEngineCertificateError.Type.CertificateDateInvalid: self.tr("The certificate is not valid at the current date" " and time."), - QWebEngineCertificateError.Error.CertificateAuthorityInvalid: + QWebEngineCertificateError.Type.CertificateAuthorityInvalid: self.tr("The certificate is not signed by a trusted" " authority."), - QWebEngineCertificateError.Error.CertificateContainsErrors: + QWebEngineCertificateError.Type.CertificateContainsErrors: self.tr("The certificate contains errors."), - QWebEngineCertificateError.Error.CertificateNoRevocationMechanism: + QWebEngineCertificateError.Type.CertificateNoRevocationMechanism: self.tr("The certificate has no mechanism for determining if" " it has been revoked."), - QWebEngineCertificateError.Error + QWebEngineCertificateError.Type .CertificateUnableToCheckRevocation: self.tr("Revocation information for the certificate is" " not available."), - QWebEngineCertificateError.Error.CertificateRevoked: + QWebEngineCertificateError.Type.CertificateRevoked: self.tr("The certificate has been revoked."), - QWebEngineCertificateError.Error.CertificateInvalid: + QWebEngineCertificateError.Type.CertificateInvalid: self.tr("The certificate is invalid."), - QWebEngineCertificateError.Error.CertificateWeakSignatureAlgorithm: + QWebEngineCertificateError.Type.CertificateWeakSignatureAlgorithm: self.tr("The certificate is signed using a weak signature" " algorithm."), - QWebEngineCertificateError.Error.CertificateNonUniqueName: + QWebEngineCertificateError.Type.CertificateNonUniqueName: self.tr("The host name specified in the certificate is" " not unique."), - QWebEngineCertificateError.Error.CertificateWeakKey: + QWebEngineCertificateError.Type.CertificateWeakKey: self.tr("The certificate contains a weak key."), - QWebEngineCertificateError.Error + QWebEngineCertificateError.Type .CertificateNameConstraintViolation: self.tr("The certificate claimed DNS names that are in" " violation of name constraints."), - QWebEngineCertificateError.Error.CertificateValidityTooLong: + QWebEngineCertificateError.Type.CertificateValidityTooLong: self.tr("The certificate has a validity period that is" " too long."), - QWebEngineCertificateError.Error.CertificateTransparencyRequired: + QWebEngineCertificateError.Type.CertificateTransparencyRequired: self.tr("Certificate Transparency was required for this" " connection, but the server did not provide" " information that complied with the policy."), + QWebEngineCertificateError.Type + .CertificateKnownInterceptionBlocked: + self.tr("The certificate is known to be used for interception" + " by an entity other than the device owner."), + QWebEngineCertificateError.Type.SslObsoleteVersion: + self.tr("The connection uses an obsolete version of SSL/TLS."), + QWebEngineCertificateError.Type.CertificateSymantecLegacy: + self.tr("The certificate is a legacy Symantec one that's no" + " longer valid."), } for host, errors in errorsDict.items():
--- a/eric7/WebBrowser/QtHelp/HelpIndexWidget.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/QtHelp/HelpIndexWidget.py Wed Sep 01 19:54:34 2021 +0200 @@ -73,7 +73,7 @@ self.__index.activateCurrentItem) self.__layout.addWidget(self.__index) - @pyqtSlot(QUrl, str) + @pyqtSlot(QHelpLink, str) def __documentActivated(self, document, keyword, modifiers=None): """ Private slot to handle the activation of a keyword entry. @@ -101,39 +101,39 @@ else: self.openUrl.emit(document.url) - def __documentsActivated(self, documents, keyword): + def __documentsActivated(self, documents, helpKeyword): """ Private slot to handle the activation of an entry with multiple help documents. @param documents list of help document link data structures @type list of QHelpLink - @param keyword keyword for the entry + @param helpKeyword keyword for the entry @type str """ modifiers = QApplication.keyboardModifiers() document = ( documents[0] if len(documents) == 1 else - self.__selectDocument(documents, keyword) + self.__selectDocument(documents, helpKeyword) ) - self.__documentActivated(document, keyword, modifiers) + self.__documentActivated(document, helpKeyword, modifiers) - def __selectDocument(self, documents, keyword): + def __selectDocument(self, documents, helpKeyword): """ Private method to give the user a chance to select among the given documents. @param documents list of help document link data structures @type list of QHelpLink - @param keyword keyword for the documents + @param helpKeyword keyword for the documents @type str @return selected document @rtype QHelpLink """ document = QHelpLink() from .HelpTopicDialog import HelpTopicDialog - dlg = HelpTopicDialog(self, keyword, documents) + dlg = HelpTopicDialog(self, helpKeyword, documents) if dlg.exec() == QDialog.DialogCode.Accepted: document = dlg.document() return document @@ -225,12 +225,12 @@ act = menu.exec() model = self.__index.model() if model is not None: - keyword = model.data(idx, Qt.ItemDataRole.DisplayRole) - links = model.linksForKeyword(keyword) - if len(links) == 1: - link = QUrl(links[list(links.keys())[0]]) + helpKeyword = model.data(idx, Qt.ItemDataRole.DisplayRole) + helpLinks = self.__engine.documentsForKeyword(helpKeyword, "") + if len(helpLinks) == 1: + link = helpLinks[0].url else: - link = self.__selectLink(links, keyword) + link = self.__selectDocument(helpLinks, helpKeyword) if not link.isEmpty() and link.isValid(): if act == curTab:
--- a/eric7/WebBrowser/QtHelp/HelpTopicDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/QtHelp/HelpTopicDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -18,13 +18,13 @@ """ Class implementing a dialog to select a help topic to display. """ - def __init__(self, parent, keyword, documents): + def __init__(self, parent, helpKeyword, documents): """ Constructor @param parent reference to the parent widget @type QWidget - @param keyword keyword for the link set + @param helpKeyword keyword for the link set @type str @param documents list of help document link data structures @type list of QHelpLink @@ -33,7 +33,7 @@ self.setupUi(self) self.label.setText(self.tr("Choose a &topic for <b>{0}</b>:") - .format(keyword)) + .format(helpKeyword)) for document in documents: itm = self.topicsList.addItem(document.title)
--- a/eric7/WebBrowser/QtHelp/QtHelpDocumentationConfigurationDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/QtHelp/QtHelpDocumentationConfigurationDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -75,7 +75,8 @@ @param button button that was clicked @type QAbstractButton """ - if button == QDialogButtonBox.StandardButton.Apply: + if button == self.buttonBox.button( + QDialogButtonBox.StandardButton.Apply): self.__applyConfiguration() self.__settings = QtHelpDocumentationSettings.readSettings( @@ -87,7 +88,8 @@ self.__settings.versions()) self.filterSettingsWidget.readSettings( self.__engine.filterEngine()) - elif button == QDialogButtonBox.StandardButton.Ok: + elif button == self.buttonBox.button( + QDialogButtonBox.StandardButton.Ok): self.__applyConfiguration() self.accept()
--- a/eric7/WebBrowser/QtHelp/QtHelpDocumentationSettings.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/QtHelp/QtHelpDocumentationSettings.py Wed Sep 01 19:54:34 2021 +0200 @@ -80,7 +80,7 @@ return False try: - filename = self._namespaceToFilename(namespace) + filename = self._namespaceToFilename[namespace] except KeyError: return False @@ -109,7 +109,7 @@ @return name of the namespace @rtype str """ - return self._filenameToNamespace(filename) + return self._filenameToNamespace[filename] def components(self): """
--- a/eric7/WebBrowser/QtHelp/QtHelpDocumentationSettingsWidget.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/QtHelp/QtHelpDocumentationSettingsWidget.py Wed Sep 01 19:54:34 2021 +0200 @@ -102,10 +102,8 @@ self) if dlg.exec() == QDialog.DialogCode.Accepted: documents = dlg.getData() - if not documents: - return - - self.__registerDocumentation(documents) + if documents: + self.__registerDocumentation(documents) def __registerDocumentation(self, filenames): """
--- a/eric7/WebBrowser/SafeBrowsing/SafeBrowsingInfoWidget.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/SafeBrowsing/SafeBrowsingInfoWidget.py Wed Sep 01 19:54:34 2021 +0200 @@ -13,6 +13,7 @@ import UI.PixmapCache +# FIXME: don't use QMenu class SafeBrowsingInfoWidget(QMenu): """ Class implementing a widget to show some threat information.
--- a/eric7/WebBrowser/SafeBrowsing/SafeBrowsingUrl.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/SafeBrowsing/SafeBrowsingUrl.py Wed Sep 01 19:54:34 2021 +0200 @@ -89,10 +89,10 @@ if len(url.split('://')) <= 1: url = Preferences.getWebBrowser("DefaultScheme") + url url = quote(fullUnescape(url)) - urlParts = urllib.parse.parse.urlsplit(url) + urlParts = urllib.parse.urlsplit(url) if not urlParts[0]: url = Preferences.getWebBrowser("DefaultScheme") + url - urlParts = urllib.parse.parse.urlsplit(url) + urlParts = urllib.parse.urlsplit(url) protocol = urlParts.scheme host = fullUnescape(urlParts.hostname) path = fullUnescape(urlParts.path)
--- a/eric7/WebBrowser/SiteInfo/SiteInfoWidget.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/SiteInfo/SiteInfoWidget.py Wed Sep 01 19:54:34 2021 +0200 @@ -158,6 +158,9 @@ horizontalLayout.addWidget(moreButton) moreButton.clicked.connect(self.__showSiteInfo) layout.addLayout(horizontalLayout, rows, 0, 1, -1) + + # TODO: check, if this changes anything + layout.activate() def showAt(self, pos): """
--- a/eric7/WebBrowser/VirusTotal/VirusTotalApi.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/VirusTotal/VirusTotalApi.py Wed Sep 01 19:54:34 2021 +0200 @@ -8,6 +8,7 @@ API class. """ +import contextlib import json from PyQt6.QtCore import pyqtSignal, QObject, QUrl, QUrlQuery, QByteArray @@ -169,7 +170,7 @@ WebBrowser.WebBrowserWindow.WebBrowserWindow.networkManager() ) reply = nam.post(request, params) - reply.finished.connect(self.__submitUrlFinished) + reply.finished.connect(lambda: self.__submitUrlFinished(reply)) self.__replies.append(reply) def __submitUrlFinished(self, reply): @@ -216,7 +217,8 @@ WebBrowser.WebBrowserWindow.WebBrowserWindow.networkManager() ) reply = nam.post(request, params) - reply.finished.connect(self.__getUrlScanReportUrlFinished) + reply.finished.connect( + lambda: self.__getUrlScanReportUrlFinished(reply)) self.__replies.append(reply) def __getUrlScanReportUrlFinished(self, reply): @@ -252,7 +254,8 @@ WebBrowser.WebBrowserWindow.WebBrowserWindow.networkManager() ) reply = nam.post(request, params) - reply.finished.connect(self.__getFileScanReportUrlFinished) + reply.finished.connect( + lambda: self.__getFileScanReportUrlFinished(reply)) self.__replies.append(reply) def __getFileScanReportUrlFinished(self, reply): @@ -293,7 +296,8 @@ WebBrowser.WebBrowserWindow.WebBrowserWindow.networkManager() ) reply = nam.get(request) - reply.finished.connect(self.__getIpAddressReportFinished) + reply.finished.connect( + lambda: self.__getIpAddressReportFinished(reply)) self.__replies.append(reply) def __getIpAddressReportFinished(self, reply): @@ -388,29 +392,47 @@ subdomains = result["subdomains"] except KeyError: subdomains = [] - try: - bdCategory = result["BitDefender category"] - except KeyError: - bdCategory = self.tr("not available") - try: - tmCategory = result["TrendMicro category"] - except KeyError: - tmCategory = self.tr("not available") - try: - wtsCategory = result["Websense ThreatSeeker category"] - except KeyError: - wtsCategory = self.tr("not available") + + categoriesMapping = { + "bitdefender": ("BitDefender category",), + "sophos": ("sophos category", "Sophos category"), + "valkyrie": ("Comodo Valkyrie Verdict category",), + "alpha": ("alphaMountain.ai category",), + "forcepoint": ("Forcepoint ThreatSeeker category",), + } + categories = {} + for key, vtCategories in categoriesMapping.items(): + for vtCategory in vtCategories: + with contextlib.suppress(KeyError): + categories[key] = result[vtCategory] + break + else: + categories[key] = "--" try: whois = result["whois"] except KeyError: whois = "" + webutationData = { + "adult": "--", + "safety": "--", + "verdict": "--" + } + with contextlib.suppress(KeyError): + webutation = result["Webutation domain info"] + with contextlib.suppress(KeyError): + webutationData["adult"] = webutation["Adult content"] + with contextlib.suppress(KeyError): + webutationData["safety"] = webutation["Safety score"] + with contextlib.suppress(KeyError): + webutationData["verdict"] = webutation["Verdict"] + from .VirusTotalDomainReportDialog import ( VirusTotalDomainReportDialog ) self.__domainReportDlg = VirusTotalDomainReportDialog( self.__lastDomain, resolutions, urls, subdomains, - bdCategory, tmCategory, wtsCategory, whois) + categories, webutationData, whois) self.__domainReportDlg.show() self.__replies.remove(reply) reply.deleteLater()
--- a/eric7/WebBrowser/VirusTotal/VirusTotalDomainReportDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/VirusTotal/VirusTotalDomainReportDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -20,7 +20,7 @@ Class implementing a dialog to show the VirusTotal domain report. """ def __init__(self, domain, resolutions, urls, subdomains, - bdCategory, tmCategory, wtsCategory, whois, parent=None): + categories, webutation, whois, parent=None): """ Constructor @@ -32,12 +32,11 @@ @type list of dict @param subdomains list of subdomains @type list of str - @param bdCategory BitDefender categorization - @type str - @param tmCategory TrendMicro categorization - @type str - @param wtsCategory Websense ThreatSeeker categorization - @type str + @param categories dictionary with various categorizations with keys + 'bitdefender', 'sophos', 'valkyrie', 'alpha', 'forcepoint' + @type dict + @param webutation dictionary with Webutation data with keys + 'adult', 'safety', 'verdict' @param whois whois information @type str @param parent reference to the parent widget @@ -62,8 +61,6 @@ self.resolutionsList.resizeColumnToContents(1) self.resolutionsList.sortByColumn(0, Qt.SortOrder.AscendingOrder) - if not urls: - self.detectedUrlsGroup.setVisible(False) for url in urls: QTreeWidgetItem( self.urlsList, @@ -77,15 +74,19 @@ self.urlsList.resizeColumnToContents(2) self.urlsList.sortByColumn(0, Qt.SortOrder.AscendingOrder) - if not subdomains: - self.subdomainsGroup.setVisible(False) - else: + if subdomains: self.subdomainsList.addItems(subdomains) self.subdomainsList.sortItems() - self.bdLabel.setText(bdCategory) - self.tmLabel.setText(tmCategory) - self.wtsLabel.setText(wtsCategory) + self.bdLabel.setText(categories["bitdefender"]) + self.soLabel.setText(categories["sophos"]) + self.vvLabel.setText(categories["valkyrie"]) + self.amLabel.setText(categories["alpha"]) + self.ftsLabel.setText(categories["forcepoint"]) + + self.webutationAdultLabel.setText(webutation["adult"]) + self.webutationSafetyLabel.setText(str(webutation["safety"])) + self.webutationVerdictLabel.setText(webutation["verdict"]) self.__whois = whois self.__whoisDomain = domain
--- a/eric7/WebBrowser/VirusTotal/VirusTotalDomainReportDialog.ui Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/VirusTotal/VirusTotalDomainReportDialog.ui Wed Sep 01 19:54:34 2021 +0200 @@ -48,11 +48,11 @@ </widget> </item> <item> - <layout class="QHBoxLayout" name="horizontalLayout_3"> - <item> + <layout class="QGridLayout" name="gridLayout_3"> + <item row="0" column="0" rowspan="2"> <widget class="QGroupBox" name="groupBox"> <property name="sizePolicy"> - <sizepolicy hsizetype="Preferred" vsizetype="Preferred"> + <sizepolicy hsizetype="Expanding" vsizetype="Minimum"> <horstretch>0</horstretch> <verstretch>0</verstretch> </sizepolicy> @@ -60,73 +60,204 @@ <property name="title"> <string>Categorizations</string> </property> - <layout class="QHBoxLayout" name="horizontalLayout"> - <item> - <layout class="QGridLayout" name="gridLayout"> - <item row="0" column="0"> - <widget class="QLabel" name="label"> - <property name="text"> - <string notr="true">BitDefender:</string> - </property> - </widget> - </item> - <item row="0" column="1"> - <widget class="QLabel" name="bdLabel"> - <property name="text"> - <string/> - </property> - </widget> - </item> - <item row="1" column="0"> - <widget class="QLabel" name="label_2"> - <property name="text"> - <string notr="true">TrendMicro:</string> - </property> - </widget> - </item> - <item row="1" column="1"> - <widget class="QLabel" name="tmLabel"> - <property name="text"> - <string/> - </property> - </widget> - </item> - <item row="2" column="0"> - <widget class="QLabel" name="label_3"> - <property name="text"> - <string notr="true">Websense ThreatSeeker:</string> - </property> - </widget> - </item> - <item row="2" column="1"> - <widget class="QLabel" name="wtsLabel"> - <property name="text"> - <string/> - </property> - </widget> - </item> - </layout> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="0"> + <widget class="QLabel" name="label"> + <property name="text"> + <string notr="true">BitDefender:</string> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QLabel" name="bdLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_2"> + <property name="text"> + <string notr="true">Sophos:</string> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QLabel" name="soLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="2" column="0"> + <widget class="QLabel" name="label_4"> + <property name="text"> + <string>Valkyrie Verdict:</string> + </property> + </widget> </item> - <item> - <spacer name="horizontalSpacer"> - <property name="orientation"> - <enum>Qt::Horizontal</enum> + <item row="2" column="1"> + <widget class="QLabel" name="vvLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="3" column="0"> + <widget class="QLabel" name="label_5"> + <property name="text"> + <string>alphaMountain:</string> + </property> + </widget> + </item> + <item row="3" column="1"> + <widget class="QLabel" name="amLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> </property> - <property name="sizeHint" stdset="0"> - <size> - <width>690</width> - <height>20</height> - </size> + <property name="text"> + <string/> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="4" column="0"> + <widget class="QLabel" name="label_3"> + <property name="text"> + <string notr="true">Forcepoint ThreatSeeker:</string> </property> - </spacer> + </widget> + </item> + <item row="4" column="1"> + <widget class="QLabel" name="ftsLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> </item> </layout> </widget> </item> - <item> + <item row="0" column="1"> + <widget class="QGroupBox" name="groupBox_2"> + <property name="maximumSize"> + <size> + <width>300</width> + <height>16777215</height> + </size> + </property> + <property name="title"> + <string notr="true">Webutation</string> + </property> + <layout class="QGridLayout" name="gridLayout_2"> + <item row="0" column="0"> + <widget class="QLabel" name="label_6"> + <property name="text"> + <string>Adult Content:</string> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QLabel" name="webutationAdultLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_7"> + <property name="text"> + <string>Safety Score:</string> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QLabel" name="webutationSafetyLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + </widget> + </item> + <item row="2" column="0"> + <widget class="QLabel" name="label_8"> + <property name="text"> + <string>Verdict:</string> + </property> + </widget> + </item> + <item row="2" column="1"> + <widget class="QLabel" name="webutationVerdictLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string/> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item row="1" column="1"> <widget class="QPushButton" name="whoisButton"> <property name="text"> - <string>Whois</string> + <string notr="true">Whois</string> </property> </widget> </item> @@ -148,6 +279,12 @@ <layout class="QVBoxLayout" name="verticalLayout_2"> <item> <widget class="QTreeWidget" name="resolutionsList"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> <property name="alternatingRowColors"> <bool>true</bool> </property> @@ -189,6 +326,12 @@ <layout class="QVBoxLayout" name="verticalLayout"> <item> <widget class="QListWidget" name="subdomainsList"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> <property name="alternatingRowColors"> <bool>true</bool> </property> @@ -216,6 +359,12 @@ <layout class="QVBoxLayout" name="verticalLayout_3"> <item> <widget class="QTreeWidget" name="urlsList"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> <property name="alternatingRowColors"> <bool>true</bool> </property>
--- a/eric7/WebBrowser/WebBrowserLanguagesDialog.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/WebBrowserLanguagesDialog.py Wed Sep 01 19:54:34 2021 +0200 @@ -38,9 +38,10 @@ self.__model.setStringList(languages) allLanguages = [] - for index in range(QLocale.Language.C + 1, - QLocale.Language.LastLanguage + 1): - allLanguages += self.expand(QLocale.Language(index)) + for language in QLocale.Language: + if language == QLocale.Language.C: + continue + allLanguages += self.expand(language) self.__allLanguagesModel = QStringListModel() self.__allLanguagesModel.setStringList(allLanguages) self.addCombo.setModel(self.__allLanguagesModel)
--- a/eric7/WebBrowser/WebBrowserPage.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/WebBrowserPage.py Wed Sep 01 19:54:34 2021 +0200 @@ -111,6 +111,16 @@ self.__setupChannelTimer.setInterval(100) self.__setupChannelTimer.timeout.connect(self.__setupChannelTimeout) + def view(self): + """ + Public method to get a reference to the WebBrowserView associated with + the page. + + @return reference to the WebBrowserView associated with the page + r@type WebBrowserView + """ + return self.__view + @pyqtSlot() def __setupChannelTimeout(self): """
--- a/eric7/WebBrowser/WebBrowserWindow.py Sun Aug 29 19:19:31 2021 +0200 +++ b/eric7/WebBrowser/WebBrowserWindow.py Wed Sep 01 19:54:34 2021 +0200 @@ -29,7 +29,7 @@ QWebEngineSettings, QWebEnginePage, QWebEngineProfile, QWebEngineScript ) try: - from PyQt6.QtHelp import QHelpEngine, QHelpEngineCore + from PyQt6.QtHelp import QHelpEngine QTHELP_AVAILABLE = True except ImportError: QTHELP_AVAILABLE = False @@ -197,6 +197,8 @@ self.__helpEngine = QHelpEngine( WebBrowserWindow.getQtHelpCollectionFileName(), self) + self.__helpEngine.setReadOnly(False) + self.__helpEngine.setupData() self.__helpEngine.setUsesFilterEngine(True) self.__removeOldDocumentation() self.__helpEngine.warning.connect(self.__warning) @@ -271,7 +273,6 @@ self.__indexDock) # setup the search widget - self.__searchWord = searchWord self.__indexing = False self.__indexingProgress = None self.__searchEngine = self.__helpEngine.searchEngine() @@ -437,8 +438,6 @@ state = Preferences.getWebBrowser("WebBrowserState") self.restoreState(state) - self.__initHelpDb() - self.__virusTotal = VirusTotalAPI(self) self.__virusTotal.submitUrlError.connect( self.__virusTotalSubmitUrlError) @@ -478,8 +477,8 @@ if WebBrowserWindow._useQtHelp: QTimer.singleShot(50, self.__lookForNewDocumentation) - if self.__searchWord is not None: - QTimer.singleShot(0, self.__searchForWord) + if searchWord: + QTimer.singleShot(0, lambda: self.__searchForWord(searchWord)) def __del__(self): """ @@ -2311,7 +2310,7 @@ filtertb.addWidget(QLabel(self.tr("Filtered by: "))) filtertb.addWidget(self.filterCombo) self.__helpEngine.setupFinished.connect(self.__setupFilterCombo) - self.filterCombo.currentTextChanged.connect( + self.filterCombo.currentIndexChanged.connect( self.__filterQtHelpDocumentation) self.__setupFilterCombo() self.__toolbars["filter"] = (filtertb.windowTitle(), filtertb) @@ -2352,7 +2351,8 @@ vttb.addAction(self.virustotalIpReportAct) vttb.addAction(self.virustotalDomainReportAct) self.__toolbars["virustotal"] = (vttb.windowTitle(), vttb) - + + @pyqtSlot() def __nextTab(self): """ Private slot used to show the next tab. @@ -2362,7 +2362,8 @@ fwidget = fwidget.parent() if fwidget: fwidget.nextTab() - + + @pyqtSlot() def __prevTab(self): """ Private slot used to show the previous tab. @@ -2372,7 +2373,8 @@ fwidget = fwidget.parent() if fwidget: fwidget.prevTab() - + + @pyqtSlot() def __switchTab(self): """ Private slot used to switch between the current and the previous @@ -2383,19 +2385,22 @@ fwidget = fwidget.parent() if fwidget: fwidget.switchTab() - + + @pyqtSlot() def __whatsThis(self): """ Private slot called in to enter Whats This mode. """ QWhatsThis.enterWhatsThisMode() - + def __titleChanged(self, browser, title): """ Private slot called to handle a change of a browser's title. - @param browser reference to the browser (WebBrowserView) - @param title new title (string) + @param browser reference to the browser + @type WebBrowserView + @param title new title + @type str """ self.historyManager().updateHistoryEntry( browser.url().toString(), title) @@ -2484,6 +2489,7 @@ ).format(applPath), self.tr('OK')) + @pyqtSlot() def __openFile(self): """ Private slot called to open a file. @@ -2503,7 +2509,8 @@ else: url = "file://" + fn self.currentBrowser().setSource(QUrl(url)) - + + @pyqtSlot() def __openFileNewTab(self): """ Private slot called to open a file in a new tab. @@ -2523,7 +2530,8 @@ else: url = "file://" + fn self.newTab(url) - + + @pyqtSlot() def __savePageAs(self): """ Private slot to save the current page. @@ -2541,7 +2549,8 @@ from .PageScreenDialog import PageScreenDialog self.__pageScreen = PageScreenDialog(self.currentBrowser()) self.__pageScreen.show() - + + @pyqtSlot() def __about(self): """ Private slot to show the about information. @@ -2559,43 +2568,50 @@ """ toolset.</p>""" """<p>It is based on QtWebEngine {1} and Chrome {2}.</p>""" ).format(Version, webengineVersion, chromeVersion)) - + + @pyqtSlot() def __aboutQt(self): """ Private slot to show info about Qt. """ EricMessageBox.aboutQt(self, self.tr("eric Web Browser")) - + + @pyqtSlot(bool) def setBackwardAvailable(self, b): """ Public slot called when backward references are available. - @param b flag indicating availability of the backwards action (boolean) + @param b flag indicating availability of the backwards action + @type bool """ self.backAct.setEnabled(b) self.__navigationBar.backButton().setEnabled(b) - + + @pyqtSlot(bool) def setForwardAvailable(self, b): """ Public slot called when forward references are available. @param b flag indicating the availability of the forwards action - (boolean) + @type bool """ self.forwardAct.setEnabled(b) self.__navigationBar.forwardButton().setEnabled(b) - + + @pyqtSlot(bool) def setLoadingActions(self, b): """ Public slot to set the loading dependent actions. - @param b flag indicating the loading state to consider (boolean) + @param b flag indicating the loading state to consider + @type bool """ self.reloadAct.setEnabled(not b) self.stopAct.setEnabled(b) self.__navigationBar.reloadStopButton().setLoading(b) - + + @pyqtSlot() def __addBookmark(self): """ Private slot called to add the displayed file to the bookmarks. @@ -2638,7 +2654,8 @@ idx = self.bookmarksManager().bookmarksModel().nodeIndex(menu) dlg.setCurrentIndex(idx) dlg.exec() - + + @pyqtSlot() def __addBookmarkFolder(self): """ Private slot to add a new bookmarks folder. @@ -2650,7 +2667,8 @@ dlg.setCurrentIndex(idx) dlg.setFolder(True) dlg.exec() - + + @pyqtSlot() def __showBookmarksDialog(self): """ Private slot to show the bookmarks dialog. @@ -2662,7 +2680,8 @@ self.__bookmarksDialog.newBackgroundTab.connect( self.openUrlNewBackgroundTab) self.__bookmarksDialog.show() - + + @pyqtSlot() def bookmarkAll(self): """ Public slot to bookmark all open tabs. @@ -2715,7 +2734,8 @@ bookmark.desc = description self.bookmarksManager().addBookmark(folder, bookmark) - + + @pyqtSlot() def __find(self): """ Private slot to handle the find action. @@ -2872,7 +2892,8 @@ """ Public method to shut down the web browser. - @return flag indicating successful shutdown (boolean) + @return flag indicating successful shutdown + @rtype bool """ if not self.__shallShutDown(): return False @@ -2926,45 +2947,53 @@ self.close() return True - + + @pyqtSlot() def __backward(self): """ Private slot called to handle the backward action. """ self.currentBrowser().backward() + @pyqtSlot() def __forward(self): """ Private slot called to handle the forward action. """ self.currentBrowser().forward() + @pyqtSlot() def __home(self): """ Private slot called to handle the home action. """ self.currentBrowser().home() + @pyqtSlot() def __reload(self): """ Private slot called to handle the reload action. """ self.currentBrowser().reloadBypassingCache() + @pyqtSlot() def __stopLoading(self): """ Private slot called to handle loading of the current page. """ self.currentBrowser().stop() + @pyqtSlot(int) def __zoomValueChanged(self, value): """ Private slot to handle value changes of the zoom widget. - @param value zoom value (integer) + @param value zoom value + @type int """ self.currentBrowser().setZoomValue(value) + @pyqtSlot() def __zoomIn(self): """ Private slot called to handle the zoom in action. @@ -2972,6 +3001,7 @@ self.currentBrowser().zoomIn() self.__zoomWidget.setValue(self.currentBrowser().zoomValue()) + @pyqtSlot() def __zoomOut(self): """ Private slot called to handle the zoom out action. @@ -2979,6 +3009,7 @@ self.currentBrowser().zoomOut() self.__zoomWidget.setValue(self.currentBrowser().zoomValue()) + @pyqtSlot() def __zoomReset(self): """ Private slot called to handle the zoom reset action. @@ -2986,6 +3017,7 @@ self.currentBrowser().zoomReset() self.__zoomWidget.setValue(self.currentBrowser().zoomValue()) + @pyqtSlot() def toggleFullScreen(self): """ Public slot called to toggle the full screen mode. @@ -3020,6 +3052,7 @@ """ return self.isFullScreen() and self.__navigationContainer.isVisible() + @pyqtSlot() def showFullScreenNavigation(self): """ Public slot to show full screen navigation. @@ -3033,6 +3066,7 @@ self.__navigationContainer.show() self.__tabWidget.tabBar().show() + @pyqtSlot() def hideFullScreenNavigation(self): """ Public slot to hide full screen navigation. @@ -3040,6 +3074,7 @@ if not self.__hideNavigationTimer.isActive(): self.__hideNavigationTimer.start() + @pyqtSlot() def __hideNavigation(self): """ Private slot to hide full screen navigation by timer. @@ -3051,42 +3086,49 @@ self.__navigationContainer.hide() self.__tabWidget.tabBar().hide() + @pyqtSlot() def __copy(self): """ Private slot called to handle the copy action. """ self.currentBrowser().copy() + @pyqtSlot() def __cut(self): """ Private slot called to handle the cut action. """ self.currentBrowser().cut() + @pyqtSlot() def __paste(self): """ Private slot called to handle the paste action. """ self.currentBrowser().paste() + @pyqtSlot() def __undo(self): """ Private slot to handle the undo action. """ self.currentBrowser().undo() + @pyqtSlot() def __redo(self): """ Private slot to handle the redo action. """ self.currentBrowser().redo() + @pyqtSlot() def __selectAll(self): """ Private slot to handle the select all action. """ self.currentBrowser().selectAll() + @pyqtSlot() def __unselect(self): """ Private slot to clear the selection of the current browser. @@ -3144,11 +3186,13 @@ """ return self.__tabWidget.browsers() + @pyqtSlot(int) def __currentChanged(self, index): """ Private slot to handle the currentChanged signal. - @param index index of the current tab (integer) + @param index index of the current tab + @type int """ if index > -1: cb = self.currentBrowser() @@ -3160,6 +3204,7 @@ # set value of zoom widget self.__zoomWidget.setValue(cb.zoomValue()) + @pyqtSlot() def __showPreferences(self): """ Private slot to set the preferences. @@ -3186,6 +3231,7 @@ self.preferencesChanged() self.__lastConfigurationPageName = dlg.getConfigurationPageName() + @pyqtSlot() def preferencesChanged(self): """ Public slot to handle a change of preferences. @@ -3259,6 +3305,7 @@ Preferences.convertPasswords(oldPassword, newPassword) Utilities.crypto.changeRememberedMaster(newPassword) + @pyqtSlot() def __showAcceptedLanguages(self): """ Private slot to configure the accepted languages for web pages. @@ -3268,6 +3315,7 @@ dlg.exec() self.networkManager().languagesChanged() + @pyqtSlot() def __showCookiesConfiguration(self): """ Private slot to configure the cookies handling. @@ -3344,13 +3392,15 @@ cls._cookieJar = CookieJar() return cls._cookieJar - + + @pyqtSlot() def __clearIconsDatabase(self): """ Private slot to clear the favicons databse. """ WebIconProvider.instance().clear() + @pyqtSlot() def __showWebIconsDialog(self): """ Private slot to show a dialog to manage the favicons database. @@ -3384,12 +3434,14 @@ cb.setUrl(url) self.__activating = False + @pyqtSlot() def __activateCurrentBrowser(self): """ Private slot to activate the current browser. """ self.currentBrowser().setFocus() + @pyqtSlot() def __syncTOC(self): """ Private slot to synchronize the TOC with the currently shown page. @@ -3400,7 +3452,8 @@ self.__showTocWindow() if not self.__tocWindow.syncToContent(url): self.statusBar().showMessage( - self.tr("Could not find an associated content."), 5000) + self.tr("Could not find any associated content."), + 5000) def __showTocWindow(self): """ @@ -3432,7 +3485,8 @@ widget.parent().show() widget.parent().raise_() widget.setFocus() - + + @pyqtSlot() def __setupFilterCombo(self): """ Private slot to setup the filter combo box. @@ -3441,21 +3495,28 @@ activeFilter = self.filterCombo.currentText() if not activeFilter: activeFilter = self.__helpEngine.filterEngine().activeFilter() + allFilters = self.__helpEngine.filterEngine().filters() self.filterCombo.clear() - self.filterCombo.addItems(sorted( - self.__helpEngine.filterEngine().filters())) + self.filterCombo.addItem(self.tr("Unfiltered")) + if allFilters: + self.filterCombo.insertSeparator(1) + for helpFilter in sorted(allFilters): + self.filterCombo.addItem(helpFilter, helpFilter) self.filterCombo.setCurrentText(activeFilter) - - def __filterQtHelpDocumentation(self, activeFilter): + + @pyqtSlot(int) + def __filterQtHelpDocumentation(self, index): """ Private slot to filter the QtHelp documentation. - @param activeFilter current text of the filter combobox - @type str + @param index index of the selected QtHelp documentation filter + @type int """ if self.__helpEngine: - self.__helpEngine.filterEngine().setActiveFilter(activeFilter) - + helpFilter = self.filterCombo.itemData(index) + self.__helpEngine.filterEngine().setActiveFilter(helpFilter) + + @pyqtSlot() def __manageQtHelpDocumentation(self): """ Private slot to manage the QtHelp documentation database. @@ -3476,6 +3537,7 @@ """ return self.__tabWidget.getSourceFileList() + @pyqtSlot() def __indexingStarted(self): """ Private slot to handle the start of the indexing process. @@ -3502,7 +3564,8 @@ self.statusBar().insertPermanentWidget( 0, self.__indexingProgress) - + + @pyqtSlot() def __indexingFinished(self): """ Private slot to handle the start of the indexing process. @@ -3511,33 +3574,38 @@ self.statusBar().removeWidget(self.__indexingProgress) self.__indexingProgress = None self.__indexing = False - if self.__searchWord is not None: - self.__searchForWord() - - def __searchForWord(self): + + @pyqtSlot(str) + def __searchForWord(self, searchWord): """ Private slot to search for a word. - """ - if ( - WebBrowserWindow._useQtHelp and - not self.__indexing and - self.__searchWord is not None - ): - self.__searchDock.show() - self.__searchDock.raise_() - self.__searchEngine.search(self.__searchWord) - self.__searchWord = None + + @param searchWord word to search for + @type str + """ + if WebBrowserWindow._useQtHelp and searchWord: + if self.__indexing: + # Try again a second later + QTimer.singleShot( + 1000, + lambda: self.__searchForWord(searchWord) + ) + else: + self.__searchDock.show() + self.__searchDock.raise_() + self.__searchEngine.search(searchWord) def search(self, word): """ Public method to search for a word. - @param word word to search for (string) + @param word word to search for + @type str """ if WebBrowserWindow._useQtHelp: - self.__searchWord = word - self.__searchForWord() - + self.__searchForWord(word) + + @pyqtSlot() def __removeOldDocumentation(self): """ Private slot to remove non-existing documentation from the help engine. @@ -3547,7 +3615,8 @@ docFile = self.__helpEngine.documentationFileName(namespace) if not os.path.exists(docFile): self.__helpEngine.unregisterDocumentation(namespace) - + + @pyqtSlot() def __lookForNewDocumentation(self): """ Private slot to look for new documentation to be loaded into the @@ -3564,61 +3633,53 @@ self.statusBar().showMessage( self.tr("Looking for Documentation...")) self.__helpInstaller.installDocs() - + + @pyqtSlot(str) def __showInstallationError(self, message): """ Private slot to show installation errors. - @param message message to be shown (string) + @param message message to be shown + @type str """ EricMessageBox.warning( self, self.tr("eric Web Browser"), message) - + + @pyqtSlot(bool) def __docsInstalled(self, installed): """ Private slot handling the end of documentation installation. @param installed flag indicating that documents were installed - (boolean) + @type bool """ if WebBrowserWindow._useQtHelp: self.statusBar().clearMessage() - - def __initHelpDb(self): - """ - Private slot to initialize the documentation database. - """ - if WebBrowserWindow._useQtHelp: - unfiltered = self.tr("Unfiltered") - if unfiltered not in self.__helpEngine.customFilters(): - hc = QHelpEngineCore(self.__helpEngine.collectionFile()) - hc.addCustomFilter(unfiltered, []) - hc = None - del hc - - self.__helpEngine.blockSignals(True) - self.__helpEngine.setCurrentFilter(unfiltered) - self.__helpEngine.blockSignals(False) - + self.__helpEngine.setupData() + + @pyqtSlot(str) def __warning(self, msg): """ Private slot handling warnings from the help engine. - @param msg message sent by the help engine (string) + @param msg message sent by the help engine + @type str """ EricMessageBox.warning( self, self.tr("Help Engine"), msg) - + + @pyqtSlot() def __aboutToShowSettingsMenu(self): """ Private slot to show the Settings menu. """ self.editMessageFilterAct.setEnabled( EricErrorMessage.messageHandlerInstalled()) - + + @pyqtSlot() def __clearPrivateData(self): """ Private slot to clear the private data. @@ -3661,7 +3722,8 @@ ZoomManager.instance().clear() if sslExceptions: self.networkManager().clearSslExceptions() - + + @pyqtSlot() def __showEnginesConfigurationDialog(self): """ Private slot to show the search engines configuration dialog. @@ -3679,7 +3741,8 @@ @return reference to the search engines configuration action (QAction) """ return self.searchEnginesAct - + + @pyqtSlot() def __showPasswordsDialog(self): """ Private slot to show the passwords management dialog. @@ -3689,36 +3752,42 @@ dlg = PasswordsDialog(self) dlg.exec() + @pyqtSlot() def __showCertificateErrorsDialog(self): """ Private slot to show the certificate errors management dialog. """ self.networkManager().showSslErrorExceptionsDialog() + @pyqtSlot() def __showAdBlockDialog(self): """ Private slot to show the AdBlock configuration dialog. """ self.adBlockManager().showDialog() - + + @pyqtSlot() def __showPersonalInformationDialog(self): """ Private slot to show the Personal Information configuration dialog. """ self.personalInformationManager().showConfigurationDialog() - + + @pyqtSlot() def __showGreaseMonkeyConfigDialog(self): """ Private slot to show the GreaseMonkey scripts configuration dialog. """ self.greaseMonkeyManager().showConfigurationDialog() - + + @pyqtSlot() def __showFeaturePermissionDialog(self): """ Private slot to show the feature permission dialog. """ self.featurePermissionManager().showFeaturePermissionsDialog() - + + @pyqtSlot() def __showZoomValuesDialog(self): """ Private slot to show the zoom values management dialog. @@ -3728,12 +3797,14 @@ dlg = ZoomValuesDialog(self) dlg.exec() + @pyqtSlot() def __showDownloadsWindow(self): """ Private slot to show the downloads dialog. """ self.downloadManager().show() - + + @pyqtSlot() def __showPageSource(self): """ Private slot to show the source of the current page in an editor. @@ -3753,6 +3824,7 @@ editor.setLanguage("dummy.html") editor.show() + @pyqtSlot() def __toggleJavaScriptConsole(self): """ Private slot to toggle the JavaScript console. @@ -3794,51 +3866,72 @@ return cls._bookmarksManager + @pyqtSlot(QUrl) + @pyqtSlot(QUrl, str) def openUrl(self, url, title=None): """ Public slot to load a URL in the current tab. - @param url URL to be opened (QUrl) - @param title title of the bookmark (string) + @param url URL to be opened + @type QUrl + @param title title of the bookmark + @type str """ self.__linkActivated(url) + @pyqtSlot(QUrl) + @pyqtSlot(QUrl, str) def openUrlNewTab(self, url, title=None): """ Public slot to load a URL in a new tab. - @param url URL to be opened (QUrl) - @param title title of the bookmark (string) + @param url URL to be opened + @type QUrl + @param title title of the bookmark + @type str """ self.newTab(url) + @pyqtSlot(QUrl) + @pyqtSlot(QUrl, str) def openUrlNewBackgroundTab(self, url, title=None): """ Public slot to load a URL in a new background tab. - @param url URL to be opened (QUrl) - @param title title of the bookmark (string) + @param url URL to be opened + @type QUrl + @param title title of the bookmark + @type str """ self.newTab(url, background=True) + @pyqtSlot(QUrl) + @pyqtSlot(QUrl, str) def openUrlNewWindow(self, url, title=None): """ Public slot to load a URL in a new window. - @param url URL to be opened (QUrl) - @param title title of the bookmark (string) + @param url URL to be opened + @type QUrl + @param title title of the bookmark + @type str """ self.newWindow(url) + @pyqtSlot(QUrl) + @pyqtSlot(QUrl, str) def openUrlNewPrivateWindow(self, url, title=None): """ Public slot to load a URL in a new private window. - @param url URL to be opened (QUrl) - @param title title of the bookmark (string) + @param url URL to be opened + @type QUrl + @param title title of the bookmark + @type str """ self.newPrivateWindow(url) + @pyqtSlot() def __sendPageLink(self): """ Private slot to send the link of the current page via email. @@ -4106,6 +4199,7 @@ parentMenu.addMenu(menu) + @pyqtSlot() def __aboutToShowTextEncodingMenu(self): """ Private slot to populate the text encoding menu. @@ -4156,12 +4250,14 @@ self.__createTextEncodingSubmenu(self.tr("Other"), otherCodecs, self.__textEncodingMenu) + @pyqtSlot(QAction) def __setTextEncoding(self, act): """ Private slot to set the selected text encoding as the default for this session. - @param act reference to the selected action (QAction) + @param act reference to the selected action + @type QAction """ codec = act.data() if codec == "": @@ -4220,7 +4316,8 @@ self.__populateToolbarsMenu(menu) return menu - + + @pyqtSlot() def __showToolbarsMenu(self): """ Private slot to display the Toolbars menu. @@ -4366,6 +4463,7 @@ return cls._feedsManager + @pyqtSlot() def __showFeedsManager(self): """ Private slot to show the feeds manager dialog. @@ -4377,7 +4475,7 @@ feedsManager.newWindow.connect(self.openUrlNewWindow) feedsManager.newPrivateWindow.connect(self.openUrlNewPrivateWindow) feedsManager.rejected.connect( - lambda fm: self.__feedsManagerClosed(fm)) + lambda: self.__feedsManagerClosed(feedsManager)) feedsManager.show() def __feedsManagerClosed(self, feedsManager): @@ -4394,6 +4492,7 @@ feedsManager.newPrivateWindow.disconnect(self.openUrlNewPrivateWindow) feedsManager.rejected.disconnect() + @pyqtSlot() def __showSiteinfoDialog(self): """ Private slot to show the site info dialog. @@ -4415,6 +4514,7 @@ return cls._userAgentsManager + @pyqtSlot() def __showUserAgentsDialog(self): """ Private slot to show the user agents management dialog. @@ -4437,6 +4537,7 @@ return cls._syncManager + @pyqtSlot() def __showSyncDialog(self): """ Private slot to show the synchronization dialog. @@ -4554,6 +4655,7 @@ ## Interface to VirusTotal below ## ########################################################################### + @pyqtSlot() def __virusTotalScanCurrentSite(self): """ Private slot to ask VirusTotal for a scan of the URL of the current @@ -4573,11 +4675,13 @@ """ self.__virusTotal.submitUrl(url) + @pyqtSlot(str) def __virusTotalSubmitUrlError(self, msg): """ Private slot to handle an URL scan submission error. - @param msg error message (str) + @param msg error message + @type str """ EricMessageBox.critical( self, @@ -4585,22 +4689,27 @@ self.tr("""<p>The VirusTotal scan could not be""" """ scheduled.<p>\n<p>Reason: {0}</p>""").format(msg)) + @pyqtSlot(str) def __virusTotalUrlScanReport(self, url): """ Private slot to initiate the display of the URL scan report page. - @param url URL of the URL scan report page (string) + @param url URL of the URL scan report page + @type str """ self.newTab(url) + @pyqtSlot(str) def __virusTotalFileScanReport(self, url): """ Private slot to initiate the display of the file scan report page. - @param url URL of the file scan report page (string) + @param url URL of the file scan report page + @type str """ self.newTab(url) + @pyqtSlot() def __virusTotalIpAddressReport(self): """ Private slot to retrieve an IP address report. @@ -4620,6 +4729,7 @@ self.tr("""The given IP address is not in dotted quad""" """ notation.""")) + @pyqtSlot() def __virusTotalDomainReport(self): """ Private slot to retrieve a domain report. @@ -4854,6 +4964,7 @@ return cls._sessionManager + @pyqtSlot() def __showSessionManagerDialog(self): """ Private slot to show the session manager dialog. @@ -4878,6 +4989,7 @@ return cls._safeBrowsingManager + @pyqtSlot() def __showSafeBrowsingDialog(self): """ Private slot to show the safe browsing management dialog. @@ -4902,6 +5014,7 @@ return cls._protocolHandlerManager + @pyqtSlot() def __showProtocolHandlerManagerDialog(self): """ Private slot to show the protocol handler manager dialog. @@ -4951,8 +5064,7 @@ @type str """ if WebBrowserWindow._useQtHelp: - self.__searchWord = word - self.__searchForWord() + self.__searchForWord(word) self.raise_() self.activateWindow() @@ -4961,6 +5073,7 @@ ## Methods below implement shortcuts related functions ###################################################### + @pyqtSlot() def __configShortcuts(self): """ Private slot to configure the keyboard shortcuts. @@ -4971,6 +5084,7 @@ self.__shortcutsDialog.populate(helpViewer=self) self.__shortcutsDialog.show() + @pyqtSlot() def __exportShortcuts(self): """ Private slot to export the keyboard shortcuts. @@ -5005,7 +5119,8 @@ if ok: from Preferences import Shortcuts Shortcuts.exportShortcuts(fn, helpViewer=self) - + + @pyqtSlot() def __importShortcuts(self): """ Private slot to import the keyboard shortcuts.
--- a/scripts/install.py Sun Aug 29 19:19:31 2021 +0200 +++ b/scripts/install.py Wed Sep 01 19:54:34 2021 +0200 @@ -500,17 +500,12 @@ # Remove the wrapper scripts rem_wnames = [ - "eric7_api", "eric7_compare", - "eric7_configure", "eric7_diff", - "eric7_doc", "eric7_qregularexpression", - "eric7_qregexp", "eric7_re", - "eric7_trpreviewer", "eric7_uipreviewer", - "eric7_unittest", "eric7", - "eric7_tray", "eric7_editor", - "eric7_plugininstall", "eric7_pluginuninstall", - "eric7_pluginrepository", "eric7_sqlbrowser", - "eric7_iconeditor", "eric7_snap", "eric7_hexeditor", - "eric7_browser", "eric7_shell", + "eric7_api", "eric7_browser", "eric7_compare", "eric7_configure", + "eric7_diff", "eric7_doc", "eric7_editor", "eric7_hexeditor", + "eric7_iconeditor", "eric7_plugininstall", "eric7_pluginrepository", + "eric7_pluginuninstall", "eric7_qregularexpression", "eric7_re", + "eric7_shell", "eric7_snap", "eric7_sqlbrowser", "eric7_tray", + "eric7_trpreviewer", "eric7_uipreviewer", "eric7_unittest", "eric7" ] try: @@ -703,14 +698,14 @@ wnames = [] for name in ["eric7_api", "eric7_doc"]: wnames.append(createPyWrapper(cfg['ericDir'], name, scriptsDir, False)) - # TODO: add "eric7_browser" once PyQt 6.2.0/Qt 6.2.0 is released - for name in ["eric7_compare", "eric7_configure", "eric7_diff", - "eric7_editor", "eric7_hexeditor", "eric7_iconeditor", - "eric7_plugininstall", "eric7_pluginrepository", - "eric7_pluginuninstall", "eric7_qregularexpression", - "eric7_re", "eric7_snap", "eric7_sqlbrowser", "eric7_tray", - "eric7_trpreviewer", "eric7_uipreviewer", "eric7_unittest", - "eric7_shell", "eric7"]: + for name in ["eric7_browser", "eric7_compare", "eric7_configure", + "eric7_diff", "eric7_editor", "eric7_hexeditor", + "eric7_iconeditor", "eric7_plugininstall", + "eric7_pluginrepository", "eric7_pluginuninstall", + "eric7_qregularexpression", "eric7_re", "eric7_snap", + "eric7_sqlbrowser", "eric7_tray", "eric7_trpreviewer", + "eric7_uipreviewer", "eric7_unittest", "eric7_shell", + "eric7"]: wnames.append(createPyWrapper(cfg['ericDir'], name, scriptsDir)) # set install prefix, if not None @@ -793,12 +788,10 @@ os.path.join(eric7SourceDir, "UI", "data"), os.path.join(cfg['ericDir'], "UI", "data"), ['*.css']) - # TODO: enable this once PyQt 6.2.0/Qt 6.2.0 is released - if False: - copyTree( - os.path.join(eric7SourceDir, "WebBrowser"), - os.path.join(cfg['ericDir'], "WebBrowser"), - ['*.xbel', '*.xml', '*.html', '*.png', '*.gif', '*.js']) + copyTree( + os.path.join(eric7SourceDir, "WebBrowser"), + os.path.join(cfg['ericDir'], "WebBrowser"), + ['*.xbel', '*.xml', '*.html', '*.png', '*.gif', '*.js']) # copy the wrappers for wname in wnames: @@ -1500,11 +1493,11 @@ exit(1) print("Found {0}".format(pyuic)) - # TODO: enable this once PyQt 6.2.0/Qt 6.2.0 is released - if False: - try: - from PyQt6 import QtWebEngineWidgets # __IGNORE_WARNING__ - except ImportError as msg: + try: + from PyQt6 import QtWebEngineWidgets # __IGNORE_WARNING__ + except ImportError as msg: + # TODO: enable this once PyQt 6.2.0/Qt 6.2.0 is released + if False: if isSudo: print("Optional 'PyQt6-WebEngine' could not be detected.") else: