Получить свойство измененного уведомителя из метаобъекта

Я хочу написать соединитель свойств для соединения свойств в C ++ Qt в манере QML. Это может быть так:

new PropConnector ( receiver, "propName", sender, "propName" );

Класс propConnector — это небольшой класс QObject, который использует отправителя в качестве родителя, прослушивает сигнал об изменении свойства и устанавливает соответствующее свойство получателя. Как это:

class PropConnector : public QObject
{
Q_OBJECT
private:
QObject *_sender;
QObject *_receiver;
QString _senderProp;
QString _receiverProp;
public:
PropConnector(QObject *sender, QObject *receiver, QString senderProp, QString receiverProp) :
QObject(sender)
,_sender(sender)
,_receiver(receiver)
,_senderProp(senderProp)
,_receiverProp(receiverProp)
{
// Is it possible to get the proper property-changed notifier signal?
//connect(sender, SIGNAL( on<PROPERTY>Changed() ), this, SLOT( forward ) );
}

private slots:
void forward()
{
_receiver->setProperty( receiverProp, _sender->property( senderProp ) );
}
};

Единственная проблема в том, как мне найти правильное имя сигнала для имени свойства, которое я хочу прослушать? Я думаю, это возможно, но я до сих пор не узнал, прочитав документацию по мета-объектам.

Редактировать: С предложением Кевина я смог реализовать класс.

propconnector.h

#ifndef PROPCONNECTOR_H
#define PROPCONNECTOR_H

#include <QObject>
#include <QString>

class PropConnector : public QObject
{
Q_OBJECT
private:
QObject *_sender;
QObject *_receiver;
QString _senderProperty;
QString _receiverProperty;
public:
PropConnector(QObject *sender, QString senderProperty, QObject *receiver, QString receiverProperty);

private slots:
void forward();
};

#endif // PROPCONNECTOR_H

propconnector.cpp

#include "propconnector.h"#include <QMetaObject>
#include <QMetaProperty>

PropConnector::PropConnector(QObject *sender, QString senderProperty, QObject *receiver, QString receiverProperty) :
QObject(sender)
,_sender(sender)
,_receiver(receiver)
,_senderProperty(senderProperty)
,_receiverProperty(receiverProperty)
{
const QMetaObject *senderMeta = sender->metaObject();
const int index = senderMeta->indexOfProperty(senderProperty.toUtf8().constData());
if (index != -1) {
const QMetaProperty p = senderMeta->property(index);
if ( p.hasNotifySignal() ) {
const QMetaMethod s = p.notifySignal();

QString sig = QString("2%1").arg(s.signature());
const char *ssig = SLOT(forward());
bool ok = connect(sender, sig.toStdString().c_str() , this, SLOT(forward()));
int i=0;
i++;
}
}
}

void PropConnector::forward()
{
_receiver->setProperty( _receiverProperty.toStdString().c_str(), _sender->property( _senderProperty.toStdString().c_str() ) );
}

0

Решение

Вы можете получить эту информацию из QMetaProperty

QMetaObject *senderMeta = sender->metaObject();
const int index = senderMeta->indexOfProperty(senderProperty.toUtf8().constData());
if (index != -1) {
const QMetaProperty property = senderMeta->property(index);
if (property.hasNotifySignal) {
const QMetaMethod notifySignal = property.notifySignal();

connect(sender, notifySignal, receiver, metaMethodOfSlot);
}
}

Не проверено, может не скомпилироваться. metaMethodOfSlot будет QMetaMethod для слота приемника, получить это аналогичным образом.

2

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]