如何使项目在 QML 中的圆圈内拖动?

Aqu*_*irl 4 qt drag-and-drop qml qt5

下面的代码允许在一个区域中拖动红色小矩形,该区域是由最小和最大拖动值定义的矩形。

我希望它只持续到半径为 100 的父矩形的边界,这意味着它现在是一个圆。

如何使项目在 QML 中的圆圈内拖动?

Window {
    width: 200; height: 200; visible: true

    Rectangle
    {
        x: 10; y: 10
        width: 200; height: 200
        radius: 100
        color: "blue"

        Rectangle {
            x: 10; y: 10
            width: 20; height: 20
            color: "red"

            MouseArea
            {
                id: dragArea
                anchors.fill: parent

                drag.target: parent
                drag.minimumX : 20
                drag.maximumX : 150

                drag.minimumY : 20
                drag.maximumY : 150
            }
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

der*_*erM 5

所以我找了一些时间来提供上述更流畅的解决方案。

import QtQuick 2.5
import QtQuick.Window 2.2

Window {
    id: root
    visible: true
    width: 640
    height: 480
    title: qsTr("Hello World")

    property int radius: 100

    Rectangle {
        id: circle
        width: 2 * radius
        height: 2 * radius
        radius: root.radius

        color: 'blue'
    }

    Rectangle {
        id: mark
        width: 20
        height: 20
        x: (dragObj.dragRadius <= root.radius ? dragObj.x : root.radius + ((dragObj.x - root.radius) * (root.radius / dragObj.dragRadius))) - 10
        y: (dragObj.dragRadius <= root.radius ? dragObj.y : root.radius + ((dragObj.y - root.radius) * (root.radius / dragObj.dragRadius))) - 10
        color: 'red'

        MouseArea {
            id: markArea
            anchors.fill: parent
            drag.target: dragObj
            onPressed: {
                dragObj.x = mark.x + 10
                dragObj.y = mark.y + 10
            }
        }
    }

    Item {
        id: dragObj
        readonly property real dragRadius: Math.sqrt(Math.pow(x - root.radius, 2) + Math.pow(y - root.radius, 2))
        x: root.radius
        y: root.radius

        onDragRadiusChanged: console.log(dragRadius)
    }
}
Run Code Online (Sandbox Code Playgroud)

我使用dragObj来避免拖动位置的限制。这跨越了一个从圆心开始的向量。只要dragObj它本身包含在圆圈中,我就会使用它的位置作为标记的位置。
但是一旦它离开圆,我会将向量投影到圆上,因此它会保持在限制范围内。

为确保每次拖动都在标记上重新开始dragObj,当再次按下鼠标时,我会将 的位置重置为标记的位置(新拖动事件的前提)

玩得开心。