Weird Box3 behavior

Hello community :wave:

I’m trying to make a collision system using Box3.
Each player have their meshes in a group (this.group), red on the gif.
In the constructor of the Player class, I create the AABB box using setFromObject which is white on the gif.

this.hitbox = new THREE.Box3().setFromObject(this.group);
this.hitboxHelper = new THREE.Box3Helper(this.hitbox, new THREE.Color('#ffffff'));
this.group.add(this.hitboxHelper);

In a setInterval loop (to simulate frame update loop and avoid spamming in case of problems), I make setFromObject again to update positions and then have accurate collisions.

But, when I change the positions or the rotation of the group, the hitbox have a weird behavior :

What I’m doing wrong ?
Thank you

AABB means axis-aligned bounding boxes
dim of your box3helper ( AABB) is calcuted according x,y,z axis at every time . so if use it after rotation of your group , dim change and will be different at every time .

A correct AABB encapsulating a group of objects looks like so: https://jsfiddle.net/vLtq1dhw/

As you can see, the fiddle uses an instance of BoxHelper.

If you want to achieve the same with Box3Helper, you have to recompute the AABB manually every frame: https://jsfiddle.net/vLtq1dhw/1/

As mentioned by @elysium11, Box3 is an AABB so it can never be rotated.

Thank you @elysium11, @Mugen87

As I described, I don’t transform the AABB itself.
Only things I do is playing with the group.

Take a look to the update method called each frame :

public update(delta: number) {
	this.hitbox.setFromObject(this.group);
	if (this.actions.move.left || this.actions.move.right) {
		const direction = this.actions.move.right ? 1 : -1;
		const rotationDelta = (this.stats.turnSpeed / 40) * direction * delta;
		this.group.rotation.y += rotationDelta;
		Game.emitPlayerUpdate({
			action: 'move',
			data: {
				rotation: {
					y: this.group.rotation.y
				} 
			}
		});
	}
	if (this.actions.move.forward || this.actions.move.backward) {
		const direction = this.actions.move.forward ? 1 : -1;
		const translationDelta = (this.stats.moveSpeed / 10) * delta;
		this.group.translateOnAxis(new THREE.Vector3(0, 0, direction), translationDelta);
		Game.emitPlayerUpdate({
			action: 'move',
			data: {
				position: {
					x: this.group.position.x,
					z: this.group.position.z
				}
			}
		});
	}
}

The result is still unexepected :

What could cause this phenomenon ?

you init once hitbox

this.hitbox = new THREE.Box3().setFromObject(this.group);
this.hitboxHelper = new THREE.Box3Helper(this.hitbox, new THREE.Color(’#ffffff’));
this.group.add(this.hitboxHelper);

but after you write ( this is the origin of issue )
public update(delta: number) {
this.hitbox.setFromObject(this.group);

the only thing you have to do is to translate or rotate your group but don t redefine hitbox inside update .

edit : step 1
you define your group and your hitbox .
step 2
you rotate or translate your group
step 3
update hitbox , so dim are bigger than initial
step 4
you rotate or translate group which contain now a hitbox bigger
step 5
update hitbox , so dim bigger than previous step 4

and so on   =   your  hitbox ( see by your helperbox ) increase )
1 Like

Ok so Box3 doesn’t need to be updated ?

I tried this before, I can see with the Box3Helper that the hitbox follows the group but collisions (with intersectsBox) are not accurate or even completely wrong.

If I update with setFromObject, the hitbox grows yes but collisions are accurate.

I probably miss something…
Thank you for your answer :slight_smile:

if you need an aabb hitbox with update , so don’t add at start , your hitbox to your group , like this it will not increase .

1 Like

You are the man, you solved my issue !
Thank you @elysium11.

export default abstract class Collidable {

	public hitbox: THREE.Box3;
	public hitboxHelper: THREE.Box3Helper;

	constructor() {
		this.hitbox = new THREE.Box3();
		this.hitboxHelper = new THREE.Box3Helper(this.hitbox);
		this.initHitbox();
	}

	public initHitbox() {
		Engine.addToScene([this.hitboxHelper]);
	}

	public updateHitbox(group: THREE.Group) {
		this.hitbox.setFromObject(group);
	}

}

And in the player class, at every frame :

this.updateHitbox(this.group);