winemac: Take control over when a window can become focused away from Cocoa.
This commit is contained in:
parent
bd269786a5
commit
6cde62ac18
|
@ -45,6 +45,8 @@ @interface WineWindow : NSPanel <NSWindowDelegate>
|
||||||
CGFloat colorKeyRed, colorKeyGreen, colorKeyBlue;
|
CGFloat colorKeyRed, colorKeyGreen, colorKeyBlue;
|
||||||
|
|
||||||
BOOL usePerPixelAlpha;
|
BOOL usePerPixelAlpha;
|
||||||
|
|
||||||
|
BOOL causing_becomeKeyWindow;
|
||||||
}
|
}
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
|
@ -440,14 +440,52 @@ - (void) postMouseButtonEvent:(NSEvent *)theEvent pressed:(int)pressed
|
||||||
[queue postEvent:&event];
|
[queue postEvent:&event];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
- (void) makeFocused
|
||||||
|
{
|
||||||
|
NSArray* screens;
|
||||||
|
|
||||||
|
[NSApp transformProcessToForeground];
|
||||||
|
|
||||||
|
/* If a borderless window is offscreen, orderFront: won't move
|
||||||
|
it onscreen like it would for a titled window. Do that ourselves. */
|
||||||
|
screens = [NSScreen screens];
|
||||||
|
if (!([self styleMask] & NSTitledWindowMask) && ![self isVisible] &&
|
||||||
|
!frame_intersects_screens([self frame], screens))
|
||||||
|
{
|
||||||
|
NSScreen* primaryScreen = [screens objectAtIndex:0];
|
||||||
|
NSRect frame = [primaryScreen frame];
|
||||||
|
[self setFrameTopLeftPoint:NSMakePoint(NSMinX(frame), NSMaxY(frame))];
|
||||||
|
frame = [self constrainFrameRect:[self frame] toScreen:primaryScreen];
|
||||||
|
[self setFrame:frame display:YES];
|
||||||
|
}
|
||||||
|
|
||||||
|
[self orderFront:nil];
|
||||||
|
causing_becomeKeyWindow = TRUE;
|
||||||
|
[self makeKeyWindow];
|
||||||
|
causing_becomeKeyWindow = FALSE;
|
||||||
|
if (latentParentWindow)
|
||||||
|
{
|
||||||
|
[latentParentWindow addChildWindow:self ordered:NSWindowAbove];
|
||||||
|
self.latentParentWindow = nil;
|
||||||
|
}
|
||||||
|
if (![self isExcludedFromWindowsMenu])
|
||||||
|
[NSApp addWindowsItem:self title:[self title] filename:NO];
|
||||||
|
|
||||||
|
/* Cocoa may adjust the frame when the window is ordered onto the screen.
|
||||||
|
Generate a frame-changed event just in case. The back end will ignore
|
||||||
|
it if nothing actually changed. */
|
||||||
|
[self windowDidResize:nil];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* ---------- NSWindow method overrides ----------
|
* ---------- NSWindow method overrides ----------
|
||||||
*/
|
*/
|
||||||
- (BOOL) canBecomeKeyWindow
|
- (BOOL) canBecomeKeyWindow
|
||||||
{
|
{
|
||||||
|
if (causing_becomeKeyWindow) return YES;
|
||||||
if (self.disabled || self.noActivate) return NO;
|
if (self.disabled || self.noActivate) return NO;
|
||||||
return YES;
|
return [self isKeyWindow];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (BOOL) canBecomeMainWindow
|
- (BOOL) canBecomeMainWindow
|
||||||
|
@ -841,3 +879,19 @@ void macdrv_window_use_per_pixel_alpha(macdrv_window w, int use_per_pixel_alpha)
|
||||||
|
|
||||||
[pool release];
|
[pool release];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/***********************************************************************
|
||||||
|
* macdrv_give_cocoa_window_focus
|
||||||
|
*
|
||||||
|
* Makes the Cocoa window "key" (gives it keyboard focus). This also
|
||||||
|
* orders it front and, if its frame was not within the desktop bounds,
|
||||||
|
* Cocoa will typically move it on-screen.
|
||||||
|
*/
|
||||||
|
void macdrv_give_cocoa_window_focus(macdrv_window w)
|
||||||
|
{
|
||||||
|
WineWindow* window = (WineWindow*)w;
|
||||||
|
|
||||||
|
OnMainThread(^{
|
||||||
|
[window makeFocused];
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
|
@ -205,5 +205,6 @@ extern void macdrv_set_window_color_key(macdrv_window w, CGFloat keyRed, CGFloat
|
||||||
CGFloat keyBlue) DECLSPEC_HIDDEN;
|
CGFloat keyBlue) DECLSPEC_HIDDEN;
|
||||||
extern void macdrv_clear_window_color_key(macdrv_window w) DECLSPEC_HIDDEN;
|
extern void macdrv_clear_window_color_key(macdrv_window w) DECLSPEC_HIDDEN;
|
||||||
extern void macdrv_window_use_per_pixel_alpha(macdrv_window w, int use_per_pixel_alpha) DECLSPEC_HIDDEN;
|
extern void macdrv_window_use_per_pixel_alpha(macdrv_window w, int use_per_pixel_alpha) DECLSPEC_HIDDEN;
|
||||||
|
extern void macdrv_give_cocoa_window_focus(macdrv_window w) DECLSPEC_HIDDEN;
|
||||||
|
|
||||||
#endif /* __WINE_MACDRV_COCOA_H */
|
#endif /* __WINE_MACDRV_COCOA_H */
|
||||||
|
|
|
@ -43,6 +43,9 @@ static CRITICAL_SECTION win_data_section = { &critsect_debug, -1, 0, 0, 0, 0 };
|
||||||
static CFMutableDictionaryRef win_datas;
|
static CFMutableDictionaryRef win_datas;
|
||||||
|
|
||||||
|
|
||||||
|
void CDECL macdrv_SetFocus(HWND hwnd);
|
||||||
|
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
* get_cocoa_window_features
|
* get_cocoa_window_features
|
||||||
*/
|
*/
|
||||||
|
@ -154,6 +157,12 @@ static void show_window(struct macdrv_win_data *data)
|
||||||
TRACE("win %p/%p\n", data->hwnd, data->cocoa_window);
|
TRACE("win %p/%p\n", data->hwnd, data->cocoa_window);
|
||||||
|
|
||||||
data->on_screen = macdrv_order_cocoa_window(data->cocoa_window, NULL, NULL);
|
data->on_screen = macdrv_order_cocoa_window(data->cocoa_window, NULL, NULL);
|
||||||
|
if (data->on_screen)
|
||||||
|
{
|
||||||
|
HWND hwndFocus = GetFocus();
|
||||||
|
if (hwndFocus && (data->hwnd == hwndFocus || IsChild(data->hwnd, hwndFocus)))
|
||||||
|
macdrv_SetFocus(hwndFocus);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -820,6 +829,31 @@ void CDECL macdrv_DestroyWindow(HWND hwnd)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*****************************************************************
|
||||||
|
* SetFocus (MACDRV.@)
|
||||||
|
*
|
||||||
|
* Set the Mac focus.
|
||||||
|
*/
|
||||||
|
void CDECL macdrv_SetFocus(HWND hwnd)
|
||||||
|
{
|
||||||
|
struct macdrv_win_data *data;
|
||||||
|
|
||||||
|
TRACE("%p\n", hwnd);
|
||||||
|
|
||||||
|
if (!(hwnd = GetAncestor(hwnd, GA_ROOT))) return;
|
||||||
|
if (!(data = get_win_data(hwnd))) return;
|
||||||
|
|
||||||
|
if (data->cocoa_window)
|
||||||
|
{
|
||||||
|
/* Set Mac focus */
|
||||||
|
macdrv_give_cocoa_window_focus(data->cocoa_window);
|
||||||
|
data->on_screen = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
release_win_data(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
* SetLayeredWindowAttributes (MACDRV.@)
|
* SetLayeredWindowAttributes (MACDRV.@)
|
||||||
*
|
*
|
||||||
|
|
|
@ -10,6 +10,7 @@
|
||||||
@ cdecl EnumDisplayMonitors(long ptr ptr long) macdrv_EnumDisplayMonitors
|
@ cdecl EnumDisplayMonitors(long ptr ptr long) macdrv_EnumDisplayMonitors
|
||||||
@ cdecl GetMonitorInfo(long ptr) macdrv_GetMonitorInfo
|
@ cdecl GetMonitorInfo(long ptr) macdrv_GetMonitorInfo
|
||||||
@ cdecl MsgWaitForMultipleObjectsEx(long ptr long long long) macdrv_MsgWaitForMultipleObjectsEx
|
@ cdecl MsgWaitForMultipleObjectsEx(long ptr long long long) macdrv_MsgWaitForMultipleObjectsEx
|
||||||
|
@ cdecl SetFocus(long) macdrv_SetFocus
|
||||||
@ cdecl SetLayeredWindowAttributes(long long long long) macdrv_SetLayeredWindowAttributes
|
@ cdecl SetLayeredWindowAttributes(long long long long) macdrv_SetLayeredWindowAttributes
|
||||||
@ cdecl SetParent(long long long) macdrv_SetParent
|
@ cdecl SetParent(long long long) macdrv_SetParent
|
||||||
@ cdecl SetWindowRgn(long long long) macdrv_SetWindowRgn
|
@ cdecl SetWindowRgn(long long long) macdrv_SetWindowRgn
|
||||||
|
|
Loading…
Reference in New Issue