PySide2和支持addToJavaScriptWindowObject

时间:2018-06-24 15:17:30

标签: python python-3.x pyside2 qwebengineview qtwebchannel

我试图将PySide应用程序版本1移植到PySide2,并努力找到移植以下代码段的解决方案:

private func setupNavBarWithUser() {
    let titleView = UIView()
    let width = titleView.sizeThatFits(CGSize(width: CGFloat.greatestFiniteMagnitude, height: CGFloat.greatestFiniteMagnitude)).width
    titleView.frame = CGRect(origin:CGPoint.zero, size:CGSize(width: width, height: 500))

    let profileImageView = UIImageView()
    profileImageView.translatesAutoresizingMaskIntoConstraints = false
    profileImageView.contentMode = .scaleAspectFill
    profileImageView.layer.cornerRadius = 20
    profileImageView.clipsToBounds = true
    ImageService.getImage(withURL: NSURL(string: (user?.pictureURL)!)! as URL) { (image) in
        profileImageView.image = image
    }
    titleView.addSubview(profileImageView)
    profileImageView.leftAnchor.constraint(equalTo: titleView.leftAnchor).isActive = true
    profileImageView.centerYAnchor.constraint(equalTo: titleView.centerYAnchor).isActive = true
    profileImageView.widthAnchor.constraint(equalToConstant: 40).isActive = true
    profileImageView.heightAnchor.constraint(equalToConstant: 40).isActive = true

    let nameLabel = UILabel()
    titleView.addSubview(nameLabel)
    nameLabel.text = user?.first_name
    nameLabel.textColor = .white
    nameLabel.translatesAutoresizingMaskIntoConstraints = false
    nameLabel.leftAnchor.constraint(equalTo: profileImageView.rightAnchor, constant: 8).isActive = true
    nameLabel.centerYAnchor.constraint(equalTo: profileImageView.centerYAnchor).isActive = true
    nameLabel.rightAnchor.constraint(equalTo: titleView.rightAnchor).isActive = true
    nameLabel.heightAnchor.constraint(equalTo: profileImageView.heightAnchor).isActive = true

    titleView.centerXAnchor.constraint(equalTo: titleView.centerXAnchor).isActive = true
    titleView.centerYAnchor.constraint(equalTo: titleView.centerYAnchor).isActive = true

    self.navigationItem.titleView = titleView
    let recognizer = UITapGestureRecognizer(target: self, action: #selector(self.testing))
    titleView.isUserInteractionEnabled = true
    titleView.addGestureRecognizer(recognizer)
}

@objc func testing() {
    print("hello")
}

我在文档中找不到必须解决的问题

1 个答案:

答案 0 :(得分:3)

您必须使用QWebChannel,为此您必须下载qwebchannel.js(针对Qt 5.12 的链接指向 qwebchannel.js ,对于不同的版本,请更改github分支)。

在下面的代码中,我显示了一个示例:

.
├── index.html
├── main.py
└── qwebchannel.js

main.py

import sys

from PySide2 import QtCore, QtGui, QtWidgets, QtWebEngineWidgets, QtWebChannel


class WebEnginePage(QtWebEngineWidgets.QWebEnginePage):
    pass

class AppManager(QtCore.QObject):
    textChanged = QtCore.Signal(str)
    def __init__(self, webview):
        QtCore.QObject.__init__(self)
        self.m_text = ""

        timer = QtCore.QTimer(self)
        timer.timeout.connect(self.on_timeout)
        timer.start(1000)

    def on_timeout(self):
        self.text  = QtCore.QDateTime.currentDateTime().toString()

    @QtCore.Property(str, notify=textChanged)
    def text(self):
        return self.m_text

    @text.setter
    def setText(self, text):
        if self.m_text == text:
            return
        self.m_text = text
        self.textChanged.emit(self.m_text)


class WebView(QtWebEngineWidgets.QWebEngineView):
    def __init__(self, parent=None):
        QtWebEngineWidgets.QWebEngineView.__init__(self, parent)
        self.setPage(WebEnginePage(self))

    def contextMenuEvent(self, event):
        pass


class AppWindow(QtWidgets.QMainWindow):
    def __init__(self):
        QtWidgets.QMainWindow.__init__(self)
        self.view = WebView(self)
        self.page = self.view.page()
        self.app_manager = AppManager(self.view)
        channel = QtWebChannel.QWebChannel(self)
        self.page.setWebChannel(channel)
        channel.registerObject("app_manager", self.app_manager)
        self.view.load(QtCore.QUrl.fromLocalFile(QtCore.QDir.current().filePath("index.html")))
        self.setCentralWidget(self.view)

if __name__ == '__main__':
    app = QtWidgets.QApplication(sys.argv)
    w = AppWindow()
    w.show()
    sys.exit(app.exec_())

index.html

<html>
<head>
    <script type="text/javascript" src="./qwebchannel.js"></script>
</head>
<header><title>This is title</title></header>
<body>

<p id="output"></p>

<script type="text/javascript">
    window.onload = function() {
        new QWebChannel(qt.webChannelTransport, function (channel) {
            window.app_manager = channel.objects.app_manager;
            console.log(app_manager);

            app_manager.textChanged.connect(function(message) {
                document.getElementById("output").innerHTML = "Received message: " + message;
            });

        });
    }
</script> 
</body>
</html>