Slot with extra argument



  • I am looking to a solution for such a behaviour:

    • the boolean signal s1 connects to the slot test with an argument, e.g. widget1
    • the boolean signal s2 connects to the same slot test with another argument, e.g. widget2
    @Slot(bool, QWidget)
    def test(flag, wg):
       # the state of the flag is retrieved from the signal
       wg.apply_flag(flag)
    

    After looking into the Qt and PySide documentations and forums I still have not found anything working...
    Has anyone have a solution?

    Best regards



  • @gf-gepi you do not need to do that just do the following

    @Slot(QObject)
    

    Then in your code define what that object is made of such perhaps QObject might be {bool:QWidget} using a dictionary or perhaps [bool, QWidget] using a list then your set your code to handle whatever that Object was defined as. Always best to just K.I.S.S. it (Keep It Simple and Smart)



  • @denni-0
    I'm sorry, but I don't understand your explanation; especially how the emitted boolean is retrieved?
    One of my points being to address a 'standard' widget (i.e. not a subclass) stored in a '.ui' file, and using only its methods. A better example would be:

    s1 = Signal(bool)
    s2 = Signal(bool)
    ...
    s1.connect(test(w1))  # the destination widget is set only at the connection definition
    s2.connect(test(w2))
    ...
    s1.emit(True)  # no need to add the destination widget every time the signal is used
    s2.emit(False)
    ...
    @Slot(bool, QWidget)
    # this definition of the Slot is not right according the Signal definition
    def test(flag, wg):
       # the state of the flag is retrieved from the signal
       if flag:
           wg.setTooltip('OK')
       else:
           wg.setToolTip('Not OK')
    


  • Defined in Calling Class

    sigOne = Signal(object)
    

    You cannot pass a parameter in a Connect call in my experience
    Defined in the destination Class

    self.CallingClass.sigOne.connect(self.TestFunc)
    
    @Slot(Object)
    def test(self, objSent)
      # The object does not to be predefined as its just a generic object but you 
      # should know what you are passing around in this case we will use a List
      # where [bool, widget] is what is in the list
        self.boolValue   = objSent[0]
        self.widgetValue = objSent[1]
    

    That should basically handle this and any other variation that you want to implement. Remember the object can be a List, Dictionary, or even more complicated object unless your passing across Thread boundaries in this cases you should probably stick to Alphanumerics or Lists, Dictionaries of said data types (aka basically picklable objects). As somewhere it states you cannot pass objects through Thread boundaries and while that is not exactly true because you can I am guessing they state that because doing so can cause issues but they do not bother to explain this anomaly in functionality within the documentation. Still considering that their documentation on one should subclass a QThread is absolutely wrong I am not surprised that this is not explained.



  • @denni-0
    I think I have found the way to factorize my code, using lamdba to give an extra argument.

    s1 = Signal(bool)
    s2 = Signal(bool)
    ...
    s1.connect(lambda flag: test(flag, w1))
    s2.connect(lambda flag: test(flag, w2))
    ...
    def test(flag, wg):
       if flag:
           wg.setTooltip('OK')
       else:
           wg.setToolTip('Not OK')
    

    Note that it works:

    • with or without the @Slot(bool) decorator
    • with an user-defined signal s_user = Signal(bool) or a built-in signal such as stateChanged

    As stated here, this may be generalized with:

    obj.signal.connect(lambda p1, ... , arg1=val1, ... : fun(p1, ... , arg1, ... ))
    ...
    def fun(p1, ... , arg1, ... ):
        [...]
    

 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.