Limit FPS?

Hey everyone,
is it possible to limit the framerate? The iPad Pro runs draw() 120 times per second, which is great, but I assume it also drains the battery much faster than if it ran at half the framerate instead. Is there a way to determine how often draw() should be called per second?
Thanks in advance :slight_smile:

@Leon You can limit the frame rate with code, but you’re still executing code no matter what you do. So I would say running at 120 or 60 FPS doesn’t matter.

depends what codea does between calls to draw, doesn’t it? but i doubt it’d make much difference.

I would say that whatever else is happening on the iPad would have more of an impact on the battery drain than Codea running at less than 120 FPS. I usually close and remove everything in the background that I’m not using. My iPad case also turns off the screen when it’s closed. I’ll even put the iPad in airplane mode so it’s not constantly doing internet communication.

I‘m developing a game for iOS and calling draw() 120 timed instead of 60 timed a second definitely drains the battery more :frowning: A lot of sprites have to be drawn, I use a lot of shaders and there are a lot of calculations going on in the background. I have already taken measures to draw as few sprites and update as few things as possible. However, using draw() at half the framerate would prevent the iPad/iPhone from overheating and generally lead to better battery life.
Can you limit the Framerate in Xcode or will Codea always execute code at the maximum framerate?

I looked up 120 FPS on the iPad and there’s a setting where you can limit the FPS. Since I don’t have 120fps on my iPad Pro, I don’t have that option so I couldn’t try it.

Yes, but I’d prefer to limit the number of times draw() is called by Codea. I’d like to publish my game on the AppStore some day and I can’t expect every user to change the settings just for playing the game.

Here’s a way to run the draw function every other time. So your 120 FPS will be 60 FPS. Maybe in a future release, @Simeon can add something to allow the number of times draw is called to be changed. Maybe there’s something already. I remember @RonJeffries talking about 120 FPS.

PS. As a side note, I don’t understand how Codea running at 120 FPS is going to overheat or drain the battery faster. The iPad is running at 120 FPS for everything. Just looking at the screen showing your loaded apps is running at 120 FPS. So Codea calling the draw function at 120 times per second is no different than any other app that’s displaying anything.

Or does the iPad run everything at 60 FPS except any app that can run at 120 FPS. I don’t know, my iPad is only 60 FPS.

displayMode(STANDARD)

function setup()
    fpsLimit=0   
    y1=0
end

function draw()
    if slowFPS() then return end
    
    background(0)
    sprite(asset.builtin.Planet_Cute.Character_Horn_Girl,WIDTH/2,y1)
    y1=y1+1
end

function slowFPS()
    fpsLimit=(fpsLimit+1)%1000
    if fpsLimit%2==0 then
        return true
    end
end

@dave1707 Thanks, I will give this a try :slight_smile:

Maybe I’m wrong, but as far as I know, half the framerate typically means that an app is less expensive on battery life since only half the number of calculations have to be made. I also thought that the iPad’s refresh rate depends on the app. When an app doesn’t support 120 FPS, the iPad limits the refresh rate and therefore saves battery.

Thanks for your help :slight_smile:

@Leon My iPad are only 60fps, and looking on the internet doesn’t give much info about the 120fps except saying that fortnite runs at 120fps. So I guess if the display and code is running twice as fast, then that could heat things up and drain the battery. I can’t find any information that gives a decent answer.

@Leon I don’t know if you were able to use the code above, but here’s a more compact version to skip a draw cycle. This just uses 2 lines with no setup code.

function draw()
    skip=not skip 
    if skip then return end
    

The iPad definitely heats up more when it’s running something intense. I suspect that it has some kind of sleep or idle mode when waiting for something to do. I don’t know what Codea does between calls to draw. It could be spinning in a loop, but I think it might have a way to go to sleep.

@Leon @dave1707 There will definitely be higher battery consumption at 120fps simply because more work is being done. If you skip every second frame you will reduce power consumption but it will still be doing frame buffer swaps. We do have the ability to lock it to a lower framerate (15,20,30,60) so we just have to provide an API for doing that in Codea itself.

@John Thanks for the clarification! It would be amazing if you could provide an API for that :slight_smile:

@John fwiw I implemented something like this previously. Immediately before swapping the backbuffers I check that a specific amount of time has passed since the last buffer swap, if not I do a short sleep (with a semaphore) inside a loop until the necessary time has elapsed.

Now the juicy bit. The specific time that needs to pass is calculated every processed frame. The various game systems request a minimum frame rate required for their system to look and behave correctly. So for instance, if a video is playing we may require a minimum 30fps. If no video is playing but we’re sat on a mostly static menu, we can get away with 1fps.

If multiple systems request different frame rates, the highest requested is chosen so everything works correctly.

Unfortunately, running at 1fps does have its issues with input latency so whenever an input is detected the waiting thread is notified and stops sleeping, allowing it to process the input ASAP.

This allows for a very simple API where systems only need to call a single function like ‘requestFPS(30)’ each frame when required.

I hope this provides some inspiration for what has proven to be quite a neat little system imo!

That sounds like a very interesting solution :slight_smile:

@Simeon @John Could you provide an API for locking Codea to a lower framerate in a future update?

@John @Simeon Hope not to bother you, I would like to ask whether you have already tried implementing an API for it. Thanks for any response :slight_smile:

@Elias I would love to get to this for Codea 3.2.6 — at the moment I’m a bit tied up working on the next major feature so I’ve added it to my todo list to revisit

@Simeon Thanks! That’s great :slight_smile:

did this ever get implemented? i’m running into this issue myself, some of my loops run faster at 120, i’d like to lock to 60 but don’t want to implement the skip frame since it would also skip down to 30 on devices at 60