diff options
Diffstat (limited to 'chrome/browser/cocoa/tab_strip_controller.mm')
-rw-r--r-- | chrome/browser/cocoa/tab_strip_controller.mm | 92 |
1 files changed, 75 insertions, 17 deletions
diff --git a/chrome/browser/cocoa/tab_strip_controller.mm b/chrome/browser/cocoa/tab_strip_controller.mm index 524d11c..5d33a32 100644 --- a/chrome/browser/cocoa/tab_strip_controller.mm +++ b/chrome/browser/cocoa/tab_strip_controller.mm @@ -47,6 +47,10 @@ return self; } ++ (CGFloat)defaultTabHeight { + return 24.0; +} + // Finds the associated TabContentsController at the given |index| and swaps // out the sole child of the contentArea to display its contents. - (void)swapInTabAtIndex:(NSInteger)index { @@ -119,11 +123,29 @@ // Called when the user closes a tab. Asks the model to close the tab. - (void)closeTab:(id)sender { - int index = [self indexForTabView:sender]; - if (index >= 0 && tabModel_->ContainsIndex(index)) - tabModel_->CloseTabContentsAt(index); + if ([self numberOfTabViews] > 1) { + int index = [self indexForTabView:sender]; + if (index >= 0 && tabModel_->ContainsIndex(index)) + tabModel_->CloseTabContentsAt(index); + } else { + // Use the standard window close if this is the last tab + // this prevents the tab from being removed from the model until after + // the window dissapears + [[tabView_ window] performClose:nil]; + } +} + + +- (void)insertPlaceholderForTab:(TabView*)tab + frame:(NSRect)frame + yStretchiness:(CGFloat)yStretchiness { + placeholderTab_ = tab; + placeholderFrame_ = frame; + placeholderStretchiness_ = yStretchiness; + [self layoutTabs]; } + // Lay out all tabs in the order of their TabContentsControllers, which matches // the ordering in the TabStripModel. This call isn't that expensive, though // it is O(n) in the number of tabs. Tabs will animate to their new position @@ -152,24 +174,45 @@ kMaxTabWidth), kMinTabWidth); + CGFloat minX = NSMinX(placeholderFrame_); + + NSUInteger i = 0; + NSInteger gap = -1; for (TabController* tab in tabArray_.get()) { - // BOOL isPlaceholder = ![[[tab view] superview] isEqual:tabView_]; - BOOL isPlaceholder = NO; + BOOL isPlaceholder = [[tab view] isEqual:placeholderTab_]; NSRect tabFrame = [[tab view] frame]; - // If the tab is all the way on the left, we consider it a new tab. We - // need to show it, but not animate the movement. We do however want to - // animate the display. - BOOL newTab = NSMinX(tabFrame) == 0; + tabFrame.size.height = [[self class] defaultTabHeight]; + tabFrame.origin.y = 0; + tabFrame.origin.x = offset; + + // If the tab is hidden, we consider it a new tab. We make it visible + // and animate it in. + BOOL newTab = [[tab view] isHidden]; if (newTab) { - id visibilityTarget = visible ? [[tab view] animator] : [tab view]; - [visibilityTarget setHidden:NO]; + [[tab view] setHidden:NO]; } - tabFrame.origin = NSMakePoint(offset, 0); - if (!isPlaceholder) { - // Set the tab's new frame and animate the tab to its new location. Don't - // animate if the window isn't visible or if the tab is new. - BOOL animate = visible && !newTab; - id frameTarget = animate ? [[tab view] animator] : [tab view]; + + if (isPlaceholder) { + tabFrame.origin.x = placeholderFrame_.origin.x; + tabFrame.size.height += 10.0 * placeholderStretchiness_; + [[tab view] setFrame:tabFrame]; + continue; + } else { + // If our left edge is to the left of the placeholder's left, but our mid + // is to the right of it we should slide over to make space for it. + if (placeholderTab_ && gap < 0 && NSMidX(tabFrame) > minX) { + gap = i; + offset += NSWidth(tabFrame); + offset -= kTabOverlap; + tabFrame.origin.x = offset; + } + + // Animate the tab in by putting it below the horizon. + if (newTab && visible) { + [[tab view] setFrame:NSOffsetRect(tabFrame, 0, -NSHeight(tabFrame))]; + } + + id frameTarget = visible ? [[tab view] animator] : [tab view]; tabFrame.size.width = [tab selected] ? kMaxTabWidth : baseTabWidth; [frameTarget setFrame:tabFrame]; } @@ -178,11 +221,13 @@ offset += NSWidth(tabFrame); offset -= kTabOverlap; } + i++; } // Move the new tab button into place [[newTabButton_ animator] setFrameOrigin: NSMakePoint(MIN(availableWidth, offset + kNewTabButtonOffset), 0)]; + if (i > 0) [[newTabButton_ animator] setHidden:NO]; [NSAnimationContext endGrouping]; } @@ -222,6 +267,9 @@ TabController* newController = [self newTab]; [tabArray_ insertObject:newController atIndex:index]; NSView* newView = [newController view]; + [newView setFrame:NSOffsetRect([newView frame], + 0, [[self class] defaultTabHeight])]; + [tabView_ addSubview:newView positioned:inForeground ? NSWindowAbove : NSWindowBelow relativeTo:nil]; @@ -301,6 +349,16 @@ [updatedController tabDidChange:contents]; } +- (NSView *)selectedTabView { + int selectedIndex = tabModel_->selected_index(); + return [self viewAtIndex:selectedIndex]; +} + +- (void)dropTabView:(NSView *)view atIndex:(NSUInteger)index { + // TODO(pinkerton): implement drop + NOTIMPLEMENTED(); +} + // Return the rect, in WebKit coordinates (flipped), of the window's grow box // in the coordinate system of the content area of the currently selected tab. - (NSRect)selectedTabGrowBoxRect { |