Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit b1822cf

Browse filesBrowse files
committed
FIX: macos: remove our custom PyOS_InputHook after our runloop stops
We want to defer back to Python's native input hook handling when we don't have any figures to interact with, otherwise our runloop will continue running unecessarily. Additionally, we need to add a short runloop burst in our hotloop to avoid saturating the CPU while waiting for input. (i.e. sitting on an idle figure would keep 100% cpu while waiting for an input() event without this runloop trigger).
1 parent 3c7bc45 commit b1822cf
Copy full SHA for b1822cf

File tree

1 file changed

+17
-8
lines changed
Filter options

1 file changed

+17
-8
lines changed

‎src/_macosx.m

Copy file name to clipboardExpand all lines: src/_macosx.m
+17-8Lines changed: 17 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,10 @@ static int wait_for_stdin() {
8888
if (!event) { break; }
8989
[NSApp sendEvent: event];
9090
}
91+
// We need to run the run loop for a short time to allow the
92+
// events to be processed and keep flushing them while we wait for stdin
93+
// without this, the CPU usage will be very high constantly polling this loop
94+
[[NSRunLoop currentRunLoop] runUntilDate: [NSDate dateWithTimeIntervalSinceNow: 0.01]];
9195
}
9296
// Remove the input handler as an observer
9397
[[NSNotificationCenter defaultCenter] removeObserver: stdinHandle];
@@ -192,16 +196,16 @@ void process_event(char const* cls_name, char const* fmt, ...)
192196
static bool backend_inited = false;
193197

194198
static void lazy_init(void) {
199+
// Run our own event loop while waiting for stdin on the Python side
200+
// this is needed to keep the application responsive while waiting for input
201+
PyOS_InputHook = wait_for_stdin;
202+
195203
if (backend_inited) { return; }
196204
backend_inited = true;
197205

198206
NSApp = [NSApplication sharedApplication];
199207
[NSApp setActivationPolicy:NSApplicationActivationPolicyRegular];
200208
[NSApp setDelegate: [[[MatplotlibAppDelegate alloc] init] autorelease]];
201-
202-
// Run our own event loop while waiting for stdin on the Python side
203-
// this is needed to keep the application responsive while waiting for input
204-
PyOS_InputHook = wait_for_stdin;
205209
}
206210

207211
static PyObject*
@@ -236,6 +240,8 @@ static void lazy_init(void) {
236240
static PyObject*
237241
stop(PyObject* self)
238242
{
243+
// Remove our input hook and stop the event loop.
244+
PyOS_InputHook = NULL;
239245
[NSApp stop: nil];
240246
// Post an event to trigger the actual stopping.
241247
[NSApp postEvent: [NSEvent otherEventWithType: NSEventTypeApplicationDefined
@@ -1122,10 +1128,13 @@ - (void)close
11221128
{
11231129
[super close];
11241130
--FigureWindowCount;
1125-
if (!FigureWindowCount) [NSApp stop: self];
1126-
/* This is needed for show(), which should exit from [NSApp run]
1127-
* after all windows are closed.
1128-
*/
1131+
if (!FigureWindowCount) {
1132+
/* This is needed for show(), which should exit from [NSApp run]
1133+
* after all windows are closed.
1134+
*/
1135+
PyObject* x = stop(NULL);
1136+
Py_DECREF(x);
1137+
}
11291138
// For each new window, we have incremented the manager reference, so
11301139
// we need to bring that down during close and not just dealloc.
11311140
Py_DECREF(manager);

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.