Start up some simple baserunning.
This commit is contained in:
parent
5fc72c46fe
commit
5493f350df
|
@ -1 +1,2 @@
|
|||
*.pdx
|
||||
.idea
|
||||
|
|
Binary file not shown.
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.8 KiB |
Binary file not shown.
After Width: | Height: | Size: 11 KiB |
Binary file not shown.
After Width: | Height: | Size: 711 B |
125
src/main.lua
125
src/main.lua
|
@ -7,9 +7,16 @@ import 'CoreLibs/ui.lua'
|
|||
local gfx = playdate.graphics
|
||||
playdate.display.setRefreshRate(50)
|
||||
gfx.setBackgroundColor(gfx.kColorWhite)
|
||||
playdate.setMenuImage(gfx.image.new("images/game/menu-image.png"))
|
||||
|
||||
local grassBackground = gfx.image.new("images/game/grass.png")
|
||||
local playerImage = gfx.image.new("images/game/player.png")
|
||||
local playerHighHat = gfx.image.new("images/game/player.png")
|
||||
local playerLowHat = gfx.image.new("images/game/player-lowhat.png")
|
||||
local playerImage = playerHighHat
|
||||
local secPerFrame = 0.1
|
||||
local playerFrameElapsed = 0
|
||||
|
||||
local backgroundPan = -240
|
||||
|
||||
local pitchFlyTimeMs = 2500
|
||||
local ballStartY, endY = 90, 250
|
||||
|
@ -26,7 +33,6 @@ local batBaseX, batBaseY = centerX - 34, 215
|
|||
local batLength = 45
|
||||
|
||||
local ballY = ballStartY
|
||||
local lastBallY = ballY
|
||||
local ballX = 200
|
||||
local ballVelX, ballVelY = 0, 0
|
||||
local ballSize = 6
|
||||
|
@ -34,7 +40,6 @@ local ballSize = 6
|
|||
local batTipX = 0
|
||||
local batTipY = 0
|
||||
|
||||
local hit = false
|
||||
local MODES = {
|
||||
batting = 0,
|
||||
running = 1
|
||||
|
@ -80,13 +85,17 @@ function resetFielderPositions()
|
|||
end
|
||||
resetFielderPositions()
|
||||
|
||||
local playerStartingX = basePositions.home.x - 40
|
||||
local playerStartingY = basePositions.home.y - 3
|
||||
local player = {
|
||||
x = basePositions.home.x - 40,
|
||||
y = basePositions.home.y - 3,
|
||||
x = playerStartingX,
|
||||
y = playerStartingY,
|
||||
nextBase = nil,
|
||||
prevBase = nil,
|
||||
}
|
||||
|
||||
local runners = { }
|
||||
|
||||
function hitBall(destX, destY, hitFlyTime)
|
||||
ballSizeAnimator:reset(ballSizeMs)
|
||||
hitAnimatorY = gfx.animator.new(hitFlyTime, ballY, destY, playdate.easingFunctions.outQuint)
|
||||
|
@ -100,13 +109,22 @@ function throwBall(destX, destY)
|
|||
hitAnimatorX = gfx.animator.new(throwFlyTime, ballX, destX, playdate.easingFunctions.linear)
|
||||
end
|
||||
|
||||
function getNextThrowTarget()
|
||||
return basePositions.first.x, basePositions.first.y
|
||||
end
|
||||
|
||||
function pitch()
|
||||
pitchAnimator:reset()
|
||||
resetFielderPositions()
|
||||
ballVelX = 0
|
||||
ballVelY = 0
|
||||
ballX = 200
|
||||
hit = false
|
||||
currentMode = MODES.batting
|
||||
|
||||
-- TODO: Add new runners, instead
|
||||
runners = {}
|
||||
player.x = playerStartingX
|
||||
player.y = playerStartingY
|
||||
end
|
||||
|
||||
function playdate.AButtonDown()
|
||||
|
@ -131,6 +149,7 @@ end
|
|||
|
||||
local pitchClockSec = 99
|
||||
local elapsedTime = 0
|
||||
local crankChange
|
||||
|
||||
function ballPassedThruBat(ballX, ballY, batBaseX, batBaseY, batTipX, batTipY)
|
||||
-- This check currently assumes right-handedness.
|
||||
|
@ -152,22 +171,21 @@ function ballPassedThruBat(ballX, ballY, batBaseX, batBaseY, batTipX, batTipY)
|
|||
end
|
||||
|
||||
function updateInfield()
|
||||
if not hit or ballDestX == nil or ballDestY == nil then
|
||||
if ballDestX == nil or ballDestY == nil then
|
||||
return
|
||||
end
|
||||
|
||||
local fielderSpeed = 50
|
||||
local fielderSpeed = 40
|
||||
for title,fielder in pairs(fielders) do
|
||||
if fielder.targetX ~= nil and fielder.targetY ~= nil then
|
||||
local distance, a, b = distanceBetween(fielder.x, fielder.y, fielder.targetX, fielder.targetY)
|
||||
local normalizer = fielderSpeed / distance
|
||||
local x, y, distance = normalizeVector(fielder.x, fielder.y, fielder.targetX, fielder.targetY)
|
||||
|
||||
if distance > 1 then
|
||||
fielder.x -= a * normalizer * deltaTime
|
||||
fielder.y -= b * normalizer * deltaTime
|
||||
fielder.x -= x * fielderSpeed * deltaTime
|
||||
fielder.y -= y * fielderSpeed * deltaTime
|
||||
else
|
||||
if fielder.onArrive then
|
||||
fielder.onArrive(fielder.targetX, fielder.targetY)
|
||||
fielder.onArrive()
|
||||
end
|
||||
fielder.targetX = nil
|
||||
fielder.targetY = nil
|
||||
|
@ -176,6 +194,36 @@ function updateInfield()
|
|||
end
|
||||
end
|
||||
|
||||
function updateRunners()
|
||||
local runnerSpeed = 20
|
||||
for i,runner in pairs(runners) do
|
||||
if runner.nextBase then
|
||||
local nb = runner.nextBase
|
||||
local x, y, distance = normalizeVector(runner.x, runner.y, nb.x, nb.y)
|
||||
if distance > 1 then
|
||||
local mult = 1
|
||||
if crankChange < 0 then
|
||||
mult = -1
|
||||
end
|
||||
mult = (mult * runnerSpeed * deltaTime) + (crankChange / 20)
|
||||
runner.x -= x * mult
|
||||
runner.y -= y * mult
|
||||
else
|
||||
if runner.onArrive then
|
||||
runner.onArrive()
|
||||
end
|
||||
runner.targetX = nil
|
||||
runner.targetY = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function normalizeVector(x1, y1, x2, y2)
|
||||
local distance, a, b = distanceBetween(x1, y1, x2, y2)
|
||||
return a / distance, b / distance, distance
|
||||
end
|
||||
|
||||
function distanceBetween(x1, y1, x2, y2)
|
||||
local a = x1 - x2
|
||||
local b = y1 - y2
|
||||
|
@ -200,6 +248,14 @@ function getNearestFielder(x, y)
|
|||
return nearestFielder
|
||||
end
|
||||
|
||||
function ballIsBeingThrown()
|
||||
return false
|
||||
end
|
||||
|
||||
function throwArrivedBeforeRunner()
|
||||
return false
|
||||
end
|
||||
|
||||
function updateGameState()
|
||||
deltaTime = playdate.getElapsedTime()
|
||||
playdate.resetElapsedTime()
|
||||
|
@ -210,7 +266,7 @@ function updateGameState()
|
|||
pitch()
|
||||
end
|
||||
|
||||
if hit then
|
||||
if currentMode == MODES.running then
|
||||
ballX = hitAnimatorX:currentValue()
|
||||
ballY = hitAnimatorY:currentValue()
|
||||
ballSize = ballSizeAnimator:currentValue()
|
||||
|
@ -224,7 +280,7 @@ function updateGameState()
|
|||
batTipY = batBaseY + (batLength * math.cos(batAngle))
|
||||
|
||||
crankChange, acceleratedChange = playdate.getCrankChange()
|
||||
if hit == false and acceleratedChange >= 0 and
|
||||
if currentMode == MODES.batting and acceleratedChange >= 0 and
|
||||
ballPassedThruBat(ballX, ballY, batBaseX, batBaseY, batTipX, batTipY) then
|
||||
ballAngle = batAngle + math.rad(90)
|
||||
|
||||
|
@ -242,22 +298,26 @@ function updateGameState()
|
|||
chasingFielder.targetX = ballDestX
|
||||
chasingFielder.targetY = ballDestY
|
||||
chasingFielder.onArrive = function()
|
||||
throwBall(basePositions.first.x, basePositions.first.y)
|
||||
throwBall(getNextThrowTarget())
|
||||
chasingFielder.onArrive = nil
|
||||
end
|
||||
fielders.first.targetX = basePositions.first.x
|
||||
fielders.first.targetY = basePositions.first.y
|
||||
hit = true
|
||||
currentMode = MODES.running
|
||||
player.nextBase = basePositions.first
|
||||
runners[#runners+1] = player
|
||||
end
|
||||
lastBallY = ballY
|
||||
|
||||
updateInfield()
|
||||
if currentMode == MODES.running then
|
||||
updateRunners()
|
||||
updateInfield()
|
||||
end
|
||||
end
|
||||
|
||||
function playdate.update()
|
||||
updateGameState()
|
||||
|
||||
grassBackground:draw(0, 0)
|
||||
playerImage:draw(player.x, player.y)
|
||||
grassBackground:draw(0, backgroundPan)
|
||||
|
||||
gfx.setColor(gfx.kColorBlack)
|
||||
gfx.setLineWidth(2)
|
||||
|
@ -268,9 +328,30 @@ function playdate.update()
|
|||
end
|
||||
|
||||
gfx.setLineWidth(5)
|
||||
gfx.drawLine(batBaseX, batBaseY, batTipX, batTipY)
|
||||
|
||||
if currentMode == MODES.batting then
|
||||
gfx.drawLine(batBaseX, batBaseY, batTipX, batTipY)
|
||||
end
|
||||
|
||||
if playdate.isCrankDocked() then
|
||||
playdate.ui.crankIndicator:draw()
|
||||
end
|
||||
|
||||
playerImage:draw(player.x, player.y)
|
||||
|
||||
-- TODO: Use gfx.animation.blinker instead
|
||||
if currentMode == MODES.running and playerFrameElapsed > secPerFrame then
|
||||
playerFrameElapsed = 0
|
||||
if playerImage == playerHighHat then
|
||||
playerImage = playerLowHat
|
||||
else
|
||||
playerImage = playerHighHat
|
||||
end
|
||||
else
|
||||
playerFrameElapsed += deltaTime
|
||||
end
|
||||
|
||||
-- for i,runner in pairs(runners) do
|
||||
-- playerImage:draw(runner.x, runner.y)
|
||||
-- end
|
||||
end
|
||||
|
|
Loading…
Reference in New Issue