| Index: chrome/browser/ui/cocoa/tabs/tab_strip_controller.mm
|
| diff --git a/chrome/browser/ui/cocoa/tabs/tab_strip_controller.mm b/chrome/browser/ui/cocoa/tabs/tab_strip_controller.mm
|
| index fd7ad450a8f03932f4b5cf648a967c7295cf1ebe..c09b8d45e10a89a4540ba158cf8c10f7c6c4f006 100644
|
| --- a/chrome/browser/ui/cocoa/tabs/tab_strip_controller.mm
|
| +++ b/chrome/browser/ui/cocoa/tabs/tab_strip_controller.mm
|
| @@ -27,6 +27,7 @@
|
| #include "chrome/browser/sidebar/sidebar_container.h"
|
| #include "chrome/browser/sidebar/sidebar_manager.h"
|
| #include "chrome/browser/tabs/tab_strip_model.h"
|
| +#include "chrome/browser/tabs/tab_strip_selection_model.h"
|
| #include "chrome/browser/ui/browser.h"
|
| #include "chrome/browser/ui/browser_navigator.h"
|
| #include "chrome/browser/ui/find_bar/find_tab_helper.h"
|
| @@ -44,6 +45,7 @@
|
| #include "chrome/browser/ui/find_bar/find_bar_controller.h"
|
| #include "chrome/browser/ui/title_prefix_matcher.h"
|
| #include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h"
|
| +#include "chrome/browser/ui/tabs/tab_menu_model.h"
|
| #include "chrome/common/chrome_switches.h"
|
| #include "chrome/common/pref_names.h"
|
| #include "content/browser/tab_contents/navigation_controller.h"
|
| @@ -622,7 +624,7 @@ class NotificationBridge : public NotificationObserver {
|
| // |index|, this returns |index| + 2. If there are no closing tabs, this will
|
| // return |index|.
|
| - (NSInteger)indexFromModelIndex:(NSInteger)index {
|
| - DCHECK(index >= 0);
|
| + DCHECK_GE(index, 0);
|
| if (index < 0)
|
| return index;
|
|
|
| @@ -697,8 +699,18 @@ class NotificationBridge : public NotificationObserver {
|
| - (void)selectTab:(id)sender {
|
| DCHECK([sender isKindOfClass:[NSView class]]);
|
| int index = [self modelIndexForTabView:sender];
|
| - if (tabStripModel_->ContainsIndex(index))
|
| - tabStripModel_->SelectTabContentsAt(index, true);
|
| + NSUInteger modifiers = [[NSApp currentEvent] modifierFlags];
|
| + if (tabStripModel_->ContainsIndex(index)) {
|
| + if (modifiers & NSCommandKeyMask && modifiers & NSShiftKeyMask) {
|
| + tabStripModel_->AddSelectionFromAnchorTo(index);
|
| + } else if (modifiers & NSShiftKeyMask) {
|
| + tabStripModel_->ExtendSelectionTo(index);
|
| + } else if (modifiers & NSCommandKeyMask) {
|
| + tabStripModel_->ToggleSelectionAt(index);
|
| + } else if (!tabStripModel_->IsTabSelected(index)) {
|
| + tabStripModel_->SelectTabContentsAt(index, true);
|
| + }
|
| + }
|
| }
|
|
|
| // Called when the user closes a tab. Asks the model to close the tab. |sender|
|
| @@ -771,6 +783,13 @@ class NotificationBridge : public NotificationObserver {
|
| return tabStripModel_->IsContextMenuCommandEnabled(index, command) ? YES : NO;
|
| }
|
|
|
| +// Returns a context menu model for a given controller. Caller owns the result.
|
| +- (ui::SimpleMenuModel*)contextMenuModelForController:(TabController*)controller
|
| + menuDelegate:(ui::SimpleMenuModel::Delegate*)delegate {
|
| + int index = [self modelIndexForTabView:[controller view]];
|
| + return new TabMenuModel(delegate, tabStripModel_, index);
|
| +}
|
| +
|
| - (void)insertPlaceholderForTab:(TabView*)tab
|
| frame:(NSRect)frame
|
| yStretchiness:(CGFloat)yStretchiness {
|
| @@ -1150,7 +1169,7 @@ class NotificationBridge : public NotificationObserver {
|
| atIndex:(NSInteger)modelIndex
|
| userGesture:(bool)wasUserGesture {
|
| // Take closing tabs into account.
|
| - NSInteger index = [self indexFromModelIndex:modelIndex];
|
| + NSInteger activeIndex = [self indexFromModelIndex:modelIndex];
|
|
|
| if (oldContents && oldContents != newContents) {
|
| int oldModelIndex =
|
| @@ -1165,17 +1184,26 @@ class NotificationBridge : public NotificationObserver {
|
| }
|
| }
|
|
|
| - // De-select all other tabs and select the new tab.
|
| + // First get the vector of indices, which is allays sorted in ascending order.
|
| + TabStripSelectionModel::SelectedIndices selection(
|
| + tabStripModel_->selection_model().selected_indices());
|
| + // Iterate through all of the tabs, selecting each as necessary.
|
| + TabStripSelectionModel::SelectedIndices::iterator iter = selection.begin();
|
| int i = 0;
|
| for (TabController* current in tabArray_.get()) {
|
| - [current setSelected:(i == index) ? YES : NO];
|
| + BOOL selected = iter != selection.end() &&
|
| + [self indexFromModelIndex:*iter] == i;
|
| + [current setSelected:selected];
|
| + [current setActive:i == activeIndex];
|
| + if (selected)
|
| + ++iter;
|
| ++i;
|
| }
|
|
|
| // Tell the new tab contents it is about to become the selected tab. Here it
|
| // can do things like make sure the toolbar is up to date.
|
| TabContentsController* newController =
|
| - [tabContentsArray_ objectAtIndex:index];
|
| + [tabContentsArray_ objectAtIndex:activeIndex];
|
| [newController willBecomeSelectedTab];
|
|
|
| // Relayout for new tabs and to let the selected tab grow to be larger in
|
| @@ -1511,19 +1539,19 @@ class NotificationBridge : public NotificationObserver {
|
| [self updateCommonTitlePrefix];
|
| }
|
|
|
| -- (void)setFrameOfSelectedTab:(NSRect)frame {
|
| - NSView* view = [self selectedTabView];
|
| +- (void)setFrameOfActiveTab:(NSRect)frame {
|
| + NSView* view = [self activeTabView];
|
| NSValue* identifier = [NSValue valueWithPointer:view];
|
| [targetFrames_ setObject:[NSValue valueWithRect:frame]
|
| forKey:identifier];
|
| [view setFrame:frame];
|
| }
|
|
|
| -- (NSView*)selectedTabView {
|
| - int selectedIndex = tabStripModel_->selected_index();
|
| +- (NSView*)activeTabView {
|
| + int activeIndex = tabStripModel_->selected_index();
|
| // Take closing tabs into account. They can't ever be selected.
|
| - selectedIndex = [self indexFromModelIndex:selectedIndex];
|
| - return [self viewAtIndex:selectedIndex];
|
| + activeIndex = [self indexFromModelIndex:activeIndex];
|
| + return [self viewAtIndex:activeIndex];
|
| }
|
|
|
| // Find the model index based on the x coordinate of the placeholder. If there
|
| @@ -1748,19 +1776,19 @@ class NotificationBridge : public NotificationObserver {
|
| // ones.
|
| NSMutableArray* subviews = [NSMutableArray arrayWithArray:permanentSubviews_];
|
|
|
| - NSView* selectedTabView = nil;
|
| + NSView* activeTabView = nil;
|
| // Go through tabs in reverse order, since |subviews| is bottom-to-top.
|
| for (TabController* tab in [tabArray_ reverseObjectEnumerator]) {
|
| NSView* tabView = [tab view];
|
| - if ([tab selected]) {
|
| - DCHECK(!selectedTabView);
|
| - selectedTabView = tabView;
|
| + if ([tab active]) {
|
| + DCHECK(!activeTabView);
|
| + activeTabView = tabView;
|
| } else {
|
| [subviews addObject:tabView];
|
| }
|
| }
|
| - if (selectedTabView) {
|
| - [subviews addObject:selectedTabView];
|
| + if (activeTabView) {
|
| + [subviews addObject:activeTabView];
|
| }
|
| [tabStripView_ setSubviews:subviews];
|
| [self setTabTrackingAreasEnabled:mouseInside_];
|
|
|