ui/cocoa: Let the platform toggle fullscreen
It allows making the window full screen by clicking full screen button provided by the platform (the left-top green button) and save some code. Signed-off-by: Akihiko Odaki <akihiko.odaki@daynix.com> Tested-by: Rene Engel <ReneEngel80@emailn.de> Reviewed-by: Peter Maydell <peter.maydell@linaro.org> Message-ID: <20240224-cocoa-v12-6-e89f70bdda71@daynix.com> Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
This commit is contained in:
parent
1a4b64a5f5
commit
91aa508d02
420
ui/cocoa.m
420
ui/cocoa.m
@ -308,20 +308,17 @@ static void handleAnyDeviceErrors(Error * err)
|
||||
*/
|
||||
@interface QemuCocoaView : NSView
|
||||
{
|
||||
NSTrackingArea *trackingArea;
|
||||
QEMUScreen screen;
|
||||
NSWindow *fullScreenWindow;
|
||||
float cx,cy,cw,ch,cdx,cdy;
|
||||
pixman_image_t *pixman_image;
|
||||
QKbdState *kbd;
|
||||
BOOL isMouseGrabbed;
|
||||
BOOL isFullscreen;
|
||||
BOOL isAbsoluteEnabled;
|
||||
CFMachPortRef eventsTap;
|
||||
}
|
||||
- (void) switchSurface:(pixman_image_t *)image;
|
||||
- (void) grabMouse;
|
||||
- (void) ungrabMouse;
|
||||
- (void) toggleFullScreen:(id)sender;
|
||||
- (void) setFullGrab:(id)sender;
|
||||
- (void) handleMonitorInput:(NSEvent *)event;
|
||||
- (bool) handleEvent:(NSEvent *)event;
|
||||
@ -337,8 +334,6 @@ static void handleAnyDeviceErrors(Error * err)
|
||||
*/
|
||||
- (BOOL) isMouseGrabbed;
|
||||
- (BOOL) isAbsoluteEnabled;
|
||||
- (float) cdx;
|
||||
- (float) cdy;
|
||||
- (QEMUScreen) gscreen;
|
||||
- (void) raiseAllKeys;
|
||||
@end
|
||||
@ -399,46 +394,43 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
return YES;
|
||||
}
|
||||
|
||||
- (BOOL) screenContainsPoint:(NSPoint) p
|
||||
- (void) removeTrackingRect
|
||||
{
|
||||
return (p.x > -1 && p.x < screen.width && p.y > -1 && p.y < screen.height);
|
||||
if (trackingArea) {
|
||||
[self removeTrackingArea:trackingArea];
|
||||
[trackingArea release];
|
||||
trackingArea = nil;
|
||||
}
|
||||
}
|
||||
|
||||
/* Get location of event and convert to virtual screen coordinate */
|
||||
- (CGPoint) screenLocationOfEvent:(NSEvent *)ev
|
||||
- (void) frameUpdated
|
||||
{
|
||||
NSWindow *eventWindow = [ev window];
|
||||
// XXX: Use CGRect and -convertRectFromScreen: to support macOS 10.10
|
||||
CGRect r = CGRectZero;
|
||||
r.origin = [ev locationInWindow];
|
||||
if (!eventWindow) {
|
||||
if (!isFullscreen) {
|
||||
return [[self window] convertRectFromScreen:r].origin;
|
||||
} else {
|
||||
CGPoint locationInSelfWindow = [[self window] convertRectFromScreen:r].origin;
|
||||
CGPoint loc = [self convertPoint:locationInSelfWindow fromView:nil];
|
||||
if (stretch_video) {
|
||||
loc.x /= cdx;
|
||||
loc.y /= cdy;
|
||||
}
|
||||
return loc;
|
||||
}
|
||||
} else if ([[self window] isEqual:eventWindow]) {
|
||||
if (!isFullscreen) {
|
||||
return r.origin;
|
||||
} else {
|
||||
CGPoint loc = [self convertPoint:r.origin fromView:nil];
|
||||
if (stretch_video) {
|
||||
loc.x /= cdx;
|
||||
loc.y /= cdy;
|
||||
}
|
||||
return loc;
|
||||
}
|
||||
} else {
|
||||
return [[self window] convertRectFromScreen:[eventWindow convertRectToScreen:r]].origin;
|
||||
[self removeTrackingRect];
|
||||
|
||||
if ([self window]) {
|
||||
NSTrackingAreaOptions options = NSTrackingActiveInKeyWindow |
|
||||
NSTrackingMouseEnteredAndExited |
|
||||
NSTrackingMouseMoved;
|
||||
trackingArea = [[NSTrackingArea alloc] initWithRect:[self frame]
|
||||
options:options
|
||||
owner:self
|
||||
userInfo:nil];
|
||||
[self addTrackingArea:trackingArea];
|
||||
[self updateUIInfo];
|
||||
}
|
||||
}
|
||||
|
||||
- (void) viewDidMoveToWindow
|
||||
{
|
||||
[self resizeWindow];
|
||||
[self frameUpdated];
|
||||
}
|
||||
|
||||
- (void) viewWillMoveToWindow:(NSWindow *)newWindow
|
||||
{
|
||||
[self removeTrackingRect];
|
||||
}
|
||||
|
||||
- (void) hideCursor
|
||||
{
|
||||
if (!cursor_hide) {
|
||||
@ -518,36 +510,25 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
}
|
||||
}
|
||||
|
||||
- (void) setContentDimensions
|
||||
- (NSSize) screenSafeAreaSize
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaView: setContentDimensions\n");
|
||||
NSSize size = [[[self window] screen] frame].size;
|
||||
NSEdgeInsets insets = [[[self window] screen] safeAreaInsets];
|
||||
size.width -= insets.left + insets.right;
|
||||
size.height -= insets.top + insets.bottom;
|
||||
return size;
|
||||
}
|
||||
|
||||
if (isFullscreen) {
|
||||
cdx = [[NSScreen mainScreen] frame].size.width / (float)screen.width;
|
||||
cdy = [[NSScreen mainScreen] frame].size.height / (float)screen.height;
|
||||
- (void) resizeWindow
|
||||
{
|
||||
[[self window] setContentAspectRatio:NSMakeSize(screen.width, screen.height)];
|
||||
|
||||
/* stretches video, but keeps same aspect ratio */
|
||||
if (stretch_video == true) {
|
||||
/* use smallest stretch value - prevents clipping on sides */
|
||||
if (MIN(cdx, cdy) == cdx) {
|
||||
cdy = cdx;
|
||||
} else {
|
||||
cdx = cdy;
|
||||
}
|
||||
} else { /* No stretching */
|
||||
cdx = cdy = 1;
|
||||
}
|
||||
cw = screen.width * cdx;
|
||||
ch = screen.height * cdy;
|
||||
cx = ([[NSScreen mainScreen] frame].size.width - cw) / 2.0;
|
||||
cy = ([[NSScreen mainScreen] frame].size.height - ch) / 2.0;
|
||||
} else {
|
||||
cx = 0;
|
||||
cy = 0;
|
||||
cw = screen.width;
|
||||
ch = screen.height;
|
||||
cdx = 1.0;
|
||||
cdy = 1.0;
|
||||
if (!stretch_video) {
|
||||
[[self window] setContentSize:NSMakeSize(screen.width, screen.height)];
|
||||
[[self window] center];
|
||||
} else if ([[self window] styleMask] & NSWindowStyleMaskFullScreen) {
|
||||
[[self window] setContentSize:[self screenSafeAreaSize]];
|
||||
[[self window] center];
|
||||
}
|
||||
}
|
||||
|
||||
@ -571,9 +552,10 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
CGDirectDisplayID display = [[description objectForKey:@"NSScreenNumber"] unsignedIntValue];
|
||||
NSSize screenSize = [[[self window] screen] frame].size;
|
||||
CGSize screenPhysicalSize = CGDisplayScreenSize(display);
|
||||
bool isFullscreen = ([[self window] styleMask] & NSWindowStyleMaskFullScreen) != 0;
|
||||
CVDisplayLinkRef displayLink;
|
||||
|
||||
frameSize = isFullscreen ? screenSize : [self frame].size;
|
||||
frameSize = isFullscreen ? [self screenSafeAreaSize] : [self frame].size;
|
||||
|
||||
if (!CVDisplayLinkCreateWithCGDisplay(display, &displayLink)) {
|
||||
CVTime period = CVDisplayLinkGetNominalOutputVideoRefreshPeriod(displayLink);
|
||||
@ -620,31 +602,19 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
});
|
||||
}
|
||||
|
||||
- (void)viewDidMoveToWindow
|
||||
{
|
||||
[self updateUIInfo];
|
||||
}
|
||||
|
||||
- (void) switchSurface:(pixman_image_t *)image
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaView: switchSurface\n");
|
||||
|
||||
int w = pixman_image_get_width(image);
|
||||
int h = pixman_image_get_height(image);
|
||||
/* cdx == 0 means this is our very first surface, in which case we need
|
||||
* to recalculate the content dimensions even if it happens to be the size
|
||||
* of the initial empty window.
|
||||
*/
|
||||
bool isResize = (w != screen.width || h != screen.height || cdx == 0.0);
|
||||
|
||||
int oldh = screen.height;
|
||||
if (isResize) {
|
||||
if (w != screen.width || h != screen.height) {
|
||||
// Resize before we trigger the redraw, or we'll redraw at the wrong size
|
||||
COCOA_DEBUG("switchSurface: new size %d x %d\n", w, h);
|
||||
screen.width = w;
|
||||
screen.height = h;
|
||||
[self setContentDimensions];
|
||||
[self setFrame:NSMakeRect(cx, cy, cw, ch)];
|
||||
[self resizeWindow];
|
||||
[self updateBounds];
|
||||
}
|
||||
|
||||
@ -654,51 +624,6 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
}
|
||||
|
||||
pixman_image = image;
|
||||
|
||||
// update windows
|
||||
if (isFullscreen) {
|
||||
[[fullScreenWindow contentView] setFrame:[[NSScreen mainScreen] frame]];
|
||||
[normalWindow setFrame:NSMakeRect([normalWindow frame].origin.x, [normalWindow frame].origin.y - h + oldh, w, h + [normalWindow frame].size.height - oldh) display:NO animate:NO];
|
||||
} else {
|
||||
if (qemu_name)
|
||||
[normalWindow setTitle:[NSString stringWithFormat:@"QEMU %s", qemu_name]];
|
||||
[normalWindow setFrame:NSMakeRect([normalWindow frame].origin.x, [normalWindow frame].origin.y - h + oldh, w, h + [normalWindow frame].size.height - oldh) display:YES animate:NO];
|
||||
}
|
||||
|
||||
if (isResize) {
|
||||
[normalWindow center];
|
||||
}
|
||||
}
|
||||
|
||||
- (void) toggleFullScreen:(id)sender
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaView: toggleFullScreen\n");
|
||||
|
||||
if (isFullscreen) { // switch from fullscreen to desktop
|
||||
isFullscreen = FALSE;
|
||||
[self ungrabMouse];
|
||||
[self setContentDimensions];
|
||||
[fullScreenWindow close];
|
||||
[normalWindow setContentView: self];
|
||||
[normalWindow makeKeyAndOrderFront: self];
|
||||
[NSMenu setMenuBarVisible:YES];
|
||||
} else { // switch from desktop to fullscreen
|
||||
isFullscreen = TRUE;
|
||||
[normalWindow orderOut: nil]; /* Hide the window */
|
||||
[self grabMouse];
|
||||
[self setContentDimensions];
|
||||
[NSMenu setMenuBarVisible:NO];
|
||||
fullScreenWindow = [[NSWindow alloc] initWithContentRect:[[NSScreen mainScreen] frame]
|
||||
styleMask:NSWindowStyleMaskBorderless
|
||||
backing:NSBackingStoreBuffered
|
||||
defer:NO];
|
||||
[fullScreenWindow setAcceptsMouseMovedEvents: YES];
|
||||
[fullScreenWindow setHasShadow:NO];
|
||||
[fullScreenWindow setBackgroundColor: [NSColor blackColor]];
|
||||
[self setFrame:NSMakeRect(cx, cy, cw, ch)];
|
||||
[[fullScreenWindow contentView] addSubview: self];
|
||||
[fullScreenWindow makeKeyAndOrderFront:self];
|
||||
}
|
||||
}
|
||||
|
||||
- (void) setFullGrab:(id)sender
|
||||
@ -812,8 +737,6 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
COCOA_DEBUG("QemuCocoaView: handleEvent\n");
|
||||
InputButton button;
|
||||
int keycode = 0;
|
||||
// Location of event in virtual screen coordinates
|
||||
NSPoint p = [self screenLocationOfEvent:event];
|
||||
NSUInteger modifiers = [event modifierFlags];
|
||||
|
||||
/*
|
||||
@ -1007,50 +930,6 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
qkbd_state_key_event(kbd, keycode, false);
|
||||
}
|
||||
return true;
|
||||
case NSEventTypeMouseMoved:
|
||||
if (isAbsoluteEnabled) {
|
||||
// Cursor re-entered into a window might generate events bound to screen coordinates
|
||||
// and `nil` window property, and in full screen mode, current window might not be
|
||||
// key window, where event location alone should suffice.
|
||||
if (![self screenContainsPoint:p] || !([[self window] isKeyWindow] || isFullscreen)) {
|
||||
if (isMouseGrabbed) {
|
||||
[self ungrabMouse];
|
||||
}
|
||||
} else {
|
||||
if (!isMouseGrabbed) {
|
||||
[self grabMouse];
|
||||
}
|
||||
}
|
||||
}
|
||||
return [self handleMouseEvent:event];
|
||||
case NSEventTypeLeftMouseDown:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_LEFT down:true];
|
||||
case NSEventTypeRightMouseDown:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_RIGHT down:true];
|
||||
case NSEventTypeOtherMouseDown:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_MIDDLE down:true];
|
||||
case NSEventTypeLeftMouseDragged:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_LEFT down:true];
|
||||
case NSEventTypeRightMouseDragged:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_RIGHT down:true];
|
||||
case NSEventTypeOtherMouseDragged:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_MIDDLE down:true];
|
||||
case NSEventTypeLeftMouseUp:
|
||||
if (!isMouseGrabbed && [self screenContainsPoint:p]) {
|
||||
/*
|
||||
* In fullscreen mode, the window of cocoaView may not be the
|
||||
* key window, therefore the position relative to the virtual
|
||||
* screen alone will be sufficient.
|
||||
*/
|
||||
if(isFullscreen || [[self window] isKeyWindow]) {
|
||||
[self grabMouse];
|
||||
}
|
||||
}
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_LEFT down:false];
|
||||
case NSEventTypeRightMouseUp:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_RIGHT down:false];
|
||||
case NSEventTypeOtherMouseUp:
|
||||
return [self handleMouseEvent:event button:INPUT_BUTTON_MIDDLE down:false];
|
||||
case NSEventTypeScrollWheel:
|
||||
/*
|
||||
* Send wheel events to the guest regardless of window focus.
|
||||
@ -1083,61 +962,118 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
}
|
||||
}
|
||||
|
||||
- (bool) handleMouseEvent:(NSEvent *)event button:(InputButton)button down:(bool)down
|
||||
{
|
||||
/* Don't send button events to the guest unless we've got a
|
||||
* mouse grab or window focus. If we have neither then this event
|
||||
* is the user clicking on the background window to activate and
|
||||
* bring us to the front, which will be done by the sendEvent
|
||||
* call below. We definitely don't want to pass that click through
|
||||
* to the guest.
|
||||
*/
|
||||
if (!isMouseGrabbed && ![[self window] isKeyWindow]) {
|
||||
return false;
|
||||
}
|
||||
|
||||
qemu_input_queue_btn(dcl.con, button, down);
|
||||
|
||||
return [self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (bool) handleMouseEvent:(NSEvent *)event
|
||||
- (void) handleMouseEvent:(NSEvent *)event button:(InputButton)button down:(bool)down
|
||||
{
|
||||
if (!isMouseGrabbed) {
|
||||
return false;
|
||||
return;
|
||||
}
|
||||
|
||||
if (isAbsoluteEnabled) {
|
||||
NSPoint p = [self screenLocationOfEvent:event];
|
||||
with_bql(^{
|
||||
qemu_input_queue_btn(dcl.con, button, down);
|
||||
});
|
||||
|
||||
/* Note that the origin for Cocoa mouse coords is bottom left, not top left.
|
||||
* The check on screenContainsPoint is to avoid sending out of range values for
|
||||
* clicks in the titlebar.
|
||||
*/
|
||||
if ([self screenContainsPoint:p]) {
|
||||
qemu_input_queue_abs(dcl.con, INPUT_AXIS_X, p.x, 0, screen.width);
|
||||
qemu_input_queue_abs(dcl.con, INPUT_AXIS_Y, screen.height - p.y, 0, screen.height);
|
||||
[self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (void) handleMouseEvent:(NSEvent *)event
|
||||
{
|
||||
if (!isMouseGrabbed) {
|
||||
return;
|
||||
}
|
||||
|
||||
with_bql(^{
|
||||
if (isAbsoluteEnabled) {
|
||||
CGFloat d = (CGFloat)screen.height / [self frame].size.height;
|
||||
NSPoint p = [event locationInWindow];
|
||||
|
||||
/* Note that the origin for Cocoa mouse coords is bottom left, not top left. */
|
||||
qemu_input_queue_abs(dcl.con, INPUT_AXIS_X, p.x * d, 0, screen.width);
|
||||
qemu_input_queue_abs(dcl.con, INPUT_AXIS_Y, screen.height - p.y * d, 0, screen.height);
|
||||
} else {
|
||||
qemu_input_queue_rel(dcl.con, INPUT_AXIS_X, [event deltaX]);
|
||||
qemu_input_queue_rel(dcl.con, INPUT_AXIS_Y, [event deltaY]);
|
||||
}
|
||||
} else {
|
||||
qemu_input_queue_rel(dcl.con, INPUT_AXIS_X, (int)[event deltaX]);
|
||||
qemu_input_queue_rel(dcl.con, INPUT_AXIS_Y, (int)[event deltaY]);
|
||||
|
||||
qemu_input_event_sync();
|
||||
});
|
||||
}
|
||||
|
||||
- (void) mouseExited:(NSEvent *)event
|
||||
{
|
||||
if (isAbsoluteEnabled && isMouseGrabbed) {
|
||||
[self ungrabMouse];
|
||||
}
|
||||
}
|
||||
|
||||
- (void) mouseEntered:(NSEvent *)event
|
||||
{
|
||||
if (isAbsoluteEnabled && !isMouseGrabbed) {
|
||||
[self grabMouse];
|
||||
}
|
||||
}
|
||||
|
||||
- (void) mouseMoved:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (void) mouseDown:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_LEFT down:true];
|
||||
}
|
||||
|
||||
- (void) rightMouseDown:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_RIGHT down:true];
|
||||
}
|
||||
|
||||
- (void) otherMouseDown:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_MIDDLE down:true];
|
||||
}
|
||||
|
||||
- (void) mouseDragged:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (void) rightMouseDragged:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (void) otherMouseDragged:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event];
|
||||
}
|
||||
|
||||
- (void) mouseUp:(NSEvent *)event
|
||||
{
|
||||
if (!isMouseGrabbed) {
|
||||
[self grabMouse];
|
||||
}
|
||||
|
||||
qemu_input_event_sync();
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_LEFT down:false];
|
||||
}
|
||||
|
||||
return true;
|
||||
- (void) rightMouseUp:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_RIGHT down:false];
|
||||
}
|
||||
|
||||
- (void) otherMouseUp:(NSEvent *)event
|
||||
{
|
||||
[self handleMouseEvent:event button:INPUT_BUTTON_MIDDLE down:false];
|
||||
}
|
||||
|
||||
- (void) grabMouse
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaView: grabMouse\n");
|
||||
|
||||
if (!isFullscreen) {
|
||||
if (qemu_name)
|
||||
[normalWindow setTitle:[NSString stringWithFormat:@"QEMU %s - (Press " UC_CTRL_KEY " " UC_ALT_KEY " G to release Mouse)", qemu_name]];
|
||||
else
|
||||
[normalWindow setTitle:@"QEMU - (Press " UC_CTRL_KEY " " UC_ALT_KEY " G to release Mouse)"];
|
||||
}
|
||||
if (qemu_name)
|
||||
[normalWindow setTitle:[NSString stringWithFormat:@"QEMU %s - (Press " UC_CTRL_KEY " " UC_ALT_KEY " G to release Mouse)", qemu_name]];
|
||||
else
|
||||
[normalWindow setTitle:@"QEMU - (Press " UC_CTRL_KEY " " UC_ALT_KEY " G to release Mouse)"];
|
||||
[self hideCursor];
|
||||
CGAssociateMouseAndMouseCursorPosition(isAbsoluteEnabled);
|
||||
isMouseGrabbed = TRUE; // while isMouseGrabbed = TRUE, QemuCocoaApp sends all events to [cocoaView handleEvent:]
|
||||
@ -1147,15 +1083,14 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaView: ungrabMouse\n");
|
||||
|
||||
if (!isFullscreen) {
|
||||
if (qemu_name)
|
||||
[normalWindow setTitle:[NSString stringWithFormat:@"QEMU %s", qemu_name]];
|
||||
else
|
||||
[normalWindow setTitle:@"QEMU"];
|
||||
}
|
||||
if (qemu_name)
|
||||
[normalWindow setTitle:[NSString stringWithFormat:@"QEMU %s", qemu_name]];
|
||||
else
|
||||
[normalWindow setTitle:@"QEMU"];
|
||||
[self unhideCursor];
|
||||
CGAssociateMouseAndMouseCursorPosition(TRUE);
|
||||
isMouseGrabbed = FALSE;
|
||||
[self raiseAllButtons];
|
||||
}
|
||||
|
||||
- (void) setAbsoluteEnabled:(BOOL)tIsAbsoluteEnabled {
|
||||
@ -1166,8 +1101,6 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
}
|
||||
- (BOOL) isMouseGrabbed {return isMouseGrabbed;}
|
||||
- (BOOL) isAbsoluteEnabled {return isAbsoluteEnabled;}
|
||||
- (float) cdx {return cdx;}
|
||||
- (float) cdy {return cdy;}
|
||||
- (QEMUScreen) gscreen {return screen;}
|
||||
|
||||
/*
|
||||
@ -1181,6 +1114,15 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
qkbd_state_lift_all_keys(kbd);
|
||||
});
|
||||
}
|
||||
|
||||
- (void) raiseAllButtons
|
||||
{
|
||||
with_bql(^{
|
||||
qemu_input_queue_btn(dcl.con, INPUT_BUTTON_LEFT, false);
|
||||
qemu_input_queue_btn(dcl.con, INPUT_BUTTON_RIGHT, false);
|
||||
qemu_input_queue_btn(dcl.con, INPUT_BUTTON_MIDDLE, false);
|
||||
});
|
||||
}
|
||||
@end
|
||||
|
||||
|
||||
@ -1195,7 +1137,6 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
{
|
||||
}
|
||||
- (void)doToggleFullScreen:(id)sender;
|
||||
- (void)toggleFullScreen:(id)sender;
|
||||
- (void)showQEMUDoc:(id)sender;
|
||||
- (void)zoomToFit:(id) sender;
|
||||
- (void)displayConsole:(id)sender;
|
||||
@ -1237,7 +1178,8 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
exit(1);
|
||||
}
|
||||
[normalWindow setAcceptsMouseMovedEvents:YES];
|
||||
[normalWindow setTitle:@"QEMU"];
|
||||
[normalWindow setCollectionBehavior:NSWindowCollectionBehaviorFullScreenPrimary];
|
||||
[normalWindow setTitle:qemu_name ? [NSString stringWithFormat:@"QEMU %s", qemu_name] : @"QEMU"];
|
||||
[normalWindow setContentView:cocoaView];
|
||||
[normalWindow makeKeyAndOrderFront:self];
|
||||
[normalWindow center];
|
||||
@ -1307,10 +1249,21 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
[cocoaView updateUIInfo];
|
||||
}
|
||||
|
||||
- (void)windowDidEnterFullScreen:(NSNotification *)notification
|
||||
{
|
||||
[cocoaView grabMouse];
|
||||
}
|
||||
|
||||
- (void)windowDidExitFullScreen:(NSNotification *)notification
|
||||
{
|
||||
[cocoaView resizeWindow];
|
||||
[cocoaView ungrabMouse];
|
||||
}
|
||||
|
||||
- (void)windowDidResize:(NSNotification *)notification
|
||||
{
|
||||
[cocoaView updateBounds];
|
||||
[cocoaView updateUIInfo];
|
||||
[cocoaView frameUpdated];
|
||||
}
|
||||
|
||||
/* Called when the user clicks on a window's close button */
|
||||
@ -1326,6 +1279,14 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
return NO;
|
||||
}
|
||||
|
||||
- (NSApplicationPresentationOptions) window:(NSWindow *)window
|
||||
willUseFullScreenPresentationOptions:(NSApplicationPresentationOptions)proposedOptions;
|
||||
|
||||
{
|
||||
return (proposedOptions & ~(NSApplicationPresentationAutoHideDock | NSApplicationPresentationAutoHideMenuBar)) |
|
||||
NSApplicationPresentationHideDock | NSApplicationPresentationHideMenuBar;
|
||||
}
|
||||
|
||||
/*
|
||||
* Called when QEMU goes into the background. Note that
|
||||
* [-NSWindowDelegate windowDidResignKey:] is used here instead of
|
||||
@ -1345,14 +1306,7 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
*/
|
||||
- (void) doToggleFullScreen:(id)sender
|
||||
{
|
||||
[self toggleFullScreen:(id)sender];
|
||||
}
|
||||
|
||||
- (void)toggleFullScreen:(id)sender
|
||||
{
|
||||
COCOA_DEBUG("QemuCocoaAppController: toggleFullScreen\n");
|
||||
|
||||
[cocoaView toggleFullScreen:sender];
|
||||
[normalWindow toggleFullScreen:sender];
|
||||
}
|
||||
|
||||
- (void) setFullGrab:(id)sender
|
||||
@ -1403,6 +1357,7 @@ static CGEventRef handleTapEvent(CGEventTapProxy proxy, CGEventType type, CGEven
|
||||
if (stretch_video == true) {
|
||||
[sender setState: NSControlStateValueOn];
|
||||
} else {
|
||||
[cocoaView resizeWindow];
|
||||
[sender setState: NSControlStateValueOff];
|
||||
}
|
||||
}
|
||||
@ -2049,8 +2004,7 @@ static void cocoa_display_init(DisplayState *ds, DisplayOptions *opts)
|
||||
|
||||
/* if fullscreen mode is to be used */
|
||||
if (opts->has_full_screen && opts->full_screen) {
|
||||
[NSApp activateIgnoringOtherApps: YES];
|
||||
[controller toggleFullScreen: nil];
|
||||
[normalWindow toggleFullScreen: nil];
|
||||
}
|
||||
if (opts->u.cocoa.has_full_grab && opts->u.cocoa.full_grab) {
|
||||
[controller setFullGrab: nil];
|
||||
|
Loading…
Reference in New Issue
Block a user