QtQMetaObjects和从QWidget到QObject的转换
Qt QMetaObjects and casting from QWidget to QObject
我正在尝试编写代码,读取xml文件并从该xml中反序列化各种qt控件,我使用QDomDocument来完成这项工作,我想从我的取消实现方法中获得QLlist。我遇到了一些麻烦,下面是模板类(.h)文件的一些代码:
QList<T*> deserialize(QIODevice *input)
{
QList<T*> objects = QList<T*>();
if(_deserializeObject(input, objects))
return objects;
}
bool _deserializeObjects(QIODevice* input, QList<QObject*>& list);
和我的.cpp文件的反序列化方法,在这里我从文件中读取控制标记:
bool Serializer::_deserializeObjects(QIODevice* input, QList<QObject *> &objects)
{
QDomDocument doc;
if (!doc.setContent(input))
return false;
QDomElement root= doc.documentElement();
for(int j = 0; j < root.childNodes().length();j++)
{
QObject* object;
qDebug() << root.tagName();
if(root.tagName().contains("QGroupBox")) // <------- Here i need to determine which control i need to process.
{
????
}
qDebug () << object->metaObject()->className();
qDebug() << object->metaObject()->propertyCount();
for(int i = 0; i < object->metaObject()->propertyCount(); i++)
{
object->metaObject()->cast()
QMetaProperty prop = object->metaObject()->property(i);
QString propName = prop.name();
if(propName == "objectName")
continue;
QDomNodeList nodeList = root.elementsByTagName(propName);
if(nodeList.length() < 1)
continue;
QDomNode node = nodeList.at(0);
QVariant value = object->property(propName.toLatin1().data());
QString v = node.toElement().text();
if(propName == "x")
{
x = v.toInt();
}
else if(propName == "y")
{
y = v.toInt();
}
else if(propName == "width")
{
width = v.toInt();
}
else if(propName == "height")
{
height = v.toInt();
}
if(propName == "geometry")
{
continue;
}
object->setProperty(propName.toLatin1().data(), QVariant(v));
}
object->setProperty("geometry",QVariant(QRect(x,y,width,height)));
objects.push_back(object);
}
return true;
}
在本部分中,
if(root.tagName().contains("QGroupBox")) // <------- Here i need to determine which control i need to process.
{
????
}
qDebug () << object->metaObject()->className();
qDebug() << object->metaObject()->propertyCount();
for(int i = 0; i < object->metaObject()->propertyCount(); i++)
{
...
}
我想以某种方式通过名称获得控件的类型,所以问题是,我可以将QGroupBox强制转换为保存QGroupBox属性的QObject吗?这样QObject metaObject类名就会是QGroupBox,这样我就可以传递所有这些属性了?因为我不想为每种控件类型创建循环。还有我当我得到这样的结果时:
QList<QObject *> ds = s.deserialize<Object>((QIODevice*)&f);
然后,我可以在一个循环中传递所有的qobject,并使用QMetaObject类名和qobject_cast将每个对象强制转换为QPushButton、QLabel等吗。?
QGroupBox是QObject的一个子类;因此,每个QGroupBox也是一个QObject,所以您可以随时将其视为一个QOobject。不需要显式的演员阵容。
在循环中对从QObject派生的所有不同对象进行迭代将执行您想要的操作,前提是您对它们调用的方法是虚拟方法(它们可能是——特别是QObject::metaObject()是一个虚拟方法,因此即使您的循环通过QObject指针调用它们的方法,也会返回相应的QMetaObject)。
(顺便说一句,这个过程中令人讨厌的部分可能是你从XML中读取了对象类型的名称,现在需要实例化该类型的对象的部分。AFAIK在C++中没有很好的自动方法来实现这一点,所以你能做的最好的事情是一个工厂函数,它包含一个巨大的switch语句,对于你可能想要实例化的每种类型都有一个单独的大小写)
或者,为正确的作业使用正确的工具。很可能您在这里构建的是一些用于定义小部件布局等的XML内容。Qt已经有了一个工具,即Qt设计器,它使用XML格式来定义UI,并使用C++代码生成器在编译时实际生成C++代码。
- 防止主数据类型C++的隐式转换
- 模板参数替换失败,并且未完成隐式转换
- 努力将整数转换为链表。不知道我在这里做错了什么
- HEX值到wchar_t字符(UTF-8)的转换
- lambda参数转换为constexpr技巧,然后获取带链接的数组
- 将 Qvector<uint8_t> 转换为 QString
- 如何在cuSparse中使用cusparseXcoo2csr从coo转换为csc
- 有关插入适配器的错误。[错误]请求从 'back_insert_iterator<vector<>>' 类型转换为非标量类型
- 在c++中使用nlohmann从类到json的转换
- 无法将参数 3 从 'const QGraphicsItem *' 转换为 'const QObject *',这是指针,对象是 QGraphicsObject 的子类
- QObject基类到继承对象的C++类型转换
- 将nativeObject转换为QObject qt5 c++
- QtQMetaObjects和从QWidget到QObject的转换
- 如何将递归QMetaObject::newInstance(..)从QObject*转换为QGenericArgumen
- 防止将 QObject* 隐式转换为布尔值:防止'Multiple constructor'警告
- Qt,无法将不完整类型'A *'的参数转换为'const QObject *'
- 如何将 QList<QObject *> 转换为 QList<ADerivedQObjectClass*>
- QObject*和void*之间的转换
- C2665:'QObject::connect':3 个重载都无法转换所有参数类型
- 将const QObject*转换为QObject*