2007-10-16 13:22:28 -04:00
var TreeStyleTabService = {
2007-10-23 02:05:44 -04:00
kID : 'treestyletab-id' ,
kCHILDREN : 'treestyletab-children' ,
kPARENT : 'treestyletab-parent' ,
kINSERT _BEFORE : 'treestyletab-insert-before' ,
kSUBTREE _COLLAPSED : 'treestyletab-subtree-collapsed' ,
kCOLLAPSED : 'treestyletab-collapsed' ,
kNEST : 'treestyletab-nest' ,
kDROP _POSITION : 'treestyletab-drop-position' ,
kTABBAR _POSITION : 'treestyletab-tabbar-position' ,
2007-10-26 08:56:04 -04:00
kMODE : 'treestyletab-mode' ,
2007-10-23 02:05:44 -04:00
kUI _INVERTED : 'treestyletab-appearance-inverted' ,
kSCROLLBAR _INVERTED : 'treestyletab-scrollbar-inverted' ,
2007-10-25 18:59:34 -04:00
kALLOW _COLLAPSE : 'treestyletab-allow-subtree-collapse' ,
2007-10-23 02:05:44 -04:00
kSTYLE : 'treestyletab-style' ,
kFIRSTTAB _BORDER : 'treestyletab-firsttab-border' ,
2007-10-18 13:11:03 -04:00
2007-10-20 02:12:22 -04:00
kTWISTY : 'treestyletab-twisty' ,
kTWISTY _CONTAINER : 'treestyletab-twisty-container' ,
kDROP _MARKER : 'treestyletab-drop-marker' ,
kDROP _MARKER _CONTAINER : 'treestyletab-drop-marker-container' ,
kCOUNTER : 'treestyletab-counter' ,
kCOUNTER _CONTAINER : 'treestyletab-counter-container' ,
2007-10-20 07:29:42 -04:00
kSPLITTER : 'treestyletab-splitter' ,
2007-10-16 13:22:28 -04:00
2007-10-19 22:44:14 -04:00
kMENUITEM _REMOVESUBTREE _SELECTION : 'multipletab-selection-item-removeTabSubTree' ,
kMENUITEM _REMOVESUBTREE _CONTEXT : 'context-item-removeTabSubTree' ,
2007-10-19 01:27:06 -04:00
2007-10-18 23:05:36 -04:00
kFOCUS _ALL : 0 ,
kFOCUS _VISIBLE : 1 ,
2007-10-19 22:44:14 -04:00
kDROP _BEFORE : - 1 ,
kDROP _ON : 0 ,
kDROP _AFTER : 1 ,
kACTION _MOVE : 1 ,
kACTION _ATTACH : 2 ,
kACTION _PART : 4 ,
2007-10-20 06:24:36 -04:00
kTABBAR _TOP : 1 ,
kTABBAR _BOTTOM : 2 ,
kTABBAR _LEFT : 4 ,
kTABBAR _RIGHT : 8 ,
kTABBAR _HORIZONTAL : 3 ,
kTABBAR _VERTICAL : 12 ,
2007-10-20 04:22:42 -04:00
levelMargin : 12 ,
levelMarginProp : 'margin-left' ,
positionProp : 'screenY' ,
sizeProp : 'height' ,
invertedSizeProp : 'width' ,
2007-10-16 13:22:28 -04:00
NSResolver : {
lookupNamespaceURI : function ( aPrefix )
{
switch ( aPrefix )
{
case 'xul' :
return 'http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul' ;
case 'html' :
case 'xhtml' :
return 'http://www.w3.org/1999/xhtml' ;
case 'xlink' :
return 'http://www.w3.org/1999/xlink' ;
default :
return '' ;
}
}
} ,
get SessionStore ( ) {
if ( ! this . _SessionStore ) {
this . _SessionStore = Components . classes [ '@mozilla.org/browser/sessionstore;1' ] . getService ( Components . interfaces . nsISessionStore ) ;
}
return this . _SessionStore ;
} ,
_SessionStore : null ,
2007-10-20 04:22:42 -04:00
get ObserverService ( ) {
if ( ! this . _ObserverService ) {
this . _ObserverService = Components . classes [ '@mozilla.org/observer-service;1' ] . getService ( Components . interfaces . nsIObserverService ) ;
}
return this . _ObserverService ;
} ,
_ObserverService : null ,
2007-10-22 05:59:43 -04:00
get IOService ( ) {
if ( ! this . _IOService ) {
this . _IOService = Components . classes [ '@mozilla.org/network/io-service;1' ] . getService ( Components . interfaces . nsIIOService ) ;
}
return this . _IOService ;
} ,
_IOService : null ,
2007-10-16 13:22:28 -04:00
2007-10-21 04:16:10 -04:00
/* API */
2007-10-28 12:07:10 -04:00
2007-10-21 04:16:10 -04:00
readyToOpenChildTab : function ( aFrameOrTabBrowser , aMultiple )
{
var frame = this . getFrameFromTabBrowserElements ( aFrameOrTabBrowser ) ;
if ( ! frame ) return ;
2007-10-23 00:33:46 -04:00
var ownerBrowser = this . getTabBrowserFromFrame ( frame ) ;
2007-10-21 04:16:10 -04:00
ownerBrowser . _ _treestyletab _ _readyToAttachNewTab = true ;
ownerBrowser . _ _treestyletab _ _readyToAttachMultiple = aMultiple || false ;
ownerBrowser . _ _treestyletab _ _parentTab = this . getTabFromFrame ( frame , ownerBrowser ) . getAttribute ( this . kID ) ;
} ,
2007-10-21 20:40:04 -04:00
readyToOpenNewTabGroup : function ( aFrameOrTabBrowser )
{
var frame = this . getFrameFromTabBrowserElements ( aFrameOrTabBrowser ) ;
if ( ! frame ) return ;
this . stopToOpenChildTab ( frame ) ;
2007-10-23 00:33:46 -04:00
var ownerBrowser = this . getTabBrowserFromFrame ( frame ) ;
2007-10-21 20:40:04 -04:00
ownerBrowser . _ _treestyletab _ _readyToAttachNewTabGroup = true ;
ownerBrowser . _ _treestyletab _ _readyToAttachMultiple = true ;
} ,
2007-10-21 04:16:10 -04:00
stopToOpenChildTab : function ( aFrameOrTabBrowser )
{
var frame = this . getFrameFromTabBrowserElements ( aFrameOrTabBrowser ) ;
if ( ! frame ) return ;
2007-10-23 00:33:46 -04:00
var ownerBrowser = this . getTabBrowserFromFrame ( frame ) ;
2007-10-21 20:40:04 -04:00
ownerBrowser . _ _treestyletab _ _readyToAttachNewTab = false ;
ownerBrowser . _ _treestyletab _ _readyToAttachNewTabGroup = false ;
ownerBrowser . _ _treestyletab _ _readyToAttachMultiple = false ;
ownerBrowser . _ _treestyletab _ _parentTab = null ;
2007-10-21 04:16:10 -04:00
} ,
2007-10-21 04:17:59 -04:00
checkToOpenChildTab : function ( aFrameOrTabBrowser )
2007-10-21 04:16:10 -04:00
{
var frame = this . getFrameFromTabBrowserElements ( aFrameOrTabBrowser ) ;
if ( ! frame ) return false ;
2007-10-23 00:33:46 -04:00
var ownerBrowser = this . getTabBrowserFromFrame ( frame ) ;
2007-10-21 20:40:04 -04:00
return ownerBrowser . _ _treestyletab _ _readyToAttachNewTab || ownerBrowser . _ _treestyletab _ _readyToAttachNewTabGroup ? true : false ;
2007-10-21 04:16:10 -04:00
} ,
2007-10-28 12:07:10 -04:00
2007-10-28 13:16:48 -04:00
checkReadyToOpenNewChildTab : function ( aFrameOrTabBrowser , aInfo )
2007-10-28 12:07:10 -04:00
{
var frame = this . getFrameFromTabBrowserElements ( aFrameOrTabBrowser ) ;
if ( ! frame ) return false ;
2007-10-28 14:03:24 -04:00
var info = aInfo || { uri : '' } ;
if ( /^javascript:/ . test ( info . uri ) ) return false ;
2007-10-28 13:16:48 -04:00
var external = info . external || { } ;
var internal = info . internal || { } ;
var targetHost = /^\w+:\/\/([^:\/]+)(\/|$)/ . test ( info . uri ) ? RegExp . $1 : null ;
2007-10-28 12:07:10 -04:00
var currentURI = frame . location . href ;
var currentHost = currentURI . match ( /^\w+:\/\/([^:\/]+)(\/|$)/ ) ? RegExp . $1 : null ;
var parentTab = this . getParentTab ( this . getTabFromFrame ( frame ) ) ;
var parentURI = parentTab ? parentTab . linkedBrowser . currentURI : null ;
var parentHost = parentURI && parentURI . spec . match ( /^\w+:\/\/([^:\/]+)(\/|$)/ ) ? RegExp . $1 : null ;
return (
(
2007-10-28 13:16:48 -04:00
internal . newTab &&
2007-10-28 12:07:10 -04:00
currentHost == targetHost &&
2007-10-28 13:16:48 -04:00
currentURI . split ( '#' ) [ 0 ] != info . uri . split ( '#' ) [ 0 ] &&
2007-10-28 12:07:10 -04:00
( this . readyToOpenChildTab (
2007-10-28 13:16:48 -04:00
parentHost == targetHost && ! internal . forceChild ?
2007-10-28 12:07:10 -04:00
parentTab :
frame
) , true )
) ||
(
2007-10-28 13:16:48 -04:00
external . newTab &&
2007-10-28 12:07:10 -04:00
currentHost != targetHost &&
2007-10-28 13:16:48 -04:00
currentURI != 'about:blank' &&
( external . forceChild ? ( this . readyToOpenChildTab ( frame ) , true ) : true )
2007-10-28 12:07:10 -04:00
)
) ;
} ,
2007-10-16 13:22:28 -04:00
/* Utilities */
2007-10-23 00:33:46 -04:00
2007-10-26 05:36:45 -04:00
isEventFiredOnTwisty : function ( aEvent )
2007-10-16 13:22:28 -04:00
{
var tab = this . getTabFromEvent ( aEvent ) ;
if ( ! tab ) return false ;
2007-10-26 05:36:45 -04:00
return tab . hasAttribute ( this . kCHILDREN ) && this . evaluateXPath (
'ancestor-or-self::*[@class="' + this . kTWISTY + '" or @class="tab-icon"]' ,
aEvent . originalTarget || aEvent . target ,
XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue ? true : false ;
2007-10-18 13:11:03 -04:00
} ,
2007-10-18 14:20:54 -04:00
2007-10-16 13:22:28 -04:00
get browser ( )
{
2007-10-26 07:24:59 -04:00
return 'SplitBrowser' in window && this . getTreePref ( 'inSubbrowsers.enabled' ) ? SplitBrowser . activeBrowser : gBrowser ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-18 23:05:36 -04:00
evaluateXPath : function ( aExpression , aContext , aType )
{
if ( ! aType ) aType = XPathResult . ORDERED _NODE _SNAPSHOT _TYPE ;
try {
var xpathResult = document . evaluate (
aExpression ,
aContext ,
this . NSResolver ,
aType ,
null
) ;
}
catch ( e ) {
return {
singleNodeValue : null ,
snapshotLength : 0 ,
snapshotItem : function ( ) {
return null
}
} ;
}
return xpathResult ;
} ,
2007-10-16 13:22:28 -04:00
getArrayFromXPathResult : function ( aXPathResult )
{
var max = aXPathResult . snapshotLength ;
var array = new Array ( max ) ;
if ( ! max ) return array ;
for ( var i = 0 ; i < max ; i ++ )
{
array [ i ] = aXPathResult . snapshotItem ( i ) ;
}
return array ;
} ,
getTabFromEvent : function ( aEvent )
{
2007-10-26 05:36:45 -04:00
return this . evaluateXPath (
'ancestor-or-self::xul:tab' ,
aEvent . originalTarget || aEvent . target , XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-17 12:07:43 -04:00
getTabFromFrame : function ( aFrame , aTabBrowser )
{
var b = aTabBrowser || this . browser ;
var docShell = aFrame . top
. QueryInterface ( Components . interfaces . nsIInterfaceRequestor )
. getInterface ( Components . interfaces . nsIWebNavigation )
. QueryInterface ( Components . interfaces . nsIDocShell ) ;
var tabs = b . mTabContainer . childNodes ;
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
if ( tabs [ i ] . linkedBrowser . docShell == docShell )
return tabs [ i ] ;
}
return null ;
} ,
2007-10-16 13:22:28 -04:00
getTabBrowserFromChildren : function ( aTab )
{
2007-10-17 12:07:43 -04:00
if ( ! aTab ) return null ;
2007-10-16 13:22:28 -04:00
if ( aTab . _ _treestyletab _ _linkedTabBrowser )
return aTab . _ _treestyletab _ _linkedTabBrowser ;
2007-10-26 06:25:59 -04:00
return this . evaluateXPath (
'ancestor-or-self::xul:tabbrowser' ,
aTab ,
XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-23 00:33:46 -04:00
getTabBrowserFromFrame : function ( aFrame )
{
return ( 'SplitBrowser' in window ) ? this . getTabBrowserFromChildren ( SplitBrowser . getSubBrowserAndBrowserFromFrame ( aFrame . top ) . browser ) : gBrowser ;
} ,
2007-10-23 04:19:32 -04:00
2007-10-21 04:16:10 -04:00
getFrameFromTabBrowserElements : function ( aFrameOrTabBrowser )
{
var frame = aFrameOrTabBrowser ;
if ( frame == '[object XULElement]' ) {
if ( frame . localName == 'tab' ) {
frame = frame . linkedBrowser . contentWindow ;
}
else if ( frame . localName == 'browser' ) {
frame = frame . contentWindow ;
}
else {
frame = this . getTabBrowserFromChildren ( frame ) ;
if ( ! frame ) return null ;
frame = frame . contentWindow ;
}
}
if ( ! frame )
frame = this . browser . contentWindow ;
return frame ;
} ,
2007-10-21 11:02:58 -04:00
2007-10-19 02:49:20 -04:00
isTabVertical : function ( aTabOrChild )
{
var b = this . getTabBrowserFromChildren ( aTabOrChild ) ;
if ( ! b ) return false ;
var box = b . mTabContainer . mTabstrip || b . mTabContainer ;
return ( box . getAttribute ( 'orient' ) || window . getComputedStyle ( box , '' ) . getPropertyValue ( '-moz-box-orient' ) ) == 'vertical' ;
} ,
2007-10-24 15:37:21 -04:00
isTabInViewport : function ( aTab )
2007-10-20 12:47:08 -04:00
{
if ( ! aTab ) return false ;
var tabBox = aTab . boxObject ;
var barBox = this . getTabBrowserFromChildren ( aTab ) . mTabContainer . mTabstrip . boxObject ;
return ( tabBox . screenX >= barBox . screenX &&
tabBox . screenX + tabBox . width <= barBox . screenX + barBox . width &&
tabBox . screenY >= barBox . screenY &&
tabBox . screenY + tabBox . height <= barBox . screenY + barBox . height ) ;
} ,
2007-10-19 01:27:06 -04:00
cleanUpTabsArray : function ( aTabs )
2007-10-16 13:22:28 -04:00
{
2007-10-19 01:27:06 -04:00
var b = this . getTabBrowserFromChildren ( aTabs [ 0 ] ) ;
2007-10-16 13:22:28 -04:00
2007-10-19 01:27:06 -04:00
var self = this ;
aTabs = aTabs . map ( function ( aTab ) { return aTab . getAttribute ( self . kID ) ; } ) ;
aTabs . sort ( ) ;
aTabs = aTabs . join ( '|' ) . replace ( /([^\|]+)(\|\1)+/g , '$1' ) . split ( '|' ) ;
2007-10-16 13:22:28 -04:00
2007-10-19 01:27:06 -04:00
for ( var i = 0 , maxi = aTabs . length ; i < maxi ; i ++ )
2007-10-16 13:22:28 -04:00
{
2007-10-19 01:27:06 -04:00
aTabs [ i ] = this . getTabById ( aTabs [ i ] , b ) ;
2007-10-16 13:22:28 -04:00
}
2007-10-19 01:27:06 -04:00
return aTabs ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-22 05:59:43 -04:00
makeURIFromSpec : function ( aURI )
{
var newURI ;
aURI = aURI || '' ;
if ( aURI && String ( aURI ) . indexOf ( 'file:' ) == 0 ) {
var fileHandler = this . IOService . getProtocolHandler ( 'file' ) . QueryInterface ( Components . interfaces . nsIFileProtocolHandler ) ;
var tempLocalFile = fileHandler . getFileFromURLSpec ( aURI ) ;
newURI = this . IOService . newFileURI ( tempLocalFile ) ;
}
else {
newURI = this . IOService . newURI ( aURI , null , null ) ;
}
return newURI ;
} ,
2007-10-19 01:27:06 -04:00
2007-10-16 13:22:28 -04:00
/* Initializing */
2007-10-23 04:19:32 -04:00
2007-10-16 13:22:28 -04:00
init : function ( )
{
if ( ! ( 'gBrowser' in window ) ) return ;
window . removeEventListener ( 'load' , this , false ) ;
2007-10-22 05:59:43 -04:00
document . getElementById ( 'contentAreaContextMenu' ) . addEventListener ( 'popupshowing' , this , false ) ;
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'inSubbrowsers.enabled' ) ) {
2007-10-20 06:44:42 -04:00
var appcontent = document . getElementById ( 'appcontent' ) ;
appcontent . addEventListener ( 'SubBrowserAdded' , this , false ) ;
appcontent . addEventListener ( 'SubBrowserRemoveRequest' , this , false ) ;
}
2007-10-17 09:25:50 -04:00
2007-10-16 13:22:28 -04:00
this . addPrefListener ( this ) ;
2007-10-20 04:22:42 -04:00
this . observe ( null , 'nsPref:changed' , 'extensions.treestyletab.levelMargin' ) ;
2007-10-16 13:22:28 -04:00
2007-10-21 11:02:58 -04:00
this . overrideGlobalFunctions ( ) ;
2007-10-21 13:47:20 -04:00
this . overrideExtensions ( ) ; // hacks.js
2007-10-17 12:07:43 -04:00
2007-10-16 13:22:28 -04:00
this . initTabBrowser ( gBrowser ) ;
} ,
2007-10-23 04:19:32 -04:00
2007-10-16 13:22:28 -04:00
initTabBrowser : function ( aTabBrowser )
{
2007-10-20 08:15:05 -04:00
this . initTabbar ( aTabBrowser ) ;
2007-10-20 06:24:36 -04:00
2007-10-16 13:22:28 -04:00
aTabBrowser . mTabContainer . addEventListener ( 'TreeStyleTab:TabOpen' , this , true ) ;
aTabBrowser . mTabContainer . addEventListener ( 'TabClose' , this , true ) ;
2007-10-17 19:48:30 -04:00
aTabBrowser . mTabContainer . addEventListener ( 'TabMove' , this , true ) ;
aTabBrowser . mTabContainer . addEventListener ( 'SSTabRestoring' , this , true ) ;
2007-10-18 13:11:03 -04:00
aTabBrowser . mTabContainer . addEventListener ( 'click' , this , true ) ;
2007-10-19 02:40:30 -04:00
aTabBrowser . mTabContainer . addEventListener ( 'dblclick' , this , true ) ;
2007-10-18 13:11:03 -04:00
aTabBrowser . mTabContainer . addEventListener ( 'mousedown' , this , true ) ;
aTabBrowser . mTabContainer . addEventListener ( 'select' , this , true ) ;
2007-10-21 11:02:58 -04:00
// aTabBrowser.mPanelContainer.addEventListener('click', this, true);
2007-10-16 13:22:28 -04:00
2007-10-20 04:22:42 -04:00
aTabBrowser . _ _treestyletab _ _levelMargin = - 1 ;
2007-10-20 02:12:22 -04:00
2007-10-21 19:38:50 -04:00
var selectNewTab = '_selectNewTab' in aTabBrowser . mTabContainer ? '_selectNewTab' : 'selectNewTab' ; // Fx3 / Fx2
eval ( 'aTabBrowser.mTabContainer.' + selectNewTab + ' = ' +
aTabBrowser . mTabContainer [ selectNewTab ] . toSource ( ) . replace (
2007-10-18 13:11:03 -04:00
/\{/ ,
< > < ! [ CDATA [
{
2007-10-18 23:05:36 -04:00
if ( arguments [ 0 ] . _ _treestyletab _ _preventSelect ) {
arguments [ 0 ] . _ _treestyletab _ _preventSelect = false ;
return ;
}
] ] > < / >
)
) ;
eval ( 'aTabBrowser.mTabContainer.advanceSelectedTab = ' +
aTabBrowser . mTabContainer . advanceSelectedTab . toSource ( ) . replace (
/\{/ ,
< > < ! [ CDATA [
{
2007-10-26 07:24:59 -04:00
if ( TreeStyleTabService . getTreePref ( 'focusMode' ) == TreeStyleTabService . kFOCUS _VISIBLE ) {
2007-10-19 22:44:14 -04:00
( function ( aDir , aWrap , aSelf ) {
var nextTab = ( aDir < 0 ) ? TreeStyleTabService . getPreviousVisibleTab ( aSelf . selectedItem ) : TreeStyleTabService . getNextVisibleTab ( aSelf . selectedItem ) ;
if ( ! nextTab && aWrap ) {
2007-10-19 01:27:06 -04:00
var xpathResult = TreeStyleTabService . evaluateXPath (
'child::xul:tab[not(@' + TreeStyleTabService . kCOLLAPSED + '="true")]' ,
aSelf
) ;
nextTab = xpathResult . snapshotItem ( aDir < 0 ? xpathResult . snapshotLength - 1 : 0 ) ;
}
if ( nextTab && nextTab != aSelf . selectedItem ) {
2007-10-21 19:38:50 -04:00
if ( '_selectNewTab' in aSelf )
aSelf . _selectNewTab ( nextTab , aDir , aWrap ) ; // Fx 3
else
aSelf . selectNewTab ( nextTab , aDir , aWrap ) ; // Fx 2
2007-10-19 01:27:06 -04:00
}
} ) ( arguments [ 0 ] , arguments [ 1 ] , this ) ;
2007-10-18 13:11:03 -04:00
return ;
}
] ] > < / >
)
) ;
2007-10-20 12:47:08 -04:00
eval ( 'aTabBrowser.mTabContainer._handleTabSelect = ' +
aTabBrowser . mTabContainer . _handleTabSelect . toSource ( ) . replace (
/\{/ ,
< > < ! [ CDATA [
{
2007-10-24 15:37:21 -04:00
if ( ! TreeStyleTabService . isTabInViewport ( this . selectedItem ) ) {
2007-10-20 12:47:08 -04:00
TreeStyleTabService . scrollToTab ( this . selectedItem ) ;
return ;
}
] ] > < / >
)
) ;
2007-10-19 22:44:14 -04:00
eval ( 'aTabBrowser.mTabContainer._notifyBackgroundTab = ' +
aTabBrowser . mTabContainer . _notifyBackgroundTab . toSource ( ) . replace (
/\.screenX/g , '[TreeStyleTabService.positionProp]'
) . replace (
/\.width/g , '[TreeStyleTabService.sizeProp]'
)
) ;
2007-10-19 09:05:29 -04:00
eval ( 'aTabBrowser.canDrop = ' +
aTabBrowser . canDrop . toSource ( ) . replace (
/\.screenX/g , '[TreeStyleTabService.positionProp]'
) . replace (
/\.width/g , '[TreeStyleTabService.sizeProp]'
) . replace (
/return true;/ ,
< > < ! [ CDATA [
2007-10-20 02:12:22 -04:00
if ( ! ( function ( aSelf ) {
2007-10-19 23:38:46 -04:00
try {
2007-10-19 09:05:29 -04:00
if ( ! aDragSession . sourceNode ||
aDragSession . sourceNode . parentNode != aSelf . mTabContainer ||
aEvent . target . localName != 'tab' )
2007-10-19 22:44:14 -04:00
return true ;
if ( aEvent . target . getAttribute ( TreeStyleTabService . kCOLLAPSED ) == 'true' )
2007-10-19 09:05:29 -04:00
return false ;
2007-10-19 22:44:14 -04:00
2007-10-20 02:12:22 -04:00
var info = TreeStyleTabService . getDropAction ( aEvent , aDragSession ) ;
return info . canDrop ;
2007-10-19 23:38:46 -04:00
}
catch ( e ) {
dump ( 'TreeStyleTabService::canDrop\n' + e + '\n' ) ;
return false ;
}
2007-10-20 02:12:22 -04:00
} ) ( this ) )
2007-10-19 09:05:29 -04:00
return false ;
return true ;
] ] > < / >
)
) ;
2007-10-19 22:44:14 -04:00
eval ( 'aTabBrowser.onDragOver = ' +
aTabBrowser . onDragOver . toSource ( ) . replace (
'{' ,
< > < ! [ CDATA [
{
2007-10-24 15:37:21 -04:00
if ( ( function ( aSelf ) {
2007-10-19 23:38:46 -04:00
try {
2007-10-20 02:12:22 -04:00
var info = TreeStyleTabService . getDropAction ( aEvent , aDragSession ) ;
if ( ! info . target || info . target != TreeStyleTabService . evaluateXPath (
'child::xul:tab[@' + TreeStyleTabService . kDROP _POSITION + ']' ,
aSelf . mTabContainer ,
XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue )
TreeStyleTabService . clearDropPosition ( aSelf ) ;
2007-10-24 15:37:21 -04:00
if ( ! aSelf . canDrop ( aEvent , aDragSession ) ) return true ;
2007-10-20 02:12:22 -04:00
info . target . setAttribute (
TreeStyleTabService . kDROP _POSITION ,
info . position == TreeStyleTabService . kDROP _BEFORE ? 'before' :
info . position == TreeStyleTabService . kDROP _AFTER ? 'after' :
'self'
2007-10-19 22:44:14 -04:00
) ;
2007-10-24 15:37:21 -04:00
aSelf . mTabDropIndicatorBar . setAttribute ( 'dragging' , ( info . position == TreeStyleTabService . kDROP _ON ) ? 'false' : 'true' ) ;
return ( info . position == TreeStyleTabService . kDROP _ON || aSelf . getAttribute ( TreeStyleTabService . kTABBAR _POSITION ) != 'top' )
2007-10-19 23:38:46 -04:00
}
catch ( e ) {
dump ( 'TreeStyleTabService::onDragOver\n' + e + '\n' ) ;
}
2007-10-24 15:37:21 -04:00
} ) ( this ) ) {
return ;
}
2007-10-19 23:38:46 -04:00
] ] > < / >
)
) ;
2007-10-20 02:12:22 -04:00
eval ( 'aTabBrowser.onDragExit = ' +
aTabBrowser . onDragExit . toSource ( ) . replace (
/(this.mTabDropIndicatorBar\.[^;]+;)/ ,
'$1; TreeStyleTabService.clearDropPosition(this);'
)
) ;
2007-10-19 23:38:46 -04:00
eval ( 'aTabBrowser.onDrop = ' +
aTabBrowser . onDrop . toSource ( ) . replace (
2007-10-20 16:42:20 -04:00
'{' ,
< > < ! [ CDATA [
{
TreeStyleTabService . clearDropPosition ( this ) ;
var dropActionInfo = TreeStyleTabService . getDropAction ( aEvent , aDragSession ) ;
] ] > < / >
2007-10-20 02:12:22 -04:00
) . replace (
2007-10-19 23:38:46 -04:00
/(if \([^\)]+\) \{)/ ,
'$1' + < > < ! [ CDATA [
2007-10-20 16:42:20 -04:00
if ( TreeStyleTabService . processDropAction ( dropActionInfo , this , aDragSession . sourceNode ) )
2007-10-19 23:38:46 -04:00
return ;
2007-10-19 22:44:14 -04:00
] ] > < / >
2007-10-20 16:42:20 -04:00
) . replace (
/(this.loadOneTab\([^;]+\));/ ,
< > < ! [ CDATA [
TreeStyleTabService . processDropAction ( dropActionInfo , this , $1 ) ;
return ;
] ] > < / >
) . replace (
'document.getBindingParent(aEvent.originalTarget).localName != "tab"' ,
'!TreeStyleTabService.getTabFromEvent(aEvent)'
) . replace (
'var tab = aEvent.target;' ,
< > < ! [ CDATA [
var tab = aEvent . target ;
2007-10-26 07:24:59 -04:00
if ( TreeStyleTabService . getTreePref ( 'loadDroppedLinkToNewChildTab' ) ||
2007-10-21 11:02:58 -04:00
dropActionInfo . position != TreeStyleTabService . kDROP _ON ) {
2007-10-20 16:42:20 -04:00
TreeStyleTabService . processDropAction ( dropActionInfo , this , this . loadOneTab ( getShortcutOrURI ( url ) , null , null , null , bgLoad , false ) ) ;
return ;
}
] ] > < / >
2007-10-19 22:44:14 -04:00
)
) ;
eval ( 'aTabBrowser.getNewIndex = ' +
aTabBrowser . getNewIndex . toSource ( ) . replace (
/\.screenX/g , '[TreeStyleTabService.positionProp]'
) . replace (
/\.width/g , '[TreeStyleTabService.sizeProp]'
)
) ;
2007-10-19 09:05:29 -04:00
eval ( 'aTabBrowser.moveTabForward = ' +
aTabBrowser . moveTabForward . toSource ( ) . replace (
'{' , '{ var nextTab;'
) . replace (
'tabPos < this.browsers.length - 1' ,
2007-10-19 22:44:14 -04:00
'nextTab = TreeStyleTabService.getNextSiblingTab(this.mCurrentTab)'
2007-10-19 09:05:29 -04:00
) . replace (
'tabPos + 1' , 'nextTab._tPos'
) . replace (
'this.moveTabTo(' ,
< > < ! [ CDATA [
2007-10-19 22:44:14 -04:00
var descendant = TreeStyleTabService . getDescendantTabs ( nextTab ) ;
2007-10-19 09:05:29 -04:00
if ( descendant . length ) {
nextTab = descendant [ descendant . length - 1 ] ;
}
this . moveTabTo ( ] ] > < / >
) . replace (
'this.moveTabToStart();' ,
< > < ! [ CDATA [
2007-10-26 15:27:30 -04:00
this . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-19 22:44:14 -04:00
var parentTab = TreeStyleTabService . getParentTab ( this . mCurrentTab ) ;
2007-10-19 09:05:29 -04:00
if ( parentTab ) {
2007-10-19 22:44:14 -04:00
this . moveTabTo ( this . mCurrentTab , TreeStyleTabService . getFirstChildTab ( parentTab ) . _tPos ) ;
2007-10-19 09:05:29 -04:00
this . mCurrentTab . focus ( ) ;
}
else {
this . moveTabToStart ( ) ;
}
2007-10-26 15:27:30 -04:00
this . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-19 09:05:29 -04:00
] ] > < / >
)
) ;
eval ( 'aTabBrowser.moveTabBackward = ' +
aTabBrowser . moveTabBackward . toSource ( ) . replace (
'{' , '{ var prevTab;'
) . replace (
'tabPos > 0' ,
2007-10-19 22:44:14 -04:00
'prevTab = TreeStyleTabService.getPreviousSiblingTab(this.mCurrentTab)'
2007-10-19 09:05:29 -04:00
) . replace (
'tabPos - 1' , 'prevTab._tPos'
) . replace (
'this.moveTabToEnd();' ,
< > < ! [ CDATA [
2007-10-26 15:27:30 -04:00
this . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-19 22:44:14 -04:00
var parentTab = TreeStyleTabService . getParentTab ( this . mCurrentTab ) ;
2007-10-19 09:05:29 -04:00
if ( parentTab ) {
2007-10-19 22:44:14 -04:00
this . moveTabTo ( this . mCurrentTab , TreeStyleTabService . getLastChildTab ( parentTab ) . _tPos ) ;
2007-10-19 09:05:29 -04:00
this . mCurrentTab . focus ( ) ;
}
else {
this . moveTabToEnd ( ) ;
}
2007-10-26 15:27:30 -04:00
this . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-19 09:05:29 -04:00
] ] > < / >
)
) ;
2007-10-19 22:44:14 -04:00
eval ( 'aTabBrowser._keyEventHandler.handleEvent = ' +
aTabBrowser . _keyEventHandler . handleEvent . toSource ( ) . replace (
'this.tabbrowser.moveTabOver(aEvent);' ,
2007-10-19 09:05:29 -04:00
< > < ! [ CDATA [
2007-10-19 22:44:14 -04:00
if ( ! TreeStyleTabService . isTabVertical ( this . tabbrowser ) ||
! TreeStyleTabService . moveTabLevel ( aEvent ) ) {
this . tabbrowser . moveTabOver ( aEvent ) ;
}
] ] > < / >
) . replace (
'this.tabbrowser.moveTabForward();' ,
< > < ! [ CDATA [
if ( TreeStyleTabService . isTabVertical ( this . tabbrowser ) ||
! TreeStyleTabService . moveTabLevel ( aEvent ) ) {
this . tabbrowser . moveTabForward ( ) ;
}
] ] > < / >
) . replace (
'this.tabbrowser.moveTabBackward();' ,
< > < ! [ CDATA [
if ( TreeStyleTabService . isTabVertical ( this . tabbrowser ) ||
! TreeStyleTabService . moveTabLevel ( aEvent ) ) {
this . tabbrowser . moveTabBackward ( ) ;
}
2007-10-19 09:05:29 -04:00
] ] > < / >
)
) ;
2007-10-21 20:40:04 -04:00
eval ( 'aTabBrowser.loadTabs = ' +
aTabBrowser . loadTabs . toSource ( ) . replace (
'var tabNum = ' ,
< > < ! [ CDATA [
if ( this . _ _treestyletab _ _readyToAttachNewTabGroup )
TreeStyleTabService . readyToOpenChildTab ( firstTabAdded || this . selectedTab , true ) ;
var tabNum = ] ] > < / >
) . replace (
'if (!aLoadInBackground)' ,
< > < ! [ CDATA [
if ( TreeStyleTabService . checkToOpenChildTab ( this ) )
TreeStyleTabService . stopToOpenChildTab ( this ) ;
if ( ! aLoadInBackground ) ] ] > < / >
)
) ;
2007-10-16 13:22:28 -04:00
var addTabMethod = 'addTab' ;
var removeTabMethod = 'removeTab' ;
if ( aTabBrowser . _ _tabextensions _ _addTab ) {
addTabMethod = '__tabextensions__addTab' ;
removeTabMethod = '__tabextensions__removeTab' ;
}
aTabBrowser . _ _treestyletab _ _originalAddTab = aTabBrowser [ addTabMethod ] ;
aTabBrowser [ addTabMethod ] = function ( ) {
var tab = this . _ _treestyletab _ _originalAddTab . apply ( this , arguments ) ;
try {
TreeStyleTabService . initTab ( tab , this ) ;
}
catch ( e ) {
}
return tab ;
} ;
aTabBrowser . _ _treestyletab _ _originalRemoveTab = aTabBrowser [ removeTabMethod ] ;
aTabBrowser [ removeTabMethod ] = function ( aTab ) {
TreeStyleTabService . destroyTab ( aTab , this ) ;
var retVal = this . _ _treestyletab _ _originalRemoveTab . apply ( this , arguments ) ;
try {
if ( aTab . parentNode )
TreeStyleTabService . initTab ( aTab , this ) ;
}
catch ( e ) {
}
return retVal ;
} ;
var tabs = aTabBrowser . mTabContainer . childNodes ;
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
this . initTab ( tabs [ i ] , aTabBrowser ) ;
}
2007-10-20 04:22:42 -04:00
aTabBrowser . _ _treestyletab _ _observer = new TreeStyleTabBrowserObserver ( aTabBrowser ) ;
2007-10-20 15:00:09 -04:00
aTabBrowser . _ _treestyletab _ _observer . observe ( null , 'nsPref:changed' , 'extensions.treestyletab.tabbar.style' ) ;
2007-10-22 08:18:34 -04:00
aTabBrowser . _ _treestyletab _ _observer . observe ( null , 'nsPref:changed' , 'extensions.treestyletab.showBorderForFirstTab' ) ;
2007-10-23 02:05:44 -04:00
aTabBrowser . _ _treestyletab _ _observer . observe ( null , 'nsPref:changed' , 'extensions.treestyletab.tabbar.invertScrollbar' ) ;
2007-10-25 18:59:34 -04:00
aTabBrowser . _ _treestyletab _ _observer . observe ( null , 'nsPref:changed' , 'extensions.treestyletab.allowSubtreeCollapseExpand' ) ;
2007-10-20 04:22:42 -04:00
2007-10-16 13:22:28 -04:00
delete addTabMethod ;
delete removeTabMethod ;
delete i ;
delete maxi ;
delete tabs ;
} ,
2007-10-19 01:27:06 -04:00
2007-10-16 13:22:28 -04:00
initTab : function ( aTab , aTabBrowser )
{
var id = 'tab-<' + Date . now ( ) + '-' + parseInt ( Math . random ( ) * 65000 ) + '>' ;
2007-10-17 14:18:16 -04:00
this . setTabValue ( aTab , this . kID , id ) ;
2007-10-16 13:22:28 -04:00
aTab . _ _treestyletab _ _linkedTabBrowser = aTabBrowser ;
2007-10-26 07:24:59 -04:00
var pos = this . getTreePref ( 'tabbar.position' ) ;
2007-10-20 07:29:42 -04:00
if ( pos == 'left' || pos == 'right' ) {
2007-10-20 06:24:36 -04:00
aTab . setAttribute ( 'align' , 'stretch' ) ;
2007-10-20 07:29:42 -04:00
aTab . maxWidth = 65000 ;
aTab . minWidth = 0 ;
}
2007-10-20 06:24:36 -04:00
2007-10-19 02:40:30 -04:00
this . initTabContents ( aTab ) ;
2007-10-18 13:11:03 -04:00
2007-10-25 18:59:34 -04:00
aTab . setAttribute ( this . kNEST , 0 ) ;
2007-10-16 13:22:28 -04:00
var event = document . createEvent ( 'Events' ) ;
event . initEvent ( 'TreeStyleTab:TabOpen' , true , false ) ;
aTab . dispatchEvent ( event ) ;
} ,
2007-10-18 13:11:03 -04:00
2007-10-19 02:40:30 -04:00
initTabContents : function ( aTab )
2007-10-18 13:11:03 -04:00
{
2007-10-19 02:40:30 -04:00
if ( ! document . getAnonymousElementByAttribute ( aTab , 'class' , this . kTWISTY ) ) {
var twisty = document . createElement ( 'image' ) ;
twisty . setAttribute ( 'class' , this . kTWISTY ) ;
var container = document . createElement ( 'hbox' ) ;
container . setAttribute ( 'class' , this . kTWISTY _CONTAINER ) ;
container . appendChild ( twisty ) ;
2007-10-18 14:54:25 -04:00
2007-10-19 02:40:30 -04:00
var icon = document . getAnonymousElementByAttribute ( aTab , 'class' , 'tab-icon' ) ;
icon . appendChild ( container ) ;
2007-10-20 02:12:22 -04:00
var marker = document . createElement ( 'image' ) ;
marker . setAttribute ( 'class' , this . kDROP _MARKER ) ;
container = document . createElement ( 'hbox' ) ;
container . setAttribute ( 'class' , this . kDROP _MARKER _CONTAINER ) ;
container . appendChild ( marker ) ;
icon . appendChild ( container ) ;
2007-10-19 02:40:30 -04:00
}
if ( ! document . getAnonymousElementByAttribute ( aTab , 'class' , this . kCOUNTER _CONTAINER ) ) {
var counter = document . createElement ( 'hbox' ) ;
counter . setAttribute ( 'class' , this . kCOUNTER _CONTAINER ) ;
2007-10-18 14:54:25 -04:00
2007-10-19 02:40:30 -04:00
counter . appendChild ( document . createElement ( 'label' ) ) ;
counter . lastChild . setAttribute ( 'class' , this . kCOUNTER ) ;
counter . lastChild . setAttribute ( 'value' , '(0)' ) ;
var text = document . getAnonymousElementByAttribute ( aTab , 'class' , 'tab-text' ) ;
if ( text ) {
if ( text . nextSibling )
text . parentNode . insertBefore ( counter , text . nextSibling ) ;
else
text . parentNode . appendChild ( counter ) ;
}
}
2007-10-18 13:11:03 -04:00
} ,
2007-10-21 11:02:58 -04:00
overrideGlobalFunctions : function ( )
{
2007-10-21 11:50:11 -04:00
var funcs ;
2007-10-26 07:24:59 -04:00
eval ( 'window.BrowserLoadURL = ' +
window . BrowserLoadURL . toSource ( ) . replace (
'aTriggeringEvent && aTriggeringEvent.altKey' ,
< > < ! [ CDATA [
( aTriggeringEvent && aTriggeringEvent . altKey ) ||
2007-10-28 12:07:10 -04:00
TreeStyleTabService . checkReadyToOpenNewChildTab (
TreeStyleTabService . browser ,
2007-10-28 13:16:48 -04:00
{
uri : url ,
external : { newTab : TreeStyleTabService . getTreePref ( 'urlbar.loadDifferentDomainToNewTab' ) } ,
internal : { newTab : TreeStyleTabService . getTreePref ( 'urlbar.loadSameDomainToNewChildTab' ) }
}
2007-10-26 07:24:59 -04:00
)
] ] > < / >
)
) ;
2007-10-21 11:02:58 -04:00
eval ( 'nsContextMenu.prototype.openLinkInTab = ' +
nsContextMenu . prototype . openLinkInTab . toSource ( ) . replace (
'{' ,
< > < ! [ CDATA [
{
TreeStyleTabService . readyToOpenChildTab ( this . target . ownerDocument . defaultView ) ;
] ] > < / >
)
) ;
eval ( 'nsContextMenu.prototype.openFrameInTab = ' +
nsContextMenu . prototype . openFrameInTab . toSource ( ) . replace (
'{' ,
< > < ! [ CDATA [
{
TreeStyleTabService . readyToOpenChildTab ( this . target . ownerDocument . defaultView ) ;
] ] > < / >
)
) ;
2007-10-22 18:45:35 -04:00
eval ( 'nsContextMenu.prototype.viewImage = ' +
nsContextMenu . prototype . viewImage . toSource ( ) . replace (
'openUILink(' ,
< > < ! [ CDATA [
if ( String ( whereToOpenLink ( e , false , true ) ) . indexOf ( 'tab' ) == 0 )
TreeStyleTabService . readyToOpenChildTab ( this . target . ownerDocument . defaultView ) ;
openUILink ( ] ] > < / >
)
) ;
eval ( 'nsContextMenu.prototype.viewBGImage = ' +
nsContextMenu . prototype . viewBGImage . toSource ( ) . replace (
'openUILink(' ,
< > < ! [ CDATA [
if ( String ( whereToOpenLink ( e , false , true ) ) . indexOf ( 'tab' ) == 0 )
TreeStyleTabService . readyToOpenChildTab ( this . target . ownerDocument . defaultView ) ;
openUILink ( ] ] > < / >
)
) ;
eval ( 'nsContextMenu.prototype.addDictionaries = ' +
nsContextMenu . prototype . addDictionaries . toSource ( ) . replace (
'openUILinkIn(' ,
< > < ! [ CDATA [
if ( where . indexOf ( 'tab' ) == 0 )
TreeStyleTabService . readyToOpenChildTab ( this . target . ownerDocument . defaultView ) ;
openUILinkIn ( ] ] > < / >
)
) ;
2007-10-21 11:02:58 -04:00
2007-10-21 11:50:11 -04:00
funcs = 'handleLinkClick __splitbrowser__handleLinkClick __ctxextensions__handleLinkClick' . split ( ' ' ) ;
for ( var i in funcs )
{
2007-10-28 12:07:10 -04:00
if ( funcs [ i ] in window && /^function handleLinkClick/ . test ( window [ funcs [ i ] ] . toString ( ) ) )
2007-10-21 11:50:11 -04:00
eval ( 'window.' + funcs [ i ] + ' = ' +
window [ funcs [ i ] ] . toSource ( ) . replace (
/openNewTabWith\(/g ,
< > < ! [ CDATA [
TreeStyleTabService . readyToOpenChildTab ( event . target . ownerDocument . defaultView ) ;
openNewTabWith ( ] ] > < / >
2007-10-28 12:07:10 -04:00
) . replace (
/(event.ctrlKey|event.metaKey)/ ,
< > < ! [ CDATA [
$1 ||
TreeStyleTabService . checkReadyToOpenNewChildTab (
TreeStyleTabService . browser ,
2007-10-28 13:16:48 -04:00
{
uri : href ,
external : {
newTab : TreeStyleTabService . getTreePref ( 'openOuterLinkInNewTab' ) || TreeStyleTabService . getTreePref ( 'openAnyLinkInNewTab' ) ,
forceChild : true
} ,
internal : {
newTab : TreeStyleTabService . getTreePref ( 'openAnyLinkInNewTab' )
}
}
2007-10-28 12:07:10 -04:00
)
] ] > < / >
2007-10-21 11:50:11 -04:00
)
) ;
}
2007-10-21 11:02:58 -04:00
2007-10-28 13:16:48 -04:00
funcs = 'contentAreaClick __ctxextensions__contentAreaClick' . split ( ' ' ) ;
for ( var i in funcs )
{
if ( funcs [ i ] in window && /^function contentAreaClick/ . test ( window [ funcs [ i ] ] . toString ( ) ) )
eval ( 'window.' + funcs [ i ] + ' = ' +
window [ funcs [ i ] ] . toSource ( ) . replace (
/(openWebPanel\([^\(]+\("webPanels"\), wrapper.href\);event.preventDefault\(\);return false;\})/ ,
< > < ! [ CDATA [
$1
else if ( TreeStyleTabService . checkReadyToOpenNewChildTab (
TreeStyleTabService . browser ,
{
uri : wrapper . href ,
external : {
newTab : TreeStyleTabService . getTreePref ( 'openOuterLinkInNewTab' ) || TreeStyleTabService . getTreePref ( 'openAnyLinkInNewTab' ) ,
forceChild : true
} ,
internal : {
newTab : TreeStyleTabService . getTreePref ( 'openAnyLinkInNewTab' )
}
} ) ) {
event . stopPropagation ( ) ;
event . preventDefault ( ) ;
handleLinkClick ( event , wrapper . href , linkNode ) ;
return true ;
}
] ] > < / >
)
) ;
}
2007-10-21 11:50:11 -04:00
funcs = 'gotoHistoryIndex BrowserForward BrowserBack __rewindforward__BrowserForward __rewindforward__BrowserBack' . split ( ' ' ) ;
for ( var i in funcs )
{
2007-10-28 12:07:10 -04:00
if ( funcs [ i ] in window &&
/^function (gotoHistoryIndex|BrowserForward|BrowserBack)/ . test ( window [ funcs [ i ] ] . toString ( ) ) )
2007-10-21 11:50:11 -04:00
eval ( 'window.' + funcs [ i ] + ' = ' +
window [ funcs [ i ] ] . toSource ( ) . replace (
/openUILinkIn\(/g ,
< > < ! [ CDATA [
if ( where == 'tab' || where == 'tabshifted' )
TreeStyleTabService . readyToOpenChildTab ( ) ;
openUILinkIn ( ] ] > < / >
)
) ;
}
2007-10-21 11:02:58 -04:00
2007-10-22 18:45:35 -04:00
eval ( 'window.BrowserHomeClick = ' +
window . BrowserHomeClick . toSource ( ) . replace (
'gBrowser.loadTabs(' ,
< > < ! [ CDATA [
TreeStyleTabService . readyToOpenNewTabGroup ( gBrowser ) ;
gBrowser . loadTabs ( ] ] > < / >
)
) ;
2007-10-22 19:29:07 -04:00
eval ( 'nsBrowserAccess.prototype.openURI = ' +
nsBrowserAccess . prototype . openURI . toSource ( ) . replace (
2007-10-21 11:02:58 -04:00
/switch\s*\(aWhere\)/ ,
< > < ! [ CDATA [
if ( aOpener &&
aWhere == Components . interfaces . nsIBrowserDOMWindow . OPEN _NEWTAB ) {
TreeStyleTabService . readyToOpenChildTab ( aOpener ) ;
}
switch ( aWhere )
] ] > < / >
)
) ;
window . QueryInterface ( Components . interfaces . nsIDOMChromeWindow ) . browserDOMWindow = null ;
window . QueryInterface ( Components . interfaces . nsIDOMChromeWindow ) . browserDOMWindow = new nsBrowserAccess ( ) ;
2007-10-22 18:45:35 -04:00
eval ( 'FeedHandler.loadFeed = ' +
FeedHandler . loadFeed . toSource ( ) . replace (
'openUILink(' ,
< > < ! [ CDATA [
if ( String ( whereToOpenLink ( event , false , true ) ) . indexOf ( 'tab' ) == 0 )
TreeStyleTabService . readyToOpenChildTab ( gBrowser ) ;
openUILink ( ] ] > < / >
)
) ;
2007-10-21 20:40:04 -04:00
if ( 'BookmarksCommand' in window ) { // Firefox 2
2007-10-21 19:38:50 -04:00
eval ( 'BookmarksCommand.openGroupBookmark = ' +
BookmarksCommand . openGroupBookmark . toSource ( ) . replace (
'browser.addTab(uri);' ,
< > < ! [ CDATA [
var openedTab = browser . addTab ( uri ) ;
if ( ! TreeStyleTabService . getPref ( 'browser.tabs.loadFolderAndReplace' ) &&
2007-10-26 07:24:59 -04:00
TreeStyleTabService . getTreePref ( 'openGroupBookmarkAsTabSubTree' ) &&
2007-10-21 19:38:50 -04:00
! browser . _ _treestyletab _ _parentTab ) {
TreeStyleTabService . readyToOpenChildTab ( openedTab , true ) ;
}
] ] > < / >
) . replace (
'if (index == index0)' ,
< > < ! [ CDATA [
TreeStyleTabService . stopToOpenChildTab ( browser ) ;
if ( index == index0 ) ] ] > < / >
)
) ;
}
2007-10-21 20:40:04 -04:00
if ( 'PlacesUtils' in window ) { // Firefox 3
eval ( 'PlacesUtils.openContainerNodeInTabs = ' +
PlacesUtils . openContainerNodeInTabs . toSource ( ) . replace (
'this._openTabset(' ,
< > < ! [ CDATA [
2007-10-26 07:24:59 -04:00
if ( TreeStyleTabService . getTreePref ( 'openGroupBookmarkAsTabSubTree' ) &&
2007-10-21 20:40:04 -04:00
String ( whereToOpenLink ( aEvent , false , true ) ) . indexOf ( 'tab' ) == 0 )
TreeStyleTabService . readyToOpenNewTabGroup ( ) ;
this . _openTabset ( ] ] > < / >
)
) ;
}
2007-10-21 11:02:58 -04:00
} ,
2007-10-28 12:07:10 -04:00
2007-10-16 13:22:28 -04:00
destroy : function ( )
{
this . destroyTabBrowser ( gBrowser ) ;
window . removeEventListener ( 'unload' , this , false ) ;
2007-10-17 12:07:43 -04:00
2007-10-22 05:59:43 -04:00
document . getElementById ( 'contentAreaContextMenu' ) . removeEventListener ( 'popupshowing' , this , false ) ;
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'inSubbrowsers.enabled' ) ) {
2007-10-20 06:44:42 -04:00
var appcontent = document . getElementById ( 'appcontent' ) ;
appcontent . removeEventListener ( 'SubBrowserAdded' , this , false ) ;
appcontent . removeEventListener ( 'SubBrowserRemoveRequest' , this , false ) ;
}
2007-10-16 13:22:28 -04:00
this . removePrefListener ( this ) ;
var tabs = gBrowser . mTabContainer . childNodes ;
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
this . destroyTab ( tabs [ i ] ) ;
}
} ,
2007-10-22 05:59:43 -04:00
2007-10-16 13:22:28 -04:00
destroyTabBrowser : function ( aTabBrowser )
{
2007-10-20 04:22:42 -04:00
aTabBrowser . _ _treestyletab _ _observer . destroy ( ) ;
delete aTabBrowser . _ _treestyletab _ _observer ;
2007-10-16 13:22:28 -04:00
aTabBrowser . mTabContainer . removeEventListener ( 'TreeStyleTab:TabOpen' , this , true ) ;
aTabBrowser . mTabContainer . removeEventListener ( 'TabClose' , this , true ) ;
2007-10-17 19:48:30 -04:00
aTabBrowser . mTabContainer . removeEventListener ( 'TabMove' , this , true ) ;
aTabBrowser . mTabContainer . removeEventListener ( 'SSTabRestoring' , this , true ) ;
2007-10-18 13:11:03 -04:00
aTabBrowser . mTabContainer . removeEventListener ( 'click' , this , true ) ;
2007-10-19 02:40:30 -04:00
aTabBrowser . mTabContainer . removeEventListener ( 'dblclick' , this , true ) ;
2007-10-18 13:11:03 -04:00
aTabBrowser . mTabContainer . removeEventListener ( 'mousedown' , this , true ) ;
aTabBrowser . mTabContainer . removeEventListener ( 'select' , this , true ) ;
2007-10-21 11:02:58 -04:00
// aTabBrowser.mPanelContainer.removeEventListener('click', this, true);
2007-10-16 13:22:28 -04:00
} ,
2007-10-19 02:49:20 -04:00
2007-10-16 13:22:28 -04:00
destroyTab : function ( aTab , aTabBrowser )
{
delete aTab . _ _treestyletab _ _linkedTabBrowser ;
} ,
/* Event Handling */
2007-10-23 04:19:32 -04:00
2007-10-16 13:22:28 -04:00
handleEvent : function ( aEvent )
{
switch ( aEvent . type )
{
case 'TreeStyleTab:TabOpen' :
this . onTabAdded ( aEvent ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
case 'TabClose' :
this . onTabRemoved ( aEvent ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
2007-10-17 19:48:30 -04:00
case 'TabMove' :
2007-10-19 09:05:29 -04:00
this . onTabMove ( aEvent ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-17 19:48:30 -04:00
case 'SSTabRestoring' :
this . onTabRestored ( aEvent ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-17 19:48:30 -04:00
2007-10-16 13:22:28 -04:00
case 'click' :
2007-10-18 13:11:03 -04:00
if ( aEvent . target . ownerDocument == document ) {
this . onTabClick ( aEvent ) ;
return ;
}
2007-10-21 11:02:58 -04:00
/ *
2007-10-16 13:22:28 -04:00
var isMiddleClick = (
aEvent . button == 1 ||
aEvent . button == 0 && ( aEvent . ctrlKey || aEvent . metaKey )
) ;
var node = aEvent . originalTarget ;
while ( node . parentNode && ! node . href )
{
node = node . parentNode ;
}
if ( node . href && isMiddleClick ) {
var b = this . getTabBrowserFromChildren ( aEvent . currentTarget ) ;
2007-10-21 04:04:39 -04:00
this . readyToOpenChildTab ( b . selectedTab ) ;
2007-10-16 13:22:28 -04:00
}
2007-10-21 11:02:58 -04:00
* /
2007-10-18 13:11:03 -04:00
return ;
2007-10-19 02:40:30 -04:00
case 'dblclick' :
var tab = this . getTabFromEvent ( aEvent ) ;
if ( tab &&
tab . getAttribute ( this . kCHILDREN ) &&
2007-10-26 07:24:59 -04:00
this . getTreePref ( 'collapseExpandSubTree.dblclick' ) ) {
2007-10-19 02:40:30 -04:00
this . collapseExpandTabSubTree ( tab , tab . getAttribute ( this . kSUBTREE _COLLAPSED ) != 'true' ) ;
aEvent . preventDefault ( ) ;
aEvent . stopPropagation ( ) ;
}
return ;
2007-10-18 13:11:03 -04:00
case 'mousedown' :
this . onTabMouseDown ( aEvent ) ;
return ;
case 'select' :
2007-10-18 14:03:05 -04:00
this . onTabSelect ( aEvent ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
case 'load' :
this . init ( ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
case 'unload' :
this . destroy ( ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
case 'popupshowing' :
2007-10-22 05:59:43 -04:00
if ( aEvent . target != aEvent . currentTarget ) return ;
this . initContextMenu ( ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-17 09:25:50 -04:00
case 'SubBrowserAdded' :
this . initTabBrowser ( aEvent . originalTarget . browser ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-17 09:25:50 -04:00
case 'SubBrowserRemoveRequest' :
this . destroyTabBrowser ( aEvent . originalTarget . browser ) ;
2007-10-18 13:11:03 -04:00
return ;
2007-10-16 13:22:28 -04:00
}
} ,
onTabAdded : function ( aEvent )
{
var tab = aEvent . originalTarget ;
var b = this . getTabBrowserFromChildren ( tab ) ;
2007-10-19 22:44:14 -04:00
if ( b . _ _treestyletab _ _readyToAttachNewTab ) {
2007-10-16 13:22:28 -04:00
var parent = this . getTabById ( b . _ _treestyletab _ _parentTab , b ) ;
if ( parent )
2007-10-19 22:44:14 -04:00
this . attachTabTo ( tab , parent ) ;
2007-10-16 13:22:28 -04:00
}
2007-10-20 13:52:42 -04:00
if ( ! b . _ _treestyletab _ _readyToAttachMultiple ) {
2007-10-21 04:04:39 -04:00
this . stopToOpenChildTab ( b ) ;
2007-10-20 13:52:42 -04:00
}
2007-10-16 13:22:28 -04:00
} ,
onTabRemoved : function ( aEvent )
{
2007-10-18 13:11:03 -04:00
var tab = aEvent . originalTarget ;
var b = this . getTabBrowserFromChildren ( tab ) ;
2007-10-20 04:22:42 -04:00
if ( tab . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ) {
2007-10-19 22:44:14 -04:00
var descendant = this . getDescendantTabs ( tab ) ;
2007-10-18 13:11:03 -04:00
for ( var i = descendant . length - 1 ; i > - 1 ; i -- )
{
b . removeTab ( descendant [ i ] ) ;
}
}
2007-10-19 22:44:14 -04:00
var firstChild = this . getFirstChildTab ( tab ) ;
var parentTab = this . getParentTab ( tab ) ;
2007-10-17 13:45:09 -04:00
var nextFocusedTab = null ;
2007-10-26 06:25:59 -04:00
var next = this . getNextSiblingTab ( tab ) ;
if ( next )
this . setTabValue ( tab , this . kINSERT _BEFORE , next . getAttribute ( this . kID ) ) ;
2007-10-18 11:40:06 -04:00
2007-10-17 13:45:09 -04:00
if ( firstChild ) {
2007-10-17 19:48:30 -04:00
var backupChildren = this . getTabValue ( tab , this . kCHILDREN ) ;
2007-10-19 22:44:14 -04:00
var children = this . getChildTabs ( tab ) ;
2007-10-17 14:18:16 -04:00
var self = this ;
2007-10-26 07:24:59 -04:00
var attach = this . getTreePref ( 'attachChildrenToGrandParentOnRemoveTab' ) ;
2007-10-19 23:38:46 -04:00
var processTab = ! attach ? function ( aTab ) {
2007-10-19 22:44:14 -04:00
self . partTab ( aTab , true ) ;
2007-10-17 14:36:39 -04:00
self . moveTabSubTreeTo ( aTab , b . mTabContainer . lastChild . _tPos ) ;
2007-10-17 14:18:16 -04:00
} :
parentTab ? function ( aTab ) {
2007-10-19 22:44:14 -04:00
self . attachTabTo ( aTab , parentTab , { insertBefore : tab , dontUpdateIndent : true } ) ;
2007-10-17 14:18:16 -04:00
} :
function ( aTab ) {
2007-10-19 22:44:14 -04:00
self . partTab ( aTab , true ) ;
2007-10-17 14:18:16 -04:00
} ;
2007-10-17 13:45:09 -04:00
for ( var i = 0 , maxi = children . length ; i < maxi ; i ++ )
{
2007-10-17 14:18:16 -04:00
processTab ( children [ i ] ) ;
}
2007-10-18 11:40:06 -04:00
this . updateTabsIndent ( children ) ;
2007-10-20 04:22:42 -04:00
this . checkTabsIndentOverflow ( b ) ;
2007-10-19 23:38:46 -04:00
if ( attach ) {
2007-10-17 14:18:16 -04:00
nextFocusedTab = firstChild ;
2007-10-17 13:45:09 -04:00
}
2007-10-17 19:48:30 -04:00
this . setTabValue ( tab , this . kCHILDREN , backupChildren ) ;
2007-10-17 13:45:09 -04:00
}
2007-10-17 14:18:16 -04:00
2007-10-28 14:48:02 -04:00
if ( parentTab ) {
var firstSibling = this . getFirstChildTab ( parentTab ) ;
var lastSibling = this . getLastChildTab ( parentTab ) ;
if ( tab == lastSibling ) {
if ( tab == firstSibling ) { // there is only one child
nextFocusedTab = parentTab ;
}
else { // previous sibling tab
nextFocusedTab = this . getPreviousSiblingTab ( tab ) ;
2007-10-17 13:45:09 -04:00
}
2007-10-17 14:18:16 -04:00
}
2007-10-28 14:48:02 -04:00
this . partTab ( tab , true ) ;
}
if ( ! nextFocusedTab ) {
nextFocusedTab = this . getNextSiblingTab ( tab ) ;
2007-10-17 13:45:09 -04:00
}
2007-10-19 02:40:30 -04:00
if ( nextFocusedTab && b . selectedTab == tab )
2007-10-17 13:45:09 -04:00
b . selectedTab = nextFocusedTab ;
2007-10-20 04:22:42 -04:00
this . checkTabsIndentOverflow ( b ) ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-19 09:05:29 -04:00
onTabMove : function ( aEvent )
{
var tab = aEvent . originalTarget ;
this . initTabContents ( tab ) ; // twisty vanished after the tab is moved!!
2007-10-26 15:27:30 -04:00
var rebuildTreeDone = false ;
2007-10-19 09:05:29 -04:00
var b = this . getTabBrowserFromChildren ( tab ) ;
if ( tab . getAttribute ( this . kCHILDREN ) && ! b . _ _treestyletab _ _isSubTreeMoving ) {
this . moveTabSubTreeTo ( tab , tab . _tPos ) ;
2007-10-26 15:27:30 -04:00
rebuildTreeDone = true ;
2007-10-19 09:05:29 -04:00
}
2007-10-19 22:44:14 -04:00
var parentTab = this . getParentTab ( tab ) ;
2007-10-19 09:05:29 -04:00
if ( parentTab && ! b . _ _treestyletab _ _isSubTreeChildrenMoving ) {
2007-10-26 15:27:30 -04:00
this . updateChildrenArray ( parentTab ) ;
}
if (
rebuildTreeDone ||
b . _ _treestyletab _ _isSubTreeMoving ||
b . _ _treestyletab _ _internallyTabMoving
)
return ;
var nest = Number ( tab . getAttribute ( this . kNEST ) || 0 ) ;
var parent = this . getParentTab ( tab ) ;
var prevParent = this . getParentTab ( tab . previousSibling ) ;
var nextParent = this . getParentTab ( tab . nextSibling ) ;
var prevNest = tab . previousSibling ? Number ( tab . previousSibling . getAttribute ( this . kNEST ) ) : - 1 ;
var nextNest = tab . nextSibling ? Number ( tab . nextSibling . getAttribute ( this . kNEST ) ) : - 1 ;
if (
! tab . previousSibling || ! tab . nextSibling ||
prevParent == nextParent ||
prevNest > nextNest
) {
if ( prevParent )
this . attachTabTo ( tab , prevParent , { insertBefore : tab . nextSibling } ) ;
else
this . partTab ( tab ) ;
}
else if ( prevNest < nextNest ) {
this . attachTabTo ( tab , tab . previousSibling , { insertBefore : tab . nextSibling } ) ;
2007-10-19 09:05:29 -04:00
}
} ,
2007-10-26 15:27:30 -04:00
updateChildrenArray : function ( aTab )
{
var children = this . getChildTabs ( aTab ) ;
children . sort ( function ( aA , aB ) { return aA . _tPos - aB . _tPos ; } ) ;
var self = this ;
this . setTabValue ( aTab , this . kCHILDREN ,
children . map ( function ( aItem ) { return aItem . getAttribute ( self . kID ) ; } ) . join ( '|' ) ) ;
} ,
2007-10-19 09:05:29 -04:00
2007-10-17 19:48:30 -04:00
onTabRestored : function ( aEvent )
{
var tab = aEvent . originalTarget ;
2007-10-18 11:40:06 -04:00
var b = this . getTabBrowserFromChildren ( tab ) ;
var id = this . getTabValue ( tab , this . kID ) ;
this . setTabValue ( tab , this . kID , id ) ;
2007-10-17 19:48:30 -04:00
2007-10-18 13:11:03 -04:00
var isSubTreeCollapsed = ( this . getTabValue ( tab , this . kSUBTREE _COLLAPSED ) == 'true' ) ;
2007-10-18 11:40:06 -04:00
var children = this . getTabValue ( tab , this . kCHILDREN ) ;
if ( children ) {
children = children . split ( '|' ) ;
var tabs = [ ] ;
for ( var i = 0 , maxi = children . length ; i < maxi ; i ++ )
{
if ( children [ i ] && ( children [ i ] = this . getTabById ( children [ i ] , b ) ) ) {
2007-10-19 22:44:14 -04:00
this . attachTabTo ( children [ i ] , tab , { dontExpand : true , dontUpdateIndent : true } ) ;
2007-10-18 11:40:06 -04:00
tabs . push ( children [ i ] ) ;
}
}
2007-10-17 19:48:30 -04:00
}
2007-10-18 11:40:06 -04:00
var parent = this . getTabValue ( tab , this . kPARENT ) ;
2007-10-18 13:11:03 -04:00
var before = this . getTabValue ( tab , this . kINSERT _BEFORE ) ;
2007-10-26 06:25:59 -04:00
if ( parent ) {
parent = this . getTabById ( parent , b ) ;
if ( parent ) {
this . attachTabTo ( tab , parent , { dontExpand : true , insertBefore : ( before ? this . getTabById ( before , b ) : null ) , dontUpdateIndent : true } ) ;
this . updateTabsIndent ( [ tab ] ) ;
this . checkTabsIndentOverflow ( b ) ;
}
else {
this . deleteTabValue ( tab , this . kPARENT ) ;
}
2007-10-18 11:40:06 -04:00
}
else if ( children ) {
this . updateTabsIndent ( tabs ) ;
2007-10-20 04:22:42 -04:00
this . checkTabsIndentOverflow ( b ) ;
2007-10-17 19:48:30 -04:00
}
2007-10-18 13:11:03 -04:00
2007-10-26 06:25:59 -04:00
if ( ! parent && ( before = this . getTabById ( before , b ) ) ) {
var index = before . _tPos ;
if ( index > tab . _tPos ) index -- ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-26 06:25:59 -04:00
b . moveTabTo ( tab , index ) ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-26 06:25:59 -04:00
}
this . deleteTabValue ( tab , this . kINSERT _BEFORE ) ;
2007-10-18 13:11:03 -04:00
if ( isSubTreeCollapsed ) {
this . collapseExpandTabSubTree ( tab , isSubTreeCollapsed ) ;
}
} ,
onTabMouseDown : function ( aEvent )
{
if ( aEvent . button != 0 ||
! this . isEventFiredOnTwisty ( aEvent ) )
return ;
this . getTabFromEvent ( aEvent ) . _ _treestyletab _ _preventSelect = true ;
2007-10-17 19:48:30 -04:00
} ,
2007-10-16 13:22:28 -04:00
onTabClick : function ( aEvent )
{
2007-10-18 13:11:03 -04:00
if ( aEvent . button != 0 ||
! this . isEventFiredOnTwisty ( aEvent ) )
return ;
2007-10-16 13:22:28 -04:00
var tab = this . getTabFromEvent ( aEvent ) ;
2007-10-18 13:11:03 -04:00
this . collapseExpandTabSubTree ( tab , tab . getAttribute ( this . kSUBTREE _COLLAPSED ) != 'true' ) ;
2007-10-16 13:22:28 -04:00
2007-10-18 13:11:03 -04:00
aEvent . preventDefault ( ) ;
aEvent . stopPropagation ( ) ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-18 14:03:05 -04:00
onTabSelect : function ( aEvent )
{
var b = this . getTabBrowserFromChildren ( aEvent . currentTarget ) ;
var tab = b . selectedTab
/ *
var p ;
if ( ( tab . getAttribute ( this . kCOLLAPSED ) == 'true' ) &&
2007-10-19 22:44:14 -04:00
( p = this . getParentTab ( tab ) ) ) {
2007-10-18 14:03:05 -04:00
b . selectedTab = p ;
}
* /
if ( tab . getAttribute ( this . kCOLLAPSED ) == 'true' ) {
var parentTab = tab ;
2007-10-19 22:44:14 -04:00
while ( parentTab = this . getParentTab ( parentTab ) )
2007-10-18 14:03:05 -04:00
{
this . collapseExpandTabSubTree ( parentTab , false ) ;
}
}
else if ( tab . getAttribute ( this . kCHILDREN ) &&
( tab . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ) &&
2007-10-26 07:24:59 -04:00
this . getTreePref ( 'autoCollapseExpandSubTreeOnSelect' ) ) {
2007-10-18 14:20:54 -04:00
this . collapseExpandTreesIntelligentlyFor ( tab ) ;
2007-10-18 14:03:05 -04:00
}
} ,
2007-10-20 07:29:42 -04:00
onTabbarResized : function ( aEvent )
{
var b = this . getTabBrowserFromChildren ( aEvent . originalTarget ) ;
this . setPref ( 'extensions.treestyletab.tabbar.width' , b . mStrip . boxObject . width ) ;
} ,
2007-10-20 16:42:20 -04:00
processDropAction : function ( aInfo , aTabBrowser , aTarget )
{
var b = this . getTabBrowserFromChildren ( aTabBrowser ) ;
var tabs = b . mTabContainer . childNodes ;
if ( aTarget && aInfo . action & this . kACTION _PART ) {
this . partTab ( aTarget ) ;
}
else if ( aInfo . action & this . kACTION _ATTACH ) {
2007-10-21 02:47:40 -04:00
if ( aInfo . parent )
this . attachTabTo ( aTarget , aInfo . parent ) ;
else
this . partTab ( aTarget ) ;
2007-10-20 16:42:20 -04:00
}
else {
return false ;
}
if (
aInfo . action & this . kACTION _MOVE &&
(
! aInfo . insertBefore ||
this . getNextVisibleTab ( aTarget ) != aInfo . insertBefore
)
) {
var newIndex = aInfo . insertBefore ? aInfo . insertBefore . _tPos : tabs . length - 1 ;
if ( aInfo . insertBefore && newIndex > aTarget . _tPos ) newIndex -- ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-20 16:42:20 -04:00
b . moveTabTo ( aTarget , newIndex ) ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-20 16:42:20 -04:00
}
return true ;
} ,
2007-10-22 05:59:43 -04:00
initContextMenu : function ( )
{
var item = document . getElementById ( 'context-treestyletab-openSelectionLinks' ) ;
var sep = document . getElementById ( 'context-treestyletab-openSelectionLinks-separator' ) ;
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'show.openSelectionLinks' ) && this . getSelectionLinks ( ) . length ) {
2007-10-22 05:59:43 -04:00
item . removeAttribute ( 'hidden' ) ;
sep . removeAttribute ( 'hidden' ) ;
}
else {
item . setAttribute ( 'hidden' , true ) ;
sep . setAttribute ( 'hidden' , true ) ;
}
} ,
2007-10-22 19:29:07 -04:00
2007-10-17 13:45:09 -04:00
/* Tab Utilities */
2007-10-20 07:29:42 -04:00
2007-10-17 19:48:30 -04:00
getTabValue : function ( aTab , aKey )
{
var value = null ;
try {
value = this . SessionStore . getTabValue ( aTab , aKey ) ;
}
catch ( e ) {
}
return value ;
} ,
2007-10-17 13:45:09 -04:00
setTabValue : function ( aTab , aKey , aValue )
{
if ( ! aValue ) {
return this . deleteTabValue ( aTab , aKey ) ;
}
aTab . setAttribute ( aKey , aValue ) ;
try {
this . SessionStore . setTabValue ( aTab , aKey , aValue ) ;
}
catch ( e ) {
}
2007-10-17 19:48:30 -04:00
return aValue ;
2007-10-17 13:45:09 -04:00
} ,
deleteTabValue : function ( aTab , aKey )
{
aTab . removeAttribute ( aKey ) ;
try {
this . SessionStore . deleteTabValue ( aTab , aKey ) ;
}
catch ( e ) {
}
} ,
2007-10-16 13:22:28 -04:00
getTabById : function ( aId , aTabBrowser )
{
2007-10-18 23:05:36 -04:00
return this . evaluateXPath (
'descendant::xul:tab[@' + this . kID + ' = "' + aId + '"]' ,
aTabBrowser . mTabContainer ,
XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-19 22:44:14 -04:00
getNextVisibleTab : function ( aTab )
{
var xpathResult = this . evaluateXPath (
'following-sibling::xul:tab[not(@' + TreeStyleTabService . kCOLLAPSED + '="true")]' ,
aTab
) ;
return xpathResult . snapshotItem ( 0 ) ;
} ,
getPreviousVisibleTab : function ( aTab )
{
var xpathResult = this . evaluateXPath (
'preceding-sibling::xul:tab[not(@' + TreeStyleTabService . kCOLLAPSED + '="true")]' ,
aTab
) ;
return xpathResult . snapshotItem ( xpathResult . snapshotLength - 1 ) ;
} ,
/* tree */
2007-10-20 06:24:36 -04:00
2007-10-20 04:22:42 -04:00
getRootTabs : function ( aTabBrowser )
{
return this . evaluateXPath (
'child::xul:tab[not(@' + this . kNEST + ') or @' + this . kNEST + '="0" or @' + this . kNEST + '=""]' ,
aTabBrowser . mTabContainer
) ;
} ,
2007-10-19 22:44:14 -04:00
getParentTab : function ( aTab )
2007-10-16 13:22:28 -04:00
{
2007-10-26 15:27:30 -04:00
if ( ! aTab ) return null ;
2007-10-18 23:05:36 -04:00
return this . evaluateXPath (
2007-10-26 15:27:30 -04:00
'parent::*/child::xul:tab[contains(@' + this . kCHILDREN + ', "' + aTab . getAttribute ( this . kID ) + '")]' ,
2007-10-18 23:05:36 -04:00
aTab ,
XPathResult . FIRST _ORDERED _NODE _TYPE
) . singleNodeValue ;
2007-10-16 13:22:28 -04:00
} ,
2007-10-17 13:45:09 -04:00
2007-10-19 22:44:14 -04:00
getNextSiblingTab : function ( aTab )
2007-10-16 13:22:28 -04:00
{
2007-10-26 15:27:30 -04:00
if ( ! aTab ) return null ;
2007-10-17 13:45:09 -04:00
var id = aTab . getAttribute ( this . kID ) ;
2007-10-19 22:44:14 -04:00
var parentTab = this . getParentTab ( aTab ) ;
2007-10-16 13:22:28 -04:00
2007-10-17 13:45:09 -04:00
if ( ! parentTab ) {
var next = aTab ;
do {
next = next . nextSibling ;
}
2007-10-19 22:44:14 -04:00
while ( next && this . getParentTab ( next ) ) ;
2007-10-17 13:45:09 -04:00
return next ;
}
2007-10-16 13:22:28 -04:00
2007-10-17 13:45:09 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
var children = parentTab . getAttribute ( this . kCHILDREN ) ;
if ( children ) {
2007-10-18 11:40:06 -04:00
var list = ( '|' + children ) . split ( '|' + id ) [ 1 ] . split ( '|' ) ;
2007-10-17 13:45:09 -04:00
for ( var i = 0 , maxi = list . length ; i < maxi ; i ++ )
{
2007-10-19 09:05:29 -04:00
var firstChild = this . getTabById ( list [ i ] , b ) ;
if ( firstChild ) return firstChild ;
2007-10-17 13:45:09 -04:00
}
}
2007-10-19 09:05:29 -04:00
return null ;
2007-10-17 13:45:09 -04:00
} ,
2007-10-19 22:44:14 -04:00
getPreviousSiblingTab : function ( aTab )
2007-10-17 13:45:09 -04:00
{
2007-10-26 15:27:30 -04:00
if ( ! aTab ) return null ;
2007-10-17 13:45:09 -04:00
var id = aTab . getAttribute ( this . kID ) ;
2007-10-19 22:44:14 -04:00
var parentTab = this . getParentTab ( aTab ) ;
2007-10-17 13:45:09 -04:00
if ( ! parentTab ) {
var prev = aTab ;
do {
prev = prev . previousSibling ;
}
2007-10-19 22:44:14 -04:00
while ( prev && this . getParentTab ( prev ) ) ;
2007-10-17 13:45:09 -04:00
return prev ;
}
var b = this . getTabBrowserFromChildren ( aTab ) ;
var children = parentTab . getAttribute ( this . kCHILDREN ) ;
if ( children ) {
2007-10-18 11:40:06 -04:00
var list = ( '|' + children ) . split ( '|' + id ) [ 0 ] . split ( '|' ) ;
2007-10-17 13:45:09 -04:00
for ( var i = list . length - 1 ; i > - 1 ; i -- )
{
2007-10-19 09:05:29 -04:00
var lastChild = this . getTabById ( list [ i ] , b )
if ( lastChild ) return lastChild ;
2007-10-17 13:45:09 -04:00
}
}
2007-10-19 09:05:29 -04:00
return null ;
2007-10-17 13:45:09 -04:00
} ,
2007-10-19 22:44:14 -04:00
getChildTabs : function ( aTab , aAllTabsArray )
2007-10-17 13:45:09 -04:00
{
2007-10-26 15:27:30 -04:00
var tabs = [ ] ;
if ( ! aTab ) return null ;
2007-10-17 13:45:09 -04:00
var children = aTab . getAttribute ( this . kCHILDREN ) ;
if ( ! children ) return tabs ;
2007-10-17 14:36:39 -04:00
if ( aAllTabsArray ) tabs = aAllTabsArray ;
2007-10-17 13:45:09 -04:00
var list = children . split ( '|' ) ;
var b = this . getTabBrowserFromChildren ( aTab ) ;
var tab ;
for ( var i = 0 , maxi = list . length ; i < maxi ; i ++ )
{
tab = this . getTabById ( list [ i ] , b )
2007-10-18 11:40:06 -04:00
if ( ! tab ) continue ;
tabs . push ( tab ) ;
if ( aAllTabsArray )
2007-10-19 22:44:14 -04:00
this . getChildTabs ( tab , tabs ) ;
2007-10-17 13:45:09 -04:00
}
return tabs ;
} ,
2007-10-19 22:44:14 -04:00
getDescendantTabs : function ( aTab )
{
var tabs = [ ] ;
this . getChildTabs ( aTab , tabs ) ;
return tabs ;
} ,
getFirstChildTab : function ( aTab )
2007-10-17 13:45:09 -04:00
{
2007-10-26 15:27:30 -04:00
if ( ! aTab ) return null ;
2007-10-17 13:45:09 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
var children = aTab . getAttribute ( this . kCHILDREN ) ;
var firstChild = null ;
if ( children ) {
var list = children . split ( '|' ) ;
for ( var i = 0 , maxi = list . length ; i < maxi ; i ++ )
{
firstChild = this . getTabById ( list [ i ] , b )
if ( firstChild ) break ;
}
}
return firstChild ;
} ,
2007-10-19 22:44:14 -04:00
getLastChildTab : function ( aTab )
2007-10-17 13:45:09 -04:00
{
2007-10-26 15:27:30 -04:00
if ( ! aTab ) return null ;
2007-10-17 13:45:09 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
var children = aTab . getAttribute ( this . kCHILDREN ) ;
2007-10-16 13:22:28 -04:00
var lastChild = null ;
if ( children ) {
var list = children . split ( '|' ) ;
for ( var i = list . length - 1 ; i > - 1 ; i -- )
{
lastChild = this . getTabById ( list [ i ] , b )
if ( lastChild ) break ;
}
}
2007-10-17 13:45:09 -04:00
return lastChild ;
} ,
2007-10-20 02:12:22 -04:00
getDropAction : function ( aEvent , aDragSession )
{
var info = this . getDropActionInternal ( aEvent ) ;
info . canDrop = true ;
2007-10-20 16:42:20 -04:00
if ( info . action & this . kACTION _ATTACH &&
aDragSession &&
aDragSession . sourceNode &&
aDragSession . sourceNode . localName == 'tab' ) {
2007-10-20 02:12:22 -04:00
var orig = aDragSession . sourceNode ;
2007-10-20 08:45:03 -04:00
if ( orig == info . parent ) {
2007-10-20 02:12:22 -04:00
info . canDrop = false ;
2007-10-20 08:45:03 -04:00
}
else {
var tab = info . target ;
while ( tab = this . getParentTab ( tab ) )
{
if ( tab != orig ) continue ;
info . canDrop = false ;
break ;
}
2007-10-20 02:12:22 -04:00
}
}
return info ;
} ,
2007-10-20 04:22:42 -04:00
getDropActionInternal : function ( aEvent )
2007-10-19 22:44:14 -04:00
{
var tab = aEvent . target ;
var b = this . getTabBrowserFromChildren ( tab ) ;
var tabs = b . mTabContainer . childNodes ;
2007-10-24 15:37:21 -04:00
var isInverted = this . isTabVertical ( b ) ? false : window . getComputedStyle ( b . parentNode , null ) . direction == 'rtl' ;
2007-10-19 22:44:14 -04:00
var info = {
2007-10-19 23:38:46 -04:00
target : null ,
position : null ,
action : null ,
parent : null ,
insertBefore : null
2007-10-19 22:44:14 -04:00
} ;
if ( tab . localName != 'tab' ) {
if ( aEvent [ this . positionProp ] < tabs [ 0 ] . boxObject [ this . positionProp ] ) {
2007-10-19 23:38:46 -04:00
info . target = info . parent = info . insertBefore = tabs [ 0 ] ;
2007-10-19 22:44:14 -04:00
info . position = isInverted ? this . kDROP _AFTER : this . kDROP _BEFORE ;
info . action = this . kACTION _MOVE | this . kACTION _PART ;
return info ;
}
else if ( aEvent [ this . positionProp ] > tabs [ tabs . length - 1 ] . boxObject [ this . positionProp ] + tabs [ tabs . length - 1 ] . boxObject [ this . sizeProp ] ) {
2007-10-19 23:38:46 -04:00
info . target = info . parent = tabs [ tabs . length - 1 ] ;
2007-10-19 22:44:14 -04:00
info . position = isInverted ? this . kDROP _BEFORE : this . kDROP _AFTER ;
info . action = this . kACTION _MOVE | this . kACTION _PART ;
return info ;
}
else {
2007-10-19 23:38:46 -04:00
info . target = tabs [ Math . min ( b . getNewIndex ( aEvent ) , tabs . length - 1 ) ] ;
2007-10-19 22:44:14 -04:00
}
}
else {
2007-10-19 23:38:46 -04:00
info . target = tab ;
2007-10-19 22:44:14 -04:00
}
var boxPos = tab . boxObject [ this . positionProp ] ;
var boxUnit = Math . round ( tab . boxObject [ this . sizeProp ] / 3 ) ;
if ( aEvent [ this . positionProp ] < boxPos + boxUnit ) {
info . position = isInverted ? this . kDROP _AFTER : this . kDROP _BEFORE ;
}
else if ( aEvent [ this . positionProp ] > boxPos + boxUnit + boxUnit ) {
info . position = isInverted ? this . kDROP _BEFORE : this . kDROP _AFTER ;
}
else {
info . position = this . kDROP _ON ;
}
switch ( info . position )
{
case this . kDROP _ON :
2007-10-19 23:38:46 -04:00
info . action = this . kACTION _ATTACH ;
info . parent = tab ;
info . insertBefore = this . getNextVisibleTab ( tab ) ;
2007-10-19 22:44:14 -04:00
break ;
case this . kDROP _BEFORE :
/ *
[ TARGET ] <EFBFBD> <EFBFBD> part from parent , and move
[ ]
2007-10-20 09:35:04 -04:00
[ TARGET ] <EFBFBD> <EFBFBD> attach to the parent of the target , and move
2007-10-19 22:44:14 -04:00
[ ]
[ TARGET ] <EFBFBD> <EFBFBD> attach to the parent of the target , and move
[ ]
2007-10-20 09:35:04 -04:00
[ TARGET ] <EFBFBD> <EFBFBD> attach to the parent of the target ( previous tab ) , and move
2007-10-19 22:44:14 -04:00
* /
var prevTab = this . getPreviousVisibleTab ( tab ) ;
if ( ! prevTab ) {
2007-10-19 23:38:46 -04:00
info . action = this . kACTION _MOVE | this . kACTION _PART ;
info . insertBefore = tabs [ 0 ] ;
2007-10-19 22:44:14 -04:00
}
else {
var prevNest = Number ( prevTab . getAttribute ( this . kNEST ) ) ;
var targetNest = Number ( tab . getAttribute ( this . kNEST ) ) ;
2007-10-20 09:41:40 -04:00
info . parent = ( prevNest < targetNest ) ? prevTab : this . getParentTab ( tab ) ;
info . action = this . kACTION _MOVE | ( info . parent ? this . kACTION _ATTACH : this . kACTION _PART ) ;
2007-10-19 23:38:46 -04:00
info . insertBefore = tab ;
2007-10-19 22:44:14 -04:00
}
break ;
case this . kDROP _AFTER :
/ *
2007-10-20 09:35:04 -04:00
[ TARGET ] <EFBFBD> <EFBFBD> if the target has a parent , attach to it and and move
2007-10-19 22:44:14 -04:00
[ TARGET ] <EFBFBD> <EFBFBD> attach to the parent of the target , and move
[ ]
[ TARGET ] <EFBFBD> <EFBFBD> attach to the parent of the target , and move
[ ]
[ TARGET ] <EFBFBD> <EFBFBD> attach to the target , and move
[ ]
* /
var nextTab = this . getNextVisibleTab ( tab ) ;
if ( ! nextTab ) {
2007-10-20 09:35:04 -04:00
info . action = this . kACTION _MOVE | this . kACTION _ATTACH ;
info . parent = this . getParentTab ( tab ) ;
2007-10-19 22:44:14 -04:00
}
else {
var targetNest = Number ( tab . getAttribute ( this . kNEST ) ) ;
var nextNest = Number ( nextTab . getAttribute ( this . kNEST ) ) ;
2007-10-20 09:41:40 -04:00
info . parent = ( targetNest < nextNest ) ? tab : this . getParentTab ( tab ) ;
info . action = this . kACTION _MOVE | ( info . parent ? this . kACTION _ATTACH : this . kACTION _PART ) ;
2007-10-19 23:38:46 -04:00
info . insertBefore = nextTab ;
2007-10-19 22:44:14 -04:00
}
break ;
}
return info ;
} ,
2007-10-20 02:12:22 -04:00
clearDropPosition : function ( aTabBrowser )
{
var b = this . getTabBrowserFromChildren ( aTabBrowser ) ;
var xpathResult = this . evaluateXPath (
'child::xul:tab[@' + this . kDROP _POSITION + ']' ,
b . mTabContainer
) ;
for ( var i = 0 , maxi = xpathResult . snapshotLength ; i < maxi ; i ++ )
{
xpathResult . snapshotItem ( i ) . removeAttribute ( this . kDROP _POSITION ) ;
}
} ,
2007-10-20 04:22:42 -04:00
2007-10-17 13:45:09 -04:00
/* Commands */
2007-10-22 19:29:07 -04:00
2007-10-20 07:29:42 -04:00
initTabbar : function ( aTabBrowser , aPosition )
2007-10-20 06:24:36 -04:00
{
2007-10-26 07:24:59 -04:00
if ( ! aPosition ) aPosition = this . getTreePref ( 'tabbar.position' ) ;
2007-10-20 06:24:36 -04:00
aPosition = String ( aPosition ) . toLowerCase ( ) ;
var pos = ( aPosition == 'left' ) ? this . kTABBAR _LEFT :
( aPosition == 'right' ) ? this . kTABBAR _RIGHT :
( aPosition == 'bottom' ) ? this . kTABBAR _BOTTOM :
this . kTABBAR _TOP ;
2007-10-20 07:29:42 -04:00
var splitter = document . getAnonymousElementByAttribute ( aTabBrowser , 'class' , this . kSPLITTER ) ;
if ( ! splitter ) {
splitter = document . createElement ( 'splitter' ) ;
splitter . setAttribute ( 'class' , this . kSPLITTER ) ;
splitter . setAttribute ( 'onmouseup' , 'TreeStyleTabService.onTabbarResized(event);' ) ;
splitter . appendChild ( document . createElement ( 'grippy' ) ) ;
var ref = aTabBrowser . mPanelContainer ;
ref . parentNode . insertBefore ( splitter , ref ) ;
}
2007-10-20 12:47:08 -04:00
var scrollInnerBox = document . getAnonymousNodes ( aTabBrowser . mTabContainer . mTabstrip . _scrollbox ) [ 0 ] ;
2007-10-20 06:24:36 -04:00
if ( pos & this . kTABBAR _VERTICAL ) {
this . positionProp = 'screenY' ;
this . sizeProp = 'height' ;
this . invertedSizeProp = 'width' ;
aTabBrowser . mTabBox . orient = 'horizontal' ;
aTabBrowser . mTabContainer . orient = aTabBrowser . mTabContainer . mTabstrip . orient = 'vertical' ;
2007-10-20 12:47:08 -04:00
scrollInnerBox . removeAttribute ( 'flex' ) ;
2007-10-20 06:24:36 -04:00
2007-10-20 08:15:05 -04:00
aTabBrowser . mPanelContainer . removeAttribute ( 'width' ) ;
2007-10-26 07:24:59 -04:00
aTabBrowser . mStrip . setAttribute ( 'width' , this . getTreePref ( 'tabbar.width' ) ) ;
2007-10-20 07:29:42 -04:00
2007-10-26 08:56:04 -04:00
aTabBrowser . setAttribute ( this . kMODE , 'vertical' ) ;
2007-10-20 08:15:05 -04:00
if ( pos == this . kTABBAR _RIGHT ) {
aTabBrowser . setAttribute ( this . kTABBAR _POSITION , 'right' ) ;
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'tabbar.invertUI' ) ) {
2007-10-23 02:05:44 -04:00
aTabBrowser . setAttribute ( this . kUI _INVERTED , 'true' ) ;
2007-10-21 23:08:14 -04:00
this . levelMarginProp = 'margin-right' ;
}
else {
2007-10-23 02:05:44 -04:00
aTabBrowser . removeAttribute ( this . kUI _INVERTED ) ;
2007-10-21 23:08:14 -04:00
this . levelMarginProp = 'margin-left' ;
}
2007-10-20 08:15:05 -04:00
window . setTimeout ( function ( ) {
2007-10-24 15:37:21 -04:00
aTabBrowser . mTabDropIndicatorBar . setAttribute ( 'ordinal' , 1 ) ;
2007-10-20 08:15:05 -04:00
aTabBrowser . mStrip . setAttribute ( 'ordinal' , 30 ) ;
splitter . setAttribute ( 'ordinal' , 20 ) ;
aTabBrowser . mPanelContainer . setAttribute ( 'ordinal' , 10 ) ;
} , 0 ) ;
}
else {
aTabBrowser . setAttribute ( this . kTABBAR _POSITION , 'left' ) ;
2007-10-23 02:05:44 -04:00
aTabBrowser . removeAttribute ( this . kUI _INVERTED ) ;
2007-10-21 23:08:14 -04:00
this . levelMarginProp = 'margin-left' ;
2007-10-20 08:15:05 -04:00
window . setTimeout ( function ( ) {
2007-10-24 15:37:21 -04:00
aTabBrowser . mTabDropIndicatorBar . setAttribute ( 'ordinal' , 1 ) ;
2007-10-20 08:15:05 -04:00
aTabBrowser . mStrip . setAttribute ( 'ordinal' , 10 ) ;
splitter . setAttribute ( 'ordinal' , 20 ) ;
aTabBrowser . mPanelContainer . setAttribute ( 'ordinal' , 30 ) ;
} , 0 ) ;
}
2007-10-20 06:24:36 -04:00
}
else {
this . positionProp = 'screenX' ;
this . sizeProp = 'width' ;
this . invertedSizeProp = 'height' ;
aTabBrowser . mTabBox . orient = 'vertical' ;
aTabBrowser . mTabContainer . orient = aTabBrowser . mTabContainer . mTabstrip . orient = 'horizontal' ;
2007-10-20 12:47:08 -04:00
scrollInnerBox . setAttribute ( 'flex' , 1 ) ;
2007-10-20 06:24:36 -04:00
2007-10-20 07:29:42 -04:00
aTabBrowser . mStrip . removeAttribute ( 'width' ) ;
2007-10-20 08:15:05 -04:00
aTabBrowser . mPanelContainer . removeAttribute ( 'width' ) ;
2007-10-20 07:29:42 -04:00
2007-10-26 08:56:04 -04:00
aTabBrowser . setAttribute ( this . kMODE , this . getTreePref ( 'tabbar.multirow' ) ? 'multirow' : 'horizontal' ) ;
2007-10-24 15:37:21 -04:00
aTabBrowser . removeAttribute ( this . kUI _INVERTED ) ;
2007-10-20 08:15:05 -04:00
if ( pos == this . kTABBAR _BOTTOM ) {
aTabBrowser . setAttribute ( this . kTABBAR _POSITION , 'bottom' ) ;
2007-10-24 15:37:21 -04:00
this . levelMarginProp = 'margin-bottom' ;
2007-10-20 08:15:05 -04:00
window . setTimeout ( function ( ) {
2007-10-24 15:37:21 -04:00
aTabBrowser . mTabDropIndicatorBar . setAttribute ( 'ordinal' , 1 ) ;
2007-10-20 08:15:05 -04:00
aTabBrowser . mStrip . setAttribute ( 'ordinal' , 30 ) ;
splitter . setAttribute ( 'ordinal' , 20 ) ;
aTabBrowser . mPanelContainer . setAttribute ( 'ordinal' , 10 ) ;
} , 0 ) ;
}
else {
aTabBrowser . setAttribute ( this . kTABBAR _POSITION , 'top' ) ;
2007-10-21 23:08:14 -04:00
this . levelMarginProp = 'margin-top' ;
2007-10-20 08:15:05 -04:00
window . setTimeout ( function ( ) {
2007-10-24 15:37:21 -04:00
aTabBrowser . mTabDropIndicatorBar . setAttribute ( 'ordinal' , 1 ) ;
2007-10-20 08:15:05 -04:00
aTabBrowser . mStrip . setAttribute ( 'ordinal' , 10 ) ;
splitter . setAttribute ( 'ordinal' , 20 ) ;
aTabBrowser . mPanelContainer . setAttribute ( 'ordinal' , 30 ) ;
} , 0 ) ;
}
2007-10-20 06:24:36 -04:00
}
} ,
2007-10-19 22:44:14 -04:00
/* attach/part */
2007-10-20 06:24:36 -04:00
2007-10-19 22:44:14 -04:00
attachTabTo : function ( aChild , aParent , aInfo )
2007-10-17 13:45:09 -04:00
{
2007-10-20 08:45:03 -04:00
if (
! aChild ||
! aParent ||
aChild == aParent ||
this . getParentTab ( aChild ) == aParent
)
return ;
2007-10-18 14:54:25 -04:00
if ( ! aInfo ) aInfo = { } ;
2007-10-18 11:40:06 -04:00
2007-10-17 13:45:09 -04:00
var id = aChild . getAttribute ( this . kID ) ;
var b = this . getTabBrowserFromChildren ( aParent ) ;
2007-10-16 13:22:28 -04:00
2007-10-19 22:44:14 -04:00
this . partTab ( aChild , true ) ;
2007-10-17 13:45:09 -04:00
var children = aParent . getAttribute ( this . kCHILDREN ) ;
var newIndex ;
2007-10-17 19:48:30 -04:00
if ( children . indexOf ( id ) > - 1 ) {
children = ( '|' + children ) . replace ( '|' + id , '' ) . replace ( /^\|/ ) ;
}
2007-10-18 14:54:25 -04:00
var insertBefore = aInfo . insertBefore ;
var beforeTab = insertBefore ? insertBefore . getAttribute ( this . kID ) : null ;
if ( beforeTab && children . indexOf ( beforeTab ) > - 1 ) {
2007-10-18 11:40:06 -04:00
children = children . replace ( beforeTab , id + '|' + beforeTab ) ;
2007-10-18 14:54:25 -04:00
newIndex = insertBefore . _tPos ;
2007-10-16 13:22:28 -04:00
}
2007-10-17 13:45:09 -04:00
else {
children = ( ( children || '' ) + '|' + id ) . replace ( /^\|/ , '' ) ;
2007-10-19 09:05:29 -04:00
var refTab = aParent ;
2007-10-19 22:44:14 -04:00
var descendant = this . getDescendantTabs ( aParent ) ;
2007-10-19 09:05:29 -04:00
if ( descendant . length ) refTab = descendant [ descendant . length - 1 ] ;
newIndex = refTab . _tPos + 1 ;
2007-10-16 13:22:28 -04:00
}
2007-10-17 13:45:09 -04:00
this . setTabValue ( aParent , this . kCHILDREN , children ) ;
2007-10-26 06:25:59 -04:00
this . setTabValue ( aChild , this . kPARENT , aParent . getAttribute ( this . kID ) ) ;
2007-10-19 02:40:30 -04:00
this . updateTabsCount ( aParent ) ;
2007-10-17 13:45:09 -04:00
2007-10-16 13:22:28 -04:00
if ( newIndex > aChild . _tPos ) newIndex -- ;
2007-10-17 19:48:30 -04:00
this . moveTabSubTreeTo ( aChild , newIndex ) ;
2007-10-16 13:22:28 -04:00
2007-10-18 14:54:25 -04:00
if ( ! aInfo . dontExpand ) {
if (
2007-10-22 16:31:11 -04:00
/ *
2007-10-18 14:54:25 -04:00
(
aParent . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ||
2007-10-22 16:31:11 -04:00
children . indexOf ( '|' ) > - 1 // not a first child
2007-10-18 14:54:25 -04:00
) &&
2007-10-22 16:31:11 -04:00
* /
2007-10-26 07:24:59 -04:00
this . getTreePref ( 'autoCollapseExpandSubTreeOnSelect' )
2007-10-18 14:54:25 -04:00
) {
2007-10-22 16:31:11 -04:00
this . collapseExpandTreesIntelligentlyFor ( aParent ) ;
2007-10-20 04:22:42 -04:00
var p = aParent ;
do {
this . collapseExpandTabSubTree ( p , false ) ;
}
while ( p = this . getParentTab ( p ) ) ;
2007-10-18 14:20:54 -04:00
}
2007-10-18 14:54:25 -04:00
else if ( aParent . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ) {
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'autoExpandSubTreeOnAppendChild' ) ) {
2007-10-18 14:54:25 -04:00
var p = aParent ;
do {
this . collapseExpandTabSubTree ( p , false ) ;
}
2007-10-19 22:44:14 -04:00
while ( p = this . getParentTab ( p ) ) ;
2007-10-18 14:54:25 -04:00
}
else
this . collapseExpandTab ( aChild , true ) ;
2007-10-18 13:11:03 -04:00
}
2007-10-18 14:54:25 -04:00
if ( aParent . getAttribute ( this . kCOLLAPSED ) == 'true' )
2007-10-18 13:11:03 -04:00
this . collapseExpandTab ( aChild , true ) ;
}
2007-10-18 14:54:25 -04:00
else if ( aParent . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ||
aParent . getAttribute ( this . kCOLLAPSED ) == 'true' ) {
2007-10-18 13:11:03 -04:00
this . collapseExpandTab ( aChild , true ) ;
2007-10-18 14:54:25 -04:00
}
2007-10-18 13:11:03 -04:00
2007-10-20 04:22:42 -04:00
if ( ! aInfo . dontUpdateIndent ) {
this . updateTabsIndent ( [ aChild ] ) ;
this . checkTabsIndentOverflow ( b ) ;
}
2007-10-16 13:22:28 -04:00
} ,
2007-10-19 22:44:14 -04:00
partTab : function ( aChild , aDontUpdateIndent )
2007-10-16 13:22:28 -04:00
{
2007-10-18 11:40:06 -04:00
if ( ! aChild ) return ;
2007-10-19 22:44:14 -04:00
var parentTab = this . getParentTab ( aChild ) ;
2007-10-17 13:45:09 -04:00
if ( ! parentTab ) return ;
2007-10-16 13:22:28 -04:00
var id = aChild . getAttribute ( this . kID ) ;
2007-10-17 13:45:09 -04:00
var children = ( '|' + parentTab . getAttribute ( this . kCHILDREN ) )
2007-10-16 13:22:28 -04:00
. replace ( new RegExp ( '\\|' + id ) , '' )
. replace ( /^\|/ , '' ) ;
2007-10-17 13:45:09 -04:00
this . setTabValue ( parentTab , this . kCHILDREN , children ) ;
2007-10-19 02:40:30 -04:00
this . updateTabsCount ( parentTab ) ;
2007-10-17 13:45:09 -04:00
2007-10-20 04:22:42 -04:00
if ( ! aDontUpdateIndent ) {
this . updateTabsIndent ( [ aChild ] ) ;
2007-10-20 09:35:04 -04:00
var b = this . getTabBrowserFromChildren ( aChild ) ;
2007-10-20 04:22:42 -04:00
this . checkTabsIndentOverflow ( b ) ;
}
2007-10-17 13:45:09 -04:00
} ,
2007-10-19 02:49:20 -04:00
updateTabsIndent : function ( aTabs , aLevel , aProp )
2007-10-17 13:45:09 -04:00
{
if ( ! aTabs || ! aTabs . length ) return ;
if ( aLevel === void ( 0 ) ) {
2007-10-19 22:44:14 -04:00
var parentTab = this . getParentTab ( aTabs [ 0 ] ) ;
2007-10-17 13:45:09 -04:00
var aLevel = 0 ;
while ( parentTab )
{
aLevel ++ ;
2007-10-19 22:44:14 -04:00
parentTab = this . getParentTab ( parentTab ) ;
2007-10-16 13:22:28 -04:00
}
}
2007-10-25 18:59:34 -04:00
if ( ! aProp ) {
2007-10-26 07:24:59 -04:00
aProp = this . getTreePref ( 'enableSubtreeIndent' ) ? this . levelMarginProp : 0 ;
2007-10-25 18:59:34 -04:00
}
2007-10-20 04:22:42 -04:00
var b = this . getTabBrowserFromChildren ( aTabs [ 0 ] ) ;
var margin = b . _ _treestyletab _ _levelMargin < 0 ? this . levelMargin : b . _ _treestyletab _ _levelMargin ;
var indent = margin * aLevel ;
2007-10-19 02:49:20 -04:00
2007-10-17 13:45:09 -04:00
for ( var i = 0 , maxi = aTabs . length ; i < maxi ; i ++ )
{
2007-10-25 18:59:34 -04:00
aTabs [ i ] . setAttribute ( 'style' , aTabs [ i ] . getAttribute ( 'style' ) . replace ( /margin(-[^:]+):[^;]+;?/g , '' ) + '; ' + aProp + ':' + indent + 'px !important;' ) ;
2007-10-19 22:44:14 -04:00
aTabs [ i ] . setAttribute ( this . kNEST , aLevel ) ;
this . updateTabsIndent ( this . getChildTabs ( aTabs [ i ] ) , aLevel + 1 , aProp ) ;
2007-10-17 13:45:09 -04:00
}
2007-10-16 13:22:28 -04:00
} ,
2007-10-19 22:44:14 -04:00
2007-10-20 04:22:42 -04:00
updateAllTabsIndent : function ( aTabBrowser )
{
var b = this . getTabBrowserFromChildren ( aTabBrowser ) ;
this . updateTabsIndent (
this . getArrayFromXPathResult (
this . getRootTabs ( b )
) ,
0
) ;
// this.checkTabsIndentOverflow(b);
} ,
2007-10-20 06:24:36 -04:00
checkTabsIndentOverflow : function ( aTabBrowser )
2007-10-20 04:22:42 -04:00
{
if ( this . checkTabsIndentOverflowTimer ) {
window . clearTimeout ( this . checkTabsIndentOverflowTimer ) ;
this . checkTabsIndentOverflowTimer = null ;
}
this . checkTabsIndentOverflowTimer = window . setTimeout ( function ( aSelf , aTabBrowser ) {
aSelf . checkTabsIndentOverflowCallback ( aTabBrowser ) ;
} , 100 , this , aTabBrowser ) ;
} ,
checkTabsIndentOverflowTimer : null ,
checkTabsIndentOverflowCallback : function ( aTabBrowser )
{
var b = aTabBrowser ;
var tabs = this . getArrayFromXPathResult ( this . evaluateXPath (
'child::xul:tab[@' + this . kNEST + ' and not(@' + this . kNEST + '="0" or @' + this . kNEST + '="")]' ,
b . mTabContainer
) ) ;
if ( ! tabs . length ) return ;
var self = this ;
tabs . sort ( function ( aA , aB ) { return Number ( aA . getAttribute ( self . kNEST ) ) - Number ( aB . getAttribute ( self . kNEST ) ) ; } ) ;
var nest = tabs [ tabs . length - 1 ] . getAttribute ( self . kNEST ) ;
if ( ! nest ) return ;
var oldMargin = b . _ _treestyletab _ _levelMargin ;
var indent = ( oldMargin < 0 ? this . levelMargin : oldMargin ) * nest ;
var maxIndent = b . mTabContainer . childNodes [ 0 ] . boxObject [ this . invertedSizeProp ] * 0.33 ;
var marginUnit = Math . max ( Math . floor ( maxIndent / nest ) , 1 ) ;
if ( indent > maxIndent ) {
b . _ _treestyletab _ _levelMargin = marginUnit ;
}
else {
b . _ _treestyletab _ _levelMargin = - 1 ;
if ( ( this . levelMargin * nest ) > maxIndent )
b . _ _treestyletab _ _levelMargin = marginUnit ;
}
if ( oldMargin != b . _ _treestyletab _ _levelMargin ) {
this . updateAllTabsIndent ( b ) ;
}
} ,
2007-10-20 06:24:36 -04:00
2007-10-19 02:40:30 -04:00
updateTabsCount : function ( aTab )
{
var count = document . getAnonymousElementByAttribute ( aTab , 'class' , this . kCOUNTER ) ;
if ( count ) {
2007-10-19 22:44:14 -04:00
count . setAttribute ( 'value' , '(' + this . getDescendantTabs ( aTab ) . length + ')' ) ;
2007-10-19 02:40:30 -04:00
}
2007-10-19 22:44:14 -04:00
var parent = this . getParentTab ( aTab ) ;
2007-10-19 02:40:30 -04:00
if ( parent )
this . updateTabsCount ( parent ) ;
} ,
2007-10-19 22:44:14 -04:00
/* move */
2007-10-20 02:12:22 -04:00
2007-10-17 14:36:39 -04:00
moveTabSubTreeTo : function ( aTab , aIndex )
{
2007-10-18 13:11:03 -04:00
if ( ! aTab ) return ;
2007-10-17 14:36:39 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
2007-10-17 19:48:30 -04:00
b . _ _treestyletab _ _isSubTreeMoving = true ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-17 14:36:39 -04:00
b . moveTabTo ( aTab , aIndex ) ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-17 14:36:39 -04:00
2007-10-19 09:05:29 -04:00
b . _ _treestyletab _ _isSubTreeChildrenMoving = true ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-19 22:44:14 -04:00
var tabs = this . getDescendantTabs ( aTab ) ;
2007-10-17 14:36:39 -04:00
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
2007-10-18 11:40:06 -04:00
b . moveTabTo ( tabs [ i ] , aTab . _tPos + i + ( aTab . _tPos < tabs [ i ] . _tPos ? 1 : 0 ) ) ;
2007-10-17 14:36:39 -04:00
}
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-19 09:05:29 -04:00
b . _ _treestyletab _ _isSubTreeChildrenMoving = false ;
2007-10-17 19:48:30 -04:00
b . _ _treestyletab _ _isSubTreeMoving = false ;
2007-10-17 14:36:39 -04:00
} ,
2007-10-18 13:11:03 -04:00
2007-10-19 22:44:14 -04:00
moveTabLevel : function ( aEvent )
2007-10-19 01:27:06 -04:00
{
2007-10-19 22:44:14 -04:00
var b = this . getTabBrowserFromChildren ( aEvent . target ) ;
var parentTab = this . getParentTab ( b . mCurrentTab ) ;
if ( aEvent . keyCode == KeyEvent . DOM _VK _RIGHT ) {
var prevTab = this . getPreviousSiblingTab ( b . mCurrentTab ) ;
if ( ( ! parentTab && prevTab ) ||
( parentTab && b . mCurrentTab != this . getFirstChildTab ( parentTab ) ) ) {
this . attachTabTo ( b . mCurrentTab , prevTab ) ;
b . mCurrentTab . focus ( ) ;
return true ;
}
2007-10-19 01:27:06 -04:00
}
2007-10-19 22:44:14 -04:00
else if ( aEvent . keyCode == KeyEvent . DOM _VK _LEFT && parentTab ) {
var grandParent = this . getParentTab ( parentTab ) ;
if ( grandParent ) {
this . attachTabTo ( b . mCurrentTab , grandParent , { insertBefore : this . getNextSiblingTab ( parentTab ) } ) ;
b . mCurrentTab . focus ( ) ;
return true ;
}
else {
var nextTab = this . getNextSiblingTab ( parentTab ) ;
this . partTab ( b . mCurrentTab ) ;
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = true ;
2007-10-19 22:44:14 -04:00
if ( nextTab ) {
b . moveTabTo ( b . mCurrentTab , nextTab . _tPos - 1 ) ;
}
else {
b . moveTabTo ( b . mCurrentTab , b . mTabContainer . lastChild . _tPos ) ;
}
2007-10-26 15:27:30 -04:00
b . _ _treestyletab _ _internallyTabMoving = false ;
2007-10-19 22:44:14 -04:00
b . mCurrentTab . focus ( ) ;
return true ;
}
2007-10-19 01:27:06 -04:00
}
2007-10-19 22:44:14 -04:00
return false ;
2007-10-19 01:27:06 -04:00
} ,
2007-10-19 22:44:14 -04:00
/* collapse/expand */
2007-10-20 02:12:22 -04:00
2007-10-18 13:11:03 -04:00
collapseExpandTabSubTree : function ( aTab , aCollapse )
{
if ( ! aTab ) return ;
2007-10-20 04:22:42 -04:00
if ( ( aTab . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ) == aCollapse ) return ;
var b = this . getTabBrowserFromChildren ( aTab ) ;
b . _ _treestyletab _ _doingCollapseExpand = true ;
2007-10-18 13:11:03 -04:00
this . setTabValue ( aTab , this . kSUBTREE _COLLAPSED , aCollapse ) ;
2007-10-19 22:44:14 -04:00
var tabs = this . getChildTabs ( aTab ) ;
2007-10-18 13:11:03 -04:00
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
this . collapseExpandTab ( tabs [ i ] , aCollapse ) ;
}
2007-10-20 04:22:42 -04:00
2007-10-20 12:47:08 -04:00
if ( ! aCollapse )
this . scrollToTabSubTree ( aTab ) ;
2007-10-20 04:22:42 -04:00
b . _ _treestyletab _ _doingCollapseExpand = false ;
2007-10-18 13:11:03 -04:00
} ,
collapseExpandTab : function ( aTab , aCollapse )
{
if ( ! aTab ) return ;
this . setTabValue ( aTab , this . kCOLLAPSED , aCollapse ) ;
var b = this . getTabBrowserFromChildren ( aTab ) ;
var p ;
2007-10-19 22:44:14 -04:00
if ( aCollapse && aTab == b . selectedTab && ( p = this . getParentTab ( aTab ) ) ) {
2007-10-18 22:08:15 -04:00
b . selectedTab = p ;
}
2007-10-18 13:11:03 -04:00
var isSubTreeCollapsed = ( aTab . getAttribute ( this . kSUBTREE _COLLAPSED ) == 'true' ) ;
2007-10-19 22:44:14 -04:00
var tabs = this . getChildTabs ( aTab ) ;
2007-10-18 13:11:03 -04:00
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
if ( ! isSubTreeCollapsed )
this . collapseExpandTab ( tabs [ i ] , aCollapse ) ;
}
} ,
2007-10-18 14:20:54 -04:00
collapseExpandTreesIntelligentlyFor : function ( aTab )
{
2007-10-20 04:22:42 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
if ( b . _ _treestyletab _ _doingCollapseExpand ) return ;
2007-10-22 16:31:11 -04:00
var sameParentTab = this . getParentTab ( aTab ) ;
2007-10-18 14:20:54 -04:00
var expandedParentTabs = [
aTab . getAttribute ( this . kID )
] ;
var parentTab = aTab ;
2007-10-19 22:44:14 -04:00
while ( parentTab = this . getParentTab ( parentTab ) )
2007-10-18 14:20:54 -04:00
{
expandedParentTabs . push ( parentTab . getAttribute ( this . kID ) ) ;
}
expandedParentTabs = expandedParentTabs . join ( '|' ) ;
2007-10-18 21:59:43 -04:00
2007-10-18 23:05:36 -04:00
var xpathResult = this . evaluateXPath (
'child::xul:tab[@' + this . kCHILDREN + ' and not(@' + this . kCOLLAPSED + '="true") and not(@' + this . kSUBTREE _COLLAPSED + '="true") and not(contains("' + expandedParentTabs + '", @' + this . kID + '))]' ,
b . mTabContainer
) ;
var collapseTab ;
var dontCollapse ;
for ( var i = 0 , maxi = xpathResult . snapshotLength ; i < maxi ; i ++ )
{
dontCollapse = false ;
collapseTab = xpathResult . snapshotItem ( i ) ;
2007-10-18 21:59:43 -04:00
2007-10-19 22:44:14 -04:00
parentTab = this . getParentTab ( collapseTab ) ;
2007-10-18 23:05:36 -04:00
if ( parentTab ) {
dontCollapse = true ;
2007-10-22 16:31:11 -04:00
if ( parentTab . getAttribute ( this . kSUBTREE _COLLAPSED ) != 'true' ) {
do {
if ( expandedParentTabs . indexOf ( parentTab . getAttribute ( this . kID ) ) < 0 )
continue ;
dontCollapse = false ;
break ;
}
while ( parentTab = this . getParentTab ( parentTab ) ) ;
2007-10-18 23:05:36 -04:00
}
2007-10-18 14:20:54 -04:00
}
2007-10-18 23:05:36 -04:00
if ( ! dontCollapse )
this . collapseExpandTabSubTree ( collapseTab , true ) ;
2007-10-18 14:20:54 -04:00
}
2007-10-18 23:05:36 -04:00
2007-10-18 14:20:54 -04:00
this . collapseExpandTabSubTree ( aTab , false ) ;
} ,
2007-10-18 13:11:03 -04:00
2007-10-20 12:47:08 -04:00
/* scroll */
2007-10-20 15:24:34 -04:00
2007-10-20 12:47:08 -04:00
scrollTo : function ( aTabBrowser , aEndX , aEndY )
{
2007-10-26 07:24:59 -04:00
if ( this . getTreePref ( 'tabbar.scroll.smooth' ) )
2007-10-20 12:47:08 -04:00
this . smoothScrollTo ( aTabBrowser , aEndX , aEndY ) ;
else
this . getTabBrowserFromChildren ( aTabBrowser ) . mTabstrip . scrollBoxObject . scrollTo ( aEndX , aEndY ) ;
} ,
smoothScrollTo : function ( aTabBrowser , aEndX , aEndY )
{
var b = this . getTabBrowserFromChildren ( aTabBrowser ) ;
if ( b . _ _treestyletab _ _smoothScrollTimer ) {
window . clearInterval ( b . _ _treestyletab _ _smoothScrollTimer ) ;
b . _ _treestyletab _ _smoothScrollTimer = null ;
}
var scrollBoxObject = b . mTabContainer . mTabstrip . scrollBoxObject ;
var x = { } , y = { } ;
scrollBoxObject . getPosition ( x , y ) ;
b . _ _treestyletab _ _smoothScrollTimer = window . setInterval (
this . smoothScrollToCallback ,
10 ,
this ,
b ,
x . value ,
y . value ,
aEndX ,
aEndY ,
Date . now ( ) ,
2007-10-26 07:24:59 -04:00
this . getTreePref ( 'tabbar.scroll.timeout' )
2007-10-20 12:47:08 -04:00
) ;
} ,
smoothScrollToCallback : function ( aSelf , aTabBrowser , aStartX , aStartY , aEndX , aEndY , aStartTime , aTimeout )
{
var newX = aStartX + parseInt (
( aEndX - aStartX ) * ( ( Date . now ( ) - aStartTime ) / aTimeout )
) ;
var newY = aStartY + parseInt (
( aEndY - aStartY ) * ( ( Date . now ( ) - aStartTime ) / aTimeout )
) ;
var scrollBoxObject = aTabBrowser . mTabContainer . mTabstrip . scrollBoxObject ;
var x = { } , y = { } ;
scrollBoxObject . getPosition ( x , y ) ;
var w = { } , h = { } ;
scrollBoxObject . getScrolledSize ( w , h ) ;
var maxX = Math . max ( 0 , w . value - scrollBoxObject . width ) ;
var maxY = Math . max ( 0 , h . value - scrollBoxObject . height ) ;
if (
(
aEndX - aStartX > 0 ?
x . value >= Math . min ( aEndX , maxX ) :
x . value <= Math . min ( aEndX , maxX )
) &&
(
aEndY - aStartY > 0 ?
y . value >= Math . min ( aEndY , maxY ) :
y . value <= Math . min ( aEndY , maxY )
)
) {
if ( aTabBrowser . _ _treestyletab _ _smoothScrollTimer ) {
window . clearInterval ( aTabBrowser . _ _treestyletab _ _smoothScrollTimer ) ;
aTabBrowser . _ _treestyletab _ _smoothScrollTimer = null ;
}
return ;
}
scrollBoxObject . scrollTo ( newX , newY ) ;
} ,
2007-10-20 15:24:34 -04:00
2007-10-20 12:47:08 -04:00
scrollToTab : function ( aTab )
{
2007-10-24 15:37:21 -04:00
if ( ! aTab || this . isTabInViewport ( aTab ) ) return ;
2007-10-20 12:47:08 -04:00
var b = this . getTabBrowserFromChildren ( aTab ) ;
var scrollBoxObject = b . mTabContainer . mTabstrip . scrollBoxObject ;
var w = { } , h = { } ;
scrollBoxObject . getScrolledSize ( w , h ) ;
var targetTabBox = aTab . boxObject ;
var baseTabBox = aTab . parentNode . firstChild . boxObject ;
var targetX = ( aTab . boxObject . screenX < scrollBoxObject . screenX ) ?
( targetTabBox . screenX - baseTabBox . screenX ) - ( targetTabBox . width * 0.5 ) :
( targetTabBox . screenX - baseTabBox . screenX ) - scrollBoxObject . width + ( targetTabBox . width * 1.5 ) ;
var targetY = ( aTab . boxObject . screenY < scrollBoxObject . screenY ) ?
( targetTabBox . screenY - baseTabBox . screenY ) - ( targetTabBox . height * 0.5 ) :
( targetTabBox . screenY - baseTabBox . screenY ) - scrollBoxObject . height + ( targetTabBox . height * 1.5 ) ;
this . scrollTo ( b , targetX , targetY ) ;
} ,
scrollToTabSubTree : function ( aTab )
{
var b = this . getTabBrowserFromChildren ( aTab ) ;
var descendant = this . getDescendantTabs ( aTab ) ;
var lastVisible = aTab ;
for ( var i = descendant . length - 1 ; i > - 1 ; i -- )
{
if ( descendant [ i ] . getAttribute ( this . kCOLLAPSED ) == 'true' ) continue ;
lastVisible = descendant [ i ] ;
break ;
}
var containerPosition = b . mStrip . boxObject [ this . positionProp ] ;
var containerSize = b . mStrip . boxObject [ this . sizeProp ] ;
var parentPosition = aTab . boxObject [ this . positionProp ] ;
var lastPosition = lastVisible . boxObject [ this . positionProp ] ;
var tabSize = lastVisible . boxObject [ this . sizeProp ] ;
2007-10-24 15:37:21 -04:00
if ( this . isTabInViewport ( aTab ) && this . isTabInViewport ( lastVisible ) ) {
2007-10-20 12:47:08 -04:00
return ;
}
if ( lastPosition - parentPosition + tabSize > containerSize - tabSize ) { // out of screen
var endPos = parentPosition - b . mTabContainer . firstChild . boxObject [ this . positionProp ] - tabSize * 0.5 ;
var endX = this . isTabVertical ( aTab ) ? 0 : endPos ;
var endY = this . isTabVertical ( aTab ) ? endPos : 0 ;
this . scrollTo ( b , endX , endY ) ;
}
2007-10-24 15:37:21 -04:00
else if ( ! this . isTabInViewport ( aTab ) && this . isTabInViewport ( lastVisible ) ) {
2007-10-20 12:47:08 -04:00
this . scrollToTab ( aTab ) ;
}
2007-10-24 15:37:21 -04:00
else if ( this . isTabInViewport ( aTab ) && ! this . isTabInViewport ( lastVisible ) ) {
2007-10-20 12:47:08 -04:00
this . scrollToTab ( lastVisible ) ;
}
else if ( parentPosition < containerPosition ) {
this . scrollToTab ( aTab ) ;
}
else {
this . scrollToTab ( lastVisible ) ;
}
} ,
2007-10-19 22:44:14 -04:00
removeTabSubTree : function ( aTabOrTabs )
{
var tabs = aTabOrTabs ;
if ( ! ( tabs instanceof Array ) ) {
tabs = [ aTabOrTabs ] ;
}
var descendant = [ ] ;
for ( var i = 0 , maxi = tabs . length ; i < maxi ; i ++ )
{
descendant = descendant . concat ( this . getDescendantTabs ( tabs [ i ] ) ) ;
}
tabs = this . cleanUpTabsArray ( tabs . concat ( descendant ) ) ;
var max = tabs . length ;
if ( ! max ) return ;
var b = this . getTabBrowserFromChildren ( tabs [ 0 ] ) ;
if (
max > 1 &&
! b . warnAboutClosingTabs ( true , max )
)
return ;
for ( var i = tabs . length - 1 ; i > - 1 ; i -- )
{
b . removeTab ( tabs [ i ] ) ;
}
} ,
2007-10-22 05:59:43 -04:00
openSelectionLinks : function ( )
{
var links = this . getSelectionLinks ( ) ;
if ( ! links . length ) return ;
var b = this . browser ;
var targetWindow = document . commandDispatcher . focusedWindow ;
if ( ! targetWindow || targetWindow . top == window )
targetWindow = b . contentWindow ;
var referrer = this . makeURIFromSpec ( targetWindow . location . href ) ;
this . readyToOpenChildTab ( targetWindow , true ) ;
var self = this ;
links . forEach ( function ( aItem , aIndex ) {
var tab = b . addTab ( aItem . uri , referrer ) ;
if ( aIndex == 0 && ! self . getPref ( 'browser.tabs.loadInBackground' ) )
b . selectedTab = tab ;
} ) ;
this . stopToOpenChildTab ( targetWindow ) ;
} ,
getSelectionLinks : function ( )
{
var links = [ ] ;
var targetWindow = document . commandDispatcher . focusedWindow ;
if ( ! targetWindow || targetWindow . top == window )
targetWindow = this . browser . contentWindow ;
var selection = targetWindow . getSelection ( ) ;
if ( ! selection || ! selection . rangeCount )
return links ;
const count = selection . rangeCount ;
var range ,
node ,
link ,
uri ,
nodeRange = targetWindow . document . createRange ( ) ;
for ( var i = 0 ; i < count ; i ++ )
{
range = selection . getRangeAt ( 0 ) ;
node = range . startContainer ;
traceTree :
while ( true )
{
nodeRange . selectNode ( node ) ;
// <20> u<EFBFBD> m<EFBFBD> [<5B> h<EFBFBD> ̏I<CC8F> [<5B> <> <EFBFBD> A<EFBFBD> I<EFBFBD> <49> <EFBFBD> ͈͂̐<CD82> <CC90> [<5B> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ɂ<EFBFBD> <C982> 邩<EFBFBD> ǂ<EFBFBD> <C782> <EFBFBD> <EFBFBD> v<EFBFBD> <76> <EFBFBD> `<60> F<EFBFBD> b<EFBFBD> N<EFBFBD> B
// <20> <> <EFBFBD> ɂ<EFBFBD> <C982> <EFBFBD> <EFBFBD> Ȃ<EFBFBD> <C882> A<CE81> <41> <EFBFBD> ̃m<CC83> [<5B> h<EFBFBD> ͑I<CD91> <49> <EFBFBD> ͈͓<CD88> <CD93> ɂ<EFBFBD> <C982> <EFBFBD> <EFBFBD> ƍ l<C68D> <6C> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> B
if ( nodeRange . compareBoundaryPoints ( Range . START _TO _END , range ) > - 1 ) {
// <20> u<EFBFBD> m<EFBFBD> [<5B> h<EFBFBD> ̐<EFBFBD> <CC90> [<5B> <> <EFBFBD> A<EFBFBD> I<EFBFBD> <49> <EFBFBD> ͈͂̏I<CC8F> [<5B> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ɂ<EFBFBD> <C982> 邩<EFBFBD> ǂ<EFBFBD> <C782> <EFBFBD> <EFBFBD> v<EFBFBD> <76> <EFBFBD> `<60> F<EFBFBD> b<EFBFBD> N<EFBFBD> B
// <20> <> <EFBFBD> ɂ<EFBFBD> <C982> <EFBFBD> <EFBFBD> Ȃ<EFBFBD> <C882> A<CE81> <41> <EFBFBD> ̃m<CC83> [<5B> h<EFBFBD> ͑I<CD91> <49> <EFBFBD> ͈͊O<CD8A> ɂ<EFBFBD> <C982> <EFBFBD> <EFBFBD> ƍ l<C68D> <6C> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> B
if ( nodeRange . compareBoundaryPoints ( Range . END _TO _START , range ) > 0 ) {
// <20> u<EFBFBD> <75> <EFBFBD> <EFBFBD> <EFBFBD> N<EFBFBD> e<EFBFBD> L<EFBFBD> X<EFBFBD> g<EFBFBD> <67> <EFBFBD> <EFBFBD> <EFBFBD> ۂɂ͑I<CD91> <49> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ă<EFBFBD> <C482> Ȃ<EFBFBD> <C882> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> N<EFBFBD> v<EFBFBD> ɂ <C982> <C282> Ă͏ <C482> <CD8F> O<EFBFBD> <4F> <EFBFBD> <EFBFBD>
if (
links . length &&
range . startContainer . nodeType != Node . ELEMENT _NODE &&
range . startOffset == range . startContainer . nodeValue . length &&
links [ 0 ] . node == this . getParentLink ( range . startContainer )
)
links . splice ( 0 , 1 ) ;
if (
links . length &&
range . endContainer . nodeType != Node . ELEMENT _NODE &&
range . endOffset == 0 &&
links [ links . length - 1 ] . node == this . getParentLink ( range . endContainer )
)
links . splice ( links . length - 1 , 1 ) ;
break ;
}
else if ( link = this . getParentLink ( node ) ) {
try {
uri = link . href ;
if ( uri && uri . indexOf ( 'mailto:' ) < 0 )
links . push ( { node : link , uri : uri } ) ;
}
catch ( e ) {
}
}
}
if ( node . hasChildNodes ( ) && ! link ) {
node = node . firstChild ;
}
else {
while ( ! node . nextSibling )
{
node = node . parentNode ;
if ( ! node ) break traceTree ;
}
node = node . nextSibling ;
}
}
}
nodeRange . detach ( ) ;
return links ;
} ,
getParentLink : function ( aNode )
{
var node = aNode ;
while ( ! node . href && node . parentNode )
node = node . parentNode ;
return node . href ? node : null ;
} ,
2007-10-16 13:22:28 -04:00
/* Pref Listener */
2007-10-21 04:16:10 -04:00
2007-10-16 13:22:28 -04:00
domain : 'extensions.treestyletab' ,
observe : function ( aSubject , aTopic , aPrefName )
{
if ( aTopic != 'nsPref:changed' ) return ;
var value = this . getPref ( aPrefName ) ;
switch ( aPrefName )
{
2007-10-20 04:22:42 -04:00
case 'extensions.treestyletab.levelMargin' :
this . levelMargin = value ;
this . ObserverService . notifyObservers ( null , 'TreeStyleTab:levelMarginModified' , value ) ;
2007-10-16 13:22:28 -04:00
break ;
default :
break ;
}
} ,
/* Save/Load Prefs */
2007-10-21 04:16:10 -04:00
2007-10-16 13:22:28 -04:00
get Prefs ( )
{
if ( ! this . _Prefs ) {
this . _Prefs = Components . classes [ '@mozilla.org/preferences;1' ] . getService ( Components . interfaces . nsIPrefBranch ) ;
}
return this . _Prefs ;
} ,
_Prefs : null ,
getPref : function ( aPrefstring )
{
try {
switch ( this . Prefs . getPrefType ( aPrefstring ) )
{
case this . Prefs . PREF _STRING :
return decodeURIComponent ( escape ( this . Prefs . getCharPref ( aPrefstring ) ) ) ;
break ;
case this . Prefs . PREF _INT :
return this . Prefs . getIntPref ( aPrefstring ) ;
break ;
default :
return this . Prefs . getBoolPref ( aPrefstring ) ;
break ;
}
}
catch ( e ) {
}
return null ;
} ,
2007-10-26 07:24:59 -04:00
getTreePref : function ( aPrefstring )
{
return this . getPref ( 'extensions.treestyletab.' + aPrefstring ) ;
} ,
2007-10-16 13:22:28 -04:00
setPref : function ( aPrefstring , aNewValue )
{
var pref = this . Prefs ;
var type ;
try {
type = typeof aNewValue ;
}
catch ( e ) {
type = null ;
}
switch ( type )
{
case 'string' :
pref . setCharPref ( aPrefstring , unescape ( encodeURIComponent ( aNewValue ) ) ) ;
break ;
case 'number' :
pref . setIntPref ( aPrefstring , parseInt ( aNewValue ) ) ;
break ;
default :
pref . setBoolPref ( aPrefstring , aNewValue ) ;
break ;
}
return true ;
} ,
clearPref : function ( aPrefstring )
{
try {
this . Prefs . clearUserPref ( aPrefstring ) ;
}
catch ( e ) {
}
return ;
} ,
addPrefListener : function ( aObserver )
{
var domains = ( 'domains' in aObserver ) ? aObserver . domains : [ aObserver . domain ] ;
try {
var pbi = this . Prefs . QueryInterface ( Components . interfaces . nsIPrefBranchInternal ) ;
for ( var i = 0 ; i < domains . length ; i ++ )
pbi . addObserver ( domains [ i ] , aObserver , false ) ;
}
catch ( e ) {
}
} ,
removePrefListener : function ( aObserver )
{
var domains = ( 'domains' in aObserver ) ? aObserver . domains : [ aObserver . domain ] ;
try {
var pbi = this . Prefs . QueryInterface ( Components . interfaces . nsIPrefBranchInternal ) ;
for ( var i = 0 ; i < domains . length ; i ++ )
pbi . removeObserver ( domains [ i ] , aObserver , false ) ;
}
catch ( e ) {
}
}
} ;
window . addEventListener ( 'load' , TreeStyleTabService , false ) ;
window . addEventListener ( 'unload' , TreeStyleTabService , false ) ;
2007-10-20 04:22:42 -04:00
function TreeStyleTabBrowserObserver ( aTabBrowser )
{
this . mTabBrowser = aTabBrowser ;
TreeStyleTabService . ObserverService . addObserver ( this , 'TreeStyleTab:levelMarginModified' , false ) ;
TreeStyleTabService . addPrefListener ( this ) ;
}
TreeStyleTabBrowserObserver . prototype = {
domain : 'extensions.treestyletab' ,
mTabBrowser : null ,
observe : function ( aSubject , aTopic , aData )
{
switch ( aTopic )
{
case 'TreeStyleTab:levelMarginModified' :
if ( this . mTabBrowser . _ _treestyletab _ _levelMargin > - 1 ) {
TreeStyleTabService . updateAllTabsIndent ( this . mTabBrowser ) ;
}
break ;
case 'nsPref:changed' :
var value = TreeStyleTabService . getPref ( aData ) ;
2007-10-20 06:24:36 -04:00
switch ( aData )
{
2007-10-20 07:29:42 -04:00
case 'extensions.treestyletab.tabbar.position' :
2007-10-24 15:37:21 -04:00
if ( value != 'left' && value != 'right' ) {
2007-10-24 13:54:40 -04:00
var container = this . mTabBrowser . mTabContainer ;
Array . prototype . slice . call ( container . childNodes ) . forEach ( function ( aTab ) {
aTab . removeAttribute ( 'align' ) ;
aTab . maxWidth = 250 ;
aTab . minWidth = container . mTabMinWidth ;
} ) ;
}
2007-10-26 08:56:04 -04:00
case 'extensions.treestyletab.tabbar.multirow' :
2007-10-21 23:08:14 -04:00
case 'extensions.treestyletab.tabbar.invertUI' :
TreeStyleTabService . initTabbar ( this . mTabBrowser ) ;
2007-10-20 08:15:05 -04:00
TreeStyleTabService . updateAllTabsIndent ( this . mTabBrowser ) ;
2007-10-20 06:24:36 -04:00
break ;
2007-10-25 18:59:34 -04:00
case 'extensions.treestyletab.enableSubtreeIndent' :
TreeStyleTabService . updateAllTabsIndent ( this . mTabBrowser ) ;
break ;
2007-10-20 15:00:09 -04:00
case 'extensions.treestyletab.tabbar.style' :
this . mTabBrowser . setAttribute ( TreeStyleTabService . kSTYLE , value ) ;
2007-10-22 08:18:34 -04:00
break ;
case 'extensions.treestyletab.showBorderForFirstTab' :
if ( value )
this . mTabBrowser . setAttribute ( TreeStyleTabService . kFIRSTTAB _BORDER , true ) ;
else
this . mTabBrowser . removeAttribute ( TreeStyleTabService . kFIRSTTAB _BORDER ) ;
break ;
2007-10-20 15:00:09 -04:00
2007-10-23 02:05:44 -04:00
case 'extensions.treestyletab.tabbar.invertScrollbar' :
if ( value &&
2007-10-26 07:24:59 -04:00
TreeStyleTabService . getTreePref ( 'tabbar.position' ) == 'left' )
2007-10-23 02:05:44 -04:00
this . mTabBrowser . setAttribute ( TreeStyleTabService . kSCROLLBAR _INVERTED , true ) ;
else
this . mTabBrowser . removeAttribute ( TreeStyleTabService . kSCROLLBAR _INVERTED ) ;
break ;
2007-10-25 18:59:34 -04:00
case 'extensions.treestyletab.allowSubtreeCollapseExpand' :
if ( value )
this . mTabBrowser . setAttribute ( TreeStyleTabService . kALLOW _COLLAPSE , true ) ;
else
this . mTabBrowser . removeAttribute ( TreeStyleTabService . kALLOW _COLLAPSE ) ;
break ;
2007-10-20 06:24:36 -04:00
default :
break ;
}
2007-10-20 04:22:42 -04:00
break ;
default :
break ;
}
} ,
destroy : function ( )
{
TreeStyleTabService . ObserverService . removeObserver ( this , 'TreeStyleTab:levelMarginModified' ) ;
TreeStyleTabService . removePrefListener ( this ) ;
delete this . mTabBrowser ;
}
} ;
2007-10-20 07:29:42 -04:00