Is it possible to disconnect all of a QObject's connections without deleting it

前端 未结 1 1895
孤城傲影
孤城傲影 2021-02-12 03:50

I have a QObject A, this is connected to another QObject B. Now I want A to connect to C, a third QObject and to completely disconnect from B.

Easy peasy! Trouble is I h

相关标签:
1条回答
  • 2021-02-12 04:24

    There are at least 2 ways. First, disconnect everything.

    disconnect(obj,0,0,0);
    //or
    obj->disconnect();
    

    Second. Every connect() returns QMetaObject::Connection which can be copied or moved, so you can save some connections in the list and after some time, just iterate through the list and call disconnect() for every object. Example with one connection:

    QMetaObject::Connection m_connection;
    //…
    m_connection = QObject::connect(…);
    //…
    QObject::disconnect(m_connection);
    

    Bonus: no, Qt doesn't support such deep introspection, you can't get list of all connected slots or something else, but in most cases you don't need this at all. One useful function that Qt gives you is sender(), which is a pointer to the object that sent the signal.

    Edit

    As the docs said:

    Disconnect everything connected to an object's signals

    So in the next example both windows will be shown:

    QWidget *a = new QWidget;
    QWidget *b = new QWidget;
    
    a->setWindowTitle("A");
    b->setWindowTitle("B");
    
    QObject::connect(a,SIGNAL(objectNameChanged(QString)), b, SLOT(show()));
    QObject::connect(b,SIGNAL(objectNameChanged(QString)), a, SLOT(show()));
    
    //a->disconnect();
    
    a->setObjectName("A");
    b->setObjectName("B");
    

    But uncomment a->disconnect(); and only A windows will be shown. It means that QObject::connect(b,SIGNAL(objectNameChanged(QString)),a,SLOT(show())); was not disconnected as stated in the doc. If you want to solve this puzzle you can do a->disconnect(b); b->disconnect(a);, but it is of course a very bad approach. So you can use second suggestion from my answer:

    QList<QMetaObject::Connection> connections;
    
    QWidget *a = new QWidget;
    QWidget *b = new QWidget;
    
    a->setWindowTitle("A");
    b->setWindowTitle("B");
    
    connections << QObject::connect(a,SIGNAL(objectNameChanged(QString)), b, SLOT(show()));
    connections << QObject::connect(b,SIGNAL(objectNameChanged(QString)), a, SLOT(show()));
    
    foreach (auto var, connections) {
        QObject::disconnect(var);
    }
    
    a->setObjectName("A");
    b->setObjectName("B");
    
    0 讨论(0)
提交回复
热议问题