unknown
BIN
source/.DS_Store
vendored
BIN
source/assets/.DS_Store
vendored
BIN
source/assets/audio/bomberTheme.mp3
Normal file
BIN
source/assets/audio/drop.wav
Normal file
BIN
source/assets/audio/drop1.wav
Normal file
BIN
source/assets/audio/hit1.wav
Normal file
BIN
source/assets/sprites/death.png
Normal file
|
After Width: | Height: | Size: 1.0 KiB |
BIN
source/assets/sprites/enemy1.png
Normal file
|
After Width: | Height: | Size: 369 B |
BIN
source/assets/sprites/enemy1_1.png
Normal file
|
After Width: | Height: | Size: 313 B |
BIN
source/assets/sprites/enemy1_2.png
Normal file
|
After Width: | Height: | Size: 379 B |
BIN
source/assets/sprites/enemy1_3.png
Normal file
|
After Width: | Height: | Size: 396 B |
BIN
source/assets/sprites/enemy1_4.png
Normal file
|
After Width: | Height: | Size: 343 B |
BIN
source/assets/sprites/enemy2.png
Normal file
|
After Width: | Height: | Size: 440 B |
BIN
source/assets/sprites/enemy_2.png
Normal file
|
After Width: | Height: | Size: 854 B |
BIN
source/assets/sprites/noise-table-400-240.png
Normal file
|
After Width: | Height: | Size: 154 KiB |
@@ -24,14 +24,16 @@ ZIndex = {
|
|||||||
ui = 10,
|
ui = 10,
|
||||||
alert = 12,
|
alert = 12,
|
||||||
ground = 100,
|
ground = 100,
|
||||||
flash = 101
|
flash = 101,
|
||||||
|
foreground = 102
|
||||||
}
|
}
|
||||||
CollideGroups = {
|
CollideGroups = {
|
||||||
player = 1,
|
player = 1,
|
||||||
enemy = 2,
|
enemy = 2,
|
||||||
props = 3,
|
props = 3,
|
||||||
items = 4,
|
items = 4,
|
||||||
wall = 5
|
wall = 5,
|
||||||
|
granade = 6
|
||||||
}
|
}
|
||||||
|
|
||||||
Maps = {
|
Maps = {
|
||||||
@@ -111,7 +113,8 @@ import "scripts/MapCard"
|
|||||||
import "scripts/bomber/movableCrosshair"
|
import "scripts/bomber/movableCrosshair"
|
||||||
import "scripts/bomber/granade"
|
import "scripts/bomber/granade"
|
||||||
import "scripts/bomber/explosionMark"
|
import "scripts/bomber/explosionMark"
|
||||||
|
import "scripts/bomber/enemy"
|
||||||
|
import "scripts/bomber/noiseAnimation"
|
||||||
import "scenes/BaseScene"
|
import "scenes/BaseScene"
|
||||||
import 'scenes/Assemble'
|
import 'scenes/Assemble'
|
||||||
import 'scenes/DroneCardSelector'
|
import 'scenes/DroneCardSelector'
|
||||||
@@ -159,4 +162,6 @@ playdate.display.setRefreshRate(50)
|
|||||||
|
|
||||||
Noble.showFPS = false
|
Noble.showFPS = false
|
||||||
|
|
||||||
Noble.new(BomberScene)
|
|
||||||
|
--Noble.new(BomberScene)
|
||||||
|
Noble.new(Menu)
|
||||||
|
|||||||
@@ -2,7 +2,7 @@ name=FPV Game
|
|||||||
author=ut3usw
|
author=ut3usw
|
||||||
description=This is a FPV Game
|
description=This is a FPV Game
|
||||||
bundleID=guru.dead.fpv
|
bundleID=guru.dead.fpv
|
||||||
version=0.2.0
|
version=0.2.6
|
||||||
buildNumber=10
|
buildNumber=13
|
||||||
imagePath=assets/launcher/
|
imagePath=assets/launcher/
|
||||||
launchSoundPath=assets/launcher/sound.wav
|
launchSoundPath=assets/launcher/sound.wav
|
||||||
@@ -159,11 +159,6 @@ This operation is crucial. Execute with precision. Command out.]]
|
|||||||
-- self.dialogue:setPadding(4)
|
-- self.dialogue:setPadding(4)
|
||||||
end
|
end
|
||||||
|
|
||||||
function round(number)
|
|
||||||
local formatted = string.format("%.2f", number)
|
|
||||||
return formatted
|
|
||||||
end
|
|
||||||
|
|
||||||
local elapsedTime = 0
|
local elapsedTime = 0
|
||||||
function scene:update()
|
function scene:update()
|
||||||
scene.super.update(self)
|
scene.super.update(self)
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ scene.inputHandler = {
|
|||||||
return
|
return
|
||||||
end
|
end
|
||||||
scene.menuConfirmSound:play(1)
|
scene.menuConfirmSound:play(1)
|
||||||
mode = Drones[scene.menuIndex].mode
|
local mode = Drones[scene.menuIndex].mode
|
||||||
local soundTable = playdate.sound.playingSources()
|
local soundTable = playdate.sound.playingSources()
|
||||||
for i=1, #soundTable do
|
for i=1, #soundTable do
|
||||||
soundTable[i]:stop()
|
soundTable[i]:stop()
|
||||||
|
|||||||
@@ -4,19 +4,6 @@ local scene = Game
|
|||||||
|
|
||||||
local font = Graphics.font.new('assets/fonts/Mini Sans 2X')
|
local font = Graphics.font.new('assets/fonts/Mini Sans 2X')
|
||||||
|
|
||||||
local function screenShake(shakeTime, shakeMagnitude)
|
|
||||||
local shakeTimer = playdate.timer.new(shakeTime, shakeMagnitude, 0)
|
|
||||||
shakeTimer.updateCallback = function(timer)
|
|
||||||
local magnitude = math.floor(timer.value)
|
|
||||||
local shakeX = math.random(-magnitude, magnitude)
|
|
||||||
local shakeY = math.random(-magnitude, magnitude)
|
|
||||||
playdate.display.setOffset(shakeX, shakeY)
|
|
||||||
end
|
|
||||||
shakeTimer.timerEndedCallback = function()
|
|
||||||
playdate.display.setOffset(0, 0)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
function scene:drawBackground()
|
function scene:drawBackground()
|
||||||
local speed = 0.1
|
local speed = 0.1
|
||||||
if scene.ground ~= nil then
|
if scene.ground ~= nil then
|
||||||
@@ -66,8 +53,6 @@ end
|
|||||||
function scene:start()
|
function scene:start()
|
||||||
scene.super.start(self)
|
scene.super.start(self)
|
||||||
|
|
||||||
playdate.ui.crankIndicator:draw() -- not sure why this is not working
|
|
||||||
|
|
||||||
self.optionsMenu:addMenuItem("Main Menu", function() Noble.transition(Menu) end)
|
self.optionsMenu:addMenuItem("Main Menu", function() Noble.transition(Menu) end)
|
||||||
Noble.showFPS = false
|
Noble.showFPS = false
|
||||||
end
|
end
|
||||||
@@ -103,14 +88,13 @@ function scene:enter()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function round(number)
|
|
||||||
local formatted = string.format("%.2f", number)
|
|
||||||
return formatted
|
|
||||||
end
|
|
||||||
|
|
||||||
function scene:update()
|
function scene:update()
|
||||||
scene.super.update(self)
|
scene.super.update(self)
|
||||||
|
|
||||||
|
if playdate.isCrankDocked() then
|
||||||
|
playdate.ui.crankIndicator:draw()
|
||||||
|
end
|
||||||
|
|
||||||
if scene.player == nil then
|
if scene.player == nil then
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
@@ -169,6 +153,7 @@ function scene:exit()
|
|||||||
if scene.tank ~= nil then
|
if scene.tank ~= nil then
|
||||||
scene.tank:remove()
|
scene.tank:remove()
|
||||||
end
|
end
|
||||||
|
scene.helloAudio:stop()
|
||||||
scene.telemLostSound:stop()
|
scene.telemLostSound:stop()
|
||||||
scene.levelAudio:stop()
|
scene.levelAudio:stop()
|
||||||
scene.balebaSpawner:remove()
|
scene.balebaSpawner:remove()
|
||||||
|
|||||||
@@ -42,6 +42,7 @@ end
|
|||||||
|
|
||||||
function scene:update()
|
function scene:update()
|
||||||
scene.super.update(self)
|
scene.super.update(self)
|
||||||
|
if not scene.cards then return end
|
||||||
elapsedTime = elapsedTime + 1 / playdate.display.getRefreshRate()
|
elapsedTime = elapsedTime + 1 / playdate.display.getRefreshRate()
|
||||||
|
|
||||||
local dy = 2 * math.sin(20 * elapsedTime)
|
local dy = 2 * math.sin(20 * elapsedTime)
|
||||||
|
|||||||
@@ -110,7 +110,7 @@ end
|
|||||||
|
|
||||||
function scene:exit()
|
function scene:exit()
|
||||||
scene.super.exit(self)
|
scene.super.exit(self)
|
||||||
-- scene.levelAudio:stop()
|
scene.levelAudio:stop()
|
||||||
self.sequence = Sequence.new():from(self.menuY):to(self.menuYTo, 0.5, Ease.inSine)
|
self.sequence = Sequence.new():from(self.menuY):to(self.menuYTo, 0.5, Ease.inSine)
|
||||||
self.sequence:start()
|
self.sequence:start()
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -11,6 +11,11 @@ function scene:init()
|
|||||||
self.bgY = 0
|
self.bgY = 0
|
||||||
self.scrollSpeed = 0.6
|
self.scrollSpeed = 0.6
|
||||||
|
|
||||||
|
scene.dropSound = playdate.sound.fileplayer.new("assets/audio/drop1")
|
||||||
|
scene.themeSound = playdate.sound.fileplayer.new("assets/audio/bomberTheme")
|
||||||
|
scene.themeSound:setVolume(0.5)
|
||||||
|
scene.themeSound:play()
|
||||||
|
|
||||||
scene.progressBar = ProgressBar(50, 210, 50, 5)
|
scene.progressBar = ProgressBar(50, 210, 50, 5)
|
||||||
scene.progressBar:set(0)
|
scene.progressBar:set(0)
|
||||||
scene.progressBar:setVisible(false)
|
scene.progressBar:setVisible(false)
|
||||||
@@ -19,9 +24,22 @@ function scene:init()
|
|||||||
scene.grenadeCooldownTimer = nil
|
scene.grenadeCooldownTimer = nil
|
||||||
scene.grenadeCooldownDuration = 100
|
scene.grenadeCooldownDuration = 100
|
||||||
scene.progressBarMax = 100
|
scene.progressBarMax = 100
|
||||||
|
|
||||||
|
scene.autoReload = false
|
||||||
|
scene.reloadProgress = 0
|
||||||
|
scene.crankSensitivity = 0.2
|
||||||
|
|
||||||
scene.availableGrenades = 8
|
scene.availableGrenades = 8
|
||||||
|
|
||||||
|
scene.enemies = {}
|
||||||
|
|
||||||
|
scene.enemySpawnTimer = nil
|
||||||
|
scene.enemySpawnInterval = 1000
|
||||||
|
scene.maxEnemies = 5
|
||||||
|
scene.nextEnemyIndex = 1
|
||||||
|
scene.minSpawnDelay = 500
|
||||||
|
scene.maxSpawnDelay = 3500
|
||||||
|
|
||||||
BomberScene.instance = self
|
BomberScene.instance = self
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -63,15 +81,21 @@ scene.inputHandler = {
|
|||||||
scene.progressBar:set(0)
|
scene.progressBar:set(0)
|
||||||
scene.progressBar:setVisible(true)
|
scene.progressBar:setVisible(true)
|
||||||
scene.availableGrenades = scene.availableGrenades - 1
|
scene.availableGrenades = scene.availableGrenades - 1
|
||||||
|
|
||||||
|
scene.dropSound:play()
|
||||||
|
|
||||||
scene.grenadeCooldownTimer = playdate.timer.new(scene.grenadeCooldownDuration, function()
|
if scene.autoReload then
|
||||||
scene.grenadeCooldown = false
|
scene.grenadeCooldownTimer = playdate.timer.new(scene.grenadeCooldownDuration, function()
|
||||||
scene.progressBar:setVisible(false)
|
scene.grenadeCooldown = false
|
||||||
end)
|
scene.progressBar:setVisible(false)
|
||||||
|
end)
|
||||||
scene.grenadeCooldownTimer.updateCallback = function(timer)
|
|
||||||
local percentage = (scene.grenadeCooldownDuration - timer.timeLeft) / scene.grenadeCooldownDuration * scene.progressBarMax
|
scene.grenadeCooldownTimer.updateCallback = function(timer)
|
||||||
scene.progressBar:set(percentage)
|
local percentage = (scene.grenadeCooldownDuration - timer.timeLeft) / scene.grenadeCooldownDuration * scene.progressBarMax
|
||||||
|
scene.progressBar:set(percentage)
|
||||||
|
end
|
||||||
|
else
|
||||||
|
scene.reloadProgress = 0
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -81,6 +105,9 @@ function scene:enter()
|
|||||||
scene.super.enter(self)
|
scene.super.enter(self)
|
||||||
Noble.Input.setHandler(scene.inputHandler)
|
Noble.Input.setHandler(scene.inputHandler)
|
||||||
scene.crosshair = MovableCrosshair(100, 100)
|
scene.crosshair = MovableCrosshair(100, 100)
|
||||||
|
|
||||||
|
scene:scheduleNextEnemySpawn()
|
||||||
|
NoiseAnimation(200, 120)
|
||||||
end
|
end
|
||||||
|
|
||||||
function scene:start()
|
function scene:start()
|
||||||
@@ -91,23 +118,81 @@ end
|
|||||||
|
|
||||||
function scene:update()
|
function scene:update()
|
||||||
scene.super.update(self)
|
scene.super.update(self)
|
||||||
|
|
||||||
|
if scene.grenadeCooldown and not scene.autoReload and not playdate.isCrankDocked() then
|
||||||
|
local change = playdate.getCrankChange()
|
||||||
|
|
||||||
|
if change > 0 or change < 0 then
|
||||||
|
scene.reloadProgress = scene.reloadProgress + (change * scene.crankSensitivity)
|
||||||
|
if scene.reloadProgress > scene.progressBarMax then
|
||||||
|
scene.reloadProgress = scene.progressBarMax
|
||||||
|
|
||||||
|
scene.grenadeCooldown = false
|
||||||
|
scene.progressBar:setVisible(false)
|
||||||
|
end
|
||||||
|
|
||||||
|
scene.progressBar:set(scene.reloadProgress)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
Noble.Text.draw(scene.availableGrenades .. "x", 10, 210, Noble.Text.ALIGN_LEFT, false, font)
|
Noble.Text.draw(scene.availableGrenades .. "x", 10, 210, Noble.Text.ALIGN_LEFT, false, font)
|
||||||
|
|
||||||
if scene.availableGrenades <= 0 then
|
if scene.availableGrenades <= 0 then
|
||||||
Noble.Text.draw("No grenades left", 200, 110, Noble.Text.ALIGN_CENTER, false, font)
|
Noble.Text.draw("No grenades left", 200, 110, Noble.Text.ALIGN_CENTER, false, font)
|
||||||
scene.crosshair:setVisible(false)
|
scene.crosshair:setVisible(false)
|
||||||
end
|
scene.progressBar:setVisible(false)
|
||||||
|
elseif playdate.isCrankDocked() then
|
||||||
if playdate.isCrankDocked() then
|
|
||||||
Noble.Text.draw("Crank it to reload!", 200, 110, Noble.Text.ALIGN_CENTER, false, font)
|
Noble.Text.draw("Crank it to reload!", 200, 110, Noble.Text.ALIGN_CENTER, false, font)
|
||||||
playdate.ui.crankIndicator:draw()
|
playdate.ui.crankIndicator:draw()
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
-- TODO: to reset grenades spin crank
|
function scene:spawnEnemies()
|
||||||
-- TODO: random spawn of enemies
|
local activeEnemies = 0
|
||||||
|
|
||||||
|
for i = 1, #scene.enemies do
|
||||||
|
if scene.enemies[i] and not scene.enemies[i].removed then
|
||||||
|
activeEnemies = activeEnemies + 1
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
if activeEnemies < self.maxEnemies then
|
||||||
|
scene.enemies[scene.nextEnemyIndex] = Enemy(math.random(30, 370), -20)
|
||||||
|
scene.nextEnemyIndex = scene.nextEnemyIndex + 1
|
||||||
|
end
|
||||||
|
|
||||||
|
scene:scheduleNextEnemySpawn()
|
||||||
|
end
|
||||||
|
|
||||||
|
function scene:scheduleNextEnemySpawn()
|
||||||
|
local delay = math.random(scene.minSpawnDelay, scene.maxSpawnDelay)
|
||||||
|
scene.enemySpawnTimer = playdate.timer.new(delay, function()
|
||||||
|
scene:spawnEnemies()
|
||||||
|
end)
|
||||||
|
end
|
||||||
|
|
||||||
|
function scene:finish()
|
||||||
|
scene.themeSound:stop()
|
||||||
|
scene.enemySpawnTimer:remove()
|
||||||
|
for i = 1, #scene.enemies do
|
||||||
|
if scene.enemies[i] then
|
||||||
|
scene.enemies[i]:remove()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
scene.enemies = {}
|
||||||
|
if scene.progressBar then
|
||||||
|
scene.progressBar:remove()
|
||||||
|
end
|
||||||
|
scene.progressBar = nil
|
||||||
|
if scene.grenadeCooldownTimer then
|
||||||
|
scene.grenadeCooldownTimer:remove()
|
||||||
|
end
|
||||||
|
scene.grenadeCooldownTimer = nil
|
||||||
|
scene.crosshair:remove()
|
||||||
|
scene.crosshair = nil
|
||||||
|
BomberScene.instance = nil
|
||||||
|
end
|
||||||
|
|
||||||
-- TODO: random spawn some decorations
|
-- TODO: random spawn some decorations
|
||||||
-- TODO: add some music
|
|
||||||
-- TODO: add some sound effects
|
|
||||||
-- TODO: add clouds or smoke
|
-- TODO: add clouds or smoke
|
||||||
-- TODO: random disactivate granades
|
-- TODO: random disactivate granades
|
||||||
94
source/scripts/bomber/enemy.lua
Normal file
@@ -0,0 +1,94 @@
|
|||||||
|
Enemy = {}
|
||||||
|
class('Enemy').extends(NobleSprite)
|
||||||
|
|
||||||
|
function Enemy:init(x,y)
|
||||||
|
Enemy.super.init(self)
|
||||||
|
self:moveTo(x, y)
|
||||||
|
self:setZIndex(4)
|
||||||
|
self:add(x,y)
|
||||||
|
self.markImage = Graphics.image.new("assets/sprites/enemy"..math.random(1,2)) -- TODO: make it random
|
||||||
|
self.deadImage = Graphics.image.new("assets/sprites/enemy1_3")
|
||||||
|
self.hitSound = playdate.sound.fileplayer.new("assets/audio/hit1")
|
||||||
|
self:setImage(self.markImage)
|
||||||
|
self.removed = false
|
||||||
|
self:setGroups(CollideGroups.enemy)
|
||||||
|
self:setCollidesWithGroups({
|
||||||
|
CollideGroups.granade,
|
||||||
|
CollideGroups.enemy
|
||||||
|
})
|
||||||
|
self:setCollideRect(-6, -6, 46, 46)
|
||||||
|
self:setSize(32, 32)
|
||||||
|
|
||||||
|
self.vx = 0
|
||||||
|
self.vy = 0
|
||||||
|
self.isDying = false
|
||||||
|
self.friction = 0.95
|
||||||
|
end
|
||||||
|
|
||||||
|
function Enemy:update()
|
||||||
|
if not BomberScene.instance then return end
|
||||||
|
local speed = 0
|
||||||
|
|
||||||
|
if self.isDying then
|
||||||
|
self.vx = self.vx * self.friction
|
||||||
|
self.vy = self.vy * self.friction
|
||||||
|
|
||||||
|
self:moveBy(self.vx, self.vy + BomberScene.instance.scrollSpeed)
|
||||||
|
|
||||||
|
if math.abs(self.vx) < 0.1 and math.abs(self.vy) < 0.1 then
|
||||||
|
self.isDying = false
|
||||||
|
self.removed = true
|
||||||
|
end
|
||||||
|
elseif not self.removed then
|
||||||
|
speed = math.random(0, 7)/10
|
||||||
|
self:moveBy(0, BomberScene.instance.scrollSpeed + speed)
|
||||||
|
else
|
||||||
|
self:moveBy(0, BomberScene.instance.scrollSpeed)
|
||||||
|
end
|
||||||
|
|
||||||
|
local actualX, actualY, collisions, numberOfCollisions = self:checkCollisions(self.x, self.y)
|
||||||
|
|
||||||
|
if numberOfCollisions > 0 then
|
||||||
|
for i, collision in ipairs(collisions) do
|
||||||
|
if collision.other:getTag() == 154 and collision.other.currentRadius <= 0.05 and not self.isDying then
|
||||||
|
print("Collision with granade")
|
||||||
|
self:setImage(self.deadImage)
|
||||||
|
self.hitSound:play()
|
||||||
|
self:applyExplosionForce(collision.other.x, collision.other.y)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.y > 240 + 10 then
|
||||||
|
if not self.removed then
|
||||||
|
print("Removing enemy")
|
||||||
|
self:remove()
|
||||||
|
self:superRemove()
|
||||||
|
self.removed = true
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function Enemy:applyExplosionForce(explosionX, explosionY)
|
||||||
|
local dx = self.x - explosionX
|
||||||
|
local dy = self.y - explosionY
|
||||||
|
|
||||||
|
local dist = math.sqrt(dx*dx + dy*dy)
|
||||||
|
if dist == 0 then dist = 0.001 end
|
||||||
|
|
||||||
|
dx = dx / dist
|
||||||
|
dy = dy / dist
|
||||||
|
|
||||||
|
local maxForce = 5
|
||||||
|
local maxRadius = 100
|
||||||
|
|
||||||
|
local force = maxForce * (1 - math.min(dist, maxRadius) / maxRadius)
|
||||||
|
force = math.max(force, 1)
|
||||||
|
|
||||||
|
self.vx = dx * force
|
||||||
|
self.vy = dy * force * 0.5
|
||||||
|
|
||||||
|
self.isDying = true
|
||||||
|
|
||||||
|
self:setRotation(math.random() * 360)
|
||||||
|
end
|
||||||
@@ -4,7 +4,7 @@ class('ExplosionMark').extends(NobleSprite)
|
|||||||
function ExplosionMark:init(x, y)
|
function ExplosionMark:init(x, y)
|
||||||
ExplosionMark.super.init(self)
|
ExplosionMark.super.init(self)
|
||||||
self.id = math.random(1, 2)
|
self.id = math.random(1, 2)
|
||||||
self.markImage = Graphics.image.new("assets/sprites/boomSplash" .. self.id) -- TODO: make it random
|
self.markImage = Graphics.image.new("assets/sprites/boomSplash" .. self.id)
|
||||||
self:setImage(self.markImage)
|
self:setImage(self.markImage)
|
||||||
self:moveTo(x, y)
|
self:moveTo(x, y)
|
||||||
self:setZIndex(5)
|
self:setZIndex(5)
|
||||||
@@ -12,6 +12,7 @@ function ExplosionMark:init(x, y)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function ExplosionMark:update()
|
function ExplosionMark:update()
|
||||||
|
if not BomberScene.instance then return end
|
||||||
self:moveBy(0, BomberScene.instance.scrollSpeed)
|
self:moveBy(0, BomberScene.instance.scrollSpeed)
|
||||||
|
|
||||||
if self.y > 240 + 32 then
|
if self.y > 240 + 32 then
|
||||||
|
|||||||
@@ -1,19 +1,6 @@
|
|||||||
Granade = {}
|
Granade = {}
|
||||||
class('Granade').extends(NobleSprite)
|
class('Granade').extends(NobleSprite)
|
||||||
|
|
||||||
local function screenShake(shakeTime, shakeMagnitude)
|
|
||||||
local shakeTimer = playdate.timer.new(shakeTime, shakeMagnitude, 0)
|
|
||||||
shakeTimer.updateCallback = function(timer)
|
|
||||||
local magnitude = math.floor(timer.value)
|
|
||||||
local shakeX = math.random(-magnitude, magnitude)
|
|
||||||
local shakeY = math.random(-magnitude, magnitude)
|
|
||||||
playdate.display.setOffset(shakeX, shakeY)
|
|
||||||
end
|
|
||||||
shakeTimer.timerEndedCallback = function()
|
|
||||||
playdate.display.setOffset(0, 0)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
function Granade:init(x, y)
|
function Granade:init(x, y)
|
||||||
Granade.super.init(self)
|
Granade.super.init(self)
|
||||||
|
|
||||||
@@ -21,12 +8,12 @@ function Granade:init(x, y)
|
|||||||
self.currentRadius = self.initialRadius
|
self.currentRadius = self.initialRadius
|
||||||
self.shrinkRate = 0.2
|
self.shrinkRate = 0.2
|
||||||
|
|
||||||
random = math.random(1, 4)
|
local random = math.random(1, 4)
|
||||||
self.boomSound = playdate.sound.fileplayer.new("assets/audio/boom" .. random)
|
self.boomSound = playdate.sound.fileplayer.new("assets/audio/boom" .. random)
|
||||||
self.boomSound:setVolume(0.5)
|
self.boomSound:setVolume(0.5)
|
||||||
|
|
||||||
self.isActive = true
|
self.isActive = true
|
||||||
-- Variables for random movement
|
|
||||||
self.randomMovementTimer = 0
|
self.randomMovementTimer = 0
|
||||||
self.randomXVelocity = 0
|
self.randomXVelocity = 0
|
||||||
self.randomYVelocity = 0
|
self.randomYVelocity = 0
|
||||||
@@ -35,8 +22,15 @@ function Granade:init(x, y)
|
|||||||
self.spriteSize = size
|
self.spriteSize = size
|
||||||
self:setSize(size, size)
|
self:setSize(size, size)
|
||||||
self:moveTo(x, y)
|
self:moveTo(x, y)
|
||||||
|
self:setZIndex(10)
|
||||||
|
self:setTag(154)
|
||||||
self:setCenter(0.5, 0.5)
|
self:setCenter(0.5, 0.5)
|
||||||
|
self:setGroups(CollideGroups.granade)
|
||||||
|
self:setCollidesWithGroups({
|
||||||
|
CollideGroups.enemy
|
||||||
|
})
|
||||||
|
self:setCollideRect(0, 0, self:getSize())
|
||||||
|
|
||||||
print("Granade init")
|
print("Granade init")
|
||||||
print(self.x, self.y)
|
print(self.x, self.y)
|
||||||
self:add(x, y)
|
self:add(x, y)
|
||||||
|
|||||||
@@ -4,28 +4,25 @@ class('MovableCrosshair').extends(playdate.graphics.sprite)
|
|||||||
function MovableCrosshair:init()
|
function MovableCrosshair:init()
|
||||||
MovableCrosshair.super.init(self)
|
MovableCrosshair.super.init(self)
|
||||||
|
|
||||||
-- Parameters for crosshair
|
|
||||||
self.lineLength = 10
|
self.lineLength = 10
|
||||||
self.gapSize = 3
|
self.gapSize = 3
|
||||||
|
|
||||||
-- Parameters for movement
|
|
||||||
self.baseX = 200
|
self.baseX = 200
|
||||||
self.baseY = 150
|
self.baseY = 150
|
||||||
self.moveRadius = 2
|
self.moveRadius = 2
|
||||||
self.moveSpeed = 2
|
self.moveSpeed = 2.3
|
||||||
self.time = 0
|
self.time = 0
|
||||||
|
|
||||||
-- Calculate size based on crosshair dimensions
|
|
||||||
local totalSize = (self.lineLength + self.gapSize) * 2 + 10
|
local totalSize = (self.lineLength + self.gapSize) * 2 + 10
|
||||||
self:setSize(totalSize, totalSize)
|
self:setSize(totalSize, totalSize)
|
||||||
|
|
||||||
-- Set the drawing offset to middle of sprite
|
|
||||||
self.drawOffsetX = totalSize / 2
|
self.drawOffsetX = totalSize / 2
|
||||||
self.drawOffsetY = totalSize / 2
|
self.drawOffsetY = totalSize / 2
|
||||||
|
|
||||||
self:add(self.baseX, self.baseY)
|
self:add(self.baseX, self.baseY)
|
||||||
self:setCenter(0.5, 0.5)
|
self:setCenter(0.5, 0.5)
|
||||||
self:markDirty()
|
self:markDirty()
|
||||||
|
self:setZIndex(11)
|
||||||
end
|
end
|
||||||
|
|
||||||
function MovableCrosshair:update()
|
function MovableCrosshair:update()
|
||||||
@@ -66,24 +63,24 @@ end
|
|||||||
|
|
||||||
function MovableCrosshair:moveUp()
|
function MovableCrosshair:moveUp()
|
||||||
if self.baseY > 5 then
|
if self.baseY > 5 then
|
||||||
self.baseY = self.baseY - 1
|
self.baseY = self.baseY - self.moveSpeed
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function MovableCrosshair:moveDown()
|
function MovableCrosshair:moveDown()
|
||||||
if self.baseY < 235 then
|
if self.baseY < 235 then
|
||||||
self.baseY = self.baseY + 1
|
self.baseY = self.baseY + self.moveSpeed
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function MovableCrosshair:moveLeft()
|
function MovableCrosshair:moveLeft()
|
||||||
if self.baseX > 5 then
|
if self.baseX > 5 then
|
||||||
self.baseX = self.baseX - 1
|
self.baseX = self.baseX - self.moveSpeed
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function MovableCrosshair:moveRight()
|
function MovableCrosshair:moveRight()
|
||||||
if self.baseX < 395 then
|
if self.baseX < 395 then
|
||||||
self.baseX = self.baseX + 1
|
self.baseX = self.baseX + self.moveSpeed
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
36
source/scripts/bomber/noiseAnimation.lua
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
NoiseAnimation = {}
|
||||||
|
class('NoiseAnimation').extends(NobleSprite)
|
||||||
|
|
||||||
|
function NoiseAnimation:init(x, y)
|
||||||
|
NoiseAnimation.super.init(self, "assets/sprites/noise", true)
|
||||||
|
self.animation:addState("run", 2, 11)
|
||||||
|
self.animation:addState("idle", 1, 1)
|
||||||
|
self.animation.run.frameDuration = 2.5
|
||||||
|
self.animation:setState("idle")
|
||||||
|
self:setZIndex(ZIndex.foreground)
|
||||||
|
self:setSize(400, 240)
|
||||||
|
self:add()
|
||||||
|
self:moveTo(x, y)
|
||||||
|
|
||||||
|
self.state = "idle"
|
||||||
|
self.idleFrames = 0
|
||||||
|
end
|
||||||
|
|
||||||
|
function NoiseAnimation:update()
|
||||||
|
if self.state == "idle" then
|
||||||
|
self.idleFrames -= 1
|
||||||
|
if self.idleFrames <= 0 then
|
||||||
|
self.state = "run"
|
||||||
|
self.animation:setState("run")
|
||||||
|
end
|
||||||
|
else
|
||||||
|
local r = math.random(0)
|
||||||
|
if r < 0.01 then
|
||||||
|
self.state = "idle"
|
||||||
|
self.idleFrames = math.random(30, 100)
|
||||||
|
self.animation:setState("idle")
|
||||||
|
else
|
||||||
|
self.animation:setState("run")
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
@@ -2,7 +2,7 @@ PageSprite = {}
|
|||||||
class('PageSprite').extends(NobleSprite)
|
class('PageSprite').extends(NobleSprite)
|
||||||
|
|
||||||
function PageSprite:init(x, y)
|
function PageSprite:init(x, y)
|
||||||
Baleba.super.init(self, "assets/sprites/pages", true)
|
PageSprite.super.init(self, "assets/sprites/pages", true)
|
||||||
self.animation:addState("1", 1, 1)
|
self.animation:addState("1", 1, 1)
|
||||||
self.animation:addState("2", 2, 2)
|
self.animation:addState("2", 2, 2)
|
||||||
self.animation:addState("3", 3, 3)
|
self.animation:addState("3", 3, 3)
|
||||||
|
|||||||
@@ -192,9 +192,6 @@ function Player:handleMovementAndCollisions()
|
|||||||
self:boom()
|
self:boom()
|
||||||
return
|
return
|
||||||
elseif collisionTag == 154 then -- Baleba
|
elseif collisionTag == 154 then -- Baleba
|
||||||
-- if self.debug then TODO: why debug always true?
|
|
||||||
-- return
|
|
||||||
-- end
|
|
||||||
self:boom(collisionObject)
|
self:boom(collisionObject)
|
||||||
return
|
return
|
||||||
elseif collisionTag == 2 then -- Tank
|
elseif collisionTag == 2 then -- Tank
|
||||||
|
|||||||