Skip to content

Commit

Permalink
Mac OS: 1) simpler tracking of window changes between retina/non reti…
Browse files Browse the repository at this point in the history
…na displays.

2) improved window creation in iconized state (child windows still don't show in icon, though).

git-svn-id: file:///fltk/svn/fltk/branches/branch-1.3@10860 ea41ed52-d2ee-0310-a9c1-e6b18d33e121
  • Loading branch information
Manolo Gouy authored and Manolo Gouy committed Sep 10, 2015
1 parent fa9880e commit 157eb68
Showing 1 changed file with 23 additions and 50 deletions.
73 changes: 23 additions & 50 deletions src/Fl_cocoa.mm
Expand Up @@ -3,7 +3,7 @@
//
// MacOS-Cocoa specific code for the Fast Light Tool Kit (FLTK).
//
// Copyright 1998-2014 by Bill Spitzak and others.
// Copyright 1998-2015 by Bill Spitzak and others.
//
// This library is free software. Distribution and use rights are outlined in
// the file "COPYING" which should have been included with this file. If this
Expand Down Expand Up @@ -1157,26 +1157,6 @@ static void orderfront_subwindows(FLWindow *xid)
#endif
}

//determines whether a window is mapped to a retina display
static void compute_mapped_to_retina(Fl_Window *window)
{
if (fl_mac_os_version >= 100700) { // determine whether window is now mapped to a retina display
Fl_X *flx = Fl_X::i(window);
bool previous = flx->mapped_to_retina();
// rewrite next call that requires 10.7 and therefore triggers a compiler warning on old SDKs
//NSSize s = [[flx->xid contentView] convertSizeToBacking:NSMakeSize(10, 10)];
typedef NSSize (*convertSizeIMP)(id, SEL, NSSize);
static convertSizeIMP addr = (convertSizeIMP)[NSView instanceMethodForSelector:@selector(convertSizeToBacking:)];
NSSize s = addr([flx->xid contentView], @selector(convertSizeToBacking:), NSMakeSize(10, 10));
flx->mapped_to_retina( int(s.width + 0.5) > 10 );
if (previous != flx->mapped_to_retina()) flx->changed_resolution(true);
// window needs redrawn when moving from low res to retina
if ((!previous) && flx->mapped_to_retina()) {
window->redraw();
}
}
}

