-
Notifications
You must be signed in to change notification settings - Fork 42
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix CPU usage #397
Fix CPU usage #397
Conversation
I also checked having animated terrains on the screen and the CPU usage didn't spike for those. |
|
|
I don't think animated terrain would work with this? But if there's a way to have both, then sure. |
force-pushed to rebase. |
I decided instead of only redrawing dialog when an event happens, to actually delve into the multiline string wrapping that causes the CPU spikes. Because it is still pretty bad if I can get a 60% CPU spike by fiddling with the mouse when multiline text is visible. |
7442136
to
e7d5b4f
Compare
What was holding this up? |
I got confused about the When I get too confused or frustrated I usually switch to other tasks for a while. |
Also caching the line wrapping was making multiline input fields behave VERY wildly, which doesn't feel like a very good priority to fix because I can't think of any multiline input fields in the game. Aren't those all in the scenario editor? |
I don't have a good way set up to profile the code execution. With Xcode I can profile CPU usage over time but I have no way to delve into the spikes and see which code was running at the time. Do you know of a way? |
Yeah, there are no multiline text fields in the game itself, only in the scenario editor. Pretty sure even the character editor doesn't have them.
I'm not very familiar with Xcode profiling, but I thought it had a way to tell you what function was running during a spike… |
Maybe that's possible if you build through Xcode--a lot of debugging features are limited for me because I'm building through scons. Like, I can't browse through the source files to set breakpoints. It's really annoying. I haven't been able to get the xcode build to work for me locally. |
Hmm… I bet there's a way to set up something like a "source mapping" to map the symbol information actually in the file to the source files that Xcode is actually looking at – a scons build would be built from the build directory, so the input source files are actually different, I think. But I'm not sure how you would do that in either lldb or an Xcode scheme… I'd also say it's a bit of a problem that the Xcode build doesn't work for you. Maybe that's something to work out separately. |
Every change in this PR related to CPU has been merged through other ways. I've taken note of the rest of the potentially useful commits, which I will reincorporate in an appropriately-themed future PR. |
We have 3 open issues that reference unreasonably high CPU usage. Using XCode to debug CPU usage, I believe I found all the cases that have been reported and fixed them.
#227 - DialogXMLs with wrapped text are doing all of their processing every time
draw()
is called. So whenever such a dialog is onscreen, CPU usage jumps to about 90% for me until it's closed. I fixed this by only callingdraw()
on frames where an input event occurs. This still will be drawing more than necessary, probably, and a fix could go further by passing aneed_redraw
flag to the event handlers instead of treating any event as a reason to redraw.#321 and #372 - these issues were more vague about which specific game states were using 100% CPU, and asked for a total overhaul of the game loop. From what I can tell, though, CPU spikes in the intro splash screen, when clicking on controls, and when dialogxmls are wrapping text, are the real problems. Theoretically it would be ideal to convert the whole game to an event-responsive code style where CPU usage stays near 0 in between player turns, but I don't think that's really warranted as long as I've actually found the aberrant cases and fixed them.
To fix the mini event loops that every control has in its
handleClick()
method I added an fps_limiter to the method signature and have them finish their frames with it. This required changing an absurd number of function signatures, and at first I thought just making onefps_limiter
global would be better, but I realized one advantage of changing all these function signatures is that it becomes more clear in the code when a subcomponent is expecting to spawn its own internal event loop.