QQuickItem::mapToItem 返回类型是啥?

Posted

技术标签:

【中文标题】QQuickItem::mapToItem 返回类型是啥?【英文标题】:What is the QQuickItem::mapToItem return type?QQuickItem::mapToItem 返回类型是什么? 【发布时间】:2014-01-08 16:24:40 【问题描述】:

下面的应用程序输出从一个QQuickItem 映射到另一个的坐标。根据文档:

object mapToItem(Item item, real x, real y) 将位于此项的坐标系中的点 (x, y) 或 rect (x, y, width, height) 映射到项的坐标系,并返回一个 x 和 y(以及可选的宽度和高度)属性匹配的对象映射坐标。

我希望输出是这样的:

0 0 1 1 2 2

但我明白了:

QPointF(9, 6)   100  
QPointF(9, 5)   100  
QPointF(8, 5)   100  

为什么mapped.x 的类型是QPointF?我希望它是一个浮点值。什么是实际的 mapped 类型?

import QtQuick 2.1
import QtQuick.Controls 1.0
import QtQuick.Window 2.0
import QtQuick.Layouts 1.0

ApplicationWindow 
    width: 640
    height: 480

    Rectangle 
        anchors.fill: parent
        id: r0
        color: "green"
        Rectangle 
            x: 50; y:100; width: 100; height: 100;
            id: r
            color: "yellow"
            MouseArea 
                id: mousearea
                anchors.fill: parent
                hoverEnabled: true
                onPositionChanged: 
                    var mouseP = Qt.point(mouse.x, mouse.y);
                    var mapped = r.mapToItem(r0, mouseP);
                    console.log(mapped.x, ' ', mapped.y);
                
            
        
    

UPDATE1: QQuickItem 有 mapToItem 有 2 个参数,Item 有 mapToItem 有 3 个参数。上面的代码调用了哪一个?

【问题讨论】:

我查看了QQuickItem::mapToItem(QQmlV4Function *args),但我无法弄清楚为什么mapped.x 的类型是QPointF 有趣的问题,看我的更新。 【参考方案1】:

在您的情况下,mapToItem 需要 3 个参数。您无需先创建点。

onPositionChanged: 
    var mapped = r.mapToItem(r0, mouse.x, mouse.y);
    console.log(mapped.x, ' ', mapped.y);

背景说明:这似乎是一个错误,我只是reported。

您的代码调用 QQuickItem::mapToItem() 有两个原因。首先,QQuickItem::mapToItem(const QQuickItem *item, const QPointF &point) const; 不是 INVOKABLE,即它没有从 C++ 暴露给 QML。其次,QQuickItem::mapToItem(const QQuickItem *item, const QPointF &point) const; 直接返回一个QPointF,其内部属性称为xpyp,而不是xy(这可以使用调试器观察到)。

QQuickItem::mapToItem() 中,xy 被 C++ 强制为 qreal 类型,这是 C++ double 的别名。就连if (v = (*args)[1])->asDouble() 都吓坏了,x 一定是

普通双精度值 NaN +∞ -∞ -0 +0。

在您的情况下,它应该是NaNy = 0 因为没有设置参数 3。因此创建了一个点(NaN, 0)。从那时起,其余的计算就没有任何意义了,只是缺少错误处理。

从 Qt 5.2 开始使用了一个新的 javascript 引擎。在 5.1 及之前版本中,使用了 V8,它向 QML 返回 NaN 而不是 QPointF

【讨论】:

嗯,现在很清楚了。最后一个——mapped.x怎么变成QPointF 我不知道。但据我所知,处理 Javascript 值的 C++ 函数并不是精确的科学。这可能与动态类型的 Javascript 有关。 据我了解,mapToItem 使用 QQmlV4Function * 作为参数和结果。当我们传递不正确的第二个参数时,可能会在(v = (*args)[1])->asDouble() 上失败。在该引擎之后,将 arg x 视为名为 x 的结果字段。好像是这样的。感谢您的回复:) ...这就是为什么mapped.xQPointFmapped.x 只是第二个参数。 xy 被 C++ 强制为 qreal 类型,这是 C++ double 的别名。即使(v = (*args)[1])->asDouble() 完全崩溃了,x 也必须是一个普通的 double 值,NaN+∞−∞-0+0。在您的情况下,它应该是NaNy = 0。创建了一个点(NaN, 0)。从那时起,其余的计算没有任何意义,但缺少错误处理。从 Qt 5.2 开始使用了一个新的 Javascript 引擎。在 5.1 及之前版本中,使用了 V8,它向 QML 返回 NaN 而不是 QPointF

以上是关于QQuickItem::mapToItem 返回类型是啥?的主要内容,如果未能解决你的问题,请参考以下文章

抽象类接口作为方法返回值和参数

SpringBoot 通用返回类设计

如何将类属性设置为类方法返回类型?

Result类,公共返回类创建

返回多个类时使用jQuery使用一个类

Java基础第三天--内部类