Aframe 物理球体在碰撞时破碎成更小的球体
Aframe physics sphere breaks into smaller spheres on collision
在我的游戏中,我制作了一个球体(使用 a-sphere 创建),一个动态物体,与另一个动态物体(a-box)碰撞。
碰撞后,球体分裂成多个更小的球体。我需要阻止这种分裂
这是代码笔 - sphere breaks on collision with dynamic body
这是附带的代码 -
HTML
<a-scene physics="debug: true; gravity: -5.0">
<a-entity camera="userHeight: 1.6"
look-controls
kinematic-body>
<a-entity cursor
position="0 0 -1"
geometry="primitive: circle; radius: 0.01; segments: 4;"
material="color: #FF4444; shader: flat"></a-entity>
<a-entity position="0 0 1" id="attachment"></a-entity>
</a-entity>
<a-entity geometry="primitive: box; height:2" material="color: black; shader: flat" position="0 2 -5" dynamic-body></a-entity>
<a-plane static-body color="#ccc" height="100" width="100" position="0 -0.1 0" rotation="-90 0 0"></a-plane>
</a-scene>
和 JS
const scene = document.querySelector('a-scene');
const camera = document.querySelector('[camera]');
const attachment = document.querySelector('#attachment');
function spawnBullet() {
let entity = document.createElement('a-sphere');
let impulseAmount = 8;
entity.setAttribute('radius', 1);
// Set initial position of projectile to that of the camera.
entity.setAttribute('position', camera.getAttribute('position'));
entity.setAttribute('color', '#00FFCC');
entity.setAttribute('shader', 'flat');
entity.setAttribute('mass', 10);
// Append projectile to the scene, not to the camera, to
// avoid all sorts of complications. Most notably, CANNON.js
// has no scene graph or nesting.
scene.appendChild(entity);
entity.setAttribute('dynamic-body', true);
entity.addEventListener('body-loaded', function(){
// Can't apply forces during the same tick that attaches the body, because
// it hasn't been fully synced to the physics sim. (bug)
setTimeout(function () {
let pStart = new CANNON.Vec3();
// Use an origin point behind the head, not at the head, so
// there's a useful vector between the origin and the projectile.
pStart.copy(attachment.object3D.getWorldPosition());
let force = entity.body.position.vsub(pStart);
force.normalize();
force.scale(impulseAmount, force);
entity.body.applyImpulse(force, entity.body.position);
}, 0);
entity.addEventListener('collide', function(e){
console.log("hit");
})
});
}
if (scene.hasLoaded) init(); // change 2
else scene.addEventListener('loaded', init);
function init () {
// any code that appends things to the scene
scene.addEventListener('click', spawnBullet);
}
有没有办法可以阻止这种情况,并且球体在碰撞后保持完好无损?
球体没有破裂,发生的情况是您的 click
事件处理程序在每次点击时被多次调用,并同时创建许多球体。我不完全确定为什么会这样。解决此问题的一种方法是,使用 AFRAME.utils.throttle
来防止过快地创建球体:
spawnBullet = AFRAME.utils.throttle(spawnBullet, 100);
scene.addEventListener('click', spawnBullet);
更新到较新版本的 A-Frame 也可能会解决此问题。
在现场监听 click
事件适得其反,因为你得到了三个事件
- 单击某物时光标会发出一个
- target
在点击时发出一个
- canvas 发出一个(鼠标点击,而不是 a-frame 光标 - 在 DOM canvas 元素上)。
你可以在this示例中看到它,点击场景中的任何对象,并查看控制台。
您可以监听光标每次 "clicked" 时发出的 mousedown
事件。检查一下 here
如果您使用的是 PC,您还可以监听 aframe canvas 上的点击。如果您在 vive
上,则只需在扣动扳机时调用 shootBullet
。
检查它是否正常工作 here。
在我的游戏中,我制作了一个球体(使用 a-sphere 创建),一个动态物体,与另一个动态物体(a-box)碰撞。
碰撞后,球体分裂成多个更小的球体。我需要阻止这种分裂
这是代码笔 - sphere breaks on collision with dynamic body
这是附带的代码 -
HTML
<a-scene physics="debug: true; gravity: -5.0">
<a-entity camera="userHeight: 1.6"
look-controls
kinematic-body>
<a-entity cursor
position="0 0 -1"
geometry="primitive: circle; radius: 0.01; segments: 4;"
material="color: #FF4444; shader: flat"></a-entity>
<a-entity position="0 0 1" id="attachment"></a-entity>
</a-entity>
<a-entity geometry="primitive: box; height:2" material="color: black; shader: flat" position="0 2 -5" dynamic-body></a-entity>
<a-plane static-body color="#ccc" height="100" width="100" position="0 -0.1 0" rotation="-90 0 0"></a-plane>
</a-scene>
和 JS
const scene = document.querySelector('a-scene');
const camera = document.querySelector('[camera]');
const attachment = document.querySelector('#attachment');
function spawnBullet() {
let entity = document.createElement('a-sphere');
let impulseAmount = 8;
entity.setAttribute('radius', 1);
// Set initial position of projectile to that of the camera.
entity.setAttribute('position', camera.getAttribute('position'));
entity.setAttribute('color', '#00FFCC');
entity.setAttribute('shader', 'flat');
entity.setAttribute('mass', 10);
// Append projectile to the scene, not to the camera, to
// avoid all sorts of complications. Most notably, CANNON.js
// has no scene graph or nesting.
scene.appendChild(entity);
entity.setAttribute('dynamic-body', true);
entity.addEventListener('body-loaded', function(){
// Can't apply forces during the same tick that attaches the body, because
// it hasn't been fully synced to the physics sim. (bug)
setTimeout(function () {
let pStart = new CANNON.Vec3();
// Use an origin point behind the head, not at the head, so
// there's a useful vector between the origin and the projectile.
pStart.copy(attachment.object3D.getWorldPosition());
let force = entity.body.position.vsub(pStart);
force.normalize();
force.scale(impulseAmount, force);
entity.body.applyImpulse(force, entity.body.position);
}, 0);
entity.addEventListener('collide', function(e){
console.log("hit");
})
});
}
if (scene.hasLoaded) init(); // change 2
else scene.addEventListener('loaded', init);
function init () {
// any code that appends things to the scene
scene.addEventListener('click', spawnBullet);
}
有没有办法可以阻止这种情况,并且球体在碰撞后保持完好无损?
球体没有破裂,发生的情况是您的 click
事件处理程序在每次点击时被多次调用,并同时创建许多球体。我不完全确定为什么会这样。解决此问题的一种方法是,使用 AFRAME.utils.throttle
来防止过快地创建球体:
spawnBullet = AFRAME.utils.throttle(spawnBullet, 100);
scene.addEventListener('click', spawnBullet);
更新到较新版本的 A-Frame 也可能会解决此问题。
在现场监听 click
事件适得其反,因为你得到了三个事件
- 单击某物时光标会发出一个
- target
在点击时发出一个
- canvas 发出一个(鼠标点击,而不是 a-frame 光标 - 在 DOM canvas 元素上)。
你可以在this示例中看到它,点击场景中的任何对象,并查看控制台。
您可以监听光标每次 "clicked" 时发出的
mousedown
事件。检查一下 here
如果您使用的是 PC,您还可以监听 aframe canvas 上的点击。如果您在
vive
上,则只需在扣动扳机时调用 shootBullet
。
检查它是否正常工作 here。