2011-09-23 89 views
3

我想寫一個程序,將與QGraphicsView交互。我想在QGraphicsView中收集鼠標和鍵盤事件。例如,如果用戶點擊QGraphicsView小部件,我將得到鼠標位置,類似的東西。我可以很容易地對它進行硬編碼,但我想使用QtDesigner,因爲UI將會頻繁更改。pyQt信號/插槽與QtDesigner

這是我對gui.py的代碼。一個簡單的小部件,裏面有一個QGraphicsView。

from PyQt4 import QtCore, QtGui 

try: 
    _fromUtf8 = QtCore.QString.fromUtf8 
except AttributeError: 
    _fromUtf8 = lambda s: s 

class Ui_graphicsViewWidget(object): 
    def setupUi(self, graphicsViewWidget): 
     graphicsViewWidget.setObjectName(_fromUtf8("graphicsViewWidget")) 
     graphicsViewWidget.resize(400, 300) 
     graphicsViewWidget.setMouseTracking(True) 
     self.graphicsView = QtGui.QGraphicsView(graphicsViewWidget) 
     self.graphicsView.setGeometry(QtCore.QRect(70, 40, 256, 192)) 
     self.graphicsView.setObjectName(_fromUtf8("graphicsView")) 

     self.retranslateUi(graphicsViewWidget) 
     QtCore.QMetaObject.connectSlotsByName(graphicsViewWidget) 

    def retranslateUi(self, graphicsViewWidget): 
     graphicsViewWidget.setWindowTitle(QtGui.QApplication.translate("graphicsViewWidget", "Form", None, QtGui.QApplication.UnicodeUTF8)) 

爲程序代碼:

#!/usr/bin/python -d 

import sys 
from PyQt4 import QtCore, QtGui 
from gui import Ui_graphicsViewWidget 

class MyForm(QtGui.QMainWindow): 

    def __init__(self, parent=None): 
     QtGui.QWidget.__init__(self, parent) 
     self.ui = Ui_graphicsViewWidget() 
     self.ui.setupUi(self) 
     QtCore.QObject.connect(self.ui.graphicsView, QtCore.SIGNAL("moved"), self.test) 

    def mouseMoveEvent(self, event): 
     print "Mouse Pointer is currently hovering at: ", event.pos() 
     self.emit(QtCore.SIGNAL("moved"), event) 

    def test(self, event): 
     print('in test') 

if __name__ == "__main__": 
    app = QtGui.QApplication(sys.argv) 
    myapp = MyForm() 
    myapp.show() 
    sys.exit(app.exec_()) 

當我運行這段代碼,它給我的,我想的正好相反。除了QGraphicsView以外,我在任何地方都能看到鼠標位置。

我確定這是我的QObject.connect問題。但每次我回頭閱讀有關信號和插槽的信息時,它都是有道理的,但我無法得到它。

請大家幫忙,我過去幾天一直在b my我的腦袋。我很抱歉,如果這是以前問過,但我已經通過了這個話題的所有主題,我不能得到任何地方。

由於

+0

在你的gui.py文件中,'self.graphicsView = MyForm(graphicsViewWidget)'這一行會拋出一個異常,因爲'MyForm'沒有被定義。我不確定你在那裏的意思。你能修好那條線嗎? –

+0

對不起,MyForm應該是QtGui.QGraphicsView。我將它固定在線程中,然後在我的計算機上運行,​​現在應該可以正常工作。 – Jeff

+0

正如一個建議,如果你使用'從PyQt4.QtGui import *'和'從PyQt4.QtCore import *'導入,你可以刪除'QtCore.'和'QtGui.'的所有實例,使代碼更具可讀性。 – Blender

回答

3

信號必須來自在UI中定義的QGraphicsView對象。

您可以從QGraphicsView得出這樣

from PyQt4.QtCore import * 
from PyQt4.QtGui import * 

class MyView(QGraphicsView): 
    moved = pyqtSignal(QMouseEvent) 

    def __init__(self, parent = None): 
     super(MyView, self).__init__(parent) 

    def mouseMoveEvent(self, event): 
     # call the base method to be sure the events are forwarded to the scene 
     super(MyView, self).mouseMoveEvent(event) 

     print "Mouse Pointer is currently hovering at: ", event.pos() 
     self.moved.emit(event) 

然後一類,在設計師:

  • 右鍵單擊QGraphicsView然後提升到
  • 寫的類名稱推薦類名稱字段(例如「MyView」),
  • 寫的文件名如該班是在頭文件場,但沒有的.py擴展,
  • 點擊添加按鈕,然後在促進按鈕。

而且你可以用pyuic4重新生成你的文件gui.py

+0

正是我所期待的,謝謝你的一步一步。 – Jeff

+0

非常好的解釋,謝謝:) 我只是有一個小問題,是否可以讓QtDesigner知道您在文件中創建了哪些插槽/信號(或其他方式)。要定義它們兩次似乎沒有意義。 – Wolph

+0

@WoLpH我想你可以創建一個插件([像那樣](http://diotavelli.net/PyQtWiki/Using_Python_Custom_Widgets_in_Qt_Designer),但是如果你只在一個項目中使用這個類,看起來很複雜 – alexisdm