I'm having trouble getting the crank indicator working.
If I run crankIndicator:start() near the top of my main.lua, and then call crankIndicator:update() in playdate.update() (after updateTimers()), the indicator appears.
but if I move crankIndicator:update() into the update function of one of my classes that extends 'sprite', I can't make the indicator appear.
I know crankIndicator:update() is/should be being called, because I have a print statement just before it.
Are you sure that your sprite's update() method is being called? It will need to be added to the display list via sprite:add() and have updatesEnabled set to true, and you'll need to call sprite.update() (note: dot, not colon) from playdate.update().
I'm having the same problem: crankIndicator inside a class extending sprite, and the crank is not shown.
I solved it with a messy workaround: I sent an event from the sprite to the main.lua asking to show the indicator.
main.lua extract
local showCrankAlertAskedForShowing = false
local function initialize()
player = Player()
playdate.ui.crankIndicator:start()
player.onShouldCrankIndicatorChangeCallback = function (shouldShow)
showCrankAlertAskedForShowing = shouldShow
end
end
function playdate.update()
playdate.timer.updateTimers()
gfx.sprite.update()
if playdate.isCrankDocked() and showCrankAlertAskedForShowing then
playdate.ui.crankIndicator:update()
end
end
player.lua extract
class('Player').extends(gfx.sprite)
function Player:init()
-- i removed some standard code from this init
self.onShouldCrankIndicatorChangeCallback = nil
end
function Player:update()
Player.super.update(self)
local crankRequired = false
--I am hiding some code here
if myCustomConditionThatRequiresCrank then
crankRequired = true
end
--si la palanca esta escondida y deberia usarse, solicitamos que se envie la alerta
if self.onShouldCrankIndicatorChangeCallback ~= nil then
self.onShouldCrankIndicatorChangeCallback(crankRequired)
end
end
I found the issue, but not sure how to solve it without using a variable like others have mentioned.
Works:
function playdate.update()
playdate.timer.updateTimers()
gfx.sprite.update()
playdate.ui.crankIndicator:update()
end
Doesn't Work:
function playdate.update()
playdate.timer.updateTimers()
playdate.ui.crankIndicator:update()
gfx.sprite.update()
end
So this means that the crankIndicator can't be invoked from within the sprite update method. It needs to be invoked after the update loop. So, the easiest way is to use a global variable as indicated. The interesting thing is that the screen is being updated if you look at the simulator, but it must be being drawn "underneath" all the sprites on screen so you can't see the UI. This is why it must be called outside the update loop so its ui is drawn on top of all sprites. I'm still investigating the source code to see if there's a way around this issue.
Good catch. I just added support for the crank indicator to my Plupdate toybox. This lets you display the indicator with a single call to Plupdate.showCrankIndicator() (no need to call playdate.ui.crankIndicator:start()) and that can be called from anywhere in your code, even a sprite update method.
Great catch, ManOVision! I was tearing my hair out trying to figure out why the indicator was not showing up despite following everything in the documentation, and it turns out it was because I was calling gfx.sprite.update after the crankIndicator:update() like you have there. That seems like something that should be added to the documentation if it's necessary...