python - 如何使用 HTML 按钮关闭应用程序
问题描述
在我的 PyQt5 浏览器窗口中,我加载了 HTML 和 JavaScript。我在 HTML 中包含了一个按钮,它应该使用 vanilla JavaScript 关闭 Python 应用程序。这是我的 Python 代码,它制作窗口并加载 HTML 文件:
import sys
import os
from PyQt5.QtCore import *
from PyQt5.QtWidgets import *
from PyQt5.QtWebEngineWidgets import *
class MainWindow(QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
self.browser = QWebEngineView()
config_name = 'data_files/init.html'
if getattr(sys, 'frozen', False):
application_path = os.path.dirname(sys.executable)
elif __file__:
application_path = os.path.dirname(__file__)
config_path = os.path.join(application_path, config_name)
self.browser.load(QUrl().fromLocalFile(config_path))
self.setCentralWidget(self.browser)
self.showMaximized()
app = QApplication(sys.argv)
QApplication.setApplicationName('v0.1')
window = MainWindow()
app.exec_()
在我的 HTML 中,我有这个:
<button onclick="exitApplication()">Exit</button>
<script>
function exitApplication() {
// How can I tell Python to call self.close() ??
}
</script>
正如我所说,我想使用 HTML 中的按钮关闭应用程序。我查看了各种来源,但我永远找不到任何可以帮助我或太令人困惑的东西。
调用 -Function 时如何关闭应用程序exitApplication()
?
解决方案
首先要知道,关闭窗口和退出应用程序是不一样的,如果你只有一个窗口,并且属性quitOnLastWindowClosed为True,那么它们是等价的,但总的来说是不一样的。
QtWeb 频道:
import sys
import os
from PyQt5.QtCore import pyqtSignal, pyqtSlot, QCoreApplication, QObject, QUrl
from PyQt5.QtWidgets import QApplication, QMainWindow
from PyQt5.QtWebEngineWidgets import QWebEngineView
from PyQt5.QtWebChannel import QWebChannel
application_path = (
os.path.dirname(sys.executable)
if getattr(sys, "frozen", False)
else os.path.dirname(__file__)
)
class Bridge(QObject):
request_closed = pyqtSignal()
@pyqtSlot()
def quit(self):
QCoreApplication.quit()
@pyqtSlot()
def close(self):
self.request_closed.emit()
class MainWindow(QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
self.browser = QWebEngineView()
self.bridge = Bridge()
self.bridge.request_closed.connect(self.close)
self.channel = QWebChannel()
self.channel.registerObject("bridge", self.bridge)
self.browser.page().setWebChannel(self.channel)
config_name = "data_files/init.html"
config_path = os.path.join(application_path, config_name)
self.browser.load(QUrl.fromLocalFile(config_path))
self.setCentralWidget(self.browser)
self.showMaximized()
if __name__ == "__main__":
app = QApplication(sys.argv)
QApplication.setApplicationName("v0.1")
window = MainWindow()
app.exec_()
<!DOCTYPE html>
<html>
<head>
<script src="qrc:///qtwebchannel/qwebchannel.js"></script>
</head>
<body>
<button onclick="exitApplication()">Exit</button>
<script>
var bridge = null;
function exitApplication() {
bridge.quit();
// bridge.close();
}
if (typeof QWebChannel !== "undefined") {
new QWebChannel(qt.webChannelTransport, function (channel) {
bridge = channel.objects.bridge;
});
}
</script>
</body>
</html>
QWebEngineUrlSchemeHandler:
import sys
import os
from PyQt5.QtCore import QCoreApplication, QUrl
from PyQt5.QtWidgets import QApplication, QMainWindow
from PyQt5.QtWebEngineCore import (
QWebEngineUrlScheme,
QWebEngineUrlSchemeHandler,
QWebEngineUrlRequestJob,
)
from PyQt5.QtWebEngineWidgets import QWebEngineView
application_path = (
os.path.dirname(sys.executable)
if getattr(sys, "frozen", False)
else os.path.dirname(__file__)
)
class QtSchemeHandler(QWebEngineUrlSchemeHandler):
def requestStarted(self, job):
if job.requestMethod() == b"POST" and job.requestUrl() == QUrl(
"qt://commands/quit"
):
QCoreApplication.quit()
return
job.fail(QWebEngineUrlRequestJob.RequestFailed)
class MainWindow(QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
self.browser = QWebEngineView()
self.scheme_handler = QtSchemeHandler()
self.browser.page().profile().installUrlSchemeHandler(
b"qt", self.scheme_handler
)
config_name = "data_files/init.html"
config_path = os.path.join(application_path, config_name)
self.browser.load(QUrl.fromLocalFile(config_path))
self.setCentralWidget(self.browser)
self.showMaximized()
if __name__ == "__main__":
scheme = QWebEngineUrlScheme(b"qt")
scheme.setFlags(QWebEngineUrlScheme.CorsEnabled)
QWebEngineUrlScheme.registerScheme(scheme)
app = QApplication(sys.argv)
QApplication.setApplicationName("v0.1")
window = MainWindow()
app.exec_()
<!DOCTYPE html>
<html>
<body>
<button onclick="exitApplication()">Exit</button>
<script>
function exitApplication() {
const xhr = new XMLHttpRequest();
xhr.open("POST", "qt://commands/quit", true);
xhr.send();
}
</script>
</body>
</html>
推荐阅读
- amazon-web-services - 为什么我在 aws 上的 spring-cloud-config 服务器间歇性地没有响应?
- swiftui - SwiftUI - 追加到空数组
- python - django 应用程序的数据库设计
- javascript - 为什么不是“使用严格”默认值?
- python - Spectrum1D 无法将 u.dimensionless_unscaled 数量识别为 Quantity
- vba - 无法建立与服务器的连接 (WinHTTPRequest5.1) 在 VBA 中调用
- javascript - 使用 RegEx javascript 在字符串中查找单词
- c++ - 在一条指令中声明更多指针的运算符优先级
- css - 在 React 应用程序中的页面加载时运行的关键帧动画
- c++ - Qt WiFi网络扫描