tab jumpback like in firefox (bug 342492)

This commit is contained in:
pinkerton%aol.net 2006-06-23 03:10:23 +00:00
Родитель 5a8f39facf
Коммит 55f0064389
7 изменённых файлов: 118 добавлений и 12 удалений

Просмотреть файл

@ -52,6 +52,10 @@ extern NSString* const kTabBarBackgroundDoubleClickedNotification;
BOOL mLastClickIsPotentialDrag;
BOOL mVisible; // YES if the view is in the hierarchy
IBOutlet BrowserTabBarView * mTabBar;
// if non-nil, the tab to jump back to when the currently visible tab is
// closed.
BrowserTabViewItem* mJumpbackTab;
}
+ (BrowserTabViewItem*)makeNewTabItem;
@ -72,4 +76,11 @@ extern NSString* const kTabBarBackgroundDoubleClickedNotification;
- (void)setVisible:(BOOL)show;
- (void)windowClosed;
// get and set the "jumpback tab", the tab that is jumped to when the currently
// visible tab is closed. Reset automatically when switching tabs or after
// jumping back. This isn't designed to be a tab history, it only lives for a very
// well-defined period.
- (void)setJumpbackTab:(BrowserTabViewItem*)inTab;
- (BrowserTabViewItem*)jumpbackTab;
@end

Просмотреть файл

@ -96,6 +96,14 @@ NSString* const kTabBarBackgroundDoubleClickedNotification = @"kTabBarBackground
[self registerForDraggedTypes:[NSArray arrayWithObjects:
kCaminoBookmarkListPBoardType, kWebURLsWithTitlesPboardType,
NSStringPboardType, NSFilenamesPboardType, NSURLPboardType, nil]];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(tabWillChange:)
name:kTabWillChangeNotifcation object:nil];
}
- (void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[super dealloc];
}
/******************************************/
@ -119,6 +127,9 @@ NSString* const kTabBarBackgroundDoubleClickedNotification = @"kTabBarBackground
- (void)addTabViewItem:(NSTabViewItem *)tabViewItem
{
// creating a new tab means clearing the jumpback tab.
[self setJumpbackTab:nil];
[super addTabViewItem:tabViewItem];
// the new tab view item needs to have its tab visibility synchronized to the tab bar so that
// its content view will be hooked up correctly
@ -133,17 +144,34 @@ NSString* const kTabBarBackgroundDoubleClickedNotification = @"kTabBarBackground
// of the tab being removed. Users, however, want the tab to the right to
// be selected. This also matches how mozilla works. Select the right tab
// first so we don't take the hit of displaying the left tab before we switch.
//
// Ben and I talked about a way to improve this slightly, with the concept
// of a "jumpback tab" that is associated with a tab that is opened via
// cmd-click or single-window-mode. When the current tab is closed, we jump
// back to that tab, the thought being they are related. Switching tabs in
// any way (even closing a tab) will clear the jumpback tab and return to
// the "select to the right" behavior.
// make sure the close button and spinner get removed
[(BrowserTabViewItem *)tabViewItem willBeRemoved:YES];
if ([self selectedTabViewItem] == tabViewItem)
[self selectNextTabViewItem:self];
if ([self selectedTabViewItem] == tabViewItem) {
if (mJumpbackTab)
[mJumpbackTab selectTab:self];
else
[self selectNextTabViewItem:self];
}
[super removeTabViewItem:tabViewItem];
[self showOrHideTabsAsAppropriate];
// clear the jumpback tab, it's served its purpose
[self setJumpbackTab:nil];
}
- (void)insertTabViewItem:(NSTabViewItem *)tabViewItem atIndex:(int)index
{
// inserting a new tab means clearing the jumpback tab.
[self setJumpbackTab:nil];
[super insertTabViewItem:tabViewItem atIndex:index];
[self showOrHideTabsAsAppropriate];
}
@ -453,4 +481,38 @@ NSString* const kTabBarBackgroundDoubleClickedNotification = @"kTabBarBackground
return [[[BrowserTabViewItem alloc] init] autorelease];
}
#pragma mark -
//
// get and set the "jumpback tab", the tab that is jumped to when the currently
// visible tab is closed. Reset automatically when switching tabs or after
// jumping back. This isn't designed to be a tab history, it only lives for a very
// well-defined period.
//
- (void)setJumpbackTab:(BrowserTabViewItem*)inTab
{
NSLog(@"setting jumpback to %d", inTab);
mJumpbackTab = inTab;
}
- (BrowserTabViewItem*)jumpbackTab
{
return mJumpbackTab;
}
//
// tabWillChange:
//
// Called when the tab is about to change and is our cue to clear out the jumpback tab.
//
- (void)tabWillChange:(NSNotification*)inNotify
{
// If the user clicks on the same tab that's already selected, we'll still get
// a notification, so do nothing if we're "switching" to the currently selected tab
id object = [inNotify object];
if (!object || object != [self selectedTabViewItem])
[self setJumpbackTab:nil];
}
@end

