2016-10-06 3 views
0

Ich arbeitete mit OpenCV GUI-Funktionen für eine Weile, und die Möglichkeiten sind ein wenig einschränkend für Python-Benutzer. Heute habe ich mit Pyqt angefangen und komme zu folgendem Ergebnis: qt ist wirklich verwirrend.Behandlung von Mausereignissen opencv gui vs pyqt

Nun ist die Frage über Mausereignisse:

In OpenCV ich folgendes gerade tun:

import cv2 
cv2.namedWindow('Window',1) 
def CallBackFunc(event,x,y,flags,param): 
    global xc,yc,evt,flg 
    xc,yc,evt,flg=x,y,event,flags 

cv2.setMouseCallback('Window', CallBackFunc) 

Dies eröffnet einen separaten Thread, der die globalen Variablen ständig aktualisiert xc,yc,evt,flg, und ich kann sie überall zugreifen Ich will jederzeit. Wenn ich die erfrischenden stoppen will, kann ich nur ein cv2.setMouseCallback('Window',nothing), wobei nothing ist

def nothing(): 
    pass 

Es ist nicht die schönste Art und Weise des Umgangs mit Maus-Ereignissen sein kann, aber ich bin mit ihm in Ordnung. Wie kann ich mit PyQt eine solche Freiheit erreichen?

EDIT:

Zum Beispiel das folgende Skript einen weißen Kreis angezeigt wird, und ständig einen Text hinein zu ziehen.

import sys 
from PySide import QtGui 
import numpy as np 
import cv2 

class QCustomLabel (QtGui.QLabel): 


    def __init__ (self, parent = None): 
     super(QCustomLabel, self).__init__(parent) 
     self.setMouseTracking(True) 


    def mouseMoveEvent (self, eventQMouseEvent): 
     self.x,self.y=eventQMouseEvent.x(),eventQMouseEvent.y() 
     cvImg=np.zeros((900,900),dtype=np.uint8) 
     cv2.circle(cvImg,(449,449),100,255,-1) 
     cv2.putText(cvImg,"x at {}, y at {}".format(self.x,self.y),(375,455), cv2.FONT_HERSHEY_SIMPLEX,0.5,(0,0,0),1,cv2.LINE_AA) 
     height, width= cvImg.shape 
     bytearr=cvImg.data 
     qImg = QtGui.QImage(bytearr, width, height, QtGui.QImage.Format_Indexed8) 
     self.setPixmap(QtGui.QPixmap.fromImage(qImg)) 

    def mousePressEvent (self, eventQMouseEvent): 
     self.evt=eventQMouseEvent.button() 


class QCustomWidget (QtGui.QWidget): 
    def __init__ (self, parent = None): 
     super(QCustomWidget, self).__init__(parent) 
     self.setWindowOpacity(1) 
     # Init QLabel 
     self.positionQLabel = QCustomLabel(self) 
     # Init QLayout 
     layoutQHBoxLayout = QtGui.QHBoxLayout() 
     layoutQHBoxLayout.addWidget(self.positionQLabel) 

     self.setLayout(layoutQHBoxLayout) 
     self.show() 


if QtGui.QApplication.instance() is not None: 
    myQApplication=QtGui.QApplication.instance() 
else: 
    myQApplication = QtGui.QApplication(sys.argv) 


myQTestWidget = QCustomWidget() 
myQTestWidget.show() 
myQApplication.exec_() 

Das Problem hierbei ist, dass dies alles in der QCustomLabel Klasse, und innerhalb der Funktion mousemove ausgeführt wird. Aber ich möchte eine separate Funktion, lassen Sie es anrufen drawCircle, außerhalb der Klasse, die Zugriff auf die Mausposition und Ereignisse hat. Mit opencv wäre das überhaupt kein Problem. Und es würde nur einen Bruchteil des Schreibaufwands erfordern, der für eine pyqt-Implementierung benötigt wird.

Ich denke, die richtige Frage ist: Warum mag ich Pygyt noch nicht?

+0

Sie pyside verwenden, nicht PyQt. Wie auch immer, es ist immer ein Fehler zu versuchen, eine Sprache/Bibliothek/ein Framework so zu zwingen, sich genau wie ein anderes zu verhalten. – ekhumoro

Antwort

0

Sie können ein Ereignis-Filter verwenden, um zu vermeiden, die QLabel Unterklasse:

class QCustomWidget (QtGui.QWidget): 
    def __init__ (self, parent = None): 
     super(QCustomWidget, self).__init__(parent) 
     self.setWindowOpacity(1) 
     # Init QLabel 
     self.positionQLabel = QtGui.QLabel(self) 
     self.positionQLabel.setMouseTracking(True) 
     self.positionQLabel.installEventFilter(self) 
     # Init QLayout 
     layoutQHBoxLayout = QtGui.QHBoxLayout() 
     layoutQHBoxLayout.addWidget(self.positionQLabel)  
     self.setLayout(layoutQHBoxLayout) 
     self.show() 

    def eventFilter(self, source, event): 
     if event.type() == QtCore.QEvent.MouseMove: 
      self.drawCircle(event.x(), event.y()) 
     return super(QCustomWidget, self).eventFilter(source, event) 

    def drawCircle(self, x, y): 
     # whatever 
+0

vielen Dank. Soweit ich weiß, Opencvs GUI-Funktionen bauen auf qt. Daher erschien es mir naheliegend, eine ähnliche Implementierung in beiden Frameworks abzuleiten. –

+0

@AntonAlice. Ich bin mir sicher, dass es viele Überschneidungen gibt, aber offensichtlich werden einige Dinge anders funktionieren. Ich denke, Sie werden feststellen, dass qt Ihnen viel Flexibilität bietet, aber manchmal kommt dies auf Kosten einer ausführlichen Implementierung. – ekhumoro

+0

haben Sie vergessen, ein Q vor dem QtGui._Label (self) –