Столкновение радиовещания Three.js не работает - PullRequest
0 голосов
/ 08 июля 2019

Я работаю над аркадным стилем Everest Flight Simulator.

В моем отладчике, где я его строю, у меня есть класс местности и вертолет, который генерирует сетку ландшафта BufferGeometry, группы для геометрии вертолетной площадки и группу для камеры и геометрии вертолета.

Моя проблема в том, что в настоящее время я не могу обнаружить никакого столкновения. Я полагаю, что он может не поддерживать BufferGeometries, так что это проблема для меня, потому что мне нужно, чтобы ландшафт был буфером, так как он слишком обширный ... как стандартная геометрия, он вызывает сбой памяти в браузере.

Тем не менее, тестирование геометрии вертолетной площадки само по себе не срабатывает. Они находятся в группе, поэтому я добавляю группы в глобальный массив окон и устанавливаю проверку столкновения как рекурсивную, но безрезультатно.

В конечном счете, я открыт для других форм обнаружения столкновений, и мне могут понадобиться два типа, поскольку у меня есть для использования геометрии буфера. Любые идеи о том, как исправить это или лучшее решение?

Сам объект вертолета

// Rect to Simulate Helicopter
const geometry = new THREE.BoxGeometry( 2, 1, 4 ),
      material = new THREE.MeshBasicMaterial(),
      rect = new THREE.Mesh( geometry, material );

rect.position.x = 0;
rect.position.y = terrain.returnCameraStartPosY();
rect.position.z = 0;
rect.rotation.order = "YXZ";
rect.name = "heli";

// Link Camera and Helicopter
const heliCam = new THREE.Group(),
      player = new Helicopter(heliCam, "OH-58 Kiowa", 14000);

heliCam.add(camera);
heliCam.add(rect);
heliCam.position.set( 0, 2040, -2000 );
heliCam.name = "heliCam";
scene.add(heliCam);

Добавление объектов в глобальный массив столкновений

// Add Terrain
const terrain = new Terrain.ProceduralTerrain(),
      terrainObj = terrain.returnTerrainObj(),
      helipadEnd = new Terrain.Helipad( 0, 1200, -3600, "Finish", true ),
      helipadStart = new Terrain.Helipad( 0, 2000, -2000, "Start", false ),
      helipadObjStart = helipadStart.returnHelipadObj(),
      helipadObjEnd = helipadEnd.returnHelipadObj();

window.collidableMeshList.push(terrainObj);
window.collidableMeshList.push(helipadObjStart);
window.collidableMeshList.push(helipadObjEnd);

Функция обнаружения столкновений запускается каждый кадр

collisionDetection(){
    const playerOrigin = this.heli.children[1].clone(); // Get Box Mesh from Player Group

    for (let i = playerOrigin.geometry.vertices.length - 1; i >= 0; i--) {
        const localVertex      = playerOrigin.geometry.vertices[i].clone(),
              globalVertex     = localVertex.applyMatrix4( playerOrigin.matrix ),
              directionVector  = globalVertex.sub( playerOrigin.position ),
              ray              = new THREE.Raycaster( playerOrigin, directionVector.clone().normalize() ),
              collisionResults = ray.intersectObjects( window.collidableMeshList, true ); // Recursive Boolean for children

        if ( collisionResults.length > 0 ){
            this.landed = true;
            console.log("Collision");
        }

        // if ( collisionResults.length > 0 && collisionResults[0].distance < directionVector.length() ){
        //  this.landed = true;
        //  console.log("Collision with vectorLength")
        // }    
    }
}

1 Ответ

0 голосов
/ 08 июля 2019

Трудно сказать, что происходит внутри ваших пользовательских классов, но похоже, что вы используете Object3D в качестве первого аргумента raycaster, вместо Vector3, когда вы используете this.heli.children[1].clone(). Почему бы вам не попробовать что-то вроде:

var raycaster = new THREE.Raycaster();
var origin = this.heli.children[1].position;

raycaster.set(origin, direction);

Кроме того, вы уверены, что используете BufferGeometry? Потому что, когда вы получаете доступ к значению вершины, например: playerOrigin.geometry.vertices[i], оно должно дать вам ошибку. В BufferGeometry отсутствует атрибут vertices, поэтому я не знаю, как вы определяете вектор направления.

...