#if FLTK_ABI_VERSION >= 10304
static const unsigned mapped_mask = 2;
static const unsigned changed_mask = 4;
Expand Down Expand Up @@ -1285,7 +1265,6 @@ - (void)windowDidMove:(NSNotification *)notif
parent = parent->window();
}
window->position((int)pt2.x, (int)pt2.y);
compute_mapped_to_retina(window);
if (fl_mac_os_version < 100700) { // after move, redraw parent and children of GL windows
parent = window->window();
if (parent && parent->as_gl_window()) window->redraw();
Expand Down Expand Up @@ -1359,16 +1338,15 @@ - (void)windowDidDeminiaturize:(NSNotification *)notif
Fl_Window *window = [nsw getFl_Window];
Fl::handle(FL_SHOW, window);
update_e_xy_and_e_xy_root(nsw);
Fl_X::i(window)->wait_for_expose = 0; // necessary when window was created miniaturized
if (fl_mac_os_version < 101100) Fl::flush(); // process redraws set by FL_SHOW
Fl::flush(); // Process redraws set by FL_SHOW.
fl_unlock_function();
}
- (void)windowWillMiniaturize:(NSNotification *)notif
{
// subwindows are not captured in system-built miniature window image
fl_lock_function();
FLWindow *nsw = (FLWindow*)[notif object];
if ([nsw childWindows]) {
if ([[nsw childWindows] count]) {
// capture the window and its subwindows and use as miniature window image
Fl_Window *window = [nsw getFl_Window];
NSBitmapImageRep *bitmap = rect_to_NSBitmapImageRep(window, 0, 0, window->w(), window->h());
Expand Down Expand Up @@ -1884,13 +1862,22 @@ static void handleUpdateEvent( Fl_Window *window )
{
if ( !window ) return;
Fl_X *i = Fl_X::i( window );
if (fl_mac_os_version >= 100700) { // determine whether window is mapped to a retina display
bool previous = i->mapped_to_retina();
// rewrite next call that requires 10.7 and therefore triggers a compiler warning on old SDKs
//NSSize s = [[i->xid contentView] convertSizeToBacking:NSMakeSize(10, 10)];
typedef NSSize (*convertSizeIMP)(id, SEL, NSSize);
static convertSizeIMP addr = (convertSizeIMP)[NSView instanceMethodForSelector:@selector(convertSizeToBacking:)];
NSSize s = addr([i->xid contentView], @selector(convertSizeToBacking:), NSMakeSize(10, 10));
i->mapped_to_retina( int(s.width + 0.5) > 10 );
if (i->wait_for_expose == 0 && previous != i->mapped_to_retina()) i->changed_resolution(true);
}
i->wait_for_expose = 0;

if ( i->region ) {
XDestroyRegion(i->region);
i->region = 0;
}

window->clear_damage(FL_DAMAGE_ALL);
i->flush();
window->clear_damage();
Expand Down Expand Up @@ -2220,11 +2207,9 @@ - (void)drawRect:(NSRect)rect
fl_lock_function();
FLWindow *cw = (FLWindow*)[self window];
Fl_Window *w = [cw getFl_Window];
if (w->visible()) {
through_drawRect = YES;
handleUpdateEvent(w);
through_drawRect = NO;
}
through_drawRect = YES;
handleUpdateEvent(w);
through_drawRect = NO;
fl_unlock_function();
}

Expand Down Expand Up @@ -2921,9 +2906,9 @@ static void set_subwindow_frame(Fl_Window *w) { // maps a subwindow at its corre
x->subRect(0);
x->cursor = NULL;
x->gc = 0;
if (w->parent()) x->mapped_to_retina( w->top_window()->i->mapped_to_retina() );
else x->mapped_to_retina(false);
x->mapped_to_retina(false);
x->changed_resolution(false);
x->in_windowDidResize(false);

NSRect crect;
if (w->fullscreen_active()) {
Expand Down Expand Up @@ -3027,8 +3012,10 @@ static void set_subwindow_frame(Fl_Window *w) { // maps a subwindow at its corre
[cw setDelegate:[FLWindowDelegate singleInstance]];
if (fl_show_iconic) {
fl_show_iconic = 0;
[cw miniaturize:nil];
} else if (w->parent()) {
// w->handle(FL_SHOW); this creates subwindows correctly, but they are deiconized at a wrong location
if (fl_mac_os_version < 101100) [myview display]; // draws the view before its icon is computed
[cw miniaturize:nil]; // on 10.11 this sends drawRect:
} else if (w->parent()) { // a subwindow
[cw setIgnoresMouseEvents:YES]; // needs OS X 10.2
// next 2 statements so a subwindow doesn't leak out of its parent window
[cw setOpaque:NO];
Expand All @@ -3049,24 +3036,10 @@ static void set_subwindow_frame(Fl_Window *w) { // maps a subwindow at its corre
// needed if top window was first displayed miniaturized
FLWindow *pxid = fl_xid(w->top_window());
[pxid makeFirstResponder:[pxid contentView]];
} else {
// this is useful for menu/tooltip windows where no windowDidMove notification is received
// so they are drawn at high res already at first time
compute_mapped_to_retina(w);
x->changed_resolution(false);
} else { // a top-level window
[cw makeKeyAndOrderFront:nil];
}

if (!w->parent()) {
// this may be useful for menu/tooltip windows where no windowDidMove notification is received
crect = [[cw contentView] frame];
w->w(int(crect.size.width));
w->h(int(crect.size.height));
crect = [cw frame];
w->x(int(crect.origin.x));
w->y(int(main_screen_height - (crect.origin.y + w->h())));
}

int old_event = Fl::e_number;
w->handle(Fl::e_number = FL_SHOW);
Fl::e_number = old_event;
Expand Down

0 comments on commit 157eb68

Please sign in to comment.