ext-all-debug.js
上传用户:shuoshiled
上传日期:2018-01-28
资源大小:10124k
文件大小:2341k
源码类别:

中间件编程

开发平台:

JavaScript

  1. /*!  * Ext JS Library 3.0.0  * Copyright(c) 2006-2009 Ext JS, LLC  * licensing@extjs.com  * http://www.extjs.com/license  */ /**  * @class Ext.DomHelper  * <p>The DomHelper class provides a layer of abstraction from DOM and transparently supports creating  * elements via DOM or using HTML fragments. It also has the ability to create HTML fragment templates  * from your DOM building code.</p>  *  * <p><b><u>DomHelper element specification object</u></b></p>  * <p>A specification object is used when creating elements. Attributes of this object  * are assumed to be element attributes, except for 4 special attributes:  * <div class="mdetail-params"><ul>  * <li><b><tt>tag</tt></b> : <div class="sub-desc">The tag name of the element</div></li>  * <li><b><tt>children</tt></b> : or <tt>cn</tt><div class="sub-desc">An array of the  * same kind of element definition objects to be created and appended. These can be nested  * as deep as you want.</div></li>  * <li><b><tt>cls</tt></b> : <div class="sub-desc">The class attribute of the element.  * This will end up being either the "class" attribute on a HTML fragment or className  * for a DOM node, depending on whether DomHelper is using fragments or DOM.</div></li>  * <li><b><tt>html</tt></b> : <div class="sub-desc">The innerHTML for the element</div></li>  * </ul></div></p>  *  * <p><b><u>Insertion methods</u></b></p>  * <p>Commonly used insertion methods:  * <div class="mdetail-params"><ul>  * <li><b><tt>{@link #append}</tt></b> : <div class="sub-desc"></div></li>  * <li><b><tt>{@link #insertBefore}</tt></b> : <div class="sub-desc"></div></li>  * <li><b><tt>{@link #insertAfter}</tt></b> : <div class="sub-desc"></div></li>  * <li><b><tt>{@link #overwrite}</tt></b> : <div class="sub-desc"></div></li>  * <li><b><tt>{@link #createTemplate}</tt></b> : <div class="sub-desc"></div></li>  * <li><b><tt>{@link #insertHtml}</tt></b> : <div class="sub-desc"></div></li>  * </ul></div></p>  *  * <p><b><u>Example</u></b></p>  * <p>This is an example, where an unordered list with 3 children items is appended to an existing  * element with id <tt>'my-div'</tt>:<br>  <pre><code> var dh = Ext.DomHelper; // create shorthand alias // specification object var spec = {     id: 'my-ul',     tag: 'ul',     cls: 'my-list',     // append children after creating     children: [     // may also specify 'cn' instead of 'children'         {tag: 'li', id: 'item0', html: 'List Item 0'},         {tag: 'li', id: 'item1', html: 'List Item 1'},         {tag: 'li', id: 'item2', html: 'List Item 2'}     ] }; var list = dh.append(     'my-div', // the context element 'my-div' can either be the id or the actual node     spec      // the specification object );  </code></pre></p>  * <p>Element creation specification parameters in this class may also be passed as an Array of  * specification objects. This can be used to insert multiple sibling nodes into an existing  * container very efficiently. For example, to add more list items to the example above:<pre><code> dh.append('my-ul', [     {tag: 'li', id: 'item3', html: 'List Item 3'},     {tag: 'li', id: 'item4', html: 'List Item 4'} ]);  * </code></pre></p>  *  * <p><b><u>Templating</u></b></p>  * <p>The real power is in the built-in templating. Instead of creating or appending any elements,  * <tt>{@link #createTemplate}</tt> returns a Template object which can be used over and over to  * insert new elements. Revisiting the example above, we could utilize templating this time:  * <pre><code> // create the node var list = dh.append('my-div', {tag: 'ul', cls: 'my-list'}); // get template var tpl = dh.createTemplate({tag: 'li', id: 'item{0}', html: 'List Item {0}'}); for(var i = 0; i < 5, i++){     tpl.append(list, [i]); // use template to append to the actual node }  * </code></pre></p>  * <p>An example using a template:<pre><code> var html = '<a id="{0}" href="{1}" class="nav">{2}</a>'; var tpl = new Ext.DomHelper.createTemplate(html); tpl.append('blog-roll', ['link1', 'http://www.jackslocum.com/', "Jack&#39;s Site"]); tpl.append('blog-roll', ['link2', 'http://www.dustindiaz.com/', "Dustin&#39;s Site"]);  * </code></pre></p>  *  * <p>The same example using named parameters:<pre><code> var html = '<a id="{id}" href="{url}" class="nav">{text}</a>'; var tpl = new Ext.DomHelper.createTemplate(html); tpl.append('blog-roll', {     id: 'link1',     url: 'http://www.jackslocum.com/',     text: "Jack&#39;s Site" }); tpl.append('blog-roll', {     id: 'link2',     url: 'http://www.dustindiaz.com/',     text: "Dustin&#39;s Site" });  * </code></pre></p>  *  * <p><b><u>Compiling Templates</u></b></p>  * <p>Templates are applied using regular expressions. The performance is great, but if  * you are adding a bunch of DOM elements using the same template, you can increase  * performance even further by {@link Ext.Template#compile "compiling"} the template.  * The way "{@link Ext.Template#compile compile()}" works is the template is parsed and  * broken up at the different variable points and a dynamic function is created and eval'ed.  * The generated function performs string concatenation of these parts and the passed  * variables instead of using regular expressions.  * <pre><code> var html = '<a id="{id}" href="{url}" class="nav">{text}</a>'; var tpl = new Ext.DomHelper.createTemplate(html); tpl.compile(); //... use template like normal  * </code></pre></p>  *  * <p><b><u>Performance Boost</u></b></p>  * <p>DomHelper will transparently create HTML fragments when it can. Using HTML fragments instead  * of DOM can significantly boost performance.</p>  * <p>Element creation specification parameters may also be strings. If {@link #useDom} is <tt>false</tt>,  * then the string is used as innerHTML. If {@link #useDom} is <tt>true</tt>, a string specification  * results in the creation of a text node. Usage:</p>  * <pre><code> Ext.DomHelper.useDom = true; // force it to use DOM; reduces performance  * </code></pre>  * @singleton  */ Ext.DomHelper = function(){     var tempTableEl = null,      emptyTags = /^(?:br|frame|hr|img|input|link|meta|range|spacer|wbr|area|param|col)$/i,      tableRe = /^table|tbody|tr|td$/i,      pub,      // kill repeat to save bytes      afterbegin = "afterbegin",      afterend = "afterend",      beforebegin = "beforebegin",      beforeend = "beforeend",      ts = '<table>',         te = '</table>',         tbs = ts+'<tbody>',         tbe = '</tbody>'+te,         trs = tbs + '<tr>',         tre = '</tr>'+tbe;     // private     function doInsert(el, o, returnElement, pos, sibling, append){         var newNode = pub.insertHtml(pos, Ext.getDom(el), createHtml(o));         return returnElement ? Ext.get(newNode, true) : newNode;     }     // build as innerHTML where available     function createHtml(o){     var b = "",      attr,      val,      key,      keyVal,      cn;         if(typeof o == 'string'){             b = o;         } else if (Ext.isArray(o)) {         Ext.each(o, function(v) {                 b += createHtml(v);             });         } else {         b += "<" + (o.tag = o.tag || "div");             Ext.iterate(o, function(attr, val){                 if(!/tag|children|cn|html$/i.test(attr)){                     if (Ext.isObject(val)) {                         b += " " + attr + "='";                         Ext.iterate(val, function(key, keyVal){                             b += key + ":" + keyVal + ";";                         });                         b += "'";                     }else{                         b += " " + ({cls : "class", htmlFor : "for"}[attr] || attr) + "='" + val + "'";                     }                 }             });         // Now either just close the tag or try to add children and close the tag.         if (emptyTags.test(o.tag)) {             b += "/>";         } else {             b += ">";             if ((cn = o.children || o.cn)) {                 b += createHtml(cn);             } else if(o.html){                 b += o.html;             }             b += "</" + o.tag + ">";          }         }         return b;     }     function ieTable(depth, s, h, e){         tempTableEl.innerHTML = [s, h, e].join('');         var i = -1,          el = tempTableEl;         while(++i < depth){             el = el.firstChild;         }         return el;     }     /**      * @ignore      * Nasty code for IE's broken table implementation      */     function insertIntoTable(tag, where, el, html) {     var node,          before;         tempTableEl = tempTableEl || document.createElement('div');        if(tag == 'td' && (where == afterbegin || where == beforeend) ||           !/td|tr|tbody/i.test(tag) && (where == beforebegin || where == afterend)) {             return;         }         before = where == beforebegin ? el :    where == afterend ? el.nextSibling :  where == afterbegin ? el.firstChild : null;         if (where == beforebegin || where == afterend) {          el = el.parentNode;      }         if (tag == 'td' || (tag == "tr" && (where == beforeend || where == afterbegin))) {         node = ieTable(4, trs, html, tre);         } else if ((tag == "tbody" && (where == beforeend || where == afterbegin)) ||             (tag == "tr" && (where == beforebegin || where == afterend))) {         node = ieTable(3, tbs, html, tbe);         } else {       node = ieTable(2, ts, html, te);         }         el.insertBefore(node, before);         return node;     }     pub = {     /**      * Returns the markup for the passed Element(s) config.      * @param {Object} o The DOM object spec (and children)      * @return {String}      */     markup : function(o){         return createHtml(o);     },     /**      * Inserts an HTML fragment into the DOM.      * @param {String} where Where to insert the html in relation to el - beforeBegin, afterBegin, beforeEnd, afterEnd.      * @param {HTMLElement} el The context element      * @param {String} html The HTML fragmenet      * @return {HTMLElement} The new node      */     insertHtml : function(where, el, html){         var hash = {},          hashVal,            setStart,          range,          frag,          rangeEl,          rs;         where = where.toLowerCase();         // add these here because they are used in both branches of the condition.         hash[beforebegin] = ['BeforeBegin', 'previousSibling'];         hash[afterend] = ['AfterEnd', 'nextSibling'];         if (el.insertAdjacentHTML) {             if(tableRe.test(el.tagName) && (rs = insertIntoTable(el.tagName.toLowerCase(), where, el, html))){              return rs;             }             // add these two to the hash.             hash[afterbegin] = ['AfterBegin', 'firstChild'];             hash[beforeend] = ['BeforeEnd', 'lastChild'];             if ((hashVal = hash[where])) {          el.insertAdjacentHTML(hashVal[0], html);              return el[hashVal[1]];             }         } else {         range = el.ownerDocument.createRange();         setStart = "setStart" + (/end/i.test(where) ? "After" : "Before");         if (hash[where]) {       range[setStart](el);       frag = range.createContextualFragment(html);       el.parentNode.insertBefore(frag, where == beforebegin ? el : el.nextSibling);       return el[(where == beforebegin ? "previous" : "next") + "Sibling"];         } else {         rangeEl = (where == afterbegin ? "first" : "last") + "Child";         if (el.firstChild) {         range[setStart](el[rangeEl]);         frag = range.createContextualFragment(html);                         if(where == afterbegin){                             el.insertBefore(frag, el.firstChild);                         }else{                             el.appendChild(frag);                         }         } else {               el.innerHTML = html;               }               return el[rangeEl];         }         }         throw 'Illegal insertion point -> "' + where + '"';     },     /**      * Creates new DOM element(s) and inserts them before el.      * @param {Mixed} el The context element      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob      * @param {Boolean} returnElement (optional) true to return a Ext.Element      * @return {HTMLElement/Ext.Element} The new node      */     insertBefore : function(el, o, returnElement){         return doInsert(el, o, returnElement, beforebegin);     },     /**      * Creates new DOM element(s) and inserts them after el.      * @param {Mixed} el The context element      * @param {Object} o The DOM object spec (and children)      * @param {Boolean} returnElement (optional) true to return a Ext.Element      * @return {HTMLElement/Ext.Element} The new node      */     insertAfter : function(el, o, returnElement){         return doInsert(el, o, returnElement, afterend, "nextSibling");     },     /**      * Creates new DOM element(s) and inserts them as the first child of el.      * @param {Mixed} el The context element      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob      * @param {Boolean} returnElement (optional) true to return a Ext.Element      * @return {HTMLElement/Ext.Element} The new node      */     insertFirst : function(el, o, returnElement){         return doInsert(el, o, returnElement, afterbegin, "firstChild");     },     /**      * Creates new DOM element(s) and appends them to el.      * @param {Mixed} el The context element      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob      * @param {Boolean} returnElement (optional) true to return a Ext.Element      * @return {HTMLElement/Ext.Element} The new node      */     append : function(el, o, returnElement){     return doInsert(el, o, returnElement, beforeend, "", true);     },     /**      * Creates new DOM element(s) and overwrites the contents of el with them.      * @param {Mixed} el The context element      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob      * @param {Boolean} returnElement (optional) true to return a Ext.Element      * @return {HTMLElement/Ext.Element} The new node      */     overwrite : function(el, o, returnElement){         el = Ext.getDom(el);         el.innerHTML = createHtml(o);         return returnElement ? Ext.get(el.firstChild) : el.firstChild;     },     createHtml : createHtml     };     return pub; }();/**
  2.  * @class Ext.DomHelper
  3.  */
  4. Ext.apply(Ext.DomHelper,
  5. function(){
  6. var pub,
  7. afterbegin = 'afterbegin',
  8.      afterend = 'afterend',
  9.      beforebegin = 'beforebegin',
  10.      beforeend = 'beforeend';
  11. // private
  12.     function doInsert(el, o, returnElement, pos, sibling, append){
  13.         el = Ext.getDom(el);
  14.         var newNode;
  15.         if (pub.useDom) {
  16.             newNode = createDom(o, null);
  17.             if (append) {
  18.             el.appendChild(newNode);
  19.             } else {
  20.          (sibling == 'firstChild' ? el : el.parentNode).insertBefore(newNode, el[sibling] || el);
  21.             }
  22.         } else {
  23.             newNode = Ext.DomHelper.insertHtml(pos, el, Ext.DomHelper.createHtml(o));
  24.         }
  25.         return returnElement ? Ext.get(newNode, true) : newNode;
  26.     }
  27. // build as dom
  28.     /** @ignore */
  29.     function createDom(o, parentNode){
  30.         var el,
  31.          doc = document,
  32.          useSet,
  33.          attr,
  34.          val,
  35.          cn;
  36.         if (Ext.isArray(o)) {                       // Allow Arrays of siblings to be inserted
  37.             el = doc.createDocumentFragment(); // in one shot using a DocumentFragment
  38.         Ext.each(o, function(v) {
  39.                 createDom(v, el);
  40.             });
  41.         } else if (Ext.isString(o)) {         // Allow a string as a child spec.
  42.             el = doc.createTextNode(o);
  43.         } else {
  44.             el = doc.createElement( o.tag || 'div' );
  45.             useSet = !!el.setAttribute; // In IE some elements don't have setAttribute
  46.             Ext.iterate(o, function(attr, val){
  47.                 if(!/tag|children|cn|html|style/.test(attr)){
  48.                 if(attr == 'cls'){
  49.                     el.className = val;
  50.                 }else{
  51.                         if(useSet){
  52.                             el.setAttribute(attr, val);
  53.                         }else{
  54.                             el[attr] = val;
  55.                         }
  56.                 }
  57.                 }
  58.             });
  59.             pub.applyStyles(el, o.style);
  60.             if ((cn = o.children || o.cn)) {
  61.                 createDom(cn, el);
  62.             } else if (o.html) {
  63.                 el.innerHTML = o.html;
  64.             }
  65.         }
  66.         if(parentNode){
  67.            parentNode.appendChild(el);
  68.         }
  69.         return el;
  70.     }
  71. pub = {
  72. /**
  73.      * Creates a new Ext.Template from the DOM object spec.
  74.      * @param {Object} o The DOM object spec (and children)
  75.      * @return {Ext.Template} The new template
  76.      */
  77.     createTemplate : function(o){
  78.         var html = Ext.DomHelper.createHtml(o);
  79.         return new Ext.Template(html);
  80.     },
  81. /** True to force the use of DOM instead of html fragments @type Boolean */
  82.     useDom : false,
  83.     /**
  84.      * Applies a style specification to an element.
  85.      * @param {String/HTMLElement} el The element to apply styles to
  86.      * @param {String/Object/Function} styles A style specification string e.g. 'width:100px', or object in the form {width:'100px'}, or
  87.      * a function which returns such a specification.
  88.      */
  89.     applyStyles : function(el, styles){
  90.     if(styles){
  91. var i = 0,
  92.      len,
  93.      style;
  94.      el = Ext.fly(el);
  95. if(Ext.isFunction(styles)){
  96.     styles = styles.call();
  97. }
  98. if(Ext.isString(styles)){
  99. styles = styles.trim().split(/s*(?::|;)s*/);
  100. for(len = styles.length; i < len;){
  101. el.setStyle(styles[i++], styles[i++]);
  102. }
  103. }else if (Ext.isObject(styles)){
  104. el.setStyle(styles);
  105. }
  106. }
  107.     },
  108.     /**
  109.      * Creates new DOM element(s) and inserts them before el.
  110.      * @param {Mixed} el The context element
  111.      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob
  112.      * @param {Boolean} returnElement (optional) true to return a Ext.Element
  113.      * @return {HTMLElement/Ext.Element} The new node
  114.          * @hide (repeat)
  115.      */
  116.     insertBefore : function(el, o, returnElement){
  117.         return doInsert(el, o, returnElement, beforebegin);
  118.     },
  119.     /**
  120.      * Creates new DOM element(s) and inserts them after el.
  121.      * @param {Mixed} el The context element
  122.      * @param {Object} o The DOM object spec (and children)
  123.      * @param {Boolean} returnElement (optional) true to return a Ext.Element
  124.      * @return {HTMLElement/Ext.Element} The new node
  125.          * @hide (repeat)
  126.      */
  127.     insertAfter : function(el, o, returnElement){
  128.         return doInsert(el, o, returnElement, afterend, 'nextSibling');
  129.     },
  130.     /**
  131.      * Creates new DOM element(s) and inserts them as the first child of el.
  132.      * @param {Mixed} el The context element
  133.      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob
  134.      * @param {Boolean} returnElement (optional) true to return a Ext.Element
  135.      * @return {HTMLElement/Ext.Element} The new node
  136.          * @hide (repeat)
  137.      */
  138.     insertFirst : function(el, o, returnElement){
  139.         return doInsert(el, o, returnElement, afterbegin, 'firstChild');
  140.     },
  141.     /**
  142.      * Creates new DOM element(s) and appends them to el.
  143.      * @param {Mixed} el The context element
  144.      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob
  145.      * @param {Boolean} returnElement (optional) true to return a Ext.Element
  146.      * @return {HTMLElement/Ext.Element} The new node
  147.          * @hide (repeat)
  148.      */
  149.     append: function(el, o, returnElement){
  150.             return doInsert(el, o, returnElement, beforeend, '', true);
  151.         },
  152.     /**
  153.      * Creates new DOM element(s) without inserting them to the document.
  154.      * @param {Object/String} o The DOM object spec (and children) or raw HTML blob
  155.      * @return {HTMLElement} The new uninserted node
  156.      */
  157.         createDom: createDom
  158. };
  159. return pub;
  160. }());/**  * @class Ext.Template  * Represents an HTML fragment template. Templates can be precompiled for greater performance.  * For a list of available format functions, see {@link Ext.util.Format}.<br />  * Usage: <pre><code> var t = new Ext.Template(     '&lt;div name="{id}"&gt;',         '&lt;span class="{cls}"&gt;{name:trim} {value:ellipsis(10)}&lt;/span&gt;',     '&lt;/div&gt;' ); t.append('some-element', {id: 'myid', cls: 'myclass', name: 'foo', value: 'bar'}); </code></pre>  * @constructor  * @param {String/Array} html The HTML fragment or an array of fragments to join("") or multiple arguments to join("")  */ Ext.Template = function(html){     var me = this,      a = arguments,      buf = [];     if (Ext.isArray(html)) {         html = html.join("");     } else if (a.length > 1) {     Ext.each(a, function(v) {             if (Ext.isObject(v)) {                 Ext.apply(me, v);             } else {                 buf.push(v);             }         });         html = buf.join('');     }     /**@private*/     me.html = html;     if (me.compiled) {         me.compile();     } }; Ext.Template.prototype = {     /**      * Returns an HTML fragment of this template with the specified values applied.      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @return {String} The HTML fragment      */     applyTemplate : function(values){ var me = this;         return me.compiled ?          me.compiled(values) : me.html.replace(me.re, function(m, name){          return values[name] !== undefined ? values[name] : "";         }); },     /**      * Sets the HTML used as the template and optionally compiles it.      * @param {String} html      * @param {Boolean} compile (optional) True to compile the template (defaults to undefined)      * @return {Ext.Template} this      */     set : function(html, compile){     var me = this;         me.html = html;         me.compiled = null;         return compile ? me.compile() : me;     },     /**     * The regular expression used to match template variables     * @type RegExp     * @property     */     re : /{([w-]+)}/g,     /**      * Compiles the template into an internal function, eliminating the RegEx overhead.      * @return {Ext.Template} this      */     compile : function(){         var me = this,          sep = Ext.isGecko ? "+" : ",";         function fn(m, name){                                 name = "values['" + name + "']";         return "'"+ sep + '(' + name + " == undefined ? '' : " + name + ')' + sep + "'";         }                          eval("this.compiled = function(values){ return " + (Ext.isGecko ? "'" : "['") +              me.html.replace(/\/g, '\\').replace(/(rn|n)/g, '\n').replace(/'/g, "\'").replace(this.re, fn) +              (Ext.isGecko ?  "';};" : "'].join('');};"));         return me;     },     /**      * Applies the supplied values to the template and inserts the new node(s) as the first child of el.      * @param {Mixed} el The context element      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @param {Boolean} returnElement (optional) true to return a Ext.Element (defaults to undefined)      * @return {HTMLElement/Ext.Element} The new node or Element      */     insertFirst: function(el, values, returnElement){         return this.doInsert('afterBegin', el, values, returnElement);     },     /**      * Applies the supplied values to the template and inserts the new node(s) before el.      * @param {Mixed} el The context element      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @param {Boolean} returnElement (optional) true to return a Ext.Element (defaults to undefined)      * @return {HTMLElement/Ext.Element} The new node or Element      */     insertBefore: function(el, values, returnElement){         return this.doInsert('beforeBegin', el, values, returnElement);     },     /**      * Applies the supplied values to the template and inserts the new node(s) after el.      * @param {Mixed} el The context element      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @param {Boolean} returnElement (optional) true to return a Ext.Element (defaults to undefined)      * @return {HTMLElement/Ext.Element} The new node or Element      */     insertAfter : function(el, values, returnElement){         return this.doInsert('afterEnd', el, values, returnElement);     },     /**      * Applies the supplied values to the template and appends the new node(s) to el.      * @param {Mixed} el The context element      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @param {Boolean} returnElement (optional) true to return a Ext.Element (defaults to undefined)      * @return {HTMLElement/Ext.Element} The new node or Element      */     append : function(el, values, returnElement){         return this.doInsert('beforeEnd', el, values, returnElement);     },     doInsert : function(where, el, values, returnEl){         el = Ext.getDom(el);         var newNode = Ext.DomHelper.insertHtml(where, el, this.applyTemplate(values));         return returnEl ? Ext.get(newNode, true) : newNode;     },     /**      * Applies the supplied values to the template and overwrites the content of el with the new node(s).      * @param {Mixed} el The context element      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})      * @param {Boolean} returnElement (optional) true to return a Ext.Element (defaults to undefined)      * @return {HTMLElement/Ext.Element} The new node or Element      */     overwrite : function(el, values, returnElement){         el = Ext.getDom(el);         el.innerHTML = this.applyTemplate(values);         return returnElement ? Ext.get(el.firstChild, true) : el.firstChild;     } }; /**  * Alias for {@link #applyTemplate}  * Returns an HTML fragment of this template with the specified values applied.  * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})  * @return {String} The HTML fragment  * @member Ext.Template  * @method apply  */ Ext.Template.prototype.apply = Ext.Template.prototype.applyTemplate; /**  * Creates a template from the passed element's value (<i>display:none</i> textarea, preferred) or innerHTML.  * @param {String/HTMLElement} el A DOM element or its id  * @param {Object} config A configuration object  * @return {Ext.Template} The created template  * @static  */ Ext.Template.from = function(el, config){     el = Ext.getDom(el);     return new Ext.Template(el.value || el.innerHTML, config || ''); };/**
  161.  * @class Ext.Template
  162.  */
  163. Ext.apply(Ext.Template.prototype, {
  164.     /**
  165.      * Returns an HTML fragment of this template with the specified values applied.
  166.      * @param {Object/Array} values The template values. Can be an array if your params are numeric (i.e. {0}) or an object (i.e. {foo: 'bar'})
  167.      * @return {String} The HTML fragment
  168.      * @hide repeat doc
  169.      */
  170.     applyTemplate : function(values){
  171. var me = this,
  172. useF = me.disableFormats !== true,
  173.          fm = Ext.util.Format, 
  174.          tpl = me;     
  175.     
  176.         if(me.compiled){
  177.             return me.compiled(values);
  178.         }
  179.         function fn(m, name, format, args){
  180.             if (format && useF) {
  181.                 if (format.substr(0, 5) == "this.") {
  182.                     return tpl.call(format.substr(5), values[name], values);
  183.                 } else {
  184.                     if (args) {
  185.                         // quoted values are required for strings in compiled templates,
  186.                         // but for non compiled we need to strip them
  187.                         // quoted reversed for jsmin
  188.                         var re = /^s*['"](.*)["']s*$/;
  189.                         args = args.split(',');
  190.                         for(var i = 0, len = args.length; i < len; i++){
  191.                             args[i] = args[i].replace(re, "$1");
  192.                         }
  193.                         args = [values[name]].concat(args);
  194.                     } else {
  195.                         args = [values[name]];
  196.                     }
  197.                     return fm[format].apply(fm, args);
  198.                 }
  199.             } else {
  200.                 return values[name] !== undefined ? values[name] : "";
  201.             }
  202.         }
  203.         return me.html.replace(me.re, fn);
  204.     },
  205.     /**
  206.      * <tt>true</tt> to disable format functions (defaults to <tt>false</tt>)
  207.      * @type Boolean
  208.      * @property
  209.      */
  210.     disableFormats : false,
  211.     /**
  212.      * The regular expression used to match template variables
  213.      * @type RegExp
  214.      * @property
  215.      * @hide repeat doc
  216.      */
  217.     re : /{([w-]+)(?::([w.]*)(?:((.*?)?))?)?}/g,
  218.     
  219.     /**
  220.      * Compiles the template into an internal function, eliminating the RegEx overhead.
  221.      * @return {Ext.Template} this
  222.      * @hide repeat doc
  223.      */
  224.     compile : function(){
  225.         var me = this,
  226.          fm = Ext.util.Format,
  227.          useF = me.disableFormats !== true,
  228.          sep = Ext.isGecko ? "+" : ",",
  229.          body;
  230.         
  231.         function fn(m, name, format, args){
  232.             if(format && useF){
  233.                 args = args ? ',' + args : "";
  234.                 if(format.substr(0, 5) != "this."){
  235.                     format = "fm." + format + '(';
  236.                 }else{
  237.                     format = 'this.call("'+ format.substr(5) + '", ';
  238.                     args = ", values";
  239.                 }
  240.             }else{
  241.                 args= ''; format = "(values['" + name + "'] == undefined ? '' : ";
  242.             }
  243.             return "'"+ sep + format + "values['" + name + "']" + args + ")"+sep+"'";
  244.         }
  245.         
  246.         // branched to use + in gecko and [].join() in others
  247.         if(Ext.isGecko){
  248.             body = "this.compiled = function(values){ return '" +
  249.                    me.html.replace(/\/g, '\\').replace(/(rn|n)/g, '\n').replace(/'/g, "\'").replace(this.re, fn) +
  250.                     "';};";
  251.         }else{
  252.             body = ["this.compiled = function(values){ return ['"];
  253.             body.push(me.html.replace(/\/g, '\\').replace(/(rn|n)/g, '\n').replace(/'/g, "\'").replace(this.re, fn));
  254.             body.push("'].join('');};");
  255.             body = body.join('');
  256.         }
  257.         eval(body);
  258.         return me;
  259.     },
  260.     
  261.     // private function used to call members
  262.     call : function(fnName, value, allValues){
  263.         return this[fnName](value, allValues);
  264.     }
  265. });
  266. Ext.Template.prototype.apply = Ext.Template.prototype.applyTemplate; /*
  267.  * This is code is also distributed under MIT license for use
  268.  * with jQuery and prototype JavaScript libraries.
  269.  */
  270. /**
  271.  * @class Ext.DomQuery
  272. Provides high performance selector/xpath processing by compiling queries into reusable functions. New pseudo classes and matchers can be plugged. It works on HTML and XML documents (if a content node is passed in).
  273. <p>
  274. DomQuery supports most of the <a href="http://www.w3.org/TR/2005/WD-css3-selectors-20051215/#selectors">CSS3 selectors spec</a>, along with some custom selectors and basic XPath.</p>
  275. <p>
  276. All selectors, attribute filters and pseudos below can be combined infinitely in any order. For example "div.foo:nth-child(odd)[@foo=bar].bar:first" would be a perfectly valid selector. Node filters are processed in the order in which they appear, which allows you to optimize your queries for your document structure.
  277. </p>
  278. <h4>Element Selectors:</h4>
  279. <ul class="list">
  280.     <li> <b>*</b> any element</li>
  281.     <li> <b>E</b> an element with the tag E</li>
  282.     <li> <b>E F</b> All descendent elements of E that have the tag F</li>
  283.     <li> <b>E > F</b> or <b>E/F</b> all direct children elements of E that have the tag F</li>
  284.     <li> <b>E + F</b> all elements with the tag F that are immediately preceded by an element with the tag E</li>
  285.     <li> <b>E ~ F</b> all elements with the tag F that are preceded by a sibling element with the tag E</li>
  286. </ul>
  287. <h4>Attribute Selectors:</h4>
  288. <p>The use of &#64; and quotes are optional. For example, div[&#64;foo='bar'] is also a valid attribute selector.</p>
  289. <ul class="list">
  290.     <li> <b>E[foo]</b> has an attribute "foo"</li>
  291.     <li> <b>E[foo=bar]</b> has an attribute "foo" that equals "bar"</li>
  292.     <li> <b>E[foo^=bar]</b> has an attribute "foo" that starts with "bar"</li>
  293.     <li> <b>E[foo$=bar]</b> has an attribute "foo" that ends with "bar"</li>
  294.     <li> <b>E[foo*=bar]</b> has an attribute "foo" that contains the substring "bar"</li>
  295.     <li> <b>E[foo%=2]</b> has an attribute "foo" that is evenly divisible by 2</li>
  296.     <li> <b>E[foo!=bar]</b> has an attribute "foo" that does not equal "bar"</li>
  297. </ul>
  298. <h4>Pseudo Classes:</h4>
  299. <ul class="list">
  300.     <li> <b>E:first-child</b> E is the first child of its parent</li>
  301.     <li> <b>E:last-child</b> E is the last child of its parent</li>
  302.     <li> <b>E:nth-child(<i>n</i>)</b> E is the <i>n</i>th child of its parent (1 based as per the spec)</li>
  303.     <li> <b>E:nth-child(odd)</b> E is an odd child of its parent</li>
  304.     <li> <b>E:nth-child(even)</b> E is an even child of its parent</li>
  305.     <li> <b>E:only-child</b> E is the only child of its parent</li>
  306.     <li> <b>E:checked</b> E is an element that is has a checked attribute that is true (e.g. a radio or checkbox) </li>
  307.     <li> <b>E:first</b> the first E in the resultset</li>
  308.     <li> <b>E:last</b> the last E in the resultset</li>
  309.     <li> <b>E:nth(<i>n</i>)</b> the <i>n</i>th E in the resultset (1 based)</li>
  310.     <li> <b>E:odd</b> shortcut for :nth-child(odd)</li>
  311.     <li> <b>E:even</b> shortcut for :nth-child(even)</li>
  312.     <li> <b>E:contains(foo)</b> E's innerHTML contains the substring "foo"</li>
  313.     <li> <b>E:nodeValue(foo)</b> E contains a textNode with a nodeValue that equals "foo"</li>
  314.     <li> <b>E:not(S)</b> an E element that does not match simple selector S</li>
  315.     <li> <b>E:has(S)</b> an E element that has a descendent that matches simple selector S</li>
  316.     <li> <b>E:next(S)</b> an E element whose next sibling matches simple selector S</li>
  317.     <li> <b>E:prev(S)</b> an E element whose previous sibling matches simple selector S</li>
  318. </ul>
  319. <h4>CSS Value Selectors:</h4>
  320. <ul class="list">
  321.     <li> <b>E{display=none}</b> css value "display" that equals "none"</li>
  322.     <li> <b>E{display^=none}</b> css value "display" that starts with "none"</li>
  323.     <li> <b>E{display$=none}</b> css value "display" that ends with "none"</li>
  324.     <li> <b>E{display*=none}</b> css value "display" that contains the substring "none"</li>
  325.     <li> <b>E{display%=2}</b> css value "display" that is evenly divisible by 2</li>
  326.     <li> <b>E{display!=none}</b> css value "display" that does not equal "none"</li>
  327. </ul>
  328.  * @singleton
  329.  */
  330. Ext.DomQuery = function(){
  331.     var cache = {}, 
  332.      simpleCache = {}, 
  333.      valueCache = {},
  334.      nonSpace = /S/,
  335.      trimRe = /^s+|s+$/g,
  336.      tplRe = /{(d+)}/g,
  337.      modeRe = /^(s?[/>+~]s?|s|$)/,
  338.      tagTokenRe = /^(#)?([w-*]+)/,
  339.      nthRe = /(d*)n+?(d*)/, 
  340.      nthRe2 = /D/,
  341.      // This is for IE MSXML which does not support expandos.
  342.     // IE runs the same speed using setAttribute, however FF slows way down
  343.     // and Safari completely fails so they need to continue to use expandos.
  344.     isIE = window.ActiveXObject ? true : false,
  345.         isOpera = Ext.isOpera,
  346.     key = 30803;
  347.     
  348.     // this eval is stop the compressor from
  349. // renaming the variable to something shorter
  350. eval("var batch = 30803;");    
  351.     function child(p, index){
  352.         var i = 0,
  353.          n = p.firstChild;
  354.         while(n){
  355.             if(n.nodeType == 1){
  356.                if(++i == index){
  357.                    return n;
  358.                }
  359.             }
  360.             n = n.nextSibling;
  361.         }
  362.         return null;
  363.     };
  364.     function next(n){
  365.         while((n = n.nextSibling) && n.nodeType != 1);
  366.         return n;
  367.     };
  368.     function prev(n){
  369.         while((n = n.previousSibling) && n.nodeType != 1);
  370.         return n;
  371.     };
  372.     function children(d){
  373.         var n = d.firstChild, ni = -1,
  374.          nx;
  375.       while(n){
  376.           nx = n.nextSibling;
  377.           if(n.nodeType == 3 && !nonSpace.test(n.nodeValue)){
  378.               d.removeChild(n);
  379.           }else{
  380.               n.nodeIndex = ++ni;
  381.           }
  382.           n = nx;
  383.       }
  384.       return this;
  385.   };
  386.     function byClassName(c, a, v){
  387.         if(!v){
  388.             return c;
  389.         }
  390.         var r = [], ri = -1, cn;
  391.         for(var i = 0, ci; ci = c[i]; i++){
  392.             if((' '+ci.className+' ').indexOf(v) != -1){
  393.                 r[++ri] = ci;
  394.             }
  395.         }
  396.         return r;
  397.     };
  398.     function attrValue(n, attr){
  399.         if(!n.tagName && typeof n.length != "undefined"){
  400.             n = n[0];
  401.         }
  402.         if(!n){
  403.             return null;
  404.         }
  405.         if(attr == "for"){
  406.             return n.htmlFor;
  407.         }
  408.         if(attr == "class" || attr == "className"){
  409.             return n.className;
  410.         }
  411.         return n.getAttribute(attr) || n[attr];
  412.     };
  413.     function getNodes(ns, mode, tagName){
  414.         var result = [], ri = -1, cs;
  415.         if(!ns){
  416.             return result;
  417.         }
  418.         tagName = tagName || "*";
  419.         if(typeof ns.getElementsByTagName != "undefined"){
  420.             ns = [ns];
  421.         }
  422.         if(!mode){
  423.             for(var i = 0, ni; ni = ns[i]; i++){
  424.                 cs = ni.getElementsByTagName(tagName);
  425.                 for(var j = 0, ci; ci = cs[j]; j++){
  426.                     result[++ri] = ci;
  427.                 }
  428.             }
  429.         }else if(mode == "/" || mode == ">"){
  430.             var utag = tagName.toUpperCase();
  431.             for(var i = 0, ni, cn; ni = ns[i]; i++){
  432.                 cn = isOpera ? ni.childNodes : (ni.children || ni.childNodes);
  433.                 for(var j = 0, cj; cj = cn[j]; j++){
  434.                     if(cj.nodeName == utag || cj.nodeName == tagName  || tagName == '*'){
  435.                         result[++ri] = cj;
  436.                     }
  437.                 }
  438.             }
  439.         }else if(mode == "+"){
  440.             var utag = tagName.toUpperCase();
  441.             for(var i = 0, n; n = ns[i]; i++){
  442.                 while((n = n.nextSibling) && n.nodeType != 1);
  443.                 if(n && (n.nodeName == utag || n.nodeName == tagName || tagName == '*')){
  444.                     result[++ri] = n;
  445.                 }
  446.             }
  447.         }else if(mode == "~"){
  448.             var utag = tagName.toUpperCase();
  449.             for(var i = 0, n; n = ns[i]; i++){
  450.                 while((n = n.nextSibling)){
  451.                     if (n.nodeName == utag || n.nodeName == tagName || tagName == '*'){
  452.                         result[++ri] = n;
  453.                     }
  454.                 }
  455.             }
  456.         }
  457.         return result;
  458.     };
  459.     function concat(a, b){
  460.         if(b.slice){
  461.             return a.concat(b);
  462.         }
  463.         for(var i = 0, l = b.length; i < l; i++){
  464.             a[a.length] = b[i];
  465.         }
  466.         return a;
  467.     }
  468.     function byTag(cs, tagName){
  469.         if(cs.tagName || cs == document){
  470.             cs = [cs];
  471.         }
  472.         if(!tagName){
  473.             return cs;
  474.         }
  475.         var r = [], ri = -1;
  476.         tagName = tagName.toLowerCase();
  477.         for(var i = 0, ci; ci = cs[i]; i++){
  478.             if(ci.nodeType == 1 && ci.tagName.toLowerCase()==tagName){
  479.                 r[++ri] = ci;
  480.             }
  481.         }
  482.         return r;
  483.     };
  484.     function byId(cs, attr, id){
  485.         if(cs.tagName || cs == document){
  486.             cs = [cs];
  487.         }
  488.         if(!id){
  489.             return cs;
  490.         }
  491.         var r = [], ri = -1;
  492.         for(var i = 0,ci; ci = cs[i]; i++){
  493.             if(ci && ci.id == id){
  494.                 r[++ri] = ci;
  495.                 return r;
  496.             }
  497.         }
  498.         return r;
  499.     };
  500.     function byAttribute(cs, attr, value, op, custom){
  501.         var r = [], 
  502.          ri = -1, 
  503.          st = custom=="{",
  504.          f = Ext.DomQuery.operators[op];
  505.         for(var i = 0, ci; ci = cs[i]; i++){
  506.             if(ci.nodeType != 1){
  507.                 continue;
  508.             }
  509.             var a;
  510.             if(st){
  511.                 a = Ext.DomQuery.getStyle(ci, attr);
  512.             }
  513.             else if(attr == "class" || attr == "className"){
  514.                 a = ci.className;
  515.             }else if(attr == "for"){
  516.                 a = ci.htmlFor;
  517.             }else if(attr == "href"){
  518.                 a = ci.getAttribute("href", 2);
  519.             }else{
  520.                 a = ci.getAttribute(attr);
  521.             }
  522.             if((f && f(a, value)) || (!f && a)){
  523.                 r[++ri] = ci;
  524.             }
  525.         }
  526.         return r;
  527.     };
  528.     function byPseudo(cs, name, value){
  529.         return Ext.DomQuery.pseudos[name](cs, value);
  530.     };
  531.     function nodupIEXml(cs){
  532.         var d = ++key, 
  533.          r;
  534.         cs[0].setAttribute("_nodup", d);
  535.         r = [cs[0]];
  536.         for(var i = 1, len = cs.length; i < len; i++){
  537.             var c = cs[i];
  538.             if(!c.getAttribute("_nodup") != d){
  539.                 c.setAttribute("_nodup", d);
  540.                 r[r.length] = c;
  541.             }
  542.         }
  543.         for(var i = 0, len = cs.length; i < len; i++){
  544.             cs[i].removeAttribute("_nodup");
  545.         }
  546.         return r;
  547.     }
  548.     function nodup(cs){
  549.         if(!cs){
  550.             return [];
  551.         }
  552.         var len = cs.length, c, i, r = cs, cj, ri = -1;
  553.         if(!len || typeof cs.nodeType != "undefined" || len == 1){
  554.             return cs;
  555.         }
  556.         if(isIE && typeof cs[0].selectSingleNode != "undefined"){
  557.             return nodupIEXml(cs);
  558.         }
  559.         var d = ++key;
  560.         cs[0]._nodup = d;
  561.         for(i = 1; c = cs[i]; i++){
  562.             if(c._nodup != d){
  563.                 c._nodup = d;
  564.             }else{
  565.                 r = [];
  566.                 for(var j = 0; j < i; j++){
  567.                     r[++ri] = cs[j];
  568.                 }
  569.                 for(j = i+1; cj = cs[j]; j++){
  570.                     if(cj._nodup != d){
  571.                         cj._nodup = d;
  572.                         r[++ri] = cj;
  573.                     }
  574.                 }
  575.                 return r;
  576.             }
  577.         }
  578.         return r;
  579.     }
  580.     function quickDiffIEXml(c1, c2){
  581.         var d = ++key,
  582.          r = [];
  583.         for(var i = 0, len = c1.length; i < len; i++){
  584.             c1[i].setAttribute("_qdiff", d);
  585.         }        
  586.         for(var i = 0, len = c2.length; i < len; i++){
  587.             if(c2[i].getAttribute("_qdiff") != d){
  588.                 r[r.length] = c2[i];
  589.             }
  590.         }
  591.         for(var i = 0, len = c1.length; i < len; i++){
  592.            c1[i].removeAttribute("_qdiff");
  593.         }
  594.         return r;
  595.     }
  596.     function quickDiff(c1, c2){
  597.         var len1 = c1.length,
  598.          d = ++key,
  599.          r = [];
  600.         if(!len1){
  601.             return c2;
  602.         }
  603.         if(isIE && c1[0].selectSingleNode){
  604.             return quickDiffIEXml(c1, c2);
  605.         }        
  606.         for(var i = 0; i < len1; i++){
  607.             c1[i]._qdiff = d;
  608.         }        
  609.         for(var i = 0, len = c2.length; i < len; i++){
  610.             if(c2[i]._qdiff != d){
  611.                 r[r.length] = c2[i];
  612.             }
  613.         }
  614.         return r;
  615.     }
  616.     function quickId(ns, mode, root, id){
  617.         if(ns == root){
  618.            var d = root.ownerDocument || root;
  619.            return d.getElementById(id);
  620.         }
  621.         ns = getNodes(ns, mode, "*");
  622.         return byId(ns, null, id);
  623.     }
  624.     return {
  625.         getStyle : function(el, name){
  626.             return Ext.fly(el).getStyle(name);
  627.         },
  628.         /**
  629.          * Compiles a selector/xpath query into a reusable function. The returned function
  630.          * takes one parameter "root" (optional), which is the context node from where the query should start.
  631.          * @param {String} selector The selector/xpath query
  632.          * @param {String} type (optional) Either "select" (the default) or "simple" for a simple selector match
  633.          * @return {Function}
  634.          */
  635.         compile : function(path, type){
  636.             type = type || "select";
  637.             var fn = ["var f = function(root){n var mode; ++batch; var n = root || document;n"],
  638.              q = path, mode, lq,
  639.              tk = Ext.DomQuery.matchers,
  640.              tklen = tk.length,
  641.              mm,
  642.              // accept leading mode switch
  643.              lmode = q.match(modeRe);
  644.             
  645.             if(lmode && lmode[1]){
  646.                 fn[fn.length] = 'mode="'+lmode[1].replace(trimRe, "")+'";';
  647.                 q = q.replace(lmode[1], "");
  648.             }
  649.             // strip leading slashes
  650.             while(path.substr(0, 1)=="/"){
  651.                 path = path.substr(1);
  652.             }
  653.             while(q && lq != q){
  654.                 lq = q;
  655.                 var tm = q.match(tagTokenRe);
  656.                 if(type == "select"){
  657.                     if(tm){
  658.                         if(tm[1] == "#"){
  659.                             fn[fn.length] = 'n = quickId(n, mode, root, "'+tm[2]+'");';
  660.                         }else{
  661.                             fn[fn.length] = 'n = getNodes(n, mode, "'+tm[2]+'");';
  662.                         }
  663.                         q = q.replace(tm[0], "");
  664.                     }else if(q.substr(0, 1) != '@'){
  665.                         fn[fn.length] = 'n = getNodes(n, mode, "*");';
  666.                     }
  667.                 }else{
  668.                     if(tm){
  669.                         if(tm[1] == "#"){
  670.                             fn[fn.length] = 'n = byId(n, null, "'+tm[2]+'");';
  671.                         }else{
  672.                             fn[fn.length] = 'n = byTag(n, "'+tm[2]+'");';
  673.                         }
  674.                         q = q.replace(tm[0], "");
  675.                     }
  676.                 }
  677.                 while(!(mm = q.match(modeRe))){
  678.                     var matched = false;
  679.                     for(var j = 0; j < tklen; j++){
  680.                         var t = tk[j];
  681.                         var m = q.match(t.re);
  682.                         if(m){
  683.                             fn[fn.length] = t.select.replace(tplRe, function(x, i){
  684.                                                     return m[i];
  685.                                                 });
  686.                             q = q.replace(m[0], "");
  687.                             matched = true;
  688.                             break;
  689.                         }
  690.                     }
  691.                     // prevent infinite loop on bad selector
  692.                     if(!matched){
  693.                         throw 'Error parsing selector, parsing failed at "' + q + '"';
  694.                     }
  695.                 }
  696.                 if(mm[1]){
  697.                     fn[fn.length] = 'mode="'+mm[1].replace(trimRe, "")+'";';
  698.                     q = q.replace(mm[1], "");
  699.                 }
  700.             }
  701.             fn[fn.length] = "return nodup(n);n}";
  702.             eval(fn.join(""));
  703.             return f;
  704.         },
  705.         /**
  706.          * Selects a group of elements.
  707.          * @param {String} selector The selector/xpath query (can be a comma separated list of selectors)
  708.          * @param {Node} root (optional) The start of the query (defaults to document).
  709.          * @return {Array} An Array of DOM elements which match the selector. If there are
  710.          * no matches, and empty Array is returned.
  711.          */
  712.         select : function(path, root, type){
  713.             if(!root || root == document){
  714.                 root = document;
  715.             }
  716.             if(typeof root == "string"){
  717.                 root = document.getElementById(root);
  718.             }
  719.             var paths = path.split(","),
  720.              results = [];
  721.             for(var i = 0, len = paths.length; i < len; i++){
  722.                 var p = paths[i].replace(trimRe, "");
  723.                 if(!cache[p]){
  724.                     cache[p] = Ext.DomQuery.compile(p);
  725.                     if(!cache[p]){
  726.                         throw p + " is not a valid selector";
  727.                     }
  728.                 }
  729.                 var result = cache[p](root);
  730.                 if(result && result != document){
  731.                     results = results.concat(result);
  732.                 }
  733.             }
  734.             if(paths.length > 1){
  735.                 return nodup(results);
  736.             }
  737.             return results;
  738.         },
  739.         /**
  740.          * Selects a single element.
  741.          * @param {String} selector The selector/xpath query
  742.          * @param {Node} root (optional) The start of the query (defaults to document).
  743.          * @return {Element} The DOM element which matched the selector.
  744.          */
  745.         selectNode : function(path, root){
  746.             return Ext.DomQuery.select(path, root)[0];
  747.         },
  748.         /**
  749.          * Selects the value of a node, optionally replacing null with the defaultValue.
  750.          * @param {String} selector The selector/xpath query
  751.          * @param {Node} root (optional) The start of the query (defaults to document).
  752.          * @param {String} defaultValue
  753.          * @return {String}
  754.          */
  755.         selectValue : function(path, root, defaultValue){
  756.             path = path.replace(trimRe, "");
  757.             if(!valueCache[path]){
  758.                 valueCache[path] = Ext.DomQuery.compile(path, "select");
  759.             }
  760.             var n = valueCache[path](root),
  761.              v;
  762.             n = n[0] ? n[0] : n;
  763.             v = (n && n.firstChild ? n.firstChild.nodeValue : null);
  764.             return ((v === null||v === undefined||v==='') ? defaultValue : v);
  765.         },
  766.         /**
  767.          * Selects the value of a node, parsing integers and floats. Returns the defaultValue, or 0 if none is specified.
  768.          * @param {String} selector The selector/xpath query
  769.          * @param {Node} root (optional) The start of the query (defaults to document).
  770.          * @param {Number} defaultValue
  771.          * @return {Number}
  772.          */
  773.         selectNumber : function(path, root, defaultValue){
  774.             var v = Ext.DomQuery.selectValue(path, root, defaultValue || 0);
  775.             return parseFloat(v);
  776.         },
  777.         /**
  778.          * Returns true if the passed element(s) match the passed simple selector (e.g. div.some-class or span:first-child)
  779.          * @param {String/HTMLElement/Array} el An element id, element or array of elements
  780.          * @param {String} selector The simple selector to test
  781.          * @return {Boolean}
  782.          */
  783.         is : function(el, ss){
  784.             if(typeof el == "string"){
  785.                 el = document.getElementById(el);
  786.             }
  787.             var isArray = Ext.isArray(el),
  788.              result = Ext.DomQuery.filter(isArray ? el : [el], ss);
  789.             return isArray ? (result.length == el.length) : (result.length > 0);
  790.         },
  791.         /**
  792.          * Filters an array of elements to only include matches of a simple selector (e.g. div.some-class or span:first-child)
  793.          * @param {Array} el An array of elements to filter
  794.          * @param {String} selector The simple selector to test
  795.          * @param {Boolean} nonMatches If true, it returns the elements that DON'T match
  796.          * the selector instead of the ones that match
  797.          * @return {Array} An Array of DOM elements which match the selector. If there are
  798.          * no matches, and empty Array is returned.
  799.          */
  800.         filter : function(els, ss, nonMatches){
  801.             ss = ss.replace(trimRe, "");
  802.             if(!simpleCache[ss]){
  803.                 simpleCache[ss] = Ext.DomQuery.compile(ss, "simple");
  804.             }
  805.             var result = simpleCache[ss](els);
  806.             return nonMatches ? quickDiff(result, els) : result;
  807.         },
  808.         /**
  809.          * Collection of matching regular expressions and code snippets.
  810.          */
  811.         matchers : [{
  812.                 re: /^.([w-]+)/,
  813.                 select: 'n = byClassName(n, null, " {1} ");'
  814.             }, {
  815.                 re: /^:([w-]+)(?:(((?:[^s>/]*|.*?))))?/,
  816.                 select: 'n = byPseudo(n, "{1}", "{2}");'
  817.             },{
  818.                 re: /^(?:([[{])(?:@)?([w-]+)s?(?:(=|.=)s?['"]?(.*?)["']?)?[]}])/,
  819.                 select: 'n = byAttribute(n, "{2}", "{4}", "{3}", "{1}");'
  820.             }, {
  821.                 re: /^#([w-]+)/,
  822.                 select: 'n = byId(n, null, "{1}");'
  823.             },{
  824.                 re: /^@([w-]+)/,
  825.                 select: 'return {firstChild:{nodeValue:attrValue(n, "{1}")}};'
  826.             }
  827.         ],
  828.         /**
  829.          * Collection of operator comparison functions. The default operators are =, !=, ^=, $=, *=, %=, |= and ~=.
  830.          * New operators can be added as long as the match the format <i>c</i>= where <i>c</i> is any character other than space, &gt; &lt;.
  831.          */
  832.         operators : {
  833.             "=" : function(a, v){
  834.                 return a == v;
  835.             },
  836.             "!=" : function(a, v){
  837.                 return a != v;
  838.             },
  839.             "^=" : function(a, v){
  840.                 return a && a.substr(0, v.length) == v;
  841.             },
  842.             "$=" : function(a, v){
  843.                 return a && a.substr(a.length-v.length) == v;
  844.             },
  845.             "*=" : function(a, v){
  846.                 return a && a.indexOf(v) !== -1;
  847.             },
  848.             "%=" : function(a, v){
  849.                 return (a % v) == 0;
  850.             },
  851.             "|=" : function(a, v){
  852.                 return a && (a == v || a.substr(0, v.length+1) == v+'-');
  853.             },
  854.             "~=" : function(a, v){
  855.                 return a && (' '+a+' ').indexOf(' '+v+' ') != -1;
  856.             }
  857.         },
  858.         /**
  859.          * Collection of "pseudo class" processors. Each processor is passed the current nodeset (array)
  860.          * and the argument (if any) supplied in the selector.
  861.          */
  862.         pseudos : {
  863.             "first-child" : function(c){
  864.                 var r = [], ri = -1, n;
  865.                 for(var i = 0, ci; ci = n = c[i]; i++){
  866.                     while((n = n.previousSibling) && n.nodeType != 1);
  867.                     if(!n){
  868.                         r[++ri] = ci;
  869.                     }
  870.                 }
  871.                 return r;
  872.             },
  873.             "last-child" : function(c){
  874.                 var r = [], ri = -1, n;
  875.                 for(var i = 0, ci; ci = n = c[i]; i++){
  876.                     while((n = n.nextSibling) && n.nodeType != 1);
  877.                     if(!n){
  878.                         r[++ri] = ci;
  879.                     }
  880.                 }
  881.                 return r;
  882.             },
  883.             "nth-child" : function(c, a) {
  884.                 var r = [], ri = -1,
  885.                  m = nthRe.exec(a == "even" && "2n" || a == "odd" && "2n+1" || !nthRe2.test(a) && "n+" + a || a),
  886.                  f = (m[1] || 1) - 0, l = m[2] - 0;
  887.                 for(var i = 0, n; n = c[i]; i++){
  888.                     var pn = n.parentNode;
  889.                     if (batch != pn._batch) {
  890.                         var j = 0;
  891.                         for(var cn = pn.firstChild; cn; cn = cn.nextSibling){
  892.                             if(cn.nodeType == 1){
  893.                                cn.nodeIndex = ++j;
  894.                             }
  895.                         }
  896.                         pn._batch = batch;
  897.                     }
  898.                     if (f == 1) {
  899.                         if (l == 0 || n.nodeIndex == l){
  900.                             r[++ri] = n;
  901.                         }
  902.                     } else if ((n.nodeIndex + l) % f == 0){
  903.                         r[++ri] = n;
  904.                     }
  905.                 }
  906.                 return r;
  907.             },
  908.             "only-child" : function(c){
  909.                 var r = [], ri = -1;;
  910.                 for(var i = 0, ci; ci = c[i]; i++){
  911.                     if(!prev(ci) && !next(ci)){
  912.                         r[++ri] = ci;
  913.                     }
  914.                 }
  915.                 return r;
  916.             },
  917.             "empty" : function(c){
  918.                 var r = [], ri = -1;
  919.                 for(var i = 0, ci; ci = c[i]; i++){
  920.                     var cns = ci.childNodes, j = 0, cn, empty = true;
  921.                     while(cn = cns[j]){
  922.                         ++j;
  923.                         if(cn.nodeType == 1 || cn.nodeType == 3){
  924.                             empty = false;
  925.                             break;
  926.                         }
  927.                     }
  928.                     if(empty){
  929.                         r[++ri] = ci;
  930.                     }
  931.                 }
  932.                 return r;
  933.             },
  934.             "contains" : function(c, v){
  935.                 var r = [], ri = -1;
  936.                 for(var i = 0, ci; ci = c[i]; i++){
  937.                     if((ci.textContent||ci.innerText||'').indexOf(v) != -1){
  938.                         r[++ri] = ci;
  939.                     }
  940.                 }
  941.                 return r;
  942.             },
  943.             "nodeValue" : function(c, v){
  944.                 var r = [], ri = -1;
  945.                 for(var i = 0, ci; ci = c[i]; i++){
  946.                     if(ci.firstChild && ci.firstChild.nodeValue == v){
  947.                         r[++ri] = ci;
  948.                     }
  949.                 }
  950.                 return r;
  951.             },
  952.             "checked" : function(c){
  953.                 var r = [], ri = -1;
  954.                 for(var i = 0, ci; ci = c[i]; i++){
  955.                     if(ci.checked == true){
  956.                         r[++ri] = ci;
  957.                     }
  958.                 }
  959.                 return r;
  960.             },
  961.             "not" : function(c, ss){
  962.                 return Ext.DomQuery.filter(c, ss, true);
  963.             },
  964.             "any" : function(c, selectors){
  965.                 var ss = selectors.split('|'),
  966.                  r = [], ri = -1, s;
  967.                 for(var i = 0, ci; ci = c[i]; i++){
  968.                     for(var j = 0; s = ss[j]; j++){
  969.                         if(Ext.DomQuery.is(ci, s)){
  970.                             r[++ri] = ci;
  971.                             break;
  972.                         }
  973.                     }
  974.                 }
  975.                 return r;
  976.             },
  977.             "odd" : function(c){
  978.                 return this["nth-child"](c, "odd");
  979.             },
  980.             "even" : function(c){
  981.                 return this["nth-child"](c, "even");
  982.             },
  983.             "nth" : function(c, a){
  984.                 return c[a-1] || [];
  985.             },
  986.             "first" : function(c){
  987.                 return c[0] || [];
  988.             },
  989.             "last" : function(c){
  990.                 return c[c.length-1] || [];
  991.             },
  992.             "has" : function(c, ss){
  993.                 var s = Ext.DomQuery.select,
  994.                  r = [], ri = -1;
  995.                 for(var i = 0, ci; ci = c[i]; i++){
  996.                     if(s(ss, ci).length > 0){
  997.                         r[++ri] = ci;
  998.                     }
  999.                 }
  1000.                 return r;
  1001.             },
  1002.             "next" : function(c, ss){
  1003.                 var is = Ext.DomQuery.is,
  1004.                  r = [], ri = -1;
  1005.                 for(var i = 0, ci; ci = c[i]; i++){
  1006.                     var n = next(ci);
  1007.                     if(n && is(n, ss)){
  1008.                         r[++ri] = ci;
  1009.                     }
  1010.                 }
  1011.                 return r;
  1012.             },
  1013.             "prev" : function(c, ss){
  1014.                 var is = Ext.DomQuery.is,
  1015.                  r = [], ri = -1;
  1016.                 for(var i = 0, ci; ci = c[i]; i++){
  1017.                     var n = prev(ci);
  1018.                     if(n && is(n, ss)){
  1019.                         r[++ri] = ci;
  1020.                     }
  1021.                 }
  1022.                 return r;
  1023.             }
  1024.         }
  1025.     };
  1026. }();
  1027. /**
  1028.  * Selects an array of DOM nodes by CSS/XPath selector. Shorthand of {@link Ext.DomQuery#select}
  1029.  * @param {String} path The selector/xpath query
  1030.  * @param {Node} root (optional) The start of the query (defaults to document).
  1031.  * @return {Array}
  1032.  * @member Ext
  1033.  * @method query
  1034.  */
  1035. Ext.query = Ext.DomQuery.select;
  1036. (function(){ var EXTUTIL = Ext.util,     TOARRAY = Ext.toArray,     EACH = Ext.each,     ISOBJECT = Ext.isObject,     TRUE = true,     FALSE = false; /**  * @class Ext.util.Observable  * Base class that provides a common interface for publishing events. Subclasses are expected to  * to have a property "events" with all the events defined, and, optionally, a property "listeners"  * with configured listeners defined.<br>  * For example:  * <pre><code> Employee = Ext.extend(Ext.util.Observable, {     constructor: function(config){         this.name = config.name;         this.addEvents({             "fired" : true,             "quit" : true         });         // Copy configured listeners into *this* object so that the base class&#39;s         // constructor will add them.         this.listeners = config.listeners;         // Call our superclass constructor to complete construction process.         Employee.superclass.constructor.call(config)     } }); </code></pre>  * This could then be used like this:<pre><code> var newEmployee = new Employee({     name: employeeName,     listeners: {         quit: function() {             // By default, "this" will be the object that fired the event.             alert(this.name + " has quit!");         }     } }); </code></pre>  */ EXTUTIL.Observable = function(){     /**      * @cfg {Object} listeners (optional) <p>A config object containing one or more event handlers to be added to this      * object during initialization.  This should be a valid listeners config object as specified in the      * {@link #addListener} example for attaching multiple handlers at once.</p>      * <br><p><b><u>DOM events from ExtJs {@link Ext.Component Components}</u></b></p>      * <br><p>While <i>some</i> ExtJs Component classes export selected DOM events (e.g. "click", "mouseover" etc), this      * is usually only done when extra value can be added. For example the {@link Ext.DataView DataView}'s      * <b><code>{@link Ext.DataView#click click}</code></b> event passing the node clicked on. To access DOM      * events directly from a Component's HTMLElement, listeners must be added to the <i>{@link Ext.Component#getEl Element}</i> after the Component      * has been rendered. A plugin can simplify this step:<pre><code> // Plugin is configured with a listeners config object. // The Component is appended to the argument list of all handler functions. Ext.DomObserver = Ext.extend(Object, {     constructor: function(config) {         this.listeners = config.listeners ? config.listeners : config;     },     // Component passes itself into plugin&#39;s init method     init: function(c) {         var p, l = this.listeners;         for (p in l) {             if (Ext.isFunction(l[p])) {                 l[p] = this.createHandler(l[p], c);             } else {                 l[p].fn = this.createHandler(l[p].fn, c);             }         }         // Add the listeners to the Element immediately following the render call         c.render = c.render.{@link Function#createSequence createSequence}(function() {             var e = c.getEl();             if (e) {                 e.on(l);             }         });     },     createHandler: function(fn, c) {         return function(e) {             fn.call(this, e, c);         };     } }); var combo = new Ext.form.ComboBox({     // Collapse combo when its element is clicked on     plugins: [ new Ext.DomObserver({         click: function(evt, comp) {             comp.collapse();         }     })],     store: myStore,     typeAhead: true,     mode: 'local',     triggerAction: 'all' });      * </code></pre></p>      */     var me = this, e = me.events;     if(me.listeners){         me.on(me.listeners);         delete me.listeners;     }     me.events = e || {}; }; EXTUTIL.Observable.prototype = function(){     var filterOptRe = /^(?:scope|delay|buffer|single)$/, toLower = function(s){         return s.toLowerCase();     };     return {         /**          * <p>Fires the specified event with the passed parameters (minus the event name).</p>          * <p>An event may be set to bubble up an Observable parent hierarchy (See {@link Ext.Component#getBubbleTarget})          * by calling {@link #enableBubble}.</p>          * @param {String} eventName The name of the event to fire.          * @param {Object...} args Variable number of parameters are passed to handlers.          * @return {Boolean} returns false if any of the handlers return false otherwise it returns true.          */         fireEvent : function(){             var a = TOARRAY(arguments),                 ename = toLower(a[0]),                 me = this,                 ret = TRUE,                 ce = me.events[ename],                 q,                 c;             if (me.eventsSuspended === TRUE) {                 if (q = me.suspendedEventsQueue) {                     q.push(a);                 }             }             else if(ISOBJECT(ce) && ce.bubble){                 if(ce.fire.apply(ce, a.slice(1)) === FALSE) {                     return FALSE;                 }                 c = me.getBubbleTarget && me.getBubbleTarget();                 if(c && c.enableBubble) {                     c.enableBubble(ename);                     return c.fireEvent.apply(c, a);                 }             }             else {                 if (ISOBJECT(ce)) {                     a.shift();                     ret = ce.fire.apply(ce, a);                 }             }             return ret;         },         /**          * Appends an event handler to this object.          * @param {String}   eventName The name of the event to listen for.          * @param {Function} handler The method the event invokes.          * @param {Object}   scope (optional) The scope (<code><b>this</b></code> reference) in which the handler function is executed.          * <b>If omitted, defaults to the object which fired the event.</b>          * @param {Object}   options (optional) An object containing handler configuration.          * properties. This may contain any of the following properties:<ul>          * <li><b>scope</b> : Object<div class="sub-desc">The scope (<code><b>this</b></code> reference) in which the handler function is executed.          * <b>If omitted, defaults to the object which fired the event.</b></div></li>          * <li><b>delay</b> : Number<div class="sub-desc">The number of milliseconds to delay the invocation of the handler after the event fires.</div></li>          * <li><b>single</b> : Boolean<div class="sub-desc">True to add a handler to handle just the next firing of the event, and then remove itself.</div></li>          * <li><b>buffer</b> : Number<div class="sub-desc">Causes the handler to be scheduled to run in an {@link Ext.util.DelayedTask} delayed          * by the specified number of milliseconds. If the event fires again within that time, the original          * handler is <em>not</em> invoked, but the new handler is scheduled in its place.</div></li>          * <li><b>target</b> : Observable<div class="sub-desc">Only call the handler if the event was fired on the target Observable, <i>not</i>          * if the event was bubbled up from a child Observable.</div></li>          * </ul><br>          * <p>          * <b>Combining Options</b><br>          * Using the options argument, it is possible to combine different types of listeners:<br>          * <br>          * A delayed, one-time listener.          * <pre><code> myDataView.on('click', this.onClick, this, {     single: true,     delay: 100 });</code></pre>          * <p>          * <b>Attaching multiple handlers in 1 call</b><br>          * The method also allows for a single argument to be passed which is a config object containing properties          * which specify multiple handlers.          * <p>          * <pre><code> myGridPanel.on({     'click' : {         fn: this.onClick,         scope: this,         delay: 100     },     'mouseover' : {         fn: this.onMouseOver,         scope: this     },     'mouseout' : {         fn: this.onMouseOut,         scope: this     } });</code></pre>      * <p>      * Or a shorthand syntax:<br>      * <pre><code> myGridPanel.on({     'click' : this.onClick,     'mouseover' : this.onMouseOver,     'mouseout' : this.onMouseOut,      scope: this });</code></pre>          */         addListener : function(eventName, fn, scope, o){             var me = this,                 e,                 oe,                 isF,             ce;             if (ISOBJECT(eventName)) {                 o = eventName;                 for (e in o){                     oe = o[e];                     if (!filterOptRe.test(e)) {                         me.addListener(e, oe.fn || oe, oe.scope || o.scope, oe.fn ? oe : o);                     }                 }             } else {                 eventName = toLower(eventName);                 ce = me.events[eventName] || TRUE;                 if (typeof ce == "boolean") {                     me.events[eventName] = ce = new EXTUTIL.Event(me, eventName);                 }                 ce.addListener(fn, scope, ISOBJECT(o) ? o : {});             }         },         /**          * Removes an event handler.          * @param {String}   eventName The type of event the handler was associated with.          * @param {Function} handler   The handler to remove. <b>This must be a reference to the function passed into the {@link #addListener} call.</b>          * @param {Object}   scope     (optional) The scope originally specified for the handler.          */         removeListener : function(eventName, fn, scope){             var ce = this.events[toLower(eventName)];             if (ISOBJECT(ce)) {                 ce.removeListener(fn, scope);             }         },         /**          * Removes all listeners for this object          */         purgeListeners : function(){             var events = this.events,                 evt,                 key;             for(key in events){                 evt = events[key];                 if(ISOBJECT(evt)){                     evt.clearListeners();                 }             }         },         /**          * Used to define events on this Observable          * @param {Object} object The object with the events defined          */         addEvents : function(o){             var me = this;             me.events = me.events || {};             if (typeof o == 'string') {                 EACH(arguments, function(a) {                     me.events[a] = me.events[a] || TRUE;                 });             } else {                 Ext.applyIf(me.events, o);             }         },         /**          * Checks to see if this object has any listeners for a specified event          * @param {String} eventName The name of the event to check for          * @return {Boolean} True if the event is being listened for, else false          */         hasListener : function(eventName){             var e = this.events[eventName];             return ISOBJECT(e) && e.listeners.length > 0;         },         /**          * Suspend the firing of all events. (see {@link #resumeEvents})          * @param {Boolean} queueSuspended Pass as true to queue up suspended events to be fired          * after the {@link #resumeEvents} call instead of discarding all suspended events;          */         suspendEvents : function(queueSuspended){             this.eventsSuspended = TRUE;             if (queueSuspended){                 this.suspendedEventsQueue = [];             }         },         /**          * Resume firing events. (see {@link #suspendEvents})          * If events were suspended using the <tt><b>queueSuspended</b></tt> parameter, then all          * events fired during event suspension will be sent to any listeners now.          */         resumeEvents : function(){             var me = this;             me.eventsSuspended = !delete me.suspendedEventQueue;             EACH(me.suspendedEventsQueue, function(e) {                 me.fireEvent.apply(me, e);             });         }     } }(); var OBSERVABLE = EXTUTIL.Observable.prototype; /**  * Appends an event handler to this object (shorthand for {@link #addListener}.)  * @param {String}   eventName     The type of event to listen for  * @param {Function} handler       The method the event invokes  * @param {Object}   scope         (optional) The scope (<code><b>this</b></code> reference) in which the handler function is executed.  * <b>If omitted, defaults to the object which fired the event.</b>  * @param {Object}   options       (optional) An object containing handler configuration.  * @method  */ OBSERVABLE.on = OBSERVABLE.addListener; /**  * Removes an event handler (shorthand for {@link #removeListener}.)  * @param {String}   eventName     The type of event the handler was associated with.  * @param {Function} handler       The handler to remove. <b>This must be a reference to the function passed into the {@link #addListener} call.</b>  * @param {Object}   scope         (optional) The scope originally specified for the handler.  * @method  */ OBSERVABLE.un = OBSERVABLE.removeListener; /**  * Removes <b>all</b> added captures from the Observable.  * @param {Observable} o The Observable to release  * @static  */ EXTUTIL.Observable.releaseCapture = function(o){     o.fireEvent = OBSERVABLE.fireEvent; }; function createTargeted(h, o, scope){     return function(){         if(o.target == arguments[0]){             h.apply(scope, TOARRAY(arguments));         }     }; }; function createBuffered(h, o, scope){     var task = new EXTUTIL.DelayedTask();     return function(){         task.delay(o.buffer, h, scope, TOARRAY(arguments));     }; } function createSingle(h, e, fn, scope){     return function(){         e.removeListener(fn, scope);         return h.apply(scope, arguments);     }; } function createDelayed(h, o, scope){     return function(){         var args = TOARRAY(arguments);         (function(){             h.apply(scope, args);         }).defer(o.delay || 10);     }; }; EXTUTIL.Event = function(obj, name){     this.name = name;     this.obj = obj;     this.listeners = []; }; EXTUTIL.Event.prototype = {     addListener : function(fn, scope, options){         var me = this,             l;         scope = scope || me.obj;         if(!me.isListening(fn, scope)){             l = me.createListener(fn, scope, options);             if(me.firing){ // if we are currently firing this event, don't disturb the listener loop                 me.listeners = me.listeners.slice(0);             }             me.listeners.push(l);         }     },     createListener: function(fn, scope, o){         o = o || {}, scope = scope || this.obj;         var l = {             fn: fn,             scope: scope,             options: o         }, h = fn;         if(o.target){             h = createTargeted(h, o, scope);         }         if(o.delay){             h = createDelayed(h, o, scope);         }         if(o.single){             h = createSingle(h, this, fn, scope);         }         if(o.buffer){             h = createBuffered(h, o, scope);         }         l.fireFn = h;         return l;     },     findListener : function(fn, scope){         var s, ret = -1;         EACH(this.listeners, function(l, i) {             s = l.scope;             if(l.fn == fn && (s == scope || s == this.obj)){                 ret = i;                 return FALSE;             }         },         this);         return ret;     },     isListening : function(fn, scope){         return this.findListener(fn, scope) != -1;     },     removeListener : function(fn, scope){         var index,             me = this,             ret = FALSE;         if((index = me.findListener(fn, scope)) != -1){             if (me.firing) {                 me.listeners = me.listeners.slice(0);             }             me.listeners.splice(index, 1);             ret = TRUE;         }         return ret;     },     clearListeners : function(){         this.listeners = [];     },     fire : function(){         var me = this,             args = TOARRAY(arguments),             ret = TRUE;         EACH(me.listeners, function(l) {             me.firing = TRUE;             if (l.fireFn.apply(l.scope || me.obj || window, args) === FALSE) {                 return ret = me.firing = FALSE;             }         });         me.firing = FALSE;         return ret;     } }; })();/**
  1037.  * @class Ext.util.Observable
  1038.  */
  1039. Ext.apply(Ext.util.Observable.prototype, function(){    
  1040.     // this is considered experimental (along with beforeMethod, afterMethod, removeMethodListener?)
  1041.     // allows for easier interceptor and sequences, including cancelling and overwriting the return value of the call
  1042.     // private
  1043.     function getMethodEvent(method){
  1044.         var e = (this.methodEvents = this.methodEvents ||
  1045.         {})[method], returnValue, v, cancel, obj = this;
  1046.         
  1047.         if (!e) {
  1048.             this.methodEvents[method] = e = {};
  1049.             e.originalFn = this[method];
  1050.             e.methodName = method;
  1051.             e.before = [];
  1052.             e.after = [];
  1053.             
  1054.             var makeCall = function(fn, scope, args){
  1055.                 if (!Ext.isEmpty(v = fn.apply(scope || obj, args))) {
  1056.                     if (Ext.isObject(v)) {
  1057.                         returnValue = !Ext.isEmpty(v.returnValue) ? v.returnValue : v;
  1058.                         cancel = !!v.cancel;
  1059.                     }
  1060.                     else 
  1061.                         if (v === false) {
  1062.                             cancel = true;
  1063.                         }
  1064.                         else {
  1065.                             returnValue = v;
  1066.                         }
  1067.                 }
  1068.             };
  1069.             
  1070.             this[method] = function(){
  1071.                 var args = Ext.toArray(arguments);
  1072.                 returnValue = v = undefined;
  1073.                 cancel = false;
  1074.                 
  1075.                 Ext.each(e.before, function(b){
  1076.                     makeCall(b.fn, b.scope, args);
  1077.                     if (cancel) {
  1078.                         return returnValue;
  1079.                     }
  1080.                 });
  1081.                 
  1082.                 if (!Ext.isEmpty(v = e.originalFn.apply(obj, args))) {
  1083.                     returnValue = v;
  1084.                 }
  1085.                 Ext.each(e.after, function(a){
  1086.                     makeCall(a.fn, a.scope, args);
  1087.                     if (cancel) {
  1088.                         return returnValue;
  1089.                     }
  1090.                 });
  1091.                 return returnValue;
  1092.             };
  1093.         }
  1094.         return e;
  1095.     }
  1096.     
  1097.     return {
  1098.         // these are considered experimental
  1099.         // allows for easier interceptor and sequences, including cancelling and overwriting the return value of the call
  1100.         // adds an "interceptor" called before the original method
  1101.         beforeMethod: function(method, fn, scope){
  1102.             getMethodEvent.call(this, method).before.push({
  1103.                 fn: fn,
  1104.                 scope: scope
  1105.             });
  1106.         },
  1107.         
  1108.         // adds a "sequence" called after the original method
  1109.         afterMethod: function(method, fn, scope){
  1110.             getMethodEvent.call(this, method).after.push({
  1111.                 fn: fn,
  1112.                 scope: scope
  1113.             });
  1114.         },
  1115.         
  1116.         removeMethodListener: function(method, fn, scope){
  1117.             var e = getMethodEvent.call(this, method), found = false;
  1118.             Ext.each(e.before, function(b, i, arr){
  1119.                 if (b.fn == fn && b.scope == scope) {
  1120.                     arr.splice(i, 1);
  1121.                     found = true;
  1122.                     return false;
  1123.                 }
  1124.             });
  1125.             if (!found) {
  1126.                 Ext.each(e.after, function(a, i, arr){
  1127.                     if (a.fn == fn && a.scope == scope) {
  1128.                         arr.splice(i, 1);
  1129.                         return false;
  1130.                     }
  1131.                 });
  1132.             }
  1133.         },
  1134.         
  1135.         /**
  1136.          * Relays selected events from the specified Observable as if the events were fired by <tt><b>this</b></tt>.
  1137.          * @param {Object} o The Observable whose events this object is to relay.
  1138.          * @param {Array} events Array of event names to relay.
  1139.          */
  1140.         relayEvents: function(o, events){
  1141.             var me = this;
  1142.             function createHandler(ename){
  1143.                 return function(){
  1144.                     return me.fireEvent.apply(me, [ename].concat(Ext.toArray(arguments)));
  1145.                 };
  1146.             }
  1147.             Ext.each(events, function(ename){
  1148.                 me.events[ename] = me.events[ename] || true;
  1149.                 o.on(ename, createHandler(ename), me);
  1150.             });
  1151.         },
  1152.         
  1153.         /**
  1154.          * Used to enable bubbling of events
  1155.          * @param {Object} events
  1156.          */
  1157.         enableBubble: function(events){
  1158.             var me = this;
  1159.             events = Ext.isArray(events) ? events : Ext.toArray(arguments);
  1160.             Ext.each(events, function(ename){
  1161.                 ename = ename.toLowerCase();
  1162.                 var ce = me.events[ename] || true;
  1163.                 if (typeof ce == "boolean") {
  1164.                     ce = new Ext.util.Event(me, ename);
  1165.                     me.events[ename] = ce;
  1166.                 }
  1167.                 ce.bubble = true;
  1168.             });
  1169.         }
  1170.     };
  1171. }());
  1172. /**
  1173.  * Starts capture on the specified Observable. All events will be passed
  1174.  * to the supplied function with the event name + standard signature of the event
  1175.  * <b>before</b> the event is fired. If the supplied function returns false,
  1176.  * the event will not fire.
  1177.  * @param {Observable} o The Observable to capture
  1178.  * @param {Function} fn The function to call
  1179.  * @param {Object} scope (optional) The scope (this object) for the fn
  1180.  * @static
  1181.  */
  1182. Ext.util.Observable.capture = function(o, fn, scope){
  1183.     o.fireEvent = o.fireEvent.createInterceptor(fn, scope);
  1184. };
  1185. /**
  1186.  * Sets observability on the passed class constructor.<p>
  1187.  * <p>This makes any event fired on any instance of the passed class also fire a single event through
  1188.  * the <i>class</i> allowing for central handling of events on many instances at once.</p>
  1189.  * <p>Usage:</p><pre><code>
  1190. Ext.util.Observable.observeClass(Ext.data.Connection);
  1191. Ext.data.Connection.on('beforerequest', function(con, options) {
  1192.     console.log("Ajax request made to " + options.url);
  1193. });</code></pre>
  1194.  * @param {Function} c The class constructor to make observable.
  1195.  * @static
  1196.  */
  1197. Ext.util.Observable.observeClass = function(c){
  1198.     Ext.apply(c, new Ext.util.Observable());
  1199.     c.prototype.fireEvent = function(){
  1200.         return (c.fireEvent.apply(c, arguments) !== false) &&
  1201.         (Ext.util.Observable.prototype.fireEvent.apply(this, arguments) !== false);
  1202.     };
  1203. };/**  * @class Ext.EventManager  * Registers event handlers that want to receive a normalized EventObject instead of the standard browser event and provides  * several useful events directly.  * See {@link Ext.EventObject} for more details on normalized event objects.  * @singleton  */ Ext.EventManager = function(){     var docReadyEvent,       docReadyProcId,       docReadyState = false,          E = Ext.lib.Event,      D = Ext.lib.Dom,      DOC = document,      WINDOW = window,      IEDEFERED = "ie-deferred-loader",      DOMCONTENTLOADED = "DOMContentLoaded",      elHash = {},      propRe = /^(?:scope|delay|buffer|single|stopEvent|preventDefault|stopPropagation|normalized|args|delegate)$/;     /// There is some jquery work around stuff here that isn't needed in Ext Core.     function addListener(el, ename, fn, wrap, scope){              var id = Ext.id(el),          es = elHash[id] = elHash[id] || {};                      (es[ename] = es[ename] || []).push([fn, wrap, scope]);         E.on(el, ename, wrap);         // this is a workaround for jQuery and should somehow be removed from Ext Core in the future         // without breaking ExtJS.         if(ename == "mousewheel" && el.addEventListener){ // workaround for jQuery          var args = ["DOMMouseScroll", wrap, false];          el.addEventListener.apply(el, args);             E.on(window, 'unload', function(){             el.removeEventListener.apply(el, args);                             });         }         if(ename == "mousedown" && el == document){ // fix stopped mousedowns on the document             Ext.EventManager.stoppedMouseDownEvent.addListener(wrap);         }     };          function fireDocReady(){         if(!docReadyState){                         Ext.isReady = docReadyState = true;             if(docReadyProcId){                 clearInterval(docReadyProcId);             }             if(Ext.isGecko || Ext.isOpera) {                 DOC.removeEventListener(DOMCONTENTLOADED, fireDocReady, false);             }             if(Ext.isIE){                 var defer = DOC.getElementById(IEDEFERED);                 if(defer){                     defer.onreadystatechange = null;                     defer.parentNode.removeChild(defer);                 }             }             if(docReadyEvent){                 docReadyEvent.fire();                 docReadyEvent.clearListeners();             }         }     };     function initDocReady(){     var COMPLETE = "complete";              docReadyEvent = new Ext.util.Event();         if (Ext.isGecko || Ext.isOpera) {             DOC.addEventListener(DOMCONTENTLOADED, fireDocReady, false);         } else if (Ext.isIE){             DOC.write("<s"+'cript id=' + IEDEFERED + ' defer="defer" src="/'+'/:"></s'+"cript>");                         DOC.getElementById(IEDEFERED).onreadystatechange = function(){                 if(this.readyState == COMPLETE){                     fireDocReady();                 }             };         } else if (Ext.isWebKit){             docReadyProcId = setInterval(function(){                                 if(DOC.readyState == COMPLETE) {                     fireDocReady();                  }             }, 10);         }         // no matter what, make sure it fires on load         E.on(WINDOW, "load", fireDocReady);     };     function createTargeted(h, o){         return function(){         var args = Ext.toArray(arguments);             if(o.target == Ext.EventObject.setEvent(args[0]).target){                 h.apply(this, args);             }         };     };              function createBuffered(h, o){         var task = new Ext.util.DelayedTask(h);         return function(e){             // create new event object impl so new events don't wipe out properties                         task.delay(o.buffer, h, null, [new Ext.EventObjectImpl(e)]);         };     };     function createSingle(h, el, ename, fn, scope){         return function(e){             Ext.EventManager.removeListener(el, ename, fn, scope);             h(e);         };     };     function createDelayed(h, o){         return function(e){             // create new event object impl so new events don't wipe out properties                e = new Ext.EventObjectImpl(e);             setTimeout(function(){                 h(e);             }, o.delay || 10);         };     };     function listen(element, ename, opt, fn, scope){         var o = !Ext.isObject(opt) ? {} : opt,          el = Ext.getDom(element);                  fn = fn || o.fn;          scope = scope || o.scope;                  if(!el){             throw "Error listening for "" + ename + '". Element "' + element + '" doesn't exist.';         }         function h(e){             // prevent errors while unload occurring             if(!Ext){// !window[xname]){  ==> can't we do this?                  return;             }             e = Ext.EventObject.setEvent(e);             var t;             if (o.delegate) {                 if(!(t = e.getTarget(o.delegate, el))){                     return;                 }             } else {                 t = e.target;             }                         if (o.stopEvent) {                 e.stopEvent();             }             if (o.preventDefault) {                e.preventDefault();             }             if (o.stopPropagation) {                 e.stopPropagation();             }             if (o.normalized) {                 e = e.browserEvent;             }                          fn.call(scope || el, e, t, o);         };         if(o.target){             h = createTargeted(h, o);         }         if(o.delay){             h = createDelayed(h, o);         }         if(o.single){             h = createSingle(h, el, ename, fn, scope);         }         if(o.buffer){             h = createBuffered(h, o);         }         addListener(el, ename, fn, h, scope);         return h;     };     var pub = {     /**      * Appends an event handler to an element.  The shorthand version {@link #on} is equivalent.  Typically you will      * use {@link Ext.Element#addListener} directly on an Element in favor of calling this version.      * @param {String/HTMLElement} el The html element or id to assign the event handler to      * @param {String} eventName The type of event to listen for      * @param {Function} handler The handler function the event invokes This function is passed      * the following parameters:<ul>      * <li>evt : EventObject<div class="sub-desc">The {@link Ext.EventObject EventObject} describing the event.</div></li>      * <li>t : Element<div class="sub-desc">The {@link Ext.Element Element} which was the target of the event.      * Note that this may be filtered by using the <tt>delegate</tt> option.</div></li>      * <li>o : Object<div class="sub-desc">The options object from the addListener call.</div></li>      * </ul>      * @param {Object} scope (optional) The scope (<b><code>this</code></b> reference) in which the handler function is executed. <b>Defaults to the Element</b>.      * @param {Object} options (optional) An object containing handler configuration properties.      * This may contain any of the following properties:<ul>      * <li>scope : Object<div class="sub-desc">The scope (<b><code>this</code></b> reference) in which the handler function is executed. <b>Defaults to the Element</b>.</div></li>      * <li>delegate : String<div class="sub-desc">A simple selector to filter the target or look for a descendant of the target</div></li>      * <li>stopEvent : Boolean<div class="sub-desc">True to stop the event. That is stop propagation, and prevent the default action.</div></li>      * <li>preventDefault : Boolean<div class="sub-desc">True to prevent the default action</div></li>      * <li>stopPropagation : Boolean<div class="sub-desc">True to prevent event propagation</div></li>      * <li>normalized : Boolean<div class="sub-desc">False to pass a browser event to the handler function instead of an Ext.EventObject</div></li>      * <li>delay : Number<div class="sub-desc">The number of milliseconds to delay the invocation of the handler after te event fires.</div></li>      * <li>single : Boolean<div class="sub-desc">True to add a handler to handle just the next firing of the event, and then remove itself.</div></li>      * <li>buffer : Number<div class="sub-desc">Causes the handler to be scheduled to run in an {@link Ext.util.DelayedTask} delayed      * by the specified number of milliseconds. If the event fires again within that time, the original      * handler is <em>not</em> invoked, but the new handler is scheduled in its place.</div></li>      * <li>target : Element<div class="sub-desc">Only call the handler if the event was fired on the target Element, <i>not</i> if the event was bubbled up from a child node.</div></li>      * </ul><br>      * <p>See {@link Ext.Element#addListener} for examples of how to use these options.</p>      */ addListener : function(element, eventName, fn, scope, options){                               if(Ext.isObject(eventName)){                             var o = eventName, e, val;                 for(e in o){                 val = o[e];                     if(!propRe.test(e)){                                                           if(Ext.isFunction(val)){                         // shared options                         listen(element, e, o, val, o.scope);                     }else{                         // individual options                         listen(element, e, val);                     }                     }                 }             } else {              listen(element, eventName, options, fn, scope);          }         },                  /**          * Removes an event handler from an element.  The shorthand version {@link #un} is equivalent.  Typically          * you will use {@link Ext.Element#removeListener} directly on an Element in favor of calling this version.          * @param {String/HTMLElement} el The id or html element from which to remove the event          * @param {String} eventName The type of event          * @param {Function} fn The handler function to remove          */         removeListener : function(element, eventName, fn, scope){                         var el = Ext.getDom(element),                 id = Ext.id(el),              wrap;                        Ext.each((elHash[id] || {})[eventName], function (v,i,a) {     if (Ext.isArray(v) && v[0] == fn && (!scope || v[2] == scope)) {                           E.un(el, eventName, wrap = v[1]);         a.splice(i,1);         return false;                  }         });             // jQuery workaround that should be removed from Ext Core         if(eventName == "mousewheel" && el.addEventListener && wrap){             el.removeEventListener("DOMMouseScroll", wrap, false);         }                               if(eventName == "mousedown" && el == DOC && wrap){ // fix stopped mousedowns on the document             Ext.EventManager.stoppedMouseDownEvent.removeListener(wrap);         }         },                  /**          * Removes all event handers from an element.  Typically you will use {@link Ext.Element#removeAllListeners}          * directly on an Element in favor of calling this version.          * @param {String/HTMLElement} el The id or html element from which to remove the event          */         removeAll : function(el){         var id = Ext.id(el = Ext.getDom(el)),  es = elHash[id],  ename;                 for(ename in es){             if(es.hasOwnProperty(ename)){                                      Ext.each(es[ename], function(v) {                     E.un(el, ename, v.wrap);                                     });             }                     }         elHash[id] = null;                },         /**          * Fires when the document is ready (before onload and before images are loaded). Can be          * accessed shorthanded as Ext.onReady().          * @param {Function} fn The method the event invokes          * @param {Object} scope (optional) An object that becomes the scope of the handler          * @param {boolean} options (optional) An object containing standard {@link #addListener} options          */         onDocumentReady : function(fn, scope, options){             if(docReadyState){ // if it already fired                 docReadyEvent.addListener(fn, scope, options);                 docReadyEvent.fire();                 docReadyEvent.clearListeners();                            } else {                 if(!docReadyEvent) initDocReady();                 options = options || {};             options.delay = options.delay || 1;                          docReadyEvent.addListener(fn, scope, options);             }         },                  elHash : elHash        };      /**      * Appends an event handler to an element.  Shorthand for {@link #addListener}.      * @param {String/HTMLElement} el The html element or id to assign the event handler to      * @param {String} eventName The type of event to listen for      * @param {Function} handler The handler function the event invokes      * @param {Object} scope (optional) The scope in which to execute the handler      * function (the handler function's "this" context)      * @param {Object} options (optional) An object containing standard {@link #addListener} options      * @member Ext.EventManager      * @method on      */     pub.on = pub.addListener;     /**      * Removes an event handler from an element.  Shorthand for {@link #removeListener}.      * @param {String/HTMLElement} el The id or html element from which to remove the event      * @param {String} eventName The type of event      * @param {Function} fn The handler function to remove      * @return {Boolean} True if a listener was actually removed, else false      * @member Ext.EventManager      * @method un      */     pub.un = pub.removeListener;     pub.stoppedMouseDownEvent = new Ext.util.Event();     return pub; }(); /**   * Fires when the document is ready (before onload and before images are loaded).  Shorthand of {@link Ext.EventManager#onDocumentReady}.   * @param {Function} fn The method the event invokes   * @param {Object} scope An object that becomes the scope of the handler   * @param {boolean} options (optional) An object containing standard {@link #addListener} options   * @member Ext   * @method onReady  */ Ext.onReady = Ext.EventManager.onDocumentReady; //Initialize doc classes (function(){          var initExtCss = function(){         // find the body element         var bd = document.body || document.getElementsByTagName('body')[0];         if(!bd){ return false; }         var cls = [' ',                 Ext.isIE ? "ext-ie " + (Ext.isIE6 ? 'ext-ie6' : (Ext.isIE7 ? 'ext-ie7' : 'ext-ie8'))                 : Ext.isGecko ? "ext-gecko " + (Ext.isGecko2 ? 'ext-gecko2' : 'ext-gecko3')                 : Ext.isOpera ? "ext-opera"                 : Ext.isWebKit ? "ext-webkit" : ""];         if(Ext.isSafari){             cls.push("ext-safari " + (Ext.isSafari2 ? 'ext-safari2' : (Ext.isSafari3 ? 'ext-safari3' : 'ext-safari4')));         }else if(Ext.isChrome){             cls.push("ext-chrome");         }         if(Ext.isMac){             cls.push("ext-mac");         }         if(Ext.isLinux){             cls.push("ext-linux");         }         if(Ext.isStrict || Ext.isBorderBox){ // add to the parent to allow for selectors like ".ext-strict .ext-ie"             var p = bd.parentNode;             if(p){                 p.className += Ext.isStrict ? ' ext-strict' : ' ext-border-box';             }         }         bd.className += cls.join(' ');         return true;     }     if(!initExtCss()){         Ext.onReady(initExtCss);     } })(); /**  * @class Ext.EventObject  * Just as {@link Ext.Element} wraps around a native DOM node, Ext.EventObject   * wraps the browser's native event-object normalizing cross-browser differences,  * such as which mouse button is clicked, keys pressed, mechanisms to stop  * event-propagation along with a method to prevent default actions from taking place.  * <p>For example:</p>  * <pre><code> function handleClick(e, t){ // e is not a standard event object, it is a Ext.EventObject     e.preventDefault();     var target = e.getTarget(); // same as t (the target HTMLElement)     ... } var myDiv = {@link Ext#get Ext.get}("myDiv");  // get reference to an {@link Ext.Element} myDiv.on(         // 'on' is shorthand for addListener     "click",      // perform an action on click of myDiv     handleClick   // reference to the action handler );   // other methods to do the same: Ext.EventManager.on("myDiv", 'click', handleClick); Ext.EventManager.addListener("myDiv", 'click', handleClick);  </code></pre>  * @singleton  */ Ext.EventObject = function(){     var E = Ext.lib.Event,      // safari keypress events for special keys return bad keycodes      safariKeys = {         3 : 13, // enter         63234 : 37, // left         63235 : 39, // right         63232 : 38, // up         63233 : 40, // down         63276 : 33, // page up         63277 : 34, // page down         63272 : 46, // delete         63273 : 36, // home         63275 : 35  // end      },      // normalize button clicks      btnMap = Ext.isIE ? {1:0,4:1,2:2} :                 (Ext.isWebKit ? {1:0,2:1,3:2} : {0:0,1:1,2:2});     Ext.EventObjectImpl = function(e){         if(e){             this.setEvent(e.browserEvent || e);         }     };     Ext.EventObjectImpl.prototype = {            /** @private */         setEvent : function(e){         var me = this;             if(e == me || (e && e.browserEvent)){ // already wrapped                 return e;             }             me.browserEvent = e;             if(e){                 // normalize buttons                 me.button = e.button ? btnMap[e.button] : (e.which ? e.which - 1 : -1);                 if(e.type == 'click' && me.button == -1){                     me.button = 0;                 }                 me.type = e.type;                 me.shiftKey = e.shiftKey;                 // mac metaKey behaves like ctrlKey                 me.ctrlKey = e.ctrlKey || e.metaKey || false;                 me.altKey = e.altKey;                 // in getKey these will be normalized for the mac                 me.keyCode = e.keyCode;                 me.charCode = e.charCode;                 // cache the target for the delayed and or buffered events                 me.target = E.getTarget(e);                 // same for XY                 me.xy = E.getXY(e);             }else{                 me.button = -1;                 me.shiftKey = false;                 me.ctrlKey = false;                 me.altKey = false;                 me.keyCode = 0;                 me.charCode = 0;                 me.target = null;                 me.xy = [0, 0];             }             return me;         },         /**          * Stop the event (preventDefault and stopPropagation)          */         stopEvent : function(){         var me = this;             if(me.browserEvent){                 if(me.browserEvent.type == 'mousedown'){                     Ext.EventManager.stoppedMouseDownEvent.fire(me);                 }                 E.stopEvent(me.browserEvent);             }         },         /**          * Prevents the browsers default handling of the event.          */         preventDefault : function(){             if(this.browserEvent){                 E.preventDefault(this.browserEvent);             }         },                 /**          * Cancels bubbling of the event.          */         stopPropagation : function(){         var me = this;             if(me.browserEvent){                 if(me.browserEvent.type == 'mousedown'){                     Ext.EventManager.stoppedMouseDownEvent.fire(me);                 }                 E.stopPropagation(me.browserEvent);             }         },         /**          * Gets the character code for the event.          * @return {Number}          */         getCharCode : function(){             return this.charCode || this.keyCode;         },         /**          * Returns a normalized keyCode for the event.          * @return {Number} The key code          */         getKey : function(){             return this.normalizeKey(this.keyCode || this.charCode)         }, // private normalizeKey: function(k){ return Ext.isSafari ? (safariKeys[k] || k) : k;  },         /**          * Gets the x coordinate of the event.          * @return {Number}          */         getPageX : function(){             return this.xy[0];         },         /**          * Gets the y coordinate of the event.          * @return {Number}          */         getPageY : function(){             return this.xy[1];         },         /**          * Gets the page coordinates of the event.          * @return {Array} The xy values like [x, y]          */         getXY : function(){             return this.xy;         },         /**          * Gets the target for the event.          * @param {String} selector (optional) A simple selector to filter the target or look for an ancestor of the target          * @param {Number/Mixed} maxDepth (optional) The max depth to                 search as a number or element (defaults to 10 || document.body)          * @param {Boolean} returnEl (optional) True to return a Ext.Element object instead of DOM node          * @return {HTMLelement}          */         getTarget : function(selector, maxDepth, returnEl){             return selector ? Ext.fly(this.target).findParent(selector, maxDepth, returnEl) : (returnEl ? Ext.get(this.target) : this.target);         },         /**          * Gets the related target.          * @return {HTMLElement}          */         getRelatedTarget : function(){             return this.browserEvent ? E.getRelatedTarget(this.browserEvent) : null;         },         /**          * Normalizes mouse wheel delta across browsers          * @return {Number} The delta          */         getWheelDelta : function(){             var e = this.browserEvent;             var delta = 0;             if(e.wheelDelta){ /* IE/Opera. */                 delta = e.wheelDelta/120;             }else if(e.detail){ /* Mozilla case. */                 delta = -e.detail/3;             }             return delta;         }, /** * Returns true if the target of this event is a child of el.  Unless the allowEl parameter is set, it will return false if if the target is el. * Example usage:<pre><code> // Handle click on any child of an element Ext.getBody().on('click', function(e){ if(e.within('some-el')){ alert('Clicked on a child of some-el!'); } }); // Handle click directly on an element, ignoring clicks on child nodes Ext.getBody().on('click', function(e,t){ if((t.id == 'some-el') && !e.within(t, true)){ alert('Clicked directly on some-el!'); } }); </code></pre>  * @param {Mixed} el The id, DOM element or Ext.Element to check  * @param {Boolean} related (optional) true to test if the related target is within el instead of the target  * @param {Boolean} allowEl {optional} true to also check if the passed element is the target or related target  * @return {Boolean}  */ within : function(el, related, allowEl){             if(el){     var t = this[related ? "getRelatedTarget" : "getTarget"]();     return t && ((allowEl ? (t == Ext.getDom(el)) : false) || Ext.fly(el).contains(t));             }             return false; }  };     return new Ext.EventObjectImpl(); }();/**
  1204.  * @class Ext.EventManager
  1205.  */
  1206. Ext.apply(Ext.EventManager, function(){
  1207. var resizeEvent, 
  1208.      resizeTask, 
  1209.      textEvent, 
  1210.      textSize,
  1211.      D = Ext.lib.Dom,
  1212.      E = Ext.lib.Event,
  1213.      propRe = /^(?:scope|delay|buffer|single|stopEvent|preventDefault|stopPropagation|normalized|args|delegate)$/,
  1214.         curWidth = 0,
  1215.         curHeight = 0,
  1216.         // note 1: IE fires ONLY the keydown event on specialkey autorepeat
  1217.         // note 2: Safari < 3.1, Gecko (Mac/Linux) & Opera fire only the keypress event on specialkey autorepeat
  1218.         // (research done by @Jan Wolter at http://unixpapa.com/js/key.html)
  1219.         useKeydown = Ext.isSafari ? 
  1220.                     Ext.num(navigator.userAgent.toLowerCase().match(/version/(d+.d)/)[1] || 2) >= 3.1 :
  1221.                     !((Ext.isGecko && !Ext.isWindows) || Ext.isOpera);
  1222.       
  1223. return { 
  1224. // private
  1225.     doResizeEvent: function(){
  1226.             var h = D.getViewHeight(),
  1227.                 w = D.getViewWidth();
  1228.             
  1229.             //whacky problem in IE where the resize event will fire even though the w/h are the same.
  1230.             if(curHeight != h || curWidth != w){
  1231.                 resizeEvent.fire(curWidth = w, curHeight = h);
  1232.             }
  1233.     },
  1234.     
  1235.     /**
  1236.      * Fires when the window is resized and provides resize event buffering (50 milliseconds), passes new viewport width and height to handlers.
  1237.      * @param {Function} fn        The method the event invokes
  1238.      * @param {Object}   scope    An object that becomes the scope of the handler
  1239.      * @param {boolean}  options
  1240.      */
  1241.     onWindowResize : function(fn, scope, options){
  1242.         if(!resizeEvent){
  1243.             resizeEvent = new Ext.util.Event();
  1244.             resizeTask = new Ext.util.DelayedTask(this.doResizeEvent);
  1245.             E.on(window, "resize", this.fireWindowResize, this);
  1246.         }
  1247.         resizeEvent.addListener(fn, scope, options);
  1248.     },
  1249.     // exposed only to allow manual firing
  1250.     fireWindowResize : function(){
  1251.         if(resizeEvent){
  1252.             if((Ext.isIE||Ext.isAir) && resizeTask){
  1253.                 resizeTask.delay(50);
  1254.             }else{
  1255.                 resizeEvent.fire(D.getViewWidth(), D.getViewHeight());
  1256.             }
  1257.         }
  1258.     },
  1259.     /**
  1260.      * Fires when the user changes the active text size. Handler gets called with 2 params, the old size and the new size.
  1261.      * @param {Function} fn        The method the event invokes
  1262.      * @param {Object}   scope    An object that becomes the scope of the handler
  1263.      * @param {boolean}  options
  1264.      */
  1265.     onTextResize : function(fn, scope, options){
  1266.         if(!textEvent){
  1267.             textEvent = new Ext.util.Event();
  1268.             var textEl = new Ext.Element(document.createElement('div'));
  1269.             textEl.dom.className = 'x-text-resize';
  1270.             textEl.dom.innerHTML = 'X';
  1271.             textEl.appendTo(document.body);
  1272.             textSize = textEl.dom.offsetHeight;
  1273.             setInterval(function(){
  1274.                 if(textEl.dom.offsetHeight != textSize){
  1275.                     textEvent.fire(textSize, textSize = textEl.dom.offsetHeight);
  1276.                 }
  1277.             }, this.textResizeInterval);
  1278.         }
  1279.         textEvent.addListener(fn, scope, options);
  1280.     },
  1281.     /**
  1282.      * Removes the passed window resize listener.
  1283.      * @param {Function} fn        The method the event invokes
  1284.      * @param {Object}   scope    The scope of handler
  1285.      */
  1286.     removeResizeListener : function(fn, scope){
  1287.         if(resizeEvent){
  1288.             resizeEvent.removeListener(fn, scope);
  1289.         }
  1290.     },
  1291.     // private
  1292.     fireResize : function(){
  1293.         if(resizeEvent){
  1294.             resizeEvent.fire(D.getViewWidth(), D.getViewHeight());
  1295.         }
  1296.     },
  1297.     
  1298.      /**
  1299.      * The frequency, in milliseconds, to check for text resize events (defaults to 50)
  1300.      */
  1301.     textResizeInterval : 50,
  1302.     
  1303.     /**
  1304.          * Url used for onDocumentReady with using SSL (defaults to Ext.SSL_SECURE_URL)
  1305.          */
  1306.         ieDeferSrc : false,
  1307.         
  1308.         // protected for use inside the framework
  1309.         // detects whether we should use keydown or keypress based on the browser.
  1310.         useKeydown: useKeydown
  1311.     };
  1312. }());
  1313. Ext.EventManager.on = Ext.EventManager.addListener;
  1314. Ext.apply(Ext.EventObjectImpl.prototype, {
  1315.     /** Key constant @type Number */
  1316.     BACKSPACE: 8,
  1317.     /** Key constant @type Number */
  1318.     TAB: 9,
  1319.     /** Key constant @type Number */
  1320.     NUM_CENTER: 12,
  1321.     /** Key constant @type Number */
  1322.     ENTER: 13,
  1323.     /** Key constant @type Number */
  1324.     RETURN: 13,
  1325.     /** Key constant @type Number */
  1326.     SHIFT: 16,
  1327.     /** Key constant @type Number */
  1328.     CTRL: 17,
  1329.     CONTROL : 17, // legacy
  1330.     /** Key constant @type Number */
  1331.     ALT: 18,
  1332.     /** Key constant @type Number */
  1333.     PAUSE: 19,
  1334.     /** Key constant @type Number */
  1335.     CAPS_LOCK: 20,
  1336.     /** Key constant @type Number */
  1337.     ESC: 27,
  1338.     /** Key constant @type Number */
  1339.     SPACE: 32,
  1340.     /** Key constant @type Number */
  1341.     PAGE_UP: 33,
  1342.     PAGEUP : 33, // legacy
  1343.     /** Key constant @type Number */
  1344.     PAGE_DOWN: 34,
  1345.     PAGEDOWN : 34, // legacy
  1346.     /** Key constant @type Number */
  1347.     END: 35,
  1348.     /** Key constant @type Number */
  1349.     HOME: 36,
  1350.     /** Key constant @type Number */
  1351.     LEFT: 37,
  1352.     /** Key constant @type Number */
  1353.     UP: 38,
  1354.     /** Key constant @type Number */
  1355.     RIGHT: 39,
  1356.     /** Key constant @type Number */
  1357.     DOWN: 40,
  1358.     /** Key constant @type Number */
  1359.     PRINT_SCREEN: 44,
  1360.     /** Key constant @type Number */
  1361.     INSERT: 45,
  1362.     /** Key constant @type Number */
  1363.     DELETE: 46,
  1364.     /** Key constant @type Number */
  1365.     ZERO: 48,
  1366.     /** Key constant @type Number */
  1367.     ONE: 49,
  1368.     /** Key constant @type Number */
  1369.     TWO: 50,
  1370.     /** Key constant @type Number */
  1371.     THREE: 51,
  1372.     /** Key constant @type Number */
  1373.     FOUR: 52,
  1374.     /** Key constant @type Number */
  1375.     FIVE: 53,
  1376.     /** Key constant @type Number */
  1377.     SIX: 54,
  1378.     /** Key constant @type Number */
  1379.     SEVEN: 55,
  1380.     /** Key constant @type Number */
  1381.     EIGHT: 56,
  1382.     /** Key constant @type Number */
  1383.     NINE: 57,
  1384.     /** Key constant @type Number */
  1385.     A: 65,
  1386.     /** Key constant @type Number */
  1387.     B: 66,
  1388.     /** Key constant @type Number */
  1389.     C: 67,
  1390.     /** Key constant @type Number */
  1391.     D: 68,
  1392.     /** Key constant @type Number */
  1393.     E: 69,
  1394.     /** Key constant @type Number */
  1395.     F: 70,
  1396.     /** Key constant @type Number */
  1397.     G: 71,
  1398.     /** Key constant @type Number */
  1399.     H: 72,
  1400.     /** Key constant @type Number */
  1401.     I: 73,
  1402.     /** Key constant @type Number */
  1403.     J: 74,
  1404.     /** Key constant @type Number */
  1405.     K: 75,
  1406.     /** Key constant @type Number */
  1407.     L: 76,
  1408.     /** Key constant @type Number */
  1409.     M: 77,
  1410.     /** Key constant @type Number */
  1411.     N: 78,
  1412.     /** Key constant @type Number */
  1413.     O: 79,
  1414.     /** Key constant @type Number */
  1415.     P: 80,
  1416.     /** Key constant @type Number */
  1417.     Q: 81,
  1418.     /** Key constant @type Number */
  1419.     R: 82,
  1420.     /** Key constant @type Number */
  1421.     S: 83,
  1422.     /** Key constant @type Number */
  1423.     T: 84,
  1424.     /** Key constant @type Number */
  1425.     U: 85,
  1426.     /** Key constant @type Number */
  1427.     V: 86,
  1428.     /** Key constant @type Number */
  1429.     W: 87,
  1430.     /** Key constant @type Number */
  1431.     X: 88,
  1432.     /** Key constant @type Number */
  1433.     Y: 89,
  1434.     /** Key constant @type Number */
  1435.     Z: 90,
  1436.     /** Key constant @type Number */
  1437.     CONTEXT_MENU: 93,
  1438.     /** Key constant @type Number */
  1439.     NUM_ZERO: 96,
  1440.     /** Key constant @type Number */
  1441.     NUM_ONE: 97,
  1442.     /** Key constant @type Number */
  1443.     NUM_TWO: 98,
  1444.     /** Key constant @type Number */
  1445.     NUM_THREE: 99,
  1446.     /** Key constant @type Number */
  1447.     NUM_FOUR: 100,
  1448.     /** Key constant @type Number */
  1449.     NUM_FIVE: 101,
  1450.     /** Key constant @type Number */
  1451.     NUM_SIX: 102,
  1452.     /** Key constant @type Number */
  1453.     NUM_SEVEN: 103,
  1454.     /** Key constant @type Number */
  1455.     NUM_EIGHT: 104,
  1456.     /** Key constant @type Number */
  1457.     NUM_NINE: 105,
  1458.     /** Key constant @type Number */
  1459.     NUM_MULTIPLY: 106,
  1460.     /** Key constant @type Number */
  1461.     NUM_PLUS: 107,
  1462.     /** Key constant @type Number */
  1463.     NUM_MINUS: 109,
  1464.     /** Key constant @type Number */
  1465.     NUM_PERIOD: 110,
  1466.     /** Key constant @type Number */
  1467.     NUM_DIVISION: 111,
  1468.     /** Key constant @type Number */
  1469.     F1: 112,
  1470.     /** Key constant @type Number */
  1471.     F2: 113,
  1472.     /** Key constant @type Number */
  1473.     F3: 114,
  1474.     /** Key constant @type Number */
  1475.     F4: 115,
  1476.     /** Key constant @type Number */
  1477.     F5: 116,
  1478.     /** Key constant @type Number */
  1479.     F6: 117,
  1480.     /** Key constant @type Number */
  1481.     F7: 118,
  1482.     /** Key constant @type Number */
  1483.     F8: 119,
  1484.     /** Key constant @type Number */
  1485.     F9: 120,
  1486.     /** Key constant @type Number */
  1487.     F10: 121,
  1488.     /** Key constant @type Number */
  1489.     F11: 122,
  1490.     /** Key constant @type Number */
  1491.     F12: 123,
  1492.     
  1493.     /** @private */
  1494.     isNavKeyPress : function(){
  1495.         var me = this,
  1496.          k = this.normalizeKey(me.keyCode);
  1497.         return (k >= 33 && k <= 40) ||  // Page Up/Down, End, Home, Left, Up, Right, Down
  1498. k == me.RETURN ||
  1499. k == me.TAB ||
  1500. k == me.ESC;
  1501.     },
  1502.     isSpecialKey : function(){
  1503.         var k = this.normalizeKey(this.keyCode);
  1504.         return (this.type == 'keypress' && this.ctrlKey) ||
  1505. this.isNavKeyPress() ||
  1506.         (k == this.BACKSPACE) || // Backspace
  1507. (k >= 16 && k <= 20) || // Shift, Ctrl, Alt, Pause, Caps Lock
  1508. (k >= 44 && k <= 45);   // Print Screen, Insert
  1509.     },
  1510. getPoint : function(){
  1511.     return new Ext.lib.Point(this.xy[0], this.xy[1]);
  1512. },
  1513.     /**
  1514.      * Returns true if the control, meta, shift or alt key was pressed during this event.
  1515.      * @return {Boolean}
  1516.      */
  1517.     hasModifier : function(){
  1518.         return ((this.ctrlKey || this.altKey) || this.shiftKey);
  1519.     }
  1520. });/**
  1521.  * @class Ext.Element
  1522.  * <p>Encapsulates a DOM element, adding simple DOM manipulation facilities, normalizing for browser differences.</p>
  1523.  * <p>All instances of this class inherit the methods of {@link Ext.Fx} making visual effects easily available to all DOM elements.</p>
  1524.  * <p>Note that the events documented in this class are not Ext events, they encapsulate browser events. To
  1525.  * access the underlying browser event, see {@link Ext.EventObject#browserEvent}. Some older
  1526.  * browsers may not support the full range of events. Which events are supported is beyond the control of ExtJs.</p>
  1527.  * Usage:<br>
  1528. <pre><code>
  1529. // by id
  1530. var el = Ext.get("my-div");
  1531. // by DOM element reference
  1532. var el = Ext.get(myDivElement);
  1533. </code></pre>
  1534.  * <b>Animations</b><br />
  1535.  * <p>When an element is manipulated, by default there is no animation.</p>
  1536.  * <pre><code>
  1537. var el = Ext.get("my-div");
  1538. // no animation
  1539. el.setWidth(100);
  1540.  * </code></pre>
  1541.  * <p>Many of the functions for manipulating an element have an optional "animate" parameter.  This
  1542.  * parameter can be specified as boolean (<tt>true</tt>) for default animation effects.</p>
  1543.  * <pre><code>
  1544. // default animation
  1545. el.setWidth(100, true);
  1546.  * </code></pre>
  1547.  * 
  1548.  * <p>To configure the effects, an object literal with animation options to use as the Element animation
  1549.  * configuration object can also be specified. Note that the supported Element animation configuration
  1550.  * options are a subset of the {@link Ext.Fx} animation options specific to Fx effects.  The supported
  1551.  * Element animation configuration options are:</p>
  1552. <pre>
  1553. Option    Default   Description
  1554. --------- --------  ---------------------------------------------
  1555. {@link Ext.Fx#duration duration}  .35       The duration of the animation in seconds
  1556. {@link Ext.Fx#easing easing}    easeOut   The easing method
  1557. {@link Ext.Fx#callback callback}  none      A function to execute when the anim completes
  1558. {@link Ext.Fx#scope scope}     this      The scope (this) of the callback function
  1559. </pre>
  1560.  * 
  1561.  * <pre><code>