3 This file is part of Ext JS 4
5 Copyright (c) 2011 Sencha Inc
7 Contact: http://www.sencha.com/contact
9 GNU General Public License Usage
10 This file may be used under the terms of the GNU General Public License version 3.0 as published by the Free Software Foundation and appearing in the file LICENSE included in the packaging of this file. Please review the following information to ensure the GNU General Public License version 3.0 requirements will be met: http://www.gnu.org/copyleft/gpl.html.
12 If you are unsure which license is appropriate for your use, please contact the sales department at http://www.sencha.com/contact.
16 * @class Ext.Component
17 * @extends Ext.AbstractComponent
18 * <p>Base class for all Ext components. All subclasses of Component may participate in the automated
19 * Ext component lifecycle of creation, rendering and destruction which is provided by the {@link Ext.container.Container Container} class.
20 * Components may be added to a Container through the {@link Ext.container.Container#items items} config option at the time the Container is created,
21 * or they may be added dynamically via the {@link Ext.container.Container#add add} method.</p>
22 * <p>The Component base class has built-in support for basic hide/show and enable/disable and size control behavior.</p>
23 * <p>All Components are registered with the {@link Ext.ComponentManager} on construction so that they can be referenced at any time via
24 * {@link Ext#getCmp Ext.getCmp}, passing the {@link #id}.</p>
25 * <p>All user-developed visual widgets that are required to participate in automated lifecycle and size management should subclass Component.</p>
26 * <p>See the <a href="http://sencha.com/learn/Tutorial:Creating_new_UI_controls">Creating new UI controls</a> tutorial for details on how
27 * and to either extend or augment ExtJs base classes to create custom Components.</p>
28 * <p>Every component has a specific xtype, which is its Ext-specific type name, along with methods for checking the
29 * xtype like {@link #getXType} and {@link #isXType}. This is the list of all valid xtypes:</p>
32 ------------- ------------------
33 button {@link Ext.button.Button}
34 buttongroup {@link Ext.container.ButtonGroup}
35 colorpalette {@link Ext.picker.Color}
36 component {@link Ext.Component}
37 container {@link Ext.container.Container}
38 cycle {@link Ext.button.Cycle}
39 dataview {@link Ext.view.View}
40 datepicker {@link Ext.picker.Date}
41 editor {@link Ext.Editor}
42 editorgrid {@link Ext.grid.plugin.Editing}
43 grid {@link Ext.grid.Panel}
44 multislider {@link Ext.slider.Multi}
45 panel {@link Ext.panel.Panel}
46 progress {@link Ext.ProgressBar}
47 slider {@link Ext.slider.Single}
48 spacer {@link Ext.toolbar.Spacer}
49 splitbutton {@link Ext.button.Split}
50 tabpanel {@link Ext.tab.Panel}
51 treepanel {@link Ext.tree.Panel}
52 viewport {@link Ext.container.Viewport}
53 window {@link Ext.window.Window}
56 ---------------------------------------
57 paging {@link Ext.toolbar.Paging}
58 toolbar {@link Ext.toolbar.Toolbar}
59 tbfill {@link Ext.toolbar.Fill}
60 tbitem {@link Ext.toolbar.Item}
61 tbseparator {@link Ext.toolbar.Separator}
62 tbspacer {@link Ext.toolbar.Spacer}
63 tbtext {@link Ext.toolbar.TextItem}
66 ---------------------------------------
67 menu {@link Ext.menu.Menu}
68 menucheckitem {@link Ext.menu.CheckItem}
69 menuitem {@link Ext.menu.Item}
70 menuseparator {@link Ext.menu.Separator}
71 menutextitem {@link Ext.menu.Item}
74 ---------------------------------------
75 form {@link Ext.form.Panel}
76 checkbox {@link Ext.form.field.Checkbox}
77 combo {@link Ext.form.field.ComboBox}
78 datefield {@link Ext.form.field.Date}
79 displayfield {@link Ext.form.field.Display}
80 field {@link Ext.form.field.Base}
81 fieldset {@link Ext.form.FieldSet}
82 hidden {@link Ext.form.field.Hidden}
83 htmleditor {@link Ext.form.field.HtmlEditor}
84 label {@link Ext.form.Label}
85 numberfield {@link Ext.form.field.Number}
86 radio {@link Ext.form.field.Radio}
87 radiogroup {@link Ext.form.RadioGroup}
88 textarea {@link Ext.form.field.TextArea}
89 textfield {@link Ext.form.field.Text}
90 timefield {@link Ext.form.field.Time}
91 trigger {@link Ext.form.field.Trigger}
94 ---------------------------------------
95 chart {@link Ext.chart.Chart}
96 barchart {@link Ext.chart.series.Bar}
97 columnchart {@link Ext.chart.series.Column}
98 linechart {@link Ext.chart.series.Line}
99 piechart {@link Ext.chart.series.Pie}
102 * It should not usually be necessary to instantiate a Component because there are provided subclasses which implement specialized Component
103 * use cases which over most application needs. However it is possible to instantiate a base Component, and it will be renderable,
104 * or will particpate in layouts as the child item of a Container:
105 {@img Ext.Component/Ext.Component.png Ext.Component component}
107 Ext.create('Ext.Component', {
108 html: 'Hello world!',
114 backgroundColor:'#000000'
116 renderTo: Ext.getBody()
120 *<p>The Component above creates its encapsulating <code>div</code> upon render, and use the configured HTML as content. More complex
121 * internal structure may be created using the {@link #renderTpl} configuration, although to display database-derived mass
122 * data, it is recommended that an ExtJS data-backed Component such as a {@link Ext.view.View View}, or
123 * {@link Ext.grid.Panel GridPanel}, or {@link Ext.tree.Panel TreePanel} be used.</p>
125 * Creates new Component.
126 * @param {Ext.core.Element/String/Object} config The configuration options may be specified as either:
127 * <div class="mdetail-params"><ul>
128 * <li><b>an element</b> :
129 * <p class="sub-desc">it is set as the internal element and its id used as the component id</p></li>
130 * <li><b>a string</b> :
131 * <p class="sub-desc">it is assumed to be the id of an existing element and is used as the component id</p></li>
132 * <li><b>anything else</b> :
133 * <p class="sub-desc">it is assumed to be a standard config object and is applied to the component</p></li>
137 Ext.define('Ext.Component', {
139 /* Begin Definitions */
141 alias: ['widget.component', 'widget.box'],
143 extend: 'Ext.AbstractComponent',
146 'Ext.util.DelayedTask'
151 'Ext.resizer.Resizer',
152 'Ext.util.ComponentDragger'
156 floating: 'Ext.util.Floating'
160 // Collapse/expand directions
161 DIRECTION_TOP: 'top',
162 DIRECTION_RIGHT: 'right',
163 DIRECTION_BOTTOM: 'bottom',
164 DIRECTION_LEFT: 'left',
166 VERTICAL_DIRECTION: /^(?:top|bottom)$/
169 /* End Definitions */
172 * @cfg {Mixed} resizable
173 * <p>Specify as <code>true</code> to apply a {@link Ext.resizer.Resizer Resizer} to this Component
174 * after rendering.</p>
175 * <p>May also be specified as a config object to be passed to the constructor of {@link Ext.resizer.Resizer Resizer}
176 * to override any defaults. By default the Component passes its minimum and maximum size, and uses
177 * <code>{@link Ext.resizer.Resizer#dynamic}: false</code></p>
181 * @cfg {String} resizeHandles
182 * A valid {@link Ext.resizer.Resizer} handles config string (defaults to 'all'). Only applies when resizable = true.
184 resizeHandles: 'all',
187 * @cfg {Boolean} autoScroll
188 * <code>true</code> to use overflow:'auto' on the components layout element and show scroll bars automatically when
189 * necessary, <code>false</code> to clip any overflowing content (defaults to <code>false</code>).
193 * @cfg {Boolean} floating
194 * <p>Specify as true to float the Component outside of the document flow using CSS absolute positioning.</p>
195 * <p>Components such as {@link Ext.window.Window Window}s and {@link Ext.menu.Menu Menu}s are floating
197 * <p>Floating Components that are programatically {@link Ext.Component#render rendered} will register themselves with the global
198 * {@link Ext.WindowManager ZIndexManager}</p>
199 * <h3 class="pa">Floating Components as child items of a Container</h3>
200 * <p>A floating Component may be used as a child item of a Container. This just allows the floating Component to seek a ZIndexManager by
201 * examining the ownerCt chain.</p>
202 * <p>When configured as floating, Components acquire, at render time, a {@link Ext.ZIndexManager ZIndexManager} which manages a stack
203 * of related floating Components. The ZIndexManager brings a single floating Component to the top of its stack when
204 * the Component's {@link #toFront} method is called.</p>
205 * <p>The ZIndexManager is found by traversing up the {@link #ownerCt} chain to find an ancestor which itself is floating. This is so that
206 * descendant floating Components of floating <i>Containers</i> (Such as a ComboBox dropdown within a Window) can have its zIndex managed relative
207 * to any siblings, but always <b>above</b> that floating ancestor Container.</p>
208 * <p>If no floating ancestor is found, a floating Component registers itself with the default {@link Ext.WindowManager ZIndexManager}.</p>
209 * <p>Floating components <i>do not participate in the Container's layout</i>. Because of this, they are not rendered until you explicitly
210 * {@link #show} them.</p>
211 * <p>After rendering, the ownerCt reference is deleted, and the {@link #floatParent} property is set to the found floating ancestor Container.
212 * If no floating ancestor Container was found the {@link #floatParent} property will not be set.</p>
217 * @cfg {Boolean} toFrontOnShow
218 * <p>True to automatically call {@link #toFront} when the {@link #show} method is called
219 * on an already visible, floating component (default is <code>true</code>).</p>
224 * <p>Optional. Only present for {@link #floating} Components after they have been rendered.</p>
225 * <p>A reference to the ZIndexManager which is managing this Component's z-index.</p>
226 * <p>The {@link Ext.ZIndexManager ZIndexManager} maintains a stack of floating Component z-indices, and also provides a single modal
227 * mask which is insert just beneath the topmost visible modal floating Component.</p>
228 * <p>Floating Components may be {@link #toFront brought to the front} or {@link #toBack sent to the back} of the z-index stack.</p>
229 * <p>This defaults to the global {@link Ext.WindowManager ZIndexManager} for floating Components that are programatically
230 * {@link Ext.Component#render rendered}.</p>
231 * <p>For {@link #floating} Components which are added to a Container, the ZIndexManager is acquired from the first ancestor Container found
232 * which is floating, or if not found the global {@link Ext.WindowManager ZIndexManager} is used.</p>
233 * <p>See {@link #floating} and {@link #floatParent}</p>
234 * @property zIndexManager
235 * @type Ext.ZIndexManager
239 * <p>Optional. Only present for {@link #floating} Components which were inserted as descendant items of floating Containers.</p>
240 * <p>Floating Components that are programatically {@link Ext.Component#render rendered} will not have a <code>floatParent</code> property.</p>
241 * <p>For {@link #floating} Components which are child items of a Container, the floatParent will be the floating ancestor Container which is
242 * responsible for the base z-index value of all its floating descendants. It provides a {@link Ext.ZIndexManager ZIndexManager} which provides
243 * z-indexing services for all its descendant floating Components.</p>
244 * <p>For example, the dropdown {@link Ext.view.BoundList BoundList} of a ComboBox which is in a Window will have the Window as its
245 * <code>floatParent</code></p>
246 * <p>See {@link #floating} and {@link #zIndexManager}</p>
247 * @property floatParent
248 * @type Ext.Container
252 * @cfg {Mixed} draggable
253 * <p>Specify as true to make a {@link #floating} Component draggable using the Component's encapsulating element as the drag handle.</p>
254 * <p>This may also be specified as a config object for the {@link Ext.util.ComponentDragger ComponentDragger} which is instantiated to perform dragging.</p>
255 * <p>For example to create a Component which may only be dragged around using a certain internal element as the drag handle,
256 * use the delegate option:</p>
262 backgroundColor: '#fff',
263 border: '1px solid black'
265 html: '<h1 style="cursor:move">The title</h1><p>The content</p>',
274 * @cfg {Boolean} maintainFlex
275 * <p><b>Only valid when a sibling element of a {@link Ext.resizer.Splitter Splitter} within a {@link Ext.layout.container.VBox VBox} or
276 * {@link Ext.layout.container.HBox HBox} layout.</b></p>
277 * <p>Specifies that if an immediate sibling Splitter is moved, the Component on the <i>other</i> side is resized, and this
278 * Component maintains its configured {@link Ext.layout.container.Box#flex flex} value.</p>
285 ariaRole: 'presentation',
290 monPropRe: /^(?:scope|delay|buffer|single|stopEvent|preventDefault|stopPropagation|normalized|args|delegate)$/,
292 //renderTpl: new Ext.XTemplate(
293 // '<div id="{id}" class="{baseCls} {cls} {cmpCls}<tpl if="typeof ui !== \'undefined\'"> {uiBase}-{ui}</tpl>"<tpl if="typeof style !== \'undefined\'"> style="{style}"</tpl>></div>', {
295 // disableFormats: true
298 constructor: function(config) {
299 config = config || {};
300 if (config.initialConfig) {
302 // Being initialized from an Ext.Action instance...
303 if (config.isAction) {
304 this.baseAction = config;
306 config = config.initialConfig;
307 // component cloning / action set up
309 else if (config.tagName || config.dom || Ext.isString(config)) {
313 id: config.id || config
317 this.callParent([config]);
319 // If we were configured from an instance of Ext.Action, (or configured with a baseAction option),
320 // register this Component as one of its items
321 if (this.baseAction){
322 this.baseAction.addComponent(this);
326 initComponent: function() {
333 me.enableBubble(me.bubbleEvents);
338 afterRender: function() {
340 resizable = me.resizable;
343 me.makeFloating(me.floating);
345 me.el.setVisibilityMode(Ext.core.Element[me.hideMode.toUpperCase()]);
348 if (Ext.isDefined(me.autoScroll)) {
349 me.setAutoScroll(me.autoScroll);
353 if (!(me.x && me.y) && (me.pageX || me.pageY)) {
354 me.setPagePosition(me.pageX, me.pageY);
358 me.initResizable(resizable);
368 initAria: function() {
369 var actionEl = this.getActionEl(),
370 role = this.ariaRole;
372 actionEl.dom.setAttribute('role', role);
377 * Sets the overflow on the content element of the component.
378 * @param {Boolean} scroll True to allow the Component to auto scroll.
379 * @return {Ext.Component} this
381 setAutoScroll : function(scroll){
386 targetEl = me.getTargetEl();
387 targetEl.setStyle('overflow', scroll ? 'auto' : '');
388 if (scroll && (Ext.isIE6 || Ext.isIE7)) {
389 // The scrollable container element must be non-statically positioned or IE6/7 will make
390 // positioned children stay in place rather than scrolling with the rest of the content
394 me.autoScroll = scroll;
399 makeFloating : function(cfg){
400 this.mixins.floating.constructor.call(this, cfg);
403 initResizable: function(resizable) {
404 resizable = Ext.apply({
407 constrainTo: this.constrainTo,
408 handles: this.resizeHandles
410 resizable.target = this;
411 this.resizer = Ext.create('Ext.resizer.Resizer', resizable);
414 getDragEl: function() {
418 initDraggable: function() {
420 ddConfig = Ext.applyIf({
421 el: this.getDragEl(),
422 constrainTo: me.constrainTo || (me.floatParent ? me.floatParent.getTargetEl() : me.el.dom.parentNode)
425 // Add extra configs if Component is specified to be constrained
426 if (me.constrain || me.constrainDelegate) {
427 ddConfig.constrain = me.constrain;
428 ddConfig.constrainDelegate = me.constrainDelegate;
431 this.dd = Ext.create('Ext.util.ComponentDragger', this, ddConfig);
435 * Sets the left and top of the component. To set the page XY position instead, use {@link #setPagePosition}.
436 * This method fires the {@link #move} event.
437 * @param {Number} left The new left
438 * @param {Number} top The new top
439 * @param {Mixed} animate If true, the Component is <i>animated</i> into its new position. You may also pass an animation configuration.
440 * @return {Ext.Component} this
442 setPosition: function(x, y, animate) {
446 adj, adjX, adjY, xIsNumber, yIsNumber;
448 if (Ext.isArray(x)) {
460 adj = me.adjustPosition(x, y);
463 xIsNumber = Ext.isNumber(adjX);
464 yIsNumber = Ext.isNumber(adjY);
466 if (xIsNumber || yIsNumber) {
476 me.animate(Ext.apply({
479 afteranimate: Ext.Function.bind(me.afterSetPosition, me, [adjX, adjY])
488 else if (!yIsNumber) {
492 el.setLeftTop(adjX, adjY);
494 me.afterSetPosition(adjX, adjY);
501 * @private Template method called after a Component has been positioned.
503 afterSetPosition: function(ax, ay) {
504 this.onPosition(ax, ay);
505 this.fireEvent('move', this, ax, ay);
508 showAt: function(x, y, animate) {
509 // A floating Component is positioned relative to its ownerCt if any.
511 this.setPosition(x, y, animate);
513 this.setPagePosition(x, y, animate);
519 * Sets the page XY position of the component. To set the left and top instead, use {@link #setPosition}.
520 * This method fires the {@link #move} event.
521 * @param {Number} x The new x position
522 * @param {Number} y The new y position
523 * @param {Mixed} animate If passed, the Component is <i>animated</i> into its new position. If this parameter
524 * is a number, it is used as the animation duration in milliseconds.
525 * @return {Ext.Component} this
527 setPagePosition: function(x, y, animate) {
531 if (Ext.isArray(x)) {
537 if (me.floating && me.floatParent) {
538 // Floating Components being positioned in their ownerCt have to be made absolute
539 p = me.floatParent.getTargetEl().getViewRegion();
540 if (Ext.isNumber(x) && Ext.isNumber(p.left)) {
543 if (Ext.isNumber(y) && Ext.isNumber(p.top)) {
546 me.setPosition(x, y, animate);
549 p = me.el.translatePoints(x, y);
550 me.setPosition(p.left, p.top, animate);
556 * Gets the current box measurements of the component's underlying element.
557 * @param {Boolean} local (optional) If true the element's left and top are returned instead of page XY (defaults to false)
558 * @return {Object} box An object in the format {x, y, width, height}
560 getBox : function(local){
561 var pos = this.getPosition(local);
562 var s = this.getSize();
569 * Sets the current box measurements of the component's underlying element.
570 * @param {Object} box An object in the format {x, y, width, height}
571 * @return {Ext.Component} this
573 updateBox : function(box){
574 this.setSize(box.width, box.height);
575 this.setPagePosition(box.x, box.y);
580 getOuterSize: function() {
583 width: el.getWidth() + el.getMargin('lr'),
584 height: el.getHeight() + el.getMargin('tb')
589 adjustSize: function(w, h) {
590 if (this.autoWidth) {
594 if (this.autoHeight) {
605 adjustPosition: function(x, y) {
607 // Floating Components being positioned in their ownerCt have to be made absolute
608 if (this.floating && this.floatParent) {
609 var o = this.floatParent.getTargetEl().getViewRegion();
621 * Gets the current XY position of the component's underlying element.
622 * @param {Boolean} local (optional) If true the element's left and top are returned instead of page XY (defaults to false)
623 * @return {Array} The XY position of the element (e.g., [100, 200])
625 getPosition: function(local) {
629 if (local === true) {
630 return [el.getLeft(true), el.getTop(true)];
632 xy = this.xy || el.getXY();
634 // Floating Components in an ownerCt have to have their positions made relative
635 if (this.floating && this.floatParent) {
636 var o = this.floatParent.getTargetEl().getViewRegion();
643 // Todo: add in xtype prefix support
645 return this.id || (this.id = (this.getXType() || 'ext-comp') + '-' + this.getAutoId());
648 onEnable: function() {
649 var actionEl = this.getActionEl();
650 actionEl.dom.removeAttribute('aria-disabled');
651 actionEl.dom.disabled = false;
655 onDisable: function() {
656 var actionEl = this.getActionEl();
657 actionEl.dom.setAttribute('aria-disabled', true);
658 actionEl.dom.disabled = true;
663 * <p>Shows this Component, rendering it first if {@link #autoRender} or {@link #floating} are <code>true</code>.</p>
664 * <p>After being shown, a {@link #floating} Component (such as a {@link Ext.window.Window}), is activated it and brought to the front of
665 * its {@link #zIndexManager z-index stack}.</p>
666 * @param {String/Element} animateTarget Optional, and <b>only valid for {@link #floating} Components such as
667 * {@link Ext.window.Window Window}s or {@link Ext.tip.ToolTip ToolTip}s, or regular Components which have been configured
668 * with <code>floating: true</code>.</b> The target from which the Component should
669 * animate from while opening (defaults to null with no animation)
670 * @param {Function} callback (optional) A callback function to call after the Component is displayed. Only necessary if animation was specified.
671 * @param {Object} scope (optional) The scope (<code>this</code> reference) in which the callback is executed. Defaults to this Component.
672 * @return {Component} this
674 show: function(animateTarget, cb, scope) {
675 if (this.rendered && this.isVisible()) {
676 if (this.toFrontOnShow && this.floating) {
679 } else if (this.fireEvent('beforeshow', this) !== false) {
682 // Render on first show if there is an autoRender config, or if this is a floater (Window, Menu, BoundList etc).
683 if (!this.rendered && (this.autoRender || this.floating)) {
688 this.onShow.apply(this, arguments);
690 // Notify any owning Container unless it's suspended.
691 // Floating Components do not participate in layouts.
692 if (this.ownerCt && !this.floating && !(this.ownerCt.suspendLayout || this.ownerCt.layout.layoutBusy)) {
693 this.ownerCt.doLayout();
695 this.afterShow.apply(this, arguments);
701 beforeShow: Ext.emptyFn,
703 // Private. Override in subclasses where more complex behaviour is needed.
708 if (this.floating && this.constrain) {
711 me.callParent(arguments);
714 afterShow: function(animateTarget, cb, scope) {
720 // Default to configured animate target if none passed
721 animateTarget = animateTarget || me.animateTarget;
723 // Need to be able to ghost the Component
725 animateTarget = null;
727 // If we're animating, kick of an animation of the ghost from the target to the *Element* current box
729 animateTarget = animateTarget.el ? animateTarget.el : Ext.get(animateTarget);
730 toBox = me.el.getBox();
731 fromBox = animateTarget.getBox();
732 fromBox.width += 'px';
733 fromBox.height += 'px';
735 toBox.height += 'px';
736 me.el.addCls(Ext.baseCSSPrefix + 'hide-offsets');
737 ghostPanel = me.ghost();
738 ghostPanel.el.stopAnimation();
740 ghostPanel.el.animate({
744 afteranimate: function() {
745 delete ghostPanel.componentLayout.lastComponentSize;
747 me.el.removeCls(Ext.baseCSSPrefix + 'hide-offsets');
751 Ext.callback(cb, scope || me);
760 Ext.callback(cb, scope || me);
762 me.fireEvent('show', me);
766 * Hides this Component, setting it to invisible using the configured {@link #hideMode}.
767 * @param {String/Element/Component} animateTarget Optional, and <b>only valid for {@link #floating} Components such as
768 * {@link Ext.window.Window Window}s or {@link Ext.tip.ToolTip ToolTip}s, or regular Components which have been configured
769 * with <code>floating: true</code>.</b>.
770 * The target to which the Component should animate while hiding (defaults to null with no animation)
771 * @param {Function} callback (optional) A callback function to call after the Component is hidden.
772 * @param {Object} scope (optional) The scope (<code>this</code> reference) in which the callback is executed. Defaults to this Component.
773 * @return {Ext.Component} this
777 // Clear the flag which is set if a floatParent was hidden while this is visible.
778 // If a hide operation was subsequently called, that pending show must be hidden.
779 this.showOnParentShow = false;
781 if (!(this.rendered && !this.isVisible()) && this.fireEvent('beforehide', this) !== false) {
784 this.onHide.apply(this, arguments);
786 // Notify any owning Container unless it's suspended.
787 // Floating Components do not participate in layouts.
788 if (this.ownerCt && !this.floating && !(this.ownerCt.suspendLayout || this.ownerCt.layout.layoutBusy)) {
789 this.ownerCt.doLayout();
796 // Possibly animate down to a target element.
797 onHide: function(animateTarget, cb, scope) {
802 // Default to configured animate target if none passed
803 animateTarget = animateTarget || me.animateTarget;
805 // Need to be able to ghost the Component
807 animateTarget = null;
809 // If we're animating, kick off an animation of the ghost down to the target
811 animateTarget = animateTarget.el ? animateTarget.el : Ext.get(animateTarget);
812 ghostPanel = me.ghost();
813 ghostPanel.el.stopAnimation();
814 toBox = animateTarget.getBox();
816 toBox.height += 'px';
817 ghostPanel.el.animate({
820 afteranimate: function() {
821 delete ghostPanel.componentLayout.lastComponentSize;
822 ghostPanel.el.hide();
823 me.afterHide(cb, scope);
829 if (!animateTarget) {
830 me.afterHide(cb, scope);
834 afterHide: function(cb, scope) {
835 Ext.callback(cb, scope || this);
836 this.fireEvent('hide', this);
841 * Template method to contribute functionality at destroy time.
843 onDestroy: function() {
846 // Ensure that any ancillary components are destroyed.
852 // Different from AbstractComponent
853 if (me.actionMode == 'container' || me.removeMode == 'container') {
854 me.container.remove();
861 deleteMembers: function() {
862 var args = arguments,
865 for (; i < len; ++i) {
866 delete this[args[i]];
871 * Try to focus this component.
872 * @param {Boolean} selectText (optional) If applicable, true to also select the text in this component
873 * @param {Boolean/Number} delay (optional) Delay the focus this number of milliseconds (true for 10 milliseconds).
874 * @return {Ext.Component} this
876 focus: function(selectText, delay) {
882 me.focusTask = Ext.create('Ext.util.DelayedTask', me.focus);
884 me.focusTask.delay(Ext.isNumber(delay) ? delay : 10, null, me, [selectText, false]);
888 if (me.rendered && !me.isDestroyed) {
889 // getFocusEl could return a Component.
890 focusEl = me.getFocusEl();
892 if (focusEl.dom && selectText === true) {
893 focusEl.dom.select();
896 // Focusing a floating Component brings it to the front of its stack.
897 // this is performed by its zIndexManager. Pass preventFocus true to avoid recursion.
907 * Returns the focus holder element associated with this Component. By default, this is the Component's encapsulating
908 * element. Subclasses which use embedded focusable elements (such as Window and Button) should override this for use
909 * by the {@link #focus} method.
910 * @returns {Ext.core.Element} the focus holing element.
912 getFocusEl: function() {
919 this.getFocusEl().blur();
929 getResizeEl: function() {
934 getPositionEl: function() {
939 getActionEl: function() {
944 getVisibilityEl: function() {
949 onResize: Ext.emptyFn,
952 getBubbleTarget: function() {
957 getContentTarget: function() {
962 * Clone the current component using the original config values passed into this instance by default.
963 * @param {Object} overrides A new config containing any properties to override in the cloned version.
964 * An id property can be passed on this object, otherwise one will be generated to avoid duplicates.
965 * @return {Ext.Component} clone The cloned copy of this component
967 cloneConfig: function(overrides) {
968 overrides = overrides || {};
969 var id = overrides.id || Ext.id();
970 var cfg = Ext.applyIf(overrides, this.initialConfig);
973 var self = Ext.getClass(this);
976 return new self(cfg);
980 * Gets the xtype for this component as registered with {@link Ext.ComponentManager}. For a list of all
981 * available xtypes, see the {@link Ext.Component} header. Example usage:
983 var t = new Ext.form.field.Text();
984 alert(t.getXType()); // alerts 'textfield'
986 * @return {String} The xtype
988 getXType: function() {
989 return this.self.xtype;
993 * Find a container above this component at any level by a custom function. If the passed function returns
994 * true, the container will be returned.
995 * @param {Function} fn The custom function to call with the arguments (container, this component).
996 * @return {Ext.container.Container} The first Container for which the custom function returns true
998 findParentBy: function(fn) {
1001 // Iterate up the ownerCt chain until there's no ownerCt, or we find an ancestor which matches using the selector function.
1002 for (p = this.ownerCt; p && !fn(p, this); p = p.ownerCt);
1007 * <p>Find a container above this component at any level by xtype or class</p>
1008 * <p>See also the {@link Ext.Component#up up} method.</p>
1009 * @param {String/Class} xtype The xtype string for a component, or the class of the component directly
1010 * @return {Ext.container.Container} The first Container which matches the given xtype or class
1012 findParentByType: function(xtype) {
1013 return Ext.isFunction(xtype) ?
1014 this.findParentBy(function(p) {
1015 return p.constructor === xtype;
1022 * Bubbles up the component/container heirarchy, calling the specified function with each component. The scope (<i>this</i>) of
1023 * function call will be the scope provided or the current component. The arguments to the function
1024 * will be the args provided or the current component. If the function returns false at any point,
1025 * the bubble is stopped.
1026 * @param {Function} fn The function to call
1027 * @param {Object} scope (optional) The scope of the function (defaults to current node)
1028 * @param {Array} args (optional) The args to call the function with (default to passing the current component)
1029 * @return {Ext.Component} this
1031 bubble: function(fn, scope, args) {
1034 if (fn.apply(scope || p, args || [p]) === false) {
1042 getProxy: function() {
1044 this.proxy = this.el.createProxy(Ext.baseCSSPrefix + 'proxy-el', Ext.getBody(), true);