如何在 QList 中将 QMap 注册为 QtScript 中的元类型?
How to register a QMap inside of a QList as a Meta Type in QtScript?
我正在考虑将 QList<QMap<QString, QString>>
对象从我的 Qt 代码传递到 JavaScript 文件,并想知道如何正确处理代码的 qScriptRegisterMetaType 部分。
目前我正在考虑让我的脚本值转换方法使用 QList 注册方法和 QMap 注册方法的一部分。
可以找到我引用的代码here for QList and here for QMap。
具体来说,在将 QList<QMap<QString, QString>>
转换为 QScriptValue 时,我想使用此代码段来处理 QMap 部分:
QScriptValue obj = engine->newObject();
StringMap::const_iterator it(map.begin());
for (; it != map.end(); ++it)
{
obj.setProperty(it.key(), qScriptValueFromValue(engine,it.value()));
}
return obj;
然后我想使用它 运行 QMap 转换,同时为 QList 设置每个 属性 和 return 结果 QScriptValue。
QScriptValue ScriptListtoScriptValue(QScriptEngine* engine, const ListMap& list)
{
QScriptValue obj = engine->newArray(list.size());
for ( int i = 0; i < list.size(); i++ ) {
obj.setProperty(i, engine->newQObject(list[i]));
}
return obj;
}
我能否在 QList 转换中调用 运行s QMap 转换的函数并以这种方式设置 属性?我想知道我是否遗漏了什么,或者 Qt 是否对此不满意并且没有将数据正确传递给 JavaScript.
至于我这样做的原因:我希望将一个结构发送到 JavaScript 以便 QMap 将为多个列名和值保存一个 key/value 对个人记录。然后 QList 将是这些记录的列表。如果我的方法有缺陷并且有更好的方法将此类信息从 Qt 发送到 JavaScript,我将不胜感激建设性的批评。
我想出了一个解决方案,适用于任何想在未来尝试的人。我按照我建议的方式结合了这两种方法。
在头文件中,我创建了一个 QList< QMap<QString, QString> >
的 ScriptList class 并且必须在尖括号之间包含 space 否则它将被解释为 >>
.此外,我创建了一个处理 QMap<QString, QString>
.
的 StringMap class
class StringMap : public QMap<QString, QString> {};
class ScriptList : public QList< QMap<QString, QString> > {};
QScriptValue ScriptListToScriptValue(QScriptEngine* engine, const ScriptList& list);
void ScriptListFromScriptValue(const QScriptValue &obj, ScriptList& list);
QScriptValue MapToScriptValue(QScriptEngine* engine, const QMap<QString, QString>& map);
void MapFromScriptValue(const QScriptValue &obj, QMap<QString, QString>& map);
然后我做了所有必要的声明和注册:
Q_DECLARE_METATYPE(ScriptList)
Q_DECLARE_METATYPE(StringMap)
qRegisterMetaType<ScriptList>("QList< QMap<QString,QString> >");
qScriptRegisterMetaType(m_engine, ScriptListToScriptValue, ScriptListFromScriptValue);
这些行彼此位于代码的不同部分。
然后是在QList中制作QMap所需要的函数
QScriptValue ScriptListToScriptValue(QScriptEngine* engine, const ScriptList& list)
{
QScriptValue obj = engine->newArray(list.size());
for ( int i = 0; i < list.size(); i++ ) {
obj.setProperty(i, MapToScriptValue(engine, list[i]));
}
return obj;
}
void ScriptListFromScriptValue(const QScriptValue &obj, ScriptList& list)
{
list.clear();
QScriptValueIterator itr(obj);
while ( itr.hasNext() ) {
itr.next();
if ( itr.flags() & QScriptValue::SkipInEnumeration)
continue;
QMap<QString, QString> map;
MapFromScriptValue(itr.value(), map);
list.append(map);
}
}
QScriptValue MapToScriptValue(QScriptEngine *engine, const QMap<QString, QString>& map)
{
QScriptValue obj = engine->newObject();
StringMap::const_iterator it(map.begin());
for (; it != map.end(); ++it)
{
obj.setProperty(it.key(), qScriptValueFromValue(engine,it.value()));
}
return obj;
}
void MapFromScriptValue(const QScriptValue &obj, QMap<QString, QString>& map)
{
QScriptValueIterator itr(obj);
while(itr.hasNext())
{
itr.next();
map.operator [](itr.name().toUtf8()) = qscriptvalue_cast<ScriptMap::mapped_type>(itr.value());
}
}
希望这对处于类似情况的任何人有所帮助。
我正在考虑将 QList<QMap<QString, QString>>
对象从我的 Qt 代码传递到 JavaScript 文件,并想知道如何正确处理代码的 qScriptRegisterMetaType 部分。
目前我正在考虑让我的脚本值转换方法使用 QList 注册方法和 QMap 注册方法的一部分。
可以找到我引用的代码here for QList and here for QMap。
具体来说,在将 QList<QMap<QString, QString>>
转换为 QScriptValue 时,我想使用此代码段来处理 QMap 部分:
QScriptValue obj = engine->newObject();
StringMap::const_iterator it(map.begin());
for (; it != map.end(); ++it)
{
obj.setProperty(it.key(), qScriptValueFromValue(engine,it.value()));
}
return obj;
然后我想使用它 运行 QMap 转换,同时为 QList 设置每个 属性 和 return 结果 QScriptValue。
QScriptValue ScriptListtoScriptValue(QScriptEngine* engine, const ListMap& list)
{
QScriptValue obj = engine->newArray(list.size());
for ( int i = 0; i < list.size(); i++ ) {
obj.setProperty(i, engine->newQObject(list[i]));
}
return obj;
}
我能否在 QList 转换中调用 运行s QMap 转换的函数并以这种方式设置 属性?我想知道我是否遗漏了什么,或者 Qt 是否对此不满意并且没有将数据正确传递给 JavaScript.
至于我这样做的原因:我希望将一个结构发送到 JavaScript 以便 QMap 将为多个列名和值保存一个 key/value 对个人记录。然后 QList 将是这些记录的列表。如果我的方法有缺陷并且有更好的方法将此类信息从 Qt 发送到 JavaScript,我将不胜感激建设性的批评。
我想出了一个解决方案,适用于任何想在未来尝试的人。我按照我建议的方式结合了这两种方法。
在头文件中,我创建了一个 QList< QMap<QString, QString> >
的 ScriptList class 并且必须在尖括号之间包含 space 否则它将被解释为 >>
.此外,我创建了一个处理 QMap<QString, QString>
.
class StringMap : public QMap<QString, QString> {};
class ScriptList : public QList< QMap<QString, QString> > {};
QScriptValue ScriptListToScriptValue(QScriptEngine* engine, const ScriptList& list);
void ScriptListFromScriptValue(const QScriptValue &obj, ScriptList& list);
QScriptValue MapToScriptValue(QScriptEngine* engine, const QMap<QString, QString>& map);
void MapFromScriptValue(const QScriptValue &obj, QMap<QString, QString>& map);
然后我做了所有必要的声明和注册:
Q_DECLARE_METATYPE(ScriptList)
Q_DECLARE_METATYPE(StringMap)
qRegisterMetaType<ScriptList>("QList< QMap<QString,QString> >");
qScriptRegisterMetaType(m_engine, ScriptListToScriptValue, ScriptListFromScriptValue);
这些行彼此位于代码的不同部分。
然后是在QList中制作QMap所需要的函数
QScriptValue ScriptListToScriptValue(QScriptEngine* engine, const ScriptList& list)
{
QScriptValue obj = engine->newArray(list.size());
for ( int i = 0; i < list.size(); i++ ) {
obj.setProperty(i, MapToScriptValue(engine, list[i]));
}
return obj;
}
void ScriptListFromScriptValue(const QScriptValue &obj, ScriptList& list)
{
list.clear();
QScriptValueIterator itr(obj);
while ( itr.hasNext() ) {
itr.next();
if ( itr.flags() & QScriptValue::SkipInEnumeration)
continue;
QMap<QString, QString> map;
MapFromScriptValue(itr.value(), map);
list.append(map);
}
}
QScriptValue MapToScriptValue(QScriptEngine *engine, const QMap<QString, QString>& map)
{
QScriptValue obj = engine->newObject();
StringMap::const_iterator it(map.begin());
for (; it != map.end(); ++it)
{
obj.setProperty(it.key(), qScriptValueFromValue(engine,it.value()));
}
return obj;
}
void MapFromScriptValue(const QScriptValue &obj, QMap<QString, QString>& map)
{
QScriptValueIterator itr(obj);
while(itr.hasNext())
{
itr.next();
map.operator [](itr.name().toUtf8()) = qscriptvalue_cast<ScriptMap::mapped_type>(itr.value());
}
}
希望这对处于类似情况的任何人有所帮助。