[PyQt] simpler 'connect' function

Aaron Digulla digulla at hepe.com
Tue Jan 15 19:25:40 GMT 2008


Peter Shinners schrieb:
> Aaron Digulla:
>> Sorry, I can't follow you here. 1) signal and slot already
>> take string arguments. This discussion is to get rid of them.
> 
> I get "TypeError: argument 2 of QObject.connect() has an invalid type"
> when I try to pass a string to connect. Is this a change coming for 4.4?
> 
>     QObject.connect(other, "clicked()", self.onOtherClicked)
>     # Would be better

No, you still have to wrap the string in a call to QtCore.SIGNAL() but
that's still a "string" to me: No type checking, no way to know if your
signal is really connected to anything and whether it will fire or not.

That's why I'm against string literals in an API. If that API doesn't
even offer any checks to string literals, that's even worse.

>> 2) connect is already a method of QObject. Since you have to
>> connect two objects, you must always pass the second one as a
>> parameter to the first.connect() call.
>> Currently, my favorite is:
>>      self.connect(other.CLICKED, ....)
> 
> It is currently similar to a "static" method of QObject. I'd prefer and
> instance method on all QObjects. The problem I have with the above
> syntax is that seem to work well when connecting to functions. More
> generally useful would be.
> 
>     other.connect("clicked()", self.onOtherClicked)
>     # Would be best
> 
> Hopefully either of these can be added in addition to the current.
> 
>     QObject.connect(other, SIGNAL("clicked()"), self.onOtherClicked)
>     # Connect in 4.3

The actual call is

   QObject.connect(other, SIGNAL("clicked()"), self, self.onOtherClicked)

i.e. it connects "other, SIGNAL("clicked()")" to  "self,
self.onOtherClicked" (because the fourth parameter could be a method of
a third Python object).

As I said before, I'd like an API which avoid the code duplication and
the error prone string literals. In my own code, I predefine all signals
I want to use. In Python, this is actually pretty simple. Just put this
code in an __init__.py file of your module:


--------------- __init__.py -----------------------------------
from PyQt4.QtCore import SIGNAL, QAbstractTableModel,
QAbstractItemModel, QModelIndex
from PyQt4.QtGui import QTextEdit, QLineEdit, QItemSelectionModel,
QPushButton, \
        QAction

# Define constants for many signals
QAbstractItemModel.DATA_CHANGED_SIGNAL =
SIGNAL('dataChanged(QModelIndex,QModelIndex)')
QAbstractItemModel.COLUMNS_ABOUT_TO_BE_INSERTED_SIGNAL =
SIGNAL('columnsAboutToBeInserted(QModelIndex,int,int)')
QAbstractItemModel.COLUMNS_INSERTED_SIGNAL =
SIGNAL('columnsInserted(QModelIndex,int,int)')
QAbstractItemModel.COLUMNS_ABOUT_TO_BE_REMOVED_SIGNAL =
SIGNAL('columnsAboutToBeRemoved(QModelIndex,int,int)')
QAbstractItemModel.COLUMNS_REMOVED_SIGNAL =
SIGNAL('columnsRemoved(QModelIndex,int,int)')
QAbstractItemModel.ROWS_ABOUT_TO_BE_INSERTED_SIGNAL =
SIGNAL('rowsAboutToBeInserted(QModelIndex,int,int)')
QAbstractItemModel.ROWS_INSERTED_SIGNAL =
SIGNAL('rowsInserted(QModelIndex,int,int)')
QAbstractItemModel.ROWS_ABOUT_TO_BE_REMOVED_SIGNAL =
SIGNAL('rowsAboutToBeRemoved(QModelIndex,int,int)')
QAbstractItemModel.ROWS_REMOVED_SIGNAL =
SIGNAL('rowsRemoved(QModelIndex,int,int)')

QAbstractTableModel.DATA_CHANGED_SIGNAL =
SIGNAL('dataChanged(QModelIndex,QModelIndex)')

QAction.TRIGGERED = SIGNAL("triggered()")

QItemSelectionModel.SELECTION_CHANGED =
SIGNAL('selectionChanged(QItemSelection,QItemSelection)')

QLineEdit.TEXT_EDITED = SIGNAL('textEdited(QString)')

QModelIndex.__str__ = lambda self: '<QModelIndex valid=%s row=%d
column=%d>' % (self.isValid(), self.row(), self.column())

QPushButton.CLICKED = SIGNAL('clicked()')
--------------- __init__.py -----------------------------------


Now, you can do this anywhere:

        self.connect(closeButton, QPushButton.CLICKED, self.accept)

(because the init file is loaded *once* when your module is accessed
from *anywhere* for the *first* time).

Regards,

-- 
Aaron "Optimizer" Digulla a.k.a. Philmann Dark
"It's not the universe that's limited, it's our imagination.
Follow me and I'll show you something beyond the limits."
http://darkviews.blogspot.com/          http://www.pdark.de/


More information about the PyQt mailing list