Qt/QML 无法使 getOwnPropertyDescriptor 正常工作



我在使用Qt 5.7.0和QML时遇到了麻烦。我需要在运行时发现某些对象的属性。

目标是使用在其他地方找到的纯 QML 树视图。这是使用硬编码属性构建的,以保存要显示的值。这是一个非常简单的树视图,这正是我所需要的。使用控件 2.0,我没有"股票"树视图。

我的目标是更改纯 QML TreeView,为他提供对象树和专有名称,而不是硬编码的名称。

我不想使用完整的Qt模型来拥有轻量级组件。

离开该目标,有时可能不得不动态请求属性值,只知道它在运行时的名称。例如,在C#和Java中,使用反射来做到这一点很容易。

来自C#世界,我正在寻找相同的概念。在我的用例中,对象不会是纯QML对象,而是qmlRegisterType公开C++对象。

我计划使用Object.getOwnPropertyDescriptor,但经过数小时的测试,我无法让它按我想要的方式工作......

这是纯 QML/JS 中的 POC

import QtQuick 2.0
Item {
id: myTest
property int myProp : 1234

function test() {
console.log("_________________TEST_________________");
console.log(Object.getOwnPropertyNames(myTest))
console.log(myTest.hasOwnProperty("myProp"))
console.log(Object.getOwnPropertyDescriptor(myTest, "myProp"));
console.log("_________________TEST_________________");
}
}

在日志中,我得到:

qml: _________________TEST_________________
qml: [objectName,parent,data,resources,children,x,y,z,width,height,opacity,enabled,visible,visibleChildren,states,transitions,state,childrenRect,anchors,left,right,horizontalCenter,top,bottom,verticalCenter,baseline,baselineOffset,clip,focus,activeFocus,activeFocusOnTab,rotation,scale,transformOrigin,transformOriginPoint,transform,smooth,antialiasing,implicitWidth,implicitHeight,layer,myProp,objectNameChanged,childrenRectChanged,baselineOffsetChanged,stateChanged,focusChanged,activeFocusChanged,activeFocusOnTabChanged,parentChanged,transformOriginChanged,smoothChanged,antialiasingChanged,clipChanged,windowChanged,childrenChanged,opacityChanged,enabledChanged,visibleChanged,visibleChildrenChanged,rotationChanged,scaleChanged,xChanged,yChanged,widthChanged,heightChanged,zChanged,implicitWidthChanged,implicitHeightChanged,update,grabToImage,grabToImage,contains,mapToGlobal,mapFromGlobal,mapFromItem,mapToItem,forceActiveFocus,forceActiveFocus,nextItemInFocusChain,nextItemInFocusChain,childAt,myPropChanged,test]
qml: true
qml: undefined
qml: _________________TEST_________________

根据"qml:true"行,"hasOwnProperty('myProp')"找到属性并说"true"。

但是下一行试图获取属性描述符返回"未定义"。

能解决我问题的人就是我的英雄!

感觉像个菜鸟...我发现我可以使用myobj[propertyName]语法按名称查询属性。

太容易被人看到...

如果要获取属性描述符,则需要先设置它。

Item {
id: myTest
property int myProp : 1234
function test() {
console.log("_________________TEST_________________");
console.log(Object.getOwnPropertyNames(myTest))
console.log(myTest.hasOwnProperty("myProp"))
console.log(Object.getOwnPropertyDescriptor(myTest, "myProp"));
console.log(Object.getOwnPropertyDescriptor(myTest, "myProp").value)
console.log(myProp)
console.log("_________________TEST_________________");
}
Component.onCompleted: {
Object.defineProperty(myTest, 'myProp',
{
enumerable: false,
configurable: false,
writable: false,
value: '50'
})
test()
}
}

但恕我直言,这完全没用。因此,也许扩展您的最终目标会很好,因为您的这个问题很可能是那些臭名昭著的XY问题之一

最新更新