|
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136 |
- import {Trait} from "../Entity.js";
- import Vec2 from "../Vec2.js";
-
- let zeroVector = new Vec2(0, 0);
-
- export default class TPhysics extends Trait {
- constructor(entity) {
- super(entity, "physics");
-
- this.gravity = 40;
- this.groundFriction = 6;
- this.airFriction = 2;
-
- this.absVelocity = new Vec2();
- this.velocity = new Vec2();
-
- this.onGround = false;
- this.groundBounds = null;
- this.groundVelocity = null;
- this.oldGroundBounds = null;
- this.timeLastOnGround = 0;
- }
-
- collideTop(bounds, absVelocity) {
- if (this.onGround || bounds === this.oldGroundBounds)
- return;
-
- this.onGround = true;
- this.groundBounds = bounds;
- this.groundVelocity = absVelocity;
-
- this.velocity.x -= absVelocity.x;
- this.velocity.y = 0;
- this.entity.bounds.bottom = bounds.top;
- }
-
- collideWall(bounds, absVelocity) {
- let side = this.entity.bounds.intersectSide(bounds);
-
- if (side === "top")
- return this.collideTop(bounds, absVelocity);
- }
-
- collidePlatform(bounds, absVelocity) {
- let side = this.entity.bounds.intersectSide(bounds);
-
- if (side === "top")
- return this.collideTop(bounds, absVelocity);
- }
-
- update(dt) {
-
- // Gravity
- if (!this.onGround)
- this.velocity.y += this.gravity * dt;
-
- if (this.entity.has("collider")) {
-
- let jumping =
- this.groundVelocity &&
- this.velocity.y < this.groundVelocity.y;
-
- // Check if we're still on the same ground
- if (this.onGround) {
- let stillOnGround =
- (this.entity.bounds.intersects(this.groundBounds)) &&
- (this.entity.bounds.intersectSide(this.groundBounds) === "top") &&
- !jumping;
-
- if (stillOnGround) {
- this.entity.bounds.bottom = this.groundBounds.top;
- } else {
- this.velocity.x += this.groundVelocity.x;
- this.velocity.y += this.groundVelocity.y;
-
- this.onGround = false;
- this.oldGroundBounds = this.groundBounds;
- this.groundBounds = null;
- this.groundVelocity = null;
- }
- }
-
- // Collide with new stuff
- if (!jumping) {
- let collider = this.entity.t.collider;
- collider.entities.forEach(e => {
- let vel;
- if (e.has("physics"))
- vel = e.t.physics.absVelocity;
- else
- vel = zeroVector;
-
- if (e.has("wall"))
- this.collideWall(e.bounds, vel);
- else if (e.has("platform"))
- this.collidePlatform(e.bounds, vel);
- });
- collider.structures.forEach((s, i) => {
- let bounds = collider.structureBounds[i];
- if (s.attrs.wall)
- this.collideWall(bounds, zeroVector);
- else if (s.attrs.platform)
- this.collidePlatform(bounds, zeroVector);
- });
- }
-
- this.oldGroundBounds = null;
- }
-
- // Track the last time we were on the ground
- if (this.onGround)
- this.timeLastOnGround = this.entity.time;
-
- // Apply friction
- var fric = this.onGround ? this.groundFriction : this.airFriction;
- var xRatio = 1 / (1 + (dt * fric));
- this.velocity.x *= xRatio;
- }
-
- postUpdate(dt) {
- this.jumped = false;
-
- // Update absVelocity
- if (this.onGround) {
- this.absVelocity.x = this.velocity.x + this.groundVelocity.x;
- this.absVelocity.y = this.velocity.y + this.groundVelocity.y;
- } else {
- this.absVelocity.x = this.velocity.x;
- this.absVelocity.y = this.velocity.y;
- }
-
- // Move
- this.entity.bounds.pos.x += this.absVelocity.x * dt;
- this.entity.bounds.pos.y += this.absVelocity.y * dt;
- }
- }
|