athspk
athspk

Reputation: 6762

Pass arguments to a slot using QTimer

I have written a pyQt client-server application. (python:3.2.2 , pyQT:4.8.6)
The sender sends a message to the listening receivers, and the receivers send a response to the sender. I dont want the response to be sent instantly, but after a small delay.

This is part of the receiver code:

----------------------------- msghandler.py-----------------------------------
class MsgHandler(QObject):
    def __init__(self):
        QObject.__init__(self)
        self.mSec1Timer = None

    def setParentUI(self, p):
        self.parentUI = p

    def handle_ask(self, ID, stamp, length, cargo, peerSocket):
        print("Incoming:ASK")
        #self.mSec1Timer.timeout.connect(lambda:self.send_msg_reply(peerSocket))
        self.mSec1Timer.timeout.connect(self.dummyFunc) #Works
        self.mSec1Timer.timeout.connect(lambda:self.dummyFunc())#See Rem-1
        self.mSec1Timer.timeout.connect(lambda:self.shouldGiveError())#See Rem-2
        self.parentUI.timerStart.emit(5)

    @pyqtSlot(tuple)
    def send_msg_reply(self, peerSocket):
        print("This is not printed")
        self.mSec1Timer.timeout.disconnect()

    @pyqtSlot()
    def dummyFunc(self):
        print("dummy @ ",QDateTime.currentMSecsSinceEpoch())
        self.mSec1Timer.timeout.disconnect()
------------------------------------------------------------------------------

from msghandler import *
class DialogUIAgent(QDialog):

    timerStart = pyqtSignal(int)

    def __init__(self):
        QDialog.__init__(self)

        self.myHandler = MsgHandler()
        self.myHandler.setParentUI(self)

        self.myTimer = QTimer()
        self.myTimer.setSingleShot(True)
        self.myHandler.mSec1Timer = self.myTimer

        self.timerStart.connect(self.startMyTimer)

    @pyqtSlot(int)
    def startMyTimer(self, msec):
        self.myTimer.start(msec)

For testing the behaviour first, i used self.mSec1Timer.timeout.connect(self.dummyFunc), and the output was as expected:

Incoming:ASK
dummy @  1322491256315
Incoming:ASK
dummy @  1322491260310
Incoming:ASK
dummy @  1322491265319
Incoming:ASK
dummy @  1322491270323
Incoming:ASK
dummy @  1322491275331

But when i used self.mSec1Timer.timeout.connect(lambda:self.send_msg_reply(peerSocket)), the slot was never called. Output:

Incoming:ASK
Incoming:ASK
Incoming:ASK
Incoming:ASK

Why is this happening, and what can i do to fix it?
Thanks in advance.



EDIT :
Remark-1:
dummyFunc worked before, but it does not work with lambda:self.dummyFunc()

Remark-2:
I was expecting an Error with lambda:self.shouldGiveError(), because there is no such function, but instead i get nothing.

Is this a problem of the way that i use lambda?

Upvotes: 3

Views: 2257

Answers (1)

Trenton Schulz
Trenton Schulz

Reputation: 778

Have you taken a look at QObject.invokeMethod()?

It has been supported since PyQt 4.4 and it should allow you to call a slot with arguments when you don't have a signal that match.

Upvotes: 0

Related Questions