Compare commits

...

2 commits

Author SHA1 Message Date
8f379e9751 add comment clarifying pending
All checks were successful
pyrite-dev/milsko/pipeline/head This commit looks good
2026-03-10 15:46:46 -07:00
9f1b455341 mac: new event pumping architecture that sucks and i hate it but apple is happy with it so we're happy with it 2026-03-10 15:33:20 -07:00
2 changed files with 29 additions and 34 deletions

View file

@ -156,6 +156,7 @@
- (NSView *)getView;
- (MilskoCocoaWindow *)getWindow;
- (MilskoFakePointer *)getHandle;
+ (void)eventCanceller:(MilskoCocoa *)this;
@end
#define OBJC(x) x

View file

@ -142,9 +142,9 @@ static NSPoint pointFlip(NSPoint point) {
[c->application
setActivationPolicy:0 /* NSApplicationActivationPolicyRegular */];
}
[c->window makeKeyAndOrderFront:nil];
[c->application activateIgnoringOtherApps:true];
[c->window makeFirstResponder:c->view];
[c->window makeKeyAndOrderFront:nil];
}
[c->application setDelegate:[[MilskoCocoaApplicationDelegate alloc]
initWithAppl:c->application]];
@ -172,6 +172,13 @@ static NSPoint pointFlip(NSPoint point) {
return c;
}
+ (void)eventCanceller:(MilskoCocoa *)this {
this->lastEvent = [this->application currentEvent];
[this eventProcess:this->lastEvent];
[[NSApplication sharedApplication] stop:nil];
}
- (void)polygonWithPoints:(MwPoint *)points
points_count:(int)points_count
color:(MwLLColor)color {
@ -269,42 +276,29 @@ static NSPoint pointFlip(NSPoint point) {
[self forceRender];
};
- (int)pending {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
MwBool isPending = MwFALSE;
if (_forceRender) {
_forceRender = MwFALSE;
[pool release];
return 1;
}
self->lastEvent = [self->window nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantPast]
inMode:NSDefaultRunLoopMode
dequeue:YES];
/*
ok so this is a crime against god but I did in fact try the better method
of using nextEventMatchingMask and then pumping events manually. However
this gives me something that only kind of works, with strange behavior such
as the window never becoming the main window (have to make it key in order
for the menu to show up) occuring. Hours of research and digging led me down
a rabbit hole that, on all sides, pointed to "just use [NSApplication run]".
So we just to do that; of course, this is a blocking function, so we
register this function that instantly cancels it and pumps whatever event
MacOS has in store for us. We do this on loop and somehow the resulting CPU
usage is managable.
isPending = self->lastEvent != NULL;
[pool release];
return isPending;
If some Apple developer with 20 years of experience in Objective C is here:
Pls god send PR if you know how to properly do this.
*/
[MilskoCocoa performSelectorOnMainThread:@selector(eventCanceller:)
withObject:self
waitUntilDone:NO];
[self->application run];
return 1;
};
- (void)getNextEvent {
[self eventProcess:self->lastEvent];
while (true) {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSEvent *ev = [self->window nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantPast]
inMode:NSDefaultRunLoopMode
dequeue:YES];
if (!ev) {
[pool release];
break;
}
/* run through the switch case on ev.type, before calling sendEvent on any
* events we handle */
[self eventProcess:ev];
[pool release];
[self->application updateWindows];
}
[self sendClipboardEvent];
if (self->pointerLocked && [self->window isMainWindow]) {