修复box因缺少初始化报错问题

This commit is contained in:
yhh
2020-06-16 16:35:17 +08:00
parent 7f5b78f340
commit 447ea4efe4
18 changed files with 272 additions and 910 deletions

View File

@@ -55,9 +55,13 @@ class ColliderTriggerHelper {
return false;
});
this._previousTriggerIntersections.forEach(pair => this.notifyTriggerListeners(pair, false));
for (let i = 0; i < this._previousTriggerIntersections.length; i ++){
this.notifyTriggerListeners(this._previousTriggerIntersections[i], false)
}
this._previousTriggerIntersections.length = 0;
tempIntersections.forEach(value => this._previousTriggerIntersections.push(value));
for (let i = 0; i < tempIntersections.length; i ++){
this._previousTriggerIntersections.push(tempIntersections[i]);
}
this._activeTriggerIntersections.length = 0;
}

View File

@@ -3,6 +3,24 @@ class Box extends Polygon {
public width: number;
public height: number;
constructor(width: number, height: number){
super(Box.buildBox(width, height), true);
this.width = width;
this.height = height;
}
private static buildBox(width: number, height: number): Vector2[]{
let halfWidth = width / 2;
let halfHeight = height / 2;
let verts = new Array(4);
verts[0] = new Vector2(-halfWidth, -halfHeight);
verts[1] = new Vector2(halfWidth, -halfHeight);
verts[2] = new Vector2(halfWidth, halfHeight);
verts[3] = new Vector2(-halfWidth, halfHeight);
return verts;
}
public updateBox(width: number, height: number){
this.width = width;
this.height = height;

View File

@@ -14,9 +14,11 @@ class Polygon extends Shape {
}
public isBox: boolean;
constructor(vertCount: number, radius: number) {
constructor(points: Vector2[], isBox?: boolean){
super();
this.setPoints(Polygon.buildSymmertricalPolygon(vertCount, radius));
this.setPoints(points);
this.isBox = isBox;
}
private buildEdgeNormals(){
@@ -42,8 +44,10 @@ class Polygon extends Shape {
this.points = points;
this.recalculateCenterAndEdgeNormals();
this._originalPoints = new Array(this.points.length);
this.points.forEach(point => this._originalPoints.push(point));
this._originalPoints = [];
for (let i = 0; i < this.points.length; i ++){
this._originalPoints.push(this.points[i]);
}
}
public collidesWithShape(other: Shape){

View File

@@ -8,19 +8,19 @@ class SpatialHash {
private _tempHashSet: Collider[] = [];
private _cellDict: NumberDictionary = new NumberDictionary();
constructor(cellSize: number = 100){
constructor(cellSize: number = 100) {
this._cellSize = cellSize;
this._inverseCellSize = 1 / this._cellSize;
this._raycastParser = new RaycastResultParser();
}
public remove(collider: Collider){
public remove(collider: Collider) {
let bounds = collider.registeredPhysicsBounds;
let p1 = this.cellCoords(bounds.x, bounds.y);
let p2 = this.cellCoords(bounds.right, bounds.bottom);
for (let x = p1.x; x <= p2.x; x ++){
for (let y = p1.y; y <= p2.y; y ++){
for (let x = p1.x; x <= p2.x; x++) {
for (let y = p1.y; y <= p2.y; y++) {
let cell = this.cellAtPosition(x, y);
if (!cell)
console.error(`removing Collider [${collider}] from a cell that it is not present in`);
@@ -30,29 +30,29 @@ class SpatialHash {
}
}
public register(collider: Collider){
public register(collider: Collider) {
let bounds = collider.bounds;
collider.registeredPhysicsBounds = bounds;
let p1 = this.cellCoords(bounds.x, bounds.y);
let p2 = this.cellCoords(bounds.right, bounds.bottom);
if (!this.gridBounds.contains(new Vector2(p1.x, p1.y))){
if (!this.gridBounds.contains(new Vector2(p1.x, p1.y))) {
this.gridBounds = RectangleExt.union(this.gridBounds, p1);
}
if (!this.gridBounds.contains(new Vector2(p2.x, p2.y))){
if (!this.gridBounds.contains(new Vector2(p2.x, p2.y))) {
this.gridBounds = RectangleExt.union(this.gridBounds, p2);
}
for (let x = p1.x; x <= p2.x; x++){
for (let y = p1.y; y <= p2.y; y++){
for (let x = p1.x; x <= p2.x; x++) {
for (let y = p1.y; y <= p2.y; y++) {
let c = this.cellAtPosition(x, y, true);
c.push(collider);
}
}
}
public overlapCircle(circleCenter: Vector2, radius: number, results: Collider[], layerMask){
public overlapCircle(circleCenter: Vector2, radius: number, results: Collider[], layerMask) {
let bounds = new Rectangle(circleCenter.x - radius, circleCenter.y - radius, radius * 2, radius * 2);
this._overlapTestCircle.radius = radius;
@@ -60,27 +60,35 @@ class SpatialHash {
let resultCounter = 0;
let potentials = this.aabbBroadphase(bounds, null, layerMask);
potentials.forEach(collider => {
for (let i = 0; i < potentials.length; i ++){
let collider = potentials[i];
if (collider instanceof BoxCollider){
results[resultCounter] = collider;
resultCounter ++;
}else{
throw new Error("overlapCircle against this collider type is not implemented!");
}
if (resultCounter == results.length)
return resultCounter;
});
}
return resultCounter;
}
public aabbBroadphase(bounds: Rectangle, excludeCollider: Collider, layerMask: number){
public aabbBroadphase(bounds: Rectangle, excludeCollider: Collider, layerMask: number) {
this._tempHashSet.length = 0;
let p1 = this.cellCoords(bounds.x, bounds.y);
let p2 = this.cellCoords(bounds.right, bounds.bottom);
for (let x = p1.x; x <= p2.x; x ++){
for (let y = p1.y; y <= p2.y; y ++){
for (let x = p1.x; x <= p2.x; x++) {
for (let y = p1.y; y <= p2.y; y++) {
let cell = this.cellAtPosition(x, y);
if (!cell)
continue;
for (let i = 0; i < cell.length; i ++){
for (let i = 0; i < cell.length; i++) {
let collider = cell[i];
if (collider == excludeCollider || !Flags.isFlagSet(layerMask, collider.physicsLayer))
@@ -95,10 +103,10 @@ class SpatialHash {
return this._tempHashSet;
}
private cellAtPosition(x: number, y: number, createCellIfEmpty: boolean = false){
private cellAtPosition(x: number, y: number, createCellIfEmpty: boolean = false) {
let cell: Collider[] = this._cellDict.tryGetValue(x, y);
if (!cell){
if (createCellIfEmpty){
if (!cell) {
if (createCellIfEmpty) {
cell = [];
this._cellDict.add(x, y, cell);
}
@@ -118,26 +126,26 @@ class RaycastResultParser {
class NumberDictionary {
private _store: Map<number, Collider[]> = new Map<number, Collider[]>();
private getKey(x: number, y: number): number{
private getKey(x: number, y: number): number {
return x << 32 | y;
}
public add(x: number, y: number, list: Collider[]){
public add(x: number, y: number, list: Collider[]) {
this._store.set(this.getKey(x, y), list);
}
public remove(obj: Collider){
public remove(obj: Collider) {
this._store.forEach(list => {
if (list.contains(obj))
list.remove(obj);
})
}
public tryGetValue(x: number, y: number): Collider[]{
public tryGetValue(x: number, y: number): Collider[] {
return this._store.get(this.getKey(x, y));
}
public getAllObjects(): Collider[]{
public getAllObjects(): Collider[] {
let set: Collider[] = [];
this._store.forEach(list => set.concat(list));
@@ -145,7 +153,7 @@ class NumberDictionary {
return set;
}
public clear(){
public clear() {
this._store.clear();
}
}