Skip to content
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

Performance problem - hints wanted for differential throttling of render loop / decreased CPU load. #5023

Closed
dgm3333 opened this issue Feb 15, 2022 · 5 comments

Comments

@dgm3333
Copy link

dgm3333 commented Feb 15, 2022

I'm looking for hints on strategies to decrease framerate/CPU utilisation for low-spec PCs without losing responsiveness to user interactions. Reason for the query is as per background section below. I've just updated the code and tested using todays ImGui main branch.

My thoughts are (1/2=easy or 3=hard) - but wondering if anyone has thoughts before I go down any rabbit holes.

  1. Differentially increase or decrease thread priorities - to low most of the time unless it's running a "high frame rate" process - like the geographical module.

  2. Add in a differential sleep period to keep the framerate as low as possible - depending on what process was running and how much user input was being received - this could retrospective monitor the inputs and throttle the render loop depending on what had recently happened.

There are no animations in the app so it should be possible to:-
3a Run a non-graphical monitoring thread to watch for mouse, keyboard activity or a windows redraw call, while
3b. Capture each freshly rendered frame
3c If it's a windows redraw request then just recycle the captured frame
3d. Permanently sleep the render loop until mouse or keyboard input is received then inject this input back into a "normal" rendering loop to refresh the new frame (but I'm not sure how to inject the user action back into the main loop to allow it to be processed as part of the frame.

Or are there other/better options of any simple ways to do any of these using vanilla ImGui?

Background:
I developed a program for use in the NHS (UK health service).
Unfortunately it turns out I my work machine is one of the highest performance PCs in the region (an i7 with 8GB RAM 100GB SSD and no GPU running Win10) and I stupidly omitted to do any performance checks. However I've now found the typical machine (mostly I5s aren't coping and the 10% which are I3s fairly consistently crash. Because the NHS supplies all our computers we aren't allowed to throw them in the nearest rubbish dump or gut them and replace the internals (despite daily requests to do so by the people who have to use them.) I'm thus wondering if there are any options to rescue my ImGui app so it could run on lower spec machine.

On my "high performance" I7 NHS PC loading an ImGui desktop app rendering 12 200x400px image buttons (and doing essentially nothing else) my work machine causes it to increase CPU utilisation from 3% to 25% of the processor and when it's running it takes Microsoft Word approx 90 seconds to load. The task manager monitoring below is purely closing, opening then closing the app again.

In comparison the same app running it's geographical mapping module on my home machine steps the CPU from a baseline of 5% which increases to 9% CPU utilisation when the app is running and rendering ~500k polygons at 4k - the GPU is still sitting at 5% so it's not that it's offloading activity to the GPU either.

image

@sergeyn
Copy link
Contributor

sergeyn commented Feb 15, 2022

I did approach 3 in my pull request long time ago
#3124

what it does is it waits until mouse/keyb or some animation says it wants to update something. If none of these events happen, then no rendering gets triggered.

The branch is quite old , but if there's interest, I could revive it.

Regards

@dgm3333
Copy link
Author

dgm3333 commented Feb 15, 2022

It would seem that something along those lines would enable both the rendering flexibilty and simpler coding structure of IM while potentially decreasing the baseline CPU demand close to a retained mode GUI, so there would seem like minimal downside for a non/minimally-animated app. I'll need to look more at the old branch code as I'm not clear about Omars comments about it being processed in each backend rather than the core code. #4133 also notes the proposals potentially cause issues with blinking cursors and notes other similar proposals #4076, #3124, #2749 related to decreasing CPU consumption (I hadn't searched "power saving") so I might be thinking about reinventing the wheel.

@Rubeer
Copy link

Rubeer commented Feb 16, 2022

On Windows, I've used GetMessage instead of PeekMessage. To update the UI from other threads I just call PostMessage. Works fine except for some widgets where you need to e.g. hold the mouse button down (like the ImGui::InputInt +/- buttons)

@dgm3333
Copy link
Author

dgm3333 commented Feb 17, 2022

I now think that the "unknown" ImGui app has been causing an otherwise silent sentinal to activate resulting in the processor draw - thus the issue is not ImGui at all despiting the timing being directly correlated. I've still not bottomed out what the CPU is doing but I don't think it's ImGui causing the issue so I'm closing this.

@dgm3333 dgm3333 closed this as completed Feb 17, 2022
@sergeyn
Copy link
Contributor

sergeyn commented Mar 18, 2022

It would seem that something along those lines would enable both the rendering flexibilty and simpler coding structure of IM while potentially decreasing the baseline CPU demand close to a retained mode GUI, so there would seem like minimal downside for a non/minimally-animated app. I'll need to look more at the old branch code as I'm not clear about Omars comments about it being processed in each backend rather than the core code. #4133 also notes the proposals potentially cause issues with blinking cursors and notes other similar proposals #4076, #3124, #2749 related to decreasing CPU consumption (I hadn't searched "power saving") so I might be thinking about reinventing the wheel.

Hei, you can try my latest power saving mode in #5116. Blinking cursor works just fine and if nothing happens, nothing is rendered.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants