Bug 1533562 - Do not move the TitlebarGradientView from a ToolbarWindow into a BorderlessWindow when hiding the window chrome. r=spohl
☠☠ backed out by 73e8dcb8be07 ☠ ☠
authorMarkus Stange <mstange@themasta.com>
Mon, 22 Apr 2019 19:27:09 +0000
changeset 470395 b4440b1833ece120e7680763b55168913b18e0d4
parent 470394 8970cdb3c04a11ddbe86c53d5e759685949a0cb3
child 470396 19f0462bb47a3ae0e301b7ff2723407a9c178c2d
push id35905
push userdvarga@mozilla.com
push dateTue, 23 Apr 2019 09:53:27 +0000
treeherdermozilla-central@831918f009f6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersspohl
bugs1533562
milestone68.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1533562 - Do not move the TitlebarGradientView from a ToolbarWindow into a BorderlessWindow when hiding the window chrome. r=spohl Differential Revision: https://phabricator.services.mozilla.com/D25516
widget/cocoa/nsCocoaWindow.h
widget/cocoa/nsCocoaWindow.mm
--- a/widget/cocoa/nsCocoaWindow.h
+++ b/widget/cocoa/nsCocoaWindow.h
@@ -73,16 +73,25 @@ typedef struct _nsCocoaWindowList {
 - (void)mouseMoved:(NSEvent*)aEvent;
 - (void)updateTrackingArea;
 - (NSView*)trackingAreaView;
 
 - (void)setBeingShown:(BOOL)aValue;
 - (BOOL)isBeingShown;
 - (BOOL)isVisibleOrBeingShown;
 
+// Returns an autoreleased NSArray containing the NSViews that we consider the
+// "contents" of this window. All views in the returned array are subviews of
+// this window's content view. However, the array may not include all of the
+// content view's subviews; concretely, the ToolbarWindow implementation will
+// exclude its TitlebarGradientView from the array that is returned here.
+// In the vast majority of cases, the array will only have a single element:
+// this window's mainChildView.
+- (NSArray<NSView*>*)contentViewContents;
+
 - (ChildView*)mainChildView;
 
 - (NSArray*)titlebarControls;
 
 - (void)setWantsTitleDrawn:(BOOL)aDrawTitle;
 - (BOOL)wantsTitleDrawn;
 
 - (void)setUseBrightTitlebarForeground:(BOOL)aBrightForeground;
--- a/widget/cocoa/nsCocoaWindow.mm
+++ b/widget/cocoa/nsCocoaWindow.mm
@@ -1204,36 +1204,39 @@ void nsCocoaWindow::HideWindowChrome(boo
   // Remove child windows.
   NSArray* childWindows = [mWindow childWindows];
   NSEnumerator* enumerator = [childWindows objectEnumerator];
   NSWindow* child = nil;
   while ((child = [enumerator nextObject])) {
     [mWindow removeChildWindow:child];
   }
 
-  // Remove the content view.
-  NSView* contentView = [mWindow contentView];
-  [contentView retain];
-  [contentView removeFromSuperviewWithoutNeedingDisplay];
+  // Remove the views in the old window's content view.
+  // The NSArray is autoreleased and retains its NSViews.
+  NSArray<NSView*>* contentViewContents = [mWindow contentViewContents];
+  for (NSView* view in contentViewContents) {
+    [view removeFromSuperviewWithoutNeedingDisplay];
+  }
 
   // Save state (like window title).
   NSMutableDictionary* state = [mWindow exportState];
 
   // Recreate the window with the right border style.
   NSRect frameRect = [mWindow frame];
   DestroyNativeWindow();
   nsresult rv = CreateNativeWindow(frameRect, aShouldHide ? eBorderStyle_none : mBorderStyle, true);
   NS_ENSURE_SUCCESS_VOID(rv);
 
   // Re-import state.
   [mWindow importState:state];
 
-  // Reparent the content view.
-  [mWindow setContentView:contentView];
-  [contentView release];
+  // Add the old content view subviews to the new window's content view.
+  for (NSView* view in contentViewContents) {
+    [[mWindow contentView] addSubview:view];
+  }
 
   // Reparent child windows.
   enumerator = [childWindows objectEnumerator];
   while ((child = [enumerator nextObject])) {
     [mWindow addChildWindow:child ordered:NSWindowAbove];
   }
 
   // Show the new window.
@@ -2901,16 +2904,20 @@ static const NSString* kStateCollectionB
   return mBrightTitlebarForeground;
 }
 
 - (NSView*)trackingAreaView {
   NSView* contentView = [self contentView];
   return [contentView superview] ? [contentView superview] : contentView;
 }
 
+- (NSArray<NSView*>*)contentViewContents {
+  return [[[[self contentView] subviews] copy] autorelease];
+}
+
 - (ChildView*)mainChildView {
   NSView* contentView = [self contentView];
   NSView* lastView = [[contentView subviews] lastObject];
   if ([lastView isKindOfClass:[ChildView class]]) {
     return (ChildView*)lastView;
   }
   return nil;
 }
@@ -3132,20 +3139,16 @@ static const NSString* kStateCollectionB
 
   CGContextRestoreGState(ctx);
 }
 
 - (BOOL)isOpaque {
   return YES;
 }
 
-- (BOOL)mouseDownCanMoveWindow {
-  return YES;
-}
-
 - (NSView*)hitTest:(NSPoint)aPoint {
   return nil;
 }
 
 @end
 
 // This class allows us to exercise control over the window's title bar. It is
 // used for all windows with titlebars.
@@ -3207,16 +3210,25 @@ static const NSString* kStateCollectionB
   NS_OBJC_END_TRY_ABORT_BLOCK_NIL;
 }
 
 - (void)dealloc {
   [mTitlebarGradientView release];
   [super dealloc];
 }
 
+- (NSArray<NSView*>*)contentViewContents {
+  NSMutableArray<NSView*>* contents = [[[self contentView] subviews] mutableCopy];
+  if (mTitlebarGradientView) {
+    // Do not include the titlebar gradient view in the returned array.
+    [contents removeObject:mTitlebarGradientView];
+  }
+  return [contents autorelease];
+}
+
 - (void)updateTitlebarGradientViewPresence {
   BOOL needTitlebarView = ![self drawsContentsIntoWindowFrame];
   if (needTitlebarView && !mTitlebarGradientView) {
     mTitlebarGradientView = [[TitlebarGradientView alloc] initWithFrame:[self titlebarRect]];
     mTitlebarGradientView.autoresizingMask = NSViewWidthSizable | NSViewMinYMargin;
     [self.contentView addSubview:mTitlebarGradientView];
   } else if (!needTitlebarView && mTitlebarGradientView) {
     [mTitlebarGradientView removeFromSuperview];