implement hitbox
This commit is contained in:
@@ -57,7 +57,16 @@ window.WorldRenderer = class {
|
|||||||
this.webRenderer.setClearColor(0x000000, 0);
|
this.webRenderer.setClearColor(0x000000, 0);
|
||||||
this.webRenderer.clear();
|
this.webRenderer.clear();
|
||||||
|
|
||||||
|
// Create sky
|
||||||
this.generateSky();
|
this.generateSky();
|
||||||
|
|
||||||
|
// Create block hit box
|
||||||
|
let geometry = new THREE.BoxGeometry(1, 1, 1);
|
||||||
|
let edges = new THREE.EdgesGeometry(geometry);
|
||||||
|
this.blockHitBox = new THREE.LineSegments(edges, new THREE.LineBasicMaterial({
|
||||||
|
color: 0x000000,
|
||||||
|
}));
|
||||||
|
this.scene.add(this.blockHitBox);
|
||||||
}
|
}
|
||||||
|
|
||||||
render(partialTicks) {
|
render(partialTicks) {
|
||||||
@@ -73,6 +82,9 @@ window.WorldRenderer = class {
|
|||||||
// Render sky
|
// Render sky
|
||||||
this.renderSky(partialTicks);
|
this.renderSky(partialTicks);
|
||||||
|
|
||||||
|
// Render target block
|
||||||
|
this.renderBlockHitBox(player, partialTicks);
|
||||||
|
|
||||||
// Render actual scene
|
// Render actual scene
|
||||||
this.webRenderer.render(this.scene, this.camera);
|
this.webRenderer.render(this.scene, this.camera);
|
||||||
}
|
}
|
||||||
@@ -236,4 +248,43 @@ window.WorldRenderer = class {
|
|||||||
let angle = this.minecraft.world.getCelestialAngle(partialTicks);
|
let angle = this.minecraft.world.getCelestialAngle(partialTicks);
|
||||||
this.skyGroup.rotation.set(angle * Math.PI * 2 + Math.PI / 2, 0, 0);
|
this.skyGroup.rotation.set(angle * Math.PI * 2 + Math.PI / 2, 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
renderBlockHitBox(player, partialTicks) {
|
||||||
|
let hitResult = player.rayTrace(5, partialTicks);
|
||||||
|
let hitBoxVisible = !(hitResult === null);
|
||||||
|
if ((this.blockHitBox.visible = hitBoxVisible)) {
|
||||||
|
let x = hitResult.x;
|
||||||
|
let y = hitResult.y;
|
||||||
|
let z = hitResult.z;
|
||||||
|
|
||||||
|
// Get block type
|
||||||
|
let world = this.minecraft.world;
|
||||||
|
let typeId = world.getBlockAt(x, y, z);
|
||||||
|
let block = Block.getById(typeId);
|
||||||
|
|
||||||
|
if (typeId !== 0) {
|
||||||
|
let boundingBox = block.getBoundingBox(world, x, y, z);
|
||||||
|
|
||||||
|
let offset = 0.01;
|
||||||
|
|
||||||
|
let width = boundingBox.width() + offset;
|
||||||
|
let height = boundingBox.height() + offset;
|
||||||
|
let depth = boundingBox.depth() + offset;
|
||||||
|
|
||||||
|
// Update size of hit box
|
||||||
|
this.blockHitBox.scale.set(
|
||||||
|
width,
|
||||||
|
height,
|
||||||
|
depth
|
||||||
|
);
|
||||||
|
|
||||||
|
// Update position of hit box
|
||||||
|
this.blockHitBox.position.set(
|
||||||
|
x + width / 2 / width - 0.5 + boundingBox.maxX - width / 2 + offset / 2,
|
||||||
|
y + height / 2 / height - 0.5 + boundingBox.maxY - height / 2 + offset / 2,
|
||||||
|
z + depth / 2 / depth - 0.5 + boundingBox.maxZ - depth / 2 + offset / 2,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -341,7 +341,7 @@ window.World = class {
|
|||||||
let block = Block.getById(blockId);
|
let block = Block.getById(blockId);
|
||||||
|
|
||||||
if (block != null && block.canInteract()) {
|
if (block != null && block.canInteract()) {
|
||||||
let hit = block.collisionRayTrace(x, y, z, from, to);
|
let hit = block.collisionRayTrace(this, x, y, z, from, to);
|
||||||
if (hit != null) {
|
if (hit != null) {
|
||||||
return hit;
|
return hit;
|
||||||
}
|
}
|
||||||
@@ -435,7 +435,7 @@ window.World = class {
|
|||||||
let block = Block.getById(blockId);
|
let block = Block.getById(blockId);
|
||||||
|
|
||||||
if (block != null && block.canInteract()) {
|
if (block != null && block.canInteract()) {
|
||||||
let hit = block.collisionRayTrace(x, y, z, from, to);
|
let hit = block.collisionRayTrace(this, x, y, z, from, to);
|
||||||
if (hit != null) {
|
if (hit != null) {
|
||||||
return hit;
|
return hit;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -72,7 +72,7 @@ window.Block = class {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
collisionRayTrace(x, y, z, start, end) {
|
collisionRayTrace(world, x, y, z, start, end) {
|
||||||
start = start.addVector(-x, -y, -z);
|
start = start.addVector(-x, -y, -z);
|
||||||
end = end.addVector(-x, -y, -z);
|
end = end.addVector(-x, -y, -z);
|
||||||
|
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ window.BlockTorch = class extends Block {
|
|||||||
|
|
||||||
this.boundingBox = new BoundingBox(0.4, 0.0, 0.4, 0.6, 0.6, 0.6);
|
this.boundingBox = new BoundingBox(0.4, 0.0, 0.4, 0.6, 0.6, 0.6);
|
||||||
|
|
||||||
|
// Create data faces
|
||||||
this.dataFaces = [
|
this.dataFaces = [
|
||||||
EnumBlockFace.WEST,
|
EnumBlockFace.WEST,
|
||||||
EnumBlockFace.EAST,
|
EnumBlockFace.EAST,
|
||||||
@@ -31,24 +32,52 @@ window.BlockTorch = class extends Block {
|
|||||||
let dataFace = this.dataFaces[i];
|
let dataFace = this.dataFaces[i];
|
||||||
|
|
||||||
if (world.isSolidBlockAt(x + dataFace.x, y + dataFace.y, z + dataFace.z)) {
|
if (world.isSolidBlockAt(x + dataFace.x, y + dataFace.y, z + dataFace.z)) {
|
||||||
world.setBlockDataAt(x, y, z, i + 1);
|
let data = i + 1;
|
||||||
|
|
||||||
|
// Update block data in world
|
||||||
|
world.setBlockDataAt(x, y, z, data);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
onBlockPlaced(world, x, y, z, face) {
|
onBlockPlaced(world, x, y, z, face) {
|
||||||
let meta = world.getBlockDataAt(x, y, z);
|
let data = world.getBlockDataAt(x, y, z);
|
||||||
|
|
||||||
for (let i in this.dataFaces) {
|
for (let i in this.dataFaces) {
|
||||||
let dataFace = this.dataFaces[i];
|
let dataFace = this.dataFaces[i];
|
||||||
|
|
||||||
if (face === dataFace.opposite() && world.isSolidBlockAt(x + dataFace.x, y + dataFace.y, z + dataFace.z)) {
|
if (face === dataFace.opposite() && world.isSolidBlockAt(x + dataFace.x, y + dataFace.y, z + dataFace.z)) {
|
||||||
meta = parseInt(i) + 1;
|
data = parseInt(i) + 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
world.getChunkSectionAt(x >> 4, y >> 4, z >> 4).setBlockDataAt(x & 15, y & 15, z & 15, meta);
|
// Update block data in chunk section directly to avoid notify
|
||||||
|
world.getChunkSectionAt(x >> 4, y >> 4, z >> 4).setBlockDataAt(x & 15, y & 15, z & 15, data);
|
||||||
|
}
|
||||||
|
|
||||||
|
collisionRayTrace(world, x, y, z, start, end) {
|
||||||
|
let data = world.getBlockDataAt(x, y, z) & 7;
|
||||||
|
|
||||||
|
switch (data) {
|
||||||
|
case 1:
|
||||||
|
this.boundingBox = new BoundingBox(0.0, 0.2, 0.35, 0.3, 0.8, 0.65);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
this.boundingBox = new BoundingBox(0.7, 0.2, 0.35, 1.0, 0.8, 0.65);
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
this.boundingBox = new BoundingBox(0.35, 0.2, 0.0, 0.65, 0.8, 0.3);
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
this.boundingBox = new BoundingBox(0.35, 0.2, 0.7, 0.65, 0.8, 1.0);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
this.boundingBox = new BoundingBox(0.4, 0.0, 0.4, 0.6, 0.6, 0.6);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return super.collisionRayTrace(world, x, y, z, start, end);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -21,6 +21,17 @@ window.BoundingBox = class {
|
|||||||
this.maxZ = maxZ;
|
this.maxZ = maxZ;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
width() {
|
||||||
|
return this.maxX - this.minX;
|
||||||
|
}
|
||||||
|
|
||||||
|
height() {
|
||||||
|
return this.maxY - this.minY;
|
||||||
|
}
|
||||||
|
|
||||||
|
depth() {
|
||||||
|
return this.maxZ - this.minZ;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Copy the current bounding box object
|
* Copy the current bounding box object
|
||||||
|
|||||||
Reference in New Issue
Block a user