From 9be18acfd5a3b81a1ea4458553035f5f05dd7c42 Mon Sep 17 00:00:00 2001 From: Josh Curtiss Date: Wed, 29 May 2024 16:19:16 -0800 Subject: [PATCH] feat: Add salt component --- src/com/Peter.ts | 28 +++++++++++------- src/com/Salt.ts | 64 +++++++++++++++++++++++++++++++++++++++++ src/scenes/GameScene.ts | 4 ++- 3 files changed, 85 insertions(+), 11 deletions(-) create mode 100644 src/com/Salt.ts diff --git a/src/com/Peter.ts b/src/com/Peter.ts index 5c7df2c..802d06c 100644 --- a/src/com/Peter.ts +++ b/src/com/Peter.ts @@ -1,9 +1,10 @@ import { k } from '../kaboom'; -import { Comp } from 'kaboom'; +import { Comp, Vec2 } from 'kaboom'; const { isKeyDown, lifespan, + onKeyPress, vec2, } = k; @@ -12,24 +13,31 @@ export interface PeterComp extends Comp { isAlive: boolean; freeze: Function; die: Function; + setAnim: (dir: Vec2) => void; } export function peter(): PeterComp { return { id: "peter", - require: ["area", "sprite", "can-walk"], + require: ["area", "sprite", "can-salt", "can-walk"], isFrozen: false, isAlive: true, add() { - this.onDirChange(newdir=>{ - let anim = 'idle'; - let flipX = newdir.x>0; - if (newdir.y<0) anim = 'up'; - else if (newdir.y>0) anim = 'down'; - else if (newdir.x) anim = 'walk'; - if (this.curAnim() !== anim) this.play(anim); - this.flipX = flipX; + onKeyPress(key=>{ + if (key==='space') { + this.throwSalt(); + } }); + this.onDirChange(this.setAnim); + }, + setAnim(newdir) { + let anim = 'idle'; + let flipX = newdir.x>0; + if (newdir.y<0) anim = 'up'; + else if (newdir.y>0) anim = 'down'; + else if (newdir.x) anim = 'walk'; + if (this.curAnim() !== anim) this.play(anim); + this.flipX = flipX; }, update() { if (this.isFrozen) { diff --git a/src/com/Salt.ts b/src/com/Salt.ts new file mode 100644 index 0000000..729d27f --- /dev/null +++ b/src/com/Salt.ts @@ -0,0 +1,64 @@ +import { k } from '../kaboom'; +import { Comp, Vec2 } from 'kaboom'; + +const { + add, + anchor, + area, + pos, + sprite, + vec2, + wait, +} = k; + +export interface SaltComp extends Comp { + saltDelay: number; + saltDir: Vec2; + saltQty: number; + throwSalt: ()=>void; +} + +export function canSalt(): SaltComp { + return { + id: "can-salt", + require: ["peter", "can-walk"], + saltDelay: 0.6, + saltDir: vec2(1, 0), + saltQty: 5, + add() { + this.onDirChange(newdir=>{ + // Set last MOVING direction, never the idle state. + if (!newdir.isZero()) this.saltDir = newdir; + }); + }, + throwSalt() { + if (!this.saltQty) { + // TODO: Play empty salt sound + return; + } + this.saltQty-=1; + const saltPos = this.pos.sub(0, this.height/4).add(this.saltDir.x*this.width*0.75, this.saltDir.y*this.height), + saltTop = add([ + sprite('salt', { frame: 1, flipX: this.saltDir.x>0 }), + anchor('center'), + pos(saltPos), + area({collisionIgnore: ['player']}), + ]), + saltBottom = add([ + sprite('salt', { frame: 2, flipX: this.saltDir.x>0 }), + anchor('center'), + pos(saltPos.add(0, saltTop.height)), + area({collisionIgnore: ['player']}), + ]); + // TODO: Play salt sound + const anim = this.saltDir.x ? 'throw' : this.saltDir.y<0 ? 'throw-up' : 'throw-down'; + this.flipX = this.saltDir.x>0; + this.play(anim); + wait(this.saltDelay, ()=>{ + this.setAnim(this.dir); + saltTop.destroy(); + saltBottom.destroy(); + }); + }, + }; +}; diff --git a/src/scenes/GameScene.ts b/src/scenes/GameScene.ts index ba203c0..4a23af9 100644 --- a/src/scenes/GameScene.ts +++ b/src/scenes/GameScene.ts @@ -6,6 +6,7 @@ import { } from 'kaboom'; import { k } from '../kaboom'; import { peter, PeterComp } from '../com/Peter'; +import { canSalt, SaltComp } from '../com/Salt'; import { canWalk, WalkComp, WalkableObj } from '../com/Walk'; import LEVELS from '../levels.json'; @@ -70,6 +71,7 @@ const levelConf: LevelOpt = { area({ shape: new Rect(vec2(0), 8, 15) }), anchor('center'), peter(), + canSalt(), canWalk(), "player", ], @@ -110,6 +112,6 @@ export default function(levelNumber = 0) { }); // Player setup - const player: GameObj = level.spawn("p", 16, 21.625); + const player: GameObj = level.spawn("p", 16, 21.625); player.setObjects({ floors, stairs, stairtops }); }