Skip to content

Commit

Permalink
feat: Add two mechanics: climb rope, and jetpack rope
Browse files Browse the repository at this point in the history
  • Loading branch information
johnedvard committed Aug 19, 2022
1 parent 40fdf7b commit 651caad
Show file tree
Hide file tree
Showing 12 changed files with 86 additions and 44 deletions.
12 changes: 11 additions & 1 deletion src/BoneLink.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
import { RESTING_DISTANCE } from './constants';

/**
* Link between two PointMasses
*/
export class BoneLink {
restingDistance = 30;
restingDistance = RESTING_DISTANCE;
stiffness = 1;
pointMassA;
pointMassB;
Expand Down Expand Up @@ -36,4 +38,12 @@ export class BoneLink {
this.pointMassB.x -= diffX * scalarP2 * difference;
this.pointMassB.y -= diffY * scalarP2 * difference;
};

reduceRestingDistance(factor) {
const reduction = RESTING_DISTANCE * factor;
this.restingDistance -= reduction;
if (this.restingDistance <= 0) {
this.restingDistance = 0;
}
}
}
5 changes: 3 additions & 2 deletions src/Game.js
Original file line number Diff line number Diff line change
Expand Up @@ -44,9 +44,10 @@ export class Game {
const rope = this.player.rope;
for (let i = 0; i < rope.length - 2; i++) {
if (
// TODO (johnedvard) add to y-axis if saw is up down
lineIntersection(
{ x: this.saw.x - 1, y: this.saw.y },
{ x: this.saw.x + 1, y: this.saw.y },
{ x: this.saw.x - 5, y: this.saw.y },
{ x: this.saw.x + 5, y: this.saw.y },
{ x: rope[i].x, y: rope[i].y },
{ x: rope[i + 1].x, y: rope[i + 1].y }
)
Expand Down
Empty file added src/Platform.js
Empty file.
66 changes: 33 additions & 33 deletions src/Player.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,36 +3,23 @@ import skull from './assets/img/skull.png';
import { getPointer, Sprite } from 'kontra';
import { PlayerControls } from './PlayerControls';
import { PointMass } from './PointMass';
import { RESTING_DISTANCE } from './constants';

export class Player {
x;
y;
game;
rope = []; // list of pointmasses
pointMass;
pointMass; // used to attach to the end of the rope
playerControls;
sprite = { render: () => {} };
sprite = { render: () => {} }; // draw sprite on pointmass position

constructor(x, y, game) {
this.x = x;
this.y = y;
this.game = game;
this.pointMass = new PointMass(x, y, { game, mass: 2 });
this.createRope();
this.createSprite();
this.playerControls = new PlayerControls(this);
}

hasRope() {
return !!this.rope.length;
}
removeRope() {
this.pointMass.removeLink();
this.rope.length = 0;
}
shootRope() {
this.createRope();
}
updateRope() {
this.rope.forEach((p) => {
p.update();
Expand All @@ -53,31 +40,36 @@ export class Player {
};
image.onload = () => {
this.sprite = Sprite({
x: this.x,
y: this.y,
x: this.pointMass.x,
y: this.pointMass.y,
anchor: { x: 0.5, y: 0.5 },
image: image,
scaleX: 2,
scaleY: 2,
});
};
}

createRope() {
const anchor = new PointMass(this.game.canvas.width / 2, 100, {
isAnchor: true,
game: this.game,
});
this.rope.push(anchor);
for (let i = 1; i < 7; i++) {
for (let i = 1; i < 8; i++) {
const p1 = this.rope[this.rope.length - 1];
const p2 = new PointMass(i * 10, i * 10, { game: this.game });
const p2 = new PointMass(this.game.canvas.width / 2, i * 25 + 100, {
game: this.game,
});
p1.attachTo(p2);
this.rope.push(p2);
}
this.pointMass.attachTo(this.rope[this.rope.length - 1]);
this.pointMass.x = this.rope[this.rope.length - 1];
this.rope[this.rope.length - 1].attachTo(this.pointMass);
this.rope.push(this.pointMass);
}

// Debug purpose only
dragRope() {
if (this.game.isDragging && this.rope.length) {
const pointer = getPointer();
Expand Down Expand Up @@ -108,26 +100,34 @@ export class Player {
}

update() {
this.x = this.pointMass.x;
this.y = this.pointMass.y;

this.sprite.x = this.pointMass.x;
this.sprite.y = this.pointMass.y;

this.updateRope();
this.dragRope();
this.dragRope(); // TODO (johnedvard) Only enable in local and beta env
this.playerControls.updateControls();
}

climbRope() {
if (!this.rope || this.rope.length < 2) return;

const lastPointMassWithLink = this.rope[this.rope.length - 2];
lastPointMassWithLink.reduceRestingDistance(0.1);
if (lastPointMassWithLink.restingDistance <= 0) {
this.reArrangeRope();
}
}
reArrangeRope() {
this.rope.splice(this.rope.length - 2, 1);
const newLastPointWithLink = this.rope[this.rope.length - 2];
// undefined if last link was romved
if (newLastPointWithLink) {
newLastPointWithLink.removeLink();
newLastPointWithLink.attachTo(this.pointMass);
}
}
cutRope = (index) => {
if (index >= this.rope.length - 1) index = this.rope.length - 2; // Make sure we can cut the rope if we pass the wrong index
this.rope[index].removeLink();
};
toggleRope = (e) => {
// TODO (johnedvard) Maybe use state machine
if (this.hasRope()) {
this.removeRope();
} else {
this.shootRope();
}
};
}
7 changes: 6 additions & 1 deletion src/PlayerControls.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,15 @@ export class PlayerControls {
this.player.applyForce(1.5, 0);
this.player.changePlayerDirection(false);
}
if (keyPressed('arrowup')) {
this.player.climbRope();
}
if (keyPressed('space')) {
this.player.applyForce(0, -6);
}
}

initControls() {
onInput(['space'], this.player.toggleRope);
onInput(['c'], () => this.player.cutRope(3));
}
}
14 changes: 12 additions & 2 deletions src/PointMass.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { BoneLink } from './BoneLink';
import { gravity } from './constants';
import { fgc2, RESTING_DISTANCE } from './constants';

export class PointMass {
sprite; // TODO (johnedvard) maybe remove
Expand All @@ -14,6 +15,7 @@ export class PointMass {
anchorY;
mass = 1;
game;
restingDistance = RESTING_DISTANCE;

constructor(x, y, { isAnchor, game, mass }) {
this.game = game;
Expand All @@ -39,6 +41,13 @@ export class PointMass {
}
}

reduceRestingDistance(factor) {
this.links.forEach((l) => {
l.reduceRestingDistance(factor);
this.restingDistance = l.restingDistance;
});
}

isAnchor() {
return this.anchorX !== undefined || this.anchorX !== undefined;
}
Expand All @@ -56,10 +65,11 @@ export class PointMass {
render(ctx) {
if (!ctx) return;
ctx.lineWidth = 4;
ctx.strokeStyle = fgc2;

ctx.beginPath();
ctx.moveTo(this.x, this.y);
this.links.forEach((link) => {
ctx.moveTo(link.pointMassA.x, link.pointMassA.y);
ctx.lineTo(link.pointMassB.x, link.pointMassB.y);
});
ctx.stroke();
Expand All @@ -70,7 +80,7 @@ export class PointMass {
this.updatePhysics();
}
updatePhysics() {
if (this.y >= this.game.canvas.height - 2) return; // prevent humping on floor
if (this.y >= this.game.canvas.height - 3) return; // prevent humping on floor
this.applyForce(0, this.mass * gravity);

let velX = this.x - this.lastX;
Expand Down
8 changes: 5 additions & 3 deletions src/Saw.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import saw from './assets/img/saw.png';
import saw2 from './assets/img/saw3.png';
import saw from './assets/img/saw3.png';
import { Sprite } from 'kontra';
import { BACK_FORTH, UP_DOWN } from './sawBehavior';

Expand All @@ -10,6 +11,7 @@ export class Saw {
sprite = { render: () => {} };
distance = 100;
speed = 1;
rotSpeed = 0.2;

constructor(x, y, { behavior, distance }) {
this.x = x;
Expand All @@ -23,7 +25,7 @@ export class Saw {

update() {
this.moveDistance(this.behavior, this.distance);
this.sprite.rotation += 5;
this.sprite.rotation += this.rotSpeed;
}
moveDistance(behavior, distance) {
let axis = 'x';
Expand All @@ -47,7 +49,7 @@ export class Saw {
}
createSprite() {
const image = new Image();
image.src = saw;
image.src = saw2;
image.onerror = function (err) {
console.log(err);
};
Expand Down
Binary file added src/assets/img/saw2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added src/assets/img/saw3.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 3 additions & 1 deletion src/assetsUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,11 @@ import { load } from 'kontra';
import skull from './assets/img/skull.png';
import chain from './assets/img/chain.png';
import saw from './assets/img/saw.png';
import saw2 from './assets/img/saw2.png';
import saw3 from './assets/img/saw3.png';

export const initAssets = () => {
load(skull, chain, saw)
load(skull, chain, saw, saw2, saw3)
.then(function (assets) {
console.log('assets loaded');
// all assets have loaded
Expand Down
6 changes: 6 additions & 0 deletions src/constants.js
Original file line number Diff line number Diff line change
@@ -1 +1,7 @@
export const gravity = 2;
export const bgc = '#211e20';
export const bgc2 = '#555568';
export const fgc = '#a0a08b';
export const fgc2 = '#e9efec';

export const RESTING_DISTANCE = 25;
8 changes: 7 additions & 1 deletion src/styles.css
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
:root {
--bgc: #211e20;
--bgc2: #555568;
--fgc: #a0a08b;
--fgc2: #e9efec;
}
body {
width: 100vw;
height: 100vh;
Expand All @@ -10,5 +16,5 @@ body {
overflow: hidden;
}
canvas {
background-color: gray;
background-color: var(--bgc);
}

0 comments on commit 651caad

Please sign in to comment.