Index: ui/base/cocoa/focus_window_set.mm |
diff --git a/ui/base/cocoa/focus_window_set.mm b/ui/base/cocoa/focus_window_set.mm |
index 553db6fe3be597fe14f157d8623852e1f714d14e..c6669eedfda035c113f1cdc2234439f0efa420d5 100644 |
--- a/ui/base/cocoa/focus_window_set.mm |
+++ b/ui/base/cocoa/focus_window_set.mm |
@@ -8,22 +8,44 @@ |
namespace ui { |
+// This attempts to match OS X's native behavior, namely that a window |
+// is only ever deminiaturized if ALL windows on ALL workspaces are |
+// miniaturized. (This callback runs before AppKit picks its own |
+// window to deminiaturize, so we get to pick one from the right set.) |
+// |
+// In addition, limit to the windows on the current |
+// workspace. Otherwise we jump spaces haphazardly. |
+// |
+// NOTE: This is not perfect. If clicking the dock icon resulted in |
+// switching spaces, isOnActiveSpace gives the answer for the PREVIOUS |
+// space. This means that we actually raise the wrong space's |
+// windows. This seems to still work okay. |
+// |
+// However, if we decide to deminiaturize a window instead, that |
+// results in switching spaces and switching back. Fortunately, this |
+// only happens if, say, space 1 contains an app, space 2 contains a |
+// miniaturized browser. We click the icon, OS X switches to space 1, |
+// we deminiaturize the browser, and that triggers switching back. |
void FocusWindowSet(const std::set<NSWindow*>& windows) { |
NSArray* ordered_windows = [NSApp orderedWindows]; |
NSWindow* frontmost_window = nil; |
NSWindow* frontmost_miniaturized_window = nil; |
+ bool all_miniaturized = true; |
for (int i = [ordered_windows count] - 1; i >= 0; i--) { |
NSWindow* win = [ordered_windows objectAtIndex:i]; |
if (windows.find(win) != windows.end()) { |
- if ([win isVisible]) { |
- [win orderFront:nil]; |
- frontmost_window = win; |
- } else if ([win isMiniaturized]) { |
+ if ([win isMiniaturized]) { |
frontmost_miniaturized_window = win; |
+ } else if ([win isVisible]) { |
+ all_miniaturized = false; |
jackhou1
2013/09/02 06:07:23
Could this be:
} else if ([win isVisible])
davidben
2013/09/03 20:01:53
That seems to cause it to get a bit confused. If f
|
+ if ([win isOnActiveSpace]) { |
+ [win orderFront:nil]; |
+ frontmost_window = win; |
+ } |
} |
} |
} |
- if (!frontmost_window && frontmost_miniaturized_window) { |
+ if (all_miniaturized && frontmost_miniaturized_window) { |
[frontmost_miniaturized_window deminiaturize:nil]; |
frontmost_window = frontmost_miniaturized_window; |
} |