From 5d16c75cf6b11c004935d3de8f0b9d5037cc9fed Mon Sep 17 00:00:00 2001 From: Sage Vaillancourt Date: Tue, 4 Mar 2025 19:04:27 -0500 Subject: [PATCH] Extract some round control to rounds.lua Collected items are now unique entities in the world, instead of being held by the cart. Commented-out sparking logic. Very very very basic effects.lua, with things to apply to the cart. --- src/assets.lua | 4 +++ src/assets/images/Spark.png | Bin 0 -> 557 bytes src/cart.lua | 47 ++++++--------------------- src/effects.lua | 10 ++++++ src/ingredients/mushroom.lua | 4 +-- src/main.lua | 11 ++++--- src/systems/collision-resolution.lua | 44 ++++++++++++++++++++++--- src/systems/filter-types.lua | 7 ++++ src/systems/rounds.lua | 43 ++++++++++++++++++++++++ src/systems/velocity.lua | 2 +- 10 files changed, 123 insertions(+), 49 deletions(-) create mode 100644 src/assets/images/Spark.png create mode 100644 src/effects.lua create mode 100644 src/systems/rounds.lua diff --git a/src/assets.lua b/src/assets.lua index fd14996..972b732 100644 --- a/src/assets.lua +++ b/src/assets.lua @@ -17,6 +17,10 @@ LettuceSprite = playdate.graphics.image.new("assets/images/LettuceSprite.png") ---@type pd_image MushroomSprite = playdate.graphics.image.new("assets/images/MushroomSprite.png") +-- luacheck: ignore +---@type pd_image +Spark = playdate.graphics.image.new("assets/images/Spark.png") + -- luacheck: ignore ---@type pd_image TomatoSprite = playdate.graphics.image.new("assets/images/TomatoSprite.png") diff --git a/src/assets/images/Spark.png b/src/assets/images/Spark.png new file mode 100644 index 0000000000000000000000000000000000000000..a0036639752ab8ccf9f3966cf723faa250222e5a GIT binary patch literal 557 zcmV+|0@D47P)EX>4Tx04R}tkv&MmKp2MKrivmJ2MdZgWT-CM!5_r2R-p(LLaorMgUO|T(4-+r zad8w}3l9D)RvlcNb#-tR1i>E=cfm=~MN0fGDYS_3j^iHQ``(wk?*O4*W}4Lz12o+> zQ;E2k$*ziBuL#l{zy!u*W*Kvml!Wj2x<`QTcTt|@U-#$eRdW^t0wQsY8KzCVK|Hf* z8=Uuv!>lN)#OK80CS8#Dk?V@bZ=4G*3p_Jyrc?98VPdh+#!4HrqNx#26Gv1{r+gvf zvC4UivsSLM<~{ifLpgnAnd`KMk-#FBAVGwJDoQBBMwE7)6bmUjkNfzCT)#vvgpt)9ZtvT_HO>D00M0LR%W7L0@Bjb+32;bRa{vGf6951U69E94oEQKA00(qQ zO+^Rk0|X8uCnR9vZ2$lO8FWQhbVF}#ZDnqB07G(RVRU6=Aa`kWXdp*PO;A^X4i^9b v02WC^K~xCWWBC97|NsC085kIt7+?SZV#Njh%A{$x00000NkvXXu0mjf(~{^8 literal 0 HcmV?d00001 diff --git a/src/cart.lua b/src/cart.lua index c62be6f..879cd23 100644 --- a/src/cart.lua +++ b/src/cart.lua @@ -1,5 +1,3 @@ -import("plate.lua") - Cart = {} local sizeX, sizeY = CartSprite:getSize() @@ -11,7 +9,7 @@ function Cart.reset(o) y = 50, } o.velocity = { - x = 50 + (150 * math.random()), + x = 10 + (150 * math.random()), y = 150 * (math.random() - 1), } o.size = size @@ -19,52 +17,27 @@ function Cart.reset(o) flat = { x = 0, y = 0 }, mult = { x = 1, y = 1 }, } - o.canCollideWith = 1 + o.canCollideWith = 1 | 4 o.mass = 1 o.drawAsSprite = CartSprite o.focusPriority = 0 - ---@type pd_image[] - o.collectables = {} - ---@param world World function o:spawnEntitiesWhenStopped(world) - local y = self.position.y - 240 - local rectWidth = 150 - local plateSize = { x = rectWidth, y = 10 } self.velocity = { x = 300, y = 0 } - world:addEntity(self) + self.canCollideWith = 4 + world:addEntity({ + roundAction = "end", + position = { + x = self.position.x, + y = self.position.y, + }, + }) world:addEntity({ position = { x = self.position.x, y = self.position.y }, focusPriority = 1, }) - world:addEntity({ - drawAsRectangle = { size = plateSize }, - size = plateSize, - mass = 0.5, - velocity = { x = 0, y = 0 }, - position = { x = self.position.x - (rectWidth / 2), y = y }, - canCollideWith = 2, - canBeCollidedBy = 2, - isSolid = true, - stopMovingOnCollision = true, - }) - for _, collectable in ipairs(self.collectables) do - local collX, collY = collectable:getSize() - y = y - collY - 5 - world:addEntity({ - drawAsSprite = collectable, - size = { x = collX, y = collY / 2 }, - mass = 0.5, - velocity = { x = 0, y = 0 }, - position = { x = self.position.x - (collX / 2), y = y }, - canCollideWith = 2, - canBeCollidedBy = 2, - isSolid = true, - stopMovingOnCollision = true, - }) - end end return o diff --git a/src/effects.lua b/src/effects.lua new file mode 100644 index 0000000..70fd887 --- /dev/null +++ b/src/effects.lua @@ -0,0 +1,10 @@ +Effects = {} + +---@param entity { canBeBounced: CanBeBounced } +function Effects.makeBouncier(entity) + entity.canBeBounced.mult = entity.canBeBounced.mult * 1.5 +end +---@param entity { mass: number } +function Effects.makeFloatier(entity) + entity.mass = entity.mass * 0.75 +end diff --git a/src/ingredients/mushroom.lua b/src/ingredients/mushroom.lua index e2b24cf..08ed596 100644 --- a/src/ingredients/mushroom.lua +++ b/src/ingredients/mushroom.lua @@ -5,8 +5,8 @@ local size = { x = sizeX, y = sizeY } local expireWhenOffScreenBy = { x = 2000, y = 480 } local canBounce = { - flat = { x = 0, y = 190 }, - mult = { x = 1, y = -2 }, + flat = { x = 0, y = 290 }, + mult = { x = 1, y = -1 }, } function Mushroom.initialize(o, x, y) diff --git a/src/main.lua b/src/main.lua index 4db775e..bd5beb4 100644 --- a/src/main.lua +++ b/src/main.lua @@ -16,6 +16,7 @@ import("systems/collision-detection.lua") import("systems/collision-resolution.lua") import("systems/draw.lua") import("systems/gravity.lua") +import("systems/rounds.lua") import("systems/velocity.lua") import("ingredients/ingredients.lua") import("cart.lua") @@ -30,13 +31,14 @@ local floorSize = { x = 10000, y = 10 } floor = { position = { x = 0, y = 235 }, size = floorSize, - canBeCollidedBy = 1 | 2, + canBeCollidedBy = 1 | 2 | 4, canBounce = { flat = { x = 0, y = 0 }, mult = { x = 0.9, y = -0.5 }, }, drawAsRectangle = { size = floorSize }, isSolid = true, + sparkOnCollision = true, } Camera = { @@ -64,6 +66,8 @@ end world = tiny.world( fallSystem, velocitySystem, + roundSystem, + collectedEntities, collidingEntities, collisionResolution, collisionDetection, @@ -74,7 +78,7 @@ world = tiny.world( cart ) -local ingredientsEveryX = 90 +local ingredientsEveryX = 60 local function init() for i = 1, Ingredients.cacheSize() do @@ -93,9 +97,6 @@ function playdate.update() gfx.clear(gfx.kColorWhite) playdate.drawFPS(5, 5) - Camera.pan.x = math.max(0, cart.position.x - 200) - Camera.pan.y = math.min(0, cart.position.y - 120) - local newestX = Ingredients.newestIngredient().position.x local panX = Camera.pan.x local rightEdge = panX + 400 diff --git a/src/systems/collision-resolution.lua b/src/systems/collision-resolution.lua index 2536654..e4e75b1 100644 --- a/src/systems/collision-resolution.lua +++ b/src/systems/collision-resolution.lua @@ -1,4 +1,4 @@ -collisionResolution = filteredSystem({ collisionBetween = T.Collision }, function(e, _, system) +collisionResolution = filteredSystem({ collisionBetween = T.Collision }, function(e, dt, system) local collidedInto, collider = e.collisionBetween[1], e.collisionBetween[2] local colliderTop = collidedInto.position.y @@ -20,13 +20,29 @@ collisionResolution = filteredSystem({ collisionBetween = T.Collision }, functio collider.velocity.y = collider.velocity.y * collidedInto.canBounce.mult.y * collider.canBeBounced.mult.y end + if collider.focusOnCollide then + system.world:addEntity({ + focusPriority = collider.focusOnCollide, + position = { + x = collider.position.x, + y = collider.position.y, + } + }) + end + if collider.stopMovingOnCollision then - print("stopMovingOnCollision!") collider.velocity = nil collider.canCollideWith = nil system.world:addEntity(collider) end + if collider.onCollidingRemove then + for _, key in ipairs(collider.onCollidingRemove) do + collider[key] = nil + end + collider.onCollidingRemove = nil + end + if collidedInto.score then Score:add(collidedInto.score) end @@ -35,9 +51,29 @@ collisionResolution = filteredSystem({ collisionBetween = T.Collision }, functio system.world:removeEntity(collidedInto) end - if collidedInto.collectable and collider.collectables then - collider.collectables[#collider.collectables + 1] = collidedInto.collectable + if collidedInto.collectable then + system.world:addEntity({ collected = collidedInto.collectable }) end + -- if collidedInto.sparkOnCollision and collider.sparkOnCollision and (math.abs(collider.velocity.x) + math.abs(collider.velocity.y)) > 2 then + -- local size = { x = 1, y = 1 } + -- local spark = { + -- position = { + -- x = collider.position.x, + -- y = collider.position.y + collider.size.y - 2, + -- }, + -- velocity = { + -- x = -collider.velocity.x, + -- y = 150, + -- }, + -- size = size, + -- canCollideWith = 1, + -- mass = 1, + -- drawAsSprite = Spark, + -- expireAfterCollision = true, + -- } + -- system.world:addEntity(spark) + -- end + system.world:removeEntity(e) end) diff --git a/src/systems/filter-types.lua b/src/systems/filter-types.lua index 14004ad..b04f011 100644 --- a/src/systems/filter-types.lua +++ b/src/systems/filter-types.lua @@ -12,6 +12,10 @@ local XyPair = { x = 1, y = 1 } ---@alias BitMask number +---@alias CanBeBounced { flat: XyPair, mult: XyPair } + +---@alias RoundStateAction "end" | "start" + T = { XyPair = XyPair, bool = true, @@ -30,6 +34,7 @@ T = { mult = XyPair, }, --- Receiver + ---@type CanBeBounced CanBeBounced = { flat = XyPair, mult = XyPair, @@ -38,6 +43,8 @@ T = { Collision = { Entity, Entity }, ---@type pd_image PdImage = {}, + ---@type RoundStateAction + RoundStateAction = "start" } ---@generic T diff --git a/src/systems/rounds.lua b/src/systems/rounds.lua new file mode 100644 index 0000000..4d31c88 --- /dev/null +++ b/src/systems/rounds.lua @@ -0,0 +1,43 @@ +collectedEntities = filteredSystem({ collected = T.PdImage }) + +roundSystem = filteredSystem({ roundAction = T.RoundStateAction, position = Maybe(T.XyPair) }, function(e, _, system) + if e.roundAction == "end" then + playdate.setAutoLockDisabled(false) + local y = e.position.y - 240 + local rectWidth = 150 + local plateSize = { x = rectWidth, y = 10 } + + system.world:addEntity({ + drawAsRectangle = { size = plateSize }, + size = plateSize, + mass = 0.5, + velocity = { x = 0, y = 0 }, + position = { x = e.position.x - (rectWidth / 2), y = y }, + canCollideWith = 2, + canBeCollidedBy = 2, + isSolid = true, + stopMovingOnCollision = true, + }) + + for i, collectable in ipairs(collectedEntities.entities) do + local collX, collY = collectable.collected:getSize() + local onCollidingRemove = {"mass", "velocity", "canCollideWith"} + y = y - collY - 15 + system.world:addEntity({ + drawAsSprite = collectable.collected, + size = { x = collX, y = collY / 2 }, + mass = 0.5, + velocity = { x = 0, y = 0 }, + position = { x = e.position.x - (collX / 2), y = y }, + canCollideWith = 2, + canBeCollidedBy = 2, + isSolid = true, + stopMovingOnCollision = true, + onCollidingRemove = onCollidingRemove, + focusOnCollide = i, + }) + system.world:removeEntity(collectable) + end + system.world:removeEntity(e) + end +end) \ No newline at end of file diff --git a/src/systems/velocity.lua b/src/systems/velocity.lua index c55e9f4..8e2ed74 100644 --- a/src/systems/velocity.lua +++ b/src/systems/velocity.lua @@ -4,7 +4,7 @@ velocitySystem = filteredSystem({ position = T.XyPair, velocity = T.XyPair }, fu if not e.velocity then return end - if sqrt((e.velocity.x * e.velocity.x) + (e.velocity.y * e.velocity.y)) < 1 then + if sqrt((e.velocity.x * e.velocity.x) + (e.velocity.y * e.velocity.y)) < 1.5 then e.velocity = nil if e.spawnEntitiesWhenStopped then e:spawnEntitiesWhenStopped(system.world)