Qt Quick 3D Physics - Impeller-Beispiel

Demonstriert die Verwendung von Triggerkörpern und Kollisionsinformationen.

Dieses Beispiel demonstriert die Verwendung von Triggerkörpern und Kollisionsinformationen. Die Szene besteht aus einer grünen statischen Ebene, einer roten dynamischen Kugel, einem rosa Triggerkörper und einer blauen statischen Kugel. Wenn die rote Kugel den Triggerkörper überlappt, wird sie gelb, und wenn sie mit der blauen Kugel kollidiert, wird sie weggestoßen.

Einrichten

Wie üblich müssen wir unser PhysicsWorld hinzufügen:

PhysicsWorld {
    gravity: Qt.vector3d(0, -490, 0)
    scene: viewport.scene
}

Wir fügen auch ein View3D hinzu, wo wir unsere Szenenobjekte ablegen. Darin haben wir einige Einstellungen für die visuelle Umgebung:

environment: SceneEnvironment {
    clearColor: "#d6dbdf"
    backgroundMode: SceneEnvironment.Color
}

PerspectiveCamera {
    position: Qt.vector3d(0, 200, 1000)
    clipFar: 2000
    clipNear: 1
}

DirectionalLight {
    eulerRotation.x: -45
    eulerRotation.y: 45
    castsShadow: true
    brightness: 1
    shadowFactor: 50
}

Physikalische Objekte

Wir haben unsere reguläre statische Ebene:

StaticRigidBody {
    position: Qt.vector3d(0, -100, 0)
    eulerRotation: Qt.vector3d(-90, 0, 0)
    collisionShapes: PlaneShape {}
    Model {
        source: "#Rectangle"
        scale: Qt.vector3d(500, 500, 1)
        materials: PrincipledMaterial {
            baseColor: "green"
        }
        castsShadows: false
        receivesShadows: true
    }
}

So wird unsere dynamische Kugel definiert:

DynamicRigidBody {
    id: sphere
    massMode: DynamicRigidBody.CustomDensity
    density: 0.00001
    position: Qt.vector3d(0, 600, 0)
    property bool inArea: false
    sendContactReports: true
    receiveTriggerReports: true

    onEnteredTriggerBody: {
        inArea = true
    }
    onExitedTriggerBody: {
        inArea = false
    }

    collisionShapes: SphereShape {}
    Model {
        source: "#Sphere"
        materials: PrincipledMaterial {
            baseColor: sphere.inArea ? "yellow" : "red"
        }
    }
}

Die Eigenschaft inArea ist eine benutzerdefinierte Eigenschaft, die wir verwenden, um zu verfolgen, wann die Kugel den Auslösekörper der Box überlappt. Dies wird dann für die baseColor Eigenschaft verwendet, um die Kugel gelb zu machen, wenn sie die Box überlappt und ansonsten rot. Da wir wollen, dass die Kugel an der Kontaktmeldung teilnimmt, muss die Eigenschaft sendContactReports auf true gesetzt werden. Da wir auch wollen, dass die Kugel Rückrufe erhält, wenn sie ein TriggerBody betritt oder verlässt, wird die Eigenschaft receiveContactReports ebenfalls auf true gesetzt. Wir implementieren die Signalmethoden enteredTriggerBody und exitedTriggerBody auf der Kugel, wobei wir die Eigenschaft inArea auf true oder false setzen, wenn sie den Triggerkörper betritt oder verlässt.

Schauen wir uns nun den Auslöserkörper an:

TriggerBody {
    position: Qt.vector3d(0, 350, 0)
    scale: Qt.vector3d(1, 2, 1)

    collisionShapes: BoxShape {
        id: boxShape
    }
    Model {
        source: "#Cube"
        materials: PrincipledMaterial {
            baseColor: Qt.rgba(1, 0, 1, 0.2)
            alphaMode: PrincipledMaterial.Blend
        }
    }
}

Der qml-Typ ist ein TriggerBody, der sich wie ein statischer Körper verhält, außer dass seine Kollisionen inaktiv sind. Stattdessen löst er enteredTriggerBody und exitedTriggerBody Methodenaufrufe auf der Kugel aus.

Betrachten wir schließlich das Laufrad:

StaticRigidBody {
    position: Qt.vector3d(0, 0, 0)
    scale: Qt.vector3d(2, 2, 2)
    receiveContactReports: true

    collisionShapes: SphereShape {}

    Model {
        source: "#Sphere"
        materials: PrincipledMaterial {
            baseColor: "blue"
        }
    }

    onBodyContact: (body, positions, impulses, normals) => {
        for (var normal of normals) {
            let velocity = normal.times(-700)
            body.setLinearVelocity(velocity)
        }
    }
}

Dies ist ein statischer Körper und wir setzen receiveContactReports auf true, um die Kollisionsaufrufe zu aktivieren. Der Callback bodyContact wird immer dann aufgerufen, wenn eine Kollision gemeldet wird. In der Methode rufen wir setLinearVelocity auf, um die lineare Geschwindigkeit in die entgegengesetzte Richtung des Kollisions-Normalvektors zu setzen, um ein Laufrad zu simulieren.

Dateien:

© 2025 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.