Upgrade to ExtJS 4.0.0 - Released 04/26/2011
[extjs.git] / docs / source / Panel4.html
diff --git a/docs/source/Panel4.html b/docs/source/Panel4.html
new file mode 100644 (file)
index 0000000..1dcd05b
--- /dev/null
@@ -0,0 +1,581 @@
+<!DOCTYPE html><html><head><title>Sencha Documentation Project</title><link rel="stylesheet" href="../reset.css" type="text/css"><link rel="stylesheet" href="../prettify.css" type="text/css"><link rel="stylesheet" href="../prettify_sa.css" type="text/css"><script type="text/javascript" src="../prettify.js"></script></head><body onload="prettyPrint()"><pre class="prettyprint"><pre><span id='Ext-tab.Panel-method-constructor'><span id='Ext-tab.Panel'>/**
+</span></span> * @author Ed Spencer, Tommy Maintz, Brian Moeskau
+ * @class Ext.tab.Panel
+ * @extends Ext.panel.Panel
+
+A basic tab container. TabPanels can be used exactly like a standard {@link Ext.panel.Panel} for layout purposes, but also 
+have special support for containing child Components (`{@link Ext.container.Container#items items}`) that are managed 
+using a {@link Ext.layout.container.Card CardLayout layout manager}, and displayed as separate tabs.
+
+__Note:__
+
+By default, a tab's close tool _destroys_ the child tab Component and all its descendants. This makes the child tab 
+Component, and all its descendants __unusable__. To enable re-use of a tab, configure the TabPanel with `{@link #autoDestroy autoDestroy: false}`.
+
+__TabPanel's layout:__
+
+TabPanels use a Dock layout to position the {@link Ext.tab.Bar TabBar} at the top of the widget. Panels added to the TabPanel will have their 
+header hidden by default because the Tab will automatically take the Panel's configured title and icon.
+
+TabPanels use their {@link Ext.panel.Panel#header header} or {@link Ext.panel.Panel#footer footer} element (depending on the {@link #tabPosition} 
+configuration) to accommodate the tab selector buttons. This means that a TabPanel will not display any configured title, and will not display any 
+configured header {@link Ext.panel.Panel#tools tools}.
+
+To display a header, embed the TabPanel in a {@link Ext.panel.Panel Panel} which uses `{@link Ext.container.Container#layout layout:'fit'}`.
+
+__Examples:__
+
+Here is a basic TabPanel rendered to the body. This also shows the useful configuration {@link #activeTab}, which allows you to set the active tab on render. 
+If you do not set an {@link #activeTab}, no tabs will be active by default.
+{@img Ext.tab.Panel/Ext.tab.Panel1.png TabPanel component}
+Example usage:
+
+    Ext.create('Ext.tab.Panel', {
+        width: 300,
+        height: 200,
+        activeTab: 0,
+        items: [
+            {
+                title: 'Tab 1',
+                bodyPadding: 10,
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()
+    }); 
+    
+It is easy to control the visibility of items in the tab bar. Specify hidden: true to have the
+tab button hidden initially. Items can be subsequently hidden and show by accessing the
+tab property on the child item.
+
+Example usage:
+    
+    var tabs = Ext.create('Ext.tab.Panel', {
+        width: 400,
+        height: 400,
+        renderTo: document.body,
+        items: [{
+            title: 'Home',
+            html: 'Home',
+            itemId: 'home'
+        }, {
+            title: 'Users',
+            html: 'Users',
+            itemId: 'users',
+            hidden: true
+        }, {
+            title: 'Tickets',
+            html: 'Tickets',
+            itemId: 'tickets'
+        }]    
+    });
+    
+    setTimeout(function(){
+        tabs.child('#home').tab.hide();
+        var users = tabs.child('#users');
+        users.tab.show();
+        tabs.setActiveTab(users);
+    }, 1000);
+
+You can remove the background of the TabBar by setting the {@link #plain} property to `false`.
+
+Example usage:
+
+    Ext.create('Ext.tab.Panel', {
+        width: 300,
+        height: 200,
+        activeTab: 0,
+        plain: true,
+        items: [
+            {
+                title: 'Tab 1',
+                bodyPadding: 10,
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()
+    }); 
+
+Another useful configuration of TabPanel is {@link #tabPosition}. This allows you to change the position where the tabs are displayed. The available 
+options for this are `'top'` (default) and `'bottom'`.
+{@img Ext.tab.Panel/Ext.tab.Panel2.png TabPanel component}
+Example usage:
+
+    Ext.create('Ext.tab.Panel', {
+        width: 300,
+        height: 200,
+        activeTab: 0,
+        bodyPadding: 10,        
+        tabPosition: 'bottom',
+        items: [
+            {
+                title: 'Tab 1',
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()
+    }); 
+
+The {@link #setActiveTab} is a very useful method in TabPanel which will allow you to change the current active tab. You can either give it an index or 
+an instance of a tab.
+
+Example usage:
+
+    var tabs = Ext.create('Ext.tab.Panel', {
+        items: [
+            {
+                id   : 'my-tab',
+                title: 'Tab 1',
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()
+    });
+    
+    var tab = Ext.getCmp('my-tab');
+    
+    Ext.create('Ext.button.Button', {
+        renderTo: Ext.getBody(),
+        text    : 'Select the first tab',
+        scope   : this,
+        handler : function() {
+            tabs.setActiveTab(tab);
+        }
+    });
+    
+    Ext.create('Ext.button.Button', {
+        text    : 'Select the second tab',
+        scope   : this,
+        handler : function() {
+            tabs.setActiveTab(1);
+        },
+        renderTo : Ext.getBody()        
+    });
+
+The {@link #getActiveTab} is a another useful method in TabPanel which will return the current active tab.
+
+Example usage:
+
+    var tabs = Ext.create('Ext.tab.Panel', {
+        items: [
+            {
+                title: 'Tab 1',
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()        
+    });
+    
+    Ext.create('Ext.button.Button', {
+        text    : 'Get active tab',
+        scope   : this,
+        handler : function() {
+            var tab = tabs.getActiveTab();
+            alert('Current tab: ' + tab.title);
+        },
+        renderTo : Ext.getBody()        
+    });
+
+Adding a new tab is very simple with a TabPanel. You simple call the {@link #add} method with an config object for a panel.
+
+Example usage:
+
+    var tabs = Ext.Create('Ext.tab.Panel', {
+        items: [
+            {
+                title: 'Tab 1',
+                html : 'A simple tab'
+            },
+            {
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()        
+    });
+    
+    Ext.create('Ext.button.Button', {
+        text    : 'New tab',
+        scope   : this,
+        handler : function() {
+            var tab = tabs.add({
+                title: 'Tab ' + (tabs.items.length + 1), //we use the tabs.items property to get the length of current items/tabs
+                html : 'Another one'
+            });
+            
+            tabs.setActiveTab(tab);
+        },
+        renderTo : Ext.getBody()
+    });
+
+Additionally, removing a tab is very also simple with a TabPanel. You simple call the {@link #remove} method with an config object for a panel.
+
+Example usage:
+
+    var tabs = Ext.Create('Ext.tab.Panel', {        
+        items: [
+            {
+                title: 'Tab 1',
+                html : 'A simple tab'
+            },
+            {
+                id   : 'remove-this-tab',
+                title: 'Tab 2',
+                html : 'Another one'
+            }
+        ],
+        renderTo : Ext.getBody()
+    });
+    
+    Ext.Create('Ext.button.Button', {
+        text    : 'Remove tab',
+        scope   : this,
+        handler : function() {
+            var tab = Ext.getCmp('remove-this-tab');
+            tabs.remove(tab);
+        },
+        renderTo : Ext.getBody()
+    });
+
+ * @extends Ext.Panel
+ * @constructor
+ * @param {Object} config The configuration options
+ * @xtype tabpanel
+ * @markdown
+ */
+Ext.define('Ext.tab.Panel', {
+    extend: 'Ext.panel.Panel',
+    alias: 'widget.tabpanel',
+    alternateClassName: ['Ext.TabPanel'],
+
+    requires: ['Ext.layout.container.Card', 'Ext.tab.Bar'],
+
+<span id='Ext-tab.Panel-cfg-tabPosition'>    /**
+</span>     * @cfg {String} tabPosition The position where the tab strip should be rendered (defaults to &lt;code&gt;'top'&lt;/code&gt;).
+     * In 4.0, The only other supported value is &lt;code&gt;'bottom'&lt;/code&gt;.
+     */
+    tabPosition : 'top',
+    
+<span id='Ext-tab.Panel-cfg-tabBar'>    /**
+</span>     * @cfg {Object} tabBar Optional configuration object for the internal {@link Ext.tab.Bar}. If present, this is 
+     * passed straight through to the TabBar's constructor
+     */
+
+<span id='Ext-tab.Panel-cfg-layout'>    /**
+</span>     * @cfg {Object} layout Optional configuration object for the internal {@link Ext.layout.container.Card card layout}.
+     * If present, this is passed straight through to the layout's constructor
+     */
+
+<span id='Ext-tab.Panel-cfg-removePanelHeader'>    /**
+</span>     * @cfg {Boolean} removePanelHeader True to instruct each Panel added to the TabContainer to not render its header 
+     * element. This is to ensure that the title of the panel does not appear twice. Defaults to true.
+     */
+    removePanelHeader: true,
+
+<span id='Ext-tab.Panel-cfg-Boolean'>    /**
+</span>     * @cfg Boolean plain
+     * True to not show the full background on the TabBar
+     */
+    plain: false,
+
+<span id='Ext-tab.Panel-cfg-itemCls'>    /**
+</span>     * @cfg {String} itemCls The class added to each child item of this TabPanel. Defaults to 'x-tabpanel-child'.
+     */
+    itemCls: 'x-tabpanel-child',
+
+<span id='Ext-tab.Panel-cfg-minTabWidth'>    /**
+</span>     * @cfg {Number} minTabWidth The minimum width for a tab in the {@link #tabBar}. Defaults to &lt;code&gt;30&lt;/code&gt;.
+     */
+
+<span id='Ext-tab.Panel-cfg-deferredRender'>    /**
+</span>     * @cfg {Boolean} deferredRender
+     * &lt;p&gt;&lt;tt&gt;true&lt;/tt&gt; by default to defer the rendering of child &lt;tt&gt;{@link Ext.container.Container#items items}&lt;/tt&gt;
+     * to the browsers DOM until a tab is activated. &lt;tt&gt;false&lt;/tt&gt; will render all contained
+     * &lt;tt&gt;{@link Ext.container.Container#items items}&lt;/tt&gt; as soon as the {@link Ext.layout.container.Card layout}
+     * is rendered. If there is a significant amount of content or a lot of heavy controls being
+     * rendered into panels that are not displayed by default, setting this to &lt;tt&gt;true&lt;/tt&gt; might
+     * improve performance.&lt;/p&gt;
+     * &lt;br&gt;&lt;p&gt;The &lt;tt&gt;deferredRender&lt;/tt&gt; property is internally passed to the layout manager for
+     * TabPanels ({@link Ext.layout.container.Card}) as its {@link Ext.layout.container.Card#deferredRender}
+     * configuration value.&lt;/p&gt;
+     * &lt;br&gt;&lt;p&gt;&lt;b&gt;Note&lt;/b&gt;: leaving &lt;tt&gt;deferredRender&lt;/tt&gt; as &lt;tt&gt;true&lt;/tt&gt; means that the content
+     * within an unactivated tab will not be available&lt;/p&gt;
+     */
+    deferredRender : true,
+
+    //inherit docs
+    initComponent: function() {
+        var me = this,
+            dockedItems = me.dockedItems || [],
+            activeTab = me.activeTab || 0;
+
+        me.layout = Ext.create('Ext.layout.container.Card', Ext.apply({
+            owner: me,
+            deferredRender: me.deferredRender,
+            itemCls: me.itemCls
+        }, me.layout));
+
+<span id='Ext-tab.Panel-property-tabBar'>        /**
+</span>         * @property tabBar
+         * @type Ext.TabBar
+         * Internal reference to the docked TabBar
+         */
+        me.tabBar = Ext.create('Ext.tab.Bar', Ext.apply({}, me.tabBar, {
+            dock: me.tabPosition,
+            plain: me.plain,
+            border: me.border,
+            cardLayout: me.layout,
+            tabPanel: me
+        }));
+
+        if (dockedItems &amp;&amp; !Ext.isArray(dockedItems)) {
+            dockedItems = [dockedItems];
+        }
+
+        dockedItems.push(me.tabBar);
+        me.dockedItems = dockedItems;
+
+        me.addEvents(
+<span id='Ext-tab.Panel-event-beforetabchange'>            /**
+</span>             * @event beforetabchange
+             * Fires before a tab change (activated by {@link #setActiveTab}). Return false in any listener to cancel
+             * the tabchange
+             * @param {Ext.tab.Panel} tabPanel The TabPanel
+             * @param {Ext.Component} newCard The card that is about to be activated
+             * @param {Ext.Component} oldCard The card that is currently active
+             */
+            'beforetabchange',
+
+<span id='Ext-tab.Panel-event-tabchange'>            /**
+</span>             * @event tabchange
+             * Fires when a new tab has been activated (activated by {@link #setActiveTab}).
+             * @param {Ext.tab.Panel} tabPanel The TabPanel
+             * @param {Ext.Component} newCard The newly activated item
+             * @param {Ext.Component} oldCard The previously active item
+             */
+            'tabchange'
+        );
+        me.callParent(arguments);
+
+        //set the active tab
+        me.setActiveTab(activeTab);
+        //set the active tab after initial layout
+        me.on('afterlayout', me.afterInitialLayout, me, {single: true});
+    },
+
+<span id='Ext-tab.Panel-method-afterInitialLayout'>    /**
+</span>     * @private
+     * We have to wait until after the initial layout to visually activate the activeTab (if set).
+     * The active tab has different margins than normal tabs, so if the initial layout happens with
+     * a tab active, its layout will be offset improperly due to the active margin style. Waiting
+     * until after the initial layout avoids this issue.
+     */
+    afterInitialLayout: function() {
+        var me = this,
+            card = me.getComponent(me.activeTab);
+            
+        if (card) {
+            me.layout.setActiveItem(card);
+        }
+    },
+
+<span id='Ext-tab.Panel-method-setActiveTab'>    /**
+</span>     * Makes the given card active (makes it the visible card in the TabPanel's CardLayout and highlights the Tab)
+     * @param {Ext.Component} card The card to make active
+     */
+    setActiveTab: function(card) {
+        var me = this,
+            previous;
+
+        card = me.getComponent(card);
+        if (card) {
+            previous = me.getActiveTab();
+            
+            if (previous &amp;&amp; previous !== card &amp;&amp; me.fireEvent('beforetabchange', me, card, previous) === false) {
+                return false;
+            }
+            
+            me.tabBar.setActiveTab(card.tab);
+            me.activeTab = card;
+            if (me.rendered) {
+                me.layout.setActiveItem(card);
+            }
+            
+            if (previous &amp;&amp; previous !== card) {
+                me.fireEvent('tabchange', me, card, previous);
+            }
+        }
+    },
+
+<span id='Ext-tab.Panel-method-getActiveTab'>    /**
+</span>     * Returns the item that is currently active inside this TabPanel. Note that before the TabPanel first activates a
+     * child component this will return whatever was configured in the {@link #activeTab} config option 
+     * @return {Ext.Component/Integer} The currently active item
+     */
+    getActiveTab: function() {
+        return this.activeTab;
+    },
+
+<span id='Ext-tab.Panel-method-getTabBar'>    /**
+</span>     * Returns the {@link Ext.tab.Bar} currently used in this TabPanel
+     * @return {Ext.TabBar} The TabBar
+     */
+    getTabBar: function() {
+        return this.tabBar;
+    },
+
+<span id='Ext-tab.Panel-method-onAdd'>    /**
+</span>     * @ignore
+     * Makes sure we have a Tab for each item added to the TabPanel
+     */
+    onAdd: function(item, index) {
+        var me = this;
+
+        item.tab = me.tabBar.insert(index, {
+            xtype: 'tab',
+            card: item,
+            disabled: item.disabled,
+            closable: item.closable,
+            hidden: item.hidden,
+            tabBar: me.tabBar
+        });
+        
+        item.on({
+            scope : me,
+            enable: me.onItemEnable,
+            disable: me.onItemDisable,
+            beforeshow: me.onItemBeforeShow,
+            iconchange: me.onItemIconChange,
+            titlechange: me.onItemTitleChange
+        });
+
+        if (item.isPanel) {
+            if (me.removePanelHeader) {
+                item.preventHeader = true;
+                if (item.rendered) {
+                    item.updateHeader();
+                }
+            }
+            if (item.isPanel &amp;&amp; me.border) {
+                item.setBorder(false);
+            }
+        }
+
+        // ensure that there is at least one active tab
+        if (this.rendered &amp;&amp; me.items.getCount() === 1) {
+            me.setActiveTab(0);
+        }
+    },
+    
+<span id='Ext-tab.Panel-method-onItemEnable'>    /**
+</span>     * @private
+     * Enable corresponding tab when item is enabled.
+     */
+    onItemEnable: function(item){
+        item.tab.enable();
+    },
+
+<span id='Ext-tab.Panel-method-onItemDisable'>    /**
+</span>     * @private
+     * Disable corresponding tab when item is enabled.
+     */    
+    onItemDisable: function(item){
+        item.tab.disable();
+    },
+    
+<span id='Ext-tab.Panel-method-onItemBeforeShow'>    /**
+</span>     * @private
+     * Sets activeTab before item is shown.
+     */
+    onItemBeforeShow: function(item) {
+        if (item !== this.activeTab) {
+            this.setActiveTab(item);
+            return false;
+        }    
+    },
+    
+<span id='Ext-tab.Panel-method-onItemIconChange'>    /**
+</span>     * @private
+     * Update the tab iconCls when panel iconCls has been set or changed.
+     */
+    onItemIconChange: function(item, newIconCls) {
+        item.tab.setIconCls(newIconCls);
+        this.getTabBar().doLayout();
+    },
+    
+<span id='Ext-tab.Panel-method-onItemTitleChange'>    /**
+</span>     * @private
+     * Update the tab title when panel title has been set or changed.
+     */
+    onItemTitleChange: function(item, newTitle) {
+        item.tab.setText(newTitle);
+        this.getTabBar().doLayout();
+    },
+
+
+<span id='Ext-tab.Panel-method-doRemove'>    /**
+</span>     * @ignore
+     * If we're removing the currently active tab, activate the nearest one. The item is removed when we call super,
+     * so we can do preprocessing before then to find the card's index
+     */
+    doRemove: function(item, autoDestroy) {
+        var me = this,
+            items = me.items,
+<span id='Ext-tab.Panel-property-hasItemsLeft'>            /**
+</span>             * At this point the item hasn't been removed from the items collection.
+             * As such, if we want to check if there are no more tabs left, we have to
+             * check for one, as opposed to 0.
+             */
+            hasItemsLeft = items.getCount() &gt; 1;
+
+        if (me.destroying || !hasItemsLeft) {
+            me.activeTab = null;
+        } else if (item === me.activeTab) {
+             me.setActiveTab(item.next() || items.getAt(0)); 
+        }
+        me.callParent(arguments);
+
+        // Remove the two references
+        delete item.tab.card;
+        delete item.tab;
+    },
+
+<span id='Ext-tab.Panel-method-onRemove'>    /**
+</span>     * @ignore
+     * Makes sure we remove the corresponding Tab when an item is removed
+     */
+    onRemove: function(item, autoDestroy) {
+        var me = this;
+        
+        item.un({
+            scope : me,
+            enable: me.onItemEnable,
+            disable: me.onItemDisable,
+            beforeshow: me.onItemBeforeShow
+        });
+        if (!me.destroying &amp;&amp; item.tab.ownerCt == me.tabBar) {
+            me.tabBar.remove(item.tab);
+        }
+    }
+});
+</pre></pre></body></html>
\ No newline at end of file