Просмотреть файл

@ -40,6 +40,12 @@
#import "IconTabViewItem.h"
// sent when the current tab will changed. The object is the tab that's being
// switched to. NSTabView does have a delegate method when the tab changes,
// but no notification and we don't want to take over the delegate for internal
// implementation.
extern NSString* const kTabWillChangeNotifcation;
// a subclass of IconTabViewItem that handles dragging of site icons
@class BrowserTabItemContainerView;
@class TruncatingTextAndImageCell;

Просмотреть файл

@ -50,6 +50,8 @@
#import "TabButtonCell.h"
#import "RolloverImageButton.h"
NSString* const kTabWillChangeNotifcation = @"kTabWillChangeNotifcation";
// we cannot use the spinner before 10.2, so don't allow it. This is the
// version of appkit in 10.2 (taken from the 10.3 SDK headers which we cannot use).
const double kJaguarAppKitVersion = 663;
@ -240,6 +242,7 @@ const int kMenuTruncationChars = 60;
}
mSelectTabOnMouseUp = NO;
[[NSNotificationCenter defaultCenter] postNotificationName:kTabWillChangeNotifcation object:mTabViewItem];
[[mTabViewItem tabView] selectTabViewItem:mTabViewItem];
}
@ -247,6 +250,7 @@ const int kMenuTruncationChars = 60;
{
if (mSelectTabOnMouseUp)
{
[[NSNotificationCenter defaultCenter] postNotificationName:kTabWillChangeNotifcation object:mTabViewItem];
[[mTabViewItem tabView] selectTabViewItem:mTabViewItem];
mSelectTabOnMouseUp = NO;
}
@ -522,6 +526,7 @@ const int kMenuTruncationChars = 60;
- (void) selectTab:(id)sender
{
[[NSNotificationCenter defaultCenter] postNotificationName:kTabWillChangeNotifcation object:self];
[[self tabView] selectTabViewItem:self];
}

Просмотреть файл

@ -262,7 +262,7 @@ typedef enum
- (IBAction)frameToThisWindow:(id)sender;
- (BrowserWindowController*)openNewWindowWithURL: (NSString*)aURLSpec referrer:(NSString*)aReferrer loadInBackground: (BOOL)aLoadInBG allowPopups:(BOOL)inAllowPopups;
- (void)openNewTabWithURL: (NSString*)aURLSpec referrer: (NSString*)aReferrer loadInBackground: (BOOL)aLoadInBG allowPopups:(BOOL)inAllowPopups;
- (void)openNewTabWithURL: (NSString*)aURLSpec referrer: (NSString*)aReferrer loadInBackground: (BOOL)aLoadInBG allowPopups:(BOOL)inAllowPopups setJumpback:(BOOL)inSetJumpback;
- (void)openURLArray:(NSArray*)urlArray tabOpenPolicy:(ETabOpenPolicy)tabPolicy allowPopups:(BOOL)inAllowPopups;
- (void)openURLArrayReplacingTabs:(NSArray*)urlArray closeExtraTabs:(BOOL)closeExtra allowPopups:(BOOL)inAllowPopups;

Просмотреть файл

@ -1894,7 +1894,7 @@ enum BWCOpenDest {
if ([resolvedURLs count] == 1) {
resolvedURL = [resolvedURLs lastObject];
if (inDest == kDestinationNewTab)
[self openNewTabWithURL:resolvedURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
[self openNewTabWithURL:resolvedURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO setJumpback:NO];
else if (inDest == kDestinationNewWindow)
[self openNewWindowWithURL:resolvedURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
else // if it's not a new window or a new tab, load into the current view
@ -1960,7 +1960,7 @@ enum BWCOpenDest {
if (canUseCache)
[self openNewTabWithDescriptor:desc displayType:nsIWebPageDescriptor::DISPLAY_AS_SOURCE loadInBackground:loadInBackground];
else
[self openNewTabWithURL:viewSource referrer:nil loadInBackground:loadInBackground allowPopups:NO];
[self openNewTabWithURL:viewSource referrer:nil loadInBackground:loadInBackground allowPopups:NO setJumpback:NO];
}
else {
// open a new window and hide the toolbars for prettyness
@ -2070,7 +2070,7 @@ enum BWCOpenDest {
aDomain = [NSString stringWithUTF8String:spec.get()];
if (inDest == kDestinationNewTab)
[self openNewTabWithURL:aDomain referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
[self openNewTabWithURL:aDomain referrer:nil loadInBackground:inLoadInBG allowPopups:NO setJumpback:NO];
else if (inDest == kDestinationNewWindow)
[self openNewWindowWithURL:aDomain referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
else // if it's not a new window or a new tab, load into the current view
@ -2097,7 +2097,7 @@ enum BWCOpenDest {
[escapedSearchString release];
if (inDest == kDestinationNewTab)
[self openNewTabWithURL:searchURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
[self openNewTabWithURL:searchURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO setJumpback:NO];
else if (inDest == kDestinationNewWindow)
[self openNewWindowWithURL:searchURL referrer:nil loadInBackground:inLoadInBG allowPopups:NO];
else // if it's not a new window or a new tab, load into the current view
@ -2552,7 +2552,7 @@ enum BWCOpenDest {
// assumes mContextMenuNode has been set
NSString* frameURL = [self getContextMenuNodeDocumentURL];
if ([frameURL length] > 0)
[self openNewTabWithURL:frameURL referrer:nil loadInBackground:NO allowPopups:NO]; // follow the pref?
[self openNewTabWithURL:frameURL referrer:nil loadInBackground:NO allowPopups:NO setJumpback:NO]; // follow the pref?
}
- (IBAction)frameToThisWindow:(id)sender
@ -2786,6 +2786,8 @@ enum BWCOpenDest {
- (IBAction)previousTab:(id)sender
{
// pass |nil| because it's way too complicated to compute the previous tab.
[[NSNotificationCenter defaultCenter] postNotificationName:kTabWillChangeNotifcation object:nil];
if ([mTabBrowser indexOfTabViewItem:[mTabBrowser selectedTabViewItem]] == 0)
[mTabBrowser selectLastTabViewItem:sender];
else
@ -2794,6 +2796,8 @@ enum BWCOpenDest {
- (IBAction)nextTab:(id)sender
{
// pass |nil| because it's way too complicated to compute the next tab.
[[NSNotificationCenter defaultCenter] postNotificationName:kTabWillChangeNotifcation object:nil];
if ([mTabBrowser indexOfTabViewItem:[mTabBrowser selectedTabViewItem]] == [mTabBrowser numberOfTabViewItems] - 1)
[mTabBrowser selectFirstTabViewItem:sender];
else
@ -2978,9 +2982,19 @@ enum BWCOpenDest {
return browser;
}
-(void)openNewTabWithURL:(NSString*)aURLSpec referrer:(NSString*)aReferrer loadInBackground:(BOOL)aLoadInBG allowPopups:(BOOL)inAllowPopups
-(void)openNewTabWithURL:(NSString*)aURLSpec referrer:(NSString*)aReferrer loadInBackground:(BOOL)aLoadInBG
allowPopups:(BOOL)inAllowPopups setJumpback:(BOOL)inSetJumpback
{
BrowserTabViewItem* previouslySelected = [mTabBrowser selectedTabViewItem];
BrowserTabViewItem* newTab = [self openNewTab:aLoadInBG];
// if instructed, tell the tab browser to remember the currently selected tab to
// jump back to if this new one is closed w/out switching to any other tabs.
// This must come after the call to |openNewTab:| which clears the jumpback
// tab and changes the selected tab to the new tab.
if (inSetJumpback)
[mTabBrowser setJumpbackTab:previouslySelected];
[[newTab view] loadURI:aURLSpec referrer:aReferrer flags:NSLoadFlagsNone activate:!aLoadInBG allowPopups:inAllowPopups];
}
@ -2993,7 +3007,15 @@ enum BWCOpenDest {
//
- (CHBrowserView*)createNewTabBrowser:(BOOL)inLoadInBG
{
BrowserTabViewItem* previouslySelected = [mTabBrowser selectedTabViewItem];
BrowserTabViewItem* newTab = [self openNewTab:inLoadInBG];
// tell the tab browser to remember the currently selected tab to
// jump back to if this new one is closed w/out switching to any other tabs.
// This must come after the call to |openNewTab:| which clears the jumpback
// tab and changes the selected tab to the new tab.
[mTabBrowser setJumpbackTab:previouslySelected];
return [[newTab view] getBrowserView];
}
@ -3439,7 +3461,7 @@ enum BWCOpenDest {
if (aUseWindow)
[self openNewWindowWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO];
else
[self openNewTabWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO];
[self openNewTabWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO setJumpback:NO];
}
- (IBAction)savePageAs:(id)aSender
@ -3526,7 +3548,7 @@ enum BWCOpenDest {
if (modifiers & NSShiftKeyMask)
loadInBG = !loadInBG; // shift key should toggle the foreground/background pref as it does elsewhere
if (loadInTab)
[self openNewTabWithURL:urlStr referrer:referrer loadInBackground:loadInBG allowPopups:NO];
[self openNewTabWithURL:urlStr referrer:referrer loadInBackground:loadInBG allowPopups:NO setJumpback:NO];
else
[self openNewWindowWithURL:urlStr referrer:referrer loadInBackground:loadInBG allowPopups:NO];
}

Просмотреть файл

@ -107,7 +107,7 @@ ContentClickListener::MouseClick(nsIDOMEvent* aEvent)
if (shiftKey)
loadInBackground = !loadInBackground;
if (useTab)
[mBrowserController openNewTabWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO];
[mBrowserController openNewTabWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO setJumpback:YES];
else
[mBrowserController openNewWindowWithURL: hrefStr referrer:referrer loadInBackground: loadInBackground allowPopups:NO];
}