refactor: aabbs and impassability
This commit is contained in:
parent
6ff824ace6
commit
7a83e1bc7a
|
@ -35,9 +35,9 @@ export default async function createHomestead(Ecs) {
|
|||
impassable: 1,
|
||||
points: [
|
||||
{x: -52, y: -16},
|
||||
{x: 48, y: -16},
|
||||
{x: 44, y: -16},
|
||||
{x: -52, y: 15},
|
||||
{x: 48, y: 15},
|
||||
{x: 44, y: 15},
|
||||
],
|
||||
},
|
||||
],
|
||||
|
|
|
@ -8,6 +8,28 @@ export default class Collider extends Component {
|
|||
const {ecs} = this;
|
||||
return class ColliderInstance extends super.instanceFromSchema() {
|
||||
collidingWith = {};
|
||||
get aabb() {
|
||||
const {Position: {x: px, y: py}} = ecs.get(this.entity);
|
||||
return {
|
||||
x0: this.$$aabb.x0 + px,
|
||||
x1: this.$$aabb.x1 + px,
|
||||
y0: this.$$aabb.y0 + py,
|
||||
y1: this.$$aabb.y1 + py,
|
||||
};
|
||||
}
|
||||
get aabbs() {
|
||||
const {Position: {x: px, y: py}} = ecs.get(this.entity);
|
||||
const aabbs = [];
|
||||
for (const aabb of this.$$aabbs) {
|
||||
aabbs.push({
|
||||
x0: aabb.x0 + px,
|
||||
x1: aabb.x1 + px,
|
||||
y0: aabb.y0 + py,
|
||||
y1: aabb.y1 + py,
|
||||
})
|
||||
}
|
||||
return aabbs;
|
||||
}
|
||||
isCollidingWith(other) {
|
||||
const {aabb, aabbs} = this;
|
||||
const {aabb: otherAabb, aabbs: otherAabbs} = other;
|
||||
|
@ -38,36 +60,34 @@ export default class Collider extends Component {
|
|||
}
|
||||
return false;
|
||||
}
|
||||
recalculateAabbs() {
|
||||
const {Position: {x: px, y: py}} = ecs.get(this.entity);
|
||||
this.aabb = {x0: Infinity, x1: -Infinity, y0: Infinity, y1: -Infinity};
|
||||
this.aabbs = [];
|
||||
const {bodies} = this;
|
||||
for (const body of bodies) {
|
||||
let x0 = Infinity, x1 = -Infinity, y0 = Infinity, y1 = -Infinity;
|
||||
for (const point of body.points) {
|
||||
const x = point.x + px;
|
||||
const y = point.y + py;
|
||||
if (x < x0) x0 = x;
|
||||
if (x < this.aabb.x0) this.aabb.x0 = x;
|
||||
if (x > x1) x1 = x;
|
||||
if (x > this.aabb.x1) this.aabb.x1 = x;
|
||||
if (y < y0) y0 = y;
|
||||
if (y < this.aabb.y0) this.aabb.y0 = y;
|
||||
if (y > y1) y1 = y;
|
||||
if (y > this.aabb.y1) this.aabb.y1 = y;
|
||||
}
|
||||
this.aabbs.push({
|
||||
x0: x0 > x1 ? x1 : x0,
|
||||
x1: x0 > x1 ? x0 : x1,
|
||||
y0: y0 > y1 ? y1 : y0,
|
||||
y1: y0 > y1 ? y0 : y1,
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
async load(instance) {
|
||||
instance.$$aabb = {x0: Infinity, x1: -Infinity, y0: Infinity, y1: -Infinity};
|
||||
instance.$$aabbs = [];
|
||||
const {bodies} = instance;
|
||||
for (const body of bodies) {
|
||||
let x0 = Infinity, x1 = -Infinity, y0 = Infinity, y1 = -Infinity;
|
||||
for (const point of body.points) {
|
||||
const x = point.x;
|
||||
const y = point.y;
|
||||
if (x < x0) x0 = x;
|
||||
if (x < instance.$$aabb.x0) instance.$$aabb.x0 = x;
|
||||
if (x > x1) x1 = x;
|
||||
if (x > instance.$$aabb.x1) instance.$$aabb.x1 = x;
|
||||
if (y < y0) y0 = y;
|
||||
if (y < instance.$$aabb.y0) instance.$$aabb.y0 = y;
|
||||
if (y > y1) y1 = y;
|
||||
if (y > instance.$$aabb.y1) instance.$$aabb.y1 = y;
|
||||
}
|
||||
instance.$$aabbs.push({
|
||||
x0: x0 > x1 ? x1 : x0,
|
||||
x1: x0 > x1 ? x0 : x1,
|
||||
y0: y0 > y1 ? y1 : y0,
|
||||
y1: y0 > y1 ? y0 : y1,
|
||||
});
|
||||
}
|
||||
|
||||
// heavy handed...
|
||||
if ('undefined' !== typeof window) {
|
||||
return;
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
import {System} from '@/ecs/index.js';
|
||||
import {intersects} from '@/util/math.js';
|
||||
import SpatialHash from '@/util/spatial-hash.js';
|
||||
|
||||
export default class Colliders extends System {
|
||||
|
@ -34,7 +35,6 @@ export default class Colliders extends System {
|
|||
if (!entity.Collider) {
|
||||
return;
|
||||
}
|
||||
entity.Collider.recalculateAabbs();
|
||||
this.hash.update(entity.Collider.aabb, entity.id);
|
||||
}
|
||||
|
||||
|
@ -79,10 +79,40 @@ export default class Colliders extends System {
|
|||
other.Ticking.addTickingPromise(script.tickingPromise());
|
||||
}
|
||||
}
|
||||
for (const [, {impassable}] of intersections) {
|
||||
for (const i in intersections) {
|
||||
const [body, otherBody] = intersections[i];
|
||||
const {impassable} = otherBody;
|
||||
if (impassable) {
|
||||
entity.Position.x = entity.Position.lastX
|
||||
entity.Position.y = entity.Position.lastY
|
||||
const j = entity.Collider.bodies.indexOf(body);
|
||||
const oj = other.Collider.bodies.indexOf(otherBody);
|
||||
const aabb = entity.Collider.$$aabbs[j];
|
||||
const otherAabb = other.Collider.aabbs[oj];
|
||||
if (!intersects(
|
||||
{
|
||||
x0: aabb.x0 + entity.Position.lastX,
|
||||
x1: aabb.x1 + entity.Position.lastX,
|
||||
y0: aabb.y0 + entity.Position.y,
|
||||
y1: aabb.y1 + entity.Position.y,
|
||||
},
|
||||
otherAabb,
|
||||
)) {
|
||||
entity.Position.x = entity.Position.lastX
|
||||
}
|
||||
else if (!intersects(
|
||||
{
|
||||
x0: aabb.x0 + entity.Position.x,
|
||||
x1: aabb.x1 + entity.Position.x,
|
||||
y0: aabb.y0 + entity.Position.lastY,
|
||||
y1: aabb.y1 + entity.Position.lastY,
|
||||
},
|
||||
otherAabb,
|
||||
)) {
|
||||
entity.Position.y = entity.Position.lastY
|
||||
}
|
||||
else {
|
||||
entity.Position.x = entity.Position.lastX
|
||||
entity.Position.y = entity.Position.lastY
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -51,9 +51,6 @@ function Entity({entity, ...rest}) {
|
|||
if (!entity) {
|
||||
return false;
|
||||
}
|
||||
if (debug) {
|
||||
entity.Collider?.recalculateAabbs();
|
||||
}
|
||||
return (
|
||||
<Container
|
||||
zIndex={entity.Position?.y || 0}
|
||||
|
|
Loading…
Reference in New Issue
Block a user