Forked mumble-django project from https://bitbucket.org/Svedrin/mumble-django
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

37063 lines
1.0 MiB

  1. /*
  2. * Ext JS Library 2.2.1
  3. * Copyright(c) 2006-2009, Ext JS, LLC.
  4. * licensing@extjs.com
  5. *
  6. * http://extjs.com/license
  7. */
  8. Ext.DomHelper = function(){
  9. var tempTableEl = null;
  10. var emptyTags = /^(?:br|frame|hr|img|input|link|meta|range|spacer|wbr|area|param|col)$/i;
  11. var tableRe = /^table|tbody|tr|td$/i;
  12. // build as innerHTML where available
  13. var createHtml = function(o){
  14. if(typeof o == 'string'){
  15. return o;
  16. }
  17. var b = "";
  18. if (Ext.isArray(o)) {
  19. for (var i = 0, l = o.length; i < l; i++) {
  20. b += createHtml(o[i]);
  21. }
  22. return b;
  23. }
  24. if(!o.tag){
  25. o.tag = "div";
  26. }
  27. b += "<" + o.tag;
  28. for(var attr in o){
  29. if(attr == "tag" || attr == "children" || attr == "cn" || attr == "html" || typeof o[attr] == "function") continue;
  30. if(attr == "style"){
  31. var s = o["style"];
  32. if(typeof s == "function"){
  33. s = s.call();
  34. }
  35. if(typeof s == "string"){
  36. b += ' style="' + s + '"';
  37. }else if(typeof s == "object"){
  38. b += ' style="';
  39. for(var key in s){
  40. if(typeof s[key] != "function"){
  41. b += key + ":" + s[key] + ";";
  42. }
  43. }
  44. b += '"';
  45. }
  46. }else{
  47. if(attr == "cls"){
  48. b += ' class="' + o["cls"] + '"';
  49. }else if(attr == "htmlFor"){
  50. b += ' for="' + o["htmlFor"] + '"';
  51. }else{
  52. b += " " + attr + '="' + o[attr] + '"';
  53. }
  54. }
  55. }
  56. if(emptyTags.test(o.tag)){
  57. b += "/>";
  58. }else{
  59. b += ">";
  60. var cn = o.children || o.cn;
  61. if(cn){
  62. b += createHtml(cn);
  63. } else if(o.html){
  64. b += o.html;
  65. }
  66. b += "</" + o.tag + ">";
  67. }
  68. return b;
  69. };
  70. // build as dom
  71. var createDom = function(o, parentNode){
  72. var el;
  73. if (Ext.isArray(o)) { // Allow Arrays of siblings to be inserted
  74. el = document.createDocumentFragment(); // in one shot using a DocumentFragment
  75. for(var i = 0, l = o.length; i < l; i++) {
  76. createDom(o[i], el);
  77. }
  78. } else if (typeof o == "string") { // Allow a string as a child spec.
  79. el = document.createTextNode(o);
  80. } else {
  81. el = document.createElement(o.tag||'div');
  82. var useSet = !!el.setAttribute; // In IE some elements don't have setAttribute
  83. for(var attr in o){
  84. if(attr == "tag" || attr == "children" || attr == "cn" || attr == "html" || attr == "style" || typeof o[attr] == "function") continue;
  85. if(attr=="cls"){
  86. el.className = o["cls"];
  87. }else{
  88. if(useSet) el.setAttribute(attr, o[attr]);
  89. else el[attr] = o[attr];
  90. }
  91. }
  92. Ext.DomHelper.applyStyles(el, o.style);
  93. var cn = o.children || o.cn;
  94. if(cn){
  95. createDom(cn, el);
  96. } else if(o.html){
  97. el.innerHTML = o.html;
  98. }
  99. }
  100. if(parentNode){
  101. parentNode.appendChild(el);
  102. }
  103. return el;
  104. };
  105. var ieTable = function(depth, s, h, e){
  106. tempTableEl.innerHTML = [s, h, e].join('');
  107. var i = -1, el = tempTableEl;
  108. while(++i < depth){
  109. el = el.firstChild;
  110. }
  111. return el;
  112. };
  113. // kill repeat to save bytes
  114. var ts = '<table>',
  115. te = '</table>',
  116. tbs = ts+'<tbody>',
  117. tbe = '</tbody>'+te,
  118. trs = tbs + '<tr>',
  119. tre = '</tr>'+tbe;
  120. var insertIntoTable = function(tag, where, el, html){
  121. if(!tempTableEl){
  122. tempTableEl = document.createElement('div');
  123. }
  124. var node;
  125. var before = null;
  126. if(tag == 'td'){
  127. if(where == 'afterbegin' || where == 'beforeend'){ // INTO a TD
  128. return;
  129. }
  130. if(where == 'beforebegin'){
  131. before = el;
  132. el = el.parentNode;
  133. } else{
  134. before = el.nextSibling;
  135. el = el.parentNode;
  136. }
  137. node = ieTable(4, trs, html, tre);
  138. }
  139. else if(tag == 'tr'){
  140. if(where == 'beforebegin'){
  141. before = el;
  142. el = el.parentNode;
  143. node = ieTable(3, tbs, html, tbe);
  144. } else if(where == 'afterend'){
  145. before = el.nextSibling;
  146. el = el.parentNode;
  147. node = ieTable(3, tbs, html, tbe);
  148. } else{ // INTO a TR
  149. if(where == 'afterbegin'){
  150. before = el.firstChild;
  151. }
  152. node = ieTable(4, trs, html, tre);
  153. }
  154. } else if(tag == 'tbody'){
  155. if(where == 'beforebegin'){
  156. before = el;
  157. el = el.parentNode;
  158. node = ieTable(2, ts, html, te);
  159. } else if(where == 'afterend'){
  160. before = el.nextSibling;
  161. el = el.parentNode;
  162. node = ieTable(2, ts, html, te);
  163. } else{
  164. if(where == 'afterbegin'){
  165. before = el.firstChild;
  166. }
  167. node = ieTable(3, tbs, html, tbe);
  168. }
  169. } else{ // TABLE
  170. if(where == 'beforebegin' || where == 'afterend'){ // OUTSIDE the table
  171. return;
  172. }
  173. if(where == 'afterbegin'){
  174. before = el.firstChild;
  175. }
  176. node = ieTable(2, ts, html, te);
  177. }
  178. el.insertBefore(node, before);
  179. return node;
  180. };
  181. return {
  182. useDom : false,
  183. markup : function(o){
  184. return createHtml(o);
  185. },
  186. applyStyles : function(el, styles){
  187. if(styles){
  188. el = Ext.fly(el);
  189. if(typeof styles == "string"){
  190. var re = /\s?([a-z\-]*)\:\s?([^;]*);?/gi;
  191. var matches;
  192. while ((matches = re.exec(styles)) != null){
  193. el.setStyle(matches[1], matches[2]);
  194. }
  195. }else if (typeof styles == "object"){
  196. for (var style in styles){
  197. el.setStyle(style, styles[style]);
  198. }
  199. }else if (typeof styles == "function"){
  200. Ext.DomHelper.applyStyles(el, styles.call());
  201. }
  202. }
  203. },
  204. insertHtml : function(where, el, html){
  205. where = where.toLowerCase();
  206. if(el.insertAdjacentHTML){
  207. if(tableRe.test(el.tagName)){
  208. var rs;
  209. if(rs = insertIntoTable(el.tagName.toLowerCase(), where, el, html)){
  210. return rs;
  211. }
  212. }
  213. switch(where){
  214. case "beforebegin":
  215. el.insertAdjacentHTML('BeforeBegin', html);
  216. return el.previousSibling;
  217. case "afterbegin":
  218. el.insertAdjacentHTML('AfterBegin', html);
  219. return el.firstChild;
  220. case "beforeend":
  221. el.insertAdjacentHTML('BeforeEnd', html);
  222. return el.lastChild;
  223. case "afterend":
  224. el.insertAdjacentHTML('AfterEnd', html);
  225. return el.nextSibling;
  226. }
  227. throw 'Illegal insertion point -> "' + where + '"';
  228. }
  229. var range = el.ownerDocument.createRange();
  230. var frag;
  231. switch(where){
  232. case "beforebegin":
  233. range.setStartBefore(el);
  234. frag = range.createContextualFragment(html);
  235. el.parentNode.insertBefore(frag, el);
  236. return el.previousSibling;
  237. case "afterbegin":
  238. if(el.firstChild){
  239. range.setStartBefore(el.firstChild);
  240. frag = range.createContextualFragment(html);
  241. el.insertBefore(frag, el.firstChild);
  242. return el.firstChild;
  243. }else{
  244. el.innerHTML = html;
  245. return el.firstChild;
  246. }
  247. case "beforeend":
  248. if(el.lastChild){
  249. range.setStartAfter(el.lastChild);
  250. frag = range.createContextualFragment(html);
  251. el.appendChild(frag);
  252. return el.lastChild;
  253. }else{
  254. el.innerHTML = html;
  255. return el.lastChild;
  256. }
  257. case "afterend":
  258. range.setStartAfter(el);
  259. frag = range.createContextualFragment(html);
  260. el.parentNode.insertBefore(frag, el.nextSibling);
  261. return el.nextSibling;
  262. }
  263. throw 'Illegal insertion point -> "' + where + '"';
  264. },
  265. insertBefore : function(el, o, returnElement){
  266. return this.doInsert(el, o, returnElement, "beforeBegin");
  267. },
  268. insertAfter : function(el, o, returnElement){
  269. return this.doInsert(el, o, returnElement, "afterEnd", "nextSibling");
  270. },
  271. insertFirst : function(el, o, returnElement){
  272. return this.doInsert(el, o, returnElement, "afterBegin", "firstChild");
  273. },
  274. // private
  275. doInsert : function(el, o, returnElement, pos, sibling){
  276. el = Ext.getDom(el);
  277. var newNode;
  278. if(this.useDom){
  279. newNode = createDom(o, null);
  280. (sibling === "firstChild" ? el : el.parentNode).insertBefore(newNode, sibling ? el[sibling] : el);
  281. }else{
  282. var html = createHtml(o);
  283. newNode = this.insertHtml(pos, el, html);
  284. }
  285. return returnElement ? Ext.get(newNode, true) : newNode;
  286. },
  287. append : function(el, o, returnElement){
  288. el = Ext.getDom(el);
  289. var newNode;
  290. if(this.useDom){
  291. newNode = createDom(o, null);
  292. el.appendChild(newNode);
  293. }else{
  294. var html = createHtml(o);
  295. newNode = this.insertHtml("beforeEnd", el, html);
  296. }
  297. return returnElement ? Ext.get(newNode, true) : newNode;
  298. },
  299. overwrite : function(el, o, returnElement){
  300. el = Ext.getDom(el);
  301. el.innerHTML = createHtml(o);
  302. return returnElement ? Ext.get(el.firstChild, true) : el.firstChild;
  303. },
  304. createTemplate : function(o){
  305. var html = createHtml(o);
  306. return new Ext.Template(html);
  307. }
  308. };
  309. }();
  310. Ext.Template = function(html){
  311. var a = arguments;
  312. if(Ext.isArray(html)){
  313. html = html.join("");
  314. }else if(a.length > 1){
  315. var buf = [];
  316. for(var i = 0, len = a.length; i < len; i++){
  317. if(typeof a[i] == 'object'){
  318. Ext.apply(this, a[i]);
  319. }else{
  320. buf[buf.length] = a[i];
  321. }
  322. }
  323. html = buf.join('');
  324. }
  325. this.html = html;
  326. if(this.compiled){
  327. this.compile();
  328. }
  329. };
  330. Ext.Template.prototype = {
  331. applyTemplate : function(values){
  332. if(this.compiled){
  333. return this.compiled(values);
  334. }
  335. var useF = this.disableFormats !== true;
  336. var fm = Ext.util.Format, tpl = this;
  337. var fn = function(m, name, format, args){
  338. if(format && useF){
  339. if(format.substr(0, 5) == "this."){
  340. return tpl.call(format.substr(5), values[name], values);
  341. }else{
  342. if(args){
  343. // quoted values are required for strings in compiled templates,
  344. // but for non compiled we need to strip them
  345. // quoted reversed for jsmin
  346. var re = /^\s*['"](.*)["']\s*$/;
  347. args = args.split(',');
  348. for(var i = 0, len = args.length; i < len; i++){
  349. args[i] = args[i].replace(re, "$1");
  350. }
  351. args = [values[name]].concat(args);
  352. }else{
  353. args = [values[name]];
  354. }
  355. return fm[format].apply(fm, args);
  356. }
  357. }else{
  358. return values[name] !== undefined ? values[name] : "";
  359. }
  360. };
  361. return this.html.replace(this.re, fn);
  362. },
  363. set : function(html, compile){
  364. this.html = html;
  365. this.compiled = null;
  366. if(compile){
  367. this.compile();
  368. }
  369. return this;
  370. },
  371. disableFormats : false,
  372. re : /\{([\w-]+)(?:\:([\w\.]*)(?:\((.*?)?\))?)?\}/g,
  373. compile : function(){
  374. var fm = Ext.util.Format;
  375. var useF = this.disableFormats !== true;
  376. var sep = Ext.isGecko ? "+" : ",";
  377. var fn = function(m, name, format, args){
  378. if(format && useF){
  379. args = args ? ',' + args : "";
  380. if(format.substr(0, 5) != "this."){
  381. format = "fm." + format + '(';
  382. }else{
  383. format = 'this.call("'+ format.substr(5) + '", ';
  384. args = ", values";
  385. }
  386. }else{
  387. args= ''; format = "(values['" + name + "'] == undefined ? '' : ";
  388. }
  389. return "'"+ sep + format + "values['" + name + "']" + args + ")"+sep+"'";
  390. };
  391. var body;
  392. // branched to use + in gecko and [].join() in others
  393. if(Ext.isGecko){
  394. body = "this.compiled = function(values){ return '" +
  395. this.html.replace(/\\/g, '\\\\').replace(/(\r\n|\n)/g, '\\n').replace(/'/g, "\\'").replace(this.re, fn) +
  396. "';};";
  397. }else{
  398. body = ["this.compiled = function(values){ return ['"];
  399. body.push(this.html.replace(/\\/g, '\\\\').replace(/(\r\n|\n)/g, '\\n').replace(/'/g, "\\'").replace(this.re, fn));
  400. body.push("'].join('');};");
  401. body = body.join('');
  402. }
  403. eval(body);
  404. return this;
  405. },
  406. // private function used to call members
  407. call : function(fnName, value, allValues){
  408. return this[fnName](value, allValues);
  409. },
  410. insertFirst: function(el, values, returnElement){
  411. return this.doInsert('afterBegin', el, values, returnElement);
  412. },
  413. insertBefore: function(el, values, returnElement){
  414. return this.doInsert('beforeBegin', el, values, returnElement);
  415. },
  416. insertAfter : function(el, values, returnElement){
  417. return this.doInsert('afterEnd', el, values, returnElement);
  418. },
  419. append : function(el, values, returnElement){
  420. return this.doInsert('beforeEnd', el, values, returnElement);
  421. },
  422. doInsert : function(where, el, values, returnEl){
  423. el = Ext.getDom(el);
  424. var newNode = Ext.DomHelper.insertHtml(where, el, this.applyTemplate(values));
  425. return returnEl ? Ext.get(newNode, true) : newNode;
  426. },
  427. overwrite : function(el, values, returnElement){
  428. el = Ext.getDom(el);
  429. el.innerHTML = this.applyTemplate(values);
  430. return returnElement ? Ext.get(el.firstChild, true) : el.firstChild;
  431. }
  432. };
  433. Ext.Template.prototype.apply = Ext.Template.prototype.applyTemplate;
  434. // backwards compat
  435. Ext.DomHelper.Template = Ext.Template;
  436. Ext.Template.from = function(el, config){
  437. el = Ext.getDom(el);
  438. return new Ext.Template(el.value || el.innerHTML, config || '');
  439. };
  440. Ext.DomQuery = function(){
  441. var cache = {}, simpleCache = {}, valueCache = {};
  442. var nonSpace = /\S/;
  443. var trimRe = /^\s+|\s+$/g;
  444. var tplRe = /\{(\d+)\}/g;
  445. var modeRe = /^(\s?[\/>+~]\s?|\s|$)/;
  446. var tagTokenRe = /^(#)?([\w-\*]+)/;
  447. var nthRe = /(\d*)n\+?(\d*)/, nthRe2 = /\D/;
  448. function child(p, index){
  449. var i = 0;
  450. var n = p.firstChild;
  451. while(n){
  452. if(n.nodeType == 1){
  453. if(++i == index){
  454. return n;
  455. }
  456. }
  457. n = n.nextSibling;
  458. }
  459. return null;
  460. };
  461. function next(n){
  462. while((n = n.nextSibling) && n.nodeType != 1);
  463. return n;
  464. };
  465. function prev(n){
  466. while((n = n.previousSibling) && n.nodeType != 1);
  467. return n;
  468. };
  469. function children(d){
  470. var n = d.firstChild, ni = -1;
  471. while(n){
  472. var nx = n.nextSibling;
  473. if(n.nodeType == 3 && !nonSpace.test(n.nodeValue)){
  474. d.removeChild(n);
  475. }else{
  476. n.nodeIndex = ++ni;
  477. }
  478. n = nx;
  479. }
  480. return this;
  481. };
  482. function byClassName(c, a, v){
  483. if(!v){
  484. return c;
  485. }
  486. var r = [], ri = -1, cn;
  487. for(var i = 0, ci; ci = c[i]; i++){
  488. if((' '+ci.className+' ').indexOf(v) != -1){
  489. r[++ri] = ci;
  490. }
  491. }
  492. return r;
  493. };
  494. function attrValue(n, attr){
  495. if(!n.tagName && typeof n.length != "undefined"){
  496. n = n[0];
  497. }
  498. if(!n){
  499. return null;
  500. }
  501. if(attr == "for"){
  502. return n.htmlFor;
  503. }
  504. if(attr == "class" || attr == "className"){
  505. return n.className;
  506. }
  507. return n.getAttribute(attr) || n[attr];
  508. };
  509. function getNodes(ns, mode, tagName){
  510. var result = [], ri = -1, cs;
  511. if(!ns){
  512. return result;
  513. }
  514. tagName = tagName || "*";
  515. if(typeof ns.getElementsByTagName != "undefined"){
  516. ns = [ns];
  517. }
  518. if(!mode){
  519. for(var i = 0, ni; ni = ns[i]; i++){
  520. cs = ni.getElementsByTagName(tagName);
  521. for(var j = 0, ci; ci = cs[j]; j++){
  522. result[++ri] = ci;
  523. }
  524. }
  525. }else if(mode == "/" || mode == ">"){
  526. var utag = tagName.toUpperCase();
  527. for(var i = 0, ni, cn; ni = ns[i]; i++){
  528. cn = ni.children || ni.childNodes;
  529. for(var j = 0, cj; cj = cn[j]; j++){
  530. if(cj.nodeName == utag || cj.nodeName == tagName || tagName == '*'){
  531. result[++ri] = cj;
  532. }
  533. }
  534. }
  535. }else if(mode == "+"){
  536. var utag = tagName.toUpperCase();
  537. for(var i = 0, n; n = ns[i]; i++){
  538. while((n = n.nextSibling) && n.nodeType != 1);
  539. if(n && (n.nodeName == utag || n.nodeName == tagName || tagName == '*')){
  540. result[++ri] = n;
  541. }
  542. }
  543. }else if(mode == "~"){
  544. for(var i = 0, n; n = ns[i]; i++){
  545. while((n = n.nextSibling) && (n.nodeType != 1 || (tagName == '*' || n.tagName.toLowerCase()!=tagName)));
  546. if(n){
  547. result[++ri] = n;
  548. }
  549. }
  550. }
  551. return result;
  552. };
  553. function concat(a, b){
  554. if(b.slice){
  555. return a.concat(b);
  556. }
  557. for(var i = 0, l = b.length; i < l; i++){
  558. a[a.length] = b[i];
  559. }
  560. return a;
  561. }
  562. function byTag(cs, tagName){
  563. if(cs.tagName || cs == document){
  564. cs = [cs];
  565. }
  566. if(!tagName){
  567. return cs;
  568. }
  569. var r = [], ri = -1;
  570. tagName = tagName.toLowerCase();
  571. for(var i = 0, ci; ci = cs[i]; i++){
  572. if(ci.nodeType == 1 && ci.tagName.toLowerCase()==tagName){
  573. r[++ri] = ci;
  574. }
  575. }
  576. return r;
  577. };
  578. function byId(cs, attr, id){
  579. if(cs.tagName || cs == document){
  580. cs = [cs];
  581. }
  582. if(!id){
  583. return cs;
  584. }
  585. var r = [], ri = -1;
  586. for(var i = 0,ci; ci = cs[i]; i++){
  587. if(ci && ci.id == id){
  588. r[++ri] = ci;
  589. return r;
  590. }
  591. }
  592. return r;
  593. };
  594. function byAttribute(cs, attr, value, op, custom){
  595. var r = [], ri = -1, st = custom=="{";
  596. var f = Ext.DomQuery.operators[op];
  597. for(var i = 0, ci; ci = cs[i]; i++){
  598. var a;
  599. if(st){
  600. a = Ext.DomQuery.getStyle(ci, attr);
  601. }
  602. else if(attr == "class" || attr == "className"){
  603. a = ci.className;
  604. }else if(attr == "for"){
  605. a = ci.htmlFor;
  606. }else if(attr == "href"){
  607. a = ci.getAttribute("href", 2);
  608. }else{
  609. a = ci.getAttribute(attr);
  610. }
  611. if((f && f(a, value)) || (!f && a)){
  612. r[++ri] = ci;
  613. }
  614. }
  615. return r;
  616. };
  617. function byPseudo(cs, name, value){
  618. return Ext.DomQuery.pseudos[name](cs, value);
  619. };
  620. // This is for IE MSXML which does not support expandos.
  621. // IE runs the same speed using setAttribute, however FF slows way down
  622. // and Safari completely fails so they need to continue to use expandos.
  623. var isIE = window.ActiveXObject ? true : false;
  624. // this eval is stop the compressor from
  625. // renaming the variable to something shorter
  626. eval("var batch = 30803;");
  627. var key = 30803;
  628. function nodupIEXml(cs){
  629. var d = ++key;
  630. cs[0].setAttribute("_nodup", d);
  631. var r = [cs[0]];
  632. for(var i = 1, len = cs.length; i < len; i++){
  633. var c = cs[i];
  634. if(!c.getAttribute("_nodup") != d){
  635. c.setAttribute("_nodup", d);
  636. r[r.length] = c;
  637. }
  638. }
  639. for(var i = 0, len = cs.length; i < len; i++){
  640. cs[i].removeAttribute("_nodup");
  641. }
  642. return r;
  643. }
  644. function nodup(cs){
  645. if(!cs){
  646. return [];
  647. }
  648. var len = cs.length, c, i, r = cs, cj, ri = -1;
  649. if(!len || typeof cs.nodeType != "undefined" || len == 1){
  650. return cs;
  651. }
  652. if(isIE && typeof cs[0].selectSingleNode != "undefined"){
  653. return nodupIEXml(cs);
  654. }
  655. var d = ++key;
  656. cs[0]._nodup = d;
  657. for(i = 1; c = cs[i]; i++){
  658. if(c._nodup != d){
  659. c._nodup = d;
  660. }else{
  661. r = [];
  662. for(var j = 0; j < i; j++){
  663. r[++ri] = cs[j];
  664. }
  665. for(j = i+1; cj = cs[j]; j++){
  666. if(cj._nodup != d){
  667. cj._nodup = d;
  668. r[++ri] = cj;
  669. }
  670. }
  671. return r;
  672. }
  673. }
  674. return r;
  675. }
  676. function quickDiffIEXml(c1, c2){
  677. var d = ++key;
  678. for(var i = 0, len = c1.length; i < len; i++){
  679. c1[i].setAttribute("_qdiff", d);
  680. }
  681. var r = [];
  682. for(var i = 0, len = c2.length; i < len; i++){
  683. if(c2[i].getAttribute("_qdiff") != d){
  684. r[r.length] = c2[i];
  685. }
  686. }
  687. for(var i = 0, len = c1.length; i < len; i++){
  688. c1[i].removeAttribute("_qdiff");
  689. }
  690. return r;
  691. }
  692. function quickDiff(c1, c2){
  693. var len1 = c1.length;
  694. if(!len1){
  695. return c2;
  696. }
  697. if(isIE && c1[0].selectSingleNode){
  698. return quickDiffIEXml(c1, c2);
  699. }
  700. var d = ++key;
  701. for(var i = 0; i < len1; i++){
  702. c1[i]._qdiff = d;
  703. }
  704. var r = [];
  705. for(var i = 0, len = c2.length; i < len; i++){
  706. if(c2[i]._qdiff != d){
  707. r[r.length] = c2[i];
  708. }
  709. }
  710. return r;
  711. }
  712. function quickId(ns, mode, root, id){
  713. if(ns == root){
  714. var d = root.ownerDocument || root;
  715. return d.getElementById(id);
  716. }
  717. ns = getNodes(ns, mode, "*");
  718. return byId(ns, null, id);
  719. }
  720. return {
  721. getStyle : function(el, name){
  722. return Ext.fly(el).getStyle(name);
  723. },
  724. compile : function(path, type){
  725. type = type || "select";
  726. var fn = ["var f = function(root){\n var mode; ++batch; var n = root || document;\n"];
  727. var q = path, mode, lq;
  728. var tk = Ext.DomQuery.matchers;
  729. var tklen = tk.length;
  730. var mm;
  731. // accept leading mode switch
  732. var lmode = q.match(modeRe);
  733. if(lmode && lmode[1]){
  734. fn[fn.length] = 'mode="'+lmode[1].replace(trimRe, "")+'";';
  735. q = q.replace(lmode[1], "");
  736. }
  737. // strip leading slashes
  738. while(path.substr(0, 1)=="/"){
  739. path = path.substr(1);
  740. }
  741. while(q && lq != q){
  742. lq = q;
  743. var tm = q.match(tagTokenRe);
  744. if(type == "select"){
  745. if(tm){
  746. if(tm[1] == "#"){
  747. fn[fn.length] = 'n = quickId(n, mode, root, "'+tm[2]+'");';
  748. }else{
  749. fn[fn.length] = 'n = getNodes(n, mode, "'+tm[2]+'");';
  750. }
  751. q = q.replace(tm[0], "");
  752. }else if(q.substr(0, 1) != '@'){
  753. fn[fn.length] = 'n = getNodes(n, mode, "*");';
  754. }
  755. }else{
  756. if(tm){
  757. if(tm[1] == "#"){
  758. fn[fn.length] = 'n = byId(n, null, "'+tm[2]+'");';
  759. }else{
  760. fn[fn.length] = 'n = byTag(n, "'+tm[2]+'");';
  761. }
  762. q = q.replace(tm[0], "");
  763. }
  764. }
  765. while(!(mm = q.match(modeRe))){
  766. var matched = false;
  767. for(var j = 0; j < tklen; j++){
  768. var t = tk[j];
  769. var m = q.match(t.re);
  770. if(m){
  771. fn[fn.length] = t.select.replace(tplRe, function(x, i){
  772. return m[i];
  773. });
  774. q = q.replace(m[0], "");
  775. matched = true;
  776. break;
  777. }
  778. }
  779. // prevent infinite loop on bad selector
  780. if(!matched){
  781. throw 'Error parsing selector, parsing failed at "' + q + '"';
  782. }
  783. }
  784. if(mm[1]){
  785. fn[fn.length] = 'mode="'+mm[1].replace(trimRe, "")+'";';
  786. q = q.replace(mm[1], "");
  787. }
  788. }
  789. fn[fn.length] = "return nodup(n);\n}";
  790. eval(fn.join(""));
  791. return f;
  792. },
  793. select : function(path, root, type){
  794. if(!root || root == document){
  795. root = document;
  796. }
  797. if(typeof root == "string"){
  798. root = document.getElementById(root);
  799. }
  800. var paths = path.split(",");
  801. var results = [];
  802. for(var i = 0, len = paths.length; i < len; i++){
  803. var p = paths[i].replace(trimRe, "");
  804. if(!cache[p]){
  805. cache[p] = Ext.DomQuery.compile(p);
  806. if(!cache[p]){
  807. throw p + " is not a valid selector";
  808. }
  809. }
  810. var result = cache[p](root);
  811. if(result && result != document){
  812. results = results.concat(result);
  813. }
  814. }
  815. if(paths.length > 1){
  816. return nodup(results);
  817. }
  818. return results;
  819. },
  820. selectNode : function(path, root){
  821. return Ext.DomQuery.select(path, root)[0];
  822. },
  823. selectValue : function(path, root, defaultValue){
  824. path = path.replace(trimRe, "");
  825. if(!valueCache[path]){
  826. valueCache[path] = Ext.DomQuery.compile(path, "select");
  827. }
  828. var n = valueCache[path](root);
  829. n = n[0] ? n[0] : n;
  830. var v = (n && n.firstChild ? n.firstChild.nodeValue : null);
  831. return ((v === null||v === undefined||v==='') ? defaultValue : v);
  832. },
  833. selectNumber : function(path, root, defaultValue){
  834. var v = Ext.DomQuery.selectValue(path, root, defaultValue || 0);
  835. return parseFloat(v);
  836. },
  837. is : function(el, ss){
  838. if(typeof el == "string"){
  839. el = document.getElementById(el);
  840. }
  841. var isArray = Ext.isArray(el);
  842. var result = Ext.DomQuery.filter(isArray ? el : [el], ss);
  843. return isArray ? (result.length == el.length) : (result.length > 0);
  844. },
  845. filter : function(els, ss, nonMatches){
  846. ss = ss.replace(trimRe, "");
  847. if(!simpleCache[ss]){
  848. simpleCache[ss] = Ext.DomQuery.compile(ss, "simple");
  849. }
  850. var result = simpleCache[ss](els);
  851. return nonMatches ? quickDiff(result, els) : result;
  852. },
  853. matchers : [{
  854. re: /^\.([\w-]+)/,
  855. select: 'n = byClassName(n, null, " {1} ");'
  856. }, {
  857. re: /^\:([\w-]+)(?:\(((?:[^\s>\/]*|.*?))\))?/,
  858. select: 'n = byPseudo(n, "{1}", "{2}");'
  859. },{
  860. re: /^(?:([\[\{])(?:@)?([\w-]+)\s?(?:(=|.=)\s?['"]?(.*?)["']?)?[\]\}])/,
  861. select: 'n = byAttribute(n, "{2}", "{4}", "{3}", "{1}");'
  862. }, {
  863. re: /^#([\w-]+)/,
  864. select: 'n = byId(n, null, "{1}");'
  865. },{
  866. re: /^@([\w-]+)/,
  867. select: 'return {firstChild:{nodeValue:attrValue(n, "{1}")}};'
  868. }
  869. ],
  870. operators : {
  871. "=" : function(a, v){
  872. return a == v;
  873. },
  874. "!=" : function(a, v){
  875. return a != v;
  876. },
  877. "^=" : function(a, v){
  878. return a && a.substr(0, v.length) == v;
  879. },
  880. "$=" : function(a, v){
  881. return a && a.substr(a.length-v.length) == v;
  882. },
  883. "*=" : function(a, v){
  884. return a && a.indexOf(v) !== -1;
  885. },
  886. "%=" : function(a, v){
  887. return (a % v) == 0;
  888. },
  889. "|=" : function(a, v){
  890. return a && (a == v || a.substr(0, v.length+1) == v+'-');
  891. },
  892. "~=" : function(a, v){
  893. return a && (' '+a+' ').indexOf(' '+v+' ') != -1;
  894. }
  895. },
  896. pseudos : {
  897. "first-child" : function(c){
  898. var r = [], ri = -1, n;
  899. for(var i = 0, ci; ci = n = c[i]; i++){
  900. while((n = n.previousSibling) && n.nodeType != 1);
  901. if(!n){
  902. r[++ri] = ci;
  903. }
  904. }
  905. return r;
  906. },
  907. "last-child" : function(c){
  908. var r = [], ri = -1, n;
  909. for(var i = 0, ci; ci = n = c[i]; i++){
  910. while((n = n.nextSibling) && n.nodeType != 1);
  911. if(!n){
  912. r[++ri] = ci;
  913. }
  914. }
  915. return r;
  916. },
  917. "nth-child" : function(c, a) {
  918. var r = [], ri = -1;
  919. var m = nthRe.exec(a == "even" && "2n" || a == "odd" && "2n+1" || !nthRe2.test(a) && "n+" + a || a);
  920. var f = (m[1] || 1) - 0, l = m[2] - 0;
  921. for(var i = 0, n; n = c[i]; i++){
  922. var pn = n.parentNode;
  923. if (batch != pn._batch) {
  924. var j = 0;
  925. for(var cn = pn.firstChild; cn; cn = cn.nextSibling){
  926. if(cn.nodeType == 1){
  927. cn.nodeIndex = ++j;
  928. }
  929. }
  930. pn._batch = batch;
  931. }
  932. if (f == 1) {
  933. if (l == 0 || n.nodeIndex == l){
  934. r[++ri] = n;
  935. }
  936. } else if ((n.nodeIndex + l) % f == 0){
  937. r[++ri] = n;
  938. }
  939. }
  940. return r;
  941. },
  942. "only-child" : function(c){
  943. var r = [], ri = -1;;
  944. for(var i = 0, ci; ci = c[i]; i++){
  945. if(!prev(ci) && !next(ci)){
  946. r[++ri] = ci;
  947. }
  948. }
  949. return r;
  950. },
  951. "empty" : function(c){
  952. var r = [], ri = -1;
  953. for(var i = 0, ci; ci = c[i]; i++){
  954. var cns = ci.childNodes, j = 0, cn, empty = true;
  955. while(cn = cns[j]){
  956. ++j;
  957. if(cn.nodeType == 1 || cn.nodeType == 3){
  958. empty = false;
  959. break;
  960. }
  961. }
  962. if(empty){
  963. r[++ri] = ci;
  964. }
  965. }
  966. return r;
  967. },
  968. "contains" : function(c, v){
  969. var r = [], ri = -1;
  970. for(var i = 0, ci; ci = c[i]; i++){
  971. if((ci.textContent||ci.innerText||'').indexOf(v) != -1){
  972. r[++ri] = ci;
  973. }
  974. }
  975. return r;
  976. },
  977. "nodeValue" : function(c, v){
  978. var r = [], ri = -1;
  979. for(var i = 0, ci; ci = c[i]; i++){
  980. if(ci.firstChild && ci.firstChild.nodeValue == v){
  981. r[++ri] = ci;
  982. }
  983. }
  984. return r;
  985. },
  986. "checked" : function(c){
  987. var r = [], ri = -1;
  988. for(var i = 0, ci; ci = c[i]; i++){
  989. if(ci.checked == true){
  990. r[++ri] = ci;
  991. }
  992. }
  993. return r;
  994. },
  995. "not" : function(c, ss){
  996. return Ext.DomQuery.filter(c, ss, true);
  997. },
  998. "any" : function(c, selectors){
  999. var ss = selectors.split('|');
  1000. var r = [], ri = -1, s;
  1001. for(var i = 0, ci; ci = c[i]; i++){
  1002. for(var j = 0; s = ss[j]; j++){
  1003. if(Ext.DomQuery.is(ci, s)){
  1004. r[++ri] = ci;
  1005. break;
  1006. }
  1007. }
  1008. }
  1009. return r;
  1010. },
  1011. "odd" : function(c){
  1012. return this["nth-child"](c, "odd");
  1013. },
  1014. "even" : function(c){
  1015. return this["nth-child"](c, "even");
  1016. },
  1017. "nth" : function(c, a){
  1018. return c[a-1] || [];
  1019. },
  1020. "first" : function(c){
  1021. return c[0] || [];
  1022. },
  1023. "last" : function(c){
  1024. return c[c.length-1] || [];
  1025. },
  1026. "has" : function(c, ss){
  1027. var s = Ext.DomQuery.select;
  1028. var r = [], ri = -1;
  1029. for(var i = 0, ci; ci = c[i]; i++){
  1030. if(s(ss, ci).length > 0){
  1031. r[++ri] = ci;
  1032. }
  1033. }
  1034. return r;
  1035. },
  1036. "next" : function(c, ss){
  1037. var is = Ext.DomQuery.is;
  1038. var r = [], ri = -1;
  1039. for(var i = 0, ci; ci = c[i]; i++){
  1040. var n = next(ci);
  1041. if(n && is(n, ss)){
  1042. r[++ri] = ci;
  1043. }
  1044. }
  1045. return r;
  1046. },
  1047. "prev" : function(c, ss){
  1048. var is = Ext.DomQuery.is;
  1049. var r = [], ri = -1;
  1050. for(var i = 0, ci; ci = c[i]; i++){
  1051. var n = prev(ci);
  1052. if(n && is(n, ss)){
  1053. r[++ri] = ci;
  1054. }
  1055. }
  1056. return r;
  1057. }
  1058. }
  1059. };
  1060. }();
  1061. Ext.query = Ext.DomQuery.select;
  1062. Ext.util.Observable = function(){
  1063. if(this.listeners){
  1064. this.on(this.listeners);
  1065. delete this.listeners;
  1066. }
  1067. };
  1068. Ext.util.Observable.prototype = {
  1069. fireEvent : function(){
  1070. if(this.eventsSuspended !== true){
  1071. var ce = this.events[arguments[0].toLowerCase()];
  1072. if(typeof ce == "object"){
  1073. return ce.fire.apply(ce, Array.prototype.slice.call(arguments, 1));
  1074. }
  1075. }
  1076. return true;
  1077. },
  1078. // private
  1079. filterOptRe : /^(?:scope|delay|buffer|single)$/,
  1080. addListener : function(eventName, fn, scope, o){
  1081. if(typeof eventName == "object"){
  1082. o = eventName;
  1083. for(var e in o){
  1084. if(this.filterOptRe.test(e)){
  1085. continue;
  1086. }
  1087. if(typeof o[e] == "function"){
  1088. // shared options
  1089. this.addListener(e, o[e], o.scope, o);
  1090. }else{
  1091. // individual options
  1092. this.addListener(e, o[e].fn, o[e].scope, o[e]);
  1093. }
  1094. }
  1095. return;
  1096. }
  1097. o = (!o || typeof o == "boolean") ? {} : o;
  1098. eventName = eventName.toLowerCase();
  1099. var ce = this.events[eventName] || true;
  1100. if(typeof ce == "boolean"){
  1101. ce = new Ext.util.Event(this, eventName);
  1102. this.events[eventName] = ce;
  1103. }
  1104. ce.addListener(fn, scope, o);
  1105. },
  1106. removeListener : function(eventName, fn, scope){
  1107. var ce = this.events[eventName.toLowerCase()];
  1108. if(typeof ce == "object"){
  1109. ce.removeListener(fn, scope);
  1110. }
  1111. },
  1112. purgeListeners : function(){
  1113. for(var evt in this.events){
  1114. if(typeof this.events[evt] == "object"){
  1115. this.events[evt].clearListeners();
  1116. }
  1117. }
  1118. },
  1119. relayEvents : function(o, events){
  1120. var createHandler = function(ename){
  1121. return function(){
  1122. return this.fireEvent.apply(this, Ext.combine(ename, Array.prototype.slice.call(arguments, 0)));
  1123. };
  1124. };
  1125. for(var i = 0, len = events.length; i < len; i++){
  1126. var ename = events[i];
  1127. if(!this.events[ename]){ this.events[ename] = true; };
  1128. o.on(ename, createHandler(ename), this);
  1129. }
  1130. },
  1131. addEvents : function(o){
  1132. if(!this.events){
  1133. this.events = {};
  1134. }
  1135. if(typeof o == 'string'){
  1136. for(var i = 0, a = arguments, v; v = a[i]; i++){
  1137. if(!this.events[a[i]]){
  1138. this.events[a[i]] = true;
  1139. }
  1140. }
  1141. }else{
  1142. Ext.applyIf(this.events, o);
  1143. }
  1144. },
  1145. hasListener : function(eventName){
  1146. var e = this.events[eventName];
  1147. return typeof e == "object" && e.listeners.length > 0;
  1148. },
  1149. suspendEvents : function(){
  1150. this.eventsSuspended = true;
  1151. },
  1152. resumeEvents : function(){
  1153. this.eventsSuspended = false;
  1154. },
  1155. // these are considered experimental
  1156. // allows for easier interceptor and sequences, including cancelling and overwriting the return value of the call
  1157. // private
  1158. getMethodEvent : function(method){
  1159. if(!this.methodEvents){
  1160. this.methodEvents = {};
  1161. }
  1162. var e = this.methodEvents[method];
  1163. if(!e){
  1164. e = {};
  1165. this.methodEvents[method] = e;
  1166. e.originalFn = this[method];
  1167. e.methodName = method;
  1168. e.before = [];
  1169. e.after = [];
  1170. var returnValue, v, cancel;
  1171. var obj = this;
  1172. var makeCall = function(fn, scope, args){
  1173. if((v = fn.apply(scope || obj, args)) !== undefined){
  1174. if(typeof v === 'object'){
  1175. if(v.returnValue !== undefined){
  1176. returnValue = v.returnValue;
  1177. }else{
  1178. returnValue = v;
  1179. }
  1180. if(v.cancel === true){
  1181. cancel = true;
  1182. }
  1183. }else if(v === false){
  1184. cancel = true;
  1185. }else {
  1186. returnValue = v;
  1187. }
  1188. }
  1189. }
  1190. this[method] = function(){
  1191. returnValue = v = undefined; cancel = false;
  1192. var args = Array.prototype.slice.call(arguments, 0);
  1193. for(var i = 0, len = e.before.length; i < len; i++){
  1194. makeCall(e.before[i].fn, e.before[i].scope, args);
  1195. if(cancel){
  1196. return returnValue;
  1197. }
  1198. }
  1199. if((v = e.originalFn.apply(obj, args)) !== undefined){
  1200. returnValue = v;
  1201. }
  1202. for(var i = 0, len = e.after.length; i < len; i++){
  1203. makeCall(e.after[i].fn, e.after[i].scope, args);
  1204. if(cancel){
  1205. return returnValue;
  1206. }
  1207. }
  1208. return returnValue;
  1209. };
  1210. }
  1211. return e;
  1212. },
  1213. // adds an "interceptor" called before the original method
  1214. beforeMethod : function(method, fn, scope){
  1215. var e = this.getMethodEvent(method);
  1216. e.before.push({fn: fn, scope: scope});
  1217. },
  1218. // adds a "sequence" called after the original method
  1219. afterMethod : function(method, fn, scope){
  1220. var e = this.getMethodEvent(method);
  1221. e.after.push({fn: fn, scope: scope});
  1222. },
  1223. removeMethodListener : function(method, fn, scope){
  1224. var e = this.getMethodEvent(method);
  1225. for(var i = 0, len = e.before.length; i < len; i++){
  1226. if(e.before[i].fn == fn && e.before[i].scope == scope){
  1227. e.before.splice(i, 1);
  1228. return;
  1229. }
  1230. }
  1231. for(var i = 0, len = e.after.length; i < len; i++){
  1232. if(e.after[i].fn == fn && e.after[i].scope == scope){
  1233. e.after.splice(i, 1);
  1234. return;
  1235. }
  1236. }
  1237. }
  1238. };
  1239. Ext.util.Observable.prototype.on = Ext.util.Observable.prototype.addListener;
  1240. Ext.util.Observable.prototype.un = Ext.util.Observable.prototype.removeListener;
  1241. Ext.util.Observable.capture = function(o, fn, scope){
  1242. o.fireEvent = o.fireEvent.createInterceptor(fn, scope);
  1243. };
  1244. Ext.util.Observable.releaseCapture = function(o){
  1245. o.fireEvent = Ext.util.Observable.prototype.fireEvent;
  1246. };
  1247. (function(){
  1248. var createBuffered = function(h, o, scope){
  1249. var task = new Ext.util.DelayedTask();
  1250. return function(){
  1251. task.delay(o.buffer, h, scope, Array.prototype.slice.call(arguments, 0));
  1252. };
  1253. };
  1254. var createSingle = function(h, e, fn, scope){
  1255. return function(){
  1256. e.removeListener(fn, scope);
  1257. return h.apply(scope, arguments);
  1258. };
  1259. };
  1260. var createDelayed = function(h, o, scope){
  1261. return function(){
  1262. var args = Array.prototype.slice.call(arguments, 0);
  1263. setTimeout(function(){
  1264. h.apply(scope, args);
  1265. }, o.delay || 10);
  1266. };
  1267. };
  1268. Ext.util.Event = function(obj, name){
  1269. this.name = name;
  1270. this.obj = obj;
  1271. this.listeners = [];
  1272. };
  1273. Ext.util.Event.prototype = {
  1274. addListener : function(fn, scope, options){
  1275. scope = scope || this.obj;
  1276. if(!this.isListening(fn, scope)){
  1277. var l = this.createListener(fn, scope, options);
  1278. if(!this.firing){
  1279. this.listeners.push(l);
  1280. }else{ // if we are currently firing this event, don't disturb the listener loop
  1281. this.listeners = this.listeners.slice(0);
  1282. this.listeners.push(l);
  1283. }
  1284. }
  1285. },
  1286. createListener : function(fn, scope, o){
  1287. o = o || {};
  1288. scope = scope || this.obj;
  1289. var l = {fn: fn, scope: scope, options: o};
  1290. var h = fn;
  1291. if(o.delay){
  1292. h = createDelayed(h, o, scope);
  1293. }
  1294. if(o.single){
  1295. h = createSingle(h, this, fn, scope);
  1296. }
  1297. if(o.buffer){
  1298. h = createBuffered(h, o, scope);
  1299. }
  1300. l.fireFn = h;
  1301. return l;
  1302. },
  1303. findListener : function(fn, scope){
  1304. scope = scope || this.obj;
  1305. var ls = this.listeners;
  1306. for(var i = 0, len = ls.length; i < len; i++){
  1307. var l = ls[i];
  1308. if(l.fn == fn && l.scope == scope){
  1309. return i;
  1310. }
  1311. }
  1312. return -1;
  1313. },
  1314. isListening : function(fn, scope){
  1315. return this.findListener(fn, scope) != -1;
  1316. },
  1317. removeListener : function(fn, scope){
  1318. var index;
  1319. if((index = this.findListener(fn, scope)) != -1){
  1320. if(!this.firing){
  1321. this.listeners.splice(index, 1);
  1322. }else{
  1323. this.listeners = this.listeners.slice(0);
  1324. this.listeners.splice(index, 1);
  1325. }
  1326. return true;
  1327. }
  1328. return false;
  1329. },
  1330. clearListeners : function(){
  1331. this.listeners = [];
  1332. },
  1333. fire : function(){
  1334. var ls = this.listeners, scope, len = ls.length;
  1335. if(len > 0){
  1336. this.firing = true;
  1337. var args = Array.prototype.slice.call(arguments, 0);
  1338. for(var i = 0; i < len; i++){
  1339. var l = ls[i];
  1340. if(l.fireFn.apply(l.scope||this.obj||window, arguments) === false){
  1341. this.firing = false;
  1342. return false;
  1343. }
  1344. }
  1345. this.firing = false;
  1346. }
  1347. return true;
  1348. }
  1349. };
  1350. })();
  1351. Ext.EventManager = function(){
  1352. var docReadyEvent, docReadyProcId, docReadyState = false;
  1353. var resizeEvent, resizeTask, textEvent, textSize;
  1354. var E = Ext.lib.Event;
  1355. var D = Ext.lib.Dom;
  1356. // fix parser confusion
  1357. var xname = 'Ex' + 't';
  1358. var elHash = {};
  1359. var addListener = function(el, ename, fn, wrap, scope){
  1360. var id = Ext.id(el);
  1361. if(!elHash[id]){
  1362. elHash[id] = {};
  1363. }
  1364. var es = elHash[id];
  1365. if(!es[ename]){
  1366. es[ename] = [];
  1367. }
  1368. var ls = es[ename];
  1369. ls.push({
  1370. id: id,
  1371. ename: ename,
  1372. fn: fn,
  1373. wrap: wrap,
  1374. scope: scope
  1375. });
  1376. E.on(el, ename, wrap);
  1377. if(ename == "mousewheel" && el.addEventListener){ // workaround for jQuery
  1378. el.addEventListener("DOMMouseScroll", wrap, false);
  1379. E.on(window, 'unload', function(){
  1380. el.removeEventListener("DOMMouseScroll", wrap, false);
  1381. });
  1382. }
  1383. if(ename == "mousedown" && el == document){ // fix stopped mousedowns on the document
  1384. Ext.EventManager.stoppedMouseDownEvent.addListener(wrap);
  1385. }
  1386. }
  1387. var removeListener = function(el, ename, fn, scope){
  1388. el = Ext.getDom(el);
  1389. var id = Ext.id(el), es = elHash[id], wrap;
  1390. if(es){
  1391. var ls = es[ename], l;
  1392. if(ls){
  1393. for(var i = 0, len = ls.length; i < len; i++){
  1394. l = ls[i];
  1395. if(l.fn == fn && (!scope || l.scope == scope)){
  1396. wrap = l.wrap;
  1397. E.un(el, ename, wrap);
  1398. ls.splice(i, 1);
  1399. break;
  1400. }
  1401. }
  1402. }
  1403. }
  1404. if(ename == "mousewheel" && el.addEventListener && wrap){
  1405. el.removeEventListener("DOMMouseScroll", wrap, false);
  1406. }
  1407. if(ename == "mousedown" && el == document && wrap){ // fix stopped mousedowns on the document
  1408. Ext.EventManager.stoppedMouseDownEvent.removeListener(wrap);
  1409. }
  1410. }
  1411. var removeAll = function(el){
  1412. el = Ext.getDom(el);
  1413. var id = Ext.id(el), es = elHash[id], ls;
  1414. if(es){
  1415. for(var ename in es){
  1416. if(es.hasOwnProperty(ename)){
  1417. ls = es[ename];
  1418. for(var i = 0, len = ls.length; i < len; i++){
  1419. E.un(el, ename, ls[i].wrap);
  1420. ls[i] = null;
  1421. }
  1422. }
  1423. es[ename] = null;
  1424. }
  1425. delete elHash[id];
  1426. }
  1427. }
  1428. var fireDocReady = function(){
  1429. if(!docReadyState){
  1430. docReadyState = true;
  1431. Ext.isReady = true;
  1432. if(docReadyProcId){
  1433. clearInterval(docReadyProcId);
  1434. }
  1435. if(Ext.isGecko || Ext.isOpera) {
  1436. document.removeEventListener("DOMContentLoaded", fireDocReady, false);
  1437. }
  1438. if(Ext.isIE){
  1439. var defer = document.getElementById("ie-deferred-loader");
  1440. if(defer){
  1441. defer.onreadystatechange = null;
  1442. defer.parentNode.removeChild(defer);
  1443. }
  1444. }
  1445. if(docReadyEvent){
  1446. docReadyEvent.fire();
  1447. docReadyEvent.clearListeners();
  1448. }
  1449. }
  1450. };
  1451. var initDocReady = function(){
  1452. docReadyEvent = new Ext.util.Event();
  1453. if(Ext.isGecko || Ext.isOpera) {
  1454. document.addEventListener("DOMContentLoaded", fireDocReady, false);
  1455. }else if(Ext.isIE){
  1456. document.write("<s"+'cript id="ie-deferred-loader" defer="defer" src="/'+'/:"></s'+"cript>");
  1457. var defer = document.getElementById("ie-deferred-loader");
  1458. defer.onreadystatechange = function(){
  1459. if(this.readyState == "complete"){
  1460. fireDocReady();
  1461. }
  1462. };
  1463. }else if(Ext.isSafari){
  1464. docReadyProcId = setInterval(function(){
  1465. var rs = document.readyState;
  1466. if(rs == "complete") {
  1467. fireDocReady();
  1468. }
  1469. }, 10);
  1470. }
  1471. // no matter what, make sure it fires on load
  1472. E.on(window, "load", fireDocReady);
  1473. };
  1474. var createBuffered = function(h, o){
  1475. var task = new Ext.util.DelayedTask(h);
  1476. return function(e){
  1477. // create new event object impl so new events don't wipe out properties
  1478. e = new Ext.EventObjectImpl(e);
  1479. task.delay(o.buffer, h, null, [e]);
  1480. };
  1481. };
  1482. var createSingle = function(h, el, ename, fn, scope){
  1483. return function(e){
  1484. Ext.EventManager.removeListener(el, ename, fn, scope);
  1485. h(e);
  1486. };
  1487. };
  1488. var createDelayed = function(h, o){
  1489. return function(e){
  1490. // create new event object impl so new events don't wipe out properties
  1491. e = new Ext.EventObjectImpl(e);
  1492. setTimeout(function(){
  1493. h(e);
  1494. }, o.delay || 10);
  1495. };
  1496. };
  1497. var listen = function(element, ename, opt, fn, scope){
  1498. var o = (!opt || typeof opt == "boolean") ? {} : opt;
  1499. fn = fn || o.fn; scope = scope || o.scope;
  1500. var el = Ext.getDom(element);
  1501. if(!el){
  1502. throw "Error listening for \"" + ename + '\". Element "' + element + '" doesn\'t exist.';
  1503. }
  1504. var h = function(e){
  1505. // prevent errors while unload occurring
  1506. if(!window[xname]){
  1507. return;
  1508. }
  1509. e = Ext.EventObject.setEvent(e);
  1510. var t;
  1511. if(o.delegate){
  1512. t = e.getTarget(o.delegate, el);
  1513. if(!t){
  1514. return;
  1515. }
  1516. }else{
  1517. t = e.target;
  1518. }
  1519. if(o.stopEvent === true){
  1520. e.stopEvent();
  1521. }
  1522. if(o.preventDefault === true){
  1523. e.preventDefault();
  1524. }
  1525. if(o.stopPropagation === true){
  1526. e.stopPropagation();
  1527. }
  1528. if(o.normalized === false){
  1529. e = e.browserEvent;
  1530. }
  1531. fn.call(scope || el, e, t, o);
  1532. };
  1533. if(o.delay){
  1534. h = createDelayed(h, o);
  1535. }
  1536. if(o.single){
  1537. h = createSingle(h, el, ename, fn, scope);
  1538. }
  1539. if(o.buffer){
  1540. h = createBuffered(h, o);
  1541. }
  1542. addListener(el, ename, fn, h, scope);
  1543. return h;
  1544. };
  1545. var propRe = /^(?:scope|delay|buffer|single|stopEvent|preventDefault|stopPropagation|normalized|args|delegate)$/;
  1546. var pub = {
  1547. addListener : function(element, eventName, fn, scope, options){
  1548. if(typeof eventName == "object"){
  1549. var o = eventName;
  1550. for(var e in o){
  1551. if(propRe.test(e)){
  1552. continue;
  1553. }
  1554. if(typeof o[e] == "function"){
  1555. // shared options
  1556. listen(element, e, o, o[e], o.scope);
  1557. }else{
  1558. // individual options
  1559. listen(element, e, o[e]);
  1560. }
  1561. }
  1562. return;
  1563. }
  1564. return listen(element, eventName, options, fn, scope);
  1565. },
  1566. removeListener : function(element, eventName, fn, scope){
  1567. return removeListener(element, eventName, fn, scope);
  1568. },
  1569. removeAll : function(element){
  1570. return removeAll(element);
  1571. },
  1572. onDocumentReady : function(fn, scope, options){
  1573. if(docReadyState){ // if it already fired
  1574. docReadyEvent.addListener(fn, scope, options);
  1575. docReadyEvent.fire();
  1576. docReadyEvent.clearListeners();
  1577. return;
  1578. }
  1579. if(!docReadyEvent){
  1580. initDocReady();
  1581. }
  1582. options = options || {};
  1583. if(!options.delay){
  1584. options.delay = 1;
  1585. }
  1586. docReadyEvent.addListener(fn, scope, options);
  1587. },
  1588. // private
  1589. doResizeEvent: function(){
  1590. resizeEvent.fire(D.getViewWidth(), D.getViewHeight());
  1591. },
  1592. onWindowResize : function(fn, scope, options){
  1593. if(!resizeEvent){
  1594. resizeEvent = new Ext.util.Event();
  1595. resizeTask = new Ext.util.DelayedTask(this.doResizeEvent);
  1596. E.on(window, "resize", this.fireWindowResize, this);
  1597. }
  1598. resizeEvent.addListener(fn, scope, options);
  1599. },
  1600. // exposed only to allow manual firing
  1601. fireWindowResize : function(){
  1602. if(resizeEvent){
  1603. if((Ext.isIE||Ext.isAir) && resizeTask){
  1604. resizeTask.delay(50);
  1605. }else{
  1606. resizeEvent.fire(D.getViewWidth(), D.getViewHeight());
  1607. }
  1608. }
  1609. },
  1610. onTextResize : function(fn, scope, options){
  1611. if(!textEvent){
  1612. textEvent = new Ext.util.Event();
  1613. var textEl = new Ext.Element(document.createElement('div'));
  1614. textEl.dom.className = 'x-text-resize';
  1615. textEl.dom.innerHTML = 'X';
  1616. textEl.appendTo(document.body);
  1617. textSize = textEl.dom.offsetHeight;
  1618. setInterval(function(){
  1619. if(textEl.dom.offsetHeight != textSize){
  1620. textEvent.fire(textSize, textSize = textEl.dom.offsetHeight);
  1621. }
  1622. }, this.textResizeInterval);
  1623. }
  1624. textEvent.addListener(fn, scope, options);
  1625. },
  1626. removeResizeListener : function(fn, scope){
  1627. if(resizeEvent){
  1628. resizeEvent.removeListener(fn, scope);
  1629. }
  1630. },
  1631. // private
  1632. fireResize : function(){
  1633. if(resizeEvent){
  1634. resizeEvent.fire(D.getViewWidth(), D.getViewHeight());
  1635. }
  1636. },
  1637. ieDeferSrc : false,
  1638. textResizeInterval : 50
  1639. };
  1640. pub.on = pub.addListener;
  1641. pub.un = pub.removeListener;
  1642. pub.stoppedMouseDownEvent = new Ext.util.Event();
  1643. return pub;
  1644. }();
  1645. Ext.onReady = Ext.EventManager.onDocumentReady;
  1646. // Initialize doc classes
  1647. (function(){
  1648. var initExtCss = function(){
  1649. // find the body element
  1650. var bd = document.body || document.getElementsByTagName('body')[0];
  1651. if(!bd){ return false; }
  1652. var cls = [' ',
  1653. Ext.isIE ? "ext-ie " + (Ext.isIE6 ? 'ext-ie6' : (Ext.isIE7 ? 'ext-ie7' : 'ext-ie8'))
  1654. : Ext.isGecko ? "ext-gecko " + (Ext.isGecko2 ? 'ext-gecko2' : 'ext-gecko3')
  1655. : Ext.isOpera ? "ext-opera"
  1656. : Ext.isSafari ? "ext-safari"
  1657. : Ext.isChrome ? "ext-chrome" : ""];
  1658. if(Ext.isMac){
  1659. cls.push("ext-mac");
  1660. }
  1661. if(Ext.isLinux){
  1662. cls.push("ext-linux");
  1663. }
  1664. if(Ext.isBorderBox){
  1665. cls.push('ext-border-box');
  1666. }
  1667. if(Ext.isStrict){ // add to the parent to allow for selectors like ".ext-strict .ext-ie"
  1668. var p = bd.parentNode;
  1669. if(p){
  1670. p.className += ' ext-strict';
  1671. }
  1672. }
  1673. bd.className += cls.join(' ');
  1674. return true;
  1675. }
  1676. if(!initExtCss()){
  1677. Ext.onReady(initExtCss);
  1678. }
  1679. })();
  1680. Ext.EventObject = function(){
  1681. var E = Ext.lib.Event;
  1682. // safari keypress events for special keys return bad keycodes
  1683. var safariKeys = {
  1684. 3 : 13, // enter
  1685. 63234 : 37, // left
  1686. 63235 : 39, // right
  1687. 63232 : 38, // up
  1688. 63233 : 40, // down
  1689. 63276 : 33, // page up
  1690. 63277 : 34, // page down
  1691. 63272 : 46, // delete
  1692. 63273 : 36, // home
  1693. 63275 : 35 // end
  1694. };
  1695. // normalize button clicks
  1696. var btnMap = Ext.isIE ? {1:0,4:1,2:2} :
  1697. (Ext.isSafari ? {1:0,2:1,3:2} : {0:0,1:1,2:2});
  1698. Ext.EventObjectImpl = function(e){
  1699. if(e){
  1700. this.setEvent(e.browserEvent || e);
  1701. }
  1702. };
  1703. Ext.EventObjectImpl.prototype = {
  1704. browserEvent : null,
  1705. button : -1,
  1706. shiftKey : false,
  1707. ctrlKey : false,
  1708. altKey : false,
  1709. BACKSPACE: 8,
  1710. TAB: 9,
  1711. NUM_CENTER: 12,
  1712. ENTER: 13,
  1713. RETURN: 13,
  1714. SHIFT: 16,
  1715. CTRL: 17,
  1716. CONTROL : 17, // legacy
  1717. ALT: 18,
  1718. PAUSE: 19,
  1719. CAPS_LOCK: 20,
  1720. ESC: 27,
  1721. SPACE: 32,
  1722. PAGE_UP: 33,
  1723. PAGEUP : 33, // legacy
  1724. PAGE_DOWN: 34,
  1725. PAGEDOWN : 34, // legacy
  1726. END: 35,
  1727. HOME: 36,
  1728. LEFT: 37,
  1729. UP: 38,
  1730. RIGHT: 39,
  1731. DOWN: 40,
  1732. PRINT_SCREEN: 44,
  1733. INSERT: 45,
  1734. DELETE: 46,
  1735. ZERO: 48,
  1736. ONE: 49,
  1737. TWO: 50,
  1738. THREE: 51,
  1739. FOUR: 52,
  1740. FIVE: 53,
  1741. SIX: 54,
  1742. SEVEN: 55,
  1743. EIGHT: 56,
  1744. NINE: 57,
  1745. A: 65,
  1746. B: 66,
  1747. C: 67,
  1748. D: 68,
  1749. E: 69,
  1750. F: 70,
  1751. G: 71,
  1752. H: 72,
  1753. I: 73,
  1754. J: 74,
  1755. K: 75,
  1756. L: 76,
  1757. M: 77,
  1758. N: 78,
  1759. O: 79,
  1760. P: 80,
  1761. Q: 81,
  1762. R: 82,
  1763. S: 83,
  1764. T: 84,
  1765. U: 85,
  1766. V: 86,
  1767. W: 87,
  1768. X: 88,
  1769. Y: 89,
  1770. Z: 90,
  1771. CONTEXT_MENU: 93,
  1772. NUM_ZERO: 96,
  1773. NUM_ONE: 97,
  1774. NUM_TWO: 98,
  1775. NUM_THREE: 99,
  1776. NUM_FOUR: 100,
  1777. NUM_FIVE: 101,
  1778. NUM_SIX: 102,
  1779. NUM_SEVEN: 103,
  1780. NUM_EIGHT: 104,
  1781. NUM_NINE: 105,
  1782. NUM_MULTIPLY: 106,
  1783. NUM_PLUS: 107,
  1784. NUM_MINUS: 109,
  1785. NUM_PERIOD: 110,
  1786. NUM_DIVISION: 111,
  1787. F1: 112,
  1788. F2: 113,
  1789. F3: 114,
  1790. F4: 115,
  1791. F5: 116,
  1792. F6: 117,
  1793. F7: 118,
  1794. F8: 119,
  1795. F9: 120,
  1796. F10: 121,
  1797. F11: 122,
  1798. F12: 123,
  1799. setEvent : function(e){
  1800. if(e == this || (e && e.browserEvent)){ // already wrapped
  1801. return e;
  1802. }
  1803. this.browserEvent = e;
  1804. if(e){
  1805. // normalize buttons
  1806. this.button = e.button ? btnMap[e.button] : (e.which ? e.which-1 : -1);
  1807. if(e.type == 'click' && this.button == -1){
  1808. this.button = 0;
  1809. }
  1810. this.type = e.type;
  1811. this.shiftKey = e.shiftKey;
  1812. // mac metaKey behaves like ctrlKey
  1813. this.ctrlKey = e.ctrlKey || e.metaKey;
  1814. this.altKey = e.altKey;
  1815. // in getKey these will be normalized for the mac
  1816. this.keyCode = e.keyCode;
  1817. this.charCode = e.charCode;
  1818. // cache the target for the delayed and or buffered events
  1819. this.target = E.getTarget(e);
  1820. // same for XY
  1821. this.xy = E.getXY(e);
  1822. }else{
  1823. this.button = -1;
  1824. this.shiftKey = false;
  1825. this.ctrlKey = false;
  1826. this.altKey = false;
  1827. this.keyCode = 0;
  1828. this.charCode = 0;
  1829. this.target = null;
  1830. this.xy = [0, 0];
  1831. }
  1832. return this;
  1833. },
  1834. stopEvent : function(){
  1835. if(this.browserEvent){
  1836. if(this.browserEvent.type == 'mousedown'){
  1837. Ext.EventManager.stoppedMouseDownEvent.fire(this);
  1838. }
  1839. E.stopEvent(this.browserEvent);
  1840. }
  1841. },
  1842. preventDefault : function(){
  1843. if(this.browserEvent){
  1844. E.preventDefault(this.browserEvent);
  1845. }
  1846. },
  1847. isNavKeyPress : function(){
  1848. var k = this.keyCode;
  1849. k = Ext.isSafari ? (safariKeys[k] || k) : k;
  1850. return (k >= 33 && k <= 40) || k == this.RETURN || k == this.TAB || k == this.ESC;
  1851. },
  1852. isSpecialKey : function(){
  1853. var k = this.keyCode;
  1854. return (this.type == 'keypress' && this.ctrlKey) || k == 9 || k == 13 || k == 40 || k == 27 ||
  1855. (k == 16) || (k == 17) ||
  1856. (k >= 18 && k <= 20) ||
  1857. (k >= 33 && k <= 35) ||
  1858. (k >= 36 && k <= 39) ||
  1859. (k >= 44 && k <= 45);
  1860. },
  1861. stopPropagation : function(){
  1862. if(this.browserEvent){
  1863. if(this.browserEvent.type == 'mousedown'){
  1864. Ext.EventManager.stoppedMouseDownEvent.fire(this);
  1865. }
  1866. E.stopPropagation(this.browserEvent);
  1867. }
  1868. },
  1869. getCharCode : function(){
  1870. return this.charCode || this.keyCode;
  1871. },
  1872. getKey : function(){
  1873. var k = this.keyCode || this.charCode;
  1874. return Ext.isSafari ? (safariKeys[k] || k) : k;
  1875. },
  1876. getPageX : function(){
  1877. return this.xy[0];
  1878. },
  1879. getPageY : function(){
  1880. return this.xy[1];
  1881. },
  1882. getTime : function(){
  1883. if(this.browserEvent){
  1884. return E.getTime(this.browserEvent);
  1885. }
  1886. return null;
  1887. },
  1888. getXY : function(){
  1889. return this.xy;
  1890. },
  1891. getTarget : function(selector, maxDepth, returnEl){
  1892. return selector ? Ext.fly(this.target).findParent(selector, maxDepth, returnEl) : (returnEl ? Ext.get(this.target) : this.target);
  1893. },
  1894. getRelatedTarget : function(){
  1895. if(this.browserEvent){
  1896. return E.getRelatedTarget(this.browserEvent);
  1897. }
  1898. return null;
  1899. },
  1900. getWheelDelta : function(){
  1901. var e = this.browserEvent;
  1902. var delta = 0;
  1903. if(e.wheelDelta){
  1904. delta = e.wheelDelta/120;
  1905. }else if(e.detail){
  1906. delta = -e.detail/3;
  1907. }
  1908. return delta;
  1909. },
  1910. hasModifier : function(){
  1911. return ((this.ctrlKey || this.altKey) || this.shiftKey) ? true : false;
  1912. },
  1913. within : function(el, related, allowEl){
  1914. var t = this[related ? "getRelatedTarget" : "getTarget"]();
  1915. return t && ((allowEl ? (t === Ext.getDom(el)) : false) || Ext.fly(el).contains(t));
  1916. },
  1917. getPoint : function(){
  1918. return new Ext.lib.Point(this.xy[0], this.xy[1]);
  1919. }
  1920. };
  1921. return new Ext.EventObjectImpl();
  1922. }();
  1923. (function(){
  1924. var D = Ext.lib.Dom;
  1925. var E = Ext.lib.Event;
  1926. var A = Ext.lib.Anim;
  1927. // local style camelizing for speed
  1928. var propCache = {};
  1929. var camelRe = /(-[a-z])/gi;
  1930. var camelFn = function(m, a){ return a.charAt(1).toUpperCase(); };
  1931. var view = document.defaultView;
  1932. Ext.Element = function(element, forceNew){
  1933. var dom = typeof element == "string" ?
  1934. document.getElementById(element) : element;
  1935. if(!dom){ // invalid id/element
  1936. return null;
  1937. }
  1938. var id = dom.id;
  1939. if(forceNew !== true && id && Ext.Element.cache[id]){ // element object already exists
  1940. return Ext.Element.cache[id];
  1941. }
  1942. this.dom = dom;
  1943. this.id = id || Ext.id(dom);
  1944. };
  1945. var El = Ext.Element;
  1946. El.prototype = {
  1947. originalDisplay : "",
  1948. visibilityMode : 1,
  1949. defaultUnit : "px",
  1950. setVisibilityMode : function(visMode){
  1951. this.visibilityMode = visMode;
  1952. return this;
  1953. },
  1954. enableDisplayMode : function(display){
  1955. this.setVisibilityMode(El.DISPLAY);
  1956. if(typeof display != "undefined") this.originalDisplay = display;
  1957. return this;
  1958. },
  1959. findParent : function(simpleSelector, maxDepth, returnEl){
  1960. var p = this.dom, b = document.body, depth = 0, dq = Ext.DomQuery, stopEl;
  1961. maxDepth = maxDepth || 50;
  1962. if(typeof maxDepth != "number"){
  1963. stopEl = Ext.getDom(maxDepth);
  1964. maxDepth = 10;
  1965. }
  1966. while(p && p.nodeType == 1 && depth < maxDepth && p != b && p != stopEl){
  1967. if(dq.is(p, simpleSelector)){
  1968. return returnEl ? Ext.get(p) : p;
  1969. }
  1970. depth++;
  1971. p = p.parentNode;
  1972. }
  1973. return null;
  1974. },
  1975. findParentNode : function(simpleSelector, maxDepth, returnEl){
  1976. var p = Ext.fly(this.dom.parentNode, '_internal');
  1977. return p ? p.findParent(simpleSelector, maxDepth, returnEl) : null;
  1978. },
  1979. up : function(simpleSelector, maxDepth){
  1980. return this.findParentNode(simpleSelector, maxDepth, true);
  1981. },
  1982. is : function(simpleSelector){
  1983. return Ext.DomQuery.is(this.dom, simpleSelector);
  1984. },
  1985. animate : function(args, duration, onComplete, easing, animType){
  1986. this.anim(args, {duration: duration, callback: onComplete, easing: easing}, animType);
  1987. return this;
  1988. },
  1989. anim : function(args, opt, animType, defaultDur, defaultEase, cb){
  1990. animType = animType || 'run';
  1991. opt = opt || {};
  1992. var anim = Ext.lib.Anim[animType](
  1993. this.dom, args,
  1994. (opt.duration || defaultDur) || .35,
  1995. (opt.easing || defaultEase) || 'easeOut',
  1996. function(){
  1997. Ext.callback(cb, this);
  1998. Ext.callback(opt.callback, opt.scope || this, [this, opt]);
  1999. },
  2000. this
  2001. );
  2002. opt.anim = anim;
  2003. return anim;
  2004. },
  2005. // private legacy anim prep
  2006. preanim : function(a, i){
  2007. return !a[i] ? false : (typeof a[i] == "object" ? a[i]: {duration: a[i+1], callback: a[i+2], easing: a[i+3]});
  2008. },
  2009. clean : function(forceReclean){
  2010. if(this.isCleaned && forceReclean !== true){
  2011. return this;
  2012. }
  2013. var ns = /\S/;
  2014. var d = this.dom, n = d.firstChild, ni = -1;
  2015. while(n){
  2016. var nx = n.nextSibling;
  2017. if(n.nodeType == 3 && !ns.test(n.nodeValue)){
  2018. d.removeChild(n);
  2019. }else{
  2020. n.nodeIndex = ++ni;
  2021. }
  2022. n = nx;
  2023. }
  2024. this.isCleaned = true;
  2025. return this;
  2026. },
  2027. scrollIntoView : function(container, hscroll){
  2028. var c = Ext.getDom(container) || Ext.getBody().dom;
  2029. var el = this.dom;
  2030. var o = this.getOffsetsTo(c),
  2031. l = o[0] + c.scrollLeft,
  2032. t = o[1] + c.scrollTop,
  2033. b = t+el.offsetHeight,
  2034. r = l+el.offsetWidth;
  2035. var ch = c.clientHeight;
  2036. var ct = parseInt(c.scrollTop, 10);
  2037. var cl = parseInt(c.scrollLeft, 10);
  2038. var cb = ct + ch;
  2039. var cr = cl + c.clientWidth;
  2040. if(el.offsetHeight > ch || t < ct){
  2041. c.scrollTop = t;
  2042. }else if(b > cb){
  2043. c.scrollTop = b-ch;
  2044. }
  2045. c.scrollTop = c.scrollTop; // corrects IE, other browsers will ignore
  2046. if(hscroll !== false){
  2047. if(el.offsetWidth > c.clientWidth || l < cl){
  2048. c.scrollLeft = l;
  2049. }else if(r > cr){
  2050. c.scrollLeft = r-c.clientWidth;
  2051. }
  2052. c.scrollLeft = c.scrollLeft;
  2053. }
  2054. return this;
  2055. },
  2056. // private
  2057. scrollChildIntoView : function(child, hscroll){
  2058. Ext.fly(child, '_scrollChildIntoView').scrollIntoView(this, hscroll);
  2059. },
  2060. autoHeight : function(animate, duration, onComplete, easing){
  2061. var oldHeight = this.getHeight();
  2062. this.clip();
  2063. this.setHeight(1); // force clipping
  2064. setTimeout(function(){
  2065. var height = parseInt(this.dom.scrollHeight, 10); // parseInt for Safari
  2066. if(!animate){
  2067. this.setHeight(height);
  2068. this.unclip();
  2069. if(typeof onComplete == "function"){
  2070. onComplete();
  2071. }
  2072. }else{
  2073. this.setHeight(oldHeight); // restore original height
  2074. this.setHeight(height, animate, duration, function(){
  2075. this.unclip();
  2076. if(typeof onComplete == "function") onComplete();
  2077. }.createDelegate(this), easing);
  2078. }
  2079. }.createDelegate(this), 0);
  2080. return this;
  2081. },
  2082. contains : function(el){
  2083. if(!el){return false;}
  2084. return D.isAncestor(this.dom, el.dom ? el.dom : el);
  2085. },
  2086. isVisible : function(deep) {
  2087. var vis = !(this.getStyle("visibility") == "hidden" || this.getStyle("display") == "none");
  2088. if(deep !== true || !vis){
  2089. return vis;
  2090. }
  2091. var p = this.dom.parentNode;
  2092. while(p && p.tagName.toLowerCase() != "body"){
  2093. if(!Ext.fly(p, '_isVisible').isVisible()){
  2094. return false;
  2095. }
  2096. p = p.parentNode;
  2097. }
  2098. return true;
  2099. },
  2100. select : function(selector, unique){
  2101. return El.select(selector, unique, this.dom);
  2102. },
  2103. query : function(selector){
  2104. return Ext.DomQuery.select(selector, this.dom);
  2105. },
  2106. child : function(selector, returnDom){
  2107. var n = Ext.DomQuery.selectNode(selector, this.dom);
  2108. return returnDom ? n : Ext.get(n);
  2109. },
  2110. down : function(selector, returnDom){
  2111. var n = Ext.DomQuery.selectNode(" > " + selector, this.dom);
  2112. return returnDom ? n : Ext.get(n);
  2113. },
  2114. initDD : function(group, config, overrides){
  2115. var dd = new Ext.dd.DD(Ext.id(this.dom), group, config);
  2116. return Ext.apply(dd, overrides);
  2117. },
  2118. initDDProxy : function(group, config, overrides){
  2119. var dd = new Ext.dd.DDProxy(Ext.id(this.dom), group, config);
  2120. return Ext.apply(dd, overrides);
  2121. },
  2122. initDDTarget : function(group, config, overrides){
  2123. var dd = new Ext.dd.DDTarget(Ext.id(this.dom), group, config);
  2124. return Ext.apply(dd, overrides);
  2125. },
  2126. setVisible : function(visible, animate){
  2127. if(!animate || !A){
  2128. if(this.visibilityMode == El.DISPLAY){
  2129. this.setDisplayed(visible);
  2130. }else{
  2131. this.fixDisplay();
  2132. this.dom.style.visibility = visible ? "visible" : "hidden";
  2133. }
  2134. }else{
  2135. // closure for composites
  2136. var dom = this.dom;
  2137. var visMode = this.visibilityMode;
  2138. if(visible){
  2139. this.setOpacity(.01);
  2140. this.setVisible(true);
  2141. }
  2142. this.anim({opacity: { to: (visible?1:0) }},
  2143. this.preanim(arguments, 1),
  2144. null, .35, 'easeIn', function(){
  2145. if(!visible){
  2146. if(visMode == El.DISPLAY){
  2147. dom.style.display = "none";
  2148. }else{
  2149. dom.style.visibility = "hidden";
  2150. }
  2151. Ext.get(dom).setOpacity(1);
  2152. }
  2153. });
  2154. }
  2155. return this;
  2156. },
  2157. isDisplayed : function() {
  2158. return this.getStyle("display") != "none";
  2159. },
  2160. toggle : function(animate){
  2161. this.setVisible(!this.isVisible(), this.preanim(arguments, 0));
  2162. return this;
  2163. },
  2164. setDisplayed : function(value) {
  2165. if(typeof value == "boolean"){
  2166. value = value ? this.originalDisplay : "none";
  2167. }
  2168. this.setStyle("display", value);
  2169. return this;
  2170. },
  2171. focus : function() {
  2172. try{
  2173. this.dom.focus();
  2174. }catch(e){}
  2175. return this;
  2176. },
  2177. blur : function() {
  2178. try{
  2179. this.dom.blur();
  2180. }catch(e){}
  2181. return this;
  2182. },
  2183. addClass : function(className){
  2184. if(Ext.isArray(className)){
  2185. for(var i = 0, len = className.length; i < len; i++) {
  2186. this.addClass(className[i]);
  2187. }
  2188. }else{
  2189. if(className && !this.hasClass(className)){
  2190. this.dom.className = this.dom.className + " " + className;
  2191. }
  2192. }
  2193. return this;
  2194. },
  2195. radioClass : function(className){
  2196. var siblings = this.dom.parentNode.childNodes;
  2197. for(var i = 0; i < siblings.length; i++) {
  2198. var s = siblings[i];
  2199. if(s.nodeType == 1){
  2200. Ext.get(s).removeClass(className);
  2201. }
  2202. }
  2203. this.addClass(className);
  2204. return this;
  2205. },
  2206. removeClass : function(className){
  2207. if(!className || !this.dom.className){
  2208. return this;
  2209. }
  2210. if(Ext.isArray(className)){
  2211. for(var i = 0, len = className.length; i < len; i++) {
  2212. this.removeClass(className[i]);
  2213. }
  2214. }else{
  2215. if(this.hasClass(className)){
  2216. var re = this.classReCache[className];
  2217. if (!re) {
  2218. re = new RegExp('(?:^|\\s+)' + className + '(?:\\s+|$)', "g");
  2219. this.classReCache[className] = re;
  2220. }
  2221. this.dom.className =
  2222. this.dom.className.replace(re, " ");
  2223. }
  2224. }
  2225. return this;
  2226. },
  2227. // private
  2228. classReCache: {},
  2229. toggleClass : function(className){
  2230. if(this.hasClass(className)){
  2231. this.removeClass(className);
  2232. }else{
  2233. this.addClass(className);
  2234. }
  2235. return this;
  2236. },
  2237. hasClass : function(className){
  2238. return className && (' '+this.dom.className+' ').indexOf(' '+className+' ') != -1;
  2239. },
  2240. replaceClass : function(oldClassName, newClassName){
  2241. this.removeClass(oldClassName);
  2242. this.addClass(newClassName);
  2243. return this;
  2244. },
  2245. getStyles : function(){
  2246. var a = arguments, len = a.length, r = {};
  2247. for(var i = 0; i < len; i++){
  2248. r[a[i]] = this.getStyle(a[i]);
  2249. }
  2250. return r;
  2251. },
  2252. getStyle : function(){
  2253. return view && view.getComputedStyle ?
  2254. function(prop){
  2255. var el = this.dom, v, cs, camel;
  2256. if(prop == 'float'){
  2257. prop = "cssFloat";
  2258. }
  2259. if(v = el.style[prop]){
  2260. return v;
  2261. }
  2262. if(cs = view.getComputedStyle(el, "")){
  2263. if(!(camel = propCache[prop])){
  2264. camel = propCache[prop] = prop.replace(camelRe, camelFn);
  2265. }
  2266. return cs[camel];
  2267. }
  2268. return null;
  2269. } :
  2270. function(prop){
  2271. var el = this.dom, v, cs, camel;
  2272. if(prop == 'opacity'){
  2273. if(typeof el.style.filter == 'string'){
  2274. var m = el.style.filter.match(/alpha\(opacity=(.*)\)/i);
  2275. if(m){
  2276. var fv = parseFloat(m[1]);
  2277. if(!isNaN(fv)){
  2278. return fv ? fv / 100 : 0;
  2279. }
  2280. }
  2281. }
  2282. return 1;
  2283. }else if(prop == 'float'){
  2284. prop = "styleFloat";
  2285. }
  2286. if(!(camel = propCache[prop])){
  2287. camel = propCache[prop] = prop.replace(camelRe, camelFn);
  2288. }
  2289. if(v = el.style[camel]){
  2290. return v;
  2291. }
  2292. if(cs = el.currentStyle){
  2293. return cs[camel];
  2294. }
  2295. return null;
  2296. };
  2297. }(),
  2298. setStyle : function(prop, value){
  2299. if(typeof prop == "string"){
  2300. var camel;
  2301. if(!(camel = propCache[prop])){
  2302. camel = propCache[prop] = prop.replace(camelRe, camelFn);
  2303. }
  2304. if(camel == 'opacity') {
  2305. this.setOpacity(value);
  2306. }else{
  2307. this.dom.style[camel] = value;
  2308. }
  2309. }else{
  2310. for(var style in prop){
  2311. if(typeof prop[style] != "function"){
  2312. this.setStyle(style, prop[style]);
  2313. }
  2314. }
  2315. }
  2316. return this;
  2317. },
  2318. applyStyles : function(style){
  2319. Ext.DomHelper.applyStyles(this.dom, style);
  2320. return this;
  2321. },
  2322. getX : function(){
  2323. return D.getX(this.dom);
  2324. },
  2325. getY : function(){
  2326. return D.getY(this.dom);
  2327. },
  2328. getXY : function(){
  2329. return D.getXY(this.dom);
  2330. },
  2331. getOffsetsTo : function(el){
  2332. var o = this.getXY();
  2333. var e = Ext.fly(el, '_internal').getXY();
  2334. return [o[0]-e[0],o[1]-e[1]];
  2335. },
  2336. setX : function(x, animate){
  2337. if(!animate || !A){
  2338. D.setX(this.dom, x);
  2339. }else{
  2340. this.setXY([x, this.getY()], this.preanim(arguments, 1));
  2341. }
  2342. return this;
  2343. },
  2344. setY : function(y, animate){
  2345. if(!animate || !A){
  2346. D.setY(this.dom, y);
  2347. }else{
  2348. this.setXY([this.getX(), y], this.preanim(arguments, 1));
  2349. }
  2350. return this;
  2351. },
  2352. setLeft : function(left){
  2353. this.setStyle("left", this.addUnits(left));
  2354. return this;
  2355. },
  2356. setTop : function(top){
  2357. this.setStyle("top", this.addUnits(top));
  2358. return this;
  2359. },
  2360. setRight : function(right){
  2361. this.setStyle("right", this.addUnits(right));
  2362. return this;
  2363. },
  2364. setBottom : function(bottom){
  2365. this.setStyle("bottom", this.addUnits(bottom));
  2366. return this;
  2367. },
  2368. setXY : function(pos, animate){
  2369. if(!animate || !A){
  2370. D.setXY(this.dom, pos);
  2371. }else{
  2372. this.anim({points: {to: pos}}, this.preanim(arguments, 1), 'motion');
  2373. }
  2374. return this;
  2375. },
  2376. setLocation : function(x, y, animate){
  2377. this.setXY([x, y], this.preanim(arguments, 2));
  2378. return this;
  2379. },
  2380. moveTo : function(x, y, animate){
  2381. this.setXY([x, y], this.preanim(arguments, 2));
  2382. return this;
  2383. },
  2384. getRegion : function(){
  2385. return D.getRegion(this.dom);
  2386. },
  2387. getHeight : function(contentHeight){
  2388. var h = this.dom.offsetHeight || 0;
  2389. h = contentHeight !== true ? h : h-this.getBorderWidth("tb")-this.getPadding("tb");
  2390. return h < 0 ? 0 : h;
  2391. },
  2392. getWidth : function(contentWidth){
  2393. var w = this.dom.offsetWidth || 0;
  2394. w = contentWidth !== true ? w : w-this.getBorderWidth("lr")-this.getPadding("lr");
  2395. return w < 0 ? 0 : w;
  2396. },
  2397. getComputedHeight : function(){
  2398. var h = Math.max(this.dom.offsetHeight, this.dom.clientHeight);
  2399. if(!h){
  2400. h = parseInt(this.getStyle('height'), 10) || 0;
  2401. if(!this.isBorderBox()){
  2402. h += this.getFrameWidth('tb');
  2403. }
  2404. }
  2405. return h;
  2406. },
  2407. getComputedWidth : function(){
  2408. var w = Math.max(this.dom.offsetWidth, this.dom.clientWidth);
  2409. if(!w){
  2410. w = parseInt(this.getStyle('width'), 10) || 0;
  2411. if(!this.isBorderBox()){
  2412. w += this.getFrameWidth('lr');
  2413. }
  2414. }
  2415. return w;
  2416. },
  2417. getSize : function(contentSize){
  2418. return {width: this.getWidth(contentSize), height: this.getHeight(contentSize)};
  2419. },
  2420. getStyleSize : function(){
  2421. var w, h, d = this.dom, s = d.style;
  2422. if(s.width && s.width != 'auto'){
  2423. w = parseInt(s.width, 10);
  2424. if(Ext.isBorderBox){
  2425. w -= this.getFrameWidth('lr');
  2426. }
  2427. }
  2428. if(s.height && s.height != 'auto'){
  2429. h = parseInt(s.height, 10);
  2430. if(Ext.isBorderBox){
  2431. h -= this.getFrameWidth('tb');
  2432. }
  2433. }
  2434. return {width: w || this.getWidth(true), height: h || this.getHeight(true)};
  2435. },
  2436. getViewSize : function(){
  2437. var d = this.dom, doc = document, aw = 0, ah = 0;
  2438. if(d == doc || d == doc.body){
  2439. return {width : D.getViewWidth(), height: D.getViewHeight()};
  2440. }else{
  2441. return {
  2442. width : d.clientWidth,
  2443. height: d.clientHeight
  2444. };
  2445. }
  2446. },
  2447. getValue : function(asNumber){
  2448. return asNumber ? parseInt(this.dom.value, 10) : this.dom.value;
  2449. },
  2450. // private
  2451. adjustWidth : function(width){
  2452. if(typeof width == "number"){
  2453. if(this.autoBoxAdjust && !this.isBorderBox()){
  2454. width -= (this.getBorderWidth("lr") + this.getPadding("lr"));
  2455. }
  2456. if(width < 0){
  2457. width = 0;
  2458. }
  2459. }
  2460. return width;
  2461. },
  2462. // private
  2463. adjustHeight : function(height){
  2464. if(typeof height == "number"){
  2465. if(this.autoBoxAdjust && !this.isBorderBox()){
  2466. height -= (this.getBorderWidth("tb") + this.getPadding("tb"));
  2467. }
  2468. if(height < 0){
  2469. height = 0;
  2470. }
  2471. }
  2472. return height;
  2473. },
  2474. setWidth : function(width, animate){
  2475. width = this.adjustWidth(width);
  2476. if(!animate || !A){
  2477. this.dom.style.width = this.addUnits(width);
  2478. }else{
  2479. this.anim({width: {to: width}}, this.preanim(arguments, 1));
  2480. }
  2481. return this;
  2482. },
  2483. setHeight : function(height, animate){
  2484. height = this.adjustHeight(height);
  2485. if(!animate || !A){
  2486. this.dom.style.height = this.addUnits(height);
  2487. }else{
  2488. this.anim({height: {to: height}}, this.preanim(arguments, 1));
  2489. }
  2490. return this;
  2491. },
  2492. setSize : function(width, height, animate){
  2493. if(typeof width == "object"){ // in case of object from getSize()
  2494. height = width.height; width = width.width;
  2495. }
  2496. width = this.adjustWidth(width); height = this.adjustHeight(height);
  2497. if(!animate || !A){
  2498. this.dom.style.width = this.addUnits(width);
  2499. this.dom.style.height = this.addUnits(height);
  2500. }else{
  2501. this.anim({width: {to: width}, height: {to: height}}, this.preanim(arguments, 2));
  2502. }
  2503. return this;
  2504. },
  2505. setBounds : function(x, y, width, height, animate){
  2506. if(!animate || !A){
  2507. this.setSize(width, height);
  2508. this.setLocation(x, y);
  2509. }else{
  2510. width = this.adjustWidth(width); height = this.adjustHeight(height);
  2511. this.anim({points: {to: [x, y]}, width: {to: width}, height: {to: height}},
  2512. this.preanim(arguments, 4), 'motion');
  2513. }
  2514. return this;
  2515. },
  2516. setRegion : function(region, animate){
  2517. this.setBounds(region.left, region.top, region.right-region.left, region.bottom-region.top, this.preanim(arguments, 1));
  2518. return this;
  2519. },
  2520. addListener : function(eventName, fn, scope, options){
  2521. Ext.EventManager.on(this.dom, eventName, fn, scope || this, options);
  2522. },
  2523. removeListener : function(eventName, fn, scope){
  2524. Ext.EventManager.removeListener(this.dom, eventName, fn, scope || this);
  2525. return this;
  2526. },
  2527. removeAllListeners : function(){
  2528. Ext.EventManager.removeAll(this.dom);
  2529. return this;
  2530. },
  2531. relayEvent : function(eventName, observable){
  2532. this.on(eventName, function(e){
  2533. observable.fireEvent(eventName, e);
  2534. });
  2535. },
  2536. setOpacity : function(opacity, animate){
  2537. if(!animate || !A){
  2538. var s = this.dom.style;
  2539. if(Ext.isIE){
  2540. s.zoom = 1;
  2541. s.filter = (s.filter || '').replace(/alpha\([^\)]*\)/gi,"") +
  2542. (opacity == 1 ? "" : " alpha(opacity=" + opacity * 100 + ")");
  2543. }else{
  2544. s.opacity = opacity;
  2545. }
  2546. }else{
  2547. this.anim({opacity: {to: opacity}}, this.preanim(arguments, 1), null, .35, 'easeIn');
  2548. }
  2549. return this;
  2550. },
  2551. getLeft : function(local){
  2552. if(!local){
  2553. return this.getX();
  2554. }else{
  2555. return parseInt(this.getStyle("left"), 10) || 0;
  2556. }
  2557. },
  2558. getRight : function(local){
  2559. if(!local){
  2560. return this.getX() + this.getWidth();
  2561. }else{
  2562. return (this.getLeft(true) + this.getWidth()) || 0;
  2563. }
  2564. },
  2565. getTop : function(local) {
  2566. if(!local){
  2567. return this.getY();
  2568. }else{
  2569. return parseInt(this.getStyle("top"), 10) || 0;
  2570. }
  2571. },
  2572. getBottom : function(local){
  2573. if(!local){
  2574. return this.getY() + this.getHeight();
  2575. }else{
  2576. return (this.getTop(true) + this.getHeight()) || 0;
  2577. }
  2578. },
  2579. position : function(pos, zIndex, x, y){
  2580. if(!pos){
  2581. if(this.getStyle('position') == 'static'){
  2582. this.setStyle('position', 'relative');
  2583. }
  2584. }else{
  2585. this.setStyle("position", pos);
  2586. }
  2587. if(zIndex){
  2588. this.setStyle("z-index", zIndex);
  2589. }
  2590. if(x !== undefined && y !== undefined){
  2591. this.setXY([x, y]);
  2592. }else if(x !== undefined){
  2593. this.setX(x);
  2594. }else if(y !== undefined){
  2595. this.setY(y);
  2596. }
  2597. },
  2598. clearPositioning : function(value){
  2599. value = value ||'';
  2600. this.setStyle({
  2601. "left": value,
  2602. "right": value,
  2603. "top": value,
  2604. "bottom": value,
  2605. "z-index": "",
  2606. "position" : "static"
  2607. });
  2608. return this;
  2609. },
  2610. getPositioning : function(){
  2611. var l = this.getStyle("left");
  2612. var t = this.getStyle("top");
  2613. return {
  2614. "position" : this.getStyle("position"),
  2615. "left" : l,
  2616. "right" : l ? "" : this.getStyle("right"),
  2617. "top" : t,
  2618. "bottom" : t ? "" : this.getStyle("bottom"),
  2619. "z-index" : this.getStyle("z-index")
  2620. };
  2621. },
  2622. getBorderWidth : function(side){
  2623. return this.addStyles(side, El.borders);
  2624. },
  2625. getPadding : function(side){
  2626. return this.addStyles(side, El.paddings);
  2627. },
  2628. setPositioning : function(pc){
  2629. this.applyStyles(pc);
  2630. if(pc.right == "auto"){
  2631. this.dom.style.right = "";
  2632. }
  2633. if(pc.bottom == "auto"){
  2634. this.dom.style.bottom = "";
  2635. }
  2636. return this;
  2637. },
  2638. // private
  2639. fixDisplay : function(){
  2640. if(this.getStyle("display") == "none"){
  2641. this.setStyle("visibility", "hidden");
  2642. this.setStyle("display", this.originalDisplay); // first try reverting to default
  2643. if(this.getStyle("display") == "none"){ // if that fails, default to block
  2644. this.setStyle("display", "block");
  2645. }
  2646. }
  2647. },
  2648. // private
  2649. setOverflow : function(v){
  2650. if(v=='auto' && Ext.isMac && Ext.isGecko2){ // work around stupid FF 2.0/Mac scroll bar bug
  2651. this.dom.style.overflow = 'hidden';
  2652. (function(){this.dom.style.overflow = 'auto';}).defer(1, this);
  2653. }else{
  2654. this.dom.style.overflow = v;
  2655. }
  2656. },
  2657. setLeftTop : function(left, top){
  2658. this.dom.style.left = this.addUnits(left);
  2659. this.dom.style.top = this.addUnits(top);
  2660. return this;
  2661. },
  2662. move : function(direction, distance, animate){
  2663. var xy = this.getXY();
  2664. direction = direction.toLowerCase();
  2665. switch(direction){
  2666. case "l":
  2667. case "left":
  2668. this.moveTo(xy[0]-distance, xy[1], this.preanim(arguments, 2));
  2669. break;
  2670. case "r":
  2671. case "right":
  2672. this.moveTo(xy[0]+distance, xy[1], this.preanim(arguments, 2));
  2673. break;
  2674. case "t":
  2675. case "top":
  2676. case "up":
  2677. this.moveTo(xy[0], xy[1]-distance, this.preanim(arguments, 2));
  2678. break;
  2679. case "b":
  2680. case "bottom":
  2681. case "down":
  2682. this.moveTo(xy[0], xy[1]+distance, this.preanim(arguments, 2));
  2683. break;
  2684. }
  2685. return this;
  2686. },
  2687. clip : function(){
  2688. if(!this.isClipped){
  2689. this.isClipped = true;
  2690. this.originalClip = {
  2691. "o": this.getStyle("overflow"),
  2692. "x": this.getStyle("overflow-x"),
  2693. "y": this.getStyle("overflow-y")
  2694. };
  2695. this.setStyle("overflow", "hidden");
  2696. this.setStyle("overflow-x", "hidden");
  2697. this.setStyle("overflow-y", "hidden");
  2698. }
  2699. return this;
  2700. },
  2701. unclip : function(){
  2702. if(this.isClipped){
  2703. this.isClipped = false;
  2704. var o = this.originalClip;
  2705. if(o.o){this.setStyle("overflow", o.o);}
  2706. if(o.x){this.setStyle("overflow-x", o.x);}
  2707. if(o.y){this.setStyle("overflow-y", o.y);}
  2708. }
  2709. return this;
  2710. },
  2711. getAnchorXY : function(anchor, local, s){
  2712. //Passing a different size is useful for pre-calculating anchors,
  2713. //especially for anchored animations that change the el size.
  2714. var w, h, vp = false;
  2715. if(!s){
  2716. var d = this.dom;
  2717. if(d == document.body || d == document){
  2718. vp = true;
  2719. w = D.getViewWidth(); h = D.getViewHeight();
  2720. }else{
  2721. w = this.getWidth(); h = this.getHeight();
  2722. }
  2723. }else{
  2724. w = s.width; h = s.height;
  2725. }
  2726. var x = 0, y = 0, r = Math.round;
  2727. switch((anchor || "tl").toLowerCase()){
  2728. case "c":
  2729. x = r(w*.5);
  2730. y = r(h*.5);
  2731. break;
  2732. case "t":
  2733. x = r(w*.5);
  2734. y = 0;
  2735. break;
  2736. case "l":
  2737. x = 0;
  2738. y = r(h*.5);
  2739. break;
  2740. case "r":
  2741. x = w;
  2742. y = r(h*.5);
  2743. break;
  2744. case "b":
  2745. x = r(w*.5);
  2746. y = h;
  2747. break;
  2748. case "tl":
  2749. x = 0;
  2750. y = 0;
  2751. break;
  2752. case "bl":
  2753. x = 0;
  2754. y = h;
  2755. break;
  2756. case "br":
  2757. x = w;
  2758. y = h;
  2759. break;
  2760. case "tr":
  2761. x = w;
  2762. y = 0;
  2763. break;
  2764. }
  2765. if(local === true){
  2766. return [x, y];
  2767. }
  2768. if(vp){
  2769. var sc = this.getScroll();
  2770. return [x + sc.left, y + sc.top];
  2771. }
  2772. //Add the element's offset xy
  2773. var o = this.getXY();
  2774. return [x+o[0], y+o[1]];
  2775. },
  2776. getAlignToXY : function(el, p, o){
  2777. el = Ext.get(el);
  2778. if(!el || !el.dom){
  2779. throw "Element.alignToXY with an element that doesn't exist";
  2780. }
  2781. var d = this.dom;
  2782. var c = false; //constrain to viewport
  2783. var p1 = "", p2 = "";
  2784. o = o || [0,0];
  2785. if(!p){
  2786. p = "tl-bl";
  2787. }else if(p == "?"){
  2788. p = "tl-bl?";
  2789. }else if(p.indexOf("-") == -1){
  2790. p = "tl-" + p;
  2791. }
  2792. p = p.toLowerCase();
  2793. var m = p.match(/^([a-z]+)-([a-z]+)(\?)?$/);
  2794. if(!m){
  2795. throw "Element.alignTo with an invalid alignment " + p;
  2796. }
  2797. p1 = m[1]; p2 = m[2]; c = !!m[3];
  2798. //Subtract the aligned el's internal xy from the target's offset xy
  2799. //plus custom offset to get the aligned el's new offset xy
  2800. var a1 = this.getAnchorXY(p1, true);
  2801. var a2 = el.getAnchorXY(p2, false);
  2802. var x = a2[0] - a1[0] + o[0];
  2803. var y = a2[1] - a1[1] + o[1];
  2804. if(c){
  2805. //constrain the aligned el to viewport if necessary
  2806. var w = this.getWidth(), h = this.getHeight(), r = el.getRegion();
  2807. // 5px of margin for ie
  2808. var dw = D.getViewWidth()-5, dh = D.getViewHeight()-5;
  2809. //If we are at a viewport boundary and the aligned el is anchored on a target border that is
  2810. //perpendicular to the vp border, allow the aligned el to slide on that border,
  2811. //otherwise swap the aligned el to the opposite border of the target.
  2812. var p1y = p1.charAt(0), p1x = p1.charAt(p1.length-1);
  2813. var p2y = p2.charAt(0), p2x = p2.charAt(p2.length-1);
  2814. var swapY = ((p1y=="t" && p2y=="b") || (p1y=="b" && p2y=="t"));
  2815. var swapX = ((p1x=="r" && p2x=="l") || (p1x=="l" && p2x=="r"));
  2816. var doc = document;
  2817. var scrollX = (doc.documentElement.scrollLeft || doc.body.scrollLeft || 0)+5;
  2818. var scrollY = (doc.documentElement.scrollTop || doc.body.scrollTop || 0)+5;
  2819. if((x+w) > dw + scrollX){
  2820. x = swapX ? r.left-w : dw+scrollX-w;
  2821. }
  2822. if(x < scrollX){
  2823. x = swapX ? r.right : scrollX;
  2824. }
  2825. if((y+h) > dh + scrollY){
  2826. y = swapY ? r.top-h : dh+scrollY-h;
  2827. }
  2828. if (y < scrollY){
  2829. y = swapY ? r.bottom : scrollY;
  2830. }
  2831. }
  2832. return [x,y];
  2833. },
  2834. // private
  2835. getConstrainToXY : function(){
  2836. var os = {top:0, left:0, bottom:0, right: 0};
  2837. return function(el, local, offsets, proposedXY){
  2838. el = Ext.get(el);
  2839. offsets = offsets ? Ext.applyIf(offsets, os) : os;
  2840. var vw, vh, vx = 0, vy = 0;
  2841. if(el.dom == document.body || el.dom == document){
  2842. vw = Ext.lib.Dom.getViewWidth();
  2843. vh = Ext.lib.Dom.getViewHeight();
  2844. }else{
  2845. vw = el.dom.clientWidth;
  2846. vh = el.dom.clientHeight;
  2847. if(!local){
  2848. var vxy = el.getXY();
  2849. vx = vxy[0];
  2850. vy = vxy[1];
  2851. }
  2852. }
  2853. var s = el.getScroll();
  2854. vx += offsets.left + s.left;
  2855. vy += offsets.top + s.top;
  2856. vw -= offsets.right;
  2857. vh -= offsets.bottom;
  2858. var vr = vx+vw;
  2859. var vb = vy+vh;
  2860. var xy = proposedXY || (!local ? this.getXY() : [this.getLeft(true), this.getTop(true)]);
  2861. var x = xy[0], y = xy[1];
  2862. var w = this.dom.offsetWidth, h = this.dom.offsetHeight;
  2863. // only move it if it needs it
  2864. var moved = false;
  2865. // first validate right/bottom
  2866. if((x + w) > vr){
  2867. x = vr - w;
  2868. moved = true;
  2869. }
  2870. if((y + h) > vb){
  2871. y = vb - h;
  2872. moved = true;
  2873. }
  2874. // then make sure top/left isn't negative
  2875. if(x < vx){
  2876. x = vx;
  2877. moved = true;
  2878. }
  2879. if(y < vy){
  2880. y = vy;
  2881. moved = true;
  2882. }
  2883. return moved ? [x, y] : false;
  2884. };
  2885. }(),
  2886. // private
  2887. adjustForConstraints : function(xy, parent, offsets){
  2888. return this.getConstrainToXY(parent || document, false, offsets, xy) || xy;
  2889. },
  2890. alignTo : function(element, position, offsets, animate){
  2891. var xy = this.getAlignToXY(element, position, offsets);
  2892. this.setXY(xy, this.preanim(arguments, 3));
  2893. return this;
  2894. },
  2895. anchorTo : function(el, alignment, offsets, animate, monitorScroll, callback){
  2896. var action = function(){
  2897. this.alignTo(el, alignment, offsets, animate);
  2898. Ext.callback(callback, this);
  2899. };
  2900. Ext.EventManager.onWindowResize(action, this);
  2901. var tm = typeof monitorScroll;
  2902. if(tm != 'undefined'){
  2903. Ext.EventManager.on(window, 'scroll', action, this,
  2904. {buffer: tm == 'number' ? monitorScroll : 50});
  2905. }
  2906. action.call(this); // align immediately
  2907. return this;
  2908. },
  2909. clearOpacity : function(){
  2910. if (window.ActiveXObject) {
  2911. if(typeof this.dom.style.filter == 'string' && (/alpha/i).test(this.dom.style.filter)){
  2912. this.dom.style.filter = "";
  2913. }
  2914. } else {
  2915. this.dom.style.opacity = "";
  2916. this.dom.style["-moz-opacity"] = "";
  2917. this.dom.style["-khtml-opacity"] = "";
  2918. }
  2919. return this;
  2920. },
  2921. hide : function(animate){
  2922. this.setVisible(false, this.preanim(arguments, 0));
  2923. return this;
  2924. },
  2925. show : function(animate){
  2926. this.setVisible(true, this.preanim(arguments, 0));
  2927. return this;
  2928. },
  2929. addUnits : function(size){
  2930. return Ext.Element.addUnits(size, this.defaultUnit);
  2931. },
  2932. update : function(html, loadScripts, callback){
  2933. if(typeof html == "undefined"){
  2934. html = "";
  2935. }
  2936. if(loadScripts !== true){
  2937. this.dom.innerHTML = html;
  2938. if(typeof callback == "function"){
  2939. callback();
  2940. }
  2941. return this;
  2942. }
  2943. var id = Ext.id();
  2944. var dom = this.dom;
  2945. html += '<span id="' + id + '"></span>';
  2946. E.onAvailable(id, function(){
  2947. var hd = document.getElementsByTagName("head")[0];
  2948. var re = /(?:<script([^>]*)?>)((\n|\r|.)*?)(?:<\/script>)/ig;
  2949. var srcRe = /\ssrc=([\'\"])(.*?)\1/i;
  2950. var typeRe = /\stype=([\'\"])(.*?)\1/i;
  2951. var match;
  2952. while(match = re.exec(html)){
  2953. var attrs = match[1];
  2954. var srcMatch = attrs ? attrs.match(srcRe) : false;
  2955. if(srcMatch && srcMatch[2]){
  2956. var s = document.createElement("script");
  2957. s.src = srcMatch[2];
  2958. var typeMatch = attrs.match(typeRe);
  2959. if(typeMatch && typeMatch[2]){
  2960. s.type = typeMatch[2];
  2961. }
  2962. hd.appendChild(s);
  2963. }else if(match[2] && match[2].length > 0){
  2964. if(window.execScript) {
  2965. window.execScript(match[2]);
  2966. } else {
  2967. window.eval(match[2]);
  2968. }
  2969. }
  2970. }
  2971. var el = document.getElementById(id);
  2972. if(el){Ext.removeNode(el);}
  2973. if(typeof callback == "function"){
  2974. callback();
  2975. }
  2976. });
  2977. dom.innerHTML = html.replace(/(?:<script.*?>)((\n|\r|.)*?)(?:<\/script>)/ig, "");
  2978. return this;
  2979. },
  2980. load : function(){
  2981. var um = this.getUpdater();
  2982. um.update.apply(um, arguments);
  2983. return this;
  2984. },
  2985. getUpdater : function(){
  2986. if(!this.updateManager){
  2987. this.updateManager = new Ext.Updater(this);
  2988. }
  2989. return this.updateManager;
  2990. },
  2991. unselectable : function(){
  2992. this.dom.unselectable = "on";
  2993. this.swallowEvent("selectstart", true);
  2994. this.applyStyles("-moz-user-select:none;-khtml-user-select:none;");
  2995. this.addClass("x-unselectable");
  2996. return this;
  2997. },
  2998. getCenterXY : function(){
  2999. return this.getAlignToXY(document, 'c-c');
  3000. },
  3001. center : function(centerIn){
  3002. this.alignTo(centerIn || document, 'c-c');
  3003. return this;
  3004. },
  3005. isBorderBox : function(){
  3006. return noBoxAdjust[this.dom.tagName.toLowerCase()] || Ext.isBorderBox;
  3007. },
  3008. getBox : function(contentBox, local){
  3009. var xy;
  3010. if(!local){
  3011. xy = this.getXY();
  3012. }else{
  3013. var left = parseInt(this.getStyle("left"), 10) || 0;
  3014. var top = parseInt(this.getStyle("top"), 10) || 0;
  3015. xy = [left, top];
  3016. }
  3017. var el = this.dom, w = el.offsetWidth, h = el.offsetHeight, bx;
  3018. if(!contentBox){
  3019. bx = {x: xy[0], y: xy[1], 0: xy[0], 1: xy[1], width: w, height: h};
  3020. }else{
  3021. var l = this.getBorderWidth("l")+this.getPadding("l");
  3022. var r = this.getBorderWidth("r")+this.getPadding("r");
  3023. var t = this.getBorderWidth("t")+this.getPadding("t");
  3024. var b = this.getBorderWidth("b")+this.getPadding("b");
  3025. bx = {x: xy[0]+l, y: xy[1]+t, 0: xy[0]+l, 1: xy[1]+t, width: w-(l+r), height: h-(t+b)};
  3026. }
  3027. bx.right = bx.x + bx.width;
  3028. bx.bottom = bx.y + bx.height;
  3029. return bx;
  3030. },
  3031. getFrameWidth : function(sides, onlyContentBox){
  3032. return onlyContentBox && Ext.isBorderBox ? 0 : (this.getPadding(sides) + this.getBorderWidth(sides));
  3033. },
  3034. setBox : function(box, adjust, animate){
  3035. var w = box.width, h = box.height;
  3036. if((adjust && !this.autoBoxAdjust) && !this.isBorderBox()){
  3037. w -= (this.getBorderWidth("lr") + this.getPadding("lr"));
  3038. h -= (this.getBorderWidth("tb") + this.getPadding("tb"));
  3039. }
  3040. this.setBounds(box.x, box.y, w, h, this.preanim(arguments, 2));
  3041. return this;
  3042. },
  3043. repaint : function(){
  3044. var dom = this.dom;
  3045. this.addClass("x-repaint");
  3046. setTimeout(function(){
  3047. Ext.get(dom).removeClass("x-repaint");
  3048. }, 1);
  3049. return this;
  3050. },
  3051. getMargins : function(side){
  3052. if(!side){
  3053. return {
  3054. top: parseInt(this.getStyle("margin-top"), 10) || 0,
  3055. left: parseInt(this.getStyle("margin-left"), 10) || 0,
  3056. bottom: parseInt(this.getStyle("margin-bottom"), 10) || 0,
  3057. right: parseInt(this.getStyle("margin-right"), 10) || 0
  3058. };
  3059. }else{
  3060. return this.addStyles(side, El.margins);
  3061. }
  3062. },
  3063. // private
  3064. addStyles : function(sides, styles){
  3065. var val = 0, v, w;
  3066. for(var i = 0, len = sides.length; i < len; i++){
  3067. v = this.getStyle(styles[sides.charAt(i)]);
  3068. if(v){
  3069. w = parseInt(v, 10);
  3070. if(w){ val += (w >= 0 ? w : -1 * w); }
  3071. }
  3072. }
  3073. return val;
  3074. },
  3075. createProxy : function(config, renderTo, matchBox){
  3076. config = typeof config == "object" ?
  3077. config : {tag : "div", cls: config};
  3078. var proxy;
  3079. if(renderTo){
  3080. proxy = Ext.DomHelper.append(renderTo, config, true);
  3081. }else {
  3082. proxy = Ext.DomHelper.insertBefore(this.dom, config, true);
  3083. }
  3084. if(matchBox){
  3085. proxy.setBox(this.getBox());
  3086. }
  3087. return proxy;
  3088. },
  3089. mask : function(msg, msgCls){
  3090. if(this.getStyle("position") == "static"){
  3091. this.addClass("x-masked-relative");
  3092. }
  3093. if(this._maskMsg){
  3094. this._maskMsg.remove();
  3095. }
  3096. if(this._mask){
  3097. this._mask.remove();
  3098. }
  3099. this._mask = Ext.DomHelper.append(this.dom, {cls:"ext-el-mask"}, true);
  3100. this.addClass("x-masked");
  3101. this._mask.setDisplayed(true);
  3102. if(typeof msg == 'string'){
  3103. this._maskMsg = Ext.DomHelper.append(this.dom, {cls:"ext-el-mask-msg", cn:{tag:'div'}}, true);
  3104. var mm = this._maskMsg;
  3105. mm.dom.className = msgCls ? "ext-el-mask-msg " + msgCls : "ext-el-mask-msg";
  3106. mm.dom.firstChild.innerHTML = msg;
  3107. mm.setDisplayed(true);
  3108. mm.center(this);
  3109. }
  3110. if(Ext.isIE && !(Ext.isIE7 && Ext.isStrict) && this.getStyle('height') == 'auto'){ // ie will not expand full height automatically
  3111. this._mask.setSize(this.getWidth(), this.getHeight());
  3112. }
  3113. return this._mask;
  3114. },
  3115. unmask : function(){
  3116. if(this._mask){
  3117. if(this._maskMsg){
  3118. this._maskMsg.remove();
  3119. delete this._maskMsg;
  3120. }
  3121. this._mask.remove();
  3122. delete this._mask;
  3123. }
  3124. this.removeClass(["x-masked", "x-masked-relative"]);
  3125. },
  3126. isMasked : function(){
  3127. return this._mask && this._mask.isVisible();
  3128. },
  3129. createShim : function(){
  3130. var el = document.createElement('iframe');
  3131. el.frameBorder = '0';
  3132. el.className = 'ext-shim';
  3133. if(Ext.isIE && Ext.isSecure){
  3134. el.src = Ext.SSL_SECURE_URL;
  3135. }
  3136. var shim = Ext.get(this.dom.parentNode.insertBefore(el, this.dom));
  3137. shim.autoBoxAdjust = false;
  3138. return shim;
  3139. },
  3140. remove : function(){
  3141. Ext.removeNode(this.dom);
  3142. delete El.cache[this.dom.id];
  3143. },
  3144. hover : function(overFn, outFn, scope){
  3145. var preOverFn = function(e){
  3146. if(!e.within(this, true)){
  3147. overFn.apply(scope || this, arguments);
  3148. }
  3149. };
  3150. var preOutFn = function(e){
  3151. if(!e.within(this, true)){
  3152. outFn.apply(scope || this, arguments);
  3153. }
  3154. };
  3155. this.on("mouseover", preOverFn, this.dom);
  3156. this.on("mouseout", preOutFn, this.dom);
  3157. return this;
  3158. },
  3159. addClassOnOver : function(className){
  3160. this.hover(
  3161. function(){
  3162. Ext.fly(this, '_internal').addClass(className);
  3163. },
  3164. function(){
  3165. Ext.fly(this, '_internal').removeClass(className);
  3166. }
  3167. );
  3168. return this;
  3169. },
  3170. addClassOnFocus : function(className){
  3171. this.on("focus", function(){
  3172. Ext.fly(this, '_internal').addClass(className);
  3173. }, this.dom);
  3174. this.on("blur", function(){
  3175. Ext.fly(this, '_internal').removeClass(className);
  3176. }, this.dom);
  3177. return this;
  3178. },
  3179. addClassOnClick : function(className){
  3180. var dom = this.dom;
  3181. this.on("mousedown", function(){
  3182. Ext.fly(dom, '_internal').addClass(className);
  3183. var d = Ext.getDoc();
  3184. var fn = function(){
  3185. Ext.fly(dom, '_internal').removeClass(className);
  3186. d.removeListener("mouseup", fn);
  3187. };
  3188. d.on("mouseup", fn);
  3189. });
  3190. return this;
  3191. },
  3192. swallowEvent : function(eventName, preventDefault){
  3193. var fn = function(e){
  3194. e.stopPropagation();
  3195. if(preventDefault){
  3196. e.preventDefault();
  3197. }
  3198. };
  3199. if(Ext.isArray(eventName)){
  3200. for(var i = 0, len = eventName.length; i < len; i++){
  3201. this.on(eventName[i], fn);
  3202. }
  3203. return this;
  3204. }
  3205. this.on(eventName, fn);
  3206. return this;
  3207. },
  3208. parent : function(selector, returnDom){
  3209. return this.matchNode('parentNode', 'parentNode', selector, returnDom);
  3210. },
  3211. next : function(selector, returnDom){
  3212. return this.matchNode('nextSibling', 'nextSibling', selector, returnDom);
  3213. },
  3214. prev : function(selector, returnDom){
  3215. return this.matchNode('previousSibling', 'previousSibling', selector, returnDom);
  3216. },
  3217. first : function(selector, returnDom){
  3218. return this.matchNode('nextSibling', 'firstChild', selector, returnDom);
  3219. },
  3220. last : function(selector, returnDom){
  3221. return this.matchNode('previousSibling', 'lastChild', selector, returnDom);
  3222. },
  3223. matchNode : function(dir, start, selector, returnDom){
  3224. var n = this.dom[start];
  3225. while(n){
  3226. if(n.nodeType == 1 && (!selector || Ext.DomQuery.is(n, selector))){
  3227. return !returnDom ? Ext.get(n) : n;
  3228. }
  3229. n = n[dir];
  3230. }
  3231. return null;
  3232. },
  3233. appendChild: function(el){
  3234. el = Ext.get(el);
  3235. el.appendTo(this);
  3236. return this;
  3237. },
  3238. createChild: function(config, insertBefore, returnDom){
  3239. config = config || {tag:'div'};
  3240. if(insertBefore){
  3241. return Ext.DomHelper.insertBefore(insertBefore, config, returnDom !== true);
  3242. }
  3243. return Ext.DomHelper[!this.dom.firstChild ? 'overwrite' : 'append'](this.dom, config, returnDom !== true);
  3244. },
  3245. appendTo: function(el){
  3246. el = Ext.getDom(el);
  3247. el.appendChild(this.dom);
  3248. return this;
  3249. },
  3250. insertBefore: function(el){
  3251. el = Ext.getDom(el);
  3252. el.parentNode.insertBefore(this.dom, el);
  3253. return this;
  3254. },
  3255. insertAfter: function(el){
  3256. el = Ext.getDom(el);
  3257. el.parentNode.insertBefore(this.dom, el.nextSibling);
  3258. return this;
  3259. },
  3260. insertFirst: function(el, returnDom){
  3261. el = el || {};
  3262. if(typeof el == 'object' && !el.nodeType && !el.dom){ // dh config
  3263. return this.createChild(el, this.dom.firstChild, returnDom);
  3264. }else{
  3265. el = Ext.getDom(el);
  3266. this.dom.insertBefore(el, this.dom.firstChild);
  3267. return !returnDom ? Ext.get(el) : el;
  3268. }
  3269. },
  3270. insertSibling: function(el, where, returnDom){
  3271. var rt;
  3272. if(Ext.isArray(el)){
  3273. for(var i = 0, len = el.length; i < len; i++){
  3274. rt = this.insertSibling(el[i], where, returnDom);
  3275. }
  3276. return rt;
  3277. }
  3278. where = where ? where.toLowerCase() : 'before';
  3279. el = el || {};
  3280. var refNode = where == 'before' ? this.dom : this.dom.nextSibling;
  3281. if(typeof el == 'object' && !el.nodeType && !el.dom){ // dh config
  3282. if(where == 'after' && !this.dom.nextSibling){
  3283. rt = Ext.DomHelper.append(this.dom.parentNode, el, !returnDom);
  3284. }else{
  3285. rt = Ext.DomHelper[where == 'after' ? 'insertAfter' : 'insertBefore'](this.dom, el, !returnDom);
  3286. }
  3287. }else{
  3288. rt = this.dom.parentNode.insertBefore(Ext.getDom(el), refNode);
  3289. if(!returnDom){
  3290. rt = Ext.get(rt);
  3291. }
  3292. }
  3293. return rt;
  3294. },
  3295. wrap: function(config, returnDom){
  3296. if(!config){
  3297. config = {tag: "div"};
  3298. }
  3299. var newEl = Ext.DomHelper.insertBefore(this.dom, config, !returnDom);
  3300. newEl.dom ? newEl.dom.appendChild(this.dom) : newEl.appendChild(this.dom);
  3301. return newEl;
  3302. },
  3303. replace: function(el){
  3304. el = Ext.get(el);
  3305. this.insertBefore(el);
  3306. el.remove();
  3307. return this;
  3308. },
  3309. replaceWith: function(el){
  3310. if(typeof el == 'object' && !el.nodeType && !el.dom){ // dh config
  3311. el = this.insertSibling(el, 'before');
  3312. }else{
  3313. el = Ext.getDom(el);
  3314. this.dom.parentNode.insertBefore(el, this.dom);
  3315. }
  3316. El.uncache(this.id);
  3317. Ext.removeNode(this.dom);
  3318. this.dom = el;
  3319. this.id = Ext.id(el);
  3320. El.cache[this.id] = this;
  3321. return this;
  3322. },
  3323. insertHtml : function(where, html, returnEl){
  3324. var el = Ext.DomHelper.insertHtml(where, this.dom, html);
  3325. return returnEl ? Ext.get(el) : el;
  3326. },
  3327. set : function(o, useSet){
  3328. var el = this.dom;
  3329. useSet = typeof useSet == 'undefined' ? (el.setAttribute ? true : false) : useSet;
  3330. for(var attr in o){
  3331. if(attr == "style" || typeof o[attr] == "function") continue;
  3332. if(attr=="cls"){
  3333. el.className = o["cls"];
  3334. }else if(o.hasOwnProperty(attr)){
  3335. if(useSet) el.setAttribute(attr, o[attr]);
  3336. else el[attr] = o[attr];
  3337. }
  3338. }
  3339. if(o.style){
  3340. Ext.DomHelper.applyStyles(el, o.style);
  3341. }
  3342. return this;
  3343. },
  3344. addKeyListener : function(key, fn, scope){
  3345. var config;
  3346. if(typeof key != "object" || Ext.isArray(key)){
  3347. config = {
  3348. key: key,
  3349. fn: fn,
  3350. scope: scope
  3351. };
  3352. }else{
  3353. config = {
  3354. key : key.key,
  3355. shift : key.shift,
  3356. ctrl : key.ctrl,
  3357. alt : key.alt,
  3358. fn: fn,
  3359. scope: scope
  3360. };
  3361. }
  3362. return new Ext.KeyMap(this, config);
  3363. },
  3364. addKeyMap : function(config){
  3365. return new Ext.KeyMap(this, config);
  3366. },
  3367. isScrollable : function(){
  3368. var dom = this.dom;
  3369. return dom.scrollHeight > dom.clientHeight || dom.scrollWidth > dom.clientWidth;
  3370. },
  3371. scrollTo : function(side, value, animate){
  3372. var prop = side.toLowerCase() == "left" ? "scrollLeft" : "scrollTop";
  3373. if(!animate || !A){
  3374. this.dom[prop] = value;
  3375. }else{
  3376. var to = prop == "scrollLeft" ? [value, this.dom.scrollTop] : [this.dom.scrollLeft, value];
  3377. this.anim({scroll: {"to": to}}, this.preanim(arguments, 2), 'scroll');
  3378. }
  3379. return this;
  3380. },
  3381. scroll : function(direction, distance, animate){
  3382. if(!this.isScrollable()){
  3383. return;
  3384. }
  3385. var el = this.dom;
  3386. var l = el.scrollLeft, t = el.scrollTop;
  3387. var w = el.scrollWidth, h = el.scrollHeight;
  3388. var cw = el.clientWidth, ch = el.clientHeight;
  3389. direction = direction.toLowerCase();
  3390. var scrolled = false;
  3391. var a = this.preanim(arguments, 2);
  3392. switch(direction){
  3393. case "l":
  3394. case "left":
  3395. if(w - l > cw){
  3396. var v = Math.min(l + distance, w-cw);
  3397. this.scrollTo("left", v, a);
  3398. scrolled = true;
  3399. }
  3400. break;
  3401. case "r":
  3402. case "right":
  3403. if(l > 0){
  3404. var v = Math.max(l - distance, 0);
  3405. this.scrollTo("left", v, a);
  3406. scrolled = true;
  3407. }
  3408. break;
  3409. case "t":
  3410. case "top":
  3411. case "up":
  3412. if(t > 0){
  3413. var v = Math.max(t - distance, 0);
  3414. this.scrollTo("top", v, a);
  3415. scrolled = true;
  3416. }
  3417. break;
  3418. case "b":
  3419. case "bottom":
  3420. case "down":
  3421. if(h - t > ch){
  3422. var v = Math.min(t + distance, h-ch);
  3423. this.scrollTo("top", v, a);
  3424. scrolled = true;
  3425. }
  3426. break;
  3427. }
  3428. return scrolled;
  3429. },
  3430. translatePoints : function(x, y){
  3431. if(typeof x == 'object' || Ext.isArray(x)){
  3432. y = x[1]; x = x[0];
  3433. }
  3434. var p = this.getStyle('position');
  3435. var o = this.getXY();
  3436. var l = parseInt(this.getStyle('left'), 10);
  3437. var t = parseInt(this.getStyle('top'), 10);
  3438. if(isNaN(l)){
  3439. l = (p == "relative") ? 0 : this.dom.offsetLeft;
  3440. }
  3441. if(isNaN(t)){
  3442. t = (p == "relative") ? 0 : this.dom.offsetTop;
  3443. }
  3444. return {left: (x - o[0] + l), top: (y - o[1] + t)};
  3445. },
  3446. getScroll : function(){
  3447. var d = this.dom, doc = document;
  3448. if(d == doc || d == doc.body){
  3449. var l, t;
  3450. if(Ext.isIE && Ext.isStrict){
  3451. l = doc.documentElement.scrollLeft || (doc.body.scrollLeft || 0);
  3452. t = doc.documentElement.scrollTop || (doc.body.scrollTop || 0);
  3453. }else{
  3454. l = window.pageXOffset || (doc.body.scrollLeft || 0);
  3455. t = window.pageYOffset || (doc.body.scrollTop || 0);
  3456. }
  3457. return {left: l, top: t};
  3458. }else{
  3459. return {left: d.scrollLeft, top: d.scrollTop};
  3460. }
  3461. },
  3462. getColor : function(attr, defaultValue, prefix){
  3463. var v = this.getStyle(attr);
  3464. if(!v || v == "transparent" || v == "inherit") {
  3465. return defaultValue;
  3466. }
  3467. var color = typeof prefix == "undefined" ? "#" : prefix;
  3468. if(v.substr(0, 4) == "rgb("){
  3469. var rvs = v.slice(4, v.length -1).split(",");
  3470. for(var i = 0; i < 3; i++){
  3471. var h = parseInt(rvs[i]);
  3472. var s = h.toString(16);
  3473. if(h < 16){
  3474. s = "0" + s;
  3475. }
  3476. color += s;
  3477. }
  3478. } else {
  3479. if(v.substr(0, 1) == "#"){
  3480. if(v.length == 4) {
  3481. for(var i = 1; i < 4; i++){
  3482. var c = v.charAt(i);
  3483. color += c + c;
  3484. }
  3485. }else if(v.length == 7){
  3486. color += v.substr(1);
  3487. }
  3488. }
  3489. }
  3490. return(color.length > 5 ? color.toLowerCase() : defaultValue);
  3491. },
  3492. boxWrap : function(cls){
  3493. cls = cls || 'x-box';
  3494. var el = Ext.get(this.insertHtml('beforeBegin', String.format('<div class="{0}">'+El.boxMarkup+'</div>', cls)));
  3495. el.child('.'+cls+'-mc').dom.appendChild(this.dom);
  3496. return el;
  3497. },
  3498. getAttributeNS : Ext.isIE ? function(ns, name){
  3499. var d = this.dom;
  3500. var type = typeof d[ns+":"+name];
  3501. if(type != 'undefined' && type != 'unknown'){
  3502. return d[ns+":"+name];
  3503. }
  3504. return d[name];
  3505. } : function(ns, name){
  3506. var d = this.dom;
  3507. return d.getAttributeNS(ns, name) || d.getAttribute(ns+":"+name) || d.getAttribute(name) || d[name];
  3508. },
  3509. getTextWidth : function(text, min, max){
  3510. return (Ext.util.TextMetrics.measure(this.dom, Ext.value(text, this.dom.innerHTML, true)).width).constrain(min || 0, max || 1000000);
  3511. }
  3512. };
  3513. var ep = El.prototype;
  3514. ep.on = ep.addListener;
  3515. // backwards compat
  3516. ep.mon = ep.addListener;
  3517. ep.getUpdateManager = ep.getUpdater;
  3518. ep.un = ep.removeListener;
  3519. ep.autoBoxAdjust = true;
  3520. // private
  3521. El.unitPattern = /\d+(px|em|%|en|ex|pt|in|cm|mm|pc)$/i;
  3522. // private
  3523. El.addUnits = function(v, defaultUnit){
  3524. if(v === "" || v == "auto"){
  3525. return v;
  3526. }
  3527. if(v === undefined){
  3528. return '';
  3529. }
  3530. if(typeof v == "number" || !El.unitPattern.test(v)){
  3531. return v + (defaultUnit || 'px');
  3532. }
  3533. return v;
  3534. };
  3535. // special markup used throughout Ext when box wrapping elements
  3536. El.boxMarkup = '<div class="{0}-tl"><div class="{0}-tr"><div class="{0}-tc"></div></div></div><div class="{0}-ml"><div class="{0}-mr"><div class="{0}-mc"></div></div></div><div class="{0}-bl"><div class="{0}-br"><div class="{0}-bc"></div></div></div>';
  3537. El.VISIBILITY = 1;
  3538. El.DISPLAY = 2;
  3539. El.borders = {l: "border-left-width", r: "border-right-width", t: "border-top-width", b: "border-bottom-width"};
  3540. El.paddings = {l: "padding-left", r: "padding-right", t: "padding-top", b: "padding-bottom"};
  3541. El.margins = {l: "margin-left", r: "margin-right", t: "margin-top", b: "margin-bottom"};
  3542. El.cache = {};
  3543. var docEl;
  3544. El.get = function(el){
  3545. var ex, elm, id;
  3546. if(!el){ return null; }
  3547. if(typeof el == "string"){ // element id
  3548. if(!(elm = document.getElementById(el))){
  3549. return null;
  3550. }
  3551. if(ex = El.cache[el]){
  3552. ex.dom = elm;
  3553. }else{
  3554. ex = El.cache[el] = new El(elm);
  3555. }
  3556. return ex;
  3557. }else if(el.tagName){ // dom element
  3558. if(!(id = el.id)){
  3559. id = Ext.id(el);
  3560. }
  3561. if(ex = El.cache[id]){
  3562. ex.dom = el;
  3563. }else{
  3564. ex = El.cache[id] = new El(el);
  3565. }
  3566. return ex;
  3567. }else if(el instanceof El){
  3568. if(el != docEl){
  3569. el.dom = document.getElementById(el.id) || el.dom; // refresh dom element in case no longer valid,
  3570. // catch case where it hasn't been appended
  3571. El.cache[el.id] = el; // in case it was created directly with Element(), let's cache it
  3572. }
  3573. return el;
  3574. }else if(el.isComposite){
  3575. return el;
  3576. }else if(Ext.isArray(el)){
  3577. return El.select(el);
  3578. }else if(el == document){
  3579. // create a bogus element object representing the document object
  3580. if(!docEl){
  3581. var f = function(){};
  3582. f.prototype = El.prototype;
  3583. docEl = new f();
  3584. docEl.dom = document;
  3585. }
  3586. return docEl;
  3587. }
  3588. return null;
  3589. };
  3590. // private
  3591. El.uncache = function(el){
  3592. for(var i = 0, a = arguments, len = a.length; i < len; i++) {
  3593. if(a[i]){
  3594. delete El.cache[a[i].id || a[i]];
  3595. }
  3596. }
  3597. };
  3598. // private
  3599. // Garbage collection - uncache elements/purge listeners on orphaned elements
  3600. // so we don't hold a reference and cause the browser to retain them
  3601. El.garbageCollect = function(){
  3602. if(!Ext.enableGarbageCollector){
  3603. clearInterval(El.collectorThread);
  3604. return;
  3605. }
  3606. for(var eid in El.cache){
  3607. var el = El.cache[eid], d = el.dom;
  3608. // -------------------------------------------------------
  3609. // Determining what is garbage:
  3610. // -------------------------------------------------------
  3611. // !d
  3612. // dom node is null, definitely garbage
  3613. // -------------------------------------------------------
  3614. // !d.parentNode
  3615. // no parentNode == direct orphan, definitely garbage
  3616. // -------------------------------------------------------
  3617. // !d.offsetParent && !document.getElementById(eid)
  3618. // display none elements have no offsetParent so we will
  3619. // also try to look it up by it's id. However, check
  3620. // offsetParent first so we don't do unneeded lookups.
  3621. // This enables collection of elements that are not orphans
  3622. // directly, but somewhere up the line they have an orphan
  3623. // parent.
  3624. // -------------------------------------------------------
  3625. if(!d || !d.parentNode || (!d.offsetParent && !document.getElementById(eid))){
  3626. delete El.cache[eid];
  3627. if(d && Ext.enableListenerCollection){
  3628. Ext.EventManager.removeAll(d);
  3629. }
  3630. }
  3631. }
  3632. }
  3633. El.collectorThreadId = setInterval(El.garbageCollect, 30000);
  3634. var flyFn = function(){};
  3635. flyFn.prototype = El.prototype;
  3636. var _cls = new flyFn();
  3637. // dom is optional
  3638. El.Flyweight = function(dom){
  3639. this.dom = dom;
  3640. };
  3641. El.Flyweight.prototype = _cls;
  3642. El.Flyweight.prototype.isFlyweight = true;
  3643. El._flyweights = {};
  3644. El.fly = function(el, named){
  3645. named = named || '_global';
  3646. el = Ext.getDom(el);
  3647. if(!el){
  3648. return null;
  3649. }
  3650. if(!El._flyweights[named]){
  3651. El._flyweights[named] = new El.Flyweight();
  3652. }
  3653. El._flyweights[named].dom = el;
  3654. return El._flyweights[named];
  3655. };
  3656. Ext.get = El.get;
  3657. Ext.fly = El.fly;
  3658. // speedy lookup for elements never to box adjust
  3659. var noBoxAdjust = Ext.isStrict ? {
  3660. select:1
  3661. } : {
  3662. input:1, select:1, textarea:1
  3663. };
  3664. if(Ext.isIE || Ext.isGecko){
  3665. noBoxAdjust['button'] = 1;
  3666. }
  3667. Ext.EventManager.on(window, 'unload', function(){
  3668. delete El.cache;
  3669. delete El._flyweights;
  3670. });
  3671. })();
  3672. //Notifies Element that fx methods are available
  3673. Ext.enableFx = true;
  3674. Ext.Fx = {
  3675. slideIn : function(anchor, o){
  3676. var el = this.getFxEl();
  3677. o = o || {};
  3678. el.queueFx(o, function(){
  3679. anchor = anchor || "t";
  3680. // fix display to visibility
  3681. this.fixDisplay();
  3682. // restore values after effect
  3683. var r = this.getFxRestore();
  3684. var b = this.getBox();
  3685. // fixed size for slide
  3686. this.setSize(b);
  3687. // wrap if needed
  3688. var wrap = this.fxWrap(r.pos, o, "hidden");
  3689. var st = this.dom.style;
  3690. st.visibility = "visible";
  3691. st.position = "absolute";
  3692. // clear out temp styles after slide and unwrap
  3693. var after = function(){
  3694. el.fxUnwrap(wrap, r.pos, o);
  3695. st.width = r.width;
  3696. st.height = r.height;
  3697. el.afterFx(o);
  3698. };
  3699. // time to calc the positions
  3700. var a, pt = {to: [b.x, b.y]}, bw = {to: b.width}, bh = {to: b.height};
  3701. switch(anchor.toLowerCase()){
  3702. case "t":
  3703. wrap.setSize(b.width, 0);
  3704. st.left = st.bottom = "0";
  3705. a = {height: bh};
  3706. break;
  3707. case "l":
  3708. wrap.setSize(0, b.height);
  3709. st.right = st.top = "0";
  3710. a = {width: bw};
  3711. break;
  3712. case "r":
  3713. wrap.setSize(0, b.height);
  3714. wrap.setX(b.right);
  3715. st.left = st.top = "0";
  3716. a = {width: bw, points: pt};
  3717. break;
  3718. case "b":
  3719. wrap.setSize(b.width, 0);
  3720. wrap.setY(b.bottom);
  3721. st.left = st.top = "0";
  3722. a = {height: bh, points: pt};
  3723. break;
  3724. case "tl":
  3725. wrap.setSize(0, 0);
  3726. st.right = st.bottom = "0";
  3727. a = {width: bw, height: bh};
  3728. break;
  3729. case "bl":
  3730. wrap.setSize(0, 0);
  3731. wrap.setY(b.y+b.height);
  3732. st.right = st.top = "0";
  3733. a = {width: bw, height: bh, points: pt};
  3734. break;
  3735. case "br":
  3736. wrap.setSize(0, 0);
  3737. wrap.setXY([b.right, b.bottom]);
  3738. st.left = st.top = "0";
  3739. a = {width: bw, height: bh, points: pt};
  3740. break;
  3741. case "tr":
  3742. wrap.setSize(0, 0);
  3743. wrap.setX(b.x+b.width);
  3744. st.left = st.bottom = "0";
  3745. a = {width: bw, height: bh, points: pt};
  3746. break;
  3747. }
  3748. this.dom.style.visibility = "visible";
  3749. wrap.show();
  3750. arguments.callee.anim = wrap.fxanim(a,
  3751. o,
  3752. 'motion',
  3753. .5,
  3754. 'easeOut', after);
  3755. });
  3756. return this;
  3757. },
  3758. slideOut : function(anchor, o){
  3759. var el = this.getFxEl();
  3760. o = o || {};
  3761. el.queueFx(o, function(){
  3762. anchor = anchor || "t";
  3763. // restore values after effect
  3764. var r = this.getFxRestore();
  3765. var b = this.getBox();
  3766. // fixed size for slide
  3767. this.setSize(b);
  3768. // wrap if needed
  3769. var wrap = this.fxWrap(r.pos, o, "visible");
  3770. var st = this.dom.style;
  3771. st.visibility = "visible";
  3772. st.position = "absolute";
  3773. wrap.setSize(b);
  3774. var after = function(){
  3775. if(o.useDisplay){
  3776. el.setDisplayed(false);
  3777. }else{
  3778. el.hide();
  3779. }
  3780. el.fxUnwrap(wrap, r.pos, o);
  3781. st.width = r.width;
  3782. st.height = r.height;
  3783. el.afterFx(o);
  3784. };
  3785. var a, zero = {to: 0};
  3786. switch(anchor.toLowerCase()){
  3787. case "t":
  3788. st.left = st.bottom = "0";
  3789. a = {height: zero};
  3790. break;
  3791. case "l":
  3792. st.right = st.top = "0";
  3793. a = {width: zero};
  3794. break;
  3795. case "r":
  3796. st.left = st.top = "0";
  3797. a = {width: zero, points: {to:[b.right, b.y]}};
  3798. break;
  3799. case "b":
  3800. st.left = st.top = "0";
  3801. a = {height: zero, points: {to:[b.x, b.bottom]}};
  3802. break;
  3803. case "tl":
  3804. st.right = st.bottom = "0";
  3805. a = {width: zero, height: zero};
  3806. break;
  3807. case "bl":
  3808. st.right = st.top = "0";
  3809. a = {width: zero, height: zero, points: {to:[b.x, b.bottom]}};
  3810. break;
  3811. case "br":
  3812. st.left = st.top = "0";
  3813. a = {width: zero, height: zero, points: {to:[b.x+b.width, b.bottom]}};
  3814. break;
  3815. case "tr":
  3816. st.left = st.bottom = "0";
  3817. a = {width: zero, height: zero, points: {to:[b.right, b.y]}};
  3818. break;
  3819. }
  3820. arguments.callee.anim = wrap.fxanim(a,
  3821. o,
  3822. 'motion',
  3823. .5,
  3824. "easeOut", after);
  3825. });
  3826. return this;
  3827. },
  3828. puff : function(o){
  3829. var el = this.getFxEl();
  3830. o = o || {};
  3831. el.queueFx(o, function(){
  3832. this.clearOpacity();
  3833. this.show();
  3834. // restore values after effect
  3835. var r = this.getFxRestore();
  3836. var st = this.dom.style;
  3837. var after = function(){
  3838. if(o.useDisplay){
  3839. el.setDisplayed(false);
  3840. }else{
  3841. el.hide();
  3842. }
  3843. el.clearOpacity();
  3844. el.setPositioning(r.pos);
  3845. st.width = r.width;
  3846. st.height = r.height;
  3847. st.fontSize = '';
  3848. el.afterFx(o);
  3849. };
  3850. var width = this.getWidth();
  3851. var height = this.getHeight();
  3852. arguments.callee.anim = this.fxanim({
  3853. width : {to: this.adjustWidth(width * 2)},
  3854. height : {to: this.adjustHeight(height * 2)},
  3855. points : {by: [-(width * .5), -(height * .5)]},
  3856. opacity : {to: 0},
  3857. fontSize: {to:200, unit: "%"}
  3858. },
  3859. o,
  3860. 'motion',
  3861. .5,
  3862. "easeOut", after);
  3863. });
  3864. return this;
  3865. },
  3866. switchOff : function(o){
  3867. var el = this.getFxEl();
  3868. o = o || {};
  3869. el.queueFx(o, function(){
  3870. this.clearOpacity();
  3871. this.clip();
  3872. // restore values after effect
  3873. var r = this.getFxRestore();
  3874. var st = this.dom.style;
  3875. var after = function(){
  3876. if(o.useDisplay){
  3877. el.setDisplayed(false);
  3878. }else{
  3879. el.hide();
  3880. }
  3881. el.clearOpacity();
  3882. el.setPositioning(r.pos);
  3883. st.width = r.width;
  3884. st.height = r.height;
  3885. el.afterFx(o);
  3886. };
  3887. this.fxanim({opacity:{to:0.3}}, null, null, .1, null, function(){
  3888. this.clearOpacity();
  3889. (function(){
  3890. this.fxanim({
  3891. height:{to:1},
  3892. points:{by:[0, this.getHeight() * .5]}
  3893. }, o, 'motion', 0.3, 'easeIn', after);
  3894. }).defer(100, this);
  3895. });
  3896. });
  3897. return this;
  3898. },
  3899. highlight : function(color, o){
  3900. var el = this.getFxEl();
  3901. o = o || {};
  3902. el.queueFx(o, function(){
  3903. color = color || "ffff9c";
  3904. var attr = o.attr || "backgroundColor";
  3905. this.clearOpacity();
  3906. this.show();
  3907. var origColor = this.getColor(attr);
  3908. var restoreColor = this.dom.style[attr];
  3909. var endColor = (o.endColor || origColor) || "ffffff";
  3910. var after = function(){
  3911. el.dom.style[attr] = restoreColor;
  3912. el.afterFx(o);
  3913. };
  3914. var a = {};
  3915. a[attr] = {from: color, to: endColor};
  3916. arguments.callee.anim = this.fxanim(a,
  3917. o,
  3918. 'color',
  3919. 1,
  3920. 'easeIn', after);
  3921. });
  3922. return this;
  3923. },
  3924. frame : function(color, count, o){
  3925. var el = this.getFxEl();
  3926. o = o || {};
  3927. el.queueFx(o, function(){
  3928. color = color || "#C3DAF9";
  3929. if(color.length == 6){
  3930. color = "#" + color;
  3931. }
  3932. count = count || 1;
  3933. var duration = o.duration || 1;
  3934. this.show();
  3935. var b = this.getBox();
  3936. var animFn = function(){
  3937. var proxy = Ext.getBody().createChild({
  3938. style:{
  3939. visbility:"hidden",
  3940. position:"absolute",
  3941. "z-index":"35000", // yee haw
  3942. border:"0px solid " + color
  3943. }
  3944. });
  3945. var scale = Ext.isBorderBox ? 2 : 1;
  3946. proxy.animate({
  3947. top:{from:b.y, to:b.y - 20},
  3948. left:{from:b.x, to:b.x - 20},
  3949. borderWidth:{from:0, to:10},
  3950. opacity:{from:1, to:0},
  3951. height:{from:b.height, to:(b.height + (20*scale))},
  3952. width:{from:b.width, to:(b.width + (20*scale))}
  3953. }, duration, function(){
  3954. proxy.remove();
  3955. if(--count > 0){
  3956. animFn();
  3957. }else{
  3958. el.afterFx(o);
  3959. }
  3960. });
  3961. };
  3962. animFn.call(this);
  3963. });
  3964. return this;
  3965. },
  3966. pause : function(seconds){
  3967. var el = this.getFxEl();
  3968. var o = {};
  3969. el.queueFx(o, function(){
  3970. setTimeout(function(){
  3971. el.afterFx(o);
  3972. }, seconds * 1000);
  3973. });
  3974. return this;
  3975. },
  3976. fadeIn : function(o){
  3977. var el = this.getFxEl();
  3978. o = o || {};
  3979. el.queueFx(o, function(){
  3980. this.setOpacity(0);
  3981. this.fixDisplay();
  3982. this.dom.style.visibility = 'visible';
  3983. var to = o.endOpacity || 1;
  3984. arguments.callee.anim = this.fxanim({opacity:{to:to}},
  3985. o, null, .5, "easeOut", function(){
  3986. if(to == 1){
  3987. this.clearOpacity();
  3988. }
  3989. el.afterFx(o);
  3990. });
  3991. });
  3992. return this;
  3993. },
  3994. fadeOut : function(o){
  3995. var el = this.getFxEl();
  3996. o = o || {};
  3997. el.queueFx(o, function(){
  3998. var to = o.endOpacity || 0;
  3999. arguments.callee.anim = this.fxanim({opacity:{to:to}},
  4000. o, null, .5, "easeOut", function(){
  4001. if(to === 0){
  4002. if(this.visibilityMode == Ext.Element.DISPLAY || o.useDisplay){
  4003. this.dom.style.display = "none";
  4004. }else{
  4005. this.dom.style.visibility = "hidden";
  4006. }
  4007. this.clearOpacity();
  4008. }
  4009. el.afterFx(o);
  4010. });
  4011. });
  4012. return this;
  4013. },
  4014. scale : function(w, h, o){
  4015. this.shift(Ext.apply({}, o, {
  4016. width: w,
  4017. height: h
  4018. }));
  4019. return this;
  4020. },
  4021. shift : function(o){
  4022. var el = this.getFxEl();
  4023. o = o || {};
  4024. el.queueFx(o, function(){
  4025. var a = {}, w = o.width, h = o.height, x = o.x, y = o.y, op = o.opacity;
  4026. if(w !== undefined){
  4027. a.width = {to: this.adjustWidth(w)};
  4028. }
  4029. if(h !== undefined){
  4030. a.height = {to: this.adjustHeight(h)};
  4031. }
  4032. if(o.left !== undefined){
  4033. a.left = {to: o.left};
  4034. }
  4035. if(o.top !== undefined){
  4036. a.top = {to: o.top};
  4037. }
  4038. if(o.right !== undefined){
  4039. a.right = {to: o.right};
  4040. }
  4041. if(o.bottom !== undefined){
  4042. a.bottom = {to: o.bottom};
  4043. }
  4044. if(x !== undefined || y !== undefined){
  4045. a.points = {to: [
  4046. x !== undefined ? x : this.getX(),
  4047. y !== undefined ? y : this.getY()
  4048. ]};
  4049. }
  4050. if(op !== undefined){
  4051. a.opacity = {to: op};
  4052. }
  4053. if(o.xy !== undefined){
  4054. a.points = {to: o.xy};
  4055. }
  4056. arguments.callee.anim = this.fxanim(a,
  4057. o, 'motion', .35, "easeOut", function(){
  4058. el.afterFx(o);
  4059. });
  4060. });
  4061. return this;
  4062. },
  4063. ghost : function(anchor, o){
  4064. var el = this.getFxEl();
  4065. o = o || {};
  4066. el.queueFx(o, function(){
  4067. anchor = anchor || "b";
  4068. // restore values after effect
  4069. var r = this.getFxRestore();
  4070. var w = this.getWidth(),
  4071. h = this.getHeight();
  4072. var st = this.dom.style;
  4073. var after = function(){
  4074. if(o.useDisplay){
  4075. el.setDisplayed(false);
  4076. }else{
  4077. el.hide();
  4078. }
  4079. el.clearOpacity();
  4080. el.setPositioning(r.pos);
  4081. st.width = r.width;
  4082. st.height = r.height;
  4083. el.afterFx(o);
  4084. };
  4085. var a = {opacity: {to: 0}, points: {}}, pt = a.points;
  4086. switch(anchor.toLowerCase()){
  4087. case "t":
  4088. pt.by = [0, -h];
  4089. break;
  4090. case "l":
  4091. pt.by = [-w, 0];
  4092. break;
  4093. case "r":
  4094. pt.by = [w, 0];
  4095. break;
  4096. case "b":
  4097. pt.by = [0, h];
  4098. break;
  4099. case "tl":
  4100. pt.by = [-w, -h];
  4101. break;
  4102. case "bl":
  4103. pt.by = [-w, h];
  4104. break;
  4105. case "br":
  4106. pt.by = [w, h];
  4107. break;
  4108. case "tr":
  4109. pt.by = [w, -h];
  4110. break;
  4111. }
  4112. arguments.callee.anim = this.fxanim(a,
  4113. o,
  4114. 'motion',
  4115. .5,
  4116. "easeOut", after);
  4117. });
  4118. return this;
  4119. },
  4120. syncFx : function(){
  4121. this.fxDefaults = Ext.apply(this.fxDefaults || {}, {
  4122. block : false,
  4123. concurrent : true,
  4124. stopFx : false
  4125. });
  4126. return this;
  4127. },
  4128. sequenceFx : function(){
  4129. this.fxDefaults = Ext.apply(this.fxDefaults || {}, {
  4130. block : false,
  4131. concurrent : false,
  4132. stopFx : false
  4133. });
  4134. return this;
  4135. },
  4136. nextFx : function(){
  4137. var ef = this.fxQueue[0];
  4138. if(ef){
  4139. ef.call(this);
  4140. }
  4141. },
  4142. hasActiveFx : function(){
  4143. return this.fxQueue && this.fxQueue[0];
  4144. },
  4145. stopFx : function(){
  4146. if(this.hasActiveFx()){
  4147. var cur = this.fxQueue[0];
  4148. if(cur && cur.anim && cur.anim.isAnimated()){
  4149. this.fxQueue = [cur]; // clear out others
  4150. cur.anim.stop(true);
  4151. }
  4152. }
  4153. return this;
  4154. },
  4155. beforeFx : function(o){
  4156. if(this.hasActiveFx() && !o.concurrent){
  4157. if(o.stopFx){
  4158. this.stopFx();
  4159. return true;
  4160. }
  4161. return false;
  4162. }
  4163. return true;
  4164. },
  4165. hasFxBlock : function(){
  4166. var q = this.fxQueue;
  4167. return q && q[0] && q[0].block;
  4168. },
  4169. queueFx : function(o, fn){
  4170. if(!this.fxQueue){
  4171. this.fxQueue = [];
  4172. }
  4173. if(!this.hasFxBlock()){
  4174. Ext.applyIf(o, this.fxDefaults);
  4175. if(!o.concurrent){
  4176. var run = this.beforeFx(o);
  4177. fn.block = o.block;
  4178. this.fxQueue.push(fn);
  4179. if(run){
  4180. this.nextFx();
  4181. }
  4182. }else{
  4183. fn.call(this);
  4184. }
  4185. }
  4186. return this;
  4187. },
  4188. fxWrap : function(pos, o, vis){
  4189. var wrap;
  4190. if(!o.wrap || !(wrap = Ext.get(o.wrap))){
  4191. var wrapXY;
  4192. if(o.fixPosition){
  4193. wrapXY = this.getXY();
  4194. }
  4195. var div = document.createElement("div");
  4196. div.style.visibility = vis;
  4197. wrap = Ext.get(this.dom.parentNode.insertBefore(div, this.dom));
  4198. wrap.setPositioning(pos);
  4199. if(wrap.getStyle("position") == "static"){
  4200. wrap.position("relative");
  4201. }
  4202. this.clearPositioning('auto');
  4203. wrap.clip();
  4204. wrap.dom.appendChild(this.dom);
  4205. if(wrapXY){
  4206. wrap.setXY(wrapXY);
  4207. }
  4208. }
  4209. return wrap;
  4210. },
  4211. fxUnwrap : function(wrap, pos, o){
  4212. this.clearPositioning();
  4213. this.setPositioning(pos);
  4214. if(!o.wrap){
  4215. wrap.dom.parentNode.insertBefore(this.dom, wrap.dom);
  4216. wrap.remove();
  4217. }
  4218. },
  4219. getFxRestore : function(){
  4220. var st = this.dom.style;
  4221. return {pos: this.getPositioning(), width: st.width, height : st.height};
  4222. },
  4223. afterFx : function(o){
  4224. if(o.afterStyle){
  4225. this.applyStyles(o.afterStyle);
  4226. }
  4227. if(o.afterCls){
  4228. this.addClass(o.afterCls);
  4229. }
  4230. if(o.remove === true){
  4231. this.remove();
  4232. }
  4233. Ext.callback(o.callback, o.scope, [this]);
  4234. if(!o.concurrent){
  4235. this.fxQueue.shift();
  4236. this.nextFx();
  4237. }
  4238. },
  4239. getFxEl : function(){ // support for composite element fx
  4240. return Ext.get(this.dom);
  4241. },
  4242. fxanim : function(args, opt, animType, defaultDur, defaultEase, cb){
  4243. animType = animType || 'run';
  4244. opt = opt || {};
  4245. var anim = Ext.lib.Anim[animType](
  4246. this.dom, args,
  4247. (opt.duration || defaultDur) || .35,
  4248. (opt.easing || defaultEase) || 'easeOut',
  4249. function(){
  4250. Ext.callback(cb, this);
  4251. },
  4252. this
  4253. );
  4254. opt.anim = anim;
  4255. return anim;
  4256. }
  4257. };
  4258. // backwords compat
  4259. Ext.Fx.resize = Ext.Fx.scale;
  4260. //When included, Ext.Fx is automatically applied to Element so that all basic
  4261. //effects are available directly via the Element API
  4262. Ext.apply(Ext.Element.prototype, Ext.Fx);
  4263. Ext.CompositeElement = function(els){
  4264. this.elements = [];
  4265. this.addElements(els);
  4266. };
  4267. Ext.CompositeElement.prototype = {
  4268. isComposite: true,
  4269. addElements : function(els){
  4270. if(!els) return this;
  4271. if(typeof els == "string"){
  4272. els = Ext.Element.selectorFunction(els);
  4273. }
  4274. var yels = this.elements;
  4275. var index = yels.length-1;
  4276. for(var i = 0, len = els.length; i < len; i++) {
  4277. yels[++index] = Ext.get(els[i]);
  4278. }
  4279. return this;
  4280. },
  4281. fill : function(els){
  4282. this.elements = [];
  4283. this.add(els);
  4284. return this;
  4285. },
  4286. filter : function(selector){
  4287. var els = [];
  4288. this.each(function(el){
  4289. if(el.is(selector)){
  4290. els[els.length] = el.dom;
  4291. }
  4292. });
  4293. this.fill(els);
  4294. return this;
  4295. },
  4296. invoke : function(fn, args){
  4297. var els = this.elements;
  4298. for(var i = 0, len = els.length; i < len; i++) {
  4299. Ext.Element.prototype[fn].apply(els[i], args);
  4300. }
  4301. return this;
  4302. },
  4303. add : function(els){
  4304. if(typeof els == "string"){
  4305. this.addElements(Ext.Element.selectorFunction(els));
  4306. }else if(els.length !== undefined){
  4307. this.addElements(els);
  4308. }else{
  4309. this.addElements([els]);
  4310. }
  4311. return this;
  4312. },
  4313. each : function(fn, scope){
  4314. var els = this.elements;
  4315. for(var i = 0, len = els.length; i < len; i++){
  4316. if(fn.call(scope || els[i], els[i], this, i) === false) {
  4317. break;
  4318. }
  4319. }
  4320. return this;
  4321. },
  4322. item : function(index){
  4323. return this.elements[index] || null;
  4324. },
  4325. first : function(){
  4326. return this.item(0);
  4327. },
  4328. last : function(){
  4329. return this.item(this.elements.length-1);
  4330. },
  4331. getCount : function(){
  4332. return this.elements.length;
  4333. },
  4334. contains : function(el){
  4335. return this.indexOf(el) !== -1;
  4336. },
  4337. indexOf : function(el){
  4338. return this.elements.indexOf(Ext.get(el));
  4339. },
  4340. removeElement : function(el, removeDom){
  4341. if(Ext.isArray(el)){
  4342. for(var i = 0, len = el.length; i < len; i++){
  4343. this.removeElement(el[i]);
  4344. }
  4345. return this;
  4346. }
  4347. var index = typeof el == 'number' ? el : this.indexOf(el);
  4348. if(index !== -1 && this.elements[index]){
  4349. if(removeDom){
  4350. var d = this.elements[index];
  4351. if(d.dom){
  4352. d.remove();
  4353. }else{
  4354. Ext.removeNode(d);
  4355. }
  4356. }
  4357. this.elements.splice(index, 1);
  4358. }
  4359. return this;
  4360. },
  4361. replaceElement : function(el, replacement, domReplace){
  4362. var index = typeof el == 'number' ? el : this.indexOf(el);
  4363. if(index !== -1){
  4364. if(domReplace){
  4365. this.elements[index].replaceWith(replacement);
  4366. }else{
  4367. this.elements.splice(index, 1, Ext.get(replacement))
  4368. }
  4369. }
  4370. return this;
  4371. },
  4372. clear : function(){
  4373. this.elements = [];
  4374. }
  4375. };
  4376. (function(){
  4377. Ext.CompositeElement.createCall = function(proto, fnName){
  4378. if(!proto[fnName]){
  4379. proto[fnName] = function(){
  4380. return this.invoke(fnName, arguments);
  4381. };
  4382. }
  4383. };
  4384. for(var fnName in Ext.Element.prototype){
  4385. if(typeof Ext.Element.prototype[fnName] == "function"){
  4386. Ext.CompositeElement.createCall(Ext.CompositeElement.prototype, fnName);
  4387. }
  4388. };
  4389. })();
  4390. Ext.CompositeElementLite = function(els){
  4391. Ext.CompositeElementLite.superclass.constructor.call(this, els);
  4392. this.el = new Ext.Element.Flyweight();
  4393. };
  4394. Ext.extend(Ext.CompositeElementLite, Ext.CompositeElement, {
  4395. addElements : function(els){
  4396. if(els){
  4397. if(Ext.isArray(els)){
  4398. this.elements = this.elements.concat(els);
  4399. }else{
  4400. var yels = this.elements;
  4401. var index = yels.length-1;
  4402. for(var i = 0, len = els.length; i < len; i++) {
  4403. yels[++index] = els[i];
  4404. }
  4405. }
  4406. }
  4407. return this;
  4408. },
  4409. invoke : function(fn, args){
  4410. var els = this.elements;
  4411. var el = this.el;
  4412. for(var i = 0, len = els.length; i < len; i++) {
  4413. el.dom = els[i];
  4414. Ext.Element.prototype[fn].apply(el, args);
  4415. }
  4416. return this;
  4417. },
  4418. item : function(index){
  4419. if(!this.elements[index]){
  4420. return null;
  4421. }
  4422. this.el.dom = this.elements[index];
  4423. return this.el;
  4424. },
  4425. // fixes scope with flyweight
  4426. addListener : function(eventName, handler, scope, opt){
  4427. var els = this.elements;
  4428. for(var i = 0, len = els.length; i < len; i++) {
  4429. Ext.EventManager.on(els[i], eventName, handler, scope || els[i], opt);
  4430. }
  4431. return this;
  4432. },
  4433. each : function(fn, scope){
  4434. var els = this.elements;
  4435. var el = this.el;
  4436. for(var i = 0, len = els.length; i < len; i++){
  4437. el.dom = els[i];
  4438. if(fn.call(scope || el, el, this, i) === false){
  4439. break;
  4440. }
  4441. }
  4442. return this;
  4443. },
  4444. indexOf : function(el){
  4445. return this.elements.indexOf(Ext.getDom(el));
  4446. },
  4447. replaceElement : function(el, replacement, domReplace){
  4448. var index = typeof el == 'number' ? el : this.indexOf(el);
  4449. if(index !== -1){
  4450. replacement = Ext.getDom(replacement);
  4451. if(domReplace){
  4452. var d = this.elements[index];
  4453. d.parentNode.insertBefore(replacement, d);
  4454. Ext.removeNode(d);
  4455. }
  4456. this.elements.splice(index, 1, replacement);
  4457. }
  4458. return this;
  4459. }
  4460. });
  4461. Ext.CompositeElementLite.prototype.on = Ext.CompositeElementLite.prototype.addListener;
  4462. if(Ext.DomQuery){
  4463. Ext.Element.selectorFunction = Ext.DomQuery.select;
  4464. }
  4465. Ext.Element.select = function(selector, unique, root){
  4466. var els;
  4467. if(typeof selector == "string"){
  4468. els = Ext.Element.selectorFunction(selector, root);
  4469. }else if(selector.length !== undefined){
  4470. els = selector;
  4471. }else{
  4472. throw "Invalid selector";
  4473. }
  4474. if(unique === true){
  4475. return new Ext.CompositeElement(els);
  4476. }else{
  4477. return new Ext.CompositeElementLite(els);
  4478. }
  4479. };
  4480. Ext.select = Ext.Element.select;
  4481. Ext.data.Connection = function(config){
  4482. Ext.apply(this, config);
  4483. this.addEvents(
  4484. "beforerequest",
  4485. "requestcomplete",
  4486. "requestexception"
  4487. );
  4488. Ext.data.Connection.superclass.constructor.call(this);
  4489. };
  4490. Ext.extend(Ext.data.Connection, Ext.util.Observable, {
  4491. timeout : 30000,
  4492. autoAbort:false,
  4493. disableCaching: true,
  4494. disableCachingParam: '_dc',
  4495. request : function(o){
  4496. if(this.fireEvent("beforerequest", this, o) !== false){
  4497. var p = o.params;
  4498. if(typeof p == "function"){
  4499. p = p.call(o.scope||window, o);
  4500. }
  4501. if(typeof p == "object"){
  4502. p = Ext.urlEncode(p);
  4503. }
  4504. if(this.extraParams){
  4505. var extras = Ext.urlEncode(this.extraParams);
  4506. p = p ? (p + '&' + extras) : extras;
  4507. }
  4508. var url = o.url || this.url;
  4509. if(typeof url == 'function'){
  4510. url = url.call(o.scope||window, o);
  4511. }
  4512. if(o.form){
  4513. var form = Ext.getDom(o.form);
  4514. url = url || form.action;
  4515. var enctype = form.getAttribute("enctype");
  4516. if(o.isUpload || (enctype && enctype.toLowerCase() == 'multipart/form-data')){
  4517. return this.doFormUpload(o, p, url);
  4518. }
  4519. var f = Ext.lib.Ajax.serializeForm(form);
  4520. p = p ? (p + '&' + f) : f;
  4521. }
  4522. var hs = o.headers;
  4523. if(this.defaultHeaders){
  4524. hs = Ext.apply(hs || {}, this.defaultHeaders);
  4525. if(!o.headers){
  4526. o.headers = hs;
  4527. }
  4528. }
  4529. var cb = {
  4530. success: this.handleResponse,
  4531. failure: this.handleFailure,
  4532. scope: this,
  4533. argument: {options: o},
  4534. timeout : o.timeout || this.timeout
  4535. };
  4536. var method = o.method||this.method||((p || o.xmlData || o.jsonData) ? "POST" : "GET");
  4537. if(method == 'GET' && (this.disableCaching && o.disableCaching !== false) || o.disableCaching === true){
  4538. var dcp = o.disableCachingParam || this.disableCachingParam;
  4539. url += (url.indexOf('?') != -1 ? '&' : '?') + dcp + '=' + (new Date().getTime());
  4540. }
  4541. if(typeof o.autoAbort == 'boolean'){ // options gets top priority
  4542. if(o.autoAbort){
  4543. this.abort();
  4544. }
  4545. }else if(this.autoAbort !== false){
  4546. this.abort();
  4547. }
  4548. if((method == 'GET' || o.xmlData || o.jsonData) && p){
  4549. url += (url.indexOf('?') != -1 ? '&' : '?') + p;
  4550. p = '';
  4551. }
  4552. this.transId = Ext.lib.Ajax.request(method, url, cb, p, o);
  4553. return this.transId;
  4554. }else{
  4555. Ext.callback(o.callback, o.scope, [o, null, null]);
  4556. return null;
  4557. }
  4558. },
  4559. isLoading : function(transId){
  4560. if(transId){
  4561. return Ext.lib.Ajax.isCallInProgress(transId);
  4562. }else{
  4563. return this.transId ? true : false;
  4564. }
  4565. },
  4566. abort : function(transId){
  4567. if(transId || this.isLoading()){
  4568. Ext.lib.Ajax.abort(transId || this.transId);
  4569. }
  4570. },
  4571. // private
  4572. handleResponse : function(response){
  4573. this.transId = false;
  4574. var options = response.argument.options;
  4575. response.argument = options ? options.argument : null;
  4576. this.fireEvent("requestcomplete", this, response, options);
  4577. Ext.callback(options.success, options.scope, [response, options]);
  4578. Ext.callback(options.callback, options.scope, [options, true, response]);
  4579. },
  4580. // private
  4581. handleFailure : function(response, e){
  4582. this.transId = false;
  4583. var options = response.argument.options;
  4584. response.argument = options ? options.argument : null;
  4585. this.fireEvent("requestexception", this, response, options, e);
  4586. Ext.callback(options.failure, options.scope, [response, options]);
  4587. Ext.callback(options.callback, options.scope, [options, false, response]);
  4588. },
  4589. // private
  4590. doFormUpload : function(o, ps, url){
  4591. var id = Ext.id();
  4592. var frame = document.createElement('iframe');
  4593. frame.id = id;
  4594. frame.name = id;
  4595. frame.className = 'x-hidden';
  4596. if(Ext.isIE){
  4597. frame.src = Ext.SSL_SECURE_URL;
  4598. }
  4599. document.body.appendChild(frame);
  4600. if(Ext.isIE){
  4601. document.frames[id].name = id;
  4602. }
  4603. var form = Ext.getDom(o.form);
  4604. form.target = id;
  4605. form.method = 'POST';
  4606. form.enctype = form.encoding = 'multipart/form-data';
  4607. if(url){
  4608. form.action = url;
  4609. }
  4610. var hiddens, hd;
  4611. if(ps){ // add dynamic params
  4612. hiddens = [];
  4613. ps = Ext.urlDecode(ps, false);
  4614. for(var k in ps){
  4615. if(ps.hasOwnProperty(k)){
  4616. hd = document.createElement('input');
  4617. hd.type = 'hidden';
  4618. hd.name = k;
  4619. hd.value = ps[k];
  4620. form.appendChild(hd);
  4621. hiddens.push(hd);
  4622. }
  4623. }
  4624. }
  4625. function cb(){
  4626. var r = { // bogus response object
  4627. responseText : '',
  4628. responseXML : null
  4629. };
  4630. r.argument = o ? o.argument : null;
  4631. try { //
  4632. var doc;
  4633. if(Ext.isIE){
  4634. doc = frame.contentWindow.document;
  4635. }else {
  4636. doc = (frame.contentDocument || window.frames[id].document);
  4637. }
  4638. if(doc && doc.body){
  4639. r.responseText = doc.body.innerHTML;
  4640. }
  4641. if(doc && doc.XMLDocument){
  4642. r.responseXML = doc.XMLDocument;
  4643. }else {
  4644. r.responseXML = doc;
  4645. }
  4646. }
  4647. catch(e) {
  4648. // ignore
  4649. }
  4650. Ext.EventManager.removeListener(frame, 'load', cb, this);
  4651. this.fireEvent("requestcomplete", this, r, o);
  4652. Ext.callback(o.success, o.scope, [r, o]);
  4653. Ext.callback(o.callback, o.scope, [o, true, r]);
  4654. setTimeout(function(){Ext.removeNode(frame);}, 100);
  4655. }
  4656. Ext.EventManager.on(frame, 'load', cb, this);
  4657. form.submit();
  4658. if(hiddens){ // remove dynamic params
  4659. for(var i = 0, len = hiddens.length; i < len; i++){
  4660. Ext.removeNode(hiddens[i]);
  4661. }
  4662. }
  4663. }
  4664. });
  4665. Ext.Ajax = new Ext.data.Connection({
  4666. autoAbort : false,
  4667. serializeForm : function(form){
  4668. return Ext.lib.Ajax.serializeForm(form);
  4669. }
  4670. });
  4671. Ext.Updater = Ext.extend(Ext.util.Observable, {
  4672. constructor: function(el, forceNew){
  4673. el = Ext.get(el);
  4674. if(!forceNew && el.updateManager){
  4675. return el.updateManager;
  4676. }
  4677. this.el = el;
  4678. this.defaultUrl = null;
  4679. this.addEvents(
  4680. "beforeupdate",
  4681. "update",
  4682. "failure"
  4683. );
  4684. var d = Ext.Updater.defaults;
  4685. this.sslBlankUrl = d.sslBlankUrl;
  4686. this.disableCaching = d.disableCaching;
  4687. this.indicatorText = d.indicatorText;
  4688. this.showLoadIndicator = d.showLoadIndicator;
  4689. this.timeout = d.timeout;
  4690. this.loadScripts = d.loadScripts;
  4691. this.transaction = null;
  4692. this.refreshDelegate = this.refresh.createDelegate(this);
  4693. this.updateDelegate = this.update.createDelegate(this);
  4694. this.formUpdateDelegate = this.formUpdate.createDelegate(this);
  4695. if(!this.renderer){
  4696. this.renderer = this.getDefaultRenderer();
  4697. }
  4698. Ext.Updater.superclass.constructor.call(this);
  4699. },
  4700. getDefaultRenderer: function() {
  4701. return new Ext.Updater.BasicRenderer();
  4702. },
  4703. getEl : function(){
  4704. return this.el;
  4705. },
  4706. update : function(url, params, callback, discardUrl){
  4707. if(this.fireEvent("beforeupdate", this.el, url, params) !== false){
  4708. var cfg, callerScope;
  4709. if(typeof url == "object"){ // must be config object
  4710. cfg = url;
  4711. url = cfg.url;
  4712. params = params || cfg.params;
  4713. callback = callback || cfg.callback;
  4714. discardUrl = discardUrl || cfg.discardUrl;
  4715. callerScope = cfg.scope;
  4716. if(typeof cfg.nocache != "undefined"){this.disableCaching = cfg.nocache;};
  4717. if(typeof cfg.text != "undefined"){this.indicatorText = '<div class="loading-indicator">'+cfg.text+"</div>";};
  4718. if(typeof cfg.scripts != "undefined"){this.loadScripts = cfg.scripts;};
  4719. if(typeof cfg.timeout != "undefined"){this.timeout = cfg.timeout;};
  4720. }
  4721. this.showLoading();
  4722. if(!discardUrl){
  4723. this.defaultUrl = url;
  4724. }
  4725. if(typeof url == "function"){
  4726. url = url.call(this);
  4727. }
  4728. var o = Ext.apply({}, {
  4729. url : url,
  4730. params: (typeof params == "function" && callerScope) ? params.createDelegate(callerScope) : params,
  4731. success: this.processSuccess,
  4732. failure: this.processFailure,
  4733. scope: this,
  4734. callback: undefined,
  4735. timeout: (this.timeout*1000),
  4736. disableCaching: this.disableCaching,
  4737. argument: {
  4738. "options": cfg,
  4739. "url": url,
  4740. "form": null,
  4741. "callback": callback,
  4742. "scope": callerScope || window,
  4743. "params": params
  4744. }
  4745. }, cfg);
  4746. this.transaction = Ext.Ajax.request(o);
  4747. }
  4748. },
  4749. formUpdate : function(form, url, reset, callback){
  4750. if(this.fireEvent("beforeupdate", this.el, form, url) !== false){
  4751. if(typeof url == "function"){
  4752. url = url.call(this);
  4753. }
  4754. form = Ext.getDom(form)
  4755. this.transaction = Ext.Ajax.request({
  4756. form: form,
  4757. url:url,
  4758. success: this.processSuccess,
  4759. failure: this.processFailure,
  4760. scope: this,
  4761. timeout: (this.timeout*1000),
  4762. argument: {
  4763. "url": url,
  4764. "form": form,
  4765. "callback": callback,
  4766. "reset": reset
  4767. }
  4768. });
  4769. this.showLoading.defer(1, this);
  4770. }
  4771. },
  4772. refresh : function(callback){
  4773. if(this.defaultUrl == null){
  4774. return;
  4775. }
  4776. this.update(this.defaultUrl, null, callback, true);
  4777. },
  4778. startAutoRefresh : function(interval, url, params, callback, refreshNow){
  4779. if(refreshNow){
  4780. this.update(url || this.defaultUrl, params, callback, true);
  4781. }
  4782. if(this.autoRefreshProcId){
  4783. clearInterval(this.autoRefreshProcId);
  4784. }
  4785. this.autoRefreshProcId = setInterval(this.update.createDelegate(this, [url || this.defaultUrl, params, callback, true]), interval*1000);
  4786. },
  4787. stopAutoRefresh : function(){
  4788. if(this.autoRefreshProcId){
  4789. clearInterval(this.autoRefreshProcId);
  4790. delete this.autoRefreshProcId;
  4791. }
  4792. },
  4793. isAutoRefreshing : function(){
  4794. return this.autoRefreshProcId ? true : false;
  4795. },
  4796. showLoading : function(){
  4797. if(this.showLoadIndicator){
  4798. this.el.update(this.indicatorText);
  4799. }
  4800. },
  4801. // private
  4802. processSuccess : function(response){
  4803. this.transaction = null;
  4804. if(response.argument.form && response.argument.reset){
  4805. try{ // put in try/catch since some older FF releases had problems with this
  4806. response.argument.form.reset();
  4807. }catch(e){}
  4808. }
  4809. if(this.loadScripts){
  4810. this.renderer.render(this.el, response, this,
  4811. this.updateComplete.createDelegate(this, [response]));
  4812. }else{
  4813. this.renderer.render(this.el, response, this);
  4814. this.updateComplete(response);
  4815. }
  4816. },
  4817. // private
  4818. updateComplete : function(response){
  4819. this.fireEvent("update", this.el, response);
  4820. if(typeof response.argument.callback == "function"){
  4821. response.argument.callback.call(response.argument.scope, this.el, true, response, response.argument.options);
  4822. }
  4823. },
  4824. // private
  4825. processFailure : function(response){
  4826. this.transaction = null;
  4827. this.fireEvent("failure", this.el, response);
  4828. if(typeof response.argument.callback == "function"){
  4829. response.argument.callback.call(response.argument.scope, this.el, false, response, response.argument.options);
  4830. }
  4831. },
  4832. setRenderer : function(renderer){
  4833. this.renderer = renderer;
  4834. },
  4835. getRenderer : function(){
  4836. return this.renderer;
  4837. },
  4838. setDefaultUrl : function(defaultUrl){
  4839. this.defaultUrl = defaultUrl;
  4840. },
  4841. abort : function(){
  4842. if(this.transaction){
  4843. Ext.Ajax.abort(this.transaction);
  4844. }
  4845. },
  4846. isUpdating : function(){
  4847. if(this.transaction){
  4848. return Ext.Ajax.isLoading(this.transaction);
  4849. }
  4850. return false;
  4851. }
  4852. });
  4853. Ext.Updater.defaults = {
  4854. timeout : 30,
  4855. loadScripts : false,
  4856. sslBlankUrl : (Ext.SSL_SECURE_URL || "javascript:false"),
  4857. disableCaching : false,
  4858. showLoadIndicator : true,
  4859. indicatorText : '<div class="loading-indicator">Loading...</div>'
  4860. };
  4861. Ext.Updater.updateElement = function(el, url, params, options){
  4862. var um = Ext.get(el).getUpdater();
  4863. Ext.apply(um, options);
  4864. um.update(url, params, options ? options.callback : null);
  4865. };
  4866. Ext.Updater.BasicRenderer = function(){};
  4867. Ext.Updater.BasicRenderer.prototype = {
  4868. render : function(el, response, updateManager, callback){
  4869. el.update(response.responseText, updateManager.loadScripts, callback);
  4870. }
  4871. };
  4872. Ext.UpdateManager = Ext.Updater;
  4873. (function() {
  4874. // create private copy of Ext's String.format() method
  4875. // - to remove unnecessary dependency
  4876. // - to resolve namespace conflict with M$-Ajax's implementation
  4877. function xf(format) {
  4878. var args = Array.prototype.slice.call(arguments, 1);
  4879. return format.replace(/\{(\d+)\}/g, function(m, i) {
  4880. return args[i];
  4881. });
  4882. }
  4883. // private
  4884. Date.formatCodeToRegex = function(character, currentGroup) {
  4885. // Note: currentGroup - position in regex result array (see notes for Date.parseCodes below)
  4886. var p = Date.parseCodes[character];
  4887. if (p) {
  4888. p = Ext.type(p) == 'function'? p() : p;
  4889. Date.parseCodes[character] = p; // reassign function result to prevent repeated execution
  4890. }
  4891. return p? Ext.applyIf({
  4892. c: p.c? xf(p.c, currentGroup || "{0}") : p.c
  4893. }, p) : {
  4894. g:0,
  4895. c:null,
  4896. s:Ext.escapeRe(character) // treat unrecognised characters as literals
  4897. }
  4898. }
  4899. // private shorthand for Date.formatCodeToRegex since we'll be using it fairly often
  4900. var $f = Date.formatCodeToRegex;
  4901. Ext.apply(Date, {
  4902. // private
  4903. parseFunctions: {count:0},
  4904. parseRegexes: [],
  4905. formatFunctions: {count:0},
  4906. daysInMonth : [31,28,31,30,31,30,31,31,30,31,30,31],
  4907. y2kYear : 50,
  4908. MILLI : "ms",
  4909. SECOND : "s",
  4910. MINUTE : "mi",
  4911. HOUR : "h",
  4912. DAY : "d",
  4913. MONTH : "mo",
  4914. YEAR : "y",
  4915. dayNames : [
  4916. "Sunday",
  4917. "Monday",
  4918. "Tuesday",
  4919. "Wednesday",
  4920. "Thursday",
  4921. "Friday",
  4922. "Saturday"
  4923. ],
  4924. monthNames : [
  4925. "January",
  4926. "February",
  4927. "March",
  4928. "April",
  4929. "May",
  4930. "June",
  4931. "July",
  4932. "August",
  4933. "September",
  4934. "October",
  4935. "November",
  4936. "December"
  4937. ],
  4938. monthNumbers : {
  4939. Jan:0,
  4940. Feb:1,
  4941. Mar:2,
  4942. Apr:3,
  4943. May:4,
  4944. Jun:5,
  4945. Jul:6,
  4946. Aug:7,
  4947. Sep:8,
  4948. Oct:9,
  4949. Nov:10,
  4950. Dec:11
  4951. },
  4952. getShortMonthName : function(month) {
  4953. return Date.monthNames[month].substring(0, 3);
  4954. },
  4955. getShortDayName : function(day) {
  4956. return Date.dayNames[day].substring(0, 3);
  4957. },
  4958. getMonthNumber : function(name) {
  4959. // handle camel casing for english month names (since the keys for the Date.monthNumbers hash are case sensitive)
  4960. return Date.monthNumbers[name.substring(0, 1).toUpperCase() + name.substring(1, 3).toLowerCase()];
  4961. },
  4962. formatCodes : {
  4963. d: "String.leftPad(this.getDate(), 2, '0')",
  4964. D: "Date.getShortDayName(this.getDay())", // get localised short day name
  4965. j: "this.getDate()",
  4966. l: "Date.dayNames[this.getDay()]",
  4967. N: "(this.getDay() ? this.getDay() : 7)",
  4968. S: "this.getSuffix()",
  4969. w: "this.getDay()",
  4970. z: "this.getDayOfYear()",
  4971. W: "String.leftPad(this.getWeekOfYear(), 2, '0')",
  4972. F: "Date.monthNames[this.getMonth()]",
  4973. m: "String.leftPad(this.getMonth() + 1, 2, '0')",
  4974. M: "Date.getShortMonthName(this.getMonth())", // get localised short month name
  4975. n: "(this.getMonth() + 1)",
  4976. t: "this.getDaysInMonth()",
  4977. L: "(this.isLeapYear() ? 1 : 0)",
  4978. o: "(this.getFullYear() + (this.getWeekOfYear() == 1 && this.getMonth() > 0 ? +1 : (this.getWeekOfYear() >= 52 && this.getMonth() < 11 ? -1 : 0)))",
  4979. Y: "this.getFullYear()",
  4980. y: "('' + this.getFullYear()).substring(2, 4)",
  4981. a: "(this.getHours() < 12 ? 'am' : 'pm')",
  4982. A: "(this.getHours() < 12 ? 'AM' : 'PM')",
  4983. g: "((this.getHours() % 12) ? this.getHours() % 12 : 12)",
  4984. G: "this.getHours()",
  4985. h: "String.leftPad((this.getHours() % 12) ? this.getHours() % 12 : 12, 2, '0')",
  4986. H: "String.leftPad(this.getHours(), 2, '0')",
  4987. i: "String.leftPad(this.getMinutes(), 2, '0')",
  4988. s: "String.leftPad(this.getSeconds(), 2, '0')",
  4989. u: "String.leftPad(this.getMilliseconds(), 3, '0')",
  4990. O: "this.getGMTOffset()",
  4991. P: "this.getGMTOffset(true)",
  4992. T: "this.getTimezone()",
  4993. Z: "(this.getTimezoneOffset() * -60)",
  4994. c: function() { // ISO-8601 -- GMT format
  4995. for (var c = "Y-m-dTH:i:sP", code = [], i = 0, l = c.length; i < l; ++i) {
  4996. var e = c.charAt(i);
  4997. code.push(e == "T" ? "'T'" : Date.getFormatCode(e)); // treat T as a character literal
  4998. }
  4999. return code.join(" + ");
  5000. },
  5001. U: "Math.round(this.getTime() / 1000)"
  5002. },
  5003. parseDate : function(input, format) {
  5004. var p = Date.parseFunctions;
  5005. if (p[format] == null) {
  5006. Date.createParser(format);
  5007. }
  5008. var func = p[format];
  5009. return Date[func](input);
  5010. },
  5011. // private
  5012. getFormatCode : function(character) {
  5013. var f = Date.formatCodes[character];
  5014. if (f) {
  5015. f = Ext.type(f) == 'function'? f() : f;
  5016. Date.formatCodes[character] = f; // reassign function result to prevent repeated execution
  5017. }
  5018. // note: unknown characters are treated as literals
  5019. return f || ("'" + String.escape(character) + "'");
  5020. },
  5021. // private
  5022. createNewFormat : function(format) {
  5023. var funcName = "format" + Date.formatFunctions.count++,
  5024. code = "Date.prototype." + funcName + " = function(){return ",
  5025. special = false,
  5026. ch = '';
  5027. Date.formatFunctions[format] = funcName;
  5028. for (var i = 0; i < format.length; ++i) {
  5029. ch = format.charAt(i);
  5030. if (!special && ch == "\\") {
  5031. special = true;
  5032. }
  5033. else if (special) {
  5034. special = false;
  5035. code += "'" + String.escape(ch) + "' + ";
  5036. }
  5037. else {
  5038. code += Date.getFormatCode(ch) + " + ";
  5039. }
  5040. }
  5041. eval(code.substring(0, code.length - 3) + ";}");
  5042. },
  5043. // private
  5044. createParser : function() {
  5045. var code = [
  5046. "Date.{0} = function(input){",
  5047. "var y, m, d, h = 0, i = 0, s = 0, ms = 0, o, z, u, v;",
  5048. "input = String(input);",
  5049. "d = new Date();",
  5050. "y = d.getFullYear();",
  5051. "m = d.getMonth();",
  5052. "d = d.getDate();",
  5053. "var results = input.match(Date.parseRegexes[{1}]);",
  5054. "if(results && results.length > 0){",
  5055. "{2}",
  5056. "if(u){",
  5057. "v = new Date(u * 1000);", // give top priority to UNIX time
  5058. "}else if (y >= 0 && m >= 0 && d > 0 && h >= 0 && i >= 0 && s >= 0 && ms >= 0){",
  5059. "v = new Date(y, m, d, h, i, s, ms);",
  5060. "}else if (y >= 0 && m >= 0 && d > 0 && h >= 0 && i >= 0 && s >= 0){",
  5061. "v = new Date(y, m, d, h, i, s);",
  5062. "}else if (y >= 0 && m >= 0 && d > 0 && h >= 0 && i >= 0){",
  5063. "v = new Date(y, m, d, h, i);",
  5064. "}else if (y >= 0 && m >= 0 && d > 0 && h >= 0){",
  5065. "v = new Date(y, m, d, h);",
  5066. "}else if (y >= 0 && m >= 0 && d > 0){",
  5067. "v = new Date(y, m, d);",
  5068. "}else if (y >= 0 && m >= 0){",
  5069. "v = new Date(y, m);",
  5070. "}else if (y >= 0){",
  5071. "v = new Date(y);",
  5072. "}",
  5073. "}",
  5074. "return (v && (z != null || o != null))?" // favour UTC offset over GMT offset
  5075. + " (Ext.type(z) == 'number' ? v.add(Date.SECOND, -v.getTimezoneOffset() * 60 - z) :" // reset to UTC, then add offset
  5076. + " v.add(Date.MINUTE, -v.getTimezoneOffset() + (sn == '+'? -1 : 1) * (hr * 60 + mn))) : v;", // reset to GMT, then add offset
  5077. "}"
  5078. ].join('\n');
  5079. return function(format) {
  5080. var funcName = "parse" + Date.parseFunctions.count++,
  5081. regexNum = Date.parseRegexes.length,
  5082. currentGroup = 1,
  5083. calc = "",
  5084. regex = "",
  5085. special = false,
  5086. ch = "";
  5087. Date.parseFunctions[format] = funcName;
  5088. for (var i = 0; i < format.length; ++i) {
  5089. ch = format.charAt(i);
  5090. if (!special && ch == "\\") {
  5091. special = true;
  5092. }
  5093. else if (special) {
  5094. special = false;
  5095. regex += String.escape(ch);
  5096. }
  5097. else {
  5098. var obj = $f(ch, currentGroup);
  5099. currentGroup += obj.g;
  5100. regex += obj.s;
  5101. if (obj.g && obj.c) {
  5102. calc += obj.c;
  5103. }
  5104. }
  5105. }
  5106. Date.parseRegexes[regexNum] = new RegExp("^" + regex + "$", "i");
  5107. eval(xf(code, funcName, regexNum, calc));
  5108. }
  5109. }(),
  5110. // private
  5111. parseCodes : {
  5112. d: {
  5113. g:1,
  5114. c:"d = parseInt(results[{0}], 10);\n",
  5115. s:"(\\d{2})" // day of month with leading zeroes (01 - 31)
  5116. },
  5117. j: {
  5118. g:1,
  5119. c:"d = parseInt(results[{0}], 10);\n",
  5120. s:"(\\d{1,2})" // day of month without leading zeroes (1 - 31)
  5121. },
  5122. D: function() {
  5123. for (var a = [], i = 0; i < 7; a.push(Date.getShortDayName(i)), ++i); // get localised short day names
  5124. return {
  5125. g:0,
  5126. c:null,
  5127. s:"(?:" + a.join("|") +")"
  5128. }
  5129. },
  5130. l: function() {
  5131. return {
  5132. g:0,
  5133. c:null,
  5134. s:"(?:" + Date.dayNames.join("|") + ")"
  5135. }
  5136. },
  5137. N: {
  5138. g:0,
  5139. c:null,
  5140. s:"[1-7]" // ISO-8601 day number (1 (monday) - 7 (sunday))
  5141. },
  5142. S: {
  5143. g:0,
  5144. c:null,
  5145. s:"(?:st|nd|rd|th)"
  5146. },
  5147. w: {
  5148. g:0,
  5149. c:null,
  5150. s:"[0-6]" // javascript day number (0 (sunday) - 6 (saturday))
  5151. },
  5152. z: {
  5153. g:0,
  5154. c:null,
  5155. s:"(?:\\d{1,3})" // day of the year (0 - 364 (365 in leap years))
  5156. },
  5157. W: {
  5158. g:0,
  5159. c:null,
  5160. s:"(?:\\d{2})" // ISO-8601 week number (with leading zero)
  5161. },
  5162. F: function() {
  5163. return {
  5164. g:1,
  5165. c:"m = parseInt(Date.getMonthNumber(results[{0}]), 10);\n", // get localised month number
  5166. s:"(" + Date.monthNames.join("|") + ")"
  5167. }
  5168. },
  5169. M: function() {
  5170. for (var a = [], i = 0; i < 12; a.push(Date.getShortMonthName(i)), ++i); // get localised short month names
  5171. return Ext.applyIf({
  5172. s:"(" + a.join("|") + ")"
  5173. }, $f("F"));
  5174. },
  5175. m: {
  5176. g:1,
  5177. c:"m = parseInt(results[{0}], 10) - 1;\n",
  5178. s:"(\\d{2})" // month number with leading zeros (01 - 12)
  5179. },
  5180. n: {
  5181. g:1,
  5182. c:"m = parseInt(results[{0}], 10) - 1;\n",
  5183. s:"(\\d{1,2})" // month number without leading zeros (1 - 12)
  5184. },
  5185. t: {
  5186. g:0,
  5187. c:null,
  5188. s:"(?:\\d{2})" // no. of days in the month (28 - 31)
  5189. },
  5190. L: {
  5191. g:0,
  5192. c:null,
  5193. s:"(?:1|0)"
  5194. },
  5195. o: function() {
  5196. return $f("Y");
  5197. },
  5198. Y: {
  5199. g:1,
  5200. c:"y = parseInt(results[{0}], 10);\n",
  5201. s:"(\\d{4})" // 4-digit year
  5202. },
  5203. y: {
  5204. g:1,
  5205. c:"var ty = parseInt(results[{0}], 10);\n"
  5206. + "y = ty > Date.y2kYear ? 1900 + ty : 2000 + ty;\n", // 2-digit year
  5207. s:"(\\d{1,2})"
  5208. },
  5209. a: {
  5210. g:1,
  5211. c:"if (results[{0}] == 'am') {\n"
  5212. + "if (h == 12) { h = 0; }\n"
  5213. + "} else { if (h < 12) { h += 12; }}",
  5214. s:"(am|pm)"
  5215. },
  5216. A: {
  5217. g:1,
  5218. c:"if (results[{0}] == 'AM') {\n"
  5219. + "if (h == 12) { h = 0; }\n"
  5220. + "} else { if (h < 12) { h += 12; }}",
  5221. s:"(AM|PM)"
  5222. },
  5223. g: function() {
  5224. return $f("G");
  5225. },
  5226. G: {
  5227. g:1,
  5228. c:"h = parseInt(results[{0}], 10);\n",
  5229. s:"(\\d{1,2})" // 24-hr format of an hour without leading zeroes (0 - 23)
  5230. },
  5231. h: function() {
  5232. return $f("H");
  5233. },
  5234. H: {
  5235. g:1,
  5236. c:"h = parseInt(results[{0}], 10);\n",
  5237. s:"(\\d{2})" // 24-hr format of an hour with leading zeroes (00 - 23)
  5238. },
  5239. i: {
  5240. g:1,
  5241. c:"i = parseInt(results[{0}], 10);\n",
  5242. s:"(\\d{2})" // minutes with leading zeros (00 - 59)
  5243. },
  5244. s: {
  5245. g:1,
  5246. c:"s = parseInt(results[{0}], 10);\n",
  5247. s:"(\\d{2})" // seconds with leading zeros (00 - 59)
  5248. },
  5249. u: {
  5250. g:1,
  5251. c:"ms = results[{0}]; ms = parseInt(ms, 10)/Math.pow(10, ms.length - 3);\n",
  5252. s:"(\\d+)" // decimal fraction of a second (minimum = 1 digit, maximum = unlimited)
  5253. },
  5254. O: {
  5255. g:1,
  5256. c:[
  5257. "o = results[{0}];",
  5258. "var sn = o.substring(0,1);", // get + / - sign
  5259. "var hr = o.substring(1,3)*1 + Math.floor(o.substring(3,5) / 60);", // get hours (performs minutes-to-hour conversion also, just in case)
  5260. "var mn = o.substring(3,5) % 60;", // get minutes
  5261. "o = ((-12 <= (hr*60 + mn)/60) && ((hr*60 + mn)/60 <= 14))? (sn + String.leftPad(hr, 2, '0') + String.leftPad(mn, 2, '0')) : null;\n" // -12hrs <= GMT offset <= 14hrs
  5262. ].join("\n"),
  5263. s: "([+\-]\\d{4})" // GMT offset in hrs and mins
  5264. },
  5265. P: {
  5266. g:1,
  5267. c:[
  5268. "o = results[{0}];",
  5269. "var sn = o.substring(0,1);", // get + / - sign
  5270. "var hr = o.substring(1,3)*1 + Math.floor(o.substring(4,6) / 60);", // get hours (performs minutes-to-hour conversion also, just in case)
  5271. "var mn = o.substring(4,6) % 60;", // get minutes
  5272. "o = ((-12 <= (hr*60 + mn)/60) && ((hr*60 + mn)/60 <= 14))? (sn + String.leftPad(hr, 2, '0') + String.leftPad(mn, 2, '0')) : null;\n" // -12hrs <= GMT offset <= 14hrs
  5273. ].join("\n"),
  5274. s: "([+\-]\\d{2}:\\d{2})" // GMT offset in hrs and mins (with colon separator)
  5275. },
  5276. T: {
  5277. g:0,
  5278. c:null,
  5279. s:"[A-Z]{1,4}" // timezone abbrev. may be between 1 - 4 chars
  5280. },
  5281. Z: {
  5282. g:1,
  5283. c:"z = results[{0}] * 1;\n" // -43200 <= UTC offset <= 50400
  5284. + "z = (-43200 <= z && z <= 50400)? z : null;\n",
  5285. s:"([+\-]?\\d{1,5})" // leading '+' sign is optional for UTC offset
  5286. },
  5287. c: function() {
  5288. var calc = [],
  5289. arr = [
  5290. $f("Y", 1), // year
  5291. $f("m", 2), // month
  5292. $f("d", 3), // day
  5293. $f("h", 4), // hour
  5294. $f("i", 5), // minute
  5295. $f("s", 6), // second
  5296. {c:"ms = (results[7] || '.0').substring(1); ms = parseInt(ms, 10)/Math.pow(10, ms.length - 3);\n"}, // decimal fraction of a second (minimum = 1 digit, maximum = unlimited)
  5297. {c:[ // allow both "Z" (i.e. UTC) and "+08:00" (i.e. UTC offset) time zone delimiters
  5298. "if(results[9] == 'Z'){",
  5299. "z = 0;",
  5300. "}else{",
  5301. $f("P", 9).c,
  5302. "}"
  5303. ].join('\n')}
  5304. ];
  5305. for (var i = 0, l = arr.length; i < l; ++i) {
  5306. calc.push(arr[i].c);
  5307. }
  5308. return {
  5309. g:1,
  5310. c:calc.join(""),
  5311. s:arr[0].s + "-" + arr[1].s + "-" + arr[2].s + "T" + arr[3].s + ":" + arr[4].s + ":" + arr[5].s
  5312. + "((\.|,)\\d+)?" // decimal fraction of a second (e.g. ",998465" or ".998465")
  5313. + "(Z|([+\-]\\d{2}:\\d{2}))" // "Z" (UTC) or "+08:00" (UTC offset)
  5314. }
  5315. },
  5316. U: {
  5317. g:1,
  5318. c:"u = parseInt(results[{0}], 10);\n",
  5319. s:"(-?\\d+)" // leading minus sign indicates seconds before UNIX epoch
  5320. }
  5321. }
  5322. });
  5323. }());
  5324. Ext.apply(Date.prototype, {
  5325. // private
  5326. dateFormat : function(format) {
  5327. if (Date.formatFunctions[format] == null) {
  5328. Date.createNewFormat(format);
  5329. }
  5330. var func = Date.formatFunctions[format];
  5331. return this[func]();
  5332. },
  5333. getTimezone : function() {
  5334. // the following list shows the differences between date strings from different browsers on a WinXP SP2 machine from an Asian locale:
  5335. //
  5336. // Opera : "Thu, 25 Oct 2007 22:53:45 GMT+0800" -- shortest (weirdest) date string of the lot
  5337. // Safari : "Thu Oct 25 2007 22:55:35 GMT+0800 (Malay Peninsula Standard Time)" -- value in parentheses always gives the correct timezone (same as FF)
  5338. // FF : "Thu Oct 25 2007 22:55:35 GMT+0800 (Malay Peninsula Standard Time)" -- value in parentheses always gives the correct timezone
  5339. // IE : "Thu Oct 25 22:54:35 UTC+0800 2007" -- (Asian system setting) look for 3-4 letter timezone abbrev
  5340. // IE : "Thu Oct 25 17:06:37 PDT 2007" -- (American system setting) look for 3-4 letter timezone abbrev
  5341. //
  5342. // this crazy regex attempts to guess the correct timezone abbreviation despite these differences.
  5343. // step 1: (?:\((.*)\) -- find timezone in parentheses
  5344. // step 2: ([A-Z]{1,4})(?:[\-+][0-9]{4})?(?: -?\d+)?) -- if nothing was found in step 1, find timezone from timezone offset portion of date string
  5345. // step 3: remove all non uppercase characters found in step 1 and 2
  5346. return this.toString().replace(/^.* (?:\((.*)\)|([A-Z]{1,4})(?:[\-+][0-9]{4})?(?: -?\d+)?)$/, "$1$2").replace(/[^A-Z]/g, "");
  5347. },
  5348. getGMTOffset : function(colon) {
  5349. return (this.getTimezoneOffset() > 0 ? "-" : "+")
  5350. + String.leftPad(Math.floor(Math.abs(this.getTimezoneOffset()) / 60), 2, "0")
  5351. + (colon ? ":" : "")
  5352. + String.leftPad(Math.abs(this.getTimezoneOffset() % 60), 2, "0");
  5353. },
  5354. getDayOfYear : function() {
  5355. var num = 0;
  5356. Date.daysInMonth[1] = this.isLeapYear() ? 29 : 28;
  5357. for (var i = 0; i < this.getMonth(); ++i) {
  5358. num += Date.daysInMonth[i];
  5359. }
  5360. return num + this.getDate() - 1;
  5361. },
  5362. getWeekOfYear : function() {
  5363. // adapted from http://www.merlyn.demon.co.uk/weekcalc.htm
  5364. var ms1d = 864e5, // milliseconds in a day
  5365. ms7d = 7 * ms1d; // milliseconds in a week
  5366. return function() { // return a closure so constants get calculated only once
  5367. var DC3 = Date.UTC(this.getFullYear(), this.getMonth(), this.getDate() + 3) / ms1d, // an Absolute Day Number
  5368. AWN = Math.floor(DC3 / 7), // an Absolute Week Number
  5369. Wyr = new Date(AWN * ms7d).getUTCFullYear();
  5370. return AWN - Math.floor(Date.UTC(Wyr, 0, 7) / ms7d) + 1;
  5371. }
  5372. }(),
  5373. isLeapYear : function() {
  5374. var year = this.getFullYear();
  5375. return !!((year & 3) == 0 && (year % 100 || (year % 400 == 0 && year)));
  5376. },
  5377. getFirstDayOfMonth : function() {
  5378. var day = (this.getDay() - (this.getDate() - 1)) % 7;
  5379. return (day < 0) ? (day + 7) : day;
  5380. },
  5381. getLastDayOfMonth : function() {
  5382. var day = (this.getDay() + (Date.daysInMonth[this.getMonth()] - this.getDate())) % 7;
  5383. return (day < 0) ? (day + 7) : day;
  5384. },
  5385. getFirstDateOfMonth : function() {
  5386. return new Date(this.getFullYear(), this.getMonth(), 1);
  5387. },
  5388. getLastDateOfMonth : function() {
  5389. return new Date(this.getFullYear(), this.getMonth(), this.getDaysInMonth());
  5390. },
  5391. getDaysInMonth : function() {
  5392. Date.daysInMonth[1] = this.isLeapYear() ? 29 : 28;
  5393. return Date.daysInMonth[this.getMonth()];
  5394. },
  5395. getSuffix : function() {
  5396. switch (this.getDate()) {
  5397. case 1:
  5398. case 21:
  5399. case 31:
  5400. return "st";
  5401. case 2:
  5402. case 22:
  5403. return "nd";
  5404. case 3:
  5405. case 23:
  5406. return "rd";
  5407. default:
  5408. return "th";
  5409. }
  5410. },
  5411. clone : function() {
  5412. return new Date(this.getTime());
  5413. },
  5414. clearTime : function(clone){
  5415. if(clone){
  5416. return this.clone().clearTime();
  5417. }
  5418. this.setHours(0);
  5419. this.setMinutes(0);
  5420. this.setSeconds(0);
  5421. this.setMilliseconds(0);
  5422. return this;
  5423. },
  5424. add : function(interval, value){
  5425. var d = this.clone();
  5426. if (!interval || value === 0) return d;
  5427. switch(interval.toLowerCase()){
  5428. case Date.MILLI:
  5429. d.setMilliseconds(this.getMilliseconds() + value);
  5430. break;
  5431. case Date.SECOND:
  5432. d.setSeconds(this.getSeconds() + value);
  5433. break;
  5434. case Date.MINUTE:
  5435. d.setMinutes(this.getMinutes() + value);
  5436. break;
  5437. case Date.HOUR:
  5438. d.setHours(this.getHours() + value);
  5439. break;
  5440. case Date.DAY:
  5441. d.setDate(this.getDate() + value);
  5442. break;
  5443. case Date.MONTH:
  5444. var day = this.getDate();
  5445. if(day > 28){
  5446. day = Math.min(day, this.getFirstDateOfMonth().add('mo', value).getLastDateOfMonth().getDate());
  5447. }
  5448. d.setDate(day);
  5449. d.setMonth(this.getMonth() + value);
  5450. break;
  5451. case Date.YEAR:
  5452. d.setFullYear(this.getFullYear() + value);
  5453. break;
  5454. }
  5455. return d;
  5456. },
  5457. between : function(start, end){
  5458. var t = this.getTime();
  5459. return start.getTime() <= t && t <= end.getTime();
  5460. }
  5461. });
  5462. Date.prototype.format = Date.prototype.dateFormat;
  5463. // private
  5464. // safari setMonth is broken
  5465. if(Ext.isSafari){
  5466. Date.brokenSetMonth = Date.prototype.setMonth;
  5467. Date.prototype.setMonth = function(num){
  5468. if(num <= -1){
  5469. var n = Math.ceil(-num);
  5470. var back_year = Math.ceil(n/12);
  5471. var month = (n % 12) ? 12 - n % 12 : 0 ;
  5472. this.setFullYear(this.getFullYear() - back_year);
  5473. return Date.brokenSetMonth.call(this, month);
  5474. } else {
  5475. return Date.brokenSetMonth.apply(this, arguments);
  5476. }
  5477. };
  5478. }
  5479. Ext.util.DelayedTask = function(fn, scope, args){
  5480. var id = null, d, t;
  5481. var call = function(){
  5482. var now = new Date().getTime();
  5483. if(now - t >= d){
  5484. clearInterval(id);
  5485. id = null;
  5486. fn.apply(scope, args || []);
  5487. }
  5488. };
  5489. this.delay = function(delay, newFn, newScope, newArgs){
  5490. if(id && delay != d){
  5491. this.cancel();
  5492. }
  5493. d = delay;
  5494. t = new Date().getTime();
  5495. fn = newFn || fn;
  5496. scope = newScope || scope;
  5497. args = newArgs || args;
  5498. if(!id){
  5499. id = setInterval(call, d);
  5500. }
  5501. };
  5502. this.cancel = function(){
  5503. if(id){
  5504. clearInterval(id);
  5505. id = null;
  5506. }
  5507. };
  5508. };
  5509. Ext.util.TaskRunner = function(interval){
  5510. interval = interval || 10;
  5511. var tasks = [], removeQueue = [];
  5512. var id = 0;
  5513. var running = false;
  5514. // private
  5515. var stopThread = function(){
  5516. running = false;
  5517. clearInterval(id);
  5518. id = 0;
  5519. };
  5520. // private
  5521. var startThread = function(){
  5522. if(!running){
  5523. running = true;
  5524. id = setInterval(runTasks, interval);
  5525. }
  5526. };
  5527. // private
  5528. var removeTask = function(t){
  5529. removeQueue.push(t);
  5530. if(t.onStop){
  5531. t.onStop.apply(t.scope || t);
  5532. }
  5533. };
  5534. // private
  5535. var runTasks = function(){
  5536. if(removeQueue.length > 0){
  5537. for(var i = 0, len = removeQueue.length; i < len; i++){
  5538. tasks.remove(removeQueue[i]);
  5539. }
  5540. removeQueue = [];
  5541. if(tasks.length < 1){
  5542. stopThread();
  5543. return;
  5544. }
  5545. }
  5546. var now = new Date().getTime();
  5547. for(var i = 0, len = tasks.length; i < len; ++i){
  5548. var t = tasks[i];
  5549. var itime = now - t.taskRunTime;
  5550. if(t.interval <= itime){
  5551. var rt = t.run.apply(t.scope || t, t.args || [++t.taskRunCount]);
  5552. t.taskRunTime = now;
  5553. if(rt === false || t.taskRunCount === t.repeat){
  5554. removeTask(t);
  5555. return;
  5556. }
  5557. }
  5558. if(t.duration && t.duration <= (now - t.taskStartTime)){
  5559. removeTask(t);
  5560. }
  5561. }
  5562. };
  5563. this.start = function(task){
  5564. tasks.push(task);
  5565. task.taskStartTime = new Date().getTime();
  5566. task.taskRunTime = 0;
  5567. task.taskRunCount = 0;
  5568. startThread();
  5569. return task;
  5570. };
  5571. this.stop = function(task){
  5572. removeTask(task);
  5573. return task;
  5574. };
  5575. this.stopAll = function(){
  5576. stopThread();
  5577. for(var i = 0, len = tasks.length; i < len; i++){
  5578. if(tasks[i].onStop){
  5579. tasks[i].onStop();
  5580. }
  5581. }
  5582. tasks = [];
  5583. removeQueue = [];
  5584. };
  5585. };
  5586. Ext.TaskMgr = new Ext.util.TaskRunner();
  5587. Ext.util.MixedCollection = function(allowFunctions, keyFn){
  5588. this.items = [];
  5589. this.map = {};
  5590. this.keys = [];
  5591. this.length = 0;
  5592. this.addEvents(
  5593. "clear",
  5594. "add",
  5595. "replace",
  5596. "remove",
  5597. "sort"
  5598. );
  5599. this.allowFunctions = allowFunctions === true;
  5600. if(keyFn){
  5601. this.getKey = keyFn;
  5602. }
  5603. Ext.util.MixedCollection.superclass.constructor.call(this);
  5604. };
  5605. Ext.extend(Ext.util.MixedCollection, Ext.util.Observable, {
  5606. allowFunctions : false,
  5607. add : function(key, o){
  5608. if(arguments.length == 1){
  5609. o = arguments[0];
  5610. key = this.getKey(o);
  5611. }
  5612. if(typeof key == "undefined" || key === null){
  5613. this.length++;
  5614. this.items.push(o);
  5615. this.keys.push(null);
  5616. }else{
  5617. var old = this.map[key];
  5618. if(old){
  5619. return this.replace(key, o);
  5620. }
  5621. this.length++;
  5622. this.items.push(o);
  5623. this.map[key] = o;
  5624. this.keys.push(key);
  5625. }
  5626. this.fireEvent("add", this.length-1, o, key);
  5627. return o;
  5628. },
  5629. getKey : function(o){
  5630. return o.id;
  5631. },
  5632. replace : function(key, o){
  5633. if(arguments.length == 1){
  5634. o = arguments[0];
  5635. key = this.getKey(o);
  5636. }
  5637. var old = this.item(key);
  5638. if(typeof key == "undefined" || key === null || typeof old == "undefined"){
  5639. return this.add(key, o);
  5640. }
  5641. var index = this.indexOfKey(key);
  5642. this.items[index] = o;
  5643. this.map[key] = o;
  5644. this.fireEvent("replace", key, old, o);
  5645. return o;
  5646. },
  5647. addAll : function(objs){
  5648. if(arguments.length > 1 || Ext.isArray(objs)){
  5649. var args = arguments.length > 1 ? arguments : objs;
  5650. for(var i = 0, len = args.length; i < len; i++){
  5651. this.add(args[i]);
  5652. }
  5653. }else{
  5654. for(var key in objs){
  5655. if(this.allowFunctions || typeof objs[key] != "function"){
  5656. this.add(key, objs[key]);
  5657. }
  5658. }
  5659. }
  5660. },
  5661. each : function(fn, scope){
  5662. var items = [].concat(this.items); // each safe for removal
  5663. for(var i = 0, len = items.length; i < len; i++){
  5664. if(fn.call(scope || items[i], items[i], i, len) === false){
  5665. break;
  5666. }
  5667. }
  5668. },
  5669. eachKey : function(fn, scope){
  5670. for(var i = 0, len = this.keys.length; i < len; i++){
  5671. fn.call(scope || window, this.keys[i], this.items[i], i, len);
  5672. }
  5673. },
  5674. find : function(fn, scope){
  5675. for(var i = 0, len = this.items.length; i < len; i++){
  5676. if(fn.call(scope || window, this.items[i], this.keys[i])){
  5677. return this.items[i];
  5678. }
  5679. }
  5680. return null;
  5681. },
  5682. insert : function(index, key, o){
  5683. if(arguments.length == 2){
  5684. o = arguments[1];
  5685. key = this.getKey(o);
  5686. }
  5687. if(index >= this.length){
  5688. return this.add(key, o);
  5689. }
  5690. this.length++;
  5691. this.items.splice(index, 0, o);
  5692. if(typeof key != "undefined" && key != null){
  5693. this.map[key] = o;
  5694. }
  5695. this.keys.splice(index, 0, key);
  5696. this.fireEvent("add", index, o, key);
  5697. return o;
  5698. },
  5699. remove : function(o){
  5700. return this.removeAt(this.indexOf(o));
  5701. },
  5702. removeAt : function(index){
  5703. if(index < this.length && index >= 0){
  5704. this.length--;
  5705. var o = this.items[index];
  5706. this.items.splice(index, 1);
  5707. var key = this.keys[index];
  5708. if(typeof key != "undefined"){
  5709. delete this.map[key];
  5710. }
  5711. this.keys.splice(index, 1);
  5712. this.fireEvent("remove", o, key);
  5713. return o;
  5714. }
  5715. return false;
  5716. },
  5717. removeKey : function(key){
  5718. return this.removeAt(this.indexOfKey(key));
  5719. },
  5720. getCount : function(){
  5721. return this.length;
  5722. },
  5723. indexOf : function(o){
  5724. return this.items.indexOf(o);
  5725. },
  5726. indexOfKey : function(key){
  5727. return this.keys.indexOf(key);
  5728. },
  5729. item : function(key){
  5730. var item = typeof this.map[key] != "undefined" ? this.map[key] : this.items[key];
  5731. return typeof item != 'function' || this.allowFunctions ? item : null; // for prototype!
  5732. },
  5733. itemAt : function(index){
  5734. return this.items[index];
  5735. },
  5736. key : function(key){
  5737. return this.map[key];
  5738. },
  5739. contains : function(o){
  5740. return this.indexOf(o) != -1;
  5741. },
  5742. containsKey : function(key){
  5743. return typeof this.map[key] != "undefined";
  5744. },
  5745. clear : function(){
  5746. this.length = 0;
  5747. this.items = [];
  5748. this.keys = [];
  5749. this.map = {};
  5750. this.fireEvent("clear");
  5751. },
  5752. first : function(){
  5753. return this.items[0];
  5754. },
  5755. last : function(){
  5756. return this.items[this.length-1];
  5757. },
  5758. // private
  5759. _sort : function(property, dir, fn){
  5760. var dsc = String(dir).toUpperCase() == "DESC" ? -1 : 1;
  5761. fn = fn || function(a, b){
  5762. return a-b;
  5763. };
  5764. var c = [], k = this.keys, items = this.items;
  5765. for(var i = 0, len = items.length; i < len; i++){
  5766. c[c.length] = {key: k[i], value: items[i], index: i};
  5767. }
  5768. c.sort(function(a, b){
  5769. var v = fn(a[property], b[property]) * dsc;
  5770. if(v == 0){
  5771. v = (a.index < b.index ? -1 : 1);
  5772. }
  5773. return v;
  5774. });
  5775. for(var i = 0, len = c.length; i < len; i++){
  5776. items[i] = c[i].value;
  5777. k[i] = c[i].key;
  5778. }
  5779. this.fireEvent("sort", this);
  5780. },
  5781. sort : function(dir, fn){
  5782. this._sort("value", dir, fn);
  5783. },
  5784. keySort : function(dir, fn){
  5785. this._sort("key", dir, fn || function(a, b){
  5786. var v1 = String(a).toUpperCase(), v2 = String(b).toUpperCase();
  5787. return v1 > v2 ? 1 : (v1 < v2 ? -1 : 0);
  5788. });
  5789. },
  5790. getRange : function(start, end){
  5791. var items = this.items;
  5792. if(items.length < 1){
  5793. return [];
  5794. }
  5795. start = start || 0;
  5796. end = Math.min(typeof end == "undefined" ? this.length-1 : end, this.length-1);
  5797. var r = [];
  5798. if(start <= end){
  5799. for(var i = start; i <= end; i++) {
  5800. r[r.length] = items[i];
  5801. }
  5802. }else{
  5803. for(var i = start; i >= end; i--) {
  5804. r[r.length] = items[i];
  5805. }
  5806. }
  5807. return r;
  5808. },
  5809. filter : function(property, value, anyMatch, caseSensitive){
  5810. if(Ext.isEmpty(value, false)){
  5811. return this.clone();
  5812. }
  5813. value = this.createValueMatcher(value, anyMatch, caseSensitive);
  5814. return this.filterBy(function(o){
  5815. return o && value.test(o[property]);
  5816. });
  5817. },
  5818. filterBy : function(fn, scope){
  5819. var r = new Ext.util.MixedCollection();
  5820. r.getKey = this.getKey;
  5821. var k = this.keys, it = this.items;
  5822. for(var i = 0, len = it.length; i < len; i++){
  5823. if(fn.call(scope||this, it[i], k[i])){
  5824. r.add(k[i], it[i]);
  5825. }
  5826. }
  5827. return r;
  5828. },
  5829. findIndex : function(property, value, start, anyMatch, caseSensitive){
  5830. if(Ext.isEmpty(value, false)){
  5831. return -1;
  5832. }
  5833. value = this.createValueMatcher(value, anyMatch, caseSensitive);
  5834. return this.findIndexBy(function(o){
  5835. return o && value.test(o[property]);
  5836. }, null, start);
  5837. },
  5838. findIndexBy : function(fn, scope, start){
  5839. var k = this.keys, it = this.items;
  5840. for(var i = (start||0), len = it.length; i < len; i++){
  5841. if(fn.call(scope||this, it[i], k[i])){
  5842. return i;
  5843. }
  5844. }
  5845. if(typeof start == 'number' && start > 0){
  5846. for(var i = 0; i < start; i++){
  5847. if(fn.call(scope||this, it[i], k[i])){
  5848. return i;
  5849. }
  5850. }
  5851. }
  5852. return -1;
  5853. },
  5854. // private
  5855. createValueMatcher : function(value, anyMatch, caseSensitive){
  5856. if(!value.exec){ // not a regex
  5857. value = String(value);
  5858. value = new RegExp((anyMatch === true ? '' : '^') + Ext.escapeRe(value), caseSensitive ? '' : 'i');
  5859. }
  5860. return value;
  5861. },
  5862. clone : function(){
  5863. var r = new Ext.util.MixedCollection();
  5864. var k = this.keys, it = this.items;
  5865. for(var i = 0, len = it.length; i < len; i++){
  5866. r.add(k[i], it[i]);
  5867. }
  5868. r.getKey = this.getKey;
  5869. return r;
  5870. }
  5871. });
  5872. Ext.util.MixedCollection.prototype.get = Ext.util.MixedCollection.prototype.item;
  5873. Ext.util.JSON = new (function(){
  5874. var useHasOwn = !!{}.hasOwnProperty;
  5875. // crashes Safari in some instances
  5876. //var validRE = /^("(\\.|[^"\\\n\r])*?"|[,:{}\[\]0-9.\-+Eaeflnr-u \n\r\t])+?$/;
  5877. var pad = function(n) {
  5878. return n < 10 ? "0" + n : n;
  5879. };
  5880. var m = {
  5881. "\b": '\\b',
  5882. "\t": '\\t',
  5883. "\n": '\\n',
  5884. "\f": '\\f',
  5885. "\r": '\\r',
  5886. '"' : '\\"',
  5887. "\\": '\\\\'
  5888. };
  5889. var encodeString = function(s){
  5890. if (/["\\\x00-\x1f]/.test(s)) {
  5891. return '"' + s.replace(/([\x00-\x1f\\"])/g, function(a, b) {
  5892. var c = m[b];
  5893. if(c){
  5894. return c;
  5895. }
  5896. c = b.charCodeAt();
  5897. return "\\u00" +
  5898. Math.floor(c / 16).toString(16) +
  5899. (c % 16).toString(16);
  5900. }) + '"';
  5901. }
  5902. return '"' + s + '"';
  5903. };
  5904. var encodeArray = function(o){
  5905. var a = ["["], b, i, l = o.length, v;
  5906. for (i = 0; i < l; i += 1) {
  5907. v = o[i];
  5908. switch (typeof v) {
  5909. case "undefined":
  5910. case "function":
  5911. case "unknown":
  5912. break;
  5913. default:
  5914. if (b) {
  5915. a.push(',');
  5916. }
  5917. a.push(v === null ? "null" : Ext.util.JSON.encode(v));
  5918. b = true;
  5919. }
  5920. }
  5921. a.push("]");
  5922. return a.join("");
  5923. };
  5924. this.encodeDate = function(o){
  5925. return '"' + o.getFullYear() + "-" +
  5926. pad(o.getMonth() + 1) + "-" +
  5927. pad(o.getDate()) + "T" +
  5928. pad(o.getHours()) + ":" +
  5929. pad(o.getMinutes()) + ":" +
  5930. pad(o.getSeconds()) + '"';
  5931. };
  5932. this.encode = function(o){
  5933. if(typeof o == "undefined" || o === null){
  5934. return "null";
  5935. }else if(Ext.isArray(o)){
  5936. return encodeArray(o);
  5937. }else if(Ext.isDate(o)){
  5938. return Ext.util.JSON.encodeDate(o);
  5939. }else if(typeof o == "string"){
  5940. return encodeString(o);
  5941. }else if(typeof o == "number"){
  5942. return isFinite(o) ? String(o) : "null";
  5943. }else if(typeof o == "boolean"){
  5944. return String(o);
  5945. }else {
  5946. var a = ["{"], b, i, v;
  5947. for (i in o) {
  5948. if(!useHasOwn || o.hasOwnProperty(i)) {
  5949. v = o[i];
  5950. switch (typeof v) {
  5951. case "undefined":
  5952. case "function":
  5953. case "unknown":
  5954. break;
  5955. default:
  5956. if(b){
  5957. a.push(',');
  5958. }
  5959. a.push(this.encode(i), ":",
  5960. v === null ? "null" : this.encode(v));
  5961. b = true;
  5962. }
  5963. }
  5964. }
  5965. a.push("}");
  5966. return a.join("");
  5967. }
  5968. };
  5969. this.decode = function(json){
  5970. return eval("(" + json + ')');
  5971. };
  5972. })();
  5973. Ext.encode = Ext.util.JSON.encode;
  5974. Ext.decode = Ext.util.JSON.decode;
  5975. Ext.util.Format = function(){
  5976. var trimRe = /^\s+|\s+$/g;
  5977. return {
  5978. ellipsis : function(value, len){
  5979. if(value && value.length > len){
  5980. return value.substr(0, len-3)+"...";
  5981. }
  5982. return value;
  5983. },
  5984. undef : function(value){
  5985. return value !== undefined ? value : "";
  5986. },
  5987. defaultValue : function(value, defaultValue){
  5988. return value !== undefined && value !== '' ? value : defaultValue;
  5989. },
  5990. htmlEncode : function(value){
  5991. return !value ? value : String(value).replace(/&/g, "&amp;").replace(/>/g, "&gt;").replace(/</g, "&lt;").replace(/"/g, "&quot;");
  5992. },
  5993. htmlDecode : function(value){
  5994. return !value ? value : String(value).replace(/&gt;/g, ">").replace(/&lt;/g, "<").replace(/&quot;/g, '"').replace(/&amp;/g, "&");
  5995. },
  5996. trim : function(value){
  5997. return String(value).replace(trimRe, "");
  5998. },
  5999. substr : function(value, start, length){
  6000. return String(value).substr(start, length);
  6001. },
  6002. lowercase : function(value){
  6003. return String(value).toLowerCase();
  6004. },
  6005. uppercase : function(value){
  6006. return String(value).toUpperCase();
  6007. },
  6008. capitalize : function(value){
  6009. return !value ? value : value.charAt(0).toUpperCase() + value.substr(1).toLowerCase();
  6010. },
  6011. // private
  6012. call : function(value, fn){
  6013. if(arguments.length > 2){
  6014. var args = Array.prototype.slice.call(arguments, 2);
  6015. args.unshift(value);
  6016. return eval(fn).apply(window, args);
  6017. }else{
  6018. return eval(fn).call(window, value);
  6019. }
  6020. },
  6021. usMoney : function(v){
  6022. v = (Math.round((v-0)*100))/100;
  6023. v = (v == Math.floor(v)) ? v + ".00" : ((v*10 == Math.floor(v*10)) ? v + "0" : v);
  6024. v = String(v);
  6025. var ps = v.split('.');
  6026. var whole = ps[0];
  6027. var sub = ps[1] ? '.'+ ps[1] : '.00';
  6028. var r = /(\d+)(\d{3})/;
  6029. while (r.test(whole)) {
  6030. whole = whole.replace(r, '$1' + ',' + '$2');
  6031. }
  6032. v = whole + sub;
  6033. if(v.charAt(0) == '-'){
  6034. return '-$' + v.substr(1);
  6035. }
  6036. return "$" + v;
  6037. },
  6038. date : function(v, format){
  6039. if(!v){
  6040. return "";
  6041. }
  6042. if(!Ext.isDate(v)){
  6043. v = new Date(Date.parse(v));
  6044. }
  6045. return v.dateFormat(format || "m/d/Y");
  6046. },
  6047. dateRenderer : function(format){
  6048. return function(v){
  6049. return Ext.util.Format.date(v, format);
  6050. };
  6051. },
  6052. // private
  6053. stripTagsRE : /<\/?[^>]+>/gi,
  6054. stripTags : function(v){
  6055. return !v ? v : String(v).replace(this.stripTagsRE, "");
  6056. },
  6057. // private
  6058. stripScriptsRe : /(?:<script.*?>)((\n|\r|.)*?)(?:<\/script>)/ig,
  6059. stripScripts : function(v){
  6060. return !v ? v : String(v).replace(this.stripScriptsRe, "");
  6061. },
  6062. fileSize : function(size){
  6063. if(size < 1024) {
  6064. return size + " bytes";
  6065. } else if(size < 1048576) {
  6066. return (Math.round(((size*10) / 1024))/10) + " KB";
  6067. } else {
  6068. return (Math.round(((size*10) / 1048576))/10) + " MB";
  6069. }
  6070. },
  6071. math : function(){
  6072. var fns = {};
  6073. return function(v, a){
  6074. if(!fns[a]){
  6075. fns[a] = new Function('v', 'return v ' + a + ';');
  6076. }
  6077. return fns[a](v);
  6078. }
  6079. }(),
  6080. nl2br : function(v){
  6081. return v === undefined || v === null ? '' : v.replace(/\n/g, '<br/>');
  6082. }
  6083. };
  6084. }();
  6085. Ext.XTemplate = function(){
  6086. Ext.XTemplate.superclass.constructor.apply(this, arguments);
  6087. var s = this.html;
  6088. s = ['<tpl>', s, '</tpl>'].join('');
  6089. var re = /<tpl\b[^>]*>((?:(?=([^<]+))\2|<(?!tpl\b[^>]*>))*?)<\/tpl>/;
  6090. var nameRe = /^<tpl\b[^>]*?for="(.*?)"/;
  6091. var ifRe = /^<tpl\b[^>]*?if="(.*?)"/;
  6092. var execRe = /^<tpl\b[^>]*?exec="(.*?)"/;
  6093. var m, id = 0;
  6094. var tpls = [];
  6095. while(m = s.match(re)){
  6096. var m2 = m[0].match(nameRe);
  6097. var m3 = m[0].match(ifRe);
  6098. var m4 = m[0].match(execRe);
  6099. var exp = null, fn = null, exec = null;
  6100. var name = m2 && m2[1] ? m2[1] : '';
  6101. if(m3){
  6102. exp = m3 && m3[1] ? m3[1] : null;
  6103. if(exp){
  6104. fn = new Function('values', 'parent', 'xindex', 'xcount', 'with(values){ return '+(Ext.util.Format.htmlDecode(exp))+'; }');
  6105. }
  6106. }
  6107. if(m4){
  6108. exp = m4 && m4[1] ? m4[1] : null;
  6109. if(exp){
  6110. exec = new Function('values', 'parent', 'xindex', 'xcount', 'with(values){ '+(Ext.util.Format.htmlDecode(exp))+'; }');
  6111. }
  6112. }
  6113. if(name){
  6114. switch(name){
  6115. case '.': name = new Function('values', 'parent', 'with(values){ return values; }'); break;
  6116. case '..': name = new Function('values', 'parent', 'with(values){ return parent; }'); break;
  6117. default: name = new Function('values', 'parent', 'with(values){ return '+name+'; }');
  6118. }
  6119. }
  6120. tpls.push({
  6121. id: id,
  6122. target: name,
  6123. exec: exec,
  6124. test: fn,
  6125. body: m[1]||''
  6126. });
  6127. s = s.replace(m[0], '{xtpl'+ id + '}');
  6128. ++id;
  6129. }
  6130. for(var i = tpls.length-1; i >= 0; --i){
  6131. this.compileTpl(tpls[i]);
  6132. }
  6133. this.master = tpls[tpls.length-1];
  6134. this.tpls = tpls;
  6135. };
  6136. Ext.extend(Ext.XTemplate, Ext.Template, {
  6137. // private
  6138. re : /\{([\w-\.\#]+)(?:\:([\w\.]*)(?:\((.*?)?\))?)?(\s?[\+\-\*\\]\s?[\d\.\+\-\*\\\(\)]+)?\}/g,
  6139. // private
  6140. codeRe : /\{\[((?:\\\]|.|\n)*?)\]\}/g,
  6141. // private
  6142. applySubTemplate : function(id, values, parent, xindex, xcount){
  6143. var t = this.tpls[id];
  6144. if(t.test && !t.test.call(this, values, parent, xindex, xcount)){
  6145. return '';
  6146. }
  6147. if(t.exec && t.exec.call(this, values, parent, xindex, xcount)){
  6148. return '';
  6149. }
  6150. var vs = t.target ? t.target.call(this, values, parent) : values;
  6151. parent = t.target ? values : parent;
  6152. if(t.target && Ext.isArray(vs)){
  6153. var buf = [];
  6154. for(var i = 0, len = vs.length; i < len; i++){
  6155. buf[buf.length] = t.compiled.call(this, vs[i], parent, i+1, len);
  6156. }
  6157. return buf.join('');
  6158. }
  6159. return t.compiled.call(this, vs, parent, xindex, xcount);
  6160. },
  6161. // private
  6162. compileTpl : function(tpl){
  6163. var fm = Ext.util.Format;
  6164. var useF = this.disableFormats !== true;
  6165. var sep = Ext.isGecko ? "+" : ",";
  6166. var fn = function(m, name, format, args, math){
  6167. if(name.substr(0, 4) == 'xtpl'){
  6168. return "'"+ sep +'this.applySubTemplate('+name.substr(4)+', values, parent, xindex, xcount)'+sep+"'";
  6169. }
  6170. var v;
  6171. if(name === '.'){
  6172. v = 'values';
  6173. }else if(name === '#'){
  6174. v = 'xindex';
  6175. }else if(name.indexOf('.') != -1){
  6176. v = name;
  6177. }else{
  6178. v = "values['" + name + "']";
  6179. }
  6180. if(math){
  6181. v = '(' + v + math + ')';
  6182. }
  6183. if(format && useF){
  6184. args = args ? ',' + args : "";
  6185. if(format.substr(0, 5) != "this."){
  6186. format = "fm." + format + '(';
  6187. }else{
  6188. format = 'this.call("'+ format.substr(5) + '", ';
  6189. args = ", values";
  6190. }
  6191. }else{
  6192. args= ''; format = "("+v+" === undefined ? '' : ";
  6193. }
  6194. return "'"+ sep + format + v + args + ")"+sep+"'";
  6195. };
  6196. var codeFn = function(m, code){
  6197. return "'"+ sep +'('+code+')'+sep+"'";
  6198. };
  6199. var body;
  6200. // branched to use + in gecko and [].join() in others
  6201. if(Ext.isGecko){
  6202. body = "tpl.compiled = function(values, parent, xindex, xcount){ return '" +
  6203. tpl.body.replace(/(\r\n|\n)/g, '\\n').replace(/'/g, "\\'").replace(this.re, fn).replace(this.codeRe, codeFn) +
  6204. "';};";
  6205. }else{
  6206. body = ["tpl.compiled = function(values, parent, xindex, xcount){ return ['"];
  6207. body.push(tpl.body.replace(/(\r\n|\n)/g, '\\n').replace(/'/g, "\\'").replace(this.re, fn).replace(this.codeRe, codeFn));
  6208. body.push("'].join('');};");
  6209. body = body.join('');
  6210. }
  6211. eval(body);
  6212. return this;
  6213. },
  6214. applyTemplate : function(values){
  6215. return this.master.compiled.call(this, values, {}, 1, 1);
  6216. },
  6217. compile : function(){return this;}
  6218. });
  6219. Ext.XTemplate.prototype.apply = Ext.XTemplate.prototype.applyTemplate;
  6220. Ext.XTemplate.from = function(el){
  6221. el = Ext.getDom(el);
  6222. return new Ext.XTemplate(el.value || el.innerHTML);
  6223. };
  6224. Ext.util.CSS = function(){
  6225. var rules = null;
  6226. var doc = document;
  6227. var camelRe = /(-[a-z])/gi;
  6228. var camelFn = function(m, a){ return a.charAt(1).toUpperCase(); };
  6229. return {
  6230. createStyleSheet : function(cssText, id){
  6231. var ss;
  6232. var head = doc.getElementsByTagName("head")[0];
  6233. var rules = doc.createElement("style");
  6234. rules.setAttribute("type", "text/css");
  6235. if(id){
  6236. rules.setAttribute("id", id);
  6237. }
  6238. if(Ext.isIE){
  6239. head.appendChild(rules);
  6240. ss = rules.styleSheet;
  6241. ss.cssText = cssText;
  6242. }else{
  6243. try{
  6244. rules.appendChild(doc.createTextNode(cssText));
  6245. }catch(e){
  6246. rules.cssText = cssText;
  6247. }
  6248. head.appendChild(rules);
  6249. ss = rules.styleSheet ? rules.styleSheet : (rules.sheet || doc.styleSheets[doc.styleSheets.length-1]);
  6250. }
  6251. this.cacheStyleSheet(ss);
  6252. return ss;
  6253. },
  6254. removeStyleSheet : function(id){
  6255. var existing = doc.getElementById(id);
  6256. if(existing){
  6257. existing.parentNode.removeChild(existing);
  6258. }
  6259. },
  6260. swapStyleSheet : function(id, url){
  6261. this.removeStyleSheet(id);
  6262. var ss = doc.createElement("link");
  6263. ss.setAttribute("rel", "stylesheet");
  6264. ss.setAttribute("type", "text/css");
  6265. ss.setAttribute("id", id);
  6266. ss.setAttribute("href", url);
  6267. doc.getElementsByTagName("head")[0].appendChild(ss);
  6268. },
  6269. refreshCache : function(){
  6270. return this.getRules(true);
  6271. },
  6272. // private
  6273. cacheStyleSheet : function(ss){
  6274. if(!rules){
  6275. rules = {};
  6276. }
  6277. try{// try catch for cross domain access issue
  6278. var ssRules = ss.cssRules || ss.rules;
  6279. for(var j = ssRules.length-1; j >= 0; --j){
  6280. rules[ssRules[j].selectorText] = ssRules[j];
  6281. }
  6282. }catch(e){}
  6283. },
  6284. getRules : function(refreshCache){
  6285. if(rules == null || refreshCache){
  6286. rules = {};
  6287. var ds = doc.styleSheets;
  6288. for(var i =0, len = ds.length; i < len; i++){
  6289. try{
  6290. this.cacheStyleSheet(ds[i]);
  6291. }catch(e){}
  6292. }
  6293. }
  6294. return rules;
  6295. },
  6296. getRule : function(selector, refreshCache){
  6297. var rs = this.getRules(refreshCache);
  6298. if(!Ext.isArray(selector)){
  6299. return rs[selector];
  6300. }
  6301. for(var i = 0; i < selector.length; i++){
  6302. if(rs[selector[i]]){
  6303. return rs[selector[i]];
  6304. }
  6305. }
  6306. return null;
  6307. },
  6308. updateRule : function(selector, property, value){
  6309. if(!Ext.isArray(selector)){
  6310. var rule = this.getRule(selector);
  6311. if(rule){
  6312. rule.style[property.replace(camelRe, camelFn)] = value;
  6313. return true;
  6314. }
  6315. }else{
  6316. for(var i = 0; i < selector.length; i++){
  6317. if(this.updateRule(selector[i], property, value)){
  6318. return true;
  6319. }
  6320. }
  6321. }
  6322. return false;
  6323. }
  6324. };
  6325. }();
  6326. Ext.util.ClickRepeater = function(el, config)
  6327. {
  6328. this.el = Ext.get(el);
  6329. this.el.unselectable();
  6330. Ext.apply(this, config);
  6331. this.addEvents(
  6332. "mousedown",
  6333. "click",
  6334. "mouseup"
  6335. );
  6336. this.el.on("mousedown", this.handleMouseDown, this);
  6337. if(this.preventDefault || this.stopDefault){
  6338. this.el.on("click", function(e){
  6339. if(this.preventDefault){
  6340. e.preventDefault();
  6341. }
  6342. if(this.stopDefault){
  6343. e.stopEvent();
  6344. }
  6345. }, this);
  6346. }
  6347. // allow inline handler
  6348. if(this.handler){
  6349. this.on("click", this.handler, this.scope || this);
  6350. }
  6351. Ext.util.ClickRepeater.superclass.constructor.call(this);
  6352. };
  6353. Ext.extend(Ext.util.ClickRepeater, Ext.util.Observable, {
  6354. interval : 20,
  6355. delay: 250,
  6356. preventDefault : true,
  6357. stopDefault : false,
  6358. timer : 0,
  6359. // private
  6360. destroy : function() {
  6361. Ext.destroy(this.el);
  6362. this.purgeListeners();
  6363. },
  6364. // private
  6365. handleMouseDown : function(){
  6366. clearTimeout(this.timer);
  6367. this.el.blur();
  6368. if(this.pressClass){
  6369. this.el.addClass(this.pressClass);
  6370. }
  6371. this.mousedownTime = new Date();
  6372. Ext.getDoc().on("mouseup", this.handleMouseUp, this);
  6373. this.el.on("mouseout", this.handleMouseOut, this);
  6374. this.fireEvent("mousedown", this);
  6375. this.fireEvent("click", this);
  6376. // Do not honor delay or interval if acceleration wanted.
  6377. if (this.accelerate) {
  6378. this.delay = 400;
  6379. }
  6380. this.timer = this.click.defer(this.delay || this.interval, this);
  6381. },
  6382. // private
  6383. click : function(){
  6384. this.fireEvent("click", this);
  6385. this.timer = this.click.defer(this.accelerate ?
  6386. this.easeOutExpo(this.mousedownTime.getElapsed(),
  6387. 400,
  6388. -390,
  6389. 12000) :
  6390. this.interval, this);
  6391. },
  6392. easeOutExpo : function (t, b, c, d) {
  6393. return (t==d) ? b+c : c * (-Math.pow(2, -10 * t/d) + 1) + b;
  6394. },
  6395. // private
  6396. handleMouseOut : function(){
  6397. clearTimeout(this.timer);
  6398. if(this.pressClass){
  6399. this.el.removeClass(this.pressClass);
  6400. }
  6401. this.el.on("mouseover", this.handleMouseReturn, this);
  6402. },
  6403. // private
  6404. handleMouseReturn : function(){
  6405. this.el.un("mouseover", this.handleMouseReturn, this);
  6406. if(this.pressClass){
  6407. this.el.addClass(this.pressClass);
  6408. }
  6409. this.click();
  6410. },
  6411. // private
  6412. handleMouseUp : function(){
  6413. clearTimeout(this.timer);
  6414. this.el.un("mouseover", this.handleMouseReturn, this);
  6415. this.el.un("mouseout", this.handleMouseOut, this);
  6416. Ext.getDoc().un("mouseup", this.handleMouseUp, this);
  6417. this.el.removeClass(this.pressClass);
  6418. this.fireEvent("mouseup", this);
  6419. }
  6420. });
  6421. Ext.KeyNav = function(el, config){
  6422. this.el = Ext.get(el);
  6423. Ext.apply(this, config);
  6424. if(!this.disabled){
  6425. this.disabled = true;
  6426. this.enable();
  6427. }
  6428. };
  6429. Ext.KeyNav.prototype = {
  6430. disabled : false,
  6431. defaultEventAction: "stopEvent",
  6432. forceKeyDown : false,
  6433. // private
  6434. prepareEvent : function(e){
  6435. var k = e.getKey();
  6436. var h = this.keyToHandler[k];
  6437. //if(h && this[h]){
  6438. // e.stopPropagation();
  6439. //}
  6440. if(Ext.isSafari2 && h && k >= 37 && k <= 40){
  6441. e.stopEvent();
  6442. }
  6443. },
  6444. // private
  6445. relay : function(e){
  6446. var k = e.getKey();
  6447. var h = this.keyToHandler[k];
  6448. if(h && this[h]){
  6449. if(this.doRelay(e, this[h], h) !== true){
  6450. e[this.defaultEventAction]();
  6451. }
  6452. }
  6453. },
  6454. // private
  6455. doRelay : function(e, h, hname){
  6456. return h.call(this.scope || this, e);
  6457. },
  6458. // possible handlers
  6459. enter : false,
  6460. left : false,
  6461. right : false,
  6462. up : false,
  6463. down : false,
  6464. tab : false,
  6465. esc : false,
  6466. pageUp : false,
  6467. pageDown : false,
  6468. del : false,
  6469. home : false,
  6470. end : false,
  6471. // quick lookup hash
  6472. keyToHandler : {
  6473. 37 : "left",
  6474. 39 : "right",
  6475. 38 : "up",
  6476. 40 : "down",
  6477. 33 : "pageUp",
  6478. 34 : "pageDown",
  6479. 46 : "del",
  6480. 36 : "home",
  6481. 35 : "end",
  6482. 13 : "enter",
  6483. 27 : "esc",
  6484. 9 : "tab"
  6485. },
  6486. enable: function(){
  6487. if(this.disabled){
  6488. if(this.forceKeyDown || Ext.isIE || Ext.isSafari3 || Ext.isAir){
  6489. this.el.on("keydown", this.relay, this);
  6490. }else{
  6491. this.el.on("keydown", this.prepareEvent, this);
  6492. this.el.on("keypress", this.relay, this);
  6493. }
  6494. this.disabled = false;
  6495. }
  6496. },
  6497. disable: function(){
  6498. if(!this.disabled){
  6499. if(this.forceKeyDown || Ext.isIE || Ext.isSafari3 || Ext.isAir){
  6500. this.el.un("keydown", this.relay, this);
  6501. }else{
  6502. this.el.un("keydown", this.prepareEvent, this);
  6503. this.el.un("keypress", this.relay, this);
  6504. }
  6505. this.disabled = true;
  6506. }
  6507. }
  6508. };
  6509. Ext.KeyMap = function(el, config, eventName){
  6510. this.el = Ext.get(el);
  6511. this.eventName = eventName || "keydown";
  6512. this.bindings = [];
  6513. if(config){
  6514. this.addBinding(config);
  6515. }
  6516. this.enable();
  6517. };
  6518. Ext.KeyMap.prototype = {
  6519. stopEvent : false,
  6520. addBinding : function(config){
  6521. if(Ext.isArray(config)){
  6522. for(var i = 0, len = config.length; i < len; i++){
  6523. this.addBinding(config[i]);
  6524. }
  6525. return;
  6526. }
  6527. var keyCode = config.key,
  6528. shift = config.shift,
  6529. ctrl = config.ctrl,
  6530. alt = config.alt,
  6531. fn = config.fn || config.handler,
  6532. scope = config.scope;
  6533. if (config.stopEvent) {
  6534. this.stopEvent = config.stopEvent;
  6535. }
  6536. if(typeof keyCode == "string"){
  6537. var ks = [];
  6538. var keyString = keyCode.toUpperCase();
  6539. for(var j = 0, len = keyString.length; j < len; j++){
  6540. ks.push(keyString.charCodeAt(j));
  6541. }
  6542. keyCode = ks;
  6543. }
  6544. var keyArray = Ext.isArray(keyCode);
  6545. var handler = function(e){
  6546. if((!shift || e.shiftKey) && (!ctrl || e.ctrlKey) && (!alt || e.altKey)){
  6547. var k = e.getKey();
  6548. if(keyArray){
  6549. for(var i = 0, len = keyCode.length; i < len; i++){
  6550. if(keyCode[i] == k){
  6551. if(this.stopEvent){
  6552. e.stopEvent();
  6553. }
  6554. fn.call(scope || window, k, e);
  6555. return;
  6556. }
  6557. }
  6558. }else{
  6559. if(k == keyCode){
  6560. if(this.stopEvent){
  6561. e.stopEvent();
  6562. }
  6563. fn.call(scope || window, k, e);
  6564. }
  6565. }
  6566. }
  6567. };
  6568. this.bindings.push(handler);
  6569. },
  6570. on : function(key, fn, scope){
  6571. var keyCode, shift, ctrl, alt;
  6572. if(typeof key == "object" && !Ext.isArray(key)){
  6573. keyCode = key.key;
  6574. shift = key.shift;
  6575. ctrl = key.ctrl;
  6576. alt = key.alt;
  6577. }else{
  6578. keyCode = key;
  6579. }
  6580. this.addBinding({
  6581. key: keyCode,
  6582. shift: shift,
  6583. ctrl: ctrl,
  6584. alt: alt,
  6585. fn: fn,
  6586. scope: scope
  6587. })
  6588. },
  6589. // private
  6590. handleKeyDown : function(e){
  6591. if(this.enabled){ //just in case
  6592. var b = this.bindings;
  6593. for(var i = 0, len = b.length; i < len; i++){
  6594. b[i].call(this, e);
  6595. }
  6596. }
  6597. },
  6598. isEnabled : function(){
  6599. return this.enabled;
  6600. },
  6601. enable: function(){
  6602. if(!this.enabled){
  6603. this.el.on(this.eventName, this.handleKeyDown, this);
  6604. this.enabled = true;
  6605. }
  6606. },
  6607. disable: function(){
  6608. if(this.enabled){
  6609. this.el.removeListener(this.eventName, this.handleKeyDown, this);
  6610. this.enabled = false;
  6611. }
  6612. }
  6613. };
  6614. Ext.util.TextMetrics = function(){
  6615. var shared;
  6616. return {
  6617. measure : function(el, text, fixedWidth){
  6618. if(!shared){
  6619. shared = Ext.util.TextMetrics.Instance(el, fixedWidth);
  6620. }
  6621. shared.bind(el);
  6622. shared.setFixedWidth(fixedWidth || 'auto');
  6623. return shared.getSize(text);
  6624. },
  6625. createInstance : function(el, fixedWidth){
  6626. return Ext.util.TextMetrics.Instance(el, fixedWidth);
  6627. }
  6628. };
  6629. }();
  6630. Ext.util.TextMetrics.Instance = function(bindTo, fixedWidth){
  6631. var ml = new Ext.Element(document.createElement('div'));
  6632. document.body.appendChild(ml.dom);
  6633. ml.position('absolute');
  6634. ml.setLeftTop(-1000, -1000);
  6635. ml.hide();
  6636. if(fixedWidth){
  6637. ml.setWidth(fixedWidth);
  6638. }
  6639. var instance = {
  6640. getSize : function(text){
  6641. ml.update(text);
  6642. var s = ml.getSize();
  6643. ml.update('');
  6644. return s;
  6645. },
  6646. bind : function(el){
  6647. ml.setStyle(
  6648. Ext.fly(el).getStyles('font-size','font-style', 'font-weight', 'font-family','line-height', 'text-transform', 'letter-spacing')
  6649. );
  6650. },
  6651. setFixedWidth : function(width){
  6652. ml.setWidth(width);
  6653. },
  6654. getWidth : function(text){
  6655. ml.dom.style.width = 'auto';
  6656. return this.getSize(text).width;
  6657. },
  6658. getHeight : function(text){
  6659. return this.getSize(text).height;
  6660. }
  6661. };
  6662. instance.bind(bindTo);
  6663. return instance;
  6664. };
  6665. // backwards compat
  6666. Ext.Element.measureText = Ext.util.TextMetrics.measure;
  6667. (function() {
  6668. var Event=Ext.EventManager;
  6669. var Dom=Ext.lib.Dom;
  6670. Ext.dd.DragDrop = function(id, sGroup, config) {
  6671. if(id) {
  6672. this.init(id, sGroup, config);
  6673. }
  6674. };
  6675. Ext.dd.DragDrop.prototype = {
  6676. id: null,
  6677. config: null,
  6678. dragElId: null,
  6679. handleElId: null,
  6680. invalidHandleTypes: null,
  6681. invalidHandleIds: null,
  6682. invalidHandleClasses: null,
  6683. startPageX: 0,
  6684. startPageY: 0,
  6685. groups: null,
  6686. locked: false,
  6687. lock: function() { this.locked = true; },
  6688. moveOnly: false,
  6689. unlock: function() { this.locked = false; },
  6690. isTarget: true,
  6691. padding: null,
  6692. _domRef: null,
  6693. __ygDragDrop: true,
  6694. constrainX: false,
  6695. constrainY: false,
  6696. minX: 0,
  6697. maxX: 0,
  6698. minY: 0,
  6699. maxY: 0,
  6700. maintainOffset: false,
  6701. xTicks: null,
  6702. yTicks: null,
  6703. primaryButtonOnly: true,
  6704. available: false,
  6705. hasOuterHandles: false,
  6706. b4StartDrag: function(x, y) { },
  6707. startDrag: function(x, y) { },
  6708. b4Drag: function(e) { },
  6709. onDrag: function(e) { },
  6710. onDragEnter: function(e, id) { },
  6711. b4DragOver: function(e) { },
  6712. onDragOver: function(e, id) { },
  6713. b4DragOut: function(e) { },
  6714. onDragOut: function(e, id) { },
  6715. b4DragDrop: function(e) { },
  6716. onDragDrop: function(e, id) { },
  6717. onInvalidDrop: function(e) { },
  6718. b4EndDrag: function(e) { },
  6719. endDrag: function(e) { },
  6720. b4MouseDown: function(e) { },
  6721. onMouseDown: function(e) { },
  6722. onMouseUp: function(e) { },
  6723. onAvailable: function () {
  6724. },
  6725. defaultPadding : {left:0, right:0, top:0, bottom:0},
  6726. constrainTo : function(constrainTo, pad, inContent){
  6727. if(typeof pad == "number"){
  6728. pad = {left: pad, right:pad, top:pad, bottom:pad};
  6729. }
  6730. pad = pad || this.defaultPadding;
  6731. var b = Ext.get(this.getEl()).getBox();
  6732. var ce = Ext.get(constrainTo);
  6733. var s = ce.getScroll();
  6734. var c, cd = ce.dom;
  6735. if(cd == document.body){
  6736. c = { x: s.left, y: s.top, width: Ext.lib.Dom.getViewWidth(), height: Ext.lib.Dom.getViewHeight()};
  6737. }else{
  6738. var xy = ce.getXY();
  6739. c = {x : xy[0]+s.left, y: xy[1]+s.top, width: cd.clientWidth, height: cd.clientHeight};
  6740. }
  6741. var topSpace = b.y - c.y;
  6742. var leftSpace = b.x - c.x;
  6743. this.resetConstraints();
  6744. this.setXConstraint(leftSpace - (pad.left||0), // left
  6745. c.width - leftSpace - b.width - (pad.right||0), //right
  6746. this.xTickSize
  6747. );
  6748. this.setYConstraint(topSpace - (pad.top||0), //top
  6749. c.height - topSpace - b.height - (pad.bottom||0), //bottom
  6750. this.yTickSize
  6751. );
  6752. },
  6753. getEl: function() {
  6754. if (!this._domRef) {
  6755. this._domRef = Ext.getDom(this.id);
  6756. }
  6757. return this._domRef;
  6758. },
  6759. getDragEl: function() {
  6760. return Ext.getDom(this.dragElId);
  6761. },
  6762. init: function(id, sGroup, config) {
  6763. this.initTarget(id, sGroup, config);
  6764. Event.on(this.id, "mousedown", this.handleMouseDown, this);
  6765. // Event.on(this.id, "selectstart", Event.preventDefault);
  6766. },
  6767. initTarget: function(id, sGroup, config) {
  6768. // configuration attributes
  6769. this.config = config || {};
  6770. // create a local reference to the drag and drop manager
  6771. this.DDM = Ext.dd.DDM;
  6772. // initialize the groups array
  6773. this.groups = {};
  6774. // assume that we have an element reference instead of an id if the
  6775. // parameter is not a string
  6776. if (typeof id !== "string") {
  6777. id = Ext.id(id);
  6778. }
  6779. // set the id
  6780. this.id = id;
  6781. // add to an interaction group
  6782. this.addToGroup((sGroup) ? sGroup : "default");
  6783. // We don't want to register this as the handle with the manager
  6784. // so we just set the id rather than calling the setter.
  6785. this.handleElId = id;
  6786. // the linked element is the element that gets dragged by default
  6787. this.setDragElId(id);
  6788. // by default, clicked anchors will not start drag operations.
  6789. this.invalidHandleTypes = { A: "A" };
  6790. this.invalidHandleIds = {};
  6791. this.invalidHandleClasses = [];
  6792. this.applyConfig();
  6793. this.handleOnAvailable();
  6794. },
  6795. applyConfig: function() {
  6796. // configurable properties:
  6797. // padding, isTarget, maintainOffset, primaryButtonOnly
  6798. this.padding = this.config.padding || [0, 0, 0, 0];
  6799. this.isTarget = (this.config.isTarget !== false);
  6800. this.maintainOffset = (this.config.maintainOffset);
  6801. this.primaryButtonOnly = (this.config.primaryButtonOnly !== false);
  6802. },
  6803. handleOnAvailable: function() {
  6804. this.available = true;
  6805. this.resetConstraints();
  6806. this.onAvailable();
  6807. },
  6808. setPadding: function(iTop, iRight, iBot, iLeft) {
  6809. // this.padding = [iLeft, iRight, iTop, iBot];
  6810. if (!iRight && 0 !== iRight) {
  6811. this.padding = [iTop, iTop, iTop, iTop];
  6812. } else if (!iBot && 0 !== iBot) {
  6813. this.padding = [iTop, iRight, iTop, iRight];
  6814. } else {
  6815. this.padding = [iTop, iRight, iBot, iLeft];
  6816. }
  6817. },
  6818. setInitPosition: function(diffX, diffY) {
  6819. var el = this.getEl();
  6820. if (!this.DDM.verifyEl(el)) {
  6821. return;
  6822. }
  6823. var dx = diffX || 0;
  6824. var dy = diffY || 0;
  6825. var p = Dom.getXY( el );
  6826. this.initPageX = p[0] - dx;
  6827. this.initPageY = p[1] - dy;
  6828. this.lastPageX = p[0];
  6829. this.lastPageY = p[1];
  6830. this.setStartPosition(p);
  6831. },
  6832. setStartPosition: function(pos) {
  6833. var p = pos || Dom.getXY( this.getEl() );
  6834. this.deltaSetXY = null;
  6835. this.startPageX = p[0];
  6836. this.startPageY = p[1];
  6837. },
  6838. addToGroup: function(sGroup) {
  6839. this.groups[sGroup] = true;
  6840. this.DDM.regDragDrop(this, sGroup);
  6841. },
  6842. removeFromGroup: function(sGroup) {
  6843. if (this.groups[sGroup]) {
  6844. delete this.groups[sGroup];
  6845. }
  6846. this.DDM.removeDDFromGroup(this, sGroup);
  6847. },
  6848. setDragElId: function(id) {
  6849. this.dragElId = id;
  6850. },
  6851. setHandleElId: function(id) {
  6852. if (typeof id !== "string") {
  6853. id = Ext.id(id);
  6854. }
  6855. this.handleElId = id;
  6856. this.DDM.regHandle(this.id, id);
  6857. },
  6858. setOuterHandleElId: function(id) {
  6859. if (typeof id !== "string") {
  6860. id = Ext.id(id);
  6861. }
  6862. Event.on(id, "mousedown",
  6863. this.handleMouseDown, this);
  6864. this.setHandleElId(id);
  6865. this.hasOuterHandles = true;
  6866. },
  6867. unreg: function() {
  6868. Event.un(this.id, "mousedown",
  6869. this.handleMouseDown);
  6870. this._domRef = null;
  6871. this.DDM._remove(this);
  6872. },
  6873. destroy : function(){
  6874. this.unreg();
  6875. },
  6876. isLocked: function() {
  6877. return (this.DDM.isLocked() || this.locked);
  6878. },
  6879. handleMouseDown: function(e, oDD){
  6880. if (this.primaryButtonOnly && e.button != 0) {
  6881. return;
  6882. }
  6883. if (this.isLocked()) {
  6884. return;
  6885. }
  6886. this.DDM.refreshCache(this.groups);
  6887. var pt = new Ext.lib.Point(Ext.lib.Event.getPageX(e), Ext.lib.Event.getPageY(e));
  6888. if (!this.hasOuterHandles && !this.DDM.isOverTarget(pt, this) ) {
  6889. } else {
  6890. if (this.clickValidator(e)) {
  6891. // set the initial element position
  6892. this.setStartPosition();
  6893. this.b4MouseDown(e);
  6894. this.onMouseDown(e);
  6895. this.DDM.handleMouseDown(e, this);
  6896. this.DDM.stopEvent(e);
  6897. } else {
  6898. }
  6899. }
  6900. },
  6901. clickValidator: function(e) {
  6902. var target = e.getTarget();
  6903. return ( this.isValidHandleChild(target) &&
  6904. (this.id == this.handleElId ||
  6905. this.DDM.handleWasClicked(target, this.id)) );
  6906. },
  6907. addInvalidHandleType: function(tagName) {
  6908. var type = tagName.toUpperCase();
  6909. this.invalidHandleTypes[type] = type;
  6910. },
  6911. addInvalidHandleId: function(id) {
  6912. if (typeof id !== "string") {
  6913. id = Ext.id(id);
  6914. }
  6915. this.invalidHandleIds[id] = id;
  6916. },
  6917. addInvalidHandleClass: function(cssClass) {
  6918. this.invalidHandleClasses.push(cssClass);
  6919. },
  6920. removeInvalidHandleType: function(tagName) {
  6921. var type = tagName.toUpperCase();
  6922. // this.invalidHandleTypes[type] = null;
  6923. delete this.invalidHandleTypes[type];
  6924. },
  6925. removeInvalidHandleId: function(id) {
  6926. if (typeof id !== "string") {
  6927. id = Ext.id(id);
  6928. }
  6929. delete this.invalidHandleIds[id];
  6930. },
  6931. removeInvalidHandleClass: function(cssClass) {
  6932. for (var i=0, len=this.invalidHandleClasses.length; i<len; ++i) {
  6933. if (this.invalidHandleClasses[i] == cssClass) {
  6934. delete this.invalidHandleClasses[i];
  6935. }
  6936. }
  6937. },
  6938. isValidHandleChild: function(node) {
  6939. var valid = true;
  6940. // var n = (node.nodeName == "#text") ? node.parentNode : node;
  6941. var nodeName;
  6942. try {
  6943. nodeName = node.nodeName.toUpperCase();
  6944. } catch(e) {
  6945. nodeName = node.nodeName;
  6946. }
  6947. valid = valid && !this.invalidHandleTypes[nodeName];
  6948. valid = valid && !this.invalidHandleIds[node.id];
  6949. for (var i=0, len=this.invalidHandleClasses.length; valid && i<len; ++i) {
  6950. valid = !Ext.fly(node).hasClass(this.invalidHandleClasses[i]);
  6951. }
  6952. return valid;
  6953. },
  6954. setXTicks: function(iStartX, iTickSize) {
  6955. this.xTicks = [];
  6956. this.xTickSize = iTickSize;
  6957. var tickMap = {};
  6958. for (var i = this.initPageX; i >= this.minX; i = i - iTickSize) {
  6959. if (!tickMap[i]) {
  6960. this.xTicks[this.xTicks.length] = i;
  6961. tickMap[i] = true;
  6962. }
  6963. }
  6964. for (i = this.initPageX; i <= this.maxX; i = i + iTickSize) {
  6965. if (!tickMap[i]) {
  6966. this.xTicks[this.xTicks.length] = i;
  6967. tickMap[i] = true;
  6968. }
  6969. }
  6970. this.xTicks.sort(this.DDM.numericSort) ;
  6971. },
  6972. setYTicks: function(iStartY, iTickSize) {
  6973. this.yTicks = [];
  6974. this.yTickSize = iTickSize;
  6975. var tickMap = {};
  6976. for (var i = this.initPageY; i >= this.minY; i = i - iTickSize) {
  6977. if (!tickMap[i]) {
  6978. this.yTicks[this.yTicks.length] = i;
  6979. tickMap[i] = true;
  6980. }
  6981. }
  6982. for (i = this.initPageY; i <= this.maxY; i = i + iTickSize) {
  6983. if (!tickMap[i]) {
  6984. this.yTicks[this.yTicks.length] = i;
  6985. tickMap[i] = true;
  6986. }
  6987. }
  6988. this.yTicks.sort(this.DDM.numericSort) ;
  6989. },
  6990. setXConstraint: function(iLeft, iRight, iTickSize) {
  6991. this.leftConstraint = iLeft;
  6992. this.rightConstraint = iRight;
  6993. this.minX = this.initPageX - iLeft;
  6994. this.maxX = this.initPageX + iRight;
  6995. if (iTickSize) { this.setXTicks(this.initPageX, iTickSize); }
  6996. this.constrainX = true;
  6997. },
  6998. clearConstraints: function() {
  6999. this.constrainX = false;
  7000. this.constrainY = false;
  7001. this.clearTicks();
  7002. },
  7003. clearTicks: function() {
  7004. this.xTicks = null;
  7005. this.yTicks = null;
  7006. this.xTickSize = 0;
  7007. this.yTickSize = 0;
  7008. },
  7009. setYConstraint: function(iUp, iDown, iTickSize) {
  7010. this.topConstraint = iUp;
  7011. this.bottomConstraint = iDown;
  7012. this.minY = this.initPageY - iUp;
  7013. this.maxY = this.initPageY + iDown;
  7014. if (iTickSize) { this.setYTicks(this.initPageY, iTickSize); }
  7015. this.constrainY = true;
  7016. },
  7017. resetConstraints: function() {
  7018. // Maintain offsets if necessary
  7019. if (this.initPageX || this.initPageX === 0) {
  7020. // figure out how much this thing has moved
  7021. var dx = (this.maintainOffset) ? this.lastPageX - this.initPageX : 0;
  7022. var dy = (this.maintainOffset) ? this.lastPageY - this.initPageY : 0;
  7023. this.setInitPosition(dx, dy);
  7024. // This is the first time we have detected the element's position
  7025. } else {
  7026. this.setInitPosition();
  7027. }
  7028. if (this.constrainX) {
  7029. this.setXConstraint( this.leftConstraint,
  7030. this.rightConstraint,
  7031. this.xTickSize );
  7032. }
  7033. if (this.constrainY) {
  7034. this.setYConstraint( this.topConstraint,
  7035. this.bottomConstraint,
  7036. this.yTickSize );
  7037. }
  7038. },
  7039. getTick: function(val, tickArray) {
  7040. if (!tickArray) {
  7041. // If tick interval is not defined, it is effectively 1 pixel,
  7042. // so we return the value passed to us.
  7043. return val;
  7044. } else if (tickArray[0] >= val) {
  7045. // The value is lower than the first tick, so we return the first
  7046. // tick.
  7047. return tickArray[0];
  7048. } else {
  7049. for (var i=0, len=tickArray.length; i<len; ++i) {
  7050. var next = i + 1;
  7051. if (tickArray[next] && tickArray[next] >= val) {
  7052. var diff1 = val - tickArray[i];
  7053. var diff2 = tickArray[next] - val;
  7054. return (diff2 > diff1) ? tickArray[i] : tickArray[next];
  7055. }
  7056. }
  7057. // The value is larger than the last tick, so we return the last
  7058. // tick.
  7059. return tickArray[tickArray.length - 1];
  7060. }
  7061. },
  7062. toString: function() {
  7063. return ("DragDrop " + this.id);
  7064. }
  7065. };
  7066. })();
  7067. // Only load the library once. Rewriting the manager class would orphan
  7068. // existing drag and drop instances.
  7069. if (!Ext.dd.DragDropMgr) {
  7070. Ext.dd.DragDropMgr = function() {
  7071. var Event = Ext.EventManager;
  7072. return {
  7073. ids: {},
  7074. handleIds: {},
  7075. dragCurrent: null,
  7076. dragOvers: {},
  7077. deltaX: 0,
  7078. deltaY: 0,
  7079. preventDefault: true,
  7080. stopPropagation: true,
  7081. initialized: false,
  7082. locked: false,
  7083. init: function() {
  7084. this.initialized = true;
  7085. },
  7086. POINT: 0,
  7087. INTERSECT: 1,
  7088. mode: 0,
  7089. _execOnAll: function(sMethod, args) {
  7090. for (var i in this.ids) {
  7091. for (var j in this.ids[i]) {
  7092. var oDD = this.ids[i][j];
  7093. if (! this.isTypeOfDD(oDD)) {
  7094. continue;
  7095. }
  7096. oDD[sMethod].apply(oDD, args);
  7097. }
  7098. }
  7099. },
  7100. _onLoad: function() {
  7101. this.init();
  7102. Event.on(document, "mouseup", this.handleMouseUp, this, true);
  7103. Event.on(document, "mousemove", this.handleMouseMove, this, true);
  7104. Event.on(window, "unload", this._onUnload, this, true);
  7105. Event.on(window, "resize", this._onResize, this, true);
  7106. // Event.on(window, "mouseout", this._test);
  7107. },
  7108. _onResize: function(e) {
  7109. this._execOnAll("resetConstraints", []);
  7110. },
  7111. lock: function() { this.locked = true; },
  7112. unlock: function() { this.locked = false; },
  7113. isLocked: function() { return this.locked; },
  7114. locationCache: {},
  7115. useCache: true,
  7116. clickPixelThresh: 3,
  7117. clickTimeThresh: 350,
  7118. dragThreshMet: false,
  7119. clickTimeout: null,
  7120. startX: 0,
  7121. startY: 0,
  7122. regDragDrop: function(oDD, sGroup) {
  7123. if (!this.initialized) { this.init(); }
  7124. if (!this.ids[sGroup]) {
  7125. this.ids[sGroup] = {};
  7126. }
  7127. this.ids[sGroup][oDD.id] = oDD;
  7128. },
  7129. removeDDFromGroup: function(oDD, sGroup) {
  7130. if (!this.ids[sGroup]) {
  7131. this.ids[sGroup] = {};
  7132. }
  7133. var obj = this.ids[sGroup];
  7134. if (obj && obj[oDD.id]) {
  7135. delete obj[oDD.id];
  7136. }
  7137. },
  7138. _remove: function(oDD) {
  7139. for (var g in oDD.groups) {
  7140. if (g && this.ids[g] && this.ids[g][oDD.id]) {
  7141. delete this.ids[g][oDD.id];
  7142. }
  7143. }
  7144. delete this.handleIds[oDD.id];
  7145. },
  7146. regHandle: function(sDDId, sHandleId) {
  7147. if (!this.handleIds[sDDId]) {
  7148. this.handleIds[sDDId] = {};
  7149. }
  7150. this.handleIds[sDDId][sHandleId] = sHandleId;
  7151. },
  7152. isDragDrop: function(id) {
  7153. return ( this.getDDById(id) ) ? true : false;
  7154. },
  7155. getRelated: function(p_oDD, bTargetsOnly) {
  7156. var oDDs = [];
  7157. for (var i in p_oDD.groups) {
  7158. for (j in this.ids[i]) {
  7159. var dd = this.ids[i][j];
  7160. if (! this.isTypeOfDD(dd)) {
  7161. continue;
  7162. }
  7163. if (!bTargetsOnly || dd.isTarget) {
  7164. oDDs[oDDs.length] = dd;
  7165. }
  7166. }
  7167. }
  7168. return oDDs;
  7169. },
  7170. isLegalTarget: function (oDD, oTargetDD) {
  7171. var targets = this.getRelated(oDD, true);
  7172. for (var i=0, len=targets.length;i<len;++i) {
  7173. if (targets[i].id == oTargetDD.id) {
  7174. return true;
  7175. }
  7176. }
  7177. return false;
  7178. },
  7179. isTypeOfDD: function (oDD) {
  7180. return (oDD && oDD.__ygDragDrop);
  7181. },
  7182. isHandle: function(sDDId, sHandleId) {
  7183. return ( this.handleIds[sDDId] &&
  7184. this.handleIds[sDDId][sHandleId] );
  7185. },
  7186. getDDById: function(id) {
  7187. for (var i in this.ids) {
  7188. if (this.ids[i][id]) {
  7189. return this.ids[i][id];
  7190. }
  7191. }
  7192. return null;
  7193. },
  7194. handleMouseDown: function(e, oDD) {
  7195. if(Ext.QuickTips){
  7196. Ext.QuickTips.disable();
  7197. }
  7198. if(this.dragCurrent){
  7199. // the original browser mouseup wasn't handled (e.g. outside FF browser window)
  7200. // so clean up first to avoid breaking the next drag
  7201. this.handleMouseUp(e);
  7202. }
  7203. this.currentTarget = e.getTarget();
  7204. this.dragCurrent = oDD;
  7205. var el = oDD.getEl();
  7206. // track start position
  7207. this.startX = e.getPageX();
  7208. this.startY = e.getPageY();
  7209. this.deltaX = this.startX - el.offsetLeft;
  7210. this.deltaY = this.startY - el.offsetTop;
  7211. this.dragThreshMet = false;
  7212. this.clickTimeout = setTimeout(
  7213. function() {
  7214. var DDM = Ext.dd.DDM;
  7215. DDM.startDrag(DDM.startX, DDM.startY);
  7216. },
  7217. this.clickTimeThresh );
  7218. },
  7219. startDrag: function(x, y) {
  7220. clearTimeout(this.clickTimeout);
  7221. if (this.dragCurrent) {
  7222. this.dragCurrent.b4StartDrag(x, y);
  7223. this.dragCurrent.startDrag(x, y);
  7224. }
  7225. this.dragThreshMet = true;
  7226. },
  7227. handleMouseUp: function(e) {
  7228. if(Ext.QuickTips){
  7229. Ext.QuickTips.enable();
  7230. }
  7231. if (! this.dragCurrent) {
  7232. return;
  7233. }
  7234. clearTimeout(this.clickTimeout);
  7235. if (this.dragThreshMet) {
  7236. this.fireEvents(e, true);
  7237. } else {
  7238. }
  7239. this.stopDrag(e);
  7240. this.stopEvent(e);
  7241. },
  7242. stopEvent: function(e){
  7243. if(this.stopPropagation) {
  7244. e.stopPropagation();
  7245. }
  7246. if (this.preventDefault) {
  7247. e.preventDefault();
  7248. }
  7249. },
  7250. stopDrag: function(e) {
  7251. // Fire the drag end event for the item that was dragged
  7252. if (this.dragCurrent) {
  7253. if (this.dragThreshMet) {
  7254. this.dragCurrent.b4EndDrag(e);
  7255. this.dragCurrent.endDrag(e);
  7256. }
  7257. this.dragCurrent.onMouseUp(e);
  7258. }
  7259. this.dragCurrent = null;
  7260. this.dragOvers = {};
  7261. },
  7262. handleMouseMove: function(e) {
  7263. if (! this.dragCurrent) {
  7264. return true;
  7265. }
  7266. // var button = e.which || e.button;
  7267. // check for IE mouseup outside of page boundary
  7268. if (Ext.isIE && (e.button !== 0 && e.button !== 1 && e.button !== 2)) {
  7269. this.stopEvent(e);
  7270. return this.handleMouseUp(e);
  7271. }
  7272. if (!this.dragThreshMet) {
  7273. var diffX = Math.abs(this.startX - e.getPageX());
  7274. var diffY = Math.abs(this.startY - e.getPageY());
  7275. if (diffX > this.clickPixelThresh ||
  7276. diffY > this.clickPixelThresh) {
  7277. this.startDrag(this.startX, this.startY);
  7278. }
  7279. }
  7280. if (this.dragThreshMet) {
  7281. this.dragCurrent.b4Drag(e);
  7282. this.dragCurrent.onDrag(e);
  7283. if(!this.dragCurrent.moveOnly){
  7284. this.fireEvents(e, false);
  7285. }
  7286. }
  7287. this.stopEvent(e);
  7288. return true;
  7289. },
  7290. fireEvents: function(e, isDrop) {
  7291. var dc = this.dragCurrent;
  7292. // If the user did the mouse up outside of the window, we could
  7293. // get here even though we have ended the drag.
  7294. if (!dc || dc.isLocked()) {
  7295. return;
  7296. }
  7297. var pt = e.getPoint();
  7298. // cache the previous dragOver array
  7299. var oldOvers = [];
  7300. var outEvts = [];
  7301. var overEvts = [];
  7302. var dropEvts = [];
  7303. var enterEvts = [];
  7304. // Check to see if the object(s) we were hovering over is no longer
  7305. // being hovered over so we can fire the onDragOut event
  7306. for (var i in this.dragOvers) {
  7307. var ddo = this.dragOvers[i];
  7308. if (! this.isTypeOfDD(ddo)) {
  7309. continue;
  7310. }
  7311. if (! this.isOverTarget(pt, ddo, this.mode)) {
  7312. outEvts.push( ddo );
  7313. }
  7314. oldOvers[i] = true;
  7315. delete this.dragOvers[i];
  7316. }
  7317. for (var sGroup in dc.groups) {
  7318. if ("string" != typeof sGroup) {
  7319. continue;
  7320. }
  7321. for (i in this.ids[sGroup]) {
  7322. var oDD = this.ids[sGroup][i];
  7323. if (! this.isTypeOfDD(oDD)) {
  7324. continue;
  7325. }
  7326. if (oDD.isTarget && !oDD.isLocked() && oDD != dc) {
  7327. if (this.isOverTarget(pt, oDD, this.mode)) {
  7328. // look for drop interactions
  7329. if (isDrop) {
  7330. dropEvts.push( oDD );
  7331. // look for drag enter and drag over interactions
  7332. } else {
  7333. // initial drag over: dragEnter fires
  7334. if (!oldOvers[oDD.id]) {
  7335. enterEvts.push( oDD );
  7336. // subsequent drag overs: dragOver fires
  7337. } else {
  7338. overEvts.push( oDD );
  7339. }
  7340. this.dragOvers[oDD.id] = oDD;
  7341. }
  7342. }
  7343. }
  7344. }
  7345. }
  7346. if (this.mode) {
  7347. if (outEvts.length) {
  7348. dc.b4DragOut(e, outEvts);
  7349. dc.onDragOut(e, outEvts);
  7350. }
  7351. if (enterEvts.length) {
  7352. dc.onDragEnter(e, enterEvts);
  7353. }
  7354. if (overEvts.length) {
  7355. dc.b4DragOver(e, overEvts);
  7356. dc.onDragOver(e, overEvts);
  7357. }
  7358. if (dropEvts.length) {
  7359. dc.b4DragDrop(e, dropEvts);
  7360. dc.onDragDrop(e, dropEvts);
  7361. }
  7362. } else {
  7363. // fire dragout events
  7364. var len = 0;
  7365. for (i=0, len=outEvts.length; i<len; ++i) {
  7366. dc.b4DragOut(e, outEvts[i].id);
  7367. dc.onDragOut(e, outEvts[i].id);
  7368. }
  7369. // fire enter events
  7370. for (i=0,len=enterEvts.length; i<len; ++i) {
  7371. // dc.b4DragEnter(e, oDD.id);
  7372. dc.onDragEnter(e, enterEvts[i].id);
  7373. }
  7374. // fire over events
  7375. for (i=0,len=overEvts.length; i<len; ++i) {
  7376. dc.b4DragOver(e, overEvts[i].id);
  7377. dc.onDragOver(e, overEvts[i].id);
  7378. }
  7379. // fire drop events
  7380. for (i=0, len=dropEvts.length; i<len; ++i) {
  7381. dc.b4DragDrop(e, dropEvts[i].id);
  7382. dc.onDragDrop(e, dropEvts[i].id);
  7383. }
  7384. }
  7385. // notify about a drop that did not find a target
  7386. if (isDrop && !dropEvts.length) {
  7387. dc.onInvalidDrop(e);
  7388. }
  7389. },
  7390. getBestMatch: function(dds) {
  7391. var winner = null;
  7392. // Return null if the input is not what we expect
  7393. //if (!dds || !dds.length || dds.length == 0) {
  7394. // winner = null;
  7395. // If there is only one item, it wins
  7396. //} else if (dds.length == 1) {
  7397. var len = dds.length;
  7398. if (len == 1) {
  7399. winner = dds[0];
  7400. } else {
  7401. // Loop through the targeted items
  7402. for (var i=0; i<len; ++i) {
  7403. var dd = dds[i];
  7404. // If the cursor is over the object, it wins. If the
  7405. // cursor is over multiple matches, the first one we come
  7406. // to wins.
  7407. if (dd.cursorIsOver) {
  7408. winner = dd;
  7409. break;
  7410. // Otherwise the object with the most overlap wins
  7411. } else {
  7412. if (!winner ||
  7413. winner.overlap.getArea() < dd.overlap.getArea()) {
  7414. winner = dd;
  7415. }
  7416. }
  7417. }
  7418. }
  7419. return winner;
  7420. },
  7421. refreshCache: function(groups) {
  7422. for (var sGroup in groups) {
  7423. if ("string" != typeof sGroup) {
  7424. continue;
  7425. }
  7426. for (var i in this.ids[sGroup]) {
  7427. var oDD = this.ids[sGroup][i];
  7428. if (this.isTypeOfDD(oDD)) {
  7429. // if (this.isTypeOfDD(oDD) && oDD.isTarget) {
  7430. var loc = this.getLocation(oDD);
  7431. if (loc) {
  7432. this.locationCache[oDD.id] = loc;
  7433. } else {
  7434. delete this.locationCache[oDD.id];
  7435. // this will unregister the drag and drop object if
  7436. // the element is not in a usable state
  7437. // oDD.unreg();
  7438. }
  7439. }
  7440. }
  7441. }
  7442. },
  7443. verifyEl: function(el) {
  7444. if (el) {
  7445. var parent;
  7446. if(Ext.isIE){
  7447. try{
  7448. parent = el.offsetParent;
  7449. }catch(e){}
  7450. }else{
  7451. parent = el.offsetParent;
  7452. }
  7453. if (parent) {
  7454. return true;
  7455. }
  7456. }
  7457. return false;
  7458. },
  7459. getLocation: function(oDD) {
  7460. if (! this.isTypeOfDD(oDD)) {
  7461. return null;
  7462. }
  7463. var el = oDD.getEl(), pos, x1, x2, y1, y2, t, r, b, l;
  7464. try {
  7465. pos= Ext.lib.Dom.getXY(el);
  7466. } catch (e) { }
  7467. if (!pos) {
  7468. return null;
  7469. }
  7470. x1 = pos[0];
  7471. x2 = x1 + el.offsetWidth;
  7472. y1 = pos[1];
  7473. y2 = y1 + el.offsetHeight;
  7474. t = y1 - oDD.padding[0];
  7475. r = x2 + oDD.padding[1];
  7476. b = y2 + oDD.padding[2];
  7477. l = x1 - oDD.padding[3];
  7478. return new Ext.lib.Region( t, r, b, l );
  7479. },
  7480. isOverTarget: function(pt, oTarget, intersect) {
  7481. // use cache if available
  7482. var loc = this.locationCache[oTarget.id];
  7483. if (!loc || !this.useCache) {
  7484. loc = this.getLocation(oTarget);
  7485. this.locationCache[oTarget.id] = loc;
  7486. }
  7487. if (!loc) {
  7488. return false;
  7489. }
  7490. oTarget.cursorIsOver = loc.contains( pt );
  7491. // DragDrop is using this as a sanity check for the initial mousedown
  7492. // in this case we are done. In POINT mode, if the drag obj has no
  7493. // contraints, we are also done. Otherwise we need to evaluate the
  7494. // location of the target as related to the actual location of the
  7495. // dragged element.
  7496. var dc = this.dragCurrent;
  7497. if (!dc || !dc.getTargetCoord ||
  7498. (!intersect && !dc.constrainX && !dc.constrainY)) {
  7499. return oTarget.cursorIsOver;
  7500. }
  7501. oTarget.overlap = null;
  7502. // Get the current location of the drag element, this is the
  7503. // location of the mouse event less the delta that represents
  7504. // where the original mousedown happened on the element. We
  7505. // need to consider constraints and ticks as well.
  7506. var pos = dc.getTargetCoord(pt.x, pt.y);
  7507. var el = dc.getDragEl();
  7508. var curRegion = new Ext.lib.Region( pos.y,
  7509. pos.x + el.offsetWidth,
  7510. pos.y + el.offsetHeight,
  7511. pos.x );
  7512. var overlap = curRegion.intersect(loc);
  7513. if (overlap) {
  7514. oTarget.overlap = overlap;
  7515. return (intersect) ? true : oTarget.cursorIsOver;
  7516. } else {
  7517. return false;
  7518. }
  7519. },
  7520. _onUnload: function(e, me) {
  7521. Ext.dd.DragDropMgr.unregAll();
  7522. },
  7523. unregAll: function() {
  7524. if (this.dragCurrent) {
  7525. this.stopDrag();
  7526. this.dragCurrent = null;
  7527. }
  7528. this._execOnAll("unreg", []);
  7529. for (var i in this.elementCache) {
  7530. delete this.elementCache[i];
  7531. }
  7532. this.elementCache = {};
  7533. this.ids = {};
  7534. },
  7535. elementCache: {},
  7536. getElWrapper: function(id) {
  7537. var oWrapper = this.elementCache[id];
  7538. if (!oWrapper || !oWrapper.el) {
  7539. oWrapper = this.elementCache[id] =
  7540. new this.ElementWrapper(Ext.getDom(id));
  7541. }
  7542. return oWrapper;
  7543. },
  7544. getElement: function(id) {
  7545. return Ext.getDom(id);
  7546. },
  7547. getCss: function(id) {
  7548. var el = Ext.getDom(id);
  7549. return (el) ? el.style : null;
  7550. },
  7551. ElementWrapper: function(el) {
  7552. this.el = el || null;
  7553. this.id = this.el && el.id;
  7554. this.css = this.el && el.style;
  7555. },
  7556. getPosX: function(el) {
  7557. return Ext.lib.Dom.getX(el);
  7558. },
  7559. getPosY: function(el) {
  7560. return Ext.lib.Dom.getY(el);
  7561. },
  7562. swapNode: function(n1, n2) {
  7563. if (n1.swapNode) {
  7564. n1.swapNode(n2);
  7565. } else {
  7566. var p = n2.parentNode;
  7567. var s = n2.nextSibling;
  7568. if (s == n1) {
  7569. p.insertBefore(n1, n2);
  7570. } else if (n2 == n1.nextSibling) {
  7571. p.insertBefore(n2, n1);
  7572. } else {
  7573. n1.parentNode.replaceChild(n2, n1);
  7574. p.insertBefore(n1, s);
  7575. }
  7576. }
  7577. },
  7578. getScroll: function () {
  7579. var t, l, dde=document.documentElement, db=document.body;
  7580. if (dde && (dde.scrollTop || dde.scrollLeft)) {
  7581. t = dde.scrollTop;
  7582. l = dde.scrollLeft;
  7583. } else if (db) {
  7584. t = db.scrollTop;
  7585. l = db.scrollLeft;
  7586. } else {
  7587. }
  7588. return { top: t, left: l };
  7589. },
  7590. getStyle: function(el, styleProp) {
  7591. return Ext.fly(el).getStyle(styleProp);
  7592. },
  7593. getScrollTop: function () { return this.getScroll().top; },
  7594. getScrollLeft: function () { return this.getScroll().left; },
  7595. moveToEl: function (moveEl, targetEl) {
  7596. var aCoord = Ext.lib.Dom.getXY(targetEl);
  7597. Ext.lib.Dom.setXY(moveEl, aCoord);
  7598. },
  7599. numericSort: function(a, b) { return (a - b); },
  7600. _timeoutCount: 0,
  7601. _addListeners: function() {
  7602. var DDM = Ext.dd.DDM;
  7603. if ( Ext.lib.Event && document ) {
  7604. DDM._onLoad();
  7605. } else {
  7606. if (DDM._timeoutCount > 2000) {
  7607. } else {
  7608. setTimeout(DDM._addListeners, 10);
  7609. if (document && document.body) {
  7610. DDM._timeoutCount += 1;
  7611. }
  7612. }
  7613. }
  7614. },
  7615. handleWasClicked: function(node, id) {
  7616. if (this.isHandle(id, node.id)) {
  7617. return true;
  7618. } else {
  7619. // check to see if this is a text node child of the one we want
  7620. var p = node.parentNode;
  7621. while (p) {
  7622. if (this.isHandle(id, p.id)) {
  7623. return true;
  7624. } else {
  7625. p = p.parentNode;
  7626. }
  7627. }
  7628. }
  7629. return false;
  7630. }
  7631. };
  7632. }();
  7633. // shorter alias, save a few bytes
  7634. Ext.dd.DDM = Ext.dd.DragDropMgr;
  7635. Ext.dd.DDM._addListeners();
  7636. }
  7637. Ext.dd.DD = function(id, sGroup, config) {
  7638. if (id) {
  7639. this.init(id, sGroup, config);
  7640. }
  7641. };
  7642. Ext.extend(Ext.dd.DD, Ext.dd.DragDrop, {
  7643. scroll: true,
  7644. autoOffset: function(iPageX, iPageY) {
  7645. var x = iPageX - this.startPageX;
  7646. var y = iPageY - this.startPageY;
  7647. this.setDelta(x, y);
  7648. },
  7649. setDelta: function(iDeltaX, iDeltaY) {
  7650. this.deltaX = iDeltaX;
  7651. this.deltaY = iDeltaY;
  7652. },
  7653. setDragElPos: function(iPageX, iPageY) {
  7654. // the first time we do this, we are going to check to make sure
  7655. // the element has css positioning
  7656. var el = this.getDragEl();
  7657. this.alignElWithMouse(el, iPageX, iPageY);
  7658. },
  7659. alignElWithMouse: function(el, iPageX, iPageY) {
  7660. var oCoord = this.getTargetCoord(iPageX, iPageY);
  7661. var fly = el.dom ? el : Ext.fly(el, '_dd');
  7662. if (!this.deltaSetXY) {
  7663. var aCoord = [oCoord.x, oCoord.y];
  7664. fly.setXY(aCoord);
  7665. var newLeft = fly.getLeft(true);
  7666. var newTop = fly.getTop(true);
  7667. this.deltaSetXY = [ newLeft - oCoord.x, newTop - oCoord.y ];
  7668. } else {
  7669. fly.setLeftTop(oCoord.x + this.deltaSetXY[0], oCoord.y + this.deltaSetXY[1]);
  7670. }
  7671. this.cachePosition(oCoord.x, oCoord.y);
  7672. this.autoScroll(oCoord.x, oCoord.y, el.offsetHeight, el.offsetWidth);
  7673. return oCoord;
  7674. },
  7675. cachePosition: function(iPageX, iPageY) {
  7676. if (iPageX) {
  7677. this.lastPageX = iPageX;
  7678. this.lastPageY = iPageY;
  7679. } else {
  7680. var aCoord = Ext.lib.Dom.getXY(this.getEl());
  7681. this.lastPageX = aCoord[0];
  7682. this.lastPageY = aCoord[1];
  7683. }
  7684. },
  7685. autoScroll: function(x, y, h, w) {
  7686. if (this.scroll) {
  7687. // The client height
  7688. var clientH = Ext.lib.Dom.getViewHeight();
  7689. // The client width
  7690. var clientW = Ext.lib.Dom.getViewWidth();
  7691. // The amt scrolled down
  7692. var st = this.DDM.getScrollTop();
  7693. // The amt scrolled right
  7694. var sl = this.DDM.getScrollLeft();
  7695. // Location of the bottom of the element
  7696. var bot = h + y;
  7697. // Location of the right of the element
  7698. var right = w + x;
  7699. // The distance from the cursor to the bottom of the visible area,
  7700. // adjusted so that we don't scroll if the cursor is beyond the
  7701. // element drag constraints
  7702. var toBot = (clientH + st - y - this.deltaY);
  7703. // The distance from the cursor to the right of the visible area
  7704. var toRight = (clientW + sl - x - this.deltaX);
  7705. // How close to the edge the cursor must be before we scroll
  7706. // var thresh = (document.all) ? 100 : 40;
  7707. var thresh = 40;
  7708. // How many pixels to scroll per autoscroll op. This helps to reduce
  7709. // clunky scrolling. IE is more sensitive about this ... it needs this
  7710. // value to be higher.
  7711. var scrAmt = (document.all) ? 80 : 30;
  7712. // Scroll down if we are near the bottom of the visible page and the
  7713. // obj extends below the crease
  7714. if ( bot > clientH && toBot < thresh ) {
  7715. window.scrollTo(sl, st + scrAmt);
  7716. }
  7717. // Scroll up if the window is scrolled down and the top of the object
  7718. // goes above the top border
  7719. if ( y < st && st > 0 && y - st < thresh ) {
  7720. window.scrollTo(sl, st - scrAmt);
  7721. }
  7722. // Scroll right if the obj is beyond the right border and the cursor is
  7723. // near the border.
  7724. if ( right > clientW && toRight < thresh ) {
  7725. window.scrollTo(sl + scrAmt, st);
  7726. }
  7727. // Scroll left if the window has been scrolled to the right and the obj
  7728. // extends past the left border
  7729. if ( x < sl && sl > 0 && x - sl < thresh ) {
  7730. window.scrollTo(sl - scrAmt, st);
  7731. }
  7732. }
  7733. },
  7734. getTargetCoord: function(iPageX, iPageY) {
  7735. var x = iPageX - this.deltaX;
  7736. var y = iPageY - this.deltaY;
  7737. if (this.constrainX) {
  7738. if (x < this.minX) { x = this.minX; }
  7739. if (x > this.maxX) { x = this.maxX; }
  7740. }
  7741. if (this.constrainY) {
  7742. if (y < this.minY) { y = this.minY; }
  7743. if (y > this.maxY) { y = this.maxY; }
  7744. }
  7745. x = this.getTick(x, this.xTicks);
  7746. y = this.getTick(y, this.yTicks);
  7747. return {x:x, y:y};
  7748. },
  7749. applyConfig: function() {
  7750. Ext.dd.DD.superclass.applyConfig.call(this);
  7751. this.scroll = (this.config.scroll !== false);
  7752. },
  7753. b4MouseDown: function(e) {
  7754. // this.resetConstraints();
  7755. this.autoOffset(e.getPageX(),
  7756. e.getPageY());
  7757. },
  7758. b4Drag: function(e) {
  7759. this.setDragElPos(e.getPageX(),
  7760. e.getPageY());
  7761. },
  7762. toString: function() {
  7763. return ("DD " + this.id);
  7764. }
  7765. //////////////////////////////////////////////////////////////////////////
  7766. // Debugging ygDragDrop events that can be overridden
  7767. //////////////////////////////////////////////////////////////////////////
  7768. });
  7769. Ext.dd.DDProxy = function(id, sGroup, config) {
  7770. if (id) {
  7771. this.init(id, sGroup, config);
  7772. this.initFrame();
  7773. }
  7774. };
  7775. Ext.dd.DDProxy.dragElId = "ygddfdiv";
  7776. Ext.extend(Ext.dd.DDProxy, Ext.dd.DD, {
  7777. resizeFrame: true,
  7778. centerFrame: false,
  7779. createFrame: function() {
  7780. var self = this;
  7781. var body = document.body;
  7782. if (!body || !body.firstChild) {
  7783. setTimeout( function() { self.createFrame(); }, 50 );
  7784. return;
  7785. }
  7786. var div = this.getDragEl();
  7787. if (!div) {
  7788. div = document.createElement("div");
  7789. div.id = this.dragElId;
  7790. var s = div.style;
  7791. s.position = "absolute";
  7792. s.visibility = "hidden";
  7793. s.cursor = "move";
  7794. s.border = "2px solid #aaa";
  7795. s.zIndex = 999;
  7796. // appendChild can blow up IE if invoked prior to the window load event
  7797. // while rendering a table. It is possible there are other scenarios
  7798. // that would cause this to happen as well.
  7799. body.insertBefore(div, body.firstChild);
  7800. }
  7801. },
  7802. initFrame: function() {
  7803. this.createFrame();
  7804. },
  7805. applyConfig: function() {
  7806. Ext.dd.DDProxy.superclass.applyConfig.call(this);
  7807. this.resizeFrame = (this.config.resizeFrame !== false);
  7808. this.centerFrame = (this.config.centerFrame);
  7809. this.setDragElId(this.config.dragElId || Ext.dd.DDProxy.dragElId);
  7810. },
  7811. showFrame: function(iPageX, iPageY) {
  7812. var el = this.getEl();
  7813. var dragEl = this.getDragEl();
  7814. var s = dragEl.style;
  7815. this._resizeProxy();
  7816. if (this.centerFrame) {
  7817. this.setDelta( Math.round(parseInt(s.width, 10)/2),
  7818. Math.round(parseInt(s.height, 10)/2) );
  7819. }
  7820. this.setDragElPos(iPageX, iPageY);
  7821. Ext.fly(dragEl).show();
  7822. },
  7823. _resizeProxy: function() {
  7824. if (this.resizeFrame) {
  7825. var el = this.getEl();
  7826. Ext.fly(this.getDragEl()).setSize(el.offsetWidth, el.offsetHeight);
  7827. }
  7828. },
  7829. // overrides Ext.dd.DragDrop
  7830. b4MouseDown: function(e) {
  7831. var x = e.getPageX();
  7832. var y = e.getPageY();
  7833. this.autoOffset(x, y);
  7834. this.setDragElPos(x, y);
  7835. },
  7836. // overrides Ext.dd.DragDrop
  7837. b4StartDrag: function(x, y) {
  7838. // show the drag frame
  7839. this.showFrame(x, y);
  7840. },
  7841. // overrides Ext.dd.DragDrop
  7842. b4EndDrag: function(e) {
  7843. Ext.fly(this.getDragEl()).hide();
  7844. },
  7845. // overrides Ext.dd.DragDrop
  7846. // By default we try to move the element to the last location of the frame.
  7847. // This is so that the default behavior mirrors that of Ext.dd.DD.
  7848. endDrag: function(e) {
  7849. var lel = this.getEl();
  7850. var del = this.getDragEl();
  7851. // Show the drag frame briefly so we can get its position
  7852. del.style.visibility = "";
  7853. this.beforeMove();
  7854. // Hide the linked element before the move to get around a Safari
  7855. // rendering bug.
  7856. lel.style.visibility = "hidden";
  7857. Ext.dd.DDM.moveToEl(lel, del);
  7858. del.style.visibility = "hidden";
  7859. lel.style.visibility = "";
  7860. this.afterDrag();
  7861. },
  7862. beforeMove : function(){
  7863. },
  7864. afterDrag : function(){
  7865. },
  7866. toString: function() {
  7867. return ("DDProxy " + this.id);
  7868. }
  7869. });
  7870. Ext.dd.DDTarget = function(id, sGroup, config) {
  7871. if (id) {
  7872. this.initTarget(id, sGroup, config);
  7873. }
  7874. };
  7875. // Ext.dd.DDTarget.prototype = new Ext.dd.DragDrop();
  7876. Ext.extend(Ext.dd.DDTarget, Ext.dd.DragDrop, {
  7877. toString: function() {
  7878. return ("DDTarget " + this.id);
  7879. }
  7880. });
  7881. Ext.dd.DragTracker = function(config){
  7882. Ext.apply(this, config);
  7883. this.addEvents(
  7884. 'mousedown',
  7885. 'mouseup',
  7886. 'mousemove',
  7887. 'dragstart',
  7888. 'dragend',
  7889. 'drag'
  7890. );
  7891. this.dragRegion = new Ext.lib.Region(0,0,0,0);
  7892. if(this.el){
  7893. this.initEl(this.el);
  7894. }
  7895. }
  7896. Ext.extend(Ext.dd.DragTracker, Ext.util.Observable, {
  7897. active: false,
  7898. tolerance: 5,
  7899. autoStart: false,
  7900. initEl: function(el){
  7901. this.el = Ext.get(el);
  7902. el.on('mousedown', this.onMouseDown, this,
  7903. this.delegate ? {delegate: this.delegate} : undefined);
  7904. },
  7905. destroy : function(){
  7906. this.el.un('mousedown', this.onMouseDown, this);
  7907. },
  7908. onMouseDown: function(e, target){
  7909. if(this.fireEvent('mousedown', this, e) !== false && this.onBeforeStart(e) !== false){
  7910. this.startXY = this.lastXY = e.getXY();
  7911. this.dragTarget = this.delegate ? target : this.el.dom;
  7912. e.preventDefault();
  7913. var doc = Ext.getDoc();
  7914. doc.on('mouseup', this.onMouseUp, this);
  7915. doc.on('mousemove', this.onMouseMove, this);
  7916. doc.on('selectstart', this.stopSelect, this);
  7917. if(this.autoStart){
  7918. this.timer = this.triggerStart.defer(this.autoStart === true ? 1000 : this.autoStart, this);
  7919. }
  7920. }
  7921. },
  7922. onMouseMove: function(e, target){
  7923. e.preventDefault();
  7924. var xy = e.getXY(), s = this.startXY;
  7925. this.lastXY = xy;
  7926. if(!this.active){
  7927. if(Math.abs(s[0]-xy[0]) > this.tolerance || Math.abs(s[1]-xy[1]) > this.tolerance){
  7928. this.triggerStart();
  7929. }else{
  7930. return;
  7931. }
  7932. }
  7933. this.fireEvent('mousemove', this, e);
  7934. this.onDrag(e);
  7935. this.fireEvent('drag', this, e);
  7936. },
  7937. onMouseUp: function(e){
  7938. var doc = Ext.getDoc();
  7939. doc.un('mousemove', this.onMouseMove, this);
  7940. doc.un('mouseup', this.onMouseUp, this);
  7941. doc.un('selectstart', this.stopSelect, this);
  7942. e.preventDefault();
  7943. this.clearStart();
  7944. this.active = false;
  7945. delete this.elRegion;
  7946. this.fireEvent('mouseup', this, e);
  7947. this.onEnd(e);
  7948. this.fireEvent('dragend', this, e);
  7949. },
  7950. triggerStart: function(isTimer){
  7951. this.clearStart();
  7952. this.active = true;
  7953. this.onStart(this.startXY);
  7954. this.fireEvent('dragstart', this, this.startXY);
  7955. },
  7956. clearStart : function(){
  7957. if(this.timer){
  7958. clearTimeout(this.timer);
  7959. delete this.timer;
  7960. }
  7961. },
  7962. stopSelect : function(e){
  7963. e.stopEvent();
  7964. return false;
  7965. },
  7966. onBeforeStart : function(e){
  7967. },
  7968. onStart : function(xy){
  7969. },
  7970. onDrag : function(e){
  7971. },
  7972. onEnd : function(e){
  7973. },
  7974. getDragTarget : function(){
  7975. return this.dragTarget;
  7976. },
  7977. getDragCt : function(){
  7978. return this.el;
  7979. },
  7980. getXY : function(constrain){
  7981. return constrain ?
  7982. this.constrainModes[constrain].call(this, this.lastXY) : this.lastXY;
  7983. },
  7984. getOffset : function(constrain){
  7985. var xy = this.getXY(constrain);
  7986. var s = this.startXY;
  7987. return [s[0]-xy[0], s[1]-xy[1]];
  7988. },
  7989. constrainModes: {
  7990. 'point' : function(xy){
  7991. if(!this.elRegion){
  7992. this.elRegion = this.getDragCt().getRegion();
  7993. }
  7994. var dr = this.dragRegion;
  7995. dr.left = xy[0];
  7996. dr.top = xy[1];
  7997. dr.right = xy[0];
  7998. dr.bottom = xy[1];
  7999. dr.constrainTo(this.elRegion);
  8000. return [dr.left, dr.top];
  8001. }
  8002. }
  8003. });
  8004. Ext.dd.ScrollManager = function(){
  8005. var ddm = Ext.dd.DragDropMgr;
  8006. var els = {};
  8007. var dragEl = null;
  8008. var proc = {};
  8009. var onStop = function(e){
  8010. dragEl = null;
  8011. clearProc();
  8012. };
  8013. var triggerRefresh = function(){
  8014. if(ddm.dragCurrent){
  8015. ddm.refreshCache(ddm.dragCurrent.groups);
  8016. }
  8017. };
  8018. var doScroll = function(){
  8019. if(ddm.dragCurrent){
  8020. var dds = Ext.dd.ScrollManager;
  8021. var inc = proc.el.ddScrollConfig ?
  8022. proc.el.ddScrollConfig.increment : dds.increment;
  8023. if(!dds.animate){
  8024. if(proc.el.scroll(proc.dir, inc)){
  8025. triggerRefresh();
  8026. }
  8027. }else{
  8028. proc.el.scroll(proc.dir, inc, true, dds.animDuration, triggerRefresh);
  8029. }
  8030. }
  8031. };
  8032. var clearProc = function(){
  8033. if(proc.id){
  8034. clearInterval(proc.id);
  8035. }
  8036. proc.id = 0;
  8037. proc.el = null;
  8038. proc.dir = "";
  8039. };
  8040. var startProc = function(el, dir){
  8041. clearProc();
  8042. proc.el = el;
  8043. proc.dir = dir;
  8044. var freq = (el.ddScrollConfig && el.ddScrollConfig.frequency) ?
  8045. el.ddScrollConfig.frequency : Ext.dd.ScrollManager.frequency;
  8046. proc.id = setInterval(doScroll, freq);
  8047. };
  8048. var onFire = function(e, isDrop){
  8049. if(isDrop || !ddm.dragCurrent){ return; }
  8050. var dds = Ext.dd.ScrollManager;
  8051. if(!dragEl || dragEl != ddm.dragCurrent){
  8052. dragEl = ddm.dragCurrent;
  8053. // refresh regions on drag start
  8054. dds.refreshCache();
  8055. }
  8056. var xy = Ext.lib.Event.getXY(e);
  8057. var pt = new Ext.lib.Point(xy[0], xy[1]);
  8058. for(var id in els){
  8059. var el = els[id], r = el._region;
  8060. var c = el.ddScrollConfig ? el.ddScrollConfig : dds;
  8061. if(r && r.contains(pt) && el.isScrollable()){
  8062. if(r.bottom - pt.y <= c.vthresh){
  8063. if(proc.el != el){
  8064. startProc(el, "down");
  8065. }
  8066. return;
  8067. }else if(r.right - pt.x <= c.hthresh){
  8068. if(proc.el != el){
  8069. startProc(el, "left");
  8070. }
  8071. return;
  8072. }else if(pt.y - r.top <= c.vthresh){
  8073. if(proc.el != el){
  8074. startProc(el, "up");
  8075. }
  8076. return;
  8077. }else if(pt.x - r.left <= c.hthresh){
  8078. if(proc.el != el){
  8079. startProc(el, "right");
  8080. }
  8081. return;
  8082. }
  8083. }
  8084. }
  8085. clearProc();
  8086. };
  8087. ddm.fireEvents = ddm.fireEvents.createSequence(onFire, ddm);
  8088. ddm.stopDrag = ddm.stopDrag.createSequence(onStop, ddm);
  8089. return {
  8090. register : function(el){
  8091. if(Ext.isArray(el)){
  8092. for(var i = 0, len = el.length; i < len; i++) {
  8093. this.register(el[i]);
  8094. }
  8095. }else{
  8096. el = Ext.get(el);
  8097. els[el.id] = el;
  8098. }
  8099. },
  8100. unregister : function(el){
  8101. if(Ext.isArray(el)){
  8102. for(var i = 0, len = el.length; i < len; i++) {
  8103. this.unregister(el[i]);
  8104. }
  8105. }else{
  8106. el = Ext.get(el);
  8107. delete els[el.id];
  8108. }
  8109. },
  8110. vthresh : 25,
  8111. hthresh : 25,
  8112. increment : 100,
  8113. frequency : 500,
  8114. animate: true,
  8115. animDuration: .4,
  8116. refreshCache : function(){
  8117. for(var id in els){
  8118. if(typeof els[id] == 'object'){ // for people extending the object prototype
  8119. els[id]._region = els[id].getRegion();
  8120. }
  8121. }
  8122. }
  8123. };
  8124. }();
  8125. Ext.dd.Registry = function(){
  8126. var elements = {};
  8127. var handles = {};
  8128. var autoIdSeed = 0;
  8129. var getId = function(el, autogen){
  8130. if(typeof el == "string"){
  8131. return el;
  8132. }
  8133. var id = el.id;
  8134. if(!id && autogen !== false){
  8135. id = "extdd-" + (++autoIdSeed);
  8136. el.id = id;
  8137. }
  8138. return id;
  8139. };
  8140. return {
  8141. register : function(el, data){
  8142. data = data || {};
  8143. if(typeof el == "string"){
  8144. el = document.getElementById(el);
  8145. }
  8146. data.ddel = el;
  8147. elements[getId(el)] = data;
  8148. if(data.isHandle !== false){
  8149. handles[data.ddel.id] = data;
  8150. }
  8151. if(data.handles){
  8152. var hs = data.handles;
  8153. for(var i = 0, len = hs.length; i < len; i++){
  8154. handles[getId(hs[i])] = data;
  8155. }
  8156. }
  8157. },
  8158. unregister : function(el){
  8159. var id = getId(el, false);
  8160. var data = elements[id];
  8161. if(data){
  8162. delete elements[id];
  8163. if(data.handles){
  8164. var hs = data.handles;
  8165. for(var i = 0, len = hs.length; i < len; i++){
  8166. delete handles[getId(hs[i], false)];
  8167. }
  8168. }
  8169. }
  8170. },
  8171. getHandle : function(id){
  8172. if(typeof id != "string"){ // must be element?
  8173. id = id.id;
  8174. }
  8175. return handles[id];
  8176. },
  8177. getHandleFromEvent : function(e){
  8178. var t = Ext.lib.Event.getTarget(e);
  8179. return t ? handles[t.id] : null;
  8180. },
  8181. getTarget : function(id){
  8182. if(typeof id != "string"){ // must be element?
  8183. id = id.id;
  8184. }
  8185. return elements[id];
  8186. },
  8187. getTargetFromEvent : function(e){
  8188. var t = Ext.lib.Event.getTarget(e);
  8189. return t ? elements[t.id] || handles[t.id] : null;
  8190. }
  8191. };
  8192. }();
  8193. Ext.dd.StatusProxy = function(config){
  8194. Ext.apply(this, config);
  8195. this.id = this.id || Ext.id();
  8196. this.el = new Ext.Layer({
  8197. dh: {
  8198. id: this.id, tag: "div", cls: "x-dd-drag-proxy "+this.dropNotAllowed, children: [
  8199. {tag: "div", cls: "x-dd-drop-icon"},
  8200. {tag: "div", cls: "x-dd-drag-ghost"}
  8201. ]
  8202. },
  8203. shadow: !config || config.shadow !== false
  8204. });
  8205. this.ghost = Ext.get(this.el.dom.childNodes[1]);
  8206. this.dropStatus = this.dropNotAllowed;
  8207. };
  8208. Ext.dd.StatusProxy.prototype = {
  8209. dropAllowed : "x-dd-drop-ok",
  8210. dropNotAllowed : "x-dd-drop-nodrop",
  8211. setStatus : function(cssClass){
  8212. cssClass = cssClass || this.dropNotAllowed;
  8213. if(this.dropStatus != cssClass){
  8214. this.el.replaceClass(this.dropStatus, cssClass);
  8215. this.dropStatus = cssClass;
  8216. }
  8217. },
  8218. reset : function(clearGhost){
  8219. this.el.dom.className = "x-dd-drag-proxy " + this.dropNotAllowed;
  8220. this.dropStatus = this.dropNotAllowed;
  8221. if(clearGhost){
  8222. this.ghost.update("");
  8223. }
  8224. },
  8225. update : function(html){
  8226. if(typeof html == "string"){
  8227. this.ghost.update(html);
  8228. }else{
  8229. this.ghost.update("");
  8230. html.style.margin = "0";
  8231. this.ghost.dom.appendChild(html);
  8232. }
  8233. var el = this.ghost.dom.firstChild;
  8234. if(el){
  8235. Ext.fly(el).setStyle(Ext.isIE ? 'styleFloat' : 'cssFloat', 'none');
  8236. }
  8237. },
  8238. getEl : function(){
  8239. return this.el;
  8240. },
  8241. getGhost : function(){
  8242. return this.ghost;
  8243. },
  8244. hide : function(clear){
  8245. this.el.hide();
  8246. if(clear){
  8247. this.reset(true);
  8248. }
  8249. },
  8250. stop : function(){
  8251. if(this.anim && this.anim.isAnimated && this.anim.isAnimated()){
  8252. this.anim.stop();
  8253. }
  8254. },
  8255. show : function(){
  8256. this.el.show();
  8257. },
  8258. sync : function(){
  8259. this.el.sync();
  8260. },
  8261. repair : function(xy, callback, scope){
  8262. this.callback = callback;
  8263. this.scope = scope;
  8264. if(xy && this.animRepair !== false){
  8265. this.el.addClass("x-dd-drag-repair");
  8266. this.el.hideUnders(true);
  8267. this.anim = this.el.shift({
  8268. duration: this.repairDuration || .5,
  8269. easing: 'easeOut',
  8270. xy: xy,
  8271. stopFx: true,
  8272. callback: this.afterRepair,
  8273. scope: this
  8274. });
  8275. }else{
  8276. this.afterRepair();
  8277. }
  8278. },
  8279. // private
  8280. afterRepair : function(){
  8281. this.hide(true);
  8282. if(typeof this.callback == "function"){
  8283. this.callback.call(this.scope || this);
  8284. }
  8285. this.callback = null;
  8286. this.scope = null;
  8287. }
  8288. };
  8289. Ext.dd.DragSource = function(el, config){
  8290. this.el = Ext.get(el);
  8291. if(!this.dragData){
  8292. this.dragData = {};
  8293. }
  8294. Ext.apply(this, config);
  8295. if(!this.proxy){
  8296. this.proxy = new Ext.dd.StatusProxy();
  8297. }
  8298. Ext.dd.DragSource.superclass.constructor.call(this, this.el.dom, this.ddGroup || this.group,
  8299. {dragElId : this.proxy.id, resizeFrame: false, isTarget: false, scroll: this.scroll === true});
  8300. this.dragging = false;
  8301. };
  8302. Ext.extend(Ext.dd.DragSource, Ext.dd.DDProxy, {
  8303. dropAllowed : "x-dd-drop-ok",
  8304. dropNotAllowed : "x-dd-drop-nodrop",
  8305. getDragData : function(e){
  8306. return this.dragData;
  8307. },
  8308. // private
  8309. onDragEnter : function(e, id){
  8310. var target = Ext.dd.DragDropMgr.getDDById(id);
  8311. this.cachedTarget = target;
  8312. if(this.beforeDragEnter(target, e, id) !== false){
  8313. if(target.isNotifyTarget){
  8314. var status = target.notifyEnter(this, e, this.dragData);
  8315. this.proxy.setStatus(status);
  8316. }else{
  8317. this.proxy.setStatus(this.dropAllowed);
  8318. }
  8319. if(this.afterDragEnter){
  8320. this.afterDragEnter(target, e, id);
  8321. }
  8322. }
  8323. },
  8324. beforeDragEnter : function(target, e, id){
  8325. return true;
  8326. },
  8327. // private
  8328. alignElWithMouse: function() {
  8329. Ext.dd.DragSource.superclass.alignElWithMouse.apply(this, arguments);
  8330. this.proxy.sync();
  8331. },
  8332. // private
  8333. onDragOver : function(e, id){
  8334. var target = this.cachedTarget || Ext.dd.DragDropMgr.getDDById(id);
  8335. if(this.beforeDragOver(target, e, id) !== false){
  8336. if(target.isNotifyTarget){
  8337. var status = target.notifyOver(this, e, this.dragData);
  8338. this.proxy.setStatus(status);
  8339. }
  8340. if(this.afterDragOver){
  8341. this.afterDragOver(target, e, id);
  8342. }
  8343. }
  8344. },
  8345. beforeDragOver : function(target, e, id){
  8346. return true;
  8347. },
  8348. // private
  8349. onDragOut : function(e, id){
  8350. var target = this.cachedTarget || Ext.dd.DragDropMgr.getDDById(id);
  8351. if(this.beforeDragOut(target, e, id) !== false){
  8352. if(target.isNotifyTarget){
  8353. target.notifyOut(this, e, this.dragData);
  8354. }
  8355. this.proxy.reset();
  8356. if(this.afterDragOut){
  8357. this.afterDragOut(target, e, id);
  8358. }
  8359. }
  8360. this.cachedTarget = null;
  8361. },
  8362. beforeDragOut : function(target, e, id){
  8363. return true;
  8364. },
  8365. // private
  8366. onDragDrop : function(e, id){
  8367. var target = this.cachedTarget || Ext.dd.DragDropMgr.getDDById(id);
  8368. if(this.beforeDragDrop(target, e, id) !== false){
  8369. if(target.isNotifyTarget){
  8370. if(target.notifyDrop(this, e, this.dragData)){ // valid drop?
  8371. this.onValidDrop(target, e, id);
  8372. }else{
  8373. this.onInvalidDrop(target, e, id);
  8374. }
  8375. }else{
  8376. this.onValidDrop(target, e, id);
  8377. }
  8378. if(this.afterDragDrop){
  8379. this.afterDragDrop(target, e, id);
  8380. }
  8381. }
  8382. delete this.cachedTarget;
  8383. },
  8384. beforeDragDrop : function(target, e, id){
  8385. return true;
  8386. },
  8387. // private
  8388. onValidDrop : function(target, e, id){
  8389. this.hideProxy();
  8390. if(this.afterValidDrop){
  8391. this.afterValidDrop(target, e, id);
  8392. }
  8393. },
  8394. // private
  8395. getRepairXY : function(e, data){
  8396. return this.el.getXY();
  8397. },
  8398. // private
  8399. onInvalidDrop : function(target, e, id){
  8400. this.beforeInvalidDrop(target, e, id);
  8401. if(this.cachedTarget){
  8402. if(this.cachedTarget.isNotifyTarget){
  8403. this.cachedTarget.notifyOut(this, e, this.dragData);
  8404. }
  8405. this.cacheTarget = null;
  8406. }
  8407. this.proxy.repair(this.getRepairXY(e, this.dragData), this.afterRepair, this);
  8408. if(this.afterInvalidDrop){
  8409. this.afterInvalidDrop(e, id);
  8410. }
  8411. },
  8412. // private
  8413. afterRepair : function(){
  8414. if(Ext.enableFx){
  8415. this.el.highlight(this.hlColor || "c3daf9");
  8416. }
  8417. this.dragging = false;
  8418. },
  8419. beforeInvalidDrop : function(target, e, id){
  8420. return true;
  8421. },
  8422. // private
  8423. handleMouseDown : function(e){
  8424. if(this.dragging) {
  8425. return;
  8426. }
  8427. var data = this.getDragData(e);
  8428. if(data && this.onBeforeDrag(data, e) !== false){
  8429. this.dragData = data;
  8430. this.proxy.stop();
  8431. Ext.dd.DragSource.superclass.handleMouseDown.apply(this, arguments);
  8432. }
  8433. },
  8434. onBeforeDrag : function(data, e){
  8435. return true;
  8436. },
  8437. onStartDrag : Ext.emptyFn,
  8438. // private override
  8439. startDrag : function(x, y){
  8440. this.proxy.reset();
  8441. this.dragging = true;
  8442. this.proxy.update("");
  8443. this.onInitDrag(x, y);
  8444. this.proxy.show();
  8445. },
  8446. // private
  8447. onInitDrag : function(x, y){
  8448. var clone = this.el.dom.cloneNode(true);
  8449. clone.id = Ext.id(); // prevent duplicate ids
  8450. this.proxy.update(clone);
  8451. this.onStartDrag(x, y);
  8452. return true;
  8453. },
  8454. getProxy : function(){
  8455. return this.proxy;
  8456. },
  8457. hideProxy : function(){
  8458. this.proxy.hide();
  8459. this.proxy.reset(true);
  8460. this.dragging = false;
  8461. },
  8462. // private
  8463. triggerCacheRefresh : function(){
  8464. Ext.dd.DDM.refreshCache(this.groups);
  8465. },
  8466. // private - override to prevent hiding
  8467. b4EndDrag: function(e) {
  8468. },
  8469. // private - override to prevent moving
  8470. endDrag : function(e){
  8471. this.onEndDrag(this.dragData, e);
  8472. },
  8473. // private
  8474. onEndDrag : function(data, e){
  8475. },
  8476. // private - pin to cursor
  8477. autoOffset : function(x, y) {
  8478. this.setDelta(-12, -20);
  8479. }
  8480. });
  8481. Ext.dd.DropTarget = function(el, config){
  8482. this.el = Ext.get(el);
  8483. Ext.apply(this, config);
  8484. if(this.containerScroll){
  8485. Ext.dd.ScrollManager.register(this.el);
  8486. }
  8487. Ext.dd.DropTarget.superclass.constructor.call(this, this.el.dom, this.ddGroup || this.group,
  8488. {isTarget: true});
  8489. };
  8490. Ext.extend(Ext.dd.DropTarget, Ext.dd.DDTarget, {
  8491. dropAllowed : "x-dd-drop-ok",
  8492. dropNotAllowed : "x-dd-drop-nodrop",
  8493. // private
  8494. isTarget : true,
  8495. // private
  8496. isNotifyTarget : true,
  8497. notifyEnter : function(dd, e, data){
  8498. if(this.overClass){
  8499. this.el.addClass(this.overClass);
  8500. }
  8501. return this.dropAllowed;
  8502. },
  8503. notifyOver : function(dd, e, data){
  8504. return this.dropAllowed;
  8505. },
  8506. notifyOut : function(dd, e, data){
  8507. if(this.overClass){
  8508. this.el.removeClass(this.overClass);
  8509. }
  8510. },
  8511. notifyDrop : function(dd, e, data){
  8512. return false;
  8513. }
  8514. });
  8515. Ext.dd.DragZone = function(el, config){
  8516. Ext.dd.DragZone.superclass.constructor.call(this, el, config);
  8517. if(this.containerScroll){
  8518. Ext.dd.ScrollManager.register(this.el);
  8519. }
  8520. };
  8521. Ext.extend(Ext.dd.DragZone, Ext.dd.DragSource, {
  8522. getDragData : function(e){
  8523. return Ext.dd.Registry.getHandleFromEvent(e);
  8524. },
  8525. onInitDrag : function(x, y){
  8526. this.proxy.update(this.dragData.ddel.cloneNode(true));
  8527. this.onStartDrag(x, y);
  8528. return true;
  8529. },
  8530. afterRepair : function(){
  8531. if(Ext.enableFx){
  8532. Ext.Element.fly(this.dragData.ddel).highlight(this.hlColor || "c3daf9");
  8533. }
  8534. this.dragging = false;
  8535. },
  8536. getRepairXY : function(e){
  8537. return Ext.Element.fly(this.dragData.ddel).getXY();
  8538. }
  8539. });
  8540. Ext.dd.DropZone = function(el, config){
  8541. Ext.dd.DropZone.superclass.constructor.call(this, el, config);
  8542. };
  8543. Ext.extend(Ext.dd.DropZone, Ext.dd.DropTarget, {
  8544. getTargetFromEvent : function(e){
  8545. return Ext.dd.Registry.getTargetFromEvent(e);
  8546. },
  8547. onNodeEnter : function(n, dd, e, data){
  8548. },
  8549. onNodeOver : function(n, dd, e, data){
  8550. return this.dropAllowed;
  8551. },
  8552. onNodeOut : function(n, dd, e, data){
  8553. },
  8554. onNodeDrop : function(n, dd, e, data){
  8555. return false;
  8556. },
  8557. onContainerOver : function(dd, e, data){
  8558. return this.dropNotAllowed;
  8559. },
  8560. onContainerDrop : function(dd, e, data){
  8561. return false;
  8562. },
  8563. notifyEnter : function(dd, e, data){
  8564. return this.dropNotAllowed;
  8565. },
  8566. notifyOver : function(dd, e, data){
  8567. var n = this.getTargetFromEvent(e);
  8568. if(!n){ // not over valid drop target
  8569. if(this.lastOverNode){
  8570. this.onNodeOut(this.lastOverNode, dd, e, data);
  8571. this.lastOverNode = null;
  8572. }
  8573. return this.onContainerOver(dd, e, data);
  8574. }
  8575. if(this.lastOverNode != n){
  8576. if(this.lastOverNode){
  8577. this.onNodeOut(this.lastOverNode, dd, e, data);
  8578. }
  8579. this.onNodeEnter(n, dd, e, data);
  8580. this.lastOverNode = n;
  8581. }
  8582. return this.onNodeOver(n, dd, e, data);
  8583. },
  8584. notifyOut : function(dd, e, data){
  8585. if(this.lastOverNode){
  8586. this.onNodeOut(this.lastOverNode, dd, e, data);
  8587. this.lastOverNode = null;
  8588. }
  8589. },
  8590. notifyDrop : function(dd, e, data){
  8591. if(this.lastOverNode){
  8592. this.onNodeOut(this.lastOverNode, dd, e, data);
  8593. this.lastOverNode = null;
  8594. }
  8595. var n = this.getTargetFromEvent(e);
  8596. return n ?
  8597. this.onNodeDrop(n, dd, e, data) :
  8598. this.onContainerDrop(dd, e, data);
  8599. },
  8600. // private
  8601. triggerCacheRefresh : function(){
  8602. Ext.dd.DDM.refreshCache(this.groups);
  8603. }
  8604. });
  8605. Ext.data.SortTypes = {
  8606. none : function(s){
  8607. return s;
  8608. },
  8609. stripTagsRE : /<\/?[^>]+>/gi,
  8610. asText : function(s){
  8611. return String(s).replace(this.stripTagsRE, "");
  8612. },
  8613. asUCText : function(s){
  8614. return String(s).toUpperCase().replace(this.stripTagsRE, "");
  8615. },
  8616. asUCString : function(s) {
  8617. return String(s).toUpperCase();
  8618. },
  8619. asDate : function(s) {
  8620. if(!s){
  8621. return 0;
  8622. }
  8623. if(Ext.isDate(s)){
  8624. return s.getTime();
  8625. }
  8626. return Date.parse(String(s));
  8627. },
  8628. asFloat : function(s) {
  8629. var val = parseFloat(String(s).replace(/,/g, ""));
  8630. if(isNaN(val)) val = 0;
  8631. return val;
  8632. },
  8633. asInt : function(s) {
  8634. var val = parseInt(String(s).replace(/,/g, ""));
  8635. if(isNaN(val)) val = 0;
  8636. return val;
  8637. }
  8638. };
  8639. Ext.data.Record = function(data, id){
  8640. this.id = (id || id === 0) ? id : ++Ext.data.Record.AUTO_ID;
  8641. this.data = data;
  8642. };
  8643. Ext.data.Record.create = function(o){
  8644. var f = Ext.extend(Ext.data.Record, {});
  8645. var p = f.prototype;
  8646. p.fields = new Ext.util.MixedCollection(false, function(field){
  8647. return field.name;
  8648. });
  8649. for(var i = 0, len = o.length; i < len; i++){
  8650. p.fields.add(new Ext.data.Field(o[i]));
  8651. }
  8652. f.getField = function(name){
  8653. return p.fields.get(name);
  8654. };
  8655. return f;
  8656. };
  8657. Ext.data.Record.AUTO_ID = 1000;
  8658. Ext.data.Record.EDIT = 'edit';
  8659. Ext.data.Record.REJECT = 'reject';
  8660. Ext.data.Record.COMMIT = 'commit';
  8661. Ext.data.Record.prototype = {
  8662. dirty : false,
  8663. editing : false,
  8664. error: null,
  8665. modified: null,
  8666. // private
  8667. join : function(store){
  8668. this.store = store;
  8669. },
  8670. set : function(name, value){
  8671. if(String(this.data[name]) == String(value)){
  8672. return;
  8673. }
  8674. this.dirty = true;
  8675. if(!this.modified){
  8676. this.modified = {};
  8677. }
  8678. if(typeof this.modified[name] == 'undefined'){
  8679. this.modified[name] = this.data[name];
  8680. }
  8681. this.data[name] = value;
  8682. if(!this.editing && this.store){
  8683. this.store.afterEdit(this);
  8684. }
  8685. },
  8686. get : function(name){
  8687. return this.data[name];
  8688. },
  8689. beginEdit : function(){
  8690. this.editing = true;
  8691. this.modified = {};
  8692. },
  8693. cancelEdit : function(){
  8694. this.editing = false;
  8695. delete this.modified;
  8696. },
  8697. endEdit : function(){
  8698. this.editing = false;
  8699. if(this.dirty && this.store){
  8700. this.store.afterEdit(this);
  8701. }
  8702. },
  8703. reject : function(silent){
  8704. var m = this.modified;
  8705. for(var n in m){
  8706. if(typeof m[n] != "function"){
  8707. this.data[n] = m[n];
  8708. }
  8709. }
  8710. this.dirty = false;
  8711. delete this.modified;
  8712. this.editing = false;
  8713. if(this.store && silent !== true){
  8714. this.store.afterReject(this);
  8715. }
  8716. },
  8717. commit : function(silent){
  8718. this.dirty = false;
  8719. delete this.modified;
  8720. this.editing = false;
  8721. if(this.store && silent !== true){
  8722. this.store.afterCommit(this);
  8723. }
  8724. },
  8725. getChanges : function(){
  8726. var m = this.modified, cs = {};
  8727. for(var n in m){
  8728. if(m.hasOwnProperty(n)){
  8729. cs[n] = this.data[n];
  8730. }
  8731. }
  8732. return cs;
  8733. },
  8734. // private
  8735. hasError : function(){
  8736. return this.error != null;
  8737. },
  8738. // private
  8739. clearError : function(){
  8740. this.error = null;
  8741. },
  8742. copy : function(newId) {
  8743. return new this.constructor(Ext.apply({}, this.data), newId || this.id);
  8744. },
  8745. isModified : function(fieldName){
  8746. return !!(this.modified && this.modified.hasOwnProperty(fieldName));
  8747. }
  8748. };
  8749. Ext.StoreMgr = Ext.apply(new Ext.util.MixedCollection(), {
  8750. register : function(){
  8751. for(var i = 0, s; s = arguments[i]; i++){
  8752. this.add(s);
  8753. }
  8754. },
  8755. unregister : function(){
  8756. for(var i = 0, s; s = arguments[i]; i++){
  8757. this.remove(this.lookup(s));
  8758. }
  8759. },
  8760. lookup : function(id){
  8761. return typeof id == "object" ? id : this.get(id);
  8762. },
  8763. // getKey implementation for MixedCollection
  8764. getKey : function(o){
  8765. return o.storeId || o.id;
  8766. }
  8767. });
  8768. Ext.data.Store = function(config){
  8769. this.data = new Ext.util.MixedCollection(false);
  8770. this.data.getKey = function(o){
  8771. return o.id;
  8772. };
  8773. this.baseParams = {};
  8774. this.paramNames = {
  8775. "start" : "start",
  8776. "limit" : "limit",
  8777. "sort" : "sort",
  8778. "dir" : "dir"
  8779. };
  8780. if(config && config.data){
  8781. this.inlineData = config.data;
  8782. delete config.data;
  8783. }
  8784. Ext.apply(this, config);
  8785. if(this.url && !this.proxy){
  8786. this.proxy = new Ext.data.HttpProxy({url: this.url});
  8787. }
  8788. if(this.reader){ // reader passed
  8789. if(!this.recordType){
  8790. this.recordType = this.reader.recordType;
  8791. }
  8792. if(this.reader.onMetaChange){
  8793. this.reader.onMetaChange = this.onMetaChange.createDelegate(this);
  8794. }
  8795. }
  8796. if(this.recordType){
  8797. this.fields = this.recordType.prototype.fields;
  8798. }
  8799. this.modified = [];
  8800. this.addEvents(
  8801. 'datachanged',
  8802. 'metachange',
  8803. 'add',
  8804. 'remove',
  8805. 'update',
  8806. 'clear',
  8807. 'beforeload',
  8808. 'load',
  8809. 'loadexception'
  8810. );
  8811. if(this.proxy){
  8812. this.relayEvents(this.proxy, ["loadexception"]);
  8813. }
  8814. this.sortToggle = {};
  8815. if(this.sortInfo){
  8816. this.setDefaultSort(this.sortInfo.field, this.sortInfo.direction);
  8817. }
  8818. Ext.data.Store.superclass.constructor.call(this);
  8819. if(this.storeId || this.id){
  8820. Ext.StoreMgr.register(this);
  8821. }
  8822. if(this.inlineData){
  8823. this.loadData(this.inlineData);
  8824. delete this.inlineData;
  8825. }else if(this.autoLoad){
  8826. this.load.defer(10, this, [
  8827. typeof this.autoLoad == 'object' ?
  8828. this.autoLoad : undefined]);
  8829. }
  8830. };
  8831. Ext.extend(Ext.data.Store, Ext.util.Observable, {
  8832. remoteSort : false,
  8833. pruneModifiedRecords : false,
  8834. lastOptions : null,
  8835. destroy : function(){
  8836. if(this.storeId || this.id){
  8837. Ext.StoreMgr.unregister(this);
  8838. }
  8839. this.data = null;
  8840. this.purgeListeners();
  8841. },
  8842. add : function(records){
  8843. records = [].concat(records);
  8844. if(records.length < 1){
  8845. return;
  8846. }
  8847. for(var i = 0, len = records.length; i < len; i++){
  8848. records[i].join(this);
  8849. }
  8850. var index = this.data.length;
  8851. this.data.addAll(records);
  8852. if(this.snapshot){
  8853. this.snapshot.addAll(records);
  8854. }
  8855. this.fireEvent("add", this, records, index);
  8856. },
  8857. addSorted : function(record){
  8858. var index = this.findInsertIndex(record);
  8859. this.insert(index, record);
  8860. },
  8861. remove : function(record){
  8862. var index = this.data.indexOf(record);
  8863. this.data.removeAt(index);
  8864. if(this.pruneModifiedRecords){
  8865. this.modified.remove(record);
  8866. }
  8867. if(this.snapshot){
  8868. this.snapshot.remove(record);
  8869. }
  8870. this.fireEvent("remove", this, record, index);
  8871. },
  8872. removeAt : function(index){
  8873. this.remove(this.getAt(index));
  8874. },
  8875. removeAll : function(){
  8876. this.data.clear();
  8877. if(this.snapshot){
  8878. this.snapshot.clear();
  8879. }
  8880. if(this.pruneModifiedRecords){
  8881. this.modified = [];
  8882. }
  8883. this.fireEvent("clear", this);
  8884. },
  8885. insert : function(index, records){
  8886. records = [].concat(records);
  8887. for(var i = 0, len = records.length; i < len; i++){
  8888. this.data.insert(index, records[i]);
  8889. records[i].join(this);
  8890. }
  8891. this.fireEvent("add", this, records, index);
  8892. },
  8893. indexOf : function(record){
  8894. return this.data.indexOf(record);
  8895. },
  8896. indexOfId : function(id){
  8897. return this.data.indexOfKey(id);
  8898. },
  8899. getById : function(id){
  8900. return this.data.key(id);
  8901. },
  8902. getAt : function(index){
  8903. return this.data.itemAt(index);
  8904. },
  8905. getRange : function(start, end){
  8906. return this.data.getRange(start, end);
  8907. },
  8908. // private
  8909. storeOptions : function(o){
  8910. o = Ext.apply({}, o);
  8911. delete o.callback;
  8912. delete o.scope;
  8913. this.lastOptions = o;
  8914. },
  8915. load : function(options){
  8916. options = options || {};
  8917. if(this.fireEvent("beforeload", this, options) !== false){
  8918. this.storeOptions(options);
  8919. var p = Ext.apply(options.params || {}, this.baseParams);
  8920. if(this.sortInfo && this.remoteSort){
  8921. var pn = this.paramNames;
  8922. p[pn["sort"]] = this.sortInfo.field;
  8923. p[pn["dir"]] = this.sortInfo.direction;
  8924. }
  8925. this.proxy.load(p, this.reader, this.loadRecords, this, options);
  8926. return true;
  8927. } else {
  8928. return false;
  8929. }
  8930. },
  8931. reload : function(options){
  8932. this.load(Ext.applyIf(options||{}, this.lastOptions));
  8933. },
  8934. // private
  8935. // Called as a callback by the Reader during a load operation.
  8936. loadRecords : function(o, options, success){
  8937. if(!o || success === false){
  8938. if(success !== false){
  8939. this.fireEvent("load", this, [], options);
  8940. }
  8941. if(options.callback){
  8942. options.callback.call(options.scope || this, [], options, false);
  8943. }
  8944. return;
  8945. }
  8946. var r = o.records, t = o.totalRecords || r.length;
  8947. if(!options || options.add !== true){
  8948. if(this.pruneModifiedRecords){
  8949. this.modified = [];
  8950. }
  8951. for(var i = 0, len = r.length; i < len; i++){
  8952. r[i].join(this);
  8953. }
  8954. if(this.snapshot){
  8955. this.data = this.snapshot;
  8956. delete this.snapshot;
  8957. }
  8958. this.data.clear();
  8959. this.data.addAll(r);
  8960. this.totalLength = t;
  8961. this.applySort();
  8962. this.fireEvent("datachanged", this);
  8963. }else{
  8964. this.totalLength = Math.max(t, this.data.length+r.length);
  8965. this.add(r);
  8966. }
  8967. this.fireEvent("load", this, r, options);
  8968. if(options.callback){
  8969. options.callback.call(options.scope || this, r, options, true);
  8970. }
  8971. },
  8972. loadData : function(o, append){
  8973. var r = this.reader.readRecords(o);
  8974. this.loadRecords(r, {add: append}, true);
  8975. },
  8976. getCount : function(){
  8977. return this.data.length || 0;
  8978. },
  8979. getTotalCount : function(){
  8980. return this.totalLength || 0;
  8981. },
  8982. getSortState : function(){
  8983. return this.sortInfo;
  8984. },
  8985. // private
  8986. applySort : function(){
  8987. if(this.sortInfo && !this.remoteSort){
  8988. var s = this.sortInfo, f = s.field;
  8989. this.sortData(f, s.direction);
  8990. }
  8991. },
  8992. // private
  8993. sortData : function(f, direction){
  8994. direction = direction || 'ASC';
  8995. var st = this.fields.get(f).sortType;
  8996. var fn = function(r1, r2){
  8997. var v1 = st(r1.data[f]), v2 = st(r2.data[f]);
  8998. return v1 > v2 ? 1 : (v1 < v2 ? -1 : 0);
  8999. };
  9000. this.data.sort(direction, fn);
  9001. if(this.snapshot && this.snapshot != this.data){
  9002. this.snapshot.sort(direction, fn);
  9003. }
  9004. },
  9005. setDefaultSort : function(field, dir){
  9006. dir = dir ? dir.toUpperCase() : "ASC";
  9007. this.sortInfo = {field: field, direction: dir};
  9008. this.sortToggle[field] = dir;
  9009. },
  9010. sort : function(fieldName, dir){
  9011. var f = this.fields.get(fieldName);
  9012. if(!f){
  9013. return false;
  9014. }
  9015. if(!dir){
  9016. if(this.sortInfo && this.sortInfo.field == f.name){ // toggle sort dir
  9017. dir = (this.sortToggle[f.name] || "ASC").toggle("ASC", "DESC");
  9018. }else{
  9019. dir = f.sortDir;
  9020. }
  9021. }
  9022. var st = (this.sortToggle) ? this.sortToggle[f.name] : null;
  9023. var si = (this.sortInfo) ? this.sortInfo : null;
  9024. this.sortToggle[f.name] = dir;
  9025. this.sortInfo = {field: f.name, direction: dir};
  9026. if(!this.remoteSort){
  9027. this.applySort();
  9028. this.fireEvent("datachanged", this);
  9029. }else{
  9030. if (!this.load(this.lastOptions)) {
  9031. if (st) {
  9032. this.sortToggle[f.name] = st;
  9033. }
  9034. if (si) {
  9035. this.sortInfo = si;
  9036. }
  9037. }
  9038. }
  9039. },
  9040. each : function(fn, scope){
  9041. this.data.each(fn, scope);
  9042. },
  9043. getModifiedRecords : function(){
  9044. return this.modified;
  9045. },
  9046. // private
  9047. createFilterFn : function(property, value, anyMatch, caseSensitive){
  9048. if(Ext.isEmpty(value, false)){
  9049. return false;
  9050. }
  9051. value = this.data.createValueMatcher(value, anyMatch, caseSensitive);
  9052. return function(r){
  9053. return value.test(r.data[property]);
  9054. };
  9055. },
  9056. sum : function(property, start, end){
  9057. var rs = this.data.items, v = 0;
  9058. start = start || 0;
  9059. end = (end || end === 0) ? end : rs.length-1;
  9060. for(var i = start; i <= end; i++){
  9061. v += (rs[i].data[property] || 0);
  9062. }
  9063. return v;
  9064. },
  9065. filter : function(property, value, anyMatch, caseSensitive){
  9066. var fn = this.createFilterFn(property, value, anyMatch, caseSensitive);
  9067. return fn ? this.filterBy(fn) : this.clearFilter();
  9068. },
  9069. filterBy : function(fn, scope){
  9070. this.snapshot = this.snapshot || this.data;
  9071. this.data = this.queryBy(fn, scope||this);
  9072. this.fireEvent("datachanged", this);
  9073. },
  9074. query : function(property, value, anyMatch, caseSensitive){
  9075. var fn = this.createFilterFn(property, value, anyMatch, caseSensitive);
  9076. return fn ? this.queryBy(fn) : this.data.clone();
  9077. },
  9078. queryBy : function(fn, scope){
  9079. var data = this.snapshot || this.data;
  9080. return data.filterBy(fn, scope||this);
  9081. },
  9082. find : function(property, value, start, anyMatch, caseSensitive){
  9083. var fn = this.createFilterFn(property, value, anyMatch, caseSensitive);
  9084. return fn ? this.data.findIndexBy(fn, null, start) : -1;
  9085. },
  9086. findBy : function(fn, scope, start){
  9087. return this.data.findIndexBy(fn, scope, start);
  9088. },
  9089. collect : function(dataIndex, allowNull, bypassFilter){
  9090. var d = (bypassFilter === true && this.snapshot) ?
  9091. this.snapshot.items : this.data.items;
  9092. var v, sv, r = [], l = {};
  9093. for(var i = 0, len = d.length; i < len; i++){
  9094. v = d[i].data[dataIndex];
  9095. sv = String(v);
  9096. if((allowNull || !Ext.isEmpty(v)) && !l[sv]){
  9097. l[sv] = true;
  9098. r[r.length] = v;
  9099. }
  9100. }
  9101. return r;
  9102. },
  9103. clearFilter : function(suppressEvent){
  9104. if(this.isFiltered()){
  9105. this.data = this.snapshot;
  9106. delete this.snapshot;
  9107. if(suppressEvent !== true){
  9108. this.fireEvent("datachanged", this);
  9109. }
  9110. }
  9111. },
  9112. isFiltered : function(){
  9113. return this.snapshot && this.snapshot != this.data;
  9114. },
  9115. // private
  9116. afterEdit : function(record){
  9117. if(this.modified.indexOf(record) == -1){
  9118. this.modified.push(record);
  9119. }
  9120. this.fireEvent("update", this, record, Ext.data.Record.EDIT);
  9121. },
  9122. // private
  9123. afterReject : function(record){
  9124. this.modified.remove(record);
  9125. this.fireEvent("update", this, record, Ext.data.Record.REJECT);
  9126. },
  9127. // private
  9128. afterCommit : function(record){
  9129. this.modified.remove(record);
  9130. this.fireEvent("update", this, record, Ext.data.Record.COMMIT);
  9131. },
  9132. commitChanges : function(){
  9133. var m = this.modified.slice(0);
  9134. this.modified = [];
  9135. for(var i = 0, len = m.length; i < len; i++){
  9136. m[i].commit();
  9137. }
  9138. },
  9139. rejectChanges : function(){
  9140. var m = this.modified.slice(0);
  9141. this.modified = [];
  9142. for(var i = 0, len = m.length; i < len; i++){
  9143. m[i].reject();
  9144. }
  9145. },
  9146. // private
  9147. onMetaChange : function(meta, rtype, o){
  9148. this.recordType = rtype;
  9149. this.fields = rtype.prototype.fields;
  9150. delete this.snapshot;
  9151. this.sortInfo = meta.sortInfo;
  9152. this.modified = [];
  9153. this.fireEvent('metachange', this, this.reader.meta);
  9154. },
  9155. // private
  9156. findInsertIndex : function(record){
  9157. this.suspendEvents();
  9158. var data = this.data.clone();
  9159. this.data.add(record);
  9160. this.applySort();
  9161. var index = this.data.indexOf(record);
  9162. this.data = data;
  9163. this.resumeEvents();
  9164. return index;
  9165. }
  9166. });
  9167. Ext.data.SimpleStore = function(config){
  9168. Ext.data.SimpleStore.superclass.constructor.call(this, Ext.apply(config, {
  9169. reader: new Ext.data.ArrayReader({
  9170. id: config.id
  9171. },
  9172. Ext.data.Record.create(config.fields)
  9173. )
  9174. }));
  9175. };
  9176. Ext.extend(Ext.data.SimpleStore, Ext.data.Store, {
  9177. loadData : function(data, append){
  9178. if(this.expandData === true){
  9179. var r = [];
  9180. for(var i = 0, len = data.length; i < len; i++){
  9181. r[r.length] = [data[i]];
  9182. }
  9183. data = r;
  9184. }
  9185. Ext.data.SimpleStore.superclass.loadData.call(this, data, append);
  9186. }
  9187. });
  9188. Ext.data.JsonStore = function(c){
  9189. Ext.data.JsonStore.superclass.constructor.call(this, Ext.apply(c, {
  9190. proxy: c.proxy || (!c.data ? new Ext.data.HttpProxy({url: c.url}) : undefined),
  9191. reader: new Ext.data.JsonReader(c, c.fields)
  9192. }));
  9193. };
  9194. Ext.extend(Ext.data.JsonStore, Ext.data.Store);
  9195. Ext.data.Field = function(config){
  9196. if(typeof config == "string"){
  9197. config = {name: config};
  9198. }
  9199. Ext.apply(this, config);
  9200. if(!this.type){
  9201. this.type = "auto";
  9202. }
  9203. var st = Ext.data.SortTypes;
  9204. // named sortTypes are supported, here we look them up
  9205. if(typeof this.sortType == "string"){
  9206. this.sortType = st[this.sortType];
  9207. }
  9208. // set default sortType for strings and dates
  9209. if(!this.sortType){
  9210. switch(this.type){
  9211. case "string":
  9212. this.sortType = st.asUCString;
  9213. break;
  9214. case "date":
  9215. this.sortType = st.asDate;
  9216. break;
  9217. default:
  9218. this.sortType = st.none;
  9219. }
  9220. }
  9221. // define once
  9222. var stripRe = /[\$,%]/g;
  9223. // prebuilt conversion function for this field, instead of
  9224. // switching every time we're reading a value
  9225. if(!this.convert){
  9226. var cv, dateFormat = this.dateFormat;
  9227. switch(this.type){
  9228. case "":
  9229. case "auto":
  9230. case undefined:
  9231. cv = function(v){ return v; };
  9232. break;
  9233. case "string":
  9234. cv = function(v){ return (v === undefined || v === null) ? '' : String(v); };
  9235. break;
  9236. case "int":
  9237. cv = function(v){
  9238. return v !== undefined && v !== null && v !== '' ?
  9239. parseInt(String(v).replace(stripRe, ""), 10) : '';
  9240. };
  9241. break;
  9242. case "float":
  9243. cv = function(v){
  9244. return v !== undefined && v !== null && v !== '' ?
  9245. parseFloat(String(v).replace(stripRe, ""), 10) : '';
  9246. };
  9247. break;
  9248. case "bool":
  9249. case "boolean":
  9250. cv = function(v){ return v === true || v === "true" || v == 1; };
  9251. break;
  9252. case "date":
  9253. cv = function(v){
  9254. if(!v){
  9255. return '';
  9256. }
  9257. if(Ext.isDate(v)){
  9258. return v;
  9259. }
  9260. if(dateFormat){
  9261. if(dateFormat == "timestamp"){
  9262. return new Date(v*1000);
  9263. }
  9264. if(dateFormat == "time"){
  9265. return new Date(parseInt(v, 10));
  9266. }
  9267. return Date.parseDate(v, dateFormat);
  9268. }
  9269. var parsed = Date.parse(v);
  9270. return parsed ? new Date(parsed) : null;
  9271. };
  9272. break;
  9273. }
  9274. this.convert = cv;
  9275. }
  9276. };
  9277. Ext.data.Field.prototype = {
  9278. dateFormat: null,
  9279. defaultValue: "",
  9280. mapping: null,
  9281. sortType : null,
  9282. sortDir : "ASC"
  9283. };
  9284. Ext.data.DataReader = function(meta, recordType){
  9285. this.meta = meta;
  9286. this.recordType = Ext.isArray(recordType) ?
  9287. Ext.data.Record.create(recordType) : recordType;
  9288. };
  9289. Ext.data.DataReader.prototype = {
  9290. };
  9291. Ext.data.DataProxy = function(){
  9292. this.addEvents(
  9293. 'beforeload',
  9294. 'load'
  9295. );
  9296. Ext.data.DataProxy.superclass.constructor.call(this);
  9297. };
  9298. Ext.extend(Ext.data.DataProxy, Ext.util.Observable);
  9299. Ext.data.MemoryProxy = function(data){
  9300. Ext.data.MemoryProxy.superclass.constructor.call(this);
  9301. this.data = data;
  9302. };
  9303. Ext.extend(Ext.data.MemoryProxy, Ext.data.DataProxy, {
  9304. load : function(params, reader, callback, scope, arg){
  9305. params = params || {};
  9306. var result;
  9307. try {
  9308. result = reader.readRecords(this.data);
  9309. }catch(e){
  9310. this.fireEvent("loadexception", this, arg, null, e);
  9311. callback.call(scope, null, arg, false);
  9312. return;
  9313. }
  9314. callback.call(scope, result, arg, true);
  9315. },
  9316. // private
  9317. update : function(params, records){
  9318. }
  9319. });
  9320. Ext.data.HttpProxy = function(conn){
  9321. Ext.data.HttpProxy.superclass.constructor.call(this);
  9322. this.conn = conn;
  9323. this.useAjax = !conn || !conn.events;
  9324. };
  9325. Ext.extend(Ext.data.HttpProxy, Ext.data.DataProxy, {
  9326. getConnection : function(){
  9327. return this.useAjax ? Ext.Ajax : this.conn;
  9328. },
  9329. load : function(params, reader, callback, scope, arg){
  9330. if(this.fireEvent("beforeload", this, params) !== false){
  9331. var o = {
  9332. params : params || {},
  9333. request: {
  9334. callback : callback,
  9335. scope : scope,
  9336. arg : arg
  9337. },
  9338. reader: reader,
  9339. callback : this.loadResponse,
  9340. scope: this
  9341. };
  9342. if(this.useAjax){
  9343. Ext.applyIf(o, this.conn);
  9344. if(this.activeRequest){
  9345. Ext.Ajax.abort(this.activeRequest);
  9346. }
  9347. this.activeRequest = Ext.Ajax.request(o);
  9348. }else{
  9349. this.conn.request(o);
  9350. }
  9351. }else{
  9352. callback.call(scope||this, null, arg, false);
  9353. }
  9354. },
  9355. // private
  9356. loadResponse : function(o, success, response){
  9357. delete this.activeRequest;
  9358. if(!success){
  9359. this.fireEvent("loadexception", this, o, response);
  9360. o.request.callback.call(o.request.scope, null, o.request.arg, false);
  9361. return;
  9362. }
  9363. var result;
  9364. try {
  9365. result = o.reader.read(response);
  9366. }catch(e){
  9367. this.fireEvent("loadexception", this, o, response, e);
  9368. o.request.callback.call(o.request.scope, null, o.request.arg, false);
  9369. return;
  9370. }
  9371. this.fireEvent("load", this, o, o.request.arg);
  9372. o.request.callback.call(o.request.scope, result, o.request.arg, true);
  9373. },
  9374. // private
  9375. update : function(dataSet){
  9376. },
  9377. // private
  9378. updateResponse : function(dataSet){
  9379. }
  9380. });
  9381. Ext.data.ScriptTagProxy = function(config){
  9382. Ext.data.ScriptTagProxy.superclass.constructor.call(this);
  9383. Ext.apply(this, config);
  9384. this.head = document.getElementsByTagName("head")[0];
  9385. };
  9386. Ext.data.ScriptTagProxy.TRANS_ID = 1000;
  9387. Ext.extend(Ext.data.ScriptTagProxy, Ext.data.DataProxy, {
  9388. timeout : 30000,
  9389. callbackParam : "callback",
  9390. nocache : true,
  9391. load : function(params, reader, callback, scope, arg){
  9392. if(this.fireEvent("beforeload", this, params) !== false){
  9393. var p = Ext.urlEncode(Ext.apply(params, this.extraParams));
  9394. var url = this.url;
  9395. url += (url.indexOf("?") != -1 ? "&" : "?") + p;
  9396. if(this.nocache){
  9397. url += "&_dc=" + (new Date().getTime());
  9398. }
  9399. var transId = ++Ext.data.ScriptTagProxy.TRANS_ID;
  9400. var trans = {
  9401. id : transId,
  9402. cb : "stcCallback"+transId,
  9403. scriptId : "stcScript"+transId,
  9404. params : params,
  9405. arg : arg,
  9406. url : url,
  9407. callback : callback,
  9408. scope : scope,
  9409. reader : reader
  9410. };
  9411. var conn = this;
  9412. window[trans.cb] = function(o){
  9413. conn.handleResponse(o, trans);
  9414. };
  9415. url += String.format("&{0}={1}", this.callbackParam, trans.cb);
  9416. if(this.autoAbort !== false){
  9417. this.abort();
  9418. }
  9419. trans.timeoutId = this.handleFailure.defer(this.timeout, this, [trans]);
  9420. var script = document.createElement("script");
  9421. script.setAttribute("src", url);
  9422. script.setAttribute("type", "text/javascript");
  9423. script.setAttribute("id", trans.scriptId);
  9424. this.head.appendChild(script);
  9425. this.trans = trans;
  9426. }else{
  9427. callback.call(scope||this, null, arg, false);
  9428. }
  9429. },
  9430. // private
  9431. isLoading : function(){
  9432. return this.trans ? true : false;
  9433. },
  9434. abort : function(){
  9435. if(this.isLoading()){
  9436. this.destroyTrans(this.trans);
  9437. }
  9438. },
  9439. // private
  9440. destroyTrans : function(trans, isLoaded){
  9441. this.head.removeChild(document.getElementById(trans.scriptId));
  9442. clearTimeout(trans.timeoutId);
  9443. if(isLoaded){
  9444. window[trans.cb] = undefined;
  9445. try{
  9446. delete window[trans.cb];
  9447. }catch(e){}
  9448. }else{
  9449. // if hasn't been loaded, wait for load to remove it to prevent script error
  9450. window[trans.cb] = function(){
  9451. window[trans.cb] = undefined;
  9452. try{
  9453. delete window[trans.cb];
  9454. }catch(e){}
  9455. };
  9456. }
  9457. },
  9458. // private
  9459. handleResponse : function(o, trans){
  9460. this.trans = false;
  9461. this.destroyTrans(trans, true);
  9462. var result;
  9463. try {
  9464. result = trans.reader.readRecords(o);
  9465. }catch(e){
  9466. this.fireEvent("loadexception", this, o, trans.arg, e);
  9467. trans.callback.call(trans.scope||window, null, trans.arg, false);
  9468. return;
  9469. }
  9470. this.fireEvent("load", this, o, trans.arg);
  9471. trans.callback.call(trans.scope||window, result, trans.arg, true);
  9472. },
  9473. // private
  9474. handleFailure : function(trans){
  9475. this.trans = false;
  9476. this.destroyTrans(trans, false);
  9477. this.fireEvent("loadexception", this, null, trans.arg);
  9478. trans.callback.call(trans.scope||window, null, trans.arg, false);
  9479. }
  9480. });
  9481. Ext.data.JsonReader = function(meta, recordType){
  9482. meta = meta || {};
  9483. Ext.data.JsonReader.superclass.constructor.call(this, meta, recordType || meta.fields);
  9484. };
  9485. Ext.extend(Ext.data.JsonReader, Ext.data.DataReader, {
  9486. read : function(response){
  9487. var json = response.responseText;
  9488. var o = eval("("+json+")");
  9489. if(!o) {
  9490. throw {message: "JsonReader.read: Json object not found"};
  9491. }
  9492. return this.readRecords(o);
  9493. },
  9494. // private function a store will implement
  9495. onMetaChange : function(meta, recordType, o){
  9496. },
  9497. simpleAccess: function(obj, subsc) {
  9498. return obj[subsc];
  9499. },
  9500. getJsonAccessor: function(){
  9501. var re = /[\[\.]/;
  9502. return function(expr) {
  9503. try {
  9504. return(re.test(expr))
  9505. ? new Function("obj", "return obj." + expr)
  9506. : function(obj){
  9507. return obj[expr];
  9508. };
  9509. } catch(e){}
  9510. return Ext.emptyFn;
  9511. };
  9512. }(),
  9513. readRecords : function(o){
  9514. this.jsonData = o;
  9515. if(o.metaData){
  9516. delete this.ef;
  9517. this.meta = o.metaData;
  9518. this.recordType = Ext.data.Record.create(o.metaData.fields);
  9519. this.onMetaChange(this.meta, this.recordType, o);
  9520. }
  9521. var s = this.meta, Record = this.recordType,
  9522. f = Record.prototype.fields, fi = f.items, fl = f.length;
  9523. // Generate extraction functions for the totalProperty, the root, the id, and for each field
  9524. if (!this.ef) {
  9525. if(s.totalProperty) {
  9526. this.getTotal = this.getJsonAccessor(s.totalProperty);
  9527. }
  9528. if(s.successProperty) {
  9529. this.getSuccess = this.getJsonAccessor(s.successProperty);
  9530. }
  9531. this.getRoot = s.root ? this.getJsonAccessor(s.root) : function(p){return p;};
  9532. if (s.id) {
  9533. var g = this.getJsonAccessor(s.id);
  9534. this.getId = function(rec) {
  9535. var r = g(rec);
  9536. return (r === undefined || r === "") ? null : r;
  9537. };
  9538. } else {
  9539. this.getId = function(){return null;};
  9540. }
  9541. this.ef = [];
  9542. for(var i = 0; i < fl; i++){
  9543. f = fi[i];
  9544. var map = (f.mapping !== undefined && f.mapping !== null) ? f.mapping : f.name;
  9545. this.ef[i] = this.getJsonAccessor(map);
  9546. }
  9547. }
  9548. var root = this.getRoot(o), c = root.length, totalRecords = c, success = true;
  9549. if(s.totalProperty){
  9550. var v = parseInt(this.getTotal(o), 10);
  9551. if(!isNaN(v)){
  9552. totalRecords = v;
  9553. }
  9554. }
  9555. if(s.successProperty){
  9556. var v = this.getSuccess(o);
  9557. if(v === false || v === 'false'){
  9558. success = false;
  9559. }
  9560. }
  9561. var records = [];
  9562. for(var i = 0; i < c; i++){
  9563. var n = root[i];
  9564. var values = {};
  9565. var id = this.getId(n);
  9566. for(var j = 0; j < fl; j++){
  9567. f = fi[j];
  9568. var v = this.ef[j](n);
  9569. values[f.name] = f.convert((v !== undefined) ? v : f.defaultValue, n);
  9570. }
  9571. var record = new Record(values, id);
  9572. record.json = n;
  9573. records[i] = record;
  9574. }
  9575. return {
  9576. success : success,
  9577. records : records,
  9578. totalRecords : totalRecords
  9579. };
  9580. }
  9581. });
  9582. Ext.data.XmlReader = function(meta, recordType){
  9583. meta = meta || {};
  9584. Ext.data.XmlReader.superclass.constructor.call(this, meta, recordType || meta.fields);
  9585. };
  9586. Ext.extend(Ext.data.XmlReader, Ext.data.DataReader, {
  9587. read : function(response){
  9588. var doc = response.responseXML;
  9589. if(!doc) {
  9590. throw {message: "XmlReader.read: XML Document not available"};
  9591. }
  9592. return this.readRecords(doc);
  9593. },
  9594. readRecords : function(doc){
  9595. this.xmlData = doc;
  9596. var root = doc.documentElement || doc;
  9597. var q = Ext.DomQuery;
  9598. var recordType = this.recordType, fields = recordType.prototype.fields;
  9599. var sid = this.meta.id;
  9600. var totalRecords = 0, success = true;
  9601. if(this.meta.totalRecords){
  9602. totalRecords = q.selectNumber(this.meta.totalRecords, root, 0);
  9603. }
  9604. if(this.meta.success){
  9605. var sv = q.selectValue(this.meta.success, root, true);
  9606. success = sv !== false && sv !== 'false';
  9607. }
  9608. var records = [];
  9609. var ns = q.select(this.meta.record, root);
  9610. for(var i = 0, len = ns.length; i < len; i++) {
  9611. var n = ns[i];
  9612. var values = {};
  9613. var id = sid ? q.selectValue(sid, n) : undefined;
  9614. for(var j = 0, jlen = fields.length; j < jlen; j++){
  9615. var f = fields.items[j];
  9616. var v = q.selectValue(f.mapping || f.name, n, f.defaultValue);
  9617. v = f.convert(v, n);
  9618. values[f.name] = v;
  9619. }
  9620. var record = new recordType(values, id);
  9621. record.node = n;
  9622. records[records.length] = record;
  9623. }
  9624. return {
  9625. success : success,
  9626. records : records,
  9627. totalRecords : totalRecords || records.length
  9628. };
  9629. }
  9630. });
  9631. Ext.data.ArrayReader = Ext.extend(Ext.data.JsonReader, {
  9632. readRecords : function(o){
  9633. var sid = this.meta ? this.meta.id : null;
  9634. var recordType = this.recordType, fields = recordType.prototype.fields;
  9635. var records = [];
  9636. var root = o;
  9637. for(var i = 0; i < root.length; i++){
  9638. var n = root[i];
  9639. var values = {};
  9640. var id = ((sid || sid === 0) && n[sid] !== undefined && n[sid] !== "" ? n[sid] : null);
  9641. for(var j = 0, jlen = fields.length; j < jlen; j++){
  9642. var f = fields.items[j];
  9643. var k = f.mapping !== undefined && f.mapping !== null ? f.mapping : j;
  9644. var v = n[k] !== undefined ? n[k] : f.defaultValue;
  9645. v = f.convert(v, n);
  9646. values[f.name] = v;
  9647. }
  9648. var record = new recordType(values, id);
  9649. record.json = n;
  9650. records[records.length] = record;
  9651. }
  9652. return {
  9653. records : records,
  9654. totalRecords : records.length
  9655. };
  9656. }
  9657. });
  9658. Ext.data.Tree = function(root){
  9659. this.nodeHash = {};
  9660. this.root = null;
  9661. if(root){
  9662. this.setRootNode(root);
  9663. }
  9664. this.addEvents(
  9665. "append",
  9666. "remove",
  9667. "move",
  9668. "insert",
  9669. "beforeappend",
  9670. "beforeremove",
  9671. "beforemove",
  9672. "beforeinsert"
  9673. );
  9674. Ext.data.Tree.superclass.constructor.call(this);
  9675. };
  9676. Ext.extend(Ext.data.Tree, Ext.util.Observable, {
  9677. pathSeparator: "/",
  9678. // private
  9679. proxyNodeEvent : function(){
  9680. return this.fireEvent.apply(this, arguments);
  9681. },
  9682. getRootNode : function(){
  9683. return this.root;
  9684. },
  9685. setRootNode : function(node){
  9686. this.root = node;
  9687. node.ownerTree = this;
  9688. node.isRoot = true;
  9689. this.registerNode(node);
  9690. return node;
  9691. },
  9692. getNodeById : function(id){
  9693. return this.nodeHash[id];
  9694. },
  9695. // private
  9696. registerNode : function(node){
  9697. this.nodeHash[node.id] = node;
  9698. },
  9699. // private
  9700. unregisterNode : function(node){
  9701. delete this.nodeHash[node.id];
  9702. },
  9703. toString : function(){
  9704. return "[Tree"+(this.id?" "+this.id:"")+"]";
  9705. }
  9706. });
  9707. Ext.data.Node = function(attributes){
  9708. this.attributes = attributes || {};
  9709. this.leaf = this.attributes.leaf;
  9710. this.id = this.attributes.id;
  9711. if(!this.id){
  9712. this.id = Ext.id(null, "ynode-");
  9713. this.attributes.id = this.id;
  9714. }
  9715. this.childNodes = [];
  9716. if(!this.childNodes.indexOf){ // indexOf is a must
  9717. this.childNodes.indexOf = function(o){
  9718. for(var i = 0, len = this.length; i < len; i++){
  9719. if(this[i] == o) return i;
  9720. }
  9721. return -1;
  9722. };
  9723. }
  9724. this.parentNode = null;
  9725. this.firstChild = null;
  9726. this.lastChild = null;
  9727. this.previousSibling = null;
  9728. this.nextSibling = null;
  9729. this.addEvents({
  9730. "append" : true,
  9731. "remove" : true,
  9732. "move" : true,
  9733. "insert" : true,
  9734. "beforeappend" : true,
  9735. "beforeremove" : true,
  9736. "beforemove" : true,
  9737. "beforeinsert" : true
  9738. });
  9739. this.listeners = this.attributes.listeners;
  9740. Ext.data.Node.superclass.constructor.call(this);
  9741. };
  9742. Ext.extend(Ext.data.Node, Ext.util.Observable, {
  9743. // private
  9744. fireEvent : function(evtName){
  9745. // first do standard event for this node
  9746. if(Ext.data.Node.superclass.fireEvent.apply(this, arguments) === false){
  9747. return false;
  9748. }
  9749. // then bubble it up to the tree if the event wasn't cancelled
  9750. var ot = this.getOwnerTree();
  9751. if(ot){
  9752. if(ot.proxyNodeEvent.apply(ot, arguments) === false){
  9753. return false;
  9754. }
  9755. }
  9756. return true;
  9757. },
  9758. isLeaf : function(){
  9759. return this.leaf === true;
  9760. },
  9761. // private
  9762. setFirstChild : function(node){
  9763. this.firstChild = node;
  9764. },
  9765. //private
  9766. setLastChild : function(node){
  9767. this.lastChild = node;
  9768. },
  9769. isLast : function(){
  9770. return (!this.parentNode ? true : this.parentNode.lastChild == this);
  9771. },
  9772. isFirst : function(){
  9773. return (!this.parentNode ? true : this.parentNode.firstChild == this);
  9774. },
  9775. hasChildNodes : function(){
  9776. return !this.isLeaf() && this.childNodes.length > 0;
  9777. },
  9778. isExpandable : function(){
  9779. return this.attributes.expandable || this.hasChildNodes();
  9780. },
  9781. appendChild : function(node){
  9782. var multi = false;
  9783. if(Ext.isArray(node)){
  9784. multi = node;
  9785. }else if(arguments.length > 1){
  9786. multi = arguments;
  9787. }
  9788. // if passed an array or multiple args do them one by one
  9789. if(multi){
  9790. for(var i = 0, len = multi.length; i < len; i++) {
  9791. this.appendChild(multi[i]);
  9792. }
  9793. }else{
  9794. if(this.fireEvent("beforeappend", this.ownerTree, this, node) === false){
  9795. return false;
  9796. }
  9797. var index = this.childNodes.length;
  9798. var oldParent = node.parentNode;
  9799. // it's a move, make sure we move it cleanly
  9800. if(oldParent){
  9801. if(node.fireEvent("beforemove", node.getOwnerTree(), node, oldParent, this, index) === false){
  9802. return false;
  9803. }
  9804. oldParent.removeChild(node);
  9805. }
  9806. index = this.childNodes.length;
  9807. if(index == 0){
  9808. this.setFirstChild(node);
  9809. }
  9810. this.childNodes.push(node);
  9811. node.parentNode = this;
  9812. var ps = this.childNodes[index-1];
  9813. if(ps){
  9814. node.previousSibling = ps;
  9815. ps.nextSibling = node;
  9816. }else{
  9817. node.previousSibling = null;
  9818. }
  9819. node.nextSibling = null;
  9820. this.setLastChild(node);
  9821. node.setOwnerTree(this.getOwnerTree());
  9822. this.fireEvent("append", this.ownerTree, this, node, index);
  9823. if(oldParent){
  9824. node.fireEvent("move", this.ownerTree, node, oldParent, this, index);
  9825. }
  9826. return node;
  9827. }
  9828. },
  9829. removeChild : function(node){
  9830. var index = this.childNodes.indexOf(node);
  9831. if(index == -1){
  9832. return false;
  9833. }
  9834. if(this.fireEvent("beforeremove", this.ownerTree, this, node) === false){
  9835. return false;
  9836. }
  9837. // remove it from childNodes collection
  9838. this.childNodes.splice(index, 1);
  9839. // update siblings
  9840. if(node.previousSibling){
  9841. node.previousSibling.nextSibling = node.nextSibling;
  9842. }
  9843. if(node.nextSibling){
  9844. node.nextSibling.previousSibling = node.previousSibling;
  9845. }
  9846. // update child refs
  9847. if(this.firstChild == node){
  9848. this.setFirstChild(node.nextSibling);
  9849. }
  9850. if(this.lastChild == node){
  9851. this.setLastChild(node.previousSibling);
  9852. }
  9853. node.setOwnerTree(null);
  9854. // clear any references from the node
  9855. node.parentNode = null;
  9856. node.previousSibling = null;
  9857. node.nextSibling = null;
  9858. this.fireEvent("remove", this.ownerTree, this, node);
  9859. return node;
  9860. },
  9861. insertBefore : function(node, refNode){
  9862. if(!refNode){ // like standard Dom, refNode can be null for append
  9863. return this.appendChild(node);
  9864. }
  9865. // nothing to do
  9866. if(node == refNode){
  9867. return false;
  9868. }
  9869. if(this.fireEvent("beforeinsert", this.ownerTree, this, node, refNode) === false){
  9870. return false;
  9871. }
  9872. var index = this.childNodes.indexOf(refNode);
  9873. var oldParent = node.parentNode;
  9874. var refIndex = index;
  9875. // when moving internally, indexes will change after remove
  9876. if(oldParent == this && this.childNodes.indexOf(node) < index){
  9877. refIndex--;
  9878. }
  9879. // it's a move, make sure we move it cleanly
  9880. if(oldParent){
  9881. if(node.fireEvent("beforemove", node.getOwnerTree(), node, oldParent, this, index, refNode) === false){
  9882. return false;
  9883. }
  9884. oldParent.removeChild(node);
  9885. }
  9886. if(refIndex == 0){
  9887. this.setFirstChild(node);
  9888. }
  9889. this.childNodes.splice(refIndex, 0, node);
  9890. node.parentNode = this;
  9891. var ps = this.childNodes[refIndex-1];
  9892. if(ps){
  9893. node.previousSibling = ps;
  9894. ps.nextSibling = node;
  9895. }else{
  9896. node.previousSibling = null;
  9897. }
  9898. node.nextSibling = refNode;
  9899. refNode.previousSibling = node;
  9900. node.setOwnerTree(this.getOwnerTree());
  9901. this.fireEvent("insert", this.ownerTree, this, node, refNode);
  9902. if(oldParent){
  9903. node.fireEvent("move", this.ownerTree, node, oldParent, this, refIndex, refNode);
  9904. }
  9905. return node;
  9906. },
  9907. remove : function(){
  9908. this.parentNode.removeChild(this);
  9909. return this;
  9910. },
  9911. item : function(index){
  9912. return this.childNodes[index];
  9913. },
  9914. replaceChild : function(newChild, oldChild){
  9915. var s = oldChild ? oldChild.nextSibling : null;
  9916. this.removeChild(oldChild);
  9917. this.insertBefore(newChild, s);
  9918. return oldChild;
  9919. },
  9920. indexOf : function(child){
  9921. return this.childNodes.indexOf(child);
  9922. },
  9923. getOwnerTree : function(){
  9924. // if it doesn't have one, look for one
  9925. if(!this.ownerTree){
  9926. var p = this;
  9927. while(p){
  9928. if(p.ownerTree){
  9929. this.ownerTree = p.ownerTree;
  9930. break;
  9931. }
  9932. p = p.parentNode;
  9933. }
  9934. }
  9935. return this.ownerTree;
  9936. },
  9937. getDepth : function(){
  9938. var depth = 0;
  9939. var p = this;
  9940. while(p.parentNode){
  9941. ++depth;
  9942. p = p.parentNode;
  9943. }
  9944. return depth;
  9945. },
  9946. // private
  9947. setOwnerTree : function(tree){
  9948. // if it's move, we need to update everyone
  9949. if(tree != this.ownerTree){
  9950. if(this.ownerTree){
  9951. this.ownerTree.unregisterNode(this);
  9952. }
  9953. this.ownerTree = tree;
  9954. var cs = this.childNodes;
  9955. for(var i = 0, len = cs.length; i < len; i++) {
  9956. cs[i].setOwnerTree(tree);
  9957. }
  9958. if(tree){
  9959. tree.registerNode(this);
  9960. }
  9961. }
  9962. },
  9963. getPath : function(attr){
  9964. attr = attr || "id";
  9965. var p = this.parentNode;
  9966. var b = [this.attributes[attr]];
  9967. while(p){
  9968. b.unshift(p.attributes[attr]);
  9969. p = p.parentNode;
  9970. }
  9971. var sep = this.getOwnerTree().pathSeparator;
  9972. return sep + b.join(sep);
  9973. },
  9974. bubble : function(fn, scope, args){
  9975. var p = this;
  9976. while(p){
  9977. if(fn.apply(scope || p, args || [p]) === false){
  9978. break;
  9979. }
  9980. p = p.parentNode;
  9981. }
  9982. },
  9983. cascade : function(fn, scope, args){
  9984. if(fn.apply(scope || this, args || [this]) !== false){
  9985. var cs = this.childNodes;
  9986. for(var i = 0, len = cs.length; i < len; i++) {
  9987. cs[i].cascade(fn, scope, args);
  9988. }
  9989. }
  9990. },
  9991. eachChild : function(fn, scope, args){
  9992. var cs = this.childNodes;
  9993. for(var i = 0, len = cs.length; i < len; i++) {
  9994. if(fn.apply(scope || this, args || [cs[i]]) === false){
  9995. break;
  9996. }
  9997. }
  9998. },
  9999. findChild : function(attribute, value){
  10000. var cs = this.childNodes;
  10001. for(var i = 0, len = cs.length; i < len; i++) {
  10002. if(cs[i].attributes[attribute] == value){
  10003. return cs[i];
  10004. }
  10005. }
  10006. return null;
  10007. },
  10008. findChildBy : function(fn, scope){
  10009. var cs = this.childNodes;
  10010. for(var i = 0, len = cs.length; i < len; i++) {
  10011. if(fn.call(scope||cs[i], cs[i]) === true){
  10012. return cs[i];
  10013. }
  10014. }
  10015. return null;
  10016. },
  10017. sort : function(fn, scope){
  10018. var cs = this.childNodes;
  10019. var len = cs.length;
  10020. if(len > 0){
  10021. var sortFn = scope ? function(){fn.apply(scope, arguments);} : fn;
  10022. cs.sort(sortFn);
  10023. for(var i = 0; i < len; i++){
  10024. var n = cs[i];
  10025. n.previousSibling = cs[i-1];
  10026. n.nextSibling = cs[i+1];
  10027. if(i == 0){
  10028. this.setFirstChild(n);
  10029. }
  10030. if(i == len-1){
  10031. this.setLastChild(n);
  10032. }
  10033. }
  10034. }
  10035. },
  10036. contains : function(node){
  10037. return node.isAncestor(this);
  10038. },
  10039. isAncestor : function(node){
  10040. var p = this.parentNode;
  10041. while(p){
  10042. if(p == node){
  10043. return true;
  10044. }
  10045. p = p.parentNode;
  10046. }
  10047. return false;
  10048. },
  10049. toString : function(){
  10050. return "[Node"+(this.id?" "+this.id:"")+"]";
  10051. }
  10052. });
  10053. Ext.data.GroupingStore = Ext.extend(Ext.data.Store, {
  10054. remoteGroup : false,
  10055. groupOnSort:false,
  10056. clearGrouping : function(){
  10057. this.groupField = false;
  10058. if(this.remoteGroup){
  10059. if(this.baseParams){
  10060. delete this.baseParams.groupBy;
  10061. }
  10062. this.reload();
  10063. }else{
  10064. this.applySort();
  10065. this.fireEvent('datachanged', this);
  10066. }
  10067. },
  10068. groupBy : function(field, forceRegroup){
  10069. if(this.groupField == field && !forceRegroup){
  10070. return; // already grouped by this field
  10071. }
  10072. this.groupField = field;
  10073. if(this.remoteGroup){
  10074. if(!this.baseParams){
  10075. this.baseParams = {};
  10076. }
  10077. this.baseParams['groupBy'] = field;
  10078. }
  10079. if(this.groupOnSort){
  10080. this.sort(field);
  10081. return;
  10082. }
  10083. if(this.remoteGroup){
  10084. this.reload();
  10085. }else{
  10086. var si = this.sortInfo || {};
  10087. if(si.field != field){
  10088. this.applySort();
  10089. }else{
  10090. this.sortData(field);
  10091. }
  10092. this.fireEvent('datachanged', this);
  10093. }
  10094. },
  10095. // private
  10096. applySort : function(){
  10097. Ext.data.GroupingStore.superclass.applySort.call(this);
  10098. if(!this.groupOnSort && !this.remoteGroup){
  10099. var gs = this.getGroupState();
  10100. if(gs && gs != this.sortInfo.field){
  10101. this.sortData(this.groupField);
  10102. }
  10103. }
  10104. },
  10105. // private
  10106. applyGrouping : function(alwaysFireChange){
  10107. if(this.groupField !== false){
  10108. this.groupBy(this.groupField, true);
  10109. return true;
  10110. }else{
  10111. if(alwaysFireChange === true){
  10112. this.fireEvent('datachanged', this);
  10113. }
  10114. return false;
  10115. }
  10116. },
  10117. // private
  10118. getGroupState : function(){
  10119. return this.groupOnSort && this.groupField !== false ?
  10120. (this.sortInfo ? this.sortInfo.field : undefined) : this.groupField;
  10121. }
  10122. });
  10123. Ext.ComponentMgr = function(){
  10124. var all = new Ext.util.MixedCollection();
  10125. var types = {};
  10126. return {
  10127. register : function(c){
  10128. all.add(c);
  10129. },
  10130. unregister : function(c){
  10131. all.remove(c);
  10132. },
  10133. get : function(id){
  10134. return all.get(id);
  10135. },
  10136. onAvailable : function(id, fn, scope){
  10137. all.on("add", function(index, o){
  10138. if(o.id == id){
  10139. fn.call(scope || o, o);
  10140. all.un("add", fn, scope);
  10141. }
  10142. });
  10143. },
  10144. all : all,
  10145. registerType : function(xtype, cls){
  10146. types[xtype] = cls;
  10147. cls.xtype = xtype;
  10148. },
  10149. create : function(config, defaultType){
  10150. return new types[config.xtype || defaultType](config);
  10151. }
  10152. };
  10153. }();
  10154. Ext.reg = Ext.ComponentMgr.registerType; // this will be called a lot internally, shorthand to keep the bytes down
  10155. Ext.Component = function(config){
  10156. config = config || {};
  10157. if(config.initialConfig){
  10158. if(config.isAction){ // actions
  10159. this.baseAction = config;
  10160. }
  10161. config = config.initialConfig; // component cloning / action set up
  10162. }else if(config.tagName || config.dom || typeof config == "string"){ // element object
  10163. config = {applyTo: config, id: config.id || config};
  10164. }
  10165. this.initialConfig = config;
  10166. Ext.apply(this, config);
  10167. this.addEvents(
  10168. 'disable',
  10169. 'enable',
  10170. 'beforeshow',
  10171. 'show',
  10172. 'beforehide',
  10173. 'hide',
  10174. 'beforerender',
  10175. 'render',
  10176. 'beforedestroy',
  10177. 'destroy',
  10178. 'beforestaterestore',
  10179. 'staterestore',
  10180. 'beforestatesave',
  10181. 'statesave'
  10182. );
  10183. this.getId();
  10184. Ext.ComponentMgr.register(this);
  10185. Ext.Component.superclass.constructor.call(this);
  10186. if(this.baseAction){
  10187. this.baseAction.addComponent(this);
  10188. }
  10189. this.initComponent();
  10190. if(this.plugins){
  10191. if(Ext.isArray(this.plugins)){
  10192. for(var i = 0, len = this.plugins.length; i < len; i++){
  10193. this.plugins[i] = this.initPlugin(this.plugins[i]);
  10194. }
  10195. }else{
  10196. this.plugins = this.initPlugin(this.plugins);
  10197. }
  10198. }
  10199. if(this.stateful !== false){
  10200. this.initState(config);
  10201. }
  10202. if(this.applyTo){
  10203. this.applyToMarkup(this.applyTo);
  10204. delete this.applyTo;
  10205. }else if(this.renderTo){
  10206. this.render(this.renderTo);
  10207. delete this.renderTo;
  10208. }
  10209. };
  10210. // private
  10211. Ext.Component.AUTO_ID = 1000;
  10212. Ext.extend(Ext.Component, Ext.util.Observable, {
  10213. // Configs below are used for all Components when rendered by FormLayout.
  10214. disabledClass : "x-item-disabled",
  10215. allowDomMove : true,
  10216. autoShow : false,
  10217. hideMode: 'display',
  10218. hideParent: false,
  10219. hidden : false,
  10220. disabled : false,
  10221. rendered : false,
  10222. // private
  10223. ctype : "Ext.Component",
  10224. // private
  10225. actionMode : "el",
  10226. // private
  10227. getActionEl : function(){
  10228. return this[this.actionMode];
  10229. },
  10230. initPlugin : function(p){
  10231. p.init(this);
  10232. return p;
  10233. },
  10234. initComponent : Ext.emptyFn,
  10235. render : function(container, position){
  10236. if(!this.rendered && this.fireEvent("beforerender", this) !== false){
  10237. if(!container && this.el){
  10238. this.el = Ext.get(this.el);
  10239. container = this.el.dom.parentNode;
  10240. this.allowDomMove = false;
  10241. }
  10242. this.container = Ext.get(container);
  10243. if(this.ctCls){
  10244. this.container.addClass(this.ctCls);
  10245. }
  10246. this.rendered = true;
  10247. if(position !== undefined){
  10248. if(typeof position == 'number'){
  10249. position = this.container.dom.childNodes[position];
  10250. }else{
  10251. position = Ext.getDom(position);
  10252. }
  10253. }
  10254. this.onRender(this.container, position || null);
  10255. if(this.autoShow){
  10256. this.el.removeClass(['x-hidden','x-hide-' + this.hideMode]);
  10257. }
  10258. if(this.cls){
  10259. this.el.addClass(this.cls);
  10260. delete this.cls;
  10261. }
  10262. if(this.style){
  10263. this.el.applyStyles(this.style);
  10264. delete this.style;
  10265. }
  10266. if(this.overCls){
  10267. this.el.addClassOnOver(this.overCls);
  10268. }
  10269. this.fireEvent("render", this);
  10270. this.afterRender(this.container);
  10271. if(this.hidden){
  10272. this.hide();
  10273. }
  10274. if(this.disabled){
  10275. this.disable();
  10276. }
  10277. if(this.stateful !== false){
  10278. this.initStateEvents();
  10279. }
  10280. }
  10281. return this;
  10282. },
  10283. // private
  10284. initState : function(config){
  10285. if(Ext.state.Manager){
  10286. var id = this.getStateId();
  10287. if(id){
  10288. var state = Ext.state.Manager.get(id);
  10289. if(state){
  10290. if(this.fireEvent('beforestaterestore', this, state) !== false){
  10291. this.applyState(state);
  10292. this.fireEvent('staterestore', this, state);
  10293. }
  10294. }
  10295. }
  10296. }
  10297. },
  10298. // private
  10299. getStateId : function(){
  10300. return this.stateId || ((this.id.indexOf('ext-comp-') == 0 || this.id.indexOf('ext-gen') == 0) ? null : this.id);
  10301. },
  10302. // private
  10303. initStateEvents : function(){
  10304. if(this.stateEvents){
  10305. for(var i = 0, e; e = this.stateEvents[i]; i++){
  10306. this.on(e, this.saveState, this, {delay:100});
  10307. }
  10308. }
  10309. },
  10310. // private
  10311. applyState : function(state, config){
  10312. if(state){
  10313. Ext.apply(this, state);
  10314. }
  10315. },
  10316. // private
  10317. getState : function(){
  10318. return null;
  10319. },
  10320. // private
  10321. saveState : function(){
  10322. if(Ext.state.Manager){
  10323. var id = this.getStateId();
  10324. if(id){
  10325. var state = this.getState();
  10326. if(this.fireEvent('beforestatesave', this, state) !== false){
  10327. Ext.state.Manager.set(id, state);
  10328. this.fireEvent('statesave', this, state);
  10329. }
  10330. }
  10331. }
  10332. },
  10333. applyToMarkup : function(el){
  10334. this.allowDomMove = false;
  10335. this.el = Ext.get(el);
  10336. this.render(this.el.dom.parentNode);
  10337. },
  10338. addClass : function(cls){
  10339. if(this.el){
  10340. this.el.addClass(cls);
  10341. }else{
  10342. this.cls = this.cls ? this.cls + ' ' + cls : cls;
  10343. }
  10344. },
  10345. removeClass : function(cls){
  10346. if(this.el){
  10347. this.el.removeClass(cls);
  10348. }else if(this.cls){
  10349. this.cls = this.cls.split(' ').remove(cls).join(' ');
  10350. }
  10351. },
  10352. // private
  10353. // default function is not really useful
  10354. onRender : function(ct, position){
  10355. if(this.autoEl){
  10356. if(typeof this.autoEl == 'string'){
  10357. this.el = document.createElement(this.autoEl);
  10358. }else{
  10359. var div = document.createElement('div');
  10360. Ext.DomHelper.overwrite(div, this.autoEl);
  10361. this.el = div.firstChild;
  10362. }
  10363. if (!this.el.id) {
  10364. this.el.id = this.getId();
  10365. }
  10366. }
  10367. if(this.el){
  10368. this.el = Ext.get(this.el);
  10369. if(this.allowDomMove !== false){
  10370. ct.dom.insertBefore(this.el.dom, position);
  10371. }
  10372. }
  10373. },
  10374. // private
  10375. getAutoCreate : function(){
  10376. var cfg = typeof this.autoCreate == "object" ?
  10377. this.autoCreate : Ext.apply({}, this.defaultAutoCreate);
  10378. if(this.id && !cfg.id){
  10379. cfg.id = this.id;
  10380. }
  10381. return cfg;
  10382. },
  10383. // private
  10384. afterRender : Ext.emptyFn,
  10385. destroy : function(){
  10386. if(this.fireEvent("beforedestroy", this) !== false){
  10387. this.beforeDestroy();
  10388. if(this.rendered){
  10389. this.el.removeAllListeners();
  10390. this.el.remove();
  10391. if(this.actionMode == "container"){
  10392. this.container.remove();
  10393. }
  10394. }
  10395. this.onDestroy();
  10396. Ext.ComponentMgr.unregister(this);
  10397. this.fireEvent("destroy", this);
  10398. this.purgeListeners();
  10399. }
  10400. },
  10401. // private
  10402. beforeDestroy : Ext.emptyFn,
  10403. // private
  10404. onDestroy : Ext.emptyFn,
  10405. getEl : function(){
  10406. return this.el;
  10407. },
  10408. getId : function(){
  10409. return this.id || (this.id = "ext-comp-" + (++Ext.Component.AUTO_ID));
  10410. },
  10411. getItemId : function(){
  10412. return this.itemId || this.getId();
  10413. },
  10414. focus : function(selectText, delay){
  10415. if(delay){
  10416. this.focus.defer(typeof delay == 'number' ? delay : 10, this, [selectText, false]);
  10417. return;
  10418. }
  10419. if(this.rendered){
  10420. this.el.focus();
  10421. if(selectText === true){
  10422. this.el.dom.select();
  10423. }
  10424. }
  10425. return this;
  10426. },
  10427. // private
  10428. blur : function(){
  10429. if(this.rendered){
  10430. this.el.blur();
  10431. }
  10432. return this;
  10433. },
  10434. disable : function(){
  10435. if(this.rendered){
  10436. this.onDisable();
  10437. }
  10438. this.disabled = true;
  10439. this.fireEvent("disable", this);
  10440. return this;
  10441. },
  10442. // private
  10443. onDisable : function(){
  10444. this.getActionEl().addClass(this.disabledClass);
  10445. this.el.dom.disabled = true;
  10446. },
  10447. enable : function(){
  10448. if(this.rendered){
  10449. this.onEnable();
  10450. }
  10451. this.disabled = false;
  10452. this.fireEvent("enable", this);
  10453. return this;
  10454. },
  10455. // private
  10456. onEnable : function(){
  10457. this.getActionEl().removeClass(this.disabledClass);
  10458. this.el.dom.disabled = false;
  10459. },
  10460. setDisabled : function(disabled){
  10461. this[disabled ? "disable" : "enable"]();
  10462. },
  10463. show: function(){
  10464. if(this.fireEvent("beforeshow", this) !== false){
  10465. this.hidden = false;
  10466. if(this.autoRender){
  10467. this.render(typeof this.autoRender == 'boolean' ? Ext.getBody() : this.autoRender);
  10468. }
  10469. if(this.rendered){
  10470. this.onShow();
  10471. }
  10472. this.fireEvent("show", this);
  10473. }
  10474. return this;
  10475. },
  10476. // private
  10477. onShow : function(){
  10478. if(this.hideParent){
  10479. this.container.removeClass('x-hide-' + this.hideMode);
  10480. }else{
  10481. this.getActionEl().removeClass('x-hide-' + this.hideMode);
  10482. }
  10483. },
  10484. hide: function(){
  10485. if(this.fireEvent("beforehide", this) !== false){
  10486. this.hidden = true;
  10487. if(this.rendered){
  10488. this.onHide();
  10489. }
  10490. this.fireEvent("hide", this);
  10491. }
  10492. return this;
  10493. },
  10494. // private
  10495. onHide : function(){
  10496. if(this.hideParent){
  10497. this.container.addClass('x-hide-' + this.hideMode);
  10498. }else{
  10499. this.getActionEl().addClass('x-hide-' + this.hideMode);
  10500. }
  10501. },
  10502. setVisible: function(visible){
  10503. if(visible) {
  10504. this.show();
  10505. }else{
  10506. this.hide();
  10507. }
  10508. return this;
  10509. },
  10510. isVisible : function(){
  10511. return this.rendered && this.getActionEl().isVisible();
  10512. },
  10513. cloneConfig : function(overrides){
  10514. overrides = overrides || {};
  10515. var id = overrides.id || Ext.id();
  10516. var cfg = Ext.applyIf(overrides, this.initialConfig);
  10517. cfg.id = id; // prevent dup id
  10518. return new this.constructor(cfg);
  10519. },
  10520. getXType : function(){
  10521. return this.constructor.xtype;
  10522. },
  10523. isXType : function(xtype, shallow){
  10524. //assume a string by default
  10525. if (typeof xtype == 'function'){
  10526. xtype = xtype.xtype; //handle being passed the class, eg. Ext.Component
  10527. }else if (typeof xtype == 'object'){
  10528. xtype = xtype.constructor.xtype; //handle being passed an instance
  10529. }
  10530. return !shallow ? ('/' + this.getXTypes() + '/').indexOf('/' + xtype + '/') != -1 : this.constructor.xtype == xtype;
  10531. },
  10532. getXTypes : function(){
  10533. var tc = this.constructor;
  10534. if(!tc.xtypes){
  10535. var c = [], sc = this;
  10536. while(sc && sc.constructor.xtype){
  10537. c.unshift(sc.constructor.xtype);
  10538. sc = sc.constructor.superclass;
  10539. }
  10540. tc.xtypeChain = c;
  10541. tc.xtypes = c.join('/');
  10542. }
  10543. return tc.xtypes;
  10544. },
  10545. findParentBy: function(fn) {
  10546. for (var p = this.ownerCt; (p != null) && !fn(p, this); p = p.ownerCt);
  10547. return p || null;
  10548. },
  10549. findParentByType: function(xtype) {
  10550. return typeof xtype == 'function' ?
  10551. this.findParentBy(function(p){
  10552. return p.constructor === xtype;
  10553. }) :
  10554. this.findParentBy(function(p){
  10555. return p.constructor.xtype === xtype;
  10556. });
  10557. },
  10558. // internal function for auto removal of assigned event handlers on destruction
  10559. mon : function(item, ename, fn, scope, opt){
  10560. if(!this.mons){
  10561. this.mons = [];
  10562. this.on('beforedestroy', function(){
  10563. for(var i= 0, len = this.mons.length; i < len; i++){
  10564. var m = this.mons[i];
  10565. m.item.un(m.ename, m.fn, m.scope);
  10566. }
  10567. }, this);
  10568. }
  10569. this.mons.push({
  10570. item: item, ename: ename, fn: fn, scope: scope
  10571. });
  10572. item.on(ename, fn, scope, opt);
  10573. }
  10574. });
  10575. Ext.reg('component', Ext.Component);
  10576. Ext.Action = function(config){
  10577. this.initialConfig = config;
  10578. this.items = [];
  10579. }
  10580. Ext.Action.prototype = {
  10581. // private
  10582. isAction : true,
  10583. setText : function(text){
  10584. this.initialConfig.text = text;
  10585. this.callEach('setText', [text]);
  10586. },
  10587. getText : function(){
  10588. return this.initialConfig.text;
  10589. },
  10590. setIconClass : function(cls){
  10591. this.initialConfig.iconCls = cls;
  10592. this.callEach('setIconClass', [cls]);
  10593. },
  10594. getIconClass : function(){
  10595. return this.initialConfig.iconCls;
  10596. },
  10597. setDisabled : function(v){
  10598. this.initialConfig.disabled = v;
  10599. this.callEach('setDisabled', [v]);
  10600. },
  10601. enable : function(){
  10602. this.setDisabled(false);
  10603. },
  10604. disable : function(){
  10605. this.setDisabled(true);
  10606. },
  10607. isDisabled : function(){
  10608. return this.initialConfig.disabled;
  10609. },
  10610. setHidden : function(v){
  10611. this.initialConfig.hidden = v;
  10612. this.callEach('setVisible', [!v]);
  10613. },
  10614. show : function(){
  10615. this.setHidden(false);
  10616. },
  10617. hide : function(){
  10618. this.setHidden(true);
  10619. },
  10620. isHidden : function(){
  10621. return this.initialConfig.hidden;
  10622. },
  10623. setHandler : function(fn, scope){
  10624. this.initialConfig.handler = fn;
  10625. this.initialConfig.scope = scope;
  10626. this.callEach('setHandler', [fn, scope]);
  10627. },
  10628. each : function(fn, scope){
  10629. Ext.each(this.items, fn, scope);
  10630. },
  10631. // private
  10632. callEach : function(fnName, args){
  10633. var cs = this.items;
  10634. for(var i = 0, len = cs.length; i < len; i++){
  10635. cs[i][fnName].apply(cs[i], args);
  10636. }
  10637. },
  10638. // private
  10639. addComponent : function(comp){
  10640. this.items.push(comp);
  10641. comp.on('destroy', this.removeComponent, this);
  10642. },
  10643. // private
  10644. removeComponent : function(comp){
  10645. this.items.remove(comp);
  10646. },
  10647. execute : function(){
  10648. this.initialConfig.handler.apply(this.initialConfig.scope || window, arguments);
  10649. }
  10650. };
  10651. (function(){
  10652. Ext.Layer = function(config, existingEl){
  10653. config = config || {};
  10654. var dh = Ext.DomHelper;
  10655. var cp = config.parentEl, pel = cp ? Ext.getDom(cp) : document.body;
  10656. if(existingEl){
  10657. this.dom = Ext.getDom(existingEl);
  10658. }
  10659. if(!this.dom){
  10660. var o = config.dh || {tag: "div", cls: "x-layer"};
  10661. this.dom = dh.append(pel, o);
  10662. }
  10663. if(config.cls){
  10664. this.addClass(config.cls);
  10665. }
  10666. this.constrain = config.constrain !== false;
  10667. this.visibilityMode = Ext.Element.VISIBILITY;
  10668. if(config.id){
  10669. this.id = this.dom.id = config.id;
  10670. }else{
  10671. this.id = Ext.id(this.dom);
  10672. }
  10673. this.zindex = config.zindex || this.getZIndex();
  10674. this.position("absolute", this.zindex);
  10675. if(config.shadow){
  10676. this.shadowOffset = config.shadowOffset || 4;
  10677. this.shadow = new Ext.Shadow({
  10678. offset : this.shadowOffset,
  10679. mode : config.shadow
  10680. });
  10681. }else{
  10682. this.shadowOffset = 0;
  10683. }
  10684. this.useShim = config.shim !== false && Ext.useShims;
  10685. this.useDisplay = config.useDisplay;
  10686. this.hide();
  10687. };
  10688. var supr = Ext.Element.prototype;
  10689. // shims are shared among layer to keep from having 100 iframes
  10690. var shims = [];
  10691. Ext.extend(Ext.Layer, Ext.Element, {
  10692. getZIndex : function(){
  10693. return this.zindex || parseInt(this.getStyle("z-index"), 10) || 11000;
  10694. },
  10695. getShim : function(){
  10696. if(!this.useShim){
  10697. return null;
  10698. }
  10699. if(this.shim){
  10700. return this.shim;
  10701. }
  10702. var shim = shims.shift();
  10703. if(!shim){
  10704. shim = this.createShim();
  10705. shim.enableDisplayMode('block');
  10706. shim.dom.style.display = 'none';
  10707. shim.dom.style.visibility = 'visible';
  10708. }
  10709. var pn = this.dom.parentNode;
  10710. if(shim.dom.parentNode != pn){
  10711. pn.insertBefore(shim.dom, this.dom);
  10712. }
  10713. shim.setStyle('z-index', this.getZIndex()-2);
  10714. this.shim = shim;
  10715. return shim;
  10716. },
  10717. hideShim : function(){
  10718. if(this.shim){
  10719. this.shim.setDisplayed(false);
  10720. shims.push(this.shim);
  10721. delete this.shim;
  10722. }
  10723. },
  10724. disableShadow : function(){
  10725. if(this.shadow){
  10726. this.shadowDisabled = true;
  10727. this.shadow.hide();
  10728. this.lastShadowOffset = this.shadowOffset;
  10729. this.shadowOffset = 0;
  10730. }
  10731. },
  10732. enableShadow : function(show){
  10733. if(this.shadow){
  10734. this.shadowDisabled = false;
  10735. this.shadowOffset = this.lastShadowOffset;
  10736. delete this.lastShadowOffset;
  10737. if(show){
  10738. this.sync(true);
  10739. }
  10740. }
  10741. },
  10742. // private
  10743. // this code can execute repeatedly in milliseconds (i.e. during a drag) so
  10744. // code size was sacrificed for effeciency (e.g. no getBox/setBox, no XY calls)
  10745. sync : function(doShow){
  10746. var sw = this.shadow;
  10747. if(!this.updating && this.isVisible() && (sw || this.useShim)){
  10748. var sh = this.getShim();
  10749. var w = this.getWidth(),
  10750. h = this.getHeight();
  10751. var l = this.getLeft(true),
  10752. t = this.getTop(true);
  10753. if(sw && !this.shadowDisabled){
  10754. if(doShow && !sw.isVisible()){
  10755. sw.show(this);
  10756. }else{
  10757. sw.realign(l, t, w, h);
  10758. }
  10759. if(sh){
  10760. if(doShow){
  10761. sh.show();
  10762. }
  10763. // fit the shim behind the shadow, so it is shimmed too
  10764. var a = sw.adjusts, s = sh.dom.style;
  10765. s.left = (Math.min(l, l+a.l))+"px";
  10766. s.top = (Math.min(t, t+a.t))+"px";
  10767. s.width = (w+a.w)+"px";
  10768. s.height = (h+a.h)+"px";
  10769. }
  10770. }else if(sh){
  10771. if(doShow){
  10772. sh.show();
  10773. }
  10774. sh.setSize(w, h);
  10775. sh.setLeftTop(l, t);
  10776. }
  10777. }
  10778. },
  10779. // private
  10780. destroy : function(){
  10781. this.hideShim();
  10782. if(this.shadow){
  10783. this.shadow.hide();
  10784. }
  10785. this.removeAllListeners();
  10786. Ext.removeNode(this.dom);
  10787. Ext.Element.uncache(this.id);
  10788. },
  10789. remove : function(){
  10790. this.destroy();
  10791. },
  10792. // private
  10793. beginUpdate : function(){
  10794. this.updating = true;
  10795. },
  10796. // private
  10797. endUpdate : function(){
  10798. this.updating = false;
  10799. this.sync(true);
  10800. },
  10801. // private
  10802. hideUnders : function(negOffset){
  10803. if(this.shadow){
  10804. this.shadow.hide();
  10805. }
  10806. this.hideShim();
  10807. },
  10808. // private
  10809. constrainXY : function(){
  10810. if(this.constrain){
  10811. var vw = Ext.lib.Dom.getViewWidth(),
  10812. vh = Ext.lib.Dom.getViewHeight();
  10813. var s = Ext.getDoc().getScroll();
  10814. var xy = this.getXY();
  10815. var x = xy[0], y = xy[1];
  10816. var w = this.dom.offsetWidth+this.shadowOffset, h = this.dom.offsetHeight+this.shadowOffset;
  10817. // only move it if it needs it
  10818. var moved = false;
  10819. // first validate right/bottom
  10820. if((x + w) > vw+s.left){
  10821. x = vw - w - this.shadowOffset;
  10822. moved = true;
  10823. }
  10824. if((y + h) > vh+s.top){
  10825. y = vh - h - this.shadowOffset;
  10826. moved = true;
  10827. }
  10828. // then make sure top/left isn't negative
  10829. if(x < s.left){
  10830. x = s.left;
  10831. moved = true;
  10832. }
  10833. if(y < s.top){
  10834. y = s.top;
  10835. moved = true;
  10836. }
  10837. if(moved){
  10838. if(this.avoidY){
  10839. var ay = this.avoidY;
  10840. if(y <= ay && (y+h) >= ay){
  10841. y = ay-h-5;
  10842. }
  10843. }
  10844. xy = [x, y];
  10845. this.storeXY(xy);
  10846. supr.setXY.call(this, xy);
  10847. this.sync();
  10848. }
  10849. }
  10850. },
  10851. isVisible : function(){
  10852. return this.visible;
  10853. },
  10854. // private
  10855. showAction : function(){
  10856. this.visible = true; // track visibility to prevent getStyle calls
  10857. if(this.useDisplay === true){
  10858. this.setDisplayed("");
  10859. }else if(this.lastXY){
  10860. supr.setXY.call(this, this.lastXY);
  10861. }else if(this.lastLT){
  10862. supr.setLeftTop.call(this, this.lastLT[0], this.lastLT[1]);
  10863. }
  10864. },
  10865. // private
  10866. hideAction : function(){
  10867. this.visible = false;
  10868. if(this.useDisplay === true){
  10869. this.setDisplayed(false);
  10870. }else{
  10871. this.setLeftTop(-10000,-10000);
  10872. }
  10873. },
  10874. // overridden Element method
  10875. setVisible : function(v, a, d, c, e){
  10876. if(v){
  10877. this.showAction();
  10878. }
  10879. if(a && v){
  10880. var cb = function(){
  10881. this.sync(true);
  10882. if(c){
  10883. c();
  10884. }
  10885. }.createDelegate(this);
  10886. supr.setVisible.call(this, true, true, d, cb, e);
  10887. }else{
  10888. if(!v){
  10889. this.hideUnders(true);
  10890. }
  10891. var cb = c;
  10892. if(a){
  10893. cb = function(){
  10894. this.hideAction();
  10895. if(c){
  10896. c();
  10897. }
  10898. }.createDelegate(this);
  10899. }
  10900. supr.setVisible.call(this, v, a, d, cb, e);
  10901. if(v){
  10902. this.sync(true);
  10903. }else if(!a){
  10904. this.hideAction();
  10905. }
  10906. }
  10907. },
  10908. storeXY : function(xy){
  10909. delete this.lastLT;
  10910. this.lastXY = xy;
  10911. },
  10912. storeLeftTop : function(left, top){
  10913. delete this.lastXY;
  10914. this.lastLT = [left, top];
  10915. },
  10916. // private
  10917. beforeFx : function(){
  10918. this.beforeAction();
  10919. return Ext.Layer.superclass.beforeFx.apply(this, arguments);
  10920. },
  10921. // private
  10922. afterFx : function(){
  10923. Ext.Layer.superclass.afterFx.apply(this, arguments);
  10924. this.sync(this.isVisible());
  10925. },
  10926. // private
  10927. beforeAction : function(){
  10928. if(!this.updating && this.shadow){
  10929. this.shadow.hide();
  10930. }
  10931. },
  10932. // overridden Element method
  10933. setLeft : function(left){
  10934. this.storeLeftTop(left, this.getTop(true));
  10935. supr.setLeft.apply(this, arguments);
  10936. this.sync();
  10937. },
  10938. setTop : function(top){
  10939. this.storeLeftTop(this.getLeft(true), top);
  10940. supr.setTop.apply(this, arguments);
  10941. this.sync();
  10942. },
  10943. setLeftTop : function(left, top){
  10944. this.storeLeftTop(left, top);
  10945. supr.setLeftTop.apply(this, arguments);
  10946. this.sync();
  10947. },
  10948. setXY : function(xy, a, d, c, e){
  10949. this.fixDisplay();
  10950. this.beforeAction();
  10951. this.storeXY(xy);
  10952. var cb = this.createCB(c);
  10953. supr.setXY.call(this, xy, a, d, cb, e);
  10954. if(!a){
  10955. cb();
  10956. }
  10957. },
  10958. // private
  10959. createCB : function(c){
  10960. var el = this;
  10961. return function(){
  10962. el.constrainXY();
  10963. el.sync(true);
  10964. if(c){
  10965. c();
  10966. }
  10967. };
  10968. },
  10969. // overridden Element method
  10970. setX : function(x, a, d, c, e){
  10971. this.setXY([x, this.getY()], a, d, c, e);
  10972. },
  10973. // overridden Element method
  10974. setY : function(y, a, d, c, e){
  10975. this.setXY([this.getX(), y], a, d, c, e);
  10976. },
  10977. // overridden Element method
  10978. setSize : function(w, h, a, d, c, e){
  10979. this.beforeAction();
  10980. var cb = this.createCB(c);
  10981. supr.setSize.call(this, w, h, a, d, cb, e);
  10982. if(!a){
  10983. cb();
  10984. }
  10985. },
  10986. // overridden Element method
  10987. setWidth : function(w, a, d, c, e){
  10988. this.beforeAction();
  10989. var cb = this.createCB(c);
  10990. supr.setWidth.call(this, w, a, d, cb, e);
  10991. if(!a){
  10992. cb();
  10993. }
  10994. },
  10995. // overridden Element method
  10996. setHeight : function(h, a, d, c, e){
  10997. this.beforeAction();
  10998. var cb = this.createCB(c);
  10999. supr.setHeight.call(this, h, a, d, cb, e);
  11000. if(!a){
  11001. cb();
  11002. }
  11003. },
  11004. // overridden Element method
  11005. setBounds : function(x, y, w, h, a, d, c, e){
  11006. this.beforeAction();
  11007. var cb = this.createCB(c);
  11008. if(!a){
  11009. this.storeXY([x, y]);
  11010. supr.setXY.call(this, [x, y]);
  11011. supr.setSize.call(this, w, h, a, d, cb, e);
  11012. cb();
  11013. }else{
  11014. supr.setBounds.call(this, x, y, w, h, a, d, cb, e);
  11015. }
  11016. return this;
  11017. },
  11018. setZIndex : function(zindex){
  11019. this.zindex = zindex;
  11020. this.setStyle("z-index", zindex + 2);
  11021. if(this.shadow){
  11022. this.shadow.setZIndex(zindex + 1);
  11023. }
  11024. if(this.shim){
  11025. this.shim.setStyle("z-index", zindex);
  11026. }
  11027. }
  11028. });
  11029. })();
  11030. Ext.Shadow = function(config){
  11031. Ext.apply(this, config);
  11032. if(typeof this.mode != "string"){
  11033. this.mode = this.defaultMode;
  11034. }
  11035. var o = this.offset, a = {h: 0};
  11036. var rad = Math.floor(this.offset/2);
  11037. switch(this.mode.toLowerCase()){ // all this hideous nonsense calculates the various offsets for shadows
  11038. case "drop":
  11039. a.w = 0;
  11040. a.l = a.t = o;
  11041. a.t -= 1;
  11042. if(Ext.isIE){
  11043. a.l -= this.offset + rad;
  11044. a.t -= this.offset + rad;
  11045. a.w -= rad;
  11046. a.h -= rad;
  11047. a.t += 1;
  11048. }
  11049. break;
  11050. case "sides":
  11051. a.w = (o*2);
  11052. a.l = -o;
  11053. a.t = o-1;
  11054. if(Ext.isIE){
  11055. a.l -= (this.offset - rad);
  11056. a.t -= this.offset + rad;
  11057. a.l += 1;
  11058. a.w -= (this.offset - rad)*2;
  11059. a.w -= rad + 1;
  11060. a.h -= 1;
  11061. }
  11062. break;
  11063. case "frame":
  11064. a.w = a.h = (o*2);
  11065. a.l = a.t = -o;
  11066. a.t += 1;
  11067. a.h -= 2;
  11068. if(Ext.isIE){
  11069. a.l -= (this.offset - rad);
  11070. a.t -= (this.offset - rad);
  11071. a.l += 1;
  11072. a.w -= (this.offset + rad + 1);
  11073. a.h -= (this.offset + rad);
  11074. a.h += 1;
  11075. }
  11076. break;
  11077. };
  11078. this.adjusts = a;
  11079. };
  11080. Ext.Shadow.prototype = {
  11081. offset: 4,
  11082. // private
  11083. defaultMode: "drop",
  11084. show : function(target){
  11085. target = Ext.get(target);
  11086. if(!this.el){
  11087. this.el = Ext.Shadow.Pool.pull();
  11088. if(this.el.dom.nextSibling != target.dom){
  11089. this.el.insertBefore(target);
  11090. }
  11091. }
  11092. this.el.setStyle("z-index", this.zIndex || parseInt(target.getStyle("z-index"), 10)-1);
  11093. if(Ext.isIE){
  11094. this.el.dom.style.filter="progid:DXImageTransform.Microsoft.alpha(opacity=50) progid:DXImageTransform.Microsoft.Blur(pixelradius="+(this.offset)+")";
  11095. }
  11096. this.realign(
  11097. target.getLeft(true),
  11098. target.getTop(true),
  11099. target.getWidth(),
  11100. target.getHeight()
  11101. );
  11102. this.el.dom.style.display = "block";
  11103. },
  11104. isVisible : function(){
  11105. return this.el ? true : false;
  11106. },
  11107. realign : function(l, t, w, h){
  11108. if(!this.el){
  11109. return;
  11110. }
  11111. var a = this.adjusts, d = this.el.dom, s = d.style;
  11112. var iea = 0;
  11113. s.left = (l+a.l)+"px";
  11114. s.top = (t+a.t)+"px";
  11115. var sw = (w+a.w), sh = (h+a.h), sws = sw +"px", shs = sh + "px";
  11116. if(s.width != sws || s.height != shs){
  11117. s.width = sws;
  11118. s.height = shs;
  11119. if(!Ext.isIE){
  11120. var cn = d.childNodes;
  11121. var sww = Math.max(0, (sw-12))+"px";
  11122. cn[0].childNodes[1].style.width = sww;
  11123. cn[1].childNodes[1].style.width = sww;
  11124. cn[2].childNodes[1].style.width = sww;
  11125. cn[1].style.height = Math.max(0, (sh-12))+"px";
  11126. }
  11127. }
  11128. },
  11129. hide : function(){
  11130. if(this.el){
  11131. this.el.dom.style.display = "none";
  11132. Ext.Shadow.Pool.push(this.el);
  11133. delete this.el;
  11134. }
  11135. },
  11136. setZIndex : function(z){
  11137. this.zIndex = z;
  11138. if(this.el){
  11139. this.el.setStyle("z-index", z);
  11140. }
  11141. }
  11142. };
  11143. // Private utility class that manages the internal Shadow cache
  11144. Ext.Shadow.Pool = function(){
  11145. var p = [];
  11146. var markup = Ext.isIE ?
  11147. '<div class="x-ie-shadow"></div>' :
  11148. '<div class="x-shadow"><div class="xst"><div class="xstl"></div><div class="xstc"></div><div class="xstr"></div></div><div class="xsc"><div class="xsml"></div><div class="xsmc"></div><div class="xsmr"></div></div><div class="xsb"><div class="xsbl"></div><div class="xsbc"></div><div class="xsbr"></div></div></div>';
  11149. return {
  11150. pull : function(){
  11151. var sh = p.shift();
  11152. if(!sh){
  11153. sh = Ext.get(Ext.DomHelper.insertHtml("beforeBegin", document.body.firstChild, markup));
  11154. sh.autoBoxAdjust = false;
  11155. }
  11156. return sh;
  11157. },
  11158. push : function(sh){
  11159. p.push(sh);
  11160. }
  11161. };
  11162. }();
  11163. Ext.BoxComponent = Ext.extend(Ext.Component, {
  11164. // private
  11165. initComponent : function(){
  11166. Ext.BoxComponent.superclass.initComponent.call(this);
  11167. this.addEvents(
  11168. 'resize',
  11169. 'move'
  11170. );
  11171. },
  11172. // private, set in afterRender to signify that the component has been rendered
  11173. boxReady : false,
  11174. // private, used to defer height settings to subclasses
  11175. deferHeight: false,
  11176. setSize : function(w, h){
  11177. // support for standard size objects
  11178. if(typeof w == 'object'){
  11179. h = w.height;
  11180. w = w.width;
  11181. }
  11182. // not rendered
  11183. if(!this.boxReady){
  11184. this.width = w;
  11185. this.height = h;
  11186. return this;
  11187. }
  11188. // prevent recalcs when not needed
  11189. if(this.lastSize && this.lastSize.width == w && this.lastSize.height == h){
  11190. return this;
  11191. }
  11192. this.lastSize = {width: w, height: h};
  11193. var adj = this.adjustSize(w, h);
  11194. var aw = adj.width, ah = adj.height;
  11195. if(aw !== undefined || ah !== undefined){ // this code is nasty but performs better with floaters
  11196. var rz = this.getResizeEl();
  11197. if(!this.deferHeight && aw !== undefined && ah !== undefined){
  11198. rz.setSize(aw, ah);
  11199. }else if(!this.deferHeight && ah !== undefined){
  11200. rz.setHeight(ah);
  11201. }else if(aw !== undefined){
  11202. rz.setWidth(aw);
  11203. }
  11204. this.onResize(aw, ah, w, h);
  11205. this.fireEvent('resize', this, aw, ah, w, h);
  11206. }
  11207. return this;
  11208. },
  11209. setWidth : function(width){
  11210. return this.setSize(width);
  11211. },
  11212. setHeight : function(height){
  11213. return this.setSize(undefined, height);
  11214. },
  11215. getSize : function(){
  11216. return this.el.getSize();
  11217. },
  11218. getPosition : function(local){
  11219. if(local === true){
  11220. return [this.el.getLeft(true), this.el.getTop(true)];
  11221. }
  11222. return this.xy || this.el.getXY();
  11223. },
  11224. getBox : function(local){
  11225. var s = this.el.getSize();
  11226. if(local === true){
  11227. s.x = this.el.getLeft(true);
  11228. s.y = this.el.getTop(true);
  11229. }else{
  11230. var xy = this.xy || this.el.getXY();
  11231. s.x = xy[0];
  11232. s.y = xy[1];
  11233. }
  11234. return s;
  11235. },
  11236. updateBox : function(box){
  11237. this.setSize(box.width, box.height);
  11238. this.setPagePosition(box.x, box.y);
  11239. return this;
  11240. },
  11241. // protected
  11242. getResizeEl : function(){
  11243. return this.resizeEl || this.el;
  11244. },
  11245. // protected
  11246. getPositionEl : function(){
  11247. return this.positionEl || this.el;
  11248. },
  11249. setPosition : function(x, y){
  11250. if(x && typeof x[1] == 'number'){
  11251. y = x[1];
  11252. x = x[0];
  11253. }
  11254. this.x = x;
  11255. this.y = y;
  11256. if(!this.boxReady){
  11257. return this;
  11258. }
  11259. var adj = this.adjustPosition(x, y);
  11260. var ax = adj.x, ay = adj.y;
  11261. var el = this.getPositionEl();
  11262. if(ax !== undefined || ay !== undefined){
  11263. if(ax !== undefined && ay !== undefined){
  11264. el.setLeftTop(ax, ay);
  11265. }else if(ax !== undefined){
  11266. el.setLeft(ax);
  11267. }else if(ay !== undefined){
  11268. el.setTop(ay);
  11269. }
  11270. this.onPosition(ax, ay);
  11271. this.fireEvent('move', this, ax, ay);
  11272. }
  11273. return this;
  11274. },
  11275. setPagePosition : function(x, y){
  11276. if(x && typeof x[1] == 'number'){
  11277. y = x[1];
  11278. x = x[0];
  11279. }
  11280. this.pageX = x;
  11281. this.pageY = y;
  11282. if(!this.boxReady){
  11283. return;
  11284. }
  11285. if(x === undefined || y === undefined){ // cannot translate undefined points
  11286. return;
  11287. }
  11288. var p = this.el.translatePoints(x, y);
  11289. this.setPosition(p.left, p.top);
  11290. return this;
  11291. },
  11292. // private
  11293. onRender : function(ct, position){
  11294. Ext.BoxComponent.superclass.onRender.call(this, ct, position);
  11295. if(this.resizeEl){
  11296. this.resizeEl = Ext.get(this.resizeEl);
  11297. }
  11298. if(this.positionEl){
  11299. this.positionEl = Ext.get(this.positionEl);
  11300. }
  11301. },
  11302. // private
  11303. afterRender : function(){
  11304. Ext.BoxComponent.superclass.afterRender.call(this);
  11305. this.boxReady = true;
  11306. this.setSize(this.width, this.height);
  11307. if(this.x || this.y){
  11308. this.setPosition(this.x, this.y);
  11309. }else if(this.pageX || this.pageY){
  11310. this.setPagePosition(this.pageX, this.pageY);
  11311. }
  11312. },
  11313. syncSize : function(){
  11314. delete this.lastSize;
  11315. this.setSize(this.autoWidth ? undefined : this.el.getWidth(), this.autoHeight ? undefined : this.el.getHeight());
  11316. return this;
  11317. },
  11318. onResize : function(adjWidth, adjHeight, rawWidth, rawHeight){
  11319. },
  11320. onPosition : function(x, y){
  11321. },
  11322. // private
  11323. adjustSize : function(w, h){
  11324. if(this.autoWidth){
  11325. w = 'auto';
  11326. }
  11327. if(this.autoHeight){
  11328. h = 'auto';
  11329. }
  11330. return {width : w, height: h};
  11331. },
  11332. // private
  11333. adjustPosition : function(x, y){
  11334. return {x : x, y: y};
  11335. }
  11336. });
  11337. Ext.reg('box', Ext.BoxComponent);
  11338. Ext.SplitBar = function(dragElement, resizingElement, orientation, placement, existingProxy){
  11339. this.el = Ext.get(dragElement, true);
  11340. this.el.dom.unselectable = "on";
  11341. this.resizingEl = Ext.get(resizingElement, true);
  11342. this.orientation = orientation || Ext.SplitBar.HORIZONTAL;
  11343. this.minSize = 0;
  11344. this.maxSize = 2000;
  11345. this.animate = false;
  11346. this.useShim = false;
  11347. this.shim = null;
  11348. if(!existingProxy){
  11349. this.proxy = Ext.SplitBar.createProxy(this.orientation);
  11350. }else{
  11351. this.proxy = Ext.get(existingProxy).dom;
  11352. }
  11353. this.dd = new Ext.dd.DDProxy(this.el.dom.id, "XSplitBars", {dragElId : this.proxy.id});
  11354. this.dd.b4StartDrag = this.onStartProxyDrag.createDelegate(this);
  11355. this.dd.endDrag = this.onEndProxyDrag.createDelegate(this);
  11356. this.dragSpecs = {};
  11357. this.adapter = new Ext.SplitBar.BasicLayoutAdapter();
  11358. this.adapter.init(this);
  11359. if(this.orientation == Ext.SplitBar.HORIZONTAL){
  11360. this.placement = placement || (this.el.getX() > this.resizingEl.getX() ? Ext.SplitBar.LEFT : Ext.SplitBar.RIGHT);
  11361. this.el.addClass("x-splitbar-h");
  11362. }else{
  11363. this.placement = placement || (this.el.getY() > this.resizingEl.getY() ? Ext.SplitBar.TOP : Ext.SplitBar.BOTTOM);
  11364. this.el.addClass("x-splitbar-v");
  11365. }
  11366. this.addEvents(
  11367. "resize",
  11368. "moved",
  11369. "beforeresize",
  11370. "beforeapply"
  11371. );
  11372. Ext.SplitBar.superclass.constructor.call(this);
  11373. };
  11374. Ext.extend(Ext.SplitBar, Ext.util.Observable, {
  11375. onStartProxyDrag : function(x, y){
  11376. this.fireEvent("beforeresize", this);
  11377. this.overlay = Ext.DomHelper.append(document.body, {cls: "x-drag-overlay", html: "&#160;"}, true);
  11378. this.overlay.unselectable();
  11379. this.overlay.setSize(Ext.lib.Dom.getViewWidth(true), Ext.lib.Dom.getViewHeight(true));
  11380. this.overlay.show();
  11381. Ext.get(this.proxy).setDisplayed("block");
  11382. var size = this.adapter.getElementSize(this);
  11383. this.activeMinSize = this.getMinimumSize();
  11384. this.activeMaxSize = this.getMaximumSize();
  11385. var c1 = size - this.activeMinSize;
  11386. var c2 = Math.max(this.activeMaxSize - size, 0);
  11387. if(this.orientation == Ext.SplitBar.HORIZONTAL){
  11388. this.dd.resetConstraints();
  11389. this.dd.setXConstraint(
  11390. this.placement == Ext.SplitBar.LEFT ? c1 : c2,
  11391. this.placement == Ext.SplitBar.LEFT ? c2 : c1
  11392. );
  11393. this.dd.setYConstraint(0, 0);
  11394. }else{
  11395. this.dd.resetConstraints();
  11396. this.dd.setXConstraint(0, 0);
  11397. this.dd.setYConstraint(
  11398. this.placement == Ext.SplitBar.TOP ? c1 : c2,
  11399. this.placement == Ext.SplitBar.TOP ? c2 : c1
  11400. );
  11401. }
  11402. this.dragSpecs.startSize = size;
  11403. this.dragSpecs.startPoint = [x, y];
  11404. Ext.dd.DDProxy.prototype.b4StartDrag.call(this.dd, x, y);
  11405. },
  11406. onEndProxyDrag : function(e){
  11407. Ext.get(this.proxy).setDisplayed(false);
  11408. var endPoint = Ext.lib.Event.getXY(e);
  11409. if(this.overlay){
  11410. Ext.destroy(this.overlay);
  11411. delete this.overlay;
  11412. }
  11413. var newSize;
  11414. if(this.orientation == Ext.SplitBar.HORIZONTAL){
  11415. newSize = this.dragSpecs.startSize +
  11416. (this.placement == Ext.SplitBar.LEFT ?
  11417. endPoint[0] - this.dragSpecs.startPoint[0] :
  11418. this.dragSpecs.startPoint[0] - endPoint[0]
  11419. );
  11420. }else{
  11421. newSize = this.dragSpecs.startSize +
  11422. (this.placement == Ext.SplitBar.TOP ?
  11423. endPoint[1] - this.dragSpecs.startPoint[1] :
  11424. this.dragSpecs.startPoint[1] - endPoint[1]
  11425. );
  11426. }
  11427. newSize = Math.min(Math.max(newSize, this.activeMinSize), this.activeMaxSize);
  11428. if(newSize != this.dragSpecs.startSize){
  11429. if(this.fireEvent('beforeapply', this, newSize) !== false){
  11430. this.adapter.setElementSize(this, newSize);
  11431. this.fireEvent("moved", this, newSize);
  11432. this.fireEvent("resize", this, newSize);
  11433. }
  11434. }
  11435. },
  11436. getAdapter : function(){
  11437. return this.adapter;
  11438. },
  11439. setAdapter : function(adapter){
  11440. this.adapter = adapter;
  11441. this.adapter.init(this);
  11442. },
  11443. getMinimumSize : function(){
  11444. return this.minSize;
  11445. },
  11446. setMinimumSize : function(minSize){
  11447. this.minSize = minSize;
  11448. },
  11449. getMaximumSize : function(){
  11450. return this.maxSize;
  11451. },
  11452. setMaximumSize : function(maxSize){
  11453. this.maxSize = maxSize;
  11454. },
  11455. setCurrentSize : function(size){
  11456. var oldAnimate = this.animate;
  11457. this.animate = false;
  11458. this.adapter.setElementSize(this, size);
  11459. this.animate = oldAnimate;
  11460. },
  11461. destroy : function(removeEl){
  11462. if(this.shim){
  11463. this.shim.remove();
  11464. }
  11465. this.dd.unreg();
  11466. Ext.destroy(Ext.get(this.proxy));
  11467. if(removeEl){
  11468. this.el.remove();
  11469. }
  11470. }
  11471. });
  11472. Ext.SplitBar.createProxy = function(dir){
  11473. var proxy = new Ext.Element(document.createElement("div"));
  11474. proxy.unselectable();
  11475. var cls = 'x-splitbar-proxy';
  11476. proxy.addClass(cls + ' ' + (dir == Ext.SplitBar.HORIZONTAL ? cls +'-h' : cls + '-v'));
  11477. document.body.appendChild(proxy.dom);
  11478. return proxy.dom;
  11479. };
  11480. Ext.SplitBar.BasicLayoutAdapter = function(){
  11481. };
  11482. Ext.SplitBar.BasicLayoutAdapter.prototype = {
  11483. // do nothing for now
  11484. init : function(s){
  11485. },
  11486. getElementSize : function(s){
  11487. if(s.orientation == Ext.SplitBar.HORIZONTAL){
  11488. return s.resizingEl.getWidth();
  11489. }else{
  11490. return s.resizingEl.getHeight();
  11491. }
  11492. },
  11493. setElementSize : function(s, newSize, onComplete){
  11494. if(s.orientation == Ext.SplitBar.HORIZONTAL){
  11495. if(!s.animate){
  11496. s.resizingEl.setWidth(newSize);
  11497. if(onComplete){
  11498. onComplete(s, newSize);
  11499. }
  11500. }else{
  11501. s.resizingEl.setWidth(newSize, true, .1, onComplete, 'easeOut');
  11502. }
  11503. }else{
  11504. if(!s.animate){
  11505. s.resizingEl.setHeight(newSize);
  11506. if(onComplete){
  11507. onComplete(s, newSize);
  11508. }
  11509. }else{
  11510. s.resizingEl.setHeight(newSize, true, .1, onComplete, 'easeOut');
  11511. }
  11512. }
  11513. }
  11514. };
  11515. Ext.SplitBar.AbsoluteLayoutAdapter = function(container){
  11516. this.basic = new Ext.SplitBar.BasicLayoutAdapter();
  11517. this.container = Ext.get(container);
  11518. };
  11519. Ext.SplitBar.AbsoluteLayoutAdapter.prototype = {
  11520. init : function(s){
  11521. this.basic.init(s);
  11522. },
  11523. getElementSize : function(s){
  11524. return this.basic.getElementSize(s);
  11525. },
  11526. setElementSize : function(s, newSize, onComplete){
  11527. this.basic.setElementSize(s, newSize, this.moveSplitter.createDelegate(this, [s]));
  11528. },
  11529. moveSplitter : function(s){
  11530. var yes = Ext.SplitBar;
  11531. switch(s.placement){
  11532. case yes.LEFT:
  11533. s.el.setX(s.resizingEl.getRight());
  11534. break;
  11535. case yes.RIGHT:
  11536. s.el.setStyle("right", (this.container.getWidth() - s.resizingEl.getLeft()) + "px");
  11537. break;
  11538. case yes.TOP:
  11539. s.el.setY(s.resizingEl.getBottom());
  11540. break;
  11541. case yes.BOTTOM:
  11542. s.el.setY(s.resizingEl.getTop() - s.el.getHeight());
  11543. break;
  11544. }
  11545. }
  11546. };
  11547. Ext.SplitBar.VERTICAL = 1;
  11548. Ext.SplitBar.HORIZONTAL = 2;
  11549. Ext.SplitBar.LEFT = 1;
  11550. Ext.SplitBar.RIGHT = 2;
  11551. Ext.SplitBar.TOP = 3;
  11552. Ext.SplitBar.BOTTOM = 4;
  11553. Ext.Container = Ext.extend(Ext.BoxComponent, {
  11554. autoDestroy: true,
  11555. defaultType: 'panel',
  11556. // private
  11557. initComponent : function(){
  11558. Ext.Container.superclass.initComponent.call(this);
  11559. this.addEvents(
  11560. 'afterlayout',
  11561. 'beforeadd',
  11562. 'beforeremove',
  11563. 'add',
  11564. 'remove'
  11565. );
  11566. var items = this.items;
  11567. if(items){
  11568. delete this.items;
  11569. if(Ext.isArray(items) && items.length > 0){
  11570. this.add.apply(this, items);
  11571. }else{
  11572. this.add(items);
  11573. }
  11574. }
  11575. },
  11576. // private
  11577. initItems : function(){
  11578. if(!this.items){
  11579. this.items = new Ext.util.MixedCollection(false, this.getComponentId);
  11580. this.getLayout(); // initialize the layout
  11581. }
  11582. },
  11583. // private
  11584. setLayout : function(layout){
  11585. if(this.layout && this.layout != layout){
  11586. this.layout.setContainer(null);
  11587. }
  11588. this.initItems();
  11589. this.layout = layout;
  11590. layout.setContainer(this);
  11591. },
  11592. // private
  11593. render : function(){
  11594. Ext.Container.superclass.render.apply(this, arguments);
  11595. if(this.layout){
  11596. if(typeof this.layout == 'string'){
  11597. this.layout = new Ext.Container.LAYOUTS[this.layout.toLowerCase()](this.layoutConfig);
  11598. }
  11599. this.setLayout(this.layout);
  11600. if(this.activeItem !== undefined){
  11601. var item = this.activeItem;
  11602. delete this.activeItem;
  11603. this.layout.setActiveItem(item);
  11604. return;
  11605. }
  11606. }
  11607. if(!this.ownerCt){
  11608. this.doLayout();
  11609. }
  11610. if(this.monitorResize === true){
  11611. Ext.EventManager.onWindowResize(this.doLayout, this, [false]);
  11612. }
  11613. },
  11614. getLayoutTarget : function(){
  11615. return this.el;
  11616. },
  11617. // private - used as the key lookup function for the items collection
  11618. getComponentId : function(comp){
  11619. return comp.itemId || comp.id;
  11620. },
  11621. add : function(comp){
  11622. if(!this.items){
  11623. this.initItems();
  11624. }
  11625. var a = arguments, len = a.length;
  11626. if(len > 1){
  11627. for(var i = 0; i < len; i++) {
  11628. this.add(a[i]);
  11629. }
  11630. return;
  11631. }
  11632. var c = this.lookupComponent(this.applyDefaults(comp));
  11633. var pos = this.items.length;
  11634. if(this.fireEvent('beforeadd', this, c, pos) !== false && this.onBeforeAdd(c) !== false){
  11635. this.items.add(c);
  11636. c.ownerCt = this;
  11637. this.fireEvent('add', this, c, pos);
  11638. }
  11639. return c;
  11640. },
  11641. insert : function(index, comp){
  11642. if(!this.items){
  11643. this.initItems();
  11644. }
  11645. var a = arguments, len = a.length;
  11646. if(len > 2){
  11647. for(var i = len-1; i >= 1; --i) {
  11648. this.insert(index, a[i]);
  11649. }
  11650. return;
  11651. }
  11652. var c = this.lookupComponent(this.applyDefaults(comp));
  11653. if(c.ownerCt == this && this.items.indexOf(c) < index){
  11654. --index;
  11655. }
  11656. if(this.fireEvent('beforeadd', this, c, index) !== false && this.onBeforeAdd(c) !== false){
  11657. this.items.insert(index, c);
  11658. c.ownerCt = this;
  11659. this.fireEvent('add', this, c, index);
  11660. }
  11661. return c;
  11662. },
  11663. // private
  11664. applyDefaults : function(c){
  11665. if(this.defaults){
  11666. if(typeof c == 'string'){
  11667. c = Ext.ComponentMgr.get(c);
  11668. Ext.apply(c, this.defaults);
  11669. }else if(!c.events){
  11670. Ext.applyIf(c, this.defaults);
  11671. }else{
  11672. Ext.apply(c, this.defaults);
  11673. }
  11674. }
  11675. return c;
  11676. },
  11677. // private
  11678. onBeforeAdd : function(item){
  11679. if(item.ownerCt){
  11680. item.ownerCt.remove(item, false);
  11681. }
  11682. if(this.hideBorders === true){
  11683. item.border = (item.border === true);
  11684. }
  11685. },
  11686. remove : function(comp, autoDestroy){
  11687. var c = this.getComponent(comp);
  11688. if(c && this.fireEvent('beforeremove', this, c) !== false){
  11689. this.items.remove(c);
  11690. delete c.ownerCt;
  11691. if(autoDestroy === true || (autoDestroy !== false && this.autoDestroy)){
  11692. c.destroy();
  11693. }
  11694. if(this.layout && this.layout.activeItem == c){
  11695. delete this.layout.activeItem;
  11696. }
  11697. this.fireEvent('remove', this, c);
  11698. }
  11699. return c;
  11700. },
  11701. removeAll: function(autoDestroy){
  11702. var item, items = [];
  11703. while((item = this.items.last())){
  11704. items.unshift(this.remove(item, autoDestroy));
  11705. }
  11706. return items;
  11707. },
  11708. getComponent : function(comp){
  11709. if(typeof comp == 'object'){
  11710. return comp;
  11711. }
  11712. return this.items.get(comp);
  11713. },
  11714. // private
  11715. lookupComponent : function(comp){
  11716. if(typeof comp == 'string'){
  11717. return Ext.ComponentMgr.get(comp);
  11718. }else if(!comp.events){
  11719. return this.createComponent(comp);
  11720. }
  11721. return comp;
  11722. },
  11723. // private
  11724. createComponent : function(config){
  11725. return Ext.ComponentMgr.create(config, this.defaultType);
  11726. },
  11727. doLayout : function(shallow){
  11728. if(this.rendered && this.layout){
  11729. this.layout.layout();
  11730. }
  11731. if(shallow !== false && this.items){
  11732. var cs = this.items.items;
  11733. for(var i = 0, len = cs.length; i < len; i++) {
  11734. var c = cs[i];
  11735. if(c.doLayout){
  11736. c.doLayout();
  11737. }
  11738. }
  11739. }
  11740. },
  11741. getLayout : function(){
  11742. if(!this.layout){
  11743. var layout = new Ext.layout.ContainerLayout(this.layoutConfig);
  11744. this.setLayout(layout);
  11745. }
  11746. return this.layout;
  11747. },
  11748. // private
  11749. beforeDestroy : function(){
  11750. if(this.items){
  11751. Ext.destroy.apply(Ext, this.items.items);
  11752. }
  11753. if(this.monitorResize){
  11754. Ext.EventManager.removeResizeListener(this.doLayout, this);
  11755. }
  11756. if (this.layout && this.layout.destroy) {
  11757. this.layout.destroy();
  11758. }
  11759. Ext.Container.superclass.beforeDestroy.call(this);
  11760. },
  11761. bubble : function(fn, scope, args){
  11762. var p = this;
  11763. while(p){
  11764. if(fn.apply(scope || p, args || [p]) === false){
  11765. break;
  11766. }
  11767. p = p.ownerCt;
  11768. }
  11769. },
  11770. cascade : function(fn, scope, args){
  11771. if(fn.apply(scope || this, args || [this]) !== false){
  11772. if(this.items){
  11773. var cs = this.items.items;
  11774. for(var i = 0, len = cs.length; i < len; i++){
  11775. if(cs[i].cascade){
  11776. cs[i].cascade(fn, scope, args);
  11777. }else{
  11778. fn.apply(scope || cs[i], args || [cs[i]]);
  11779. }
  11780. }
  11781. }
  11782. }
  11783. },
  11784. findById : function(id){
  11785. var m, ct = this;
  11786. this.cascade(function(c){
  11787. if(ct != c && c.id === id){
  11788. m = c;
  11789. return false;
  11790. }
  11791. });
  11792. return m || null;
  11793. },
  11794. findByType : function(xtype, shallow){
  11795. return this.findBy(function(c){
  11796. return c.isXType(xtype, shallow);
  11797. });
  11798. },
  11799. find : function(prop, value){
  11800. return this.findBy(function(c){
  11801. return c[prop] === value;
  11802. });
  11803. },
  11804. findBy : function(fn, scope){
  11805. var m = [], ct = this;
  11806. this.cascade(function(c){
  11807. if(ct != c && fn.call(scope || c, c, ct) === true){
  11808. m.push(c);
  11809. }
  11810. });
  11811. return m;
  11812. }
  11813. });
  11814. Ext.Container.LAYOUTS = {};
  11815. Ext.reg('container', Ext.Container);
  11816. Ext.layout.ContainerLayout = function(config){
  11817. Ext.apply(this, config);
  11818. };
  11819. Ext.layout.ContainerLayout.prototype = {
  11820. // private
  11821. monitorResize:false,
  11822. // private
  11823. activeItem : null,
  11824. // private
  11825. layout : function(){
  11826. var target = this.container.getLayoutTarget();
  11827. this.onLayout(this.container, target);
  11828. this.container.fireEvent('afterlayout', this.container, this);
  11829. },
  11830. // private
  11831. onLayout : function(ct, target){
  11832. this.renderAll(ct, target);
  11833. },
  11834. // private
  11835. isValidParent : function(c, target){
  11836. var el = c.getPositionEl ? c.getPositionEl() : c.getEl();
  11837. return el.dom.parentNode == target.dom;
  11838. },
  11839. // private
  11840. renderAll : function(ct, target){
  11841. var items = ct.items.items;
  11842. for(var i = 0, len = items.length; i < len; i++) {
  11843. var c = items[i];
  11844. if(c && (!c.rendered || !this.isValidParent(c, target))){
  11845. this.renderItem(c, i, target);
  11846. }
  11847. }
  11848. },
  11849. // private
  11850. renderItem : function(c, position, target){
  11851. if(c && !c.rendered){
  11852. c.render(target, position);
  11853. if(this.extraCls){
  11854. var t = c.getPositionEl ? c.getPositionEl() : c;
  11855. t.addClass(this.extraCls);
  11856. }
  11857. if (this.renderHidden && c != this.activeItem) {
  11858. c.hide();
  11859. }
  11860. }else if(c && !this.isValidParent(c, target)){
  11861. if(this.extraCls){
  11862. var t = c.getPositionEl ? c.getPositionEl() : c;
  11863. t.addClass(this.extraCls);
  11864. }
  11865. if(typeof position == 'number'){
  11866. position = target.dom.childNodes[position];
  11867. }
  11868. target.dom.insertBefore(c.getEl().dom, position || null);
  11869. if (this.renderHidden && c != this.activeItem) {
  11870. c.hide();
  11871. }
  11872. }
  11873. },
  11874. // private
  11875. onResize: function(){
  11876. if(this.container.collapsed){
  11877. return;
  11878. }
  11879. var b = this.container.bufferResize;
  11880. if(b){
  11881. if(!this.resizeTask){
  11882. this.resizeTask = new Ext.util.DelayedTask(this.layout, this);
  11883. this.resizeBuffer = typeof b == 'number' ? b : 100;
  11884. }
  11885. this.resizeTask.delay(this.resizeBuffer);
  11886. }else{
  11887. this.layout();
  11888. }
  11889. },
  11890. // private
  11891. setContainer : function(ct){
  11892. if(this.monitorResize && ct != this.container){
  11893. if(this.container){
  11894. this.container.un('resize', this.onResize, this);
  11895. }
  11896. if(ct){
  11897. ct.on('resize', this.onResize, this);
  11898. }
  11899. }
  11900. this.container = ct;
  11901. },
  11902. // private
  11903. parseMargins : function(v){
  11904. var ms = v.split(' ');
  11905. var len = ms.length;
  11906. if(len == 1){
  11907. ms[1] = ms[0];
  11908. ms[2] = ms[0];
  11909. ms[3] = ms[0];
  11910. }
  11911. if(len == 2){
  11912. ms[2] = ms[0];
  11913. ms[3] = ms[1];
  11914. }
  11915. return {
  11916. top:parseInt(ms[0], 10) || 0,
  11917. right:parseInt(ms[1], 10) || 0,
  11918. bottom:parseInt(ms[2], 10) || 0,
  11919. left:parseInt(ms[3], 10) || 0
  11920. };
  11921. },
  11922. destroy : Ext.emptyFn
  11923. };
  11924. Ext.Container.LAYOUTS['auto'] = Ext.layout.ContainerLayout;
  11925. Ext.layout.FitLayout = Ext.extend(Ext.layout.ContainerLayout, {
  11926. // private
  11927. monitorResize:true,
  11928. // private
  11929. onLayout : function(ct, target){
  11930. Ext.layout.FitLayout.superclass.onLayout.call(this, ct, target);
  11931. if(!this.container.collapsed){
  11932. this.setItemSize(this.activeItem || ct.items.itemAt(0), target.getStyleSize());
  11933. }
  11934. },
  11935. // private
  11936. setItemSize : function(item, size){
  11937. if(item && size.height > 0){ // display none?
  11938. item.setSize(size);
  11939. }
  11940. }
  11941. });
  11942. Ext.Container.LAYOUTS['fit'] = Ext.layout.FitLayout;
  11943. Ext.layout.CardLayout = Ext.extend(Ext.layout.FitLayout, {
  11944. deferredRender : false,
  11945. // private
  11946. renderHidden : true,
  11947. setActiveItem : function(item){
  11948. item = this.container.getComponent(item);
  11949. if(this.activeItem != item){
  11950. if(this.activeItem){
  11951. this.activeItem.hide();
  11952. }
  11953. this.activeItem = item;
  11954. item.show();
  11955. this.layout();
  11956. }
  11957. },
  11958. // private
  11959. renderAll : function(ct, target){
  11960. if(this.deferredRender){
  11961. this.renderItem(this.activeItem, undefined, target);
  11962. }else{
  11963. Ext.layout.CardLayout.superclass.renderAll.call(this, ct, target);
  11964. }
  11965. }
  11966. });
  11967. Ext.Container.LAYOUTS['card'] = Ext.layout.CardLayout;
  11968. Ext.layout.AnchorLayout = Ext.extend(Ext.layout.ContainerLayout, {
  11969. // private
  11970. monitorResize:true,
  11971. // private
  11972. getAnchorViewSize : function(ct, target){
  11973. return target.dom == document.body ?
  11974. target.getViewSize() : target.getStyleSize();
  11975. },
  11976. // private
  11977. onLayout : function(ct, target){
  11978. Ext.layout.AnchorLayout.superclass.onLayout.call(this, ct, target);
  11979. var size = this.getAnchorViewSize(ct, target);
  11980. var w = size.width, h = size.height;
  11981. if(w < 20 || h < 20){
  11982. return;
  11983. }
  11984. // find the container anchoring size
  11985. var aw, ah;
  11986. if(ct.anchorSize){
  11987. if(typeof ct.anchorSize == 'number'){
  11988. aw = ct.anchorSize;
  11989. }else{
  11990. aw = ct.anchorSize.width;
  11991. ah = ct.anchorSize.height;
  11992. }
  11993. }else{
  11994. aw = ct.initialConfig.width;
  11995. ah = ct.initialConfig.height;
  11996. }
  11997. var cs = ct.items.items, len = cs.length, i, c, a, cw, ch;
  11998. for(i = 0; i < len; i++){
  11999. c = cs[i];
  12000. if(c.anchor){
  12001. a = c.anchorSpec;
  12002. if(!a){ // cache all anchor values
  12003. var vs = c.anchor.split(' ');
  12004. c.anchorSpec = a = {
  12005. right: this.parseAnchor(vs[0], c.initialConfig.width, aw),
  12006. bottom: this.parseAnchor(vs[1], c.initialConfig.height, ah)
  12007. };
  12008. }
  12009. cw = a.right ? this.adjustWidthAnchor(a.right(w), c) : undefined;
  12010. ch = a.bottom ? this.adjustHeightAnchor(a.bottom(h), c) : undefined;
  12011. if(cw || ch){
  12012. c.setSize(cw || undefined, ch || undefined);
  12013. }
  12014. }
  12015. }
  12016. },
  12017. // private
  12018. parseAnchor : function(a, start, cstart){
  12019. if(a && a != 'none'){
  12020. var last;
  12021. if(/^(r|right|b|bottom)$/i.test(a)){ // standard anchor
  12022. var diff = cstart - start;
  12023. return function(v){
  12024. if(v !== last){
  12025. last = v;
  12026. return v - diff;
  12027. }
  12028. }
  12029. }else if(a.indexOf('%') != -1){
  12030. var ratio = parseFloat(a.replace('%', ''))*.01; // percentage
  12031. return function(v){
  12032. if(v !== last){
  12033. last = v;
  12034. return Math.floor(v*ratio);
  12035. }
  12036. }
  12037. }else{
  12038. a = parseInt(a, 10);
  12039. if(!isNaN(a)){ // simple offset adjustment
  12040. return function(v){
  12041. if(v !== last){
  12042. last = v;
  12043. return v + a;
  12044. }
  12045. }
  12046. }
  12047. }
  12048. }
  12049. return false;
  12050. },
  12051. // private
  12052. adjustWidthAnchor : function(value, comp){
  12053. return value;
  12054. },
  12055. // private
  12056. adjustHeightAnchor : function(value, comp){
  12057. return value;
  12058. }
  12059. });
  12060. Ext.Container.LAYOUTS['anchor'] = Ext.layout.AnchorLayout;
  12061. Ext.layout.ColumnLayout = Ext.extend(Ext.layout.ContainerLayout, {
  12062. // private
  12063. monitorResize:true,
  12064. extraCls: 'x-column',
  12065. scrollOffset : 0,
  12066. // private
  12067. isValidParent : function(c, target){
  12068. return (c.getPositionEl ? c.getPositionEl() : c.getEl()).dom.parentNode == this.innerCt.dom;
  12069. },
  12070. // private
  12071. onLayout : function(ct, target){
  12072. var cs = ct.items.items, len = cs.length, c, i;
  12073. if(!this.innerCt){
  12074. target.addClass('x-column-layout-ct');
  12075. // the innerCt prevents wrapping and shuffling while
  12076. // the container is resizing
  12077. this.innerCt = target.createChild({cls:'x-column-inner'});
  12078. this.innerCt.createChild({cls:'x-clear'});
  12079. }
  12080. this.renderAll(ct, this.innerCt);
  12081. var size = Ext.isIE && target.dom != Ext.getBody().dom ? target.getStyleSize() : target.getViewSize();
  12082. if(size.width < 1 && size.height < 1){ // display none?
  12083. return;
  12084. }
  12085. var w = size.width - target.getPadding('lr') - this.scrollOffset,
  12086. h = size.height - target.getPadding('tb'),
  12087. pw = w;
  12088. this.innerCt.setWidth(w);
  12089. // some columns can be percentages while others are fixed
  12090. // so we need to make 2 passes
  12091. for(i = 0; i < len; i++){
  12092. c = cs[i];
  12093. if(!c.columnWidth){
  12094. pw -= (c.getSize().width + c.getEl().getMargins('lr'));
  12095. }
  12096. }
  12097. pw = pw < 0 ? 0 : pw;
  12098. for(i = 0; i < len; i++){
  12099. c = cs[i];
  12100. if(c.columnWidth){
  12101. c.setSize(Math.floor(c.columnWidth*pw) - c.getEl().getMargins('lr'));
  12102. }
  12103. }
  12104. }
  12105. });
  12106. Ext.Container.LAYOUTS['column'] = Ext.layout.ColumnLayout;
  12107. Ext.layout.BorderLayout = Ext.extend(Ext.layout.ContainerLayout, {
  12108. // private
  12109. monitorResize:true,
  12110. // private
  12111. rendered : false,
  12112. // private
  12113. onLayout : function(ct, target){
  12114. var collapsed;
  12115. if(!this.rendered){
  12116. target.position();
  12117. target.addClass('x-border-layout-ct');
  12118. var items = ct.items.items;
  12119. collapsed = [];
  12120. for(var i = 0, len = items.length; i < len; i++) {
  12121. var c = items[i];
  12122. var pos = c.region;
  12123. if(c.collapsed){
  12124. collapsed.push(c);
  12125. }
  12126. c.collapsed = false;
  12127. if(!c.rendered){
  12128. c.cls = c.cls ? c.cls +' x-border-panel' : 'x-border-panel';
  12129. c.render(target, i);
  12130. }
  12131. this[pos] = pos != 'center' && c.split ?
  12132. new Ext.layout.BorderLayout.SplitRegion(this, c.initialConfig, pos) :
  12133. new Ext.layout.BorderLayout.Region(this, c.initialConfig, pos);
  12134. this[pos].render(target, c);
  12135. }
  12136. this.rendered = true;
  12137. }
  12138. var size = target.getViewSize();
  12139. if(size.width < 20 || size.height < 20){ // display none?
  12140. if(collapsed){
  12141. this.restoreCollapsed = collapsed;
  12142. }
  12143. return;
  12144. }else if(this.restoreCollapsed){
  12145. collapsed = this.restoreCollapsed;
  12146. delete this.restoreCollapsed;
  12147. }
  12148. var w = size.width, h = size.height;
  12149. var centerW = w, centerH = h, centerY = 0, centerX = 0;
  12150. var n = this.north, s = this.south, west = this.west, e = this.east, c = this.center;
  12151. if(!c && Ext.layout.BorderLayout.WARN !== false){
  12152. throw 'No center region defined in BorderLayout ' + ct.id;
  12153. }
  12154. if(n && n.isVisible()){
  12155. var b = n.getSize();
  12156. var m = n.getMargins();
  12157. b.width = w - (m.left+m.right);
  12158. b.x = m.left;
  12159. b.y = m.top;
  12160. centerY = b.height + b.y + m.bottom;
  12161. centerH -= centerY;
  12162. n.applyLayout(b);
  12163. }
  12164. if(s && s.isVisible()){
  12165. var b = s.getSize();
  12166. var m = s.getMargins();
  12167. b.width = w - (m.left+m.right);
  12168. b.x = m.left;
  12169. var totalHeight = (b.height + m.top + m.bottom);
  12170. b.y = h - totalHeight + m.top;
  12171. centerH -= totalHeight;
  12172. s.applyLayout(b);
  12173. }
  12174. if(west && west.isVisible()){
  12175. var b = west.getSize();
  12176. var m = west.getMargins();
  12177. b.height = centerH - (m.top+m.bottom);
  12178. b.x = m.left;
  12179. b.y = centerY + m.top;
  12180. var totalWidth = (b.width + m.left + m.right);
  12181. centerX += totalWidth;
  12182. centerW -= totalWidth;
  12183. west.applyLayout(b);
  12184. }
  12185. if(e && e.isVisible()){
  12186. var b = e.getSize();
  12187. var m = e.getMargins();
  12188. b.height = centerH - (m.top+m.bottom);
  12189. var totalWidth = (b.width + m.left + m.right);
  12190. b.x = w - totalWidth + m.left;
  12191. b.y = centerY + m.top;
  12192. centerW -= totalWidth;
  12193. e.applyLayout(b);
  12194. }
  12195. if(c){
  12196. var m = c.getMargins();
  12197. var centerBox = {
  12198. x: centerX + m.left,
  12199. y: centerY + m.top,
  12200. width: centerW - (m.left+m.right),
  12201. height: centerH - (m.top+m.bottom)
  12202. };
  12203. c.applyLayout(centerBox);
  12204. }
  12205. if(collapsed){
  12206. for(var i = 0, len = collapsed.length; i < len; i++){
  12207. collapsed[i].collapse(false);
  12208. }
  12209. }
  12210. if(Ext.isIE && Ext.isStrict){ // workaround IE strict repainting issue
  12211. target.repaint();
  12212. }
  12213. },
  12214. // inherit docs
  12215. destroy: function() {
  12216. var r = ['north', 'south', 'east', 'west'];
  12217. for (var i = 0; i < r.length; i++) {
  12218. var region = this[r[i]];
  12219. if(region){
  12220. if(region.destroy){
  12221. region.destroy();
  12222. }else if (region.split){
  12223. region.split.destroy(true);
  12224. }
  12225. }
  12226. }
  12227. Ext.layout.BorderLayout.superclass.destroy.call(this);
  12228. }
  12229. });
  12230. Ext.layout.BorderLayout.Region = function(layout, config, pos){
  12231. Ext.apply(this, config);
  12232. this.layout = layout;
  12233. this.position = pos;
  12234. this.state = {};
  12235. if(typeof this.margins == 'string'){
  12236. this.margins = this.layout.parseMargins(this.margins);
  12237. }
  12238. this.margins = Ext.applyIf(this.margins || {}, this.defaultMargins);
  12239. if(this.collapsible){
  12240. if(typeof this.cmargins == 'string'){
  12241. this.cmargins = this.layout.parseMargins(this.cmargins);
  12242. }
  12243. if(this.collapseMode == 'mini' && !this.cmargins){
  12244. this.cmargins = {left:0,top:0,right:0,bottom:0};
  12245. }else{
  12246. this.cmargins = Ext.applyIf(this.cmargins || {},
  12247. pos == 'north' || pos == 'south' ? this.defaultNSCMargins : this.defaultEWCMargins);
  12248. }
  12249. }
  12250. };
  12251. Ext.layout.BorderLayout.Region.prototype = {
  12252. collapsible : false,
  12253. split:false,
  12254. floatable: true,
  12255. minWidth:50,
  12256. minHeight:50,
  12257. // private
  12258. defaultMargins : {left:0,top:0,right:0,bottom:0},
  12259. // private
  12260. defaultNSCMargins : {left:5,top:5,right:5,bottom:5},
  12261. // private
  12262. defaultEWCMargins : {left:5,top:0,right:5,bottom:0},
  12263. isCollapsed : false,
  12264. // private
  12265. render : function(ct, p){
  12266. this.panel = p;
  12267. p.el.enableDisplayMode();
  12268. this.targetEl = ct;
  12269. this.el = p.el;
  12270. var gs = p.getState, ps = this.position;
  12271. p.getState = function(){
  12272. return Ext.apply(gs.call(p) || {}, this.state);
  12273. }.createDelegate(this);
  12274. if(ps != 'center'){
  12275. p.allowQueuedExpand = false;
  12276. p.on({
  12277. beforecollapse: this.beforeCollapse,
  12278. collapse: this.onCollapse,
  12279. beforeexpand: this.beforeExpand,
  12280. expand: this.onExpand,
  12281. hide: this.onHide,
  12282. show: this.onShow,
  12283. scope: this
  12284. });
  12285. if(this.collapsible){
  12286. p.collapseEl = 'el';
  12287. p.slideAnchor = this.getSlideAnchor();
  12288. }
  12289. if(p.tools && p.tools.toggle){
  12290. p.tools.toggle.addClass('x-tool-collapse-'+ps);
  12291. p.tools.toggle.addClassOnOver('x-tool-collapse-'+ps+'-over');
  12292. }
  12293. }
  12294. },
  12295. // private
  12296. getCollapsedEl : function(){
  12297. if(!this.collapsedEl){
  12298. if(!this.toolTemplate){
  12299. var tt = new Ext.Template(
  12300. '<div class="x-tool x-tool-{id}">&#160;</div>'
  12301. );
  12302. tt.disableFormats = true;
  12303. tt.compile();
  12304. Ext.layout.BorderLayout.Region.prototype.toolTemplate = tt;
  12305. }
  12306. this.collapsedEl = this.targetEl.createChild({
  12307. cls: "x-layout-collapsed x-layout-collapsed-"+this.position,
  12308. id: this.panel.id + '-xcollapsed'
  12309. });
  12310. this.collapsedEl.enableDisplayMode('block');
  12311. if(this.collapseMode == 'mini'){
  12312. this.collapsedEl.addClass('x-layout-cmini-'+this.position);
  12313. this.miniCollapsedEl = this.collapsedEl.createChild({
  12314. cls: "x-layout-mini x-layout-mini-"+this.position, html: "&#160;"
  12315. });
  12316. this.miniCollapsedEl.addClassOnOver('x-layout-mini-over');
  12317. this.collapsedEl.addClassOnOver("x-layout-collapsed-over");
  12318. this.collapsedEl.on('click', this.onExpandClick, this, {stopEvent:true});
  12319. }else {
  12320. var t = this.toolTemplate.append(
  12321. this.collapsedEl.dom,
  12322. {id:'expand-'+this.position}, true);
  12323. t.addClassOnOver('x-tool-expand-'+this.position+'-over');
  12324. t.on('click', this.onExpandClick, this, {stopEvent:true});
  12325. if(this.floatable !== false){
  12326. this.collapsedEl.addClassOnOver("x-layout-collapsed-over");
  12327. this.collapsedEl.on("click", this.collapseClick, this);
  12328. }
  12329. }
  12330. }
  12331. return this.collapsedEl;
  12332. },
  12333. // private
  12334. onExpandClick : function(e){
  12335. if(this.isSlid){
  12336. this.afterSlideIn();
  12337. this.panel.expand(false);
  12338. }else{
  12339. this.panel.expand();
  12340. }
  12341. },
  12342. // private
  12343. onCollapseClick : function(e){
  12344. this.panel.collapse();
  12345. },
  12346. // private
  12347. beforeCollapse : function(p, animate){
  12348. this.lastAnim = animate;
  12349. if(this.splitEl){
  12350. this.splitEl.hide();
  12351. }
  12352. this.getCollapsedEl().show();
  12353. this.panel.el.setStyle('z-index', 100);
  12354. this.isCollapsed = true;
  12355. this.layout.layout();
  12356. },
  12357. // private
  12358. onCollapse : function(animate){
  12359. this.panel.el.setStyle('z-index', 1);
  12360. if(this.lastAnim === false || this.panel.animCollapse === false){
  12361. this.getCollapsedEl().dom.style.visibility = 'visible';
  12362. }else{
  12363. this.getCollapsedEl().slideIn(this.panel.slideAnchor, {duration:.2});
  12364. }
  12365. this.state.collapsed = true;
  12366. this.panel.saveState();
  12367. },
  12368. // private
  12369. beforeExpand : function(animate){
  12370. var c = this.getCollapsedEl();
  12371. this.el.show();
  12372. if(this.position == 'east' || this.position == 'west'){
  12373. this.panel.setSize(undefined, c.getHeight());
  12374. }else{
  12375. this.panel.setSize(c.getWidth(), undefined);
  12376. }
  12377. c.hide();
  12378. c.dom.style.visibility = 'hidden';
  12379. this.panel.el.setStyle('z-index', 100);
  12380. },
  12381. // private
  12382. onExpand : function(){
  12383. this.isCollapsed = false;
  12384. if(this.splitEl){
  12385. this.splitEl.show();
  12386. }
  12387. this.layout.layout();
  12388. this.panel.el.setStyle('z-index', 1);
  12389. this.state.collapsed = false;
  12390. this.panel.saveState();
  12391. },
  12392. // private
  12393. collapseClick : function(e){
  12394. if(this.isSlid){
  12395. e.stopPropagation();
  12396. this.slideIn();
  12397. }else{
  12398. e.stopPropagation();
  12399. this.slideOut();
  12400. }
  12401. },
  12402. // private
  12403. onHide : function(){
  12404. if(this.isCollapsed){
  12405. this.getCollapsedEl().hide();
  12406. }else if(this.splitEl){
  12407. this.splitEl.hide();
  12408. }
  12409. },
  12410. // private
  12411. onShow : function(){
  12412. if(this.isCollapsed){
  12413. this.getCollapsedEl().show();
  12414. }else if(this.splitEl){
  12415. this.splitEl.show();
  12416. }
  12417. },
  12418. isVisible : function(){
  12419. return !this.panel.hidden;
  12420. },
  12421. getMargins : function(){
  12422. return this.isCollapsed && this.cmargins ? this.cmargins : this.margins;
  12423. },
  12424. getSize : function(){
  12425. return this.isCollapsed ? this.getCollapsedEl().getSize() : this.panel.getSize();
  12426. },
  12427. setPanel : function(panel){
  12428. this.panel = panel;
  12429. },
  12430. getMinWidth: function(){
  12431. return this.minWidth;
  12432. },
  12433. getMinHeight: function(){
  12434. return this.minHeight;
  12435. },
  12436. // private
  12437. applyLayoutCollapsed : function(box){
  12438. var ce = this.getCollapsedEl();
  12439. ce.setLeftTop(box.x, box.y);
  12440. ce.setSize(box.width, box.height);
  12441. },
  12442. // private
  12443. applyLayout : function(box){
  12444. if(this.isCollapsed){
  12445. this.applyLayoutCollapsed(box);
  12446. }else{
  12447. this.panel.setPosition(box.x, box.y);
  12448. this.panel.setSize(box.width, box.height);
  12449. }
  12450. },
  12451. // private
  12452. beforeSlide: function(){
  12453. this.panel.beforeEffect();
  12454. },
  12455. // private
  12456. afterSlide : function(){
  12457. this.panel.afterEffect();
  12458. },
  12459. // private
  12460. initAutoHide : function(){
  12461. if(this.autoHide !== false){
  12462. if(!this.autoHideHd){
  12463. var st = new Ext.util.DelayedTask(this.slideIn, this);
  12464. this.autoHideHd = {
  12465. "mouseout": function(e){
  12466. if(!e.within(this.el, true)){
  12467. st.delay(500);
  12468. }
  12469. },
  12470. "mouseover" : function(e){
  12471. st.cancel();
  12472. },
  12473. scope : this
  12474. };
  12475. }
  12476. this.el.on(this.autoHideHd);
  12477. }
  12478. },
  12479. // private
  12480. clearAutoHide : function(){
  12481. if(this.autoHide !== false){
  12482. this.el.un("mouseout", this.autoHideHd.mouseout);
  12483. this.el.un("mouseover", this.autoHideHd.mouseover);
  12484. }
  12485. },
  12486. // private
  12487. clearMonitor : function(){
  12488. Ext.getDoc().un("click", this.slideInIf, this);
  12489. },
  12490. // these names are backwards but not changed for compat
  12491. // private
  12492. slideOut : function(){
  12493. if(this.isSlid || this.el.hasActiveFx()){
  12494. return;
  12495. }
  12496. this.isSlid = true;
  12497. var ts = this.panel.tools;
  12498. if(ts && ts.toggle){
  12499. ts.toggle.hide();
  12500. }
  12501. this.el.show();
  12502. if(this.position == 'east' || this.position == 'west'){
  12503. this.panel.setSize(undefined, this.collapsedEl.getHeight());
  12504. }else{
  12505. this.panel.setSize(this.collapsedEl.getWidth(), undefined);
  12506. }
  12507. this.restoreLT = [this.el.dom.style.left, this.el.dom.style.top];
  12508. this.el.alignTo(this.collapsedEl, this.getCollapseAnchor());
  12509. this.el.setStyle("z-index", 102);
  12510. this.panel.el.replaceClass('x-panel-collapsed', 'x-panel-floating');
  12511. if(this.animFloat !== false){
  12512. this.beforeSlide();
  12513. this.el.slideIn(this.getSlideAnchor(), {
  12514. callback: function(){
  12515. this.afterSlide();
  12516. this.initAutoHide();
  12517. Ext.getDoc().on("click", this.slideInIf, this);
  12518. },
  12519. scope: this,
  12520. block: true
  12521. });
  12522. }else{
  12523. this.initAutoHide();
  12524. Ext.getDoc().on("click", this.slideInIf, this);
  12525. }
  12526. },
  12527. // private
  12528. afterSlideIn : function(){
  12529. this.clearAutoHide();
  12530. this.isSlid = false;
  12531. this.clearMonitor();
  12532. this.el.setStyle("z-index", "");
  12533. this.panel.el.replaceClass('x-panel-floating', 'x-panel-collapsed');
  12534. this.el.dom.style.left = this.restoreLT[0];
  12535. this.el.dom.style.top = this.restoreLT[1];
  12536. var ts = this.panel.tools;
  12537. if(ts && ts.toggle){
  12538. ts.toggle.show();
  12539. }
  12540. },
  12541. // private
  12542. slideIn : function(cb){
  12543. if(!this.isSlid || this.el.hasActiveFx()){
  12544. Ext.callback(cb);
  12545. return;
  12546. }
  12547. this.isSlid = false;
  12548. if(this.animFloat !== false){
  12549. this.beforeSlide();
  12550. this.el.slideOut(this.getSlideAnchor(), {
  12551. callback: function(){
  12552. this.el.hide();
  12553. this.afterSlide();
  12554. this.afterSlideIn();
  12555. Ext.callback(cb);
  12556. },
  12557. scope: this,
  12558. block: true
  12559. });
  12560. }else{
  12561. this.el.hide();
  12562. this.afterSlideIn();
  12563. }
  12564. },
  12565. // private
  12566. slideInIf : function(e){
  12567. if(!e.within(this.el)){
  12568. this.slideIn();
  12569. }
  12570. },
  12571. // private
  12572. anchors : {
  12573. "west" : "left",
  12574. "east" : "right",
  12575. "north" : "top",
  12576. "south" : "bottom"
  12577. },
  12578. // private
  12579. sanchors : {
  12580. "west" : "l",
  12581. "east" : "r",
  12582. "north" : "t",
  12583. "south" : "b"
  12584. },
  12585. // private
  12586. canchors : {
  12587. "west" : "tl-tr",
  12588. "east" : "tr-tl",
  12589. "north" : "tl-bl",
  12590. "south" : "bl-tl"
  12591. },
  12592. // private
  12593. getAnchor : function(){
  12594. return this.anchors[this.position];
  12595. },
  12596. // private
  12597. getCollapseAnchor : function(){
  12598. return this.canchors[this.position];
  12599. },
  12600. // private
  12601. getSlideAnchor : function(){
  12602. return this.sanchors[this.position];
  12603. },
  12604. // private
  12605. getAlignAdj : function(){
  12606. var cm = this.cmargins;
  12607. switch(this.position){
  12608. case "west":
  12609. return [0, 0];
  12610. break;
  12611. case "east":
  12612. return [0, 0];
  12613. break;
  12614. case "north":
  12615. return [0, 0];
  12616. break;
  12617. case "south":
  12618. return [0, 0];
  12619. break;
  12620. }
  12621. },
  12622. // private
  12623. getExpandAdj : function(){
  12624. var c = this.collapsedEl, cm = this.cmargins;
  12625. switch(this.position){
  12626. case "west":
  12627. return [-(cm.right+c.getWidth()+cm.left), 0];
  12628. break;
  12629. case "east":
  12630. return [cm.right+c.getWidth()+cm.left, 0];
  12631. break;
  12632. case "north":
  12633. return [0, -(cm.top+cm.bottom+c.getHeight())];
  12634. break;
  12635. case "south":
  12636. return [0, cm.top+cm.bottom+c.getHeight()];
  12637. break;
  12638. }
  12639. }
  12640. };
  12641. Ext.layout.BorderLayout.SplitRegion = function(layout, config, pos){
  12642. Ext.layout.BorderLayout.SplitRegion.superclass.constructor.call(this, layout, config, pos);
  12643. // prevent switch
  12644. this.applyLayout = this.applyFns[pos];
  12645. };
  12646. Ext.extend(Ext.layout.BorderLayout.SplitRegion, Ext.layout.BorderLayout.Region, {
  12647. splitTip : "Drag to resize.",
  12648. collapsibleSplitTip : "Drag to resize. Double click to hide.",
  12649. useSplitTips : false,
  12650. // private
  12651. splitSettings : {
  12652. north : {
  12653. orientation: Ext.SplitBar.VERTICAL,
  12654. placement: Ext.SplitBar.TOP,
  12655. maxFn : 'getVMaxSize',
  12656. minProp: 'minHeight',
  12657. maxProp: 'maxHeight'
  12658. },
  12659. south : {
  12660. orientation: Ext.SplitBar.VERTICAL,
  12661. placement: Ext.SplitBar.BOTTOM,
  12662. maxFn : 'getVMaxSize',
  12663. minProp: 'minHeight',
  12664. maxProp: 'maxHeight'
  12665. },
  12666. east : {
  12667. orientation: Ext.SplitBar.HORIZONTAL,
  12668. placement: Ext.SplitBar.RIGHT,
  12669. maxFn : 'getHMaxSize',
  12670. minProp: 'minWidth',
  12671. maxProp: 'maxWidth'
  12672. },
  12673. west : {
  12674. orientation: Ext.SplitBar.HORIZONTAL,
  12675. placement: Ext.SplitBar.LEFT,
  12676. maxFn : 'getHMaxSize',
  12677. minProp: 'minWidth',
  12678. maxProp: 'maxWidth'
  12679. }
  12680. },
  12681. // private
  12682. applyFns : {
  12683. west : function(box){
  12684. if(this.isCollapsed){
  12685. return this.applyLayoutCollapsed(box);
  12686. }
  12687. var sd = this.splitEl.dom, s = sd.style;
  12688. this.panel.setPosition(box.x, box.y);
  12689. var sw = sd.offsetWidth;
  12690. s.left = (box.x+box.width-sw)+'px';
  12691. s.top = (box.y)+'px';
  12692. s.height = Math.max(0, box.height)+'px';
  12693. this.panel.setSize(box.width-sw, box.height);
  12694. },
  12695. east : function(box){
  12696. if(this.isCollapsed){
  12697. return this.applyLayoutCollapsed(box);
  12698. }
  12699. var sd = this.splitEl.dom, s = sd.style;
  12700. var sw = sd.offsetWidth;
  12701. this.panel.setPosition(box.x+sw, box.y);
  12702. s.left = (box.x)+'px';
  12703. s.top = (box.y)+'px';
  12704. s.height = Math.max(0, box.height)+'px';
  12705. this.panel.setSize(box.width-sw, box.height);
  12706. },
  12707. north : function(box){
  12708. if(this.isCollapsed){
  12709. return this.applyLayoutCollapsed(box);
  12710. }
  12711. var sd = this.splitEl.dom, s = sd.style;
  12712. var sh = sd.offsetHeight;
  12713. this.panel.setPosition(box.x, box.y);
  12714. s.left = (box.x)+'px';
  12715. s.top = (box.y+box.height-sh)+'px';
  12716. s.width = Math.max(0, box.width)+'px';
  12717. this.panel.setSize(box.width, box.height-sh);
  12718. },
  12719. south : function(box){
  12720. if(this.isCollapsed){
  12721. return this.applyLayoutCollapsed(box);
  12722. }
  12723. var sd = this.splitEl.dom, s = sd.style;
  12724. var sh = sd.offsetHeight;
  12725. this.panel.setPosition(box.x, box.y+sh);
  12726. s.left = (box.x)+'px';
  12727. s.top = (box.y)+'px';
  12728. s.width = Math.max(0, box.width)+'px';
  12729. this.panel.setSize(box.width, box.height-sh);
  12730. }
  12731. },
  12732. // private
  12733. render : function(ct, p){
  12734. Ext.layout.BorderLayout.SplitRegion.superclass.render.call(this, ct, p);
  12735. var ps = this.position;
  12736. this.splitEl = ct.createChild({
  12737. cls: "x-layout-split x-layout-split-"+ps, html: "&#160;",
  12738. id: this.panel.id + '-xsplit'
  12739. });
  12740. if(this.collapseMode == 'mini'){
  12741. this.miniSplitEl = this.splitEl.createChild({
  12742. cls: "x-layout-mini x-layout-mini-"+ps, html: "&#160;"
  12743. });
  12744. this.miniSplitEl.addClassOnOver('x-layout-mini-over');
  12745. this.miniSplitEl.on('click', this.onCollapseClick, this, {stopEvent:true});
  12746. }
  12747. var s = this.splitSettings[ps];
  12748. this.split = new Ext.SplitBar(this.splitEl.dom, p.el, s.orientation);
  12749. this.split.placement = s.placement;
  12750. this.split.getMaximumSize = this[s.maxFn].createDelegate(this);
  12751. this.split.minSize = this.minSize || this[s.minProp];
  12752. this.split.on("beforeapply", this.onSplitMove, this);
  12753. this.split.useShim = this.useShim === true;
  12754. this.maxSize = this.maxSize || this[s.maxProp];
  12755. if(p.hidden){
  12756. this.splitEl.hide();
  12757. }
  12758. if(this.useSplitTips){
  12759. this.splitEl.dom.title = this.collapsible ? this.collapsibleSplitTip : this.splitTip;
  12760. }
  12761. if(this.collapsible){
  12762. this.splitEl.on("dblclick", this.onCollapseClick, this);
  12763. }
  12764. },
  12765. //docs inherit from superclass
  12766. getSize : function(){
  12767. if(this.isCollapsed){
  12768. return this.collapsedEl.getSize();
  12769. }
  12770. var s = this.panel.getSize();
  12771. if(this.position == 'north' || this.position == 'south'){
  12772. s.height += this.splitEl.dom.offsetHeight;
  12773. }else{
  12774. s.width += this.splitEl.dom.offsetWidth;
  12775. }
  12776. return s;
  12777. },
  12778. // private
  12779. getHMaxSize : function(){
  12780. var cmax = this.maxSize || 10000;
  12781. var center = this.layout.center;
  12782. return Math.min(cmax, (this.el.getWidth()+center.el.getWidth())-center.getMinWidth());
  12783. },
  12784. // private
  12785. getVMaxSize : function(){
  12786. var cmax = this.maxSize || 10000;
  12787. var center = this.layout.center;
  12788. return Math.min(cmax, (this.el.getHeight()+center.el.getHeight())-center.getMinHeight());
  12789. },
  12790. // private
  12791. onSplitMove : function(split, newSize){
  12792. var s = this.panel.getSize();
  12793. this.lastSplitSize = newSize;
  12794. if(this.position == 'north' || this.position == 'south'){
  12795. this.panel.setSize(s.width, newSize);
  12796. this.state.height = newSize;
  12797. }else{
  12798. this.panel.setSize(newSize, s.height);
  12799. this.state.width = newSize;
  12800. }
  12801. this.layout.layout();
  12802. this.panel.saveState();
  12803. return false;
  12804. },
  12805. getSplitBar : function(){
  12806. return this.split;
  12807. },
  12808. // inherit docs
  12809. destroy : function() {
  12810. Ext.destroy(
  12811. this.miniSplitEl,
  12812. this.split,
  12813. this.splitEl
  12814. );
  12815. }
  12816. });
  12817. Ext.Container.LAYOUTS['border'] = Ext.layout.BorderLayout;
  12818. Ext.layout.FormLayout = Ext.extend(Ext.layout.AnchorLayout, {
  12819. labelSeparator : ':',
  12820. // private
  12821. getAnchorViewSize : function(ct, target){
  12822. return (ct.body||ct.el).getStyleSize();
  12823. },
  12824. // private
  12825. setContainer : function(ct){
  12826. Ext.layout.FormLayout.superclass.setContainer.call(this, ct);
  12827. if(ct.labelAlign){
  12828. ct.addClass('x-form-label-'+ct.labelAlign);
  12829. }
  12830. if(ct.hideLabels){
  12831. this.labelStyle = "display:none";
  12832. this.elementStyle = "padding-left:0;";
  12833. this.labelAdjust = 0;
  12834. }else{
  12835. this.labelSeparator = ct.labelSeparator || this.labelSeparator;
  12836. ct.labelWidth = ct.labelWidth || 100;
  12837. if(typeof ct.labelWidth == 'number'){
  12838. var pad = (typeof ct.labelPad == 'number' ? ct.labelPad : 5);
  12839. this.labelAdjust = ct.labelWidth+pad;
  12840. this.labelStyle = "width:"+ct.labelWidth+"px;";
  12841. this.elementStyle = "padding-left:"+(ct.labelWidth+pad)+'px';
  12842. }
  12843. if(ct.labelAlign == 'top'){
  12844. this.labelStyle = "width:auto;";
  12845. this.labelAdjust = 0;
  12846. this.elementStyle = "padding-left:0;";
  12847. }
  12848. }
  12849. if(!this.fieldTpl){
  12850. // the default field template used by all form layouts
  12851. var t = new Ext.Template(
  12852. '<div class="x-form-item {5}" tabIndex="-1">',
  12853. '<label for="{0}" style="{2}" class="x-form-item-label">{1}{4}</label>',
  12854. '<div class="x-form-element" id="x-form-el-{0}" style="{3}">',
  12855. '</div><div class="{6}"></div>',
  12856. '</div>'
  12857. );
  12858. t.disableFormats = true;
  12859. t.compile();
  12860. Ext.layout.FormLayout.prototype.fieldTpl = t;
  12861. }
  12862. },
  12863. //private
  12864. getLabelStyle: function(s){
  12865. var ls = '', items = [this.labelStyle, s];
  12866. for (var i = 0, len = items.length; i < len; ++i){
  12867. if (items[i]){
  12868. ls += items[i];
  12869. if (ls.substr(-1, 1) != ';'){
  12870. ls += ';'
  12871. }
  12872. }
  12873. }
  12874. return ls;
  12875. },
  12876. // private
  12877. renderItem : function(c, position, target){
  12878. if(c && !c.rendered && c.isFormField && c.inputType != 'hidden'){
  12879. var args = [
  12880. c.id, c.fieldLabel,
  12881. this.getLabelStyle(c.labelStyle),
  12882. this.elementStyle||'',
  12883. typeof c.labelSeparator == 'undefined' ? this.labelSeparator : c.labelSeparator,
  12884. (c.itemCls||this.container.itemCls||'') + (c.hideLabel ? ' x-hide-label' : ''),
  12885. c.clearCls || 'x-form-clear-left'
  12886. ];
  12887. if(typeof position == 'number'){
  12888. position = target.dom.childNodes[position] || null;
  12889. }
  12890. if(position){
  12891. this.fieldTpl.insertBefore(position, args);
  12892. }else{
  12893. this.fieldTpl.append(target, args);
  12894. }
  12895. c.render('x-form-el-'+c.id);
  12896. }else {
  12897. Ext.layout.FormLayout.superclass.renderItem.apply(this, arguments);
  12898. }
  12899. },
  12900. // private
  12901. adjustWidthAnchor : function(value, comp){
  12902. return value - (comp.isFormField ? (comp.hideLabel ? 0 : this.labelAdjust) : 0);
  12903. },
  12904. // private
  12905. isValidParent : function(c, target){
  12906. return true;
  12907. }
  12908. });
  12909. Ext.Container.LAYOUTS['form'] = Ext.layout.FormLayout;
  12910. Ext.layout.Accordion = Ext.extend(Ext.layout.FitLayout, {
  12911. fill : true,
  12912. autoWidth : true,
  12913. titleCollapse : true,
  12914. hideCollapseTool : false,
  12915. collapseFirst : false,
  12916. animate : false,
  12917. sequence : false,
  12918. activeOnTop : false,
  12919. renderItem : function(c){
  12920. if(this.animate === false){
  12921. c.animCollapse = false;
  12922. }
  12923. c.collapsible = true;
  12924. if(this.autoWidth){
  12925. c.autoWidth = true;
  12926. }
  12927. if(this.titleCollapse){
  12928. c.titleCollapse = true;
  12929. }
  12930. if(this.hideCollapseTool){
  12931. c.hideCollapseTool = true;
  12932. }
  12933. if(this.collapseFirst !== undefined){
  12934. c.collapseFirst = this.collapseFirst;
  12935. }
  12936. if(!this.activeItem && !c.collapsed){
  12937. this.activeItem = c;
  12938. }else if(this.activeItem){
  12939. c.collapsed = true;
  12940. }
  12941. Ext.layout.Accordion.superclass.renderItem.apply(this, arguments);
  12942. c.header.addClass('x-accordion-hd');
  12943. c.on('beforeexpand', this.beforeExpand, this);
  12944. },
  12945. // private
  12946. beforeExpand : function(p, anim){
  12947. var ai = this.activeItem;
  12948. if(ai){
  12949. if(this.sequence){
  12950. delete this.activeItem;
  12951. if (!ai.collapsed){
  12952. ai.collapse({callback:function(){
  12953. p.expand(anim || true);
  12954. }, scope: this});
  12955. return false;
  12956. }
  12957. }else{
  12958. ai.collapse(this.animate);
  12959. }
  12960. }
  12961. this.activeItem = p;
  12962. if(this.activeOnTop){
  12963. p.el.dom.parentNode.insertBefore(p.el.dom, p.el.dom.parentNode.firstChild);
  12964. }
  12965. this.layout();
  12966. },
  12967. // private
  12968. setItemSize : function(item, size){
  12969. if(this.fill && item){
  12970. var items = this.container.items.items;
  12971. var hh = 0;
  12972. for(var i = 0, len = items.length; i < len; i++){
  12973. var p = items[i];
  12974. if(p != item){
  12975. hh += (p.getSize().height - p.bwrap.getHeight());
  12976. }
  12977. }
  12978. size.height -= hh;
  12979. item.setSize(size);
  12980. }
  12981. }
  12982. });
  12983. Ext.Container.LAYOUTS['accordion'] = Ext.layout.Accordion;
  12984. Ext.layout.TableLayout = Ext.extend(Ext.layout.ContainerLayout, {
  12985. // private
  12986. monitorResize:false,
  12987. // private
  12988. setContainer : function(ct){
  12989. Ext.layout.TableLayout.superclass.setContainer.call(this, ct);
  12990. this.currentRow = 0;
  12991. this.currentColumn = 0;
  12992. this.cells = [];
  12993. },
  12994. // private
  12995. onLayout : function(ct, target){
  12996. var cs = ct.items.items, len = cs.length, c, i;
  12997. if(!this.table){
  12998. target.addClass('x-table-layout-ct');
  12999. this.table = target.createChild(
  13000. {tag:'table', cls:'x-table-layout', cellspacing: 0, cn: {tag: 'tbody'}}, null, true);
  13001. this.renderAll(ct, target);
  13002. }
  13003. },
  13004. // private
  13005. getRow : function(index){
  13006. var row = this.table.tBodies[0].childNodes[index];
  13007. if(!row){
  13008. row = document.createElement('tr');
  13009. this.table.tBodies[0].appendChild(row);
  13010. }
  13011. return row;
  13012. },
  13013. // private
  13014. getNextCell : function(c){
  13015. var cell = this.getNextNonSpan(this.currentColumn, this.currentRow);
  13016. var curCol = this.currentColumn = cell[0], curRow = this.currentRow = cell[1];
  13017. for(var rowIndex = curRow; rowIndex < curRow + (c.rowspan || 1); rowIndex++){
  13018. if(!this.cells[rowIndex]){
  13019. this.cells[rowIndex] = [];
  13020. }
  13021. for(var colIndex = curCol; colIndex < curCol + (c.colspan || 1); colIndex++){
  13022. this.cells[rowIndex][colIndex] = true;
  13023. }
  13024. }
  13025. var td = document.createElement('td');
  13026. if(c.cellId){
  13027. td.id = c.cellId;
  13028. }
  13029. var cls = 'x-table-layout-cell';
  13030. if(c.cellCls){
  13031. cls += ' ' + c.cellCls;
  13032. }
  13033. td.className = cls;
  13034. if(c.colspan){
  13035. td.colSpan = c.colspan;
  13036. }
  13037. if(c.rowspan){
  13038. td.rowSpan = c.rowspan;
  13039. }
  13040. this.getRow(curRow).appendChild(td);
  13041. return td;
  13042. },
  13043. // private
  13044. getNextNonSpan: function(colIndex, rowIndex){
  13045. var cols = this.columns;
  13046. while((cols && colIndex >= cols) || (this.cells[rowIndex] && this.cells[rowIndex][colIndex])) {
  13047. if(cols && colIndex >= cols){
  13048. rowIndex++;
  13049. colIndex = 0;
  13050. }else{
  13051. colIndex++;
  13052. }
  13053. }
  13054. return [colIndex, rowIndex];
  13055. },
  13056. // private
  13057. renderItem : function(c, position, target){
  13058. if(c && !c.rendered){
  13059. c.render(this.getNextCell(c));
  13060. if(this.extraCls){
  13061. var t = c.getPositionEl ? c.getPositionEl() : c;
  13062. t.addClass(this.extraCls);
  13063. }
  13064. }
  13065. },
  13066. // private
  13067. isValidParent : function(c, target){
  13068. return true;
  13069. }
  13070. });
  13071. Ext.Container.LAYOUTS['table'] = Ext.layout.TableLayout;
  13072. Ext.layout.AbsoluteLayout = Ext.extend(Ext.layout.AnchorLayout, {
  13073. extraCls: 'x-abs-layout-item',
  13074. isForm: false,
  13075. // private
  13076. setContainer : function(ct){
  13077. Ext.layout.AbsoluteLayout.superclass.setContainer.call(this, ct);
  13078. if(ct.isXType('form')){
  13079. this.isForm = true;
  13080. }
  13081. },
  13082. onLayout : function(ct, target){
  13083. if(this.isForm){ ct.body.position(); } else { target.position(); }
  13084. Ext.layout.AbsoluteLayout.superclass.onLayout.call(this, ct, target);
  13085. },
  13086. // private
  13087. getAnchorViewSize : function(ct, target){
  13088. return this.isForm ? ct.body.getStyleSize() : Ext.layout.AbsoluteLayout.superclass.getAnchorViewSize.call(this, ct, target);
  13089. },
  13090. // private
  13091. isValidParent : function(c, target){
  13092. return this.isForm ? true : Ext.layout.AbsoluteLayout.superclass.isValidParent.call(this, c, target);
  13093. },
  13094. // private
  13095. adjustWidthAnchor : function(value, comp){
  13096. return value ? value - comp.getPosition(true)[0] : value;
  13097. },
  13098. // private
  13099. adjustHeightAnchor : function(value, comp){
  13100. return value ? value - comp.getPosition(true)[1] : value;
  13101. }
  13102. });
  13103. Ext.Container.LAYOUTS['absolute'] = Ext.layout.AbsoluteLayout;
  13104. Ext.Viewport = Ext.extend(Ext.Container, {
  13105. initComponent : function() {
  13106. Ext.Viewport.superclass.initComponent.call(this);
  13107. document.getElementsByTagName('html')[0].className += ' x-viewport';
  13108. this.el = Ext.getBody();
  13109. this.el.setHeight = Ext.emptyFn;
  13110. this.el.setWidth = Ext.emptyFn;
  13111. this.el.setSize = Ext.emptyFn;
  13112. this.el.dom.scroll = 'no';
  13113. this.allowDomMove = false;
  13114. this.autoWidth = true;
  13115. this.autoHeight = true;
  13116. Ext.EventManager.onWindowResize(this.fireResize, this);
  13117. this.renderTo = this.el;
  13118. },
  13119. fireResize : function(w, h){
  13120. this.fireEvent('resize', this, w, h, w, h);
  13121. }
  13122. });
  13123. Ext.reg('viewport', Ext.Viewport);
  13124. Ext.Panel = Ext.extend(Ext.Container, {
  13125. baseCls : 'x-panel',
  13126. collapsedCls : 'x-panel-collapsed',
  13127. maskDisabled: true,
  13128. animCollapse: Ext.enableFx,
  13129. headerAsText: true,
  13130. buttonAlign: 'right',
  13131. collapsed : false,
  13132. collapseFirst: true,
  13133. minButtonWidth:75,
  13134. elements : 'body',
  13135. // protected - these could be used to customize the behavior of the window,
  13136. // but changing them would not be useful without further mofifications and
  13137. // could lead to unexpected or undesirable results.
  13138. toolTarget : 'header',
  13139. collapseEl : 'bwrap',
  13140. slideAnchor : 't',
  13141. disabledClass: '',
  13142. // private, notify box this class will handle heights
  13143. deferHeight: true,
  13144. // private
  13145. expandDefaults: {
  13146. duration:.25
  13147. },
  13148. // private
  13149. collapseDefaults: {
  13150. duration:.25
  13151. },
  13152. // private
  13153. initComponent : function(){
  13154. Ext.Panel.superclass.initComponent.call(this);
  13155. this.addEvents(
  13156. 'bodyresize',
  13157. 'titlechange',
  13158. 'iconchange',
  13159. 'collapse',
  13160. 'expand',
  13161. 'beforecollapse',
  13162. 'beforeexpand',
  13163. 'beforeclose',
  13164. 'close',
  13165. 'activate',
  13166. 'deactivate'
  13167. );
  13168. // shortcuts
  13169. if(this.tbar){
  13170. this.elements += ',tbar';
  13171. if(typeof this.tbar == 'object'){
  13172. this.topToolbar = this.tbar;
  13173. }
  13174. delete this.tbar;
  13175. }
  13176. if(this.bbar){
  13177. this.elements += ',bbar';
  13178. if(typeof this.bbar == 'object'){
  13179. this.bottomToolbar = this.bbar;
  13180. }
  13181. delete this.bbar;
  13182. }
  13183. if(this.header === true){
  13184. this.elements += ',header';
  13185. delete this.header;
  13186. }else if(this.title && this.header !== false){
  13187. this.elements += ',header';
  13188. }
  13189. if(this.footer === true){
  13190. this.elements += ',footer';
  13191. delete this.footer;
  13192. }
  13193. if(this.buttons){
  13194. var btns = this.buttons;
  13195. this.buttons = [];
  13196. for(var i = 0, len = btns.length; i < len; i++) {
  13197. if(btns[i].render){ // button instance
  13198. btns[i].ownerCt = this;
  13199. this.buttons.push(btns[i]);
  13200. }else{
  13201. this.addButton(btns[i]);
  13202. }
  13203. }
  13204. }
  13205. if(this.autoLoad){
  13206. this.on('render', this.doAutoLoad, this, {delay:10});
  13207. }
  13208. },
  13209. // private
  13210. createElement : function(name, pnode){
  13211. if(this[name]){
  13212. pnode.appendChild(this[name].dom);
  13213. return;
  13214. }
  13215. if(name === 'bwrap' || this.elements.indexOf(name) != -1){
  13216. if(this[name+'Cfg']){
  13217. this[name] = Ext.fly(pnode).createChild(this[name+'Cfg']);
  13218. }else{
  13219. var el = document.createElement('div');
  13220. el.className = this[name+'Cls'];
  13221. this[name] = Ext.get(pnode.appendChild(el));
  13222. }
  13223. if(this[name+'CssClass']){
  13224. this[name].addClass(this[name+'CssClass']);
  13225. }
  13226. if(this[name+'Style']){
  13227. this[name].applyStyles(this[name+'Style']);
  13228. }
  13229. }
  13230. },
  13231. // private
  13232. onRender : function(ct, position){
  13233. Ext.Panel.superclass.onRender.call(this, ct, position);
  13234. this.createClasses();
  13235. if(this.el){ // existing markup
  13236. this.el.addClass(this.baseCls);
  13237. this.header = this.el.down('.'+this.headerCls);
  13238. this.bwrap = this.el.down('.'+this.bwrapCls);
  13239. var cp = this.bwrap ? this.bwrap : this.el;
  13240. this.tbar = cp.down('.'+this.tbarCls);
  13241. this.body = cp.down('.'+this.bodyCls);
  13242. this.bbar = cp.down('.'+this.bbarCls);
  13243. this.footer = cp.down('.'+this.footerCls);
  13244. this.fromMarkup = true;
  13245. }else{
  13246. this.el = ct.createChild({
  13247. id: this.id,
  13248. cls: this.baseCls
  13249. }, position);
  13250. }
  13251. var el = this.el, d = el.dom;
  13252. if(this.cls){
  13253. this.el.addClass(this.cls);
  13254. }
  13255. if(this.buttons){
  13256. this.elements += ',footer';
  13257. }
  13258. // This block allows for maximum flexibility and performance when using existing markup
  13259. // framing requires special markup
  13260. if(this.frame){
  13261. el.insertHtml('afterBegin', String.format(Ext.Element.boxMarkup, this.baseCls));
  13262. this.createElement('header', d.firstChild.firstChild.firstChild);
  13263. this.createElement('bwrap', d);
  13264. // append the mid and bottom frame to the bwrap
  13265. var bw = this.bwrap.dom;
  13266. var ml = d.childNodes[1], bl = d.childNodes[2];
  13267. bw.appendChild(ml);
  13268. bw.appendChild(bl);
  13269. var mc = bw.firstChild.firstChild.firstChild;
  13270. this.createElement('tbar', mc);
  13271. this.createElement('body', mc);
  13272. this.createElement('bbar', mc);
  13273. this.createElement('footer', bw.lastChild.firstChild.firstChild);
  13274. if(!this.footer){
  13275. this.bwrap.dom.lastChild.className += ' x-panel-nofooter';
  13276. }
  13277. }else{
  13278. this.createElement('header', d);
  13279. this.createElement('bwrap', d);
  13280. // append the mid and bottom frame to the bwrap
  13281. var bw = this.bwrap.dom;
  13282. this.createElement('tbar', bw);
  13283. this.createElement('body', bw);
  13284. this.createElement('bbar', bw);
  13285. this.createElement('footer', bw);
  13286. if(!this.header){
  13287. this.body.addClass(this.bodyCls + '-noheader');
  13288. if(this.tbar){
  13289. this.tbar.addClass(this.tbarCls + '-noheader');
  13290. }
  13291. }
  13292. }
  13293. if(this.border === false){
  13294. this.el.addClass(this.baseCls + '-noborder');
  13295. this.body.addClass(this.bodyCls + '-noborder');
  13296. if(this.header){
  13297. this.header.addClass(this.headerCls + '-noborder');
  13298. }
  13299. if(this.footer){
  13300. this.footer.addClass(this.footerCls + '-noborder');
  13301. }
  13302. if(this.tbar){
  13303. this.tbar.addClass(this.tbarCls + '-noborder');
  13304. }
  13305. if(this.bbar){
  13306. this.bbar.addClass(this.bbarCls + '-noborder');
  13307. }
  13308. }
  13309. if(this.bodyBorder === false){
  13310. this.body.addClass(this.bodyCls + '-noborder');
  13311. }
  13312. this.bwrap.enableDisplayMode('block');
  13313. if(this.header){
  13314. this.header.unselectable();
  13315. // for tools, we need to wrap any existing header markup
  13316. if(this.headerAsText){
  13317. this.header.dom.innerHTML =
  13318. '<span class="' + this.headerTextCls + '">'+this.header.dom.innerHTML+'</span>';
  13319. if(this.iconCls){
  13320. this.setIconClass(this.iconCls);
  13321. }
  13322. }
  13323. }
  13324. if(this.floating){
  13325. this.makeFloating(this.floating);
  13326. }
  13327. if(this.collapsible){
  13328. this.tools = this.tools ? this.tools.slice(0) : [];
  13329. if(!this.hideCollapseTool){
  13330. this.tools[this.collapseFirst?'unshift':'push']({
  13331. id: 'toggle',
  13332. handler : this.toggleCollapse,
  13333. scope: this
  13334. });
  13335. }
  13336. if(this.titleCollapse && this.header){
  13337. this.header.on('click', this.toggleCollapse, this);
  13338. this.header.setStyle('cursor', 'pointer');
  13339. }
  13340. }
  13341. if(this.tools){
  13342. var ts = this.tools;
  13343. this.tools = {};
  13344. this.addTool.apply(this, ts);
  13345. }else{
  13346. this.tools = {};
  13347. }
  13348. if(this.buttons && this.buttons.length > 0){
  13349. // tables are required to maintain order and for correct IE layout
  13350. var tb = this.footer.createChild({cls:'x-panel-btns-ct', cn: {
  13351. cls:"x-panel-btns x-panel-btns-"+this.buttonAlign,
  13352. html:'<table cellspacing="0"><tbody><tr></tr></tbody></table><div class="x-clear"></div>'
  13353. }}, null, true);
  13354. var tr = tb.getElementsByTagName('tr')[0];
  13355. for(var i = 0, len = this.buttons.length; i < len; i++) {
  13356. var b = this.buttons[i];
  13357. var td = document.createElement('td');
  13358. td.className = 'x-panel-btn-td';
  13359. b.render(tr.appendChild(td));
  13360. }
  13361. }
  13362. if(this.tbar && this.topToolbar){
  13363. if(Ext.isArray(this.topToolbar)){
  13364. this.topToolbar = new Ext.Toolbar(this.topToolbar);
  13365. }
  13366. this.topToolbar.render(this.tbar);
  13367. this.topToolbar.ownerCt = this;
  13368. }
  13369. if(this.bbar && this.bottomToolbar){
  13370. if(Ext.isArray(this.bottomToolbar)){
  13371. this.bottomToolbar = new Ext.Toolbar(this.bottomToolbar);
  13372. }
  13373. this.bottomToolbar.render(this.bbar);
  13374. this.bottomToolbar.ownerCt = this;
  13375. }
  13376. },
  13377. setIconClass : function(cls){
  13378. var old = this.iconCls;
  13379. this.iconCls = cls;
  13380. if(this.rendered && this.header){
  13381. if(this.frame){
  13382. this.header.addClass('x-panel-icon');
  13383. this.header.replaceClass(old, this.iconCls);
  13384. }else{
  13385. var hd = this.header.dom;
  13386. var img = hd.firstChild && String(hd.firstChild.tagName).toLowerCase() == 'img' ? hd.firstChild : null;
  13387. if(img){
  13388. Ext.fly(img).replaceClass(old, this.iconCls);
  13389. }else{
  13390. Ext.DomHelper.insertBefore(hd.firstChild, {
  13391. tag:'img', src: Ext.BLANK_IMAGE_URL, cls:'x-panel-inline-icon '+this.iconCls
  13392. });
  13393. }
  13394. }
  13395. }
  13396. this.fireEvent('iconchange', this, cls, old);
  13397. },
  13398. // private
  13399. makeFloating : function(cfg){
  13400. this.floating = true;
  13401. this.el = new Ext.Layer(
  13402. typeof cfg == 'object' ? cfg : {
  13403. shadow: this.shadow !== undefined ? this.shadow : 'sides',
  13404. shadowOffset: this.shadowOffset,
  13405. constrain:false,
  13406. shim: this.shim === false ? false : undefined
  13407. }, this.el
  13408. );
  13409. },
  13410. getTopToolbar : function(){
  13411. return this.topToolbar;
  13412. },
  13413. getBottomToolbar : function(){
  13414. return this.bottomToolbar;
  13415. },
  13416. addButton : function(config, handler, scope){
  13417. var bc = {
  13418. handler: handler,
  13419. scope: scope,
  13420. minWidth: this.minButtonWidth,
  13421. hideParent:true
  13422. };
  13423. if(typeof config == "string"){
  13424. bc.text = config;
  13425. }else{
  13426. Ext.apply(bc, config);
  13427. }
  13428. var btn = new Ext.Button(bc);
  13429. btn.ownerCt = this;
  13430. if(!this.buttons){
  13431. this.buttons = [];
  13432. }
  13433. this.buttons.push(btn);
  13434. return btn;
  13435. },
  13436. // private
  13437. addTool : function(){
  13438. if(!this[this.toolTarget]) { // no where to render tools!
  13439. return;
  13440. }
  13441. if(!this.toolTemplate){
  13442. // initialize the global tool template on first use
  13443. var tt = new Ext.Template(
  13444. '<div class="x-tool x-tool-{id}">&#160;</div>'
  13445. );
  13446. tt.disableFormats = true;
  13447. tt.compile();
  13448. Ext.Panel.prototype.toolTemplate = tt;
  13449. }
  13450. for(var i = 0, a = arguments, len = a.length; i < len; i++) {
  13451. var tc = a[i];
  13452. if(!this.tools[tc.id]){
  13453. var overCls = 'x-tool-'+tc.id+'-over';
  13454. var t = this.toolTemplate.insertFirst((tc.align !== 'left') ? this[this.toolTarget] : this[this.toolTarget].child('span'), tc, true);
  13455. this.tools[tc.id] = t;
  13456. t.enableDisplayMode('block');
  13457. t.on('click', this.createToolHandler(t, tc, overCls, this));
  13458. if(tc.on){
  13459. t.on(tc.on);
  13460. }
  13461. if(tc.hidden){
  13462. t.hide();
  13463. }
  13464. if(tc.qtip){
  13465. if(typeof tc.qtip == 'object'){
  13466. Ext.QuickTips.register(Ext.apply({
  13467. target: t.id
  13468. }, tc.qtip));
  13469. } else {
  13470. t.dom.qtip = tc.qtip;
  13471. }
  13472. }
  13473. t.addClassOnOver(overCls);
  13474. }
  13475. }
  13476. },
  13477. // private
  13478. onShow : function(){
  13479. if(this.floating){
  13480. return this.el.show();
  13481. }
  13482. Ext.Panel.superclass.onShow.call(this);
  13483. },
  13484. // private
  13485. onHide : function(){
  13486. if(this.floating){
  13487. return this.el.hide();
  13488. }
  13489. Ext.Panel.superclass.onHide.call(this);
  13490. },
  13491. // private
  13492. createToolHandler : function(t, tc, overCls, panel){
  13493. return function(e){
  13494. t.removeClass(overCls);
  13495. e.stopEvent();
  13496. if(tc.handler){
  13497. tc.handler.call(tc.scope || t, e, t, panel);
  13498. }
  13499. };
  13500. },
  13501. // private
  13502. afterRender : function(){
  13503. if(this.fromMarkup && this.height === undefined && !this.autoHeight){
  13504. this.height = this.el.getHeight();
  13505. }
  13506. if(this.floating && !this.hidden && !this.initHidden){
  13507. this.el.show();
  13508. }
  13509. if(this.title){
  13510. this.setTitle(this.title);
  13511. }
  13512. this.setAutoScroll();
  13513. if(this.html){
  13514. this.body.update(typeof this.html == 'object' ?
  13515. Ext.DomHelper.markup(this.html) :
  13516. this.html);
  13517. delete this.html;
  13518. }
  13519. if(this.contentEl){
  13520. var ce = Ext.getDom(this.contentEl);
  13521. Ext.fly(ce).removeClass(['x-hidden', 'x-hide-display']);
  13522. this.body.dom.appendChild(ce);
  13523. }
  13524. if(this.collapsed){
  13525. this.collapsed = false;
  13526. this.collapse(false);
  13527. }
  13528. Ext.Panel.superclass.afterRender.call(this); // do sizing calcs last
  13529. this.initEvents();
  13530. },
  13531. // private
  13532. setAutoScroll : function(){
  13533. if(this.rendered && this.autoScroll){
  13534. var el = this.body || this.el;
  13535. if(el){
  13536. el.setOverflow('auto');
  13537. }
  13538. }
  13539. },
  13540. // private
  13541. getKeyMap : function(){
  13542. if(!this.keyMap){
  13543. this.keyMap = new Ext.KeyMap(this.el, this.keys);
  13544. }
  13545. return this.keyMap;
  13546. },
  13547. // private
  13548. initEvents : function(){
  13549. if(this.keys){
  13550. this.getKeyMap();
  13551. }
  13552. if(this.draggable){
  13553. this.initDraggable();
  13554. }
  13555. },
  13556. // private
  13557. initDraggable : function(){
  13558. this.dd = new Ext.Panel.DD(this, typeof this.draggable == 'boolean' ? null : this.draggable);
  13559. },
  13560. // private
  13561. beforeEffect : function(){
  13562. if(this.floating){
  13563. this.el.beforeAction();
  13564. }
  13565. this.el.addClass('x-panel-animated');
  13566. },
  13567. // private
  13568. afterEffect : function(){
  13569. this.syncShadow();
  13570. this.el.removeClass('x-panel-animated');
  13571. },
  13572. // private - wraps up an animation param with internal callbacks
  13573. createEffect : function(a, cb, scope){
  13574. var o = {
  13575. scope:scope,
  13576. block:true
  13577. };
  13578. if(a === true){
  13579. o.callback = cb;
  13580. return o;
  13581. }else if(!a.callback){
  13582. o.callback = cb;
  13583. }else { // wrap it up
  13584. o.callback = function(){
  13585. cb.call(scope);
  13586. Ext.callback(a.callback, a.scope);
  13587. };
  13588. }
  13589. return Ext.applyIf(o, a);
  13590. },
  13591. collapse : function(animate){
  13592. if(this.collapsed || this.el.hasFxBlock() || this.fireEvent('beforecollapse', this, animate) === false){
  13593. return;
  13594. }
  13595. var doAnim = animate === true || (animate !== false && this.animCollapse);
  13596. this.beforeEffect();
  13597. this.onCollapse(doAnim, animate);
  13598. return this;
  13599. },
  13600. // private
  13601. onCollapse : function(doAnim, animArg){
  13602. if(doAnim){
  13603. this[this.collapseEl].slideOut(this.slideAnchor,
  13604. Ext.apply(this.createEffect(animArg||true, this.afterCollapse, this),
  13605. this.collapseDefaults));
  13606. }else{
  13607. this[this.collapseEl].hide();
  13608. this.afterCollapse();
  13609. }
  13610. },
  13611. // private
  13612. afterCollapse : function(){
  13613. this.collapsed = true;
  13614. this.el.addClass(this.collapsedCls);
  13615. this.afterEffect();
  13616. this.fireEvent('collapse', this);
  13617. },
  13618. expand : function(animate){
  13619. if(!this.collapsed || this.el.hasFxBlock() || this.fireEvent('beforeexpand', this, animate) === false){
  13620. return;
  13621. }
  13622. var doAnim = animate === true || (animate !== false && this.animCollapse);
  13623. this.el.removeClass(this.collapsedCls);
  13624. this.beforeEffect();
  13625. this.onExpand(doAnim, animate);
  13626. return this;
  13627. },
  13628. // private
  13629. onExpand : function(doAnim, animArg){
  13630. if(doAnim){
  13631. this[this.collapseEl].slideIn(this.slideAnchor,
  13632. Ext.apply(this.createEffect(animArg||true, this.afterExpand, this),
  13633. this.expandDefaults));
  13634. }else{
  13635. this[this.collapseEl].show();
  13636. this.afterExpand();
  13637. }
  13638. },
  13639. // private
  13640. afterExpand : function(){
  13641. this.collapsed = false;
  13642. this.afterEffect();
  13643. this.fireEvent('expand', this);
  13644. },
  13645. toggleCollapse : function(animate){
  13646. this[this.collapsed ? 'expand' : 'collapse'](animate);
  13647. return this;
  13648. },
  13649. // private
  13650. onDisable : function(){
  13651. if(this.rendered && this.maskDisabled){
  13652. this.el.mask();
  13653. }
  13654. Ext.Panel.superclass.onDisable.call(this);
  13655. },
  13656. // private
  13657. onEnable : function(){
  13658. if(this.rendered && this.maskDisabled){
  13659. this.el.unmask();
  13660. }
  13661. Ext.Panel.superclass.onEnable.call(this);
  13662. },
  13663. // private
  13664. onResize : function(w, h){
  13665. if(w !== undefined || h !== undefined){
  13666. if(!this.collapsed){
  13667. if(typeof w == 'number'){
  13668. this.body.setWidth(
  13669. this.adjustBodyWidth(w - this.getFrameWidth()));
  13670. }else if(w == 'auto'){
  13671. this.body.setWidth(w);
  13672. }
  13673. if(typeof h == 'number'){
  13674. this.body.setHeight(
  13675. this.adjustBodyHeight(h - this.getFrameHeight()));
  13676. }else if(h == 'auto'){
  13677. this.body.setHeight(h);
  13678. }
  13679. if(this.disabled && this.el._mask){
  13680. this.el._mask.setSize(this.el.dom.clientWidth, this.el.getHeight());
  13681. }
  13682. }else{
  13683. this.queuedBodySize = {width: w, height: h};
  13684. if(!this.queuedExpand && this.allowQueuedExpand !== false){
  13685. this.queuedExpand = true;
  13686. this.on('expand', function(){
  13687. delete this.queuedExpand;
  13688. this.onResize(this.queuedBodySize.width, this.queuedBodySize.height);
  13689. this.doLayout();
  13690. }, this, {single:true});
  13691. }
  13692. }
  13693. this.fireEvent('bodyresize', this, w, h);
  13694. }
  13695. this.syncShadow();
  13696. },
  13697. // private
  13698. adjustBodyHeight : function(h){
  13699. return h;
  13700. },
  13701. // private
  13702. adjustBodyWidth : function(w){
  13703. return w;
  13704. },
  13705. // private
  13706. onPosition : function(){
  13707. this.syncShadow();
  13708. },
  13709. getFrameWidth : function(){
  13710. var w = this.el.getFrameWidth('lr');
  13711. if(this.frame){
  13712. var l = this.bwrap.dom.firstChild;
  13713. w += (Ext.fly(l).getFrameWidth('l') + Ext.fly(l.firstChild).getFrameWidth('r'));
  13714. var mc = this.bwrap.dom.firstChild.firstChild.firstChild;
  13715. w += Ext.fly(mc).getFrameWidth('lr');
  13716. }
  13717. return w;
  13718. },
  13719. getFrameHeight : function(){
  13720. var h = this.el.getFrameWidth('tb');
  13721. h += (this.tbar ? this.tbar.getHeight() : 0) +
  13722. (this.bbar ? this.bbar.getHeight() : 0);
  13723. if(this.frame){
  13724. var hd = this.el.dom.firstChild;
  13725. var ft = this.bwrap.dom.lastChild;
  13726. h += (hd.offsetHeight + ft.offsetHeight);
  13727. var mc = this.bwrap.dom.firstChild.firstChild.firstChild;
  13728. h += Ext.fly(mc).getFrameWidth('tb');
  13729. }else{
  13730. h += (this.header ? this.header.getHeight() : 0) +
  13731. (this.footer ? this.footer.getHeight() : 0);
  13732. }
  13733. return h;
  13734. },
  13735. getInnerWidth : function(){
  13736. return this.getSize().width - this.getFrameWidth();
  13737. },
  13738. getInnerHeight : function(){
  13739. return this.getSize().height - this.getFrameHeight();
  13740. },
  13741. // private
  13742. syncShadow : function(){
  13743. if(this.floating){
  13744. this.el.sync(true);
  13745. }
  13746. },
  13747. // private
  13748. getLayoutTarget : function(){
  13749. return this.body;
  13750. },
  13751. setTitle : function(title, iconCls){
  13752. this.title = title;
  13753. if(this.header && this.headerAsText){
  13754. this.header.child('span').update(title);
  13755. }
  13756. if(iconCls){
  13757. this.setIconClass(iconCls);
  13758. }
  13759. this.fireEvent('titlechange', this, title);
  13760. return this;
  13761. },
  13762. getUpdater : function(){
  13763. return this.body.getUpdater();
  13764. },
  13765. load : function(){
  13766. var um = this.body.getUpdater();
  13767. um.update.apply(um, arguments);
  13768. return this;
  13769. },
  13770. // private
  13771. beforeDestroy : function(){
  13772. if(this.header){
  13773. this.header.removeAllListeners();
  13774. if(this.headerAsText){
  13775. Ext.Element.uncache(this.header.child('span'));
  13776. }
  13777. }
  13778. Ext.Element.uncache(
  13779. this.header,
  13780. this.tbar,
  13781. this.bbar,
  13782. this.footer,
  13783. this.body,
  13784. this.bwrap
  13785. );
  13786. if(this.tools){
  13787. for(var k in this.tools){
  13788. Ext.destroy(this.tools[k]);
  13789. }
  13790. }
  13791. if(this.buttons){
  13792. for(var b in this.buttons){
  13793. Ext.destroy(this.buttons[b]);
  13794. }
  13795. }
  13796. Ext.destroy(
  13797. this.topToolbar,
  13798. this.bottomToolbar
  13799. );
  13800. Ext.Panel.superclass.beforeDestroy.call(this);
  13801. },
  13802. // private
  13803. createClasses : function(){
  13804. this.headerCls = this.baseCls + '-header';
  13805. this.headerTextCls = this.baseCls + '-header-text';
  13806. this.bwrapCls = this.baseCls + '-bwrap';
  13807. this.tbarCls = this.baseCls + '-tbar';
  13808. this.bodyCls = this.baseCls + '-body';
  13809. this.bbarCls = this.baseCls + '-bbar';
  13810. this.footerCls = this.baseCls + '-footer';
  13811. },
  13812. // private
  13813. createGhost : function(cls, useShim, appendTo){
  13814. var el = document.createElement('div');
  13815. el.className = 'x-panel-ghost ' + (cls ? cls : '');
  13816. if(this.header){
  13817. el.appendChild(this.el.dom.firstChild.cloneNode(true));
  13818. }
  13819. Ext.fly(el.appendChild(document.createElement('ul'))).setHeight(this.bwrap.getHeight());
  13820. el.style.width = this.el.dom.offsetWidth + 'px';;
  13821. if(!appendTo){
  13822. this.container.dom.appendChild(el);
  13823. }else{
  13824. Ext.getDom(appendTo).appendChild(el);
  13825. }
  13826. if(useShim !== false && this.el.useShim !== false){
  13827. var layer = new Ext.Layer({shadow:false, useDisplay:true, constrain:false}, el);
  13828. layer.show();
  13829. return layer;
  13830. }else{
  13831. return new Ext.Element(el);
  13832. }
  13833. },
  13834. // private
  13835. doAutoLoad : function(){
  13836. this.body.load(
  13837. typeof this.autoLoad == 'object' ?
  13838. this.autoLoad : {url: this.autoLoad});
  13839. },
  13840. getTool: function(id) {
  13841. return this.tools[id];
  13842. }
  13843. });
  13844. Ext.reg('panel', Ext.Panel);
  13845. Ext.Window = Ext.extend(Ext.Panel, {
  13846. baseCls : 'x-window',
  13847. resizable:true,
  13848. draggable:true,
  13849. closable : true,
  13850. constrain:false,
  13851. constrainHeader:false,
  13852. plain:false,
  13853. minimizable : false,
  13854. maximizable : false,
  13855. minHeight: 100,
  13856. minWidth: 200,
  13857. expandOnShow: true,
  13858. closeAction: 'close',
  13859. elements: 'header,body',
  13860. // inherited docs, same default
  13861. collapsible:false,
  13862. // private
  13863. initHidden : true,
  13864. monitorResize : true,
  13865. frame:true,
  13866. floating:true,
  13867. // private
  13868. initComponent : function(){
  13869. Ext.Window.superclass.initComponent.call(this);
  13870. this.addEvents(
  13871. 'resize',
  13872. 'maximize',
  13873. 'minimize',
  13874. 'restore'
  13875. );
  13876. },
  13877. // private
  13878. getState : function(){
  13879. return Ext.apply(Ext.Window.superclass.getState.call(this) || {}, this.getBox());
  13880. },
  13881. // private
  13882. onRender : function(ct, position){
  13883. Ext.Window.superclass.onRender.call(this, ct, position);
  13884. if(this.plain){
  13885. this.el.addClass('x-window-plain');
  13886. }
  13887. // this element allows the Window to be focused for keyboard events
  13888. this.focusEl = this.el.createChild({
  13889. tag: "a", href:"#", cls:"x-dlg-focus",
  13890. tabIndex:"-1", html: "&#160;"});
  13891. this.focusEl.swallowEvent('click', true);
  13892. this.proxy = this.el.createProxy("x-window-proxy");
  13893. this.proxy.enableDisplayMode('block');
  13894. if(this.modal){
  13895. this.mask = this.container.createChild({cls:"ext-el-mask"}, this.el.dom);
  13896. this.mask.enableDisplayMode("block");
  13897. this.mask.hide();
  13898. this.mask.on('click', this.focus, this);
  13899. }
  13900. },
  13901. // private
  13902. initEvents : function(){
  13903. Ext.Window.superclass.initEvents.call(this);
  13904. if(this.animateTarget){
  13905. this.setAnimateTarget(this.animateTarget);
  13906. }
  13907. if(this.resizable){
  13908. this.resizer = new Ext.Resizable(this.el, {
  13909. minWidth: this.minWidth,
  13910. minHeight:this.minHeight,
  13911. handles: this.resizeHandles || "all",
  13912. pinned: true,
  13913. resizeElement : this.resizerAction
  13914. });
  13915. this.resizer.window = this;
  13916. this.resizer.on("beforeresize", this.beforeResize, this);
  13917. }
  13918. if(this.draggable){
  13919. this.header.addClass("x-window-draggable");
  13920. }
  13921. this.initTools();
  13922. this.el.on("mousedown", this.toFront, this);
  13923. this.manager = this.manager || Ext.WindowMgr;
  13924. this.manager.register(this);
  13925. this.hidden = true;
  13926. if(this.maximized){
  13927. this.maximized = false;
  13928. this.maximize();
  13929. }
  13930. if(this.closable){
  13931. var km = this.getKeyMap();
  13932. km.on(27, this.onEsc, this);
  13933. km.disable();
  13934. }
  13935. },
  13936. initDraggable : function(){
  13937. this.dd = new Ext.Window.DD(this);
  13938. },
  13939. // private
  13940. onEsc : function(){
  13941. this[this.closeAction]();
  13942. },
  13943. // private
  13944. beforeDestroy : function(){
  13945. this.hide();
  13946. if(this.doAnchor){
  13947. Ext.EventManager.removeResizeListener(this.doAnchor, this);
  13948. Ext.EventManager.un(window, 'scroll', this.doAnchor, this);
  13949. }
  13950. Ext.destroy(
  13951. this.focusEl,
  13952. this.resizer,
  13953. this.dd,
  13954. this.proxy,
  13955. this.mask
  13956. );
  13957. Ext.Window.superclass.beforeDestroy.call(this);
  13958. },
  13959. // private
  13960. onDestroy : function(){
  13961. if(this.manager){
  13962. this.manager.unregister(this);
  13963. }
  13964. Ext.Window.superclass.onDestroy.call(this);
  13965. },
  13966. // private
  13967. initTools : function(){
  13968. if(this.minimizable){
  13969. this.addTool({
  13970. id: 'minimize',
  13971. handler: this.minimize.createDelegate(this, [])
  13972. });
  13973. }
  13974. if(this.maximizable){
  13975. this.addTool({
  13976. id: 'maximize',
  13977. handler: this.maximize.createDelegate(this, [])
  13978. });
  13979. this.addTool({
  13980. id: 'restore',
  13981. handler: this.restore.createDelegate(this, []),
  13982. hidden:true
  13983. });
  13984. this.header.on('dblclick', this.toggleMaximize, this);
  13985. }
  13986. if(this.closable){
  13987. this.addTool({
  13988. id: 'close',
  13989. handler: this[this.closeAction].createDelegate(this, [])
  13990. });
  13991. }
  13992. },
  13993. // private
  13994. resizerAction : function(){
  13995. var box = this.proxy.getBox();
  13996. this.proxy.hide();
  13997. this.window.handleResize(box);
  13998. return box;
  13999. },
  14000. // private
  14001. beforeResize : function(){
  14002. this.resizer.minHeight = Math.max(this.minHeight, this.getFrameHeight() + 40); // 40 is a magic minimum content size?
  14003. this.resizer.minWidth = Math.max(this.minWidth, this.getFrameWidth() + 40);
  14004. this.resizeBox = this.el.getBox();
  14005. },
  14006. // private
  14007. updateHandles : function(){
  14008. if(Ext.isIE && this.resizer){
  14009. this.resizer.syncHandleHeight();
  14010. this.el.repaint();
  14011. }
  14012. },
  14013. // private
  14014. handleResize : function(box){
  14015. var rz = this.resizeBox;
  14016. if(rz.x != box.x || rz.y != box.y){
  14017. this.updateBox(box);
  14018. }else{
  14019. this.setSize(box);
  14020. }
  14021. this.focus();
  14022. this.updateHandles();
  14023. this.saveState();
  14024. if(this.layout){
  14025. this.doLayout();
  14026. }
  14027. this.fireEvent("resize", this, box.width, box.height);
  14028. },
  14029. focus : function(){
  14030. var f = this.focusEl, db = this.defaultButton, t = typeof db;
  14031. if(t != 'undefined'){
  14032. if(t == 'number'){
  14033. f = this.buttons[db];
  14034. }else if(t == 'string'){
  14035. f = Ext.getCmp(db);
  14036. }else{
  14037. f = db;
  14038. }
  14039. }
  14040. f.focus.defer(10, f);
  14041. },
  14042. setAnimateTarget : function(el){
  14043. el = Ext.get(el);
  14044. this.animateTarget = el;
  14045. },
  14046. // private
  14047. beforeShow : function(){
  14048. delete this.el.lastXY;
  14049. delete this.el.lastLT;
  14050. if(this.x === undefined || this.y === undefined){
  14051. var xy = this.el.getAlignToXY(this.container, 'c-c');
  14052. var pos = this.el.translatePoints(xy[0], xy[1]);
  14053. this.x = this.x === undefined? pos.left : this.x;
  14054. this.y = this.y === undefined? pos.top : this.y;
  14055. }
  14056. this.el.setLeftTop(this.x, this.y);
  14057. if(this.expandOnShow){
  14058. this.expand(false);
  14059. }
  14060. if(this.modal){
  14061. Ext.getBody().addClass("x-body-masked");
  14062. this.mask.setSize(Ext.lib.Dom.getViewWidth(true), Ext.lib.Dom.getViewHeight(true));
  14063. this.mask.show();
  14064. }
  14065. },
  14066. show : function(animateTarget, cb, scope){
  14067. if(!this.rendered){
  14068. this.render(Ext.getBody());
  14069. }
  14070. if(this.hidden === false){
  14071. this.toFront();
  14072. return;
  14073. }
  14074. if(this.fireEvent("beforeshow", this) === false){
  14075. return;
  14076. }
  14077. if(cb){
  14078. this.on('show', cb, scope, {single:true});
  14079. }
  14080. this.hidden = false;
  14081. if(animateTarget !== undefined){
  14082. this.setAnimateTarget(animateTarget);
  14083. }
  14084. this.beforeShow();
  14085. if(this.animateTarget){
  14086. this.animShow();
  14087. }else{
  14088. this.afterShow();
  14089. }
  14090. },
  14091. // private
  14092. afterShow : function(){
  14093. this.proxy.hide();
  14094. this.el.setStyle('display', 'block');
  14095. this.el.show();
  14096. if(this.maximized){
  14097. this.fitContainer();
  14098. }
  14099. if(Ext.isMac && Ext.isGecko){ // work around stupid FF 2.0/Mac scroll bar bug
  14100. this.cascade(this.setAutoScroll);
  14101. }
  14102. if(this.monitorResize || this.modal || this.constrain || this.constrainHeader){
  14103. Ext.EventManager.onWindowResize(this.onWindowResize, this);
  14104. }
  14105. this.doConstrain();
  14106. if(this.layout){
  14107. this.doLayout();
  14108. }
  14109. if(this.keyMap){
  14110. this.keyMap.enable();
  14111. }
  14112. this.toFront();
  14113. this.updateHandles();
  14114. this.fireEvent("show", this);
  14115. },
  14116. // private
  14117. animShow : function(){
  14118. this.proxy.show();
  14119. this.proxy.setBox(this.animateTarget.getBox());
  14120. this.proxy.setOpacity(0);
  14121. var b = this.getBox(false);
  14122. b.callback = this.afterShow;
  14123. b.scope = this;
  14124. b.duration = .25;
  14125. b.easing = 'easeNone';
  14126. b.opacity = .5;
  14127. b.block = true;
  14128. this.el.setStyle('display', 'none');
  14129. this.proxy.shift(b);
  14130. },
  14131. hide : function(animateTarget, cb, scope){
  14132. if(this.activeGhost){ // drag active?
  14133. this.hide.defer(100, this, [animateTarget, cb, scope]);
  14134. return;
  14135. }
  14136. if(this.hidden || this.fireEvent("beforehide", this) === false){
  14137. return;
  14138. }
  14139. if(cb){
  14140. this.on('hide', cb, scope, {single:true});
  14141. }
  14142. this.hidden = true;
  14143. if(animateTarget !== undefined){
  14144. this.setAnimateTarget(animateTarget);
  14145. }
  14146. if(this.animateTarget){
  14147. this.animHide();
  14148. }else{
  14149. this.el.hide();
  14150. this.afterHide();
  14151. }
  14152. },
  14153. // private
  14154. afterHide : function(){
  14155. this.proxy.hide();
  14156. if(this.monitorResize || this.modal || this.constrain || this.constrainHeader){
  14157. Ext.EventManager.removeResizeListener(this.onWindowResize, this);
  14158. }
  14159. if(this.modal){
  14160. this.mask.hide();
  14161. Ext.getBody().removeClass("x-body-masked");
  14162. }
  14163. if(this.keyMap){
  14164. this.keyMap.disable();
  14165. }
  14166. this.fireEvent("hide", this);
  14167. },
  14168. // private
  14169. animHide : function(){
  14170. this.proxy.setOpacity(.5);
  14171. this.proxy.show();
  14172. var tb = this.getBox(false);
  14173. this.proxy.setBox(tb);
  14174. this.el.hide();
  14175. var b = this.animateTarget.getBox();
  14176. b.callback = this.afterHide;
  14177. b.scope = this;
  14178. b.duration = .25;
  14179. b.easing = 'easeNone';
  14180. b.block = true;
  14181. b.opacity = 0;
  14182. this.proxy.shift(b);
  14183. },
  14184. // private
  14185. onWindowResize : function(){
  14186. if(this.maximized){
  14187. this.fitContainer();
  14188. }
  14189. if(this.modal){
  14190. this.mask.setSize('100%', '100%');
  14191. var force = this.mask.dom.offsetHeight;
  14192. this.mask.setSize(Ext.lib.Dom.getViewWidth(true), Ext.lib.Dom.getViewHeight(true));
  14193. }
  14194. this.doConstrain();
  14195. },
  14196. // private
  14197. doConstrain : function(){
  14198. if(this.constrain || this.constrainHeader){
  14199. var offsets;
  14200. if(this.constrain){
  14201. offsets = {
  14202. right:this.el.shadowOffset,
  14203. left:this.el.shadowOffset,
  14204. bottom:this.el.shadowOffset
  14205. };
  14206. }else {
  14207. var s = this.getSize();
  14208. offsets = {
  14209. right:-(s.width - 100),
  14210. bottom:-(s.height - 25)
  14211. };
  14212. }
  14213. var xy = this.el.getConstrainToXY(this.container, true, offsets);
  14214. if(xy){
  14215. this.setPosition(xy[0], xy[1]);
  14216. }
  14217. }
  14218. },
  14219. // private - used for dragging
  14220. ghost : function(cls){
  14221. var ghost = this.createGhost(cls);
  14222. var box = this.getBox(true);
  14223. ghost.setLeftTop(box.x, box.y);
  14224. ghost.setWidth(box.width);
  14225. this.el.hide();
  14226. this.activeGhost = ghost;
  14227. return ghost;
  14228. },
  14229. // private
  14230. unghost : function(show, matchPosition){
  14231. if(show !== false){
  14232. this.el.show();
  14233. this.focus();
  14234. if(Ext.isMac && Ext.isGecko){ // work around stupid FF 2.0/Mac scroll bar bug
  14235. this.cascade(this.setAutoScroll);
  14236. }
  14237. }
  14238. if(matchPosition !== false){
  14239. this.setPosition(this.activeGhost.getLeft(true), this.activeGhost.getTop(true));
  14240. }
  14241. this.activeGhost.hide();
  14242. this.activeGhost.remove();
  14243. delete this.activeGhost;
  14244. },
  14245. minimize : function(){
  14246. this.fireEvent('minimize', this);
  14247. },
  14248. close : function(){
  14249. if(this.fireEvent("beforeclose", this) !== false){
  14250. this.hide(null, function(){
  14251. this.fireEvent('close', this);
  14252. this.destroy();
  14253. }, this);
  14254. }
  14255. },
  14256. maximize : function(){
  14257. if(!this.maximized){
  14258. this.expand(false);
  14259. this.restoreSize = this.getSize();
  14260. this.restorePos = this.getPosition(true);
  14261. if (this.maximizable){
  14262. this.tools.maximize.hide();
  14263. this.tools.restore.show();
  14264. }
  14265. this.maximized = true;
  14266. this.el.disableShadow();
  14267. if(this.dd){
  14268. this.dd.lock();
  14269. }
  14270. if(this.collapsible){
  14271. this.tools.toggle.hide();
  14272. }
  14273. this.el.addClass('x-window-maximized');
  14274. this.container.addClass('x-window-maximized-ct');
  14275. this.setPosition(0, 0);
  14276. this.fitContainer();
  14277. this.fireEvent('maximize', this);
  14278. }
  14279. },
  14280. restore : function(){
  14281. if(this.maximized){
  14282. this.el.removeClass('x-window-maximized');
  14283. this.tools.restore.hide();
  14284. this.tools.maximize.show();
  14285. this.setPosition(this.restorePos[0], this.restorePos[1]);
  14286. this.setSize(this.restoreSize.width, this.restoreSize.height);
  14287. delete this.restorePos;
  14288. delete this.restoreSize;
  14289. this.maximized = false;
  14290. this.el.enableShadow(true);
  14291. if(this.dd){
  14292. this.dd.unlock();
  14293. }
  14294. if(this.collapsible){
  14295. this.tools.toggle.show();
  14296. }
  14297. this.container.removeClass('x-window-maximized-ct');
  14298. this.doConstrain();
  14299. this.fireEvent('restore', this);
  14300. }
  14301. },
  14302. toggleMaximize : function(){
  14303. this[this.maximized ? 'restore' : 'maximize']();
  14304. },
  14305. // private
  14306. fitContainer : function(){
  14307. var vs = this.container.getViewSize();
  14308. this.setSize(vs.width, vs.height);
  14309. },
  14310. // private
  14311. // z-index is managed by the WindowManager and may be overwritten at any time
  14312. setZIndex : function(index){
  14313. if(this.modal){
  14314. this.mask.setStyle("z-index", index);
  14315. }
  14316. this.el.setZIndex(++index);
  14317. index += 5;
  14318. if(this.resizer){
  14319. this.resizer.proxy.setStyle("z-index", ++index);
  14320. }
  14321. this.lastZIndex = index;
  14322. },
  14323. alignTo : function(element, position, offsets){
  14324. var xy = this.el.getAlignToXY(element, position, offsets);
  14325. this.setPagePosition(xy[0], xy[1]);
  14326. return this;
  14327. },
  14328. anchorTo : function(el, alignment, offsets, monitorScroll){
  14329. if(this.doAnchor){
  14330. Ext.EventManager.removeResizeListener(this.doAnchor, this);
  14331. Ext.EventManager.un(window, 'scroll', this.doAnchor, this);
  14332. }
  14333. this.doAnchor = function(){
  14334. this.alignTo(el, alignment, offsets);
  14335. };
  14336. Ext.EventManager.onWindowResize(this.doAnchor, this);
  14337. var tm = typeof monitorScroll;
  14338. if(tm != 'undefined'){
  14339. Ext.EventManager.on(window, 'scroll', this.doAnchor, this,
  14340. {buffer: tm == 'number' ? monitorScroll : 50});
  14341. }
  14342. this.doAnchor();
  14343. return this;
  14344. },
  14345. toFront : function(e){
  14346. if(this.manager.bringToFront(this)){
  14347. if(!e || !e.getTarget().focus){
  14348. this.focus();
  14349. }
  14350. }
  14351. return this;
  14352. },
  14353. setActive : function(active){
  14354. if(active){
  14355. if(!this.maximized){
  14356. this.el.enableShadow(true);
  14357. }
  14358. this.fireEvent('activate', this);
  14359. }else{
  14360. this.el.disableShadow();
  14361. this.fireEvent('deactivate', this);
  14362. }
  14363. },
  14364. toBack : function(){
  14365. this.manager.sendToBack(this);
  14366. return this;
  14367. },
  14368. center : function(){
  14369. var xy = this.el.getAlignToXY(this.container, 'c-c');
  14370. this.setPagePosition(xy[0], xy[1]);
  14371. return this;
  14372. }
  14373. });
  14374. Ext.reg('window', Ext.Window);
  14375. // private - custom Window DD implementation
  14376. Ext.Window.DD = function(win){
  14377. this.win = win;
  14378. Ext.Window.DD.superclass.constructor.call(this, win.el.id, 'WindowDD-'+win.id);
  14379. this.setHandleElId(win.header.id);
  14380. this.scroll = false;
  14381. };
  14382. Ext.extend(Ext.Window.DD, Ext.dd.DD, {
  14383. moveOnly:true,
  14384. headerOffsets:[100, 25],
  14385. startDrag : function(){
  14386. var w = this.win;
  14387. this.proxy = w.ghost();
  14388. if(w.constrain !== false){
  14389. var so = w.el.shadowOffset;
  14390. this.constrainTo(w.container, {right: so, left: so, bottom: so});
  14391. }else if(w.constrainHeader !== false){
  14392. var s = this.proxy.getSize();
  14393. this.constrainTo(w.container, {right: -(s.width-this.headerOffsets[0]), bottom: -(s.height-this.headerOffsets[1])});
  14394. }
  14395. },
  14396. b4Drag : Ext.emptyFn,
  14397. onDrag : function(e){
  14398. this.alignElWithMouse(this.proxy, e.getPageX(), e.getPageY());
  14399. },
  14400. endDrag : function(e){
  14401. this.win.unghost();
  14402. this.win.saveState();
  14403. }
  14404. });
  14405. Ext.WindowGroup = function(){
  14406. var list = {};
  14407. var accessList = [];
  14408. var front = null;
  14409. // private
  14410. var sortWindows = function(d1, d2){
  14411. return (!d1._lastAccess || d1._lastAccess < d2._lastAccess) ? -1 : 1;
  14412. };
  14413. // private
  14414. var orderWindows = function(){
  14415. var a = accessList, len = a.length;
  14416. if(len > 0){
  14417. a.sort(sortWindows);
  14418. var seed = a[0].manager.zseed;
  14419. for(var i = 0; i < len; i++){
  14420. var win = a[i];
  14421. if(win && !win.hidden){
  14422. win.setZIndex(seed + (i*10));
  14423. }
  14424. }
  14425. }
  14426. activateLast();
  14427. };
  14428. // private
  14429. var setActiveWin = function(win){
  14430. if(win != front){
  14431. if(front){
  14432. front.setActive(false);
  14433. }
  14434. front = win;
  14435. if(win){
  14436. win.setActive(true);
  14437. }
  14438. }
  14439. };
  14440. // private
  14441. var activateLast = function(){
  14442. for(var i = accessList.length-1; i >=0; --i) {
  14443. if(!accessList[i].hidden){
  14444. setActiveWin(accessList[i]);
  14445. return;
  14446. }
  14447. }
  14448. // none to activate
  14449. setActiveWin(null);
  14450. };
  14451. return {
  14452. zseed : 9000,
  14453. // private
  14454. register : function(win){
  14455. list[win.id] = win;
  14456. accessList.push(win);
  14457. win.on('hide', activateLast);
  14458. },
  14459. // private
  14460. unregister : function(win){
  14461. delete list[win.id];
  14462. win.un('hide', activateLast);
  14463. accessList.remove(win);
  14464. },
  14465. get : function(id){
  14466. return typeof id == "object" ? id : list[id];
  14467. },
  14468. bringToFront : function(win){
  14469. win = this.get(win);
  14470. if(win != front){
  14471. win._lastAccess = new Date().getTime();
  14472. orderWindows();
  14473. return true;
  14474. }
  14475. return false;
  14476. },
  14477. sendToBack : function(win){
  14478. win = this.get(win);
  14479. win._lastAccess = -(new Date().getTime());
  14480. orderWindows();
  14481. return win;
  14482. },
  14483. hideAll : function(){
  14484. for(var id in list){
  14485. if(list[id] && typeof list[id] != "function" && list[id].isVisible()){
  14486. list[id].hide();
  14487. }
  14488. }
  14489. },
  14490. getActive : function(){
  14491. return front;
  14492. },
  14493. getBy : function(fn, scope){
  14494. var r = [];
  14495. for(var i = accessList.length-1; i >=0; --i) {
  14496. var win = accessList[i];
  14497. if(fn.call(scope||win, win) !== false){
  14498. r.push(win);
  14499. }
  14500. }
  14501. return r;
  14502. },
  14503. each : function(fn, scope){
  14504. for(var id in list){
  14505. if(list[id] && typeof list[id] != "function"){
  14506. if(fn.call(scope || list[id], list[id]) === false){
  14507. return;
  14508. }
  14509. }
  14510. }
  14511. }
  14512. };
  14513. };
  14514. Ext.WindowMgr = new Ext.WindowGroup();
  14515. Ext.dd.PanelProxy = function(panel, config){
  14516. this.panel = panel;
  14517. this.id = this.panel.id +'-ddproxy';
  14518. Ext.apply(this, config);
  14519. };
  14520. Ext.dd.PanelProxy.prototype = {
  14521. insertProxy : true,
  14522. // private overrides
  14523. setStatus : Ext.emptyFn,
  14524. reset : Ext.emptyFn,
  14525. update : Ext.emptyFn,
  14526. stop : Ext.emptyFn,
  14527. sync: Ext.emptyFn,
  14528. getEl : function(){
  14529. return this.ghost;
  14530. },
  14531. getGhost : function(){
  14532. return this.ghost;
  14533. },
  14534. getProxy : function(){
  14535. return this.proxy;
  14536. },
  14537. hide : function(){
  14538. if(this.ghost){
  14539. if(this.proxy){
  14540. this.proxy.remove();
  14541. delete this.proxy;
  14542. }
  14543. this.panel.el.dom.style.display = '';
  14544. this.ghost.remove();
  14545. delete this.ghost;
  14546. }
  14547. },
  14548. show : function(){
  14549. if(!this.ghost){
  14550. this.ghost = this.panel.createGhost(undefined, undefined, Ext.getBody());
  14551. this.ghost.setXY(this.panel.el.getXY())
  14552. if(this.insertProxy){
  14553. this.proxy = this.panel.el.insertSibling({cls:'x-panel-dd-spacer'});
  14554. this.proxy.setSize(this.panel.getSize());
  14555. }
  14556. this.panel.el.dom.style.display = 'none';
  14557. }
  14558. },
  14559. // private
  14560. repair : function(xy, callback, scope){
  14561. this.hide();
  14562. if(typeof callback == "function"){
  14563. callback.call(scope || this);
  14564. }
  14565. },
  14566. moveProxy : function(parentNode, before){
  14567. if(this.proxy){
  14568. parentNode.insertBefore(this.proxy.dom, before);
  14569. }
  14570. }
  14571. };
  14572. // private - DD implementation for Panels
  14573. Ext.Panel.DD = function(panel, cfg){
  14574. this.panel = panel;
  14575. this.dragData = {panel: panel};
  14576. this.proxy = new Ext.dd.PanelProxy(panel, cfg);
  14577. Ext.Panel.DD.superclass.constructor.call(this, panel.el, cfg);
  14578. var h = panel.header;
  14579. if(h){
  14580. this.setHandleElId(h.id);
  14581. }
  14582. (h ? h : this.panel.body).setStyle('cursor', 'move');
  14583. this.scroll = false;
  14584. };
  14585. Ext.extend(Ext.Panel.DD, Ext.dd.DragSource, {
  14586. showFrame: Ext.emptyFn,
  14587. startDrag: Ext.emptyFn,
  14588. b4StartDrag: function(x, y) {
  14589. this.proxy.show();
  14590. },
  14591. b4MouseDown: function(e) {
  14592. var x = e.getPageX();
  14593. var y = e.getPageY();
  14594. this.autoOffset(x, y);
  14595. },
  14596. onInitDrag : function(x, y){
  14597. this.onStartDrag(x, y);
  14598. return true;
  14599. },
  14600. createFrame : Ext.emptyFn,
  14601. getDragEl : function(e){
  14602. return this.proxy.ghost.dom;
  14603. },
  14604. endDrag : function(e){
  14605. this.proxy.hide();
  14606. this.panel.saveState();
  14607. },
  14608. autoOffset : function(x, y) {
  14609. x -= this.startPageX;
  14610. y -= this.startPageY;
  14611. this.setDelta(x, y);
  14612. }
  14613. });
  14614. Ext.state.Provider = function(){
  14615. this.addEvents("statechange");
  14616. this.state = {};
  14617. Ext.state.Provider.superclass.constructor.call(this);
  14618. };
  14619. Ext.extend(Ext.state.Provider, Ext.util.Observable, {
  14620. get : function(name, defaultValue){
  14621. return typeof this.state[name] == "undefined" ?
  14622. defaultValue : this.state[name];
  14623. },
  14624. clear : function(name){
  14625. delete this.state[name];
  14626. this.fireEvent("statechange", this, name, null);
  14627. },
  14628. set : function(name, value){
  14629. this.state[name] = value;
  14630. this.fireEvent("statechange", this, name, value);
  14631. },
  14632. decodeValue : function(cookie){
  14633. var re = /^(a|n|d|b|s|o)\:(.*)$/;
  14634. var matches = re.exec(unescape(cookie));
  14635. if(!matches || !matches[1]) return; // non state cookie
  14636. var type = matches[1];
  14637. var v = matches[2];
  14638. switch(type){
  14639. case "n":
  14640. return parseFloat(v);
  14641. case "d":
  14642. return new Date(Date.parse(v));
  14643. case "b":
  14644. return (v == "1");
  14645. case "a":
  14646. var all = [];
  14647. var values = v.split("^");
  14648. for(var i = 0, len = values.length; i < len; i++){
  14649. all.push(this.decodeValue(values[i]));
  14650. }
  14651. return all;
  14652. case "o":
  14653. var all = {};
  14654. var values = v.split("^");
  14655. for(var i = 0, len = values.length; i < len; i++){
  14656. var kv = values[i].split("=");
  14657. all[kv[0]] = this.decodeValue(kv[1]);
  14658. }
  14659. return all;
  14660. default:
  14661. return v;
  14662. }
  14663. },
  14664. encodeValue : function(v){
  14665. var enc;
  14666. if(typeof v == "number"){
  14667. enc = "n:" + v;
  14668. }else if(typeof v == "boolean"){
  14669. enc = "b:" + (v ? "1" : "0");
  14670. }else if(Ext.isDate(v)){
  14671. enc = "d:" + v.toGMTString();
  14672. }else if(Ext.isArray(v)){
  14673. var flat = "";
  14674. for(var i = 0, len = v.length; i < len; i++){
  14675. flat += this.encodeValue(v[i]);
  14676. if(i != len-1) flat += "^";
  14677. }
  14678. enc = "a:" + flat;
  14679. }else if(typeof v == "object"){
  14680. var flat = "";
  14681. for(var key in v){
  14682. if(typeof v[key] != "function" && v[key] !== undefined){
  14683. flat += key + "=" + this.encodeValue(v[key]) + "^";
  14684. }
  14685. }
  14686. enc = "o:" + flat.substring(0, flat.length-1);
  14687. }else{
  14688. enc = "s:" + v;
  14689. }
  14690. return escape(enc);
  14691. }
  14692. });
  14693. Ext.state.Manager = function(){
  14694. var provider = new Ext.state.Provider();
  14695. return {
  14696. setProvider : function(stateProvider){
  14697. provider = stateProvider;
  14698. },
  14699. get : function(key, defaultValue){
  14700. return provider.get(key, defaultValue);
  14701. },
  14702. set : function(key, value){
  14703. provider.set(key, value);
  14704. },
  14705. clear : function(key){
  14706. provider.clear(key);
  14707. },
  14708. getProvider : function(){
  14709. return provider;
  14710. }
  14711. };
  14712. }();
  14713. Ext.state.CookieProvider = function(config){
  14714. Ext.state.CookieProvider.superclass.constructor.call(this);
  14715. this.path = "/";
  14716. this.expires = new Date(new Date().getTime()+(1000*60*60*24*7)); //7 days
  14717. this.domain = null;
  14718. this.secure = false;
  14719. Ext.apply(this, config);
  14720. this.state = this.readCookies();
  14721. };
  14722. Ext.extend(Ext.state.CookieProvider, Ext.state.Provider, {
  14723. // private
  14724. set : function(name, value){
  14725. if(typeof value == "undefined" || value === null){
  14726. this.clear(name);
  14727. return;
  14728. }
  14729. this.setCookie(name, value);
  14730. Ext.state.CookieProvider.superclass.set.call(this, name, value);
  14731. },
  14732. // private
  14733. clear : function(name){
  14734. this.clearCookie(name);
  14735. Ext.state.CookieProvider.superclass.clear.call(this, name);
  14736. },
  14737. // private
  14738. readCookies : function(){
  14739. var cookies = {};
  14740. var c = document.cookie + ";";
  14741. var re = /\s?(.*?)=(.*?);/g;
  14742. var matches;
  14743. while((matches = re.exec(c)) != null){
  14744. var name = matches[1];
  14745. var value = matches[2];
  14746. if(name && name.substring(0,3) == "ys-"){
  14747. cookies[name.substr(3)] = this.decodeValue(value);
  14748. }
  14749. }
  14750. return cookies;
  14751. },
  14752. // private
  14753. setCookie : function(name, value){
  14754. document.cookie = "ys-"+ name + "=" + this.encodeValue(value) +
  14755. ((this.expires == null) ? "" : ("; expires=" + this.expires.toGMTString())) +
  14756. ((this.path == null) ? "" : ("; path=" + this.path)) +
  14757. ((this.domain == null) ? "" : ("; domain=" + this.domain)) +
  14758. ((this.secure == true) ? "; secure" : "");
  14759. },
  14760. // private
  14761. clearCookie : function(name){
  14762. document.cookie = "ys-" + name + "=null; expires=Thu, 01-Jan-70 00:00:01 GMT" +
  14763. ((this.path == null) ? "" : ("; path=" + this.path)) +
  14764. ((this.domain == null) ? "" : ("; domain=" + this.domain)) +
  14765. ((this.secure == true) ? "; secure" : "");
  14766. }
  14767. });
  14768. Ext.DataView = Ext.extend(Ext.BoxComponent, {
  14769. selectedClass : "x-view-selected",
  14770. emptyText : "",
  14771. deferEmptyText: true,
  14772. trackOver: false,
  14773. //private
  14774. last: false,
  14775. // private
  14776. initComponent : function(){
  14777. Ext.DataView.superclass.initComponent.call(this);
  14778. if(typeof this.tpl == "string"){
  14779. this.tpl = new Ext.XTemplate(this.tpl);
  14780. }
  14781. this.addEvents(
  14782. "beforeclick",
  14783. "click",
  14784. "mouseenter",
  14785. "mouseleave",
  14786. "containerclick",
  14787. "dblclick",
  14788. "contextmenu",
  14789. "selectionchange",
  14790. "beforeselect"
  14791. );
  14792. this.all = new Ext.CompositeElementLite();
  14793. this.selected = new Ext.CompositeElementLite();
  14794. },
  14795. // private
  14796. onRender : function(){
  14797. if(!this.el){
  14798. this.el = document.createElement('div');
  14799. this.el.id = this.id;
  14800. }
  14801. Ext.DataView.superclass.onRender.apply(this, arguments);
  14802. },
  14803. // private
  14804. afterRender : function(){
  14805. Ext.DataView.superclass.afterRender.call(this);
  14806. this.el.on({
  14807. "click": this.onClick,
  14808. "dblclick": this.onDblClick,
  14809. "contextmenu": this.onContextMenu,
  14810. scope:this
  14811. });
  14812. if(this.overClass || this.trackOver){
  14813. this.el.on({
  14814. "mouseover": this.onMouseOver,
  14815. "mouseout": this.onMouseOut,
  14816. scope:this
  14817. });
  14818. }
  14819. if(this.store){
  14820. this.setStore(this.store, true);
  14821. }
  14822. },
  14823. refresh : function(){
  14824. this.clearSelections(false, true);
  14825. this.el.update("");
  14826. var records = this.store.getRange();
  14827. if(records.length < 1){
  14828. if(!this.deferEmptyText || this.hasSkippedEmptyText){
  14829. this.el.update(this.emptyText);
  14830. }
  14831. this.hasSkippedEmptyText = true;
  14832. this.all.clear();
  14833. return;
  14834. }
  14835. this.tpl.overwrite(this.el, this.collectData(records, 0));
  14836. this.all.fill(Ext.query(this.itemSelector, this.el.dom));
  14837. this.updateIndexes(0);
  14838. },
  14839. prepareData : function(data){
  14840. return data;
  14841. },
  14842. collectData : function(records, startIndex){
  14843. var r = [];
  14844. for(var i = 0, len = records.length; i < len; i++){
  14845. r[r.length] = this.prepareData(records[i].data, startIndex+i, records[i]);
  14846. }
  14847. return r;
  14848. },
  14849. // private
  14850. bufferRender : function(records){
  14851. var div = document.createElement('div');
  14852. this.tpl.overwrite(div, this.collectData(records));
  14853. return Ext.query(this.itemSelector, div);
  14854. },
  14855. // private
  14856. onUpdate : function(ds, record){
  14857. var index = this.store.indexOf(record);
  14858. var sel = this.isSelected(index);
  14859. var original = this.all.elements[index];
  14860. var node = this.bufferRender([record], index)[0];
  14861. this.all.replaceElement(index, node, true);
  14862. if(sel){
  14863. this.selected.replaceElement(original, node);
  14864. this.all.item(index).addClass(this.selectedClass);
  14865. }
  14866. this.updateIndexes(index, index);
  14867. },
  14868. // private
  14869. onAdd : function(ds, records, index){
  14870. if(this.all.getCount() == 0){
  14871. this.refresh();
  14872. return;
  14873. }
  14874. var nodes = this.bufferRender(records, index), n, a = this.all.elements;
  14875. if(index < this.all.getCount()){
  14876. n = this.all.item(index).insertSibling(nodes, 'before', true);
  14877. a.splice.apply(a, [index, 0].concat(nodes));
  14878. }else{
  14879. n = this.all.last().insertSibling(nodes, 'after', true);
  14880. a.push.apply(a, nodes);
  14881. }
  14882. this.updateIndexes(index);
  14883. },
  14884. // private
  14885. onRemove : function(ds, record, index){
  14886. this.deselect(index);
  14887. this.all.removeElement(index, true);
  14888. this.updateIndexes(index);
  14889. },
  14890. refreshNode : function(index){
  14891. this.onUpdate(this.store, this.store.getAt(index));
  14892. },
  14893. // private
  14894. updateIndexes : function(startIndex, endIndex){
  14895. var ns = this.all.elements;
  14896. startIndex = startIndex || 0;
  14897. endIndex = endIndex || ((endIndex === 0) ? 0 : (ns.length - 1));
  14898. for(var i = startIndex; i <= endIndex; i++){
  14899. ns[i].viewIndex = i;
  14900. }
  14901. },
  14902. getStore : function(){
  14903. return this.store;
  14904. },
  14905. setStore : function(store, initial){
  14906. if(!initial && this.store){
  14907. this.store.un("beforeload", this.onBeforeLoad, this);
  14908. this.store.un("datachanged", this.refresh, this);
  14909. this.store.un("add", this.onAdd, this);
  14910. this.store.un("remove", this.onRemove, this);
  14911. this.store.un("update", this.onUpdate, this);
  14912. this.store.un("clear", this.refresh, this);
  14913. }
  14914. if(store){
  14915. store = Ext.StoreMgr.lookup(store);
  14916. store.on("beforeload", this.onBeforeLoad, this);
  14917. store.on("datachanged", this.refresh, this);
  14918. store.on("add", this.onAdd, this);
  14919. store.on("remove", this.onRemove, this);
  14920. store.on("update", this.onUpdate, this);
  14921. store.on("clear", this.refresh, this);
  14922. }
  14923. this.store = store;
  14924. if(store){
  14925. this.refresh();
  14926. }
  14927. },
  14928. findItemFromChild : function(node){
  14929. return Ext.fly(node).findParent(this.itemSelector, this.el);
  14930. },
  14931. // private
  14932. onClick : function(e){
  14933. var item = e.getTarget(this.itemSelector, this.el);
  14934. if(item){
  14935. var index = this.indexOf(item);
  14936. if(this.onItemClick(item, index, e) !== false){
  14937. this.fireEvent("click", this, index, item, e);
  14938. }
  14939. }else{
  14940. if(this.fireEvent("containerclick", this, e) !== false){
  14941. this.clearSelections();
  14942. }
  14943. }
  14944. },
  14945. // private
  14946. onContextMenu : function(e){
  14947. var item = e.getTarget(this.itemSelector, this.el);
  14948. if(item){
  14949. this.fireEvent("contextmenu", this, this.indexOf(item), item, e);
  14950. }
  14951. },
  14952. // private
  14953. onDblClick : function(e){
  14954. var item = e.getTarget(this.itemSelector, this.el);
  14955. if(item){
  14956. this.fireEvent("dblclick", this, this.indexOf(item), item, e);
  14957. }
  14958. },
  14959. // private
  14960. onMouseOver : function(e){
  14961. var item = e.getTarget(this.itemSelector, this.el);
  14962. if(item && item !== this.lastItem){
  14963. this.lastItem = item;
  14964. Ext.fly(item).addClass(this.overClass);
  14965. this.fireEvent("mouseenter", this, this.indexOf(item), item, e);
  14966. }
  14967. },
  14968. // private
  14969. onMouseOut : function(e){
  14970. if(this.lastItem){
  14971. if(!e.within(this.lastItem, true, true)){
  14972. Ext.fly(this.lastItem).removeClass(this.overClass);
  14973. this.fireEvent("mouseleave", this, this.indexOf(this.lastItem), this.lastItem, e);
  14974. delete this.lastItem;
  14975. }
  14976. }
  14977. },
  14978. // private
  14979. onItemClick : function(item, index, e){
  14980. if(this.fireEvent("beforeclick", this, index, item, e) === false){
  14981. return false;
  14982. }
  14983. if(this.multiSelect){
  14984. this.doMultiSelection(item, index, e);
  14985. e.preventDefault();
  14986. }else if(this.singleSelect){
  14987. this.doSingleSelection(item, index, e);
  14988. e.preventDefault();
  14989. }
  14990. return true;
  14991. },
  14992. // private
  14993. doSingleSelection : function(item, index, e){
  14994. if(e.ctrlKey && this.isSelected(index)){
  14995. this.deselect(index);
  14996. }else{
  14997. this.select(index, false);
  14998. }
  14999. },
  15000. // private
  15001. doMultiSelection : function(item, index, e){
  15002. if(e.shiftKey && this.last !== false){
  15003. var last = this.last;
  15004. this.selectRange(last, index, e.ctrlKey);
  15005. this.last = last; // reset the last
  15006. }else{
  15007. if((e.ctrlKey||this.simpleSelect) && this.isSelected(index)){
  15008. this.deselect(index);
  15009. }else{
  15010. this.select(index, e.ctrlKey || e.shiftKey || this.simpleSelect);
  15011. }
  15012. }
  15013. },
  15014. getSelectionCount : function(){
  15015. return this.selected.getCount()
  15016. },
  15017. getSelectedNodes : function(){
  15018. return this.selected.elements;
  15019. },
  15020. getSelectedIndexes : function(){
  15021. var indexes = [], s = this.selected.elements;
  15022. for(var i = 0, len = s.length; i < len; i++){
  15023. indexes.push(s[i].viewIndex);
  15024. }
  15025. return indexes;
  15026. },
  15027. getSelectedRecords : function(){
  15028. var r = [], s = this.selected.elements;
  15029. for(var i = 0, len = s.length; i < len; i++){
  15030. r[r.length] = this.store.getAt(s[i].viewIndex);
  15031. }
  15032. return r;
  15033. },
  15034. getRecords : function(nodes){
  15035. var r = [], s = nodes;
  15036. for(var i = 0, len = s.length; i < len; i++){
  15037. r[r.length] = this.store.getAt(s[i].viewIndex);
  15038. }
  15039. return r;
  15040. },
  15041. getRecord : function(node){
  15042. return this.store.getAt(node.viewIndex);
  15043. },
  15044. clearSelections : function(suppressEvent, skipUpdate){
  15045. if((this.multiSelect || this.singleSelect) && this.selected.getCount() > 0){
  15046. if(!skipUpdate){
  15047. this.selected.removeClass(this.selectedClass);
  15048. }
  15049. this.selected.clear();
  15050. this.last = false;
  15051. if(!suppressEvent){
  15052. this.fireEvent("selectionchange", this, this.selected.elements);
  15053. }
  15054. }
  15055. },
  15056. isSelected : function(node){
  15057. return this.selected.contains(this.getNode(node));
  15058. },
  15059. deselect : function(node){
  15060. if(this.isSelected(node)){
  15061. node = this.getNode(node);
  15062. this.selected.removeElement(node);
  15063. if(this.last == node.viewIndex){
  15064. this.last = false;
  15065. }
  15066. Ext.fly(node).removeClass(this.selectedClass);
  15067. this.fireEvent("selectionchange", this, this.selected.elements);
  15068. }
  15069. },
  15070. select : function(nodeInfo, keepExisting, suppressEvent){
  15071. if(Ext.isArray(nodeInfo)){
  15072. if(!keepExisting){
  15073. this.clearSelections(true);
  15074. }
  15075. for(var i = 0, len = nodeInfo.length; i < len; i++){
  15076. this.select(nodeInfo[i], true, true);
  15077. }
  15078. if(!suppressEvent){
  15079. this.fireEvent("selectionchange", this, this.selected.elements);
  15080. }
  15081. } else{
  15082. var node = this.getNode(nodeInfo);
  15083. if(!keepExisting){
  15084. this.clearSelections(true);
  15085. }
  15086. if(node && !this.isSelected(node)){
  15087. if(this.fireEvent("beforeselect", this, node, this.selected.elements) !== false){
  15088. Ext.fly(node).addClass(this.selectedClass);
  15089. this.selected.add(node);
  15090. this.last = node.viewIndex;
  15091. if(!suppressEvent){
  15092. this.fireEvent("selectionchange", this, this.selected.elements);
  15093. }
  15094. }
  15095. }
  15096. }
  15097. },
  15098. selectRange : function(start, end, keepExisting){
  15099. if(!keepExisting){
  15100. this.clearSelections(true);
  15101. }
  15102. this.select(this.getNodes(start, end), true);
  15103. },
  15104. getNode : function(nodeInfo){
  15105. if(typeof nodeInfo == "string"){
  15106. return document.getElementById(nodeInfo);
  15107. }else if(typeof nodeInfo == "number"){
  15108. return this.all.elements[nodeInfo];
  15109. }
  15110. return nodeInfo;
  15111. },
  15112. getNodes : function(start, end){
  15113. var ns = this.all.elements;
  15114. start = start || 0;
  15115. end = typeof end == "undefined" ? Math.max(ns.length - 1, 0) : end;
  15116. var nodes = [], i;
  15117. if(start <= end){
  15118. for(i = start; i <= end && ns[i]; i++){
  15119. nodes.push(ns[i]);
  15120. }
  15121. } else{
  15122. for(i = start; i >= end && ns[i]; i--){
  15123. nodes.push(ns[i]);
  15124. }
  15125. }
  15126. return nodes;
  15127. },
  15128. indexOf : function(node){
  15129. node = this.getNode(node);
  15130. if(typeof node.viewIndex == "number"){
  15131. return node.viewIndex;
  15132. }
  15133. return this.all.indexOf(node);
  15134. },
  15135. // private
  15136. onBeforeLoad : function(){
  15137. if(this.loadingText){
  15138. this.clearSelections(false, true);
  15139. this.el.update('<div class="loading-indicator">'+this.loadingText+'</div>');
  15140. this.all.clear();
  15141. }
  15142. },
  15143. onDestroy : function(){
  15144. Ext.DataView.superclass.onDestroy.call(this);
  15145. this.setStore(null);
  15146. }
  15147. });
  15148. Ext.reg('dataview', Ext.DataView);
  15149. Ext.ColorPalette = function(config){
  15150. Ext.ColorPalette.superclass.constructor.call(this, config);
  15151. this.addEvents(
  15152. 'select'
  15153. );
  15154. if(this.handler){
  15155. this.on("select", this.handler, this.scope, true);
  15156. }
  15157. };
  15158. Ext.extend(Ext.ColorPalette, Ext.Component, {
  15159. itemCls : "x-color-palette",
  15160. value : null,
  15161. clickEvent:'click',
  15162. // private
  15163. ctype: "Ext.ColorPalette",
  15164. allowReselect : false,
  15165. colors : [
  15166. "000000", "993300", "333300", "003300", "003366", "000080", "333399", "333333",
  15167. "800000", "FF6600", "808000", "008000", "008080", "0000FF", "666699", "808080",
  15168. "FF0000", "FF9900", "99CC00", "339966", "33CCCC", "3366FF", "800080", "969696",
  15169. "FF00FF", "FFCC00", "FFFF00", "00FF00", "00FFFF", "00CCFF", "993366", "C0C0C0",
  15170. "FF99CC", "FFCC99", "FFFF99", "CCFFCC", "CCFFFF", "99CCFF", "CC99FF", "FFFFFF"
  15171. ],
  15172. // private
  15173. onRender : function(container, position){
  15174. var t = this.tpl || new Ext.XTemplate(
  15175. '<tpl for="."><a href="#" class="color-{.}" hidefocus="on"><em><span style="background:#{.}" unselectable="on">&#160;</span></em></a></tpl>'
  15176. );
  15177. var el = document.createElement("div");
  15178. el.id = this.getId();
  15179. el.className = this.itemCls;
  15180. t.overwrite(el, this.colors);
  15181. container.dom.insertBefore(el, position);
  15182. this.el = Ext.get(el);
  15183. this.el.on(this.clickEvent, this.handleClick, this, {delegate: "a"});
  15184. if(this.clickEvent != 'click'){
  15185. this.el.on('click', Ext.emptyFn, this, {delegate: "a", preventDefault:true});
  15186. }
  15187. },
  15188. // private
  15189. afterRender : function(){
  15190. Ext.ColorPalette.superclass.afterRender.call(this);
  15191. if(this.value){
  15192. var s = this.value;
  15193. this.value = null;
  15194. this.select(s);
  15195. }
  15196. },
  15197. // private
  15198. handleClick : function(e, t){
  15199. e.preventDefault();
  15200. if(!this.disabled){
  15201. var c = t.className.match(/(?:^|\s)color-(.{6})(?:\s|$)/)[1];
  15202. this.select(c.toUpperCase());
  15203. }
  15204. },
  15205. select : function(color){
  15206. color = color.replace("#", "");
  15207. if(color != this.value || this.allowReselect){
  15208. var el = this.el;
  15209. if(this.value){
  15210. el.child("a.color-"+this.value).removeClass("x-color-palette-sel");
  15211. }
  15212. el.child("a.color-"+color).addClass("x-color-palette-sel");
  15213. this.value = color;
  15214. this.fireEvent("select", this, color);
  15215. }
  15216. }
  15217. });
  15218. Ext.reg('colorpalette', Ext.ColorPalette);
  15219. Ext.DatePicker = Ext.extend(Ext.Component, {
  15220. todayText : "Today",
  15221. okText : "&#160;OK&#160;", // &#160; to give the user extra clicking room
  15222. cancelText : "Cancel",
  15223. todayTip : "{0} (Spacebar)",
  15224. minText : "This date is before the minimum date",
  15225. maxText : "This date is after the maximum date",
  15226. format : "m/d/y",
  15227. disabledDaysText : "Disabled",
  15228. disabledDatesText : "Disabled",
  15229. constrainToViewport : true,
  15230. monthNames : Date.monthNames,
  15231. dayNames : Date.dayNames,
  15232. nextText: 'Next Month (Control+Right)',
  15233. prevText: 'Previous Month (Control+Left)',
  15234. monthYearText: 'Choose a month (Control+Up/Down to move years)',
  15235. startDay : 0,
  15236. showToday : true,
  15237. // private
  15238. initComponent : function(){
  15239. Ext.DatePicker.superclass.initComponent.call(this);
  15240. this.value = this.value ?
  15241. this.value.clearTime() : new Date().clearTime();
  15242. this.addEvents(
  15243. 'select'
  15244. );
  15245. if(this.handler){
  15246. this.on("select", this.handler, this.scope || this);
  15247. }
  15248. this.initDisabledDays();
  15249. },
  15250. // private
  15251. initDisabledDays : function(){
  15252. if(!this.disabledDatesRE && this.disabledDates){
  15253. var dd = this.disabledDates;
  15254. var re = "(?:";
  15255. for(var i = 0; i < dd.length; i++){
  15256. re += dd[i];
  15257. if(i != dd.length-1) re += "|";
  15258. }
  15259. this.disabledDatesRE = new RegExp(re + ")");
  15260. }
  15261. },
  15262. setDisabledDates : function(dd){
  15263. if(Ext.isArray(dd)){
  15264. this.disabledDates = dd;
  15265. this.disabledDatesRE = null;
  15266. }else{
  15267. this.disabledDatesRE = dd;
  15268. }
  15269. this.initDisabledDays();
  15270. this.update(this.value, true);
  15271. },
  15272. setDisabledDays : function(dd){
  15273. this.disabledDays = dd;
  15274. this.update(this.value, true);
  15275. },
  15276. setMinDate : function(dt){
  15277. this.minDate = dt;
  15278. this.update(this.value, true);
  15279. },
  15280. setMaxDate : function(dt){
  15281. this.maxDate = dt;
  15282. this.update(this.value, true);
  15283. },
  15284. setValue : function(value){
  15285. var old = this.value;
  15286. this.value = value.clearTime(true);
  15287. if(this.el){
  15288. this.update(this.value);
  15289. }
  15290. },
  15291. getValue : function(){
  15292. return this.value;
  15293. },
  15294. // private
  15295. focus : function(){
  15296. if(this.el){
  15297. this.update(this.activeDate);
  15298. }
  15299. },
  15300. // private
  15301. onRender : function(container, position){
  15302. var m = [
  15303. '<table cellspacing="0">',
  15304. '<tr><td class="x-date-left"><a href="#" title="', this.prevText ,'">&#160;</a></td><td class="x-date-middle" align="center"></td><td class="x-date-right"><a href="#" title="', this.nextText ,'">&#160;</a></td></tr>',
  15305. '<tr><td colspan="3"><table class="x-date-inner" cellspacing="0"><thead><tr>'];
  15306. var dn = this.dayNames;
  15307. for(var i = 0; i < 7; i++){
  15308. var d = this.startDay+i;
  15309. if(d > 6){
  15310. d = d-7;
  15311. }
  15312. m.push("<th><span>", dn[d].substr(0,1), "</span></th>");
  15313. }
  15314. m[m.length] = "</tr></thead><tbody><tr>";
  15315. for(var i = 0; i < 42; i++) {
  15316. if(i % 7 == 0 && i != 0){
  15317. m[m.length] = "</tr><tr>";
  15318. }
  15319. m[m.length] = '<td><a href="#" hidefocus="on" class="x-date-date" tabIndex="1"><em><span></span></em></a></td>';
  15320. }
  15321. m.push('</tr></tbody></table></td></tr>',
  15322. this.showToday ? '<tr><td colspan="3" class="x-date-bottom" align="center"></td></tr>' : '',
  15323. '</table><div class="x-date-mp"></div>');
  15324. var el = document.createElement("div");
  15325. el.className = "x-date-picker";
  15326. el.innerHTML = m.join("");
  15327. container.dom.insertBefore(el, position);
  15328. this.el = Ext.get(el);
  15329. this.eventEl = Ext.get(el.firstChild);
  15330. this.leftClickRpt = new Ext.util.ClickRepeater(this.el.child("td.x-date-left a"), {
  15331. handler: this.showPrevMonth,
  15332. scope: this,
  15333. preventDefault:true,
  15334. stopDefault:true
  15335. });
  15336. this.rightClickRpt = new Ext.util.ClickRepeater(this.el.child("td.x-date-right a"), {
  15337. handler: this.showNextMonth,
  15338. scope: this,
  15339. preventDefault:true,
  15340. stopDefault:true
  15341. });
  15342. this.eventEl.on("mousewheel", this.handleMouseWheel, this);
  15343. this.monthPicker = this.el.down('div.x-date-mp');
  15344. this.monthPicker.enableDisplayMode('block');
  15345. var kn = new Ext.KeyNav(this.eventEl, {
  15346. "left" : function(e){
  15347. e.ctrlKey ?
  15348. this.showPrevMonth() :
  15349. this.update(this.activeDate.add("d", -1));
  15350. },
  15351. "right" : function(e){
  15352. e.ctrlKey ?
  15353. this.showNextMonth() :
  15354. this.update(this.activeDate.add("d", 1));
  15355. },
  15356. "up" : function(e){
  15357. e.ctrlKey ?
  15358. this.showNextYear() :
  15359. this.update(this.activeDate.add("d", -7));
  15360. },
  15361. "down" : function(e){
  15362. e.ctrlKey ?
  15363. this.showPrevYear() :
  15364. this.update(this.activeDate.add("d", 7));
  15365. },
  15366. "pageUp" : function(e){
  15367. this.showNextMonth();
  15368. },
  15369. "pageDown" : function(e){
  15370. this.showPrevMonth();
  15371. },
  15372. "enter" : function(e){
  15373. e.stopPropagation();
  15374. return true;
  15375. },
  15376. scope : this
  15377. });
  15378. this.eventEl.on("click", this.handleDateClick, this, {delegate: "a.x-date-date"});
  15379. this.el.unselectable();
  15380. this.cells = this.el.select("table.x-date-inner tbody td");
  15381. this.textNodes = this.el.query("table.x-date-inner tbody span");
  15382. this.mbtn = new Ext.Button({
  15383. text: "&#160;",
  15384. tooltip: this.monthYearText,
  15385. renderTo: this.el.child("td.x-date-middle", true)
  15386. });
  15387. this.mbtn.on('click', this.showMonthPicker, this);
  15388. this.mbtn.el.child(this.mbtn.menuClassTarget).addClass("x-btn-with-menu");
  15389. if(this.showToday){
  15390. this.todayKeyListener = this.eventEl.addKeyListener(Ext.EventObject.SPACE, this.selectToday, this);
  15391. var today = (new Date()).dateFormat(this.format);
  15392. this.todayBtn = new Ext.Button({
  15393. renderTo: this.el.child("td.x-date-bottom", true),
  15394. text: String.format(this.todayText, today),
  15395. tooltip: String.format(this.todayTip, today),
  15396. handler: this.selectToday,
  15397. scope: this
  15398. });
  15399. }
  15400. if(Ext.isIE){
  15401. this.el.repaint();
  15402. }
  15403. this.update(this.value);
  15404. },
  15405. // private
  15406. createMonthPicker : function(){
  15407. if(!this.monthPicker.dom.firstChild){
  15408. var buf = ['<table border="0" cellspacing="0">'];
  15409. for(var i = 0; i < 6; i++){
  15410. buf.push(
  15411. '<tr><td class="x-date-mp-month"><a href="#">', this.monthNames[i].substr(0, 3), '</a></td>',
  15412. '<td class="x-date-mp-month x-date-mp-sep"><a href="#">', this.monthNames[i+6].substr(0, 3), '</a></td>',
  15413. i == 0 ?
  15414. '<td class="x-date-mp-ybtn" align="center"><a class="x-date-mp-prev"></a></td><td class="x-date-mp-ybtn" align="center"><a class="x-date-mp-next"></a></td></tr>' :
  15415. '<td class="x-date-mp-year"><a href="#"></a></td><td class="x-date-mp-year"><a href="#"></a></td></tr>'
  15416. );
  15417. }
  15418. buf.push(
  15419. '<tr class="x-date-mp-btns"><td colspan="4"><button type="button" class="x-date-mp-ok">',
  15420. this.okText,
  15421. '</button><button type="button" class="x-date-mp-cancel">',
  15422. this.cancelText,
  15423. '</button></td></tr>',
  15424. '</table>'
  15425. );
  15426. this.monthPicker.update(buf.join(''));
  15427. this.monthPicker.on('click', this.onMonthClick, this);
  15428. this.monthPicker.on('dblclick', this.onMonthDblClick, this);
  15429. this.mpMonths = this.monthPicker.select('td.x-date-mp-month');
  15430. this.mpYears = this.monthPicker.select('td.x-date-mp-year');
  15431. this.mpMonths.each(function(m, a, i){
  15432. i += 1;
  15433. if((i%2) == 0){
  15434. m.dom.xmonth = 5 + Math.round(i * .5);
  15435. }else{
  15436. m.dom.xmonth = Math.round((i-1) * .5);
  15437. }
  15438. });
  15439. }
  15440. },
  15441. // private
  15442. showMonthPicker : function(){
  15443. this.createMonthPicker();
  15444. var size = this.el.getSize();
  15445. this.monthPicker.setSize(size);
  15446. this.monthPicker.child('table').setSize(size);
  15447. this.mpSelMonth = (this.activeDate || this.value).getMonth();
  15448. this.updateMPMonth(this.mpSelMonth);
  15449. this.mpSelYear = (this.activeDate || this.value).getFullYear();
  15450. this.updateMPYear(this.mpSelYear);
  15451. this.monthPicker.slideIn('t', {duration:.2});
  15452. },
  15453. // private
  15454. updateMPYear : function(y){
  15455. this.mpyear = y;
  15456. var ys = this.mpYears.elements;
  15457. for(var i = 1; i <= 10; i++){
  15458. var td = ys[i-1], y2;
  15459. if((i%2) == 0){
  15460. y2 = y + Math.round(i * .5);
  15461. td.firstChild.innerHTML = y2;
  15462. td.xyear = y2;
  15463. }else{
  15464. y2 = y - (5-Math.round(i * .5));
  15465. td.firstChild.innerHTML = y2;
  15466. td.xyear = y2;
  15467. }
  15468. this.mpYears.item(i-1)[y2 == this.mpSelYear ? 'addClass' : 'removeClass']('x-date-mp-sel');
  15469. }
  15470. },
  15471. // private
  15472. updateMPMonth : function(sm){
  15473. this.mpMonths.each(function(m, a, i){
  15474. m[m.dom.xmonth == sm ? 'addClass' : 'removeClass']('x-date-mp-sel');
  15475. });
  15476. },
  15477. // private
  15478. selectMPMonth: function(m){
  15479. },
  15480. // private
  15481. onMonthClick : function(e, t){
  15482. e.stopEvent();
  15483. var el = new Ext.Element(t), pn;
  15484. if(el.is('button.x-date-mp-cancel')){
  15485. this.hideMonthPicker();
  15486. }
  15487. else if(el.is('button.x-date-mp-ok')){
  15488. var d = new Date(this.mpSelYear, this.mpSelMonth, (this.activeDate || this.value).getDate());
  15489. if(d.getMonth() != this.mpSelMonth){
  15490. // "fix" the JS rolling date conversion if needed
  15491. d = new Date(this.mpSelYear, this.mpSelMonth, 1).getLastDateOfMonth();
  15492. }
  15493. this.update(d);
  15494. this.hideMonthPicker();
  15495. }
  15496. else if(pn = el.up('td.x-date-mp-month', 2)){
  15497. this.mpMonths.removeClass('x-date-mp-sel');
  15498. pn.addClass('x-date-mp-sel');
  15499. this.mpSelMonth = pn.dom.xmonth;
  15500. }
  15501. else if(pn = el.up('td.x-date-mp-year', 2)){
  15502. this.mpYears.removeClass('x-date-mp-sel');
  15503. pn.addClass('x-date-mp-sel');
  15504. this.mpSelYear = pn.dom.xyear;
  15505. }
  15506. else if(el.is('a.x-date-mp-prev')){
  15507. this.updateMPYear(this.mpyear-10);
  15508. }
  15509. else if(el.is('a.x-date-mp-next')){
  15510. this.updateMPYear(this.mpyear+10);
  15511. }
  15512. },
  15513. // private
  15514. onMonthDblClick : function(e, t){
  15515. e.stopEvent();
  15516. var el = new Ext.Element(t), pn;
  15517. if(pn = el.up('td.x-date-mp-month', 2)){
  15518. this.update(new Date(this.mpSelYear, pn.dom.xmonth, (this.activeDate || this.value).getDate()));
  15519. this.hideMonthPicker();
  15520. }
  15521. else if(pn = el.up('td.x-date-mp-year', 2)){
  15522. this.update(new Date(pn.dom.xyear, this.mpSelMonth, (this.activeDate || this.value).getDate()));
  15523. this.hideMonthPicker();
  15524. }
  15525. },
  15526. // private
  15527. hideMonthPicker : function(disableAnim){
  15528. if(this.monthPicker){
  15529. if(disableAnim === true){
  15530. this.monthPicker.hide();
  15531. }else{
  15532. this.monthPicker.slideOut('t', {duration:.2});
  15533. }
  15534. }
  15535. },
  15536. // private
  15537. showPrevMonth : function(e){
  15538. this.update(this.activeDate.add("mo", -1));
  15539. },
  15540. // private
  15541. showNextMonth : function(e){
  15542. this.update(this.activeDate.add("mo", 1));
  15543. },
  15544. // private
  15545. showPrevYear : function(){
  15546. this.update(this.activeDate.add("y", -1));
  15547. },
  15548. // private
  15549. showNextYear : function(){
  15550. this.update(this.activeDate.add("y", 1));
  15551. },
  15552. // private
  15553. handleMouseWheel : function(e){
  15554. var delta = e.getWheelDelta();
  15555. if(delta > 0){
  15556. this.showPrevMonth();
  15557. e.stopEvent();
  15558. } else if(delta < 0){
  15559. this.showNextMonth();
  15560. e.stopEvent();
  15561. }
  15562. },
  15563. // private
  15564. handleDateClick : function(e, t){
  15565. e.stopEvent();
  15566. if(t.dateValue && !Ext.fly(t.parentNode).hasClass("x-date-disabled")){
  15567. this.setValue(new Date(t.dateValue));
  15568. this.fireEvent("select", this, this.value);
  15569. }
  15570. },
  15571. // private
  15572. selectToday : function(){
  15573. if(this.todayBtn && !this.todayBtn.disabled){
  15574. this.setValue(new Date().clearTime());
  15575. this.fireEvent("select", this, this.value);
  15576. }
  15577. },
  15578. // private
  15579. update : function(date, forceRefresh){
  15580. var vd = this.activeDate;
  15581. this.activeDate = date;
  15582. if(!forceRefresh && vd && this.el){
  15583. var t = date.getTime();
  15584. if(vd.getMonth() == date.getMonth() && vd.getFullYear() == date.getFullYear()){
  15585. this.cells.removeClass("x-date-selected");
  15586. this.cells.each(function(c){
  15587. if(c.dom.firstChild.dateValue == t){
  15588. c.addClass("x-date-selected");
  15589. setTimeout(function(){
  15590. try{c.dom.firstChild.focus();}catch(e){}
  15591. }, 50);
  15592. return false;
  15593. }
  15594. });
  15595. return;
  15596. }
  15597. }
  15598. var days = date.getDaysInMonth();
  15599. var firstOfMonth = date.getFirstDateOfMonth();
  15600. var startingPos = firstOfMonth.getDay()-this.startDay;
  15601. if(startingPos <= this.startDay){
  15602. startingPos += 7;
  15603. }
  15604. var pm = date.add("mo", -1);
  15605. var prevStart = pm.getDaysInMonth()-startingPos;
  15606. var cells = this.cells.elements;
  15607. var textEls = this.textNodes;
  15608. days += startingPos;
  15609. // convert everything to numbers so it's fast
  15610. var day = 86400000;
  15611. var d = (new Date(pm.getFullYear(), pm.getMonth(), prevStart)).clearTime();
  15612. var today = new Date().clearTime().getTime();
  15613. var sel = date.clearTime().getTime();
  15614. var min = this.minDate ? this.minDate.clearTime() : Number.NEGATIVE_INFINITY;
  15615. var max = this.maxDate ? this.maxDate.clearTime() : Number.POSITIVE_INFINITY;
  15616. var ddMatch = this.disabledDatesRE;
  15617. var ddText = this.disabledDatesText;
  15618. var ddays = this.disabledDays ? this.disabledDays.join("") : false;
  15619. var ddaysText = this.disabledDaysText;
  15620. var format = this.format;
  15621. if(this.showToday){
  15622. var td = new Date().clearTime();
  15623. var disable = (td < min || td > max ||
  15624. (ddMatch && format && ddMatch.test(td.dateFormat(format))) ||
  15625. (ddays && ddays.indexOf(td.getDay()) != -1));
  15626. this.todayBtn.setDisabled(disable);
  15627. this.todayKeyListener[disable ? 'disable' : 'enable']();
  15628. }
  15629. var setCellClass = function(cal, cell){
  15630. cell.title = "";
  15631. var t = d.getTime();
  15632. cell.firstChild.dateValue = t;
  15633. if(t == today){
  15634. cell.className += " x-date-today";
  15635. cell.title = cal.todayText;
  15636. }
  15637. if(t == sel){
  15638. cell.className += " x-date-selected";
  15639. setTimeout(function(){
  15640. try{cell.firstChild.focus();}catch(e){}
  15641. }, 50);
  15642. }
  15643. // disabling
  15644. if(t < min) {
  15645. cell.className = " x-date-disabled";
  15646. cell.title = cal.minText;
  15647. return;
  15648. }
  15649. if(t > max) {
  15650. cell.className = " x-date-disabled";
  15651. cell.title = cal.maxText;
  15652. return;
  15653. }
  15654. if(ddays){
  15655. if(ddays.indexOf(d.getDay()) != -1){
  15656. cell.title = ddaysText;
  15657. cell.className = " x-date-disabled";
  15658. }
  15659. }
  15660. if(ddMatch && format){
  15661. var fvalue = d.dateFormat(format);
  15662. if(ddMatch.test(fvalue)){
  15663. cell.title = ddText.replace("%0", fvalue);
  15664. cell.className = " x-date-disabled";
  15665. }
  15666. }
  15667. };
  15668. var i = 0;
  15669. for(; i < startingPos; i++) {
  15670. textEls[i].innerHTML = (++prevStart);
  15671. d.setDate(d.getDate()+1);
  15672. cells[i].className = "x-date-prevday";
  15673. setCellClass(this, cells[i]);
  15674. }
  15675. for(; i < days; i++){
  15676. var intDay = i - startingPos + 1;
  15677. textEls[i].innerHTML = (intDay);
  15678. d.setDate(d.getDate()+1);
  15679. cells[i].className = "x-date-active";
  15680. setCellClass(this, cells[i]);
  15681. }
  15682. var extraDays = 0;
  15683. for(; i < 42; i++) {
  15684. textEls[i].innerHTML = (++extraDays);
  15685. d.setDate(d.getDate()+1);
  15686. cells[i].className = "x-date-nextday";
  15687. setCellClass(this, cells[i]);
  15688. }
  15689. this.mbtn.setText(this.monthNames[date.getMonth()] + " " + date.getFullYear());
  15690. if(!this.internalRender){
  15691. var main = this.el.dom.firstChild;
  15692. var w = main.offsetWidth;
  15693. this.el.setWidth(w + this.el.getBorderWidth("lr"));
  15694. Ext.fly(main).setWidth(w);
  15695. this.internalRender = true;
  15696. // opera does not respect the auto grow header center column
  15697. // then, after it gets a width opera refuses to recalculate
  15698. // without a second pass
  15699. if(Ext.isOpera && !this.secondPass){
  15700. main.rows[0].cells[1].style.width = (w - (main.rows[0].cells[0].offsetWidth+main.rows[0].cells[2].offsetWidth)) + "px";
  15701. this.secondPass = true;
  15702. this.update.defer(10, this, [date]);
  15703. }
  15704. }
  15705. },
  15706. // private
  15707. beforeDestroy : function() {
  15708. if(this.rendered){
  15709. Ext.destroy(
  15710. this.leftClickRpt,
  15711. this.rightClickRpt,
  15712. this.monthPicker,
  15713. this.eventEl,
  15714. this.mbtn,
  15715. this.todayBtn
  15716. );
  15717. }
  15718. }
  15719. });
  15720. Ext.reg('datepicker', Ext.DatePicker);
  15721. Ext.TabPanel = Ext.extend(Ext.Panel, {
  15722. monitorResize : true,
  15723. deferredRender : true,
  15724. tabWidth: 120,
  15725. minTabWidth: 30,
  15726. resizeTabs:false,
  15727. enableTabScroll: false,
  15728. scrollIncrement : 0,
  15729. scrollRepeatInterval : 400,
  15730. scrollDuration : .35,
  15731. animScroll : true,
  15732. tabPosition: 'top',
  15733. baseCls: 'x-tab-panel',
  15734. autoTabs : false,
  15735. autoTabSelector:'div.x-tab',
  15736. activeTab : null,
  15737. tabMargin : 2,
  15738. plain: false,
  15739. wheelIncrement : 20,
  15740. idDelimiter : '__',
  15741. // private
  15742. itemCls : 'x-tab-item',
  15743. // private config overrides
  15744. elements: 'body',
  15745. headerAsText: false,
  15746. frame: false,
  15747. hideBorders:true,
  15748. // private
  15749. initComponent : function(){
  15750. this.frame = false;
  15751. Ext.TabPanel.superclass.initComponent.call(this);
  15752. this.addEvents(
  15753. 'beforetabchange',
  15754. 'tabchange',
  15755. 'contextmenu'
  15756. );
  15757. this.setLayout(new Ext.layout.CardLayout({
  15758. deferredRender: this.deferredRender
  15759. }));
  15760. if(this.tabPosition == 'top'){
  15761. this.elements += ',header';
  15762. this.stripTarget = 'header';
  15763. }else {
  15764. this.elements += ',footer';
  15765. this.stripTarget = 'footer';
  15766. }
  15767. if(!this.stack){
  15768. this.stack = Ext.TabPanel.AccessStack();
  15769. }
  15770. this.initItems();
  15771. },
  15772. // private
  15773. render : function(){
  15774. Ext.TabPanel.superclass.render.apply(this, arguments);
  15775. if(this.activeTab !== undefined){
  15776. var item = this.activeTab;
  15777. delete this.activeTab;
  15778. this.setActiveTab(item);
  15779. }
  15780. },
  15781. // private
  15782. onRender : function(ct, position){
  15783. Ext.TabPanel.superclass.onRender.call(this, ct, position);
  15784. if(this.plain){
  15785. var pos = this.tabPosition == 'top' ? 'header' : 'footer';
  15786. this[pos].addClass('x-tab-panel-'+pos+'-plain');
  15787. }
  15788. var st = this[this.stripTarget];
  15789. this.stripWrap = st.createChild({cls:'x-tab-strip-wrap', cn:{
  15790. tag:'ul', cls:'x-tab-strip x-tab-strip-'+this.tabPosition}});
  15791. var beforeEl = (this.tabPosition=='bottom' ? this.stripWrap : null);
  15792. this.stripSpacer = st.createChild({cls:'x-tab-strip-spacer'}, beforeEl);
  15793. this.strip = new Ext.Element(this.stripWrap.dom.firstChild);
  15794. this.edge = this.strip.createChild({tag:'li', cls:'x-tab-edge'});
  15795. this.strip.createChild({cls:'x-clear'});
  15796. this.body.addClass('x-tab-panel-body-'+this.tabPosition);
  15797. if(!this.itemTpl){
  15798. var tt = new Ext.Template(
  15799. '<li class="{cls}" id="{id}"><a class="x-tab-strip-close" onclick="return false;"></a>',
  15800. '<a class="x-tab-right" href="#" onclick="return false;"><em class="x-tab-left">',
  15801. '<span class="x-tab-strip-inner"><span class="x-tab-strip-text {iconCls}">{text}</span></span>',
  15802. '</em></a></li>'
  15803. );
  15804. tt.disableFormats = true;
  15805. tt.compile();
  15806. Ext.TabPanel.prototype.itemTpl = tt;
  15807. }
  15808. this.items.each(this.initTab, this);
  15809. },
  15810. // private
  15811. afterRender : function(){
  15812. Ext.TabPanel.superclass.afterRender.call(this);
  15813. if(this.autoTabs){
  15814. this.readTabs(false);
  15815. }
  15816. },
  15817. // private
  15818. initEvents : function(){
  15819. Ext.TabPanel.superclass.initEvents.call(this);
  15820. this.on('add', this.onAdd, this);
  15821. this.on('remove', this.onRemove, this);
  15822. this.strip.on('mousedown', this.onStripMouseDown, this);
  15823. this.strip.on('contextmenu', this.onStripContextMenu, this);
  15824. if(this.enableTabScroll){
  15825. this.strip.on('mousewheel', this.onWheel, this);
  15826. }
  15827. },
  15828. // private
  15829. findTargets : function(e){
  15830. var item = null;
  15831. var itemEl = e.getTarget('li', this.strip);
  15832. if(itemEl){
  15833. item = this.getComponent(itemEl.id.split(this.idDelimiter)[1]);
  15834. if(item.disabled){
  15835. return {
  15836. close : null,
  15837. item : null,
  15838. el : null
  15839. };
  15840. }
  15841. }
  15842. return {
  15843. close : e.getTarget('.x-tab-strip-close', this.strip),
  15844. item : item,
  15845. el : itemEl
  15846. };
  15847. },
  15848. // private
  15849. onStripMouseDown : function(e){
  15850. if(e.button != 0){
  15851. return;
  15852. }
  15853. e.preventDefault();
  15854. var t = this.findTargets(e);
  15855. if(t.close){
  15856. this.remove(t.item);
  15857. return;
  15858. }
  15859. if(t.item && t.item != this.activeTab){
  15860. this.setActiveTab(t.item);
  15861. }
  15862. },
  15863. // private
  15864. onStripContextMenu : function(e){
  15865. e.preventDefault();
  15866. var t = this.findTargets(e);
  15867. if(t.item){
  15868. this.fireEvent('contextmenu', this, t.item, e);
  15869. }
  15870. },
  15871. readTabs : function(removeExisting){
  15872. if(removeExisting === true){
  15873. this.items.each(function(item){
  15874. this.remove(item);
  15875. }, this);
  15876. }
  15877. var tabs = this.el.query(this.autoTabSelector);
  15878. for(var i = 0, len = tabs.length; i < len; i++){
  15879. var tab = tabs[i];
  15880. var title = tab.getAttribute('title');
  15881. tab.removeAttribute('title');
  15882. this.add({
  15883. title: title,
  15884. el: tab
  15885. });
  15886. }
  15887. },
  15888. // private
  15889. initTab : function(item, index){
  15890. var before = this.strip.dom.childNodes[index];
  15891. var cls = item.closable ? 'x-tab-strip-closable' : '';
  15892. if(item.disabled){
  15893. cls += ' x-item-disabled';
  15894. }
  15895. if(item.iconCls){
  15896. cls += ' x-tab-with-icon';
  15897. }
  15898. if(item.tabCls){
  15899. cls += ' ' + item.tabCls;
  15900. }
  15901. var p = {
  15902. id: this.id + this.idDelimiter + item.getItemId(),
  15903. text: item.title,
  15904. cls: cls,
  15905. iconCls: item.iconCls || ''
  15906. };
  15907. var el = before ?
  15908. this.itemTpl.insertBefore(before, p) :
  15909. this.itemTpl.append(this.strip, p);
  15910. Ext.fly(el).addClassOnOver('x-tab-strip-over');
  15911. if(item.tabTip){
  15912. Ext.fly(el).child('span.x-tab-strip-text', true).qtip = item.tabTip;
  15913. }
  15914. item.tabEl = el;
  15915. item.on('disable', this.onItemDisabled, this);
  15916. item.on('enable', this.onItemEnabled, this);
  15917. item.on('titlechange', this.onItemTitleChanged, this);
  15918. item.on('iconchange', this.onItemIconChanged, this);
  15919. item.on('beforeshow', this.onBeforeShowItem, this);
  15920. },
  15921. // private
  15922. onAdd : function(tp, item, index){
  15923. this.initTab(item, index);
  15924. if(this.items.getCount() == 1){
  15925. this.syncSize();
  15926. }
  15927. this.delegateUpdates();
  15928. },
  15929. // private
  15930. onBeforeAdd : function(item){
  15931. var existing = item.events ? (this.items.containsKey(item.getItemId()) ? item : null) : this.items.get(item);
  15932. if(existing){
  15933. this.setActiveTab(item);
  15934. return false;
  15935. }
  15936. Ext.TabPanel.superclass.onBeforeAdd.apply(this, arguments);
  15937. var es = item.elements;
  15938. item.elements = es ? es.replace(',header', '') : es;
  15939. item.border = (item.border === true);
  15940. },
  15941. // private
  15942. onRemove : function(tp, item){
  15943. Ext.destroy(Ext.get(this.getTabEl(item)));
  15944. this.stack.remove(item);
  15945. item.un('disable', this.onItemDisabled, this);
  15946. item.un('enable', this.onItemEnabled, this);
  15947. item.un('titlechange', this.onItemTitleChanged, this);
  15948. item.un('iconchange', this.onItemIconChanged, this);
  15949. item.un('beforeshow', this.onBeforeShowItem, this);
  15950. if(item == this.activeTab){
  15951. var next = this.stack.next();
  15952. if(next){
  15953. this.setActiveTab(next);
  15954. }else if(this.items.getCount() > 0){
  15955. this.setActiveTab(0);
  15956. }else{
  15957. this.activeTab = null;
  15958. }
  15959. }
  15960. this.delegateUpdates();
  15961. },
  15962. // private
  15963. onBeforeShowItem : function(item){
  15964. if(item != this.activeTab){
  15965. this.setActiveTab(item);
  15966. return false;
  15967. }
  15968. },
  15969. // private
  15970. onItemDisabled : function(item){
  15971. var el = this.getTabEl(item);
  15972. if(el){
  15973. Ext.fly(el).addClass('x-item-disabled');
  15974. }
  15975. this.stack.remove(item);
  15976. },
  15977. // private
  15978. onItemEnabled : function(item){
  15979. var el = this.getTabEl(item);
  15980. if(el){
  15981. Ext.fly(el).removeClass('x-item-disabled');
  15982. }
  15983. },
  15984. // private
  15985. onItemTitleChanged : function(item){
  15986. var el = this.getTabEl(item);
  15987. if(el){
  15988. Ext.fly(el).child('span.x-tab-strip-text', true).innerHTML = item.title;
  15989. }
  15990. },
  15991. //private
  15992. onItemIconChanged: function(item, iconCls, oldCls){
  15993. var el = this.getTabEl(item);
  15994. if(el){
  15995. Ext.fly(el).child('span.x-tab-strip-text').replaceClass(oldCls, iconCls);
  15996. }
  15997. },
  15998. getTabEl : function(item){
  15999. var itemId = (typeof item === 'number')?this.items.items[item].getItemId() : item.getItemId();
  16000. return document.getElementById(this.id+this.idDelimiter+itemId);
  16001. },
  16002. // private
  16003. onResize : function(){
  16004. Ext.TabPanel.superclass.onResize.apply(this, arguments);
  16005. this.delegateUpdates();
  16006. },
  16007. beginUpdate : function(){
  16008. this.suspendUpdates = true;
  16009. },
  16010. endUpdate : function(){
  16011. this.suspendUpdates = false;
  16012. this.delegateUpdates();
  16013. },
  16014. hideTabStripItem : function(item){
  16015. item = this.getComponent(item);
  16016. var el = this.getTabEl(item);
  16017. if(el){
  16018. el.style.display = 'none';
  16019. this.delegateUpdates();
  16020. }
  16021. this.stack.remove(item);
  16022. },
  16023. unhideTabStripItem : function(item){
  16024. item = this.getComponent(item);
  16025. var el = this.getTabEl(item);
  16026. if(el){
  16027. el.style.display = '';
  16028. this.delegateUpdates();
  16029. }
  16030. },
  16031. // private
  16032. delegateUpdates : function(){
  16033. if(this.suspendUpdates){
  16034. return;
  16035. }
  16036. if(this.resizeTabs && this.rendered){
  16037. this.autoSizeTabs();
  16038. }
  16039. if(this.enableTabScroll && this.rendered){
  16040. this.autoScrollTabs();
  16041. }
  16042. },
  16043. // private
  16044. autoSizeTabs : function(){
  16045. var count = this.items.length;
  16046. var ce = this.tabPosition != 'bottom' ? 'header' : 'footer';
  16047. var ow = this[ce].dom.offsetWidth;
  16048. var aw = this[ce].dom.clientWidth;
  16049. if(!this.resizeTabs || count < 1 || !aw){ // !aw for display:none
  16050. return;
  16051. }
  16052. var each = Math.max(Math.min(Math.floor((aw-4) / count) - this.tabMargin, this.tabWidth), this.minTabWidth); // -4 for float errors in IE
  16053. this.lastTabWidth = each;
  16054. var lis = this.stripWrap.dom.getElementsByTagName('li');
  16055. for(var i = 0, len = lis.length-1; i < len; i++) { // -1 for the "edge" li
  16056. var li = lis[i];
  16057. var inner = li.childNodes[1].firstChild.firstChild;
  16058. var tw = li.offsetWidth;
  16059. var iw = inner.offsetWidth;
  16060. inner.style.width = (each - (tw-iw)) + 'px';
  16061. }
  16062. },
  16063. // private
  16064. adjustBodyWidth : function(w){
  16065. if(this.header){
  16066. this.header.setWidth(w);
  16067. }
  16068. if(this.footer){
  16069. this.footer.setWidth(w);
  16070. }
  16071. return w;
  16072. },
  16073. setActiveTab : function(item){
  16074. item = this.getComponent(item);
  16075. if(!item || this.fireEvent('beforetabchange', this, item, this.activeTab) === false){
  16076. return;
  16077. }
  16078. if(!this.rendered){
  16079. this.activeTab = item;
  16080. return;
  16081. }
  16082. if(this.activeTab != item){
  16083. if(this.activeTab){
  16084. var oldEl = this.getTabEl(this.activeTab);
  16085. if(oldEl){
  16086. Ext.fly(oldEl).removeClass('x-tab-strip-active');
  16087. }
  16088. this.activeTab.fireEvent('deactivate', this.activeTab);
  16089. }
  16090. var el = this.getTabEl(item);
  16091. Ext.fly(el).addClass('x-tab-strip-active');
  16092. this.activeTab = item;
  16093. this.stack.add(item);
  16094. this.layout.setActiveItem(item);
  16095. if(this.layoutOnTabChange && item.doLayout){
  16096. item.doLayout();
  16097. }
  16098. if(this.scrolling){
  16099. this.scrollToTab(item, this.animScroll);
  16100. }
  16101. item.fireEvent('activate', item);
  16102. this.fireEvent('tabchange', this, item);
  16103. }
  16104. },
  16105. getActiveTab : function(){
  16106. return this.activeTab || null;
  16107. },
  16108. getItem : function(item){
  16109. return this.getComponent(item);
  16110. },
  16111. // private
  16112. autoScrollTabs : function(){
  16113. this.pos = this.tabPosition=='bottom' ? this.footer : this.header;
  16114. var count = this.items.length;
  16115. var ow = this.pos.dom.offsetWidth;
  16116. var tw = this.pos.dom.clientWidth;
  16117. var wrap = this.stripWrap;
  16118. var wd = wrap.dom;
  16119. var cw = wd.offsetWidth;
  16120. var pos = this.getScrollPos();
  16121. var l = this.edge.getOffsetsTo(this.stripWrap)[0] + pos;
  16122. if(!this.enableTabScroll || count < 1 || cw < 20){ // 20 to prevent display:none issues
  16123. return;
  16124. }
  16125. if(l <= tw){
  16126. wd.scrollLeft = 0;
  16127. wrap.setWidth(tw);
  16128. if(this.scrolling){
  16129. this.scrolling = false;
  16130. this.pos.removeClass('x-tab-scrolling');
  16131. this.scrollLeft.hide();
  16132. this.scrollRight.hide();
  16133. if(Ext.isAir || Ext.isSafari){
  16134. wd.style.marginLeft = '';
  16135. wd.style.marginRight = '';
  16136. }
  16137. }
  16138. }else{
  16139. if(!this.scrolling){
  16140. this.pos.addClass('x-tab-scrolling');
  16141. if(Ext.isAir || Ext.isSafari){
  16142. wd.style.marginLeft = '18px';
  16143. wd.style.marginRight = '18px';
  16144. }
  16145. }
  16146. tw -= wrap.getMargins('lr');
  16147. wrap.setWidth(tw > 20 ? tw : 20);
  16148. if(!this.scrolling){
  16149. if(!this.scrollLeft){
  16150. this.createScrollers();
  16151. }else{
  16152. this.scrollLeft.show();
  16153. this.scrollRight.show();
  16154. }
  16155. }
  16156. this.scrolling = true;
  16157. if(pos > (l-tw)){ // ensure it stays within bounds
  16158. wd.scrollLeft = l-tw;
  16159. }else{ // otherwise, make sure the active tab is still visible
  16160. this.scrollToTab(this.activeTab, false);
  16161. }
  16162. this.updateScrollButtons();
  16163. }
  16164. },
  16165. // private
  16166. createScrollers : function(){
  16167. this.pos.addClass('x-tab-scrolling-' + this.tabPosition);
  16168. var h = this.stripWrap.dom.offsetHeight;
  16169. // left
  16170. var sl = this.pos.insertFirst({
  16171. cls:'x-tab-scroller-left'
  16172. });
  16173. sl.setHeight(h);
  16174. sl.addClassOnOver('x-tab-scroller-left-over');
  16175. this.leftRepeater = new Ext.util.ClickRepeater(sl, {
  16176. interval : this.scrollRepeatInterval,
  16177. handler: this.onScrollLeft,
  16178. scope: this
  16179. });
  16180. this.scrollLeft = sl;
  16181. // right
  16182. var sr = this.pos.insertFirst({
  16183. cls:'x-tab-scroller-right'
  16184. });
  16185. sr.setHeight(h);
  16186. sr.addClassOnOver('x-tab-scroller-right-over');
  16187. this.rightRepeater = new Ext.util.ClickRepeater(sr, {
  16188. interval : this.scrollRepeatInterval,
  16189. handler: this.onScrollRight,
  16190. scope: this
  16191. });
  16192. this.scrollRight = sr;
  16193. },
  16194. // private
  16195. getScrollWidth : function(){
  16196. return this.edge.getOffsetsTo(this.stripWrap)[0] + this.getScrollPos();
  16197. },
  16198. // private
  16199. getScrollPos : function(){
  16200. return parseInt(this.stripWrap.dom.scrollLeft, 10) || 0;
  16201. },
  16202. // private
  16203. getScrollArea : function(){
  16204. return parseInt(this.stripWrap.dom.clientWidth, 10) || 0;
  16205. },
  16206. // private
  16207. getScrollAnim : function(){
  16208. return {duration:this.scrollDuration, callback: this.updateScrollButtons, scope: this};
  16209. },
  16210. // private
  16211. getScrollIncrement : function(){
  16212. return this.scrollIncrement || (this.resizeTabs ? this.lastTabWidth+2 : 100);
  16213. },
  16214. scrollToTab : function(item, animate){
  16215. if(!item){ return; }
  16216. var el = this.getTabEl(item);
  16217. var pos = this.getScrollPos(), area = this.getScrollArea();
  16218. var left = Ext.fly(el).getOffsetsTo(this.stripWrap)[0] + pos;
  16219. var right = left + el.offsetWidth;
  16220. if(left < pos){
  16221. this.scrollTo(left, animate);
  16222. }else if(right > (pos + area)){
  16223. this.scrollTo(right - area, animate);
  16224. }
  16225. },
  16226. // private
  16227. scrollTo : function(pos, animate){
  16228. this.stripWrap.scrollTo('left', pos, animate ? this.getScrollAnim() : false);
  16229. if(!animate){
  16230. this.updateScrollButtons();
  16231. }
  16232. },
  16233. onWheel : function(e){
  16234. var d = e.getWheelDelta()*this.wheelIncrement*-1;
  16235. e.stopEvent();
  16236. var pos = this.getScrollPos();
  16237. var newpos = pos + d;
  16238. var sw = this.getScrollWidth()-this.getScrollArea();
  16239. var s = Math.max(0, Math.min(sw, newpos));
  16240. if(s != pos){
  16241. this.scrollTo(s, false);
  16242. }
  16243. },
  16244. // private
  16245. onScrollRight : function(){
  16246. var sw = this.getScrollWidth()-this.getScrollArea();
  16247. var pos = this.getScrollPos();
  16248. var s = Math.min(sw, pos + this.getScrollIncrement());
  16249. if(s != pos){
  16250. this.scrollTo(s, this.animScroll);
  16251. }
  16252. },
  16253. // private
  16254. onScrollLeft : function(){
  16255. var pos = this.getScrollPos();
  16256. var s = Math.max(0, pos - this.getScrollIncrement());
  16257. if(s != pos){
  16258. this.scrollTo(s, this.animScroll);
  16259. }
  16260. },
  16261. // private
  16262. updateScrollButtons : function(){
  16263. var pos = this.getScrollPos();
  16264. this.scrollLeft[pos == 0 ? 'addClass' : 'removeClass']('x-tab-scroller-left-disabled');
  16265. this.scrollRight[pos >= (this.getScrollWidth()-this.getScrollArea()) ? 'addClass' : 'removeClass']('x-tab-scroller-right-disabled');
  16266. },
  16267. // private
  16268. beforeDestroy : function() {
  16269. if(this.items){
  16270. this.items.each(function(item){
  16271. if(item && item.tabEl){
  16272. Ext.get(item.tabEl).removeAllListeners();
  16273. item.tabEl = null;
  16274. }
  16275. }, this);
  16276. }
  16277. if(this.strip){
  16278. this.strip.removeAllListeners();
  16279. }
  16280. Ext.TabPanel.superclass.beforeDestroy.apply(this);
  16281. }
  16282. });
  16283. Ext.reg('tabpanel', Ext.TabPanel);
  16284. Ext.TabPanel.prototype.activate = Ext.TabPanel.prototype.setActiveTab;
  16285. // private utility class used by TabPanel
  16286. Ext.TabPanel.AccessStack = function(){
  16287. var items = [];
  16288. return {
  16289. add : function(item){
  16290. items.push(item);
  16291. if(items.length > 10){
  16292. items.shift();
  16293. }
  16294. },
  16295. remove : function(item){
  16296. var s = [];
  16297. for(var i = 0, len = items.length; i < len; i++) {
  16298. if(items[i] != item){
  16299. s.push(items[i]);
  16300. }
  16301. }
  16302. items = s;
  16303. },
  16304. next : function(){
  16305. return items.pop();
  16306. }
  16307. };
  16308. };
  16309. Ext.Button = Ext.extend(Ext.Component, {
  16310. hidden : false,
  16311. disabled : false,
  16312. pressed : false,
  16313. enableToggle: false,
  16314. menuAlign : "tl-bl?",
  16315. type : 'button',
  16316. // private
  16317. menuClassTarget: 'tr',
  16318. clickEvent : 'click',
  16319. handleMouseEvents : true,
  16320. tooltipType : 'qtip',
  16321. buttonSelector : "button:first-child",
  16322. initComponent : function(){
  16323. Ext.Button.superclass.initComponent.call(this);
  16324. this.addEvents(
  16325. "click",
  16326. "toggle",
  16327. 'mouseover',
  16328. 'mouseout',
  16329. 'menushow',
  16330. 'menuhide',
  16331. 'menutriggerover',
  16332. 'menutriggerout'
  16333. );
  16334. if(this.menu){
  16335. this.menu = Ext.menu.MenuMgr.get(this.menu);
  16336. }
  16337. if(typeof this.toggleGroup === 'string'){
  16338. this.enableToggle = true;
  16339. }
  16340. },
  16341. // private
  16342. onRender : function(ct, position){
  16343. if(!this.template){
  16344. if(!Ext.Button.buttonTemplate){
  16345. // hideous table template
  16346. Ext.Button.buttonTemplate = new Ext.Template(
  16347. '<table border="0" cellpadding="0" cellspacing="0" class="x-btn-wrap"><tbody><tr>',
  16348. '<td class="x-btn-left"><i>&#160;</i></td><td class="x-btn-center"><em unselectable="on"><button class="x-btn-text" type="{1}">{0}</button></em></td><td class="x-btn-right"><i>&#160;</i></td>',
  16349. "</tr></tbody></table>");
  16350. }
  16351. this.template = Ext.Button.buttonTemplate;
  16352. }
  16353. var btn, targs = [this.text || '&#160;', this.type];
  16354. if(position){
  16355. btn = this.template.insertBefore(position, targs, true);
  16356. }else{
  16357. btn = this.template.append(ct, targs, true);
  16358. }
  16359. var btnEl = btn.child(this.buttonSelector);
  16360. btnEl.on('focus', this.onFocus, this);
  16361. btnEl.on('blur', this.onBlur, this);
  16362. this.initButtonEl(btn, btnEl);
  16363. if(this.menu){
  16364. this.el.child(this.menuClassTarget).addClass("x-btn-with-menu");
  16365. }
  16366. Ext.ButtonToggleMgr.register(this);
  16367. },
  16368. // private
  16369. initButtonEl : function(btn, btnEl){
  16370. this.el = btn;
  16371. btn.addClass("x-btn");
  16372. if(this.id){
  16373. this.el.dom.id = this.el.id = this.id;
  16374. }
  16375. if(this.icon){
  16376. btnEl.setStyle('background-image', 'url(' +this.icon +')');
  16377. }
  16378. if(this.iconCls){
  16379. btnEl.addClass(this.iconCls);
  16380. if(!this.cls){
  16381. btn.addClass(this.text ? 'x-btn-text-icon' : 'x-btn-icon');
  16382. }
  16383. }
  16384. if(this.tabIndex !== undefined){
  16385. btnEl.dom.tabIndex = this.tabIndex;
  16386. }
  16387. if(this.tooltip){
  16388. if(typeof this.tooltip == 'object'){
  16389. Ext.QuickTips.register(Ext.apply({
  16390. target: btnEl.id
  16391. }, this.tooltip));
  16392. } else {
  16393. btnEl.dom[this.tooltipType] = this.tooltip;
  16394. }
  16395. }
  16396. if(this.pressed){
  16397. this.el.addClass("x-btn-pressed");
  16398. }
  16399. if(this.handleMouseEvents){
  16400. btn.on("mouseover", this.onMouseOver, this);
  16401. // new functionality for monitoring on the document level
  16402. //btn.on("mouseout", this.onMouseOut, this);
  16403. btn.on("mousedown", this.onMouseDown, this);
  16404. }
  16405. if(this.menu){
  16406. this.menu.on("show", this.onMenuShow, this);
  16407. this.menu.on("hide", this.onMenuHide, this);
  16408. }
  16409. if(this.repeat){
  16410. var repeater = new Ext.util.ClickRepeater(btn,
  16411. typeof this.repeat == "object" ? this.repeat : {}
  16412. );
  16413. repeater.on("click", this.onClick, this);
  16414. }
  16415. btn.on(this.clickEvent, this.onClick, this);
  16416. },
  16417. // private
  16418. afterRender : function(){
  16419. Ext.Button.superclass.afterRender.call(this);
  16420. if(Ext.isIE6){
  16421. this.autoWidth.defer(1, this);
  16422. }else{
  16423. this.autoWidth();
  16424. }
  16425. },
  16426. setIconClass : function(cls){
  16427. if(this.el){
  16428. this.el.child(this.buttonSelector).replaceClass(this.iconCls, cls);
  16429. }
  16430. this.iconCls = cls;
  16431. },
  16432. // private
  16433. beforeDestroy: function(){
  16434. if(this.rendered){
  16435. var btnEl = this.el.child(this.buttonSelector);
  16436. if(btnEl){
  16437. if(this.tooltip){
  16438. Ext.QuickTips.unregister(btnEl);
  16439. }
  16440. btnEl.removeAllListeners();
  16441. }
  16442. }
  16443. if(this.menu){
  16444. Ext.destroy(this.menu);
  16445. }
  16446. },
  16447. // private
  16448. onDestroy : function(){
  16449. if(this.rendered){
  16450. Ext.ButtonToggleMgr.unregister(this);
  16451. }
  16452. },
  16453. // private
  16454. autoWidth : function(){
  16455. if(this.el){
  16456. this.el.setWidth("auto");
  16457. if(Ext.isIE7 && Ext.isStrict){
  16458. var ib = this.el.child(this.buttonSelector);
  16459. if(ib && ib.getWidth() > 20){
  16460. ib.clip();
  16461. ib.setWidth(Ext.util.TextMetrics.measure(ib, this.text).width+ib.getFrameWidth('lr'));
  16462. }
  16463. }
  16464. if(this.minWidth){
  16465. if(this.el.getWidth() < this.minWidth){
  16466. this.el.setWidth(this.minWidth);
  16467. }
  16468. }
  16469. }
  16470. },
  16471. setHandler : function(handler, scope){
  16472. this.handler = handler;
  16473. this.scope = scope;
  16474. },
  16475. setText : function(text){
  16476. this.text = text;
  16477. if(this.el){
  16478. this.el.child("td.x-btn-center " + this.buttonSelector).update(text);
  16479. }
  16480. this.autoWidth();
  16481. },
  16482. getText : function(){
  16483. return this.text;
  16484. },
  16485. toggle : function(state){
  16486. state = state === undefined ? !this.pressed : state;
  16487. if(state != this.pressed){
  16488. if(state){
  16489. this.el.addClass("x-btn-pressed");
  16490. this.pressed = true;
  16491. this.fireEvent("toggle", this, true);
  16492. }else{
  16493. this.el.removeClass("x-btn-pressed");
  16494. this.pressed = false;
  16495. this.fireEvent("toggle", this, false);
  16496. }
  16497. if(this.toggleHandler){
  16498. this.toggleHandler.call(this.scope || this, this, state);
  16499. }
  16500. }
  16501. },
  16502. focus : function(){
  16503. this.el.child(this.buttonSelector).focus();
  16504. },
  16505. // private
  16506. onDisable : function(){
  16507. if(this.el){
  16508. if(!Ext.isIE6 || !this.text){
  16509. this.el.addClass(this.disabledClass);
  16510. }
  16511. this.el.dom.disabled = true;
  16512. }
  16513. this.disabled = true;
  16514. },
  16515. // private
  16516. onEnable : function(){
  16517. if(this.el){
  16518. if(!Ext.isIE6 || !this.text){
  16519. this.el.removeClass(this.disabledClass);
  16520. }
  16521. this.el.dom.disabled = false;
  16522. }
  16523. this.disabled = false;
  16524. },
  16525. showMenu : function(){
  16526. if(this.menu){
  16527. this.menu.show(this.el, this.menuAlign);
  16528. }
  16529. return this;
  16530. },
  16531. hideMenu : function(){
  16532. if(this.menu){
  16533. this.menu.hide();
  16534. }
  16535. return this;
  16536. },
  16537. hasVisibleMenu : function(){
  16538. return this.menu && this.menu.isVisible();
  16539. },
  16540. // private
  16541. onClick : function(e){
  16542. if(e){
  16543. e.preventDefault();
  16544. }
  16545. if(e.button != 0){
  16546. return;
  16547. }
  16548. if(!this.disabled){
  16549. if(this.enableToggle && (this.allowDepress !== false || !this.pressed)){
  16550. this.toggle();
  16551. }
  16552. if(this.menu && !this.menu.isVisible() && !this.ignoreNextClick){
  16553. this.showMenu();
  16554. }
  16555. this.fireEvent("click", this, e);
  16556. if(this.handler){
  16557. //this.el.removeClass("x-btn-over");
  16558. this.handler.call(this.scope || this, this, e);
  16559. }
  16560. }
  16561. },
  16562. // private
  16563. isMenuTriggerOver : function(e, internal){
  16564. return this.menu && !internal;
  16565. },
  16566. // private
  16567. isMenuTriggerOut : function(e, internal){
  16568. return this.menu && !internal;
  16569. },
  16570. // private
  16571. onMouseOver : function(e){
  16572. if(!this.disabled){
  16573. var internal = e.within(this.el, true);
  16574. if(!internal){
  16575. this.el.addClass("x-btn-over");
  16576. if(!this.monitoringMouseOver){
  16577. Ext.getDoc().on('mouseover', this.monitorMouseOver, this);
  16578. this.monitoringMouseOver = true;
  16579. }
  16580. this.fireEvent('mouseover', this, e);
  16581. }
  16582. if(this.isMenuTriggerOver(e, internal)){
  16583. this.fireEvent('menutriggerover', this, this.menu, e);
  16584. }
  16585. }
  16586. },
  16587. // private
  16588. monitorMouseOver : function(e){
  16589. if(e.target != this.el.dom && !e.within(this.el)){
  16590. if(this.monitoringMouseOver){
  16591. Ext.getDoc().un('mouseover', this.monitorMouseOver, this);
  16592. this.monitoringMouseOver = false;
  16593. }
  16594. this.onMouseOut(e);
  16595. }
  16596. },
  16597. // private
  16598. onMouseOut : function(e){
  16599. var internal = e.within(this.el) && e.target != this.el.dom;
  16600. this.el.removeClass("x-btn-over");
  16601. this.fireEvent('mouseout', this, e);
  16602. if(this.isMenuTriggerOut(e, internal)){
  16603. this.fireEvent('menutriggerout', this, this.menu, e);
  16604. }
  16605. },
  16606. // private
  16607. onFocus : function(e){
  16608. if(!this.disabled){
  16609. this.el.addClass("x-btn-focus");
  16610. }
  16611. },
  16612. // private
  16613. onBlur : function(e){
  16614. this.el.removeClass("x-btn-focus");
  16615. },
  16616. // private
  16617. getClickEl : function(e, isUp){
  16618. return this.el;
  16619. },
  16620. // private
  16621. onMouseDown : function(e){
  16622. if(!this.disabled && e.button == 0){
  16623. this.getClickEl(e).addClass("x-btn-click");
  16624. Ext.getDoc().on('mouseup', this.onMouseUp, this);
  16625. }
  16626. },
  16627. // private
  16628. onMouseUp : function(e){
  16629. if(e.button == 0){
  16630. this.getClickEl(e, true).removeClass("x-btn-click");
  16631. Ext.getDoc().un('mouseup', this.onMouseUp, this);
  16632. }
  16633. },
  16634. // private
  16635. onMenuShow : function(e){
  16636. this.ignoreNextClick = 0;
  16637. this.el.addClass("x-btn-menu-active");
  16638. this.fireEvent('menushow', this, this.menu);
  16639. },
  16640. // private
  16641. onMenuHide : function(e){
  16642. this.el.removeClass("x-btn-menu-active");
  16643. this.ignoreNextClick = this.restoreClick.defer(250, this);
  16644. this.fireEvent('menuhide', this, this.menu);
  16645. },
  16646. // private
  16647. restoreClick : function(){
  16648. this.ignoreNextClick = 0;
  16649. }
  16650. });
  16651. Ext.reg('button', Ext.Button);
  16652. // Private utility class used by Button
  16653. Ext.ButtonToggleMgr = function(){
  16654. var groups = {};
  16655. function toggleGroup(btn, state){
  16656. if(state){
  16657. var g = groups[btn.toggleGroup];
  16658. for(var i = 0, l = g.length; i < l; i++){
  16659. if(g[i] != btn){
  16660. g[i].toggle(false);
  16661. }
  16662. }
  16663. }
  16664. }
  16665. return {
  16666. register : function(btn){
  16667. if(!btn.toggleGroup){
  16668. return;
  16669. }
  16670. var g = groups[btn.toggleGroup];
  16671. if(!g){
  16672. g = groups[btn.toggleGroup] = [];
  16673. }
  16674. g.push(btn);
  16675. btn.on("toggle", toggleGroup);
  16676. },
  16677. unregister : function(btn){
  16678. if(!btn.toggleGroup){
  16679. return;
  16680. }
  16681. var g = groups[btn.toggleGroup];
  16682. if(g){
  16683. g.remove(btn);
  16684. btn.un("toggle", toggleGroup);
  16685. }
  16686. }
  16687. };
  16688. }();
  16689. Ext.SplitButton = Ext.extend(Ext.Button, {
  16690. // private
  16691. arrowSelector : 'button:last',
  16692. // private
  16693. initComponent : function(){
  16694. Ext.SplitButton.superclass.initComponent.call(this);
  16695. this.addEvents("arrowclick");
  16696. },
  16697. // private
  16698. onRender : function(ct, position){
  16699. // this is one sweet looking template!
  16700. var tpl = new Ext.Template(
  16701. '<table cellspacing="0" class="x-btn-menu-wrap x-btn"><tr><td>',
  16702. '<table cellspacing="0" class="x-btn-wrap x-btn-menu-text-wrap"><tbody>',
  16703. '<tr><td class="x-btn-left"><i>&#160;</i></td><td class="x-btn-center"><button class="x-btn-text" type="{1}">{0}</button></td></tr>',
  16704. "</tbody></table></td><td>",
  16705. '<table cellspacing="0" class="x-btn-wrap x-btn-menu-arrow-wrap"><tbody>',
  16706. '<tr><td class="x-btn-center"><button class="x-btn-menu-arrow-el" type="button">&#160;</button></td><td class="x-btn-right"><i>&#160;</i></td></tr>',
  16707. "</tbody></table></td></tr></table>"
  16708. );
  16709. var btn, targs = [this.text || '&#160;', this.type];
  16710. if(position){
  16711. btn = tpl.insertBefore(position, targs, true);
  16712. }else{
  16713. btn = tpl.append(ct, targs, true);
  16714. }
  16715. var btnEl = btn.child(this.buttonSelector);
  16716. this.initButtonEl(btn, btnEl);
  16717. this.arrowBtnTable = btn.child("table:last");
  16718. if(this.arrowTooltip){
  16719. btn.child(this.arrowSelector).dom[this.tooltipType] = this.arrowTooltip;
  16720. }
  16721. },
  16722. // private
  16723. autoWidth : function(){
  16724. if(this.el){
  16725. var tbl = this.el.child("table:first");
  16726. var tbl2 = this.el.child("table:last");
  16727. this.el.setWidth("auto");
  16728. tbl.setWidth("auto");
  16729. if(Ext.isIE7 && Ext.isStrict){
  16730. var ib = this.el.child(this.buttonSelector);
  16731. if(ib && ib.getWidth() > 20){
  16732. ib.clip();
  16733. ib.setWidth(Ext.util.TextMetrics.measure(ib, this.text).width+ib.getFrameWidth('lr'));
  16734. }
  16735. }
  16736. if(this.minWidth){
  16737. if((tbl.getWidth()+tbl2.getWidth()) < this.minWidth){
  16738. tbl.setWidth(this.minWidth-tbl2.getWidth());
  16739. }
  16740. }
  16741. this.el.setWidth(tbl.getWidth()+tbl2.getWidth());
  16742. }
  16743. },
  16744. setArrowHandler : function(handler, scope){
  16745. this.arrowHandler = handler;
  16746. this.scope = scope;
  16747. },
  16748. // private
  16749. onClick : function(e){
  16750. e.preventDefault();
  16751. if(!this.disabled){
  16752. if(e.getTarget(".x-btn-menu-arrow-wrap")){
  16753. if(this.menu && !this.menu.isVisible() && !this.ignoreNextClick){
  16754. this.showMenu();
  16755. }
  16756. this.fireEvent("arrowclick", this, e);
  16757. if(this.arrowHandler){
  16758. this.arrowHandler.call(this.scope || this, this, e);
  16759. }
  16760. }else{
  16761. if(this.enableToggle){
  16762. this.toggle();
  16763. }
  16764. this.fireEvent("click", this, e);
  16765. if(this.handler){
  16766. this.handler.call(this.scope || this, this, e);
  16767. }
  16768. }
  16769. }
  16770. },
  16771. // private
  16772. getClickEl : function(e, isUp){
  16773. if(!isUp){
  16774. return (this.lastClickEl = e.getTarget("table", 10, true));
  16775. }
  16776. return this.lastClickEl;
  16777. },
  16778. // private
  16779. onDisable : function(){
  16780. if(this.el){
  16781. if(!Ext.isIE6){
  16782. this.el.addClass("x-item-disabled");
  16783. }
  16784. this.el.child(this.buttonSelector).dom.disabled = true;
  16785. this.el.child(this.arrowSelector).dom.disabled = true;
  16786. }
  16787. this.disabled = true;
  16788. },
  16789. // private
  16790. onEnable : function(){
  16791. if(this.el){
  16792. if(!Ext.isIE6){
  16793. this.el.removeClass("x-item-disabled");
  16794. }
  16795. this.el.child(this.buttonSelector).dom.disabled = false;
  16796. this.el.child(this.arrowSelector).dom.disabled = false;
  16797. }
  16798. this.disabled = false;
  16799. },
  16800. // private
  16801. isMenuTriggerOver : function(e){
  16802. return this.menu && e.within(this.arrowBtnTable) && !e.within(this.arrowBtnTable, true);
  16803. },
  16804. // private
  16805. isMenuTriggerOut : function(e, internal){
  16806. return this.menu && !e.within(this.arrowBtnTable);
  16807. },
  16808. // private
  16809. onDestroy : function(){
  16810. Ext.destroy(this.arrowBtnTable);
  16811. Ext.SplitButton.superclass.onDestroy.call(this);
  16812. }
  16813. });
  16814. // backwards compat
  16815. Ext.MenuButton = Ext.SplitButton;
  16816. Ext.reg('splitbutton', Ext.SplitButton);
  16817. Ext.CycleButton = Ext.extend(Ext.SplitButton, {
  16818. // private
  16819. getItemText : function(item){
  16820. if(item && this.showText === true){
  16821. var text = '';
  16822. if(this.prependText){
  16823. text += this.prependText;
  16824. }
  16825. text += item.text;
  16826. return text;
  16827. }
  16828. return undefined;
  16829. },
  16830. setActiveItem : function(item, suppressEvent){
  16831. if(typeof item != 'object'){
  16832. item = this.menu.items.get(item);
  16833. }
  16834. if(item){
  16835. if(!this.rendered){
  16836. this.text = this.getItemText(item);
  16837. this.iconCls = item.iconCls;
  16838. }else{
  16839. var t = this.getItemText(item);
  16840. if(t){
  16841. this.setText(t);
  16842. }
  16843. this.setIconClass(item.iconCls);
  16844. }
  16845. this.activeItem = item;
  16846. if(!item.checked){
  16847. item.setChecked(true, true);
  16848. }
  16849. if(this.forceIcon){
  16850. this.setIconClass(this.forceIcon);
  16851. }
  16852. if(!suppressEvent){
  16853. this.fireEvent('change', this, item);
  16854. }
  16855. }
  16856. },
  16857. getActiveItem : function(){
  16858. return this.activeItem;
  16859. },
  16860. // private
  16861. initComponent : function(){
  16862. this.addEvents(
  16863. "change"
  16864. );
  16865. if(this.changeHandler){
  16866. this.on('change', this.changeHandler, this.scope||this);
  16867. delete this.changeHandler;
  16868. }
  16869. this.itemCount = this.items.length;
  16870. this.menu = {cls:'x-cycle-menu', items:[]};
  16871. var checked;
  16872. for(var i = 0, len = this.itemCount; i < len; i++){
  16873. var item = this.items[i];
  16874. item.group = item.group || this.id;
  16875. item.itemIndex = i;
  16876. item.checkHandler = this.checkHandler;
  16877. item.scope = this;
  16878. item.checked = item.checked || false;
  16879. this.menu.items.push(item);
  16880. if(item.checked){
  16881. checked = item;
  16882. }
  16883. }
  16884. this.setActiveItem(checked, true);
  16885. Ext.CycleButton.superclass.initComponent.call(this);
  16886. this.on('click', this.toggleSelected, this);
  16887. },
  16888. // private
  16889. checkHandler : function(item, pressed){
  16890. if(pressed){
  16891. this.setActiveItem(item);
  16892. }
  16893. },
  16894. toggleSelected : function(){
  16895. this.menu.render();
  16896. var nextIdx, checkItem;
  16897. for (var i = 1; i < this.itemCount; i++) {
  16898. nextIdx = (this.activeItem.itemIndex + i) % this.itemCount;
  16899. // check the potential item
  16900. checkItem = this.menu.items.itemAt(nextIdx);
  16901. // if its not disabled then check it.
  16902. if (!checkItem.disabled) {
  16903. checkItem.setChecked(true);
  16904. break;
  16905. }
  16906. }
  16907. }
  16908. });
  16909. Ext.reg('cycle', Ext.CycleButton);
  16910. Ext.Toolbar = function(config){
  16911. if(Ext.isArray(config)){
  16912. config = {buttons:config};
  16913. }
  16914. Ext.Toolbar.superclass.constructor.call(this, config);
  16915. };
  16916. (function(){
  16917. var T = Ext.Toolbar;
  16918. Ext.extend(T, Ext.BoxComponent, {
  16919. trackMenus : true,
  16920. // private
  16921. initComponent : function(){
  16922. T.superclass.initComponent.call(this);
  16923. if(this.items){
  16924. this.buttons = this.items;
  16925. }
  16926. this.items = new Ext.util.MixedCollection(false, function(o){
  16927. return o.itemId || o.id || Ext.id();
  16928. });
  16929. },
  16930. // private
  16931. autoCreate: {
  16932. cls:'x-toolbar x-small-editor',
  16933. html:'<table cellspacing="0"><tr></tr></table>'
  16934. },
  16935. // private
  16936. onRender : function(ct, position){
  16937. this.el = ct.createChild(Ext.apply({ id: this.id },this.autoCreate), position);
  16938. this.tr = this.el.child("tr", true);
  16939. },
  16940. // private
  16941. afterRender : function(){
  16942. T.superclass.afterRender.call(this);
  16943. if(this.buttons){
  16944. this.add.apply(this, this.buttons);
  16945. delete this.buttons;
  16946. }
  16947. },
  16948. add : function(){
  16949. var a = arguments, l = a.length;
  16950. for(var i = 0; i < l; i++){
  16951. var el = a[i];
  16952. if(el.isFormField){ // some kind of form field
  16953. this.addField(el);
  16954. }else if(el.render){ // some kind of Toolbar.Item
  16955. this.addItem(el);
  16956. }else if(typeof el == "string"){ // string
  16957. if(el == "separator" || el == "-"){
  16958. this.addSeparator();
  16959. }else if(el == " "){
  16960. this.addSpacer();
  16961. }else if(el == "->"){
  16962. this.addFill();
  16963. }else{
  16964. this.addText(el);
  16965. }
  16966. }else if(el.tagName){ // element
  16967. this.addElement(el);
  16968. }else if(typeof el == "object"){ // must be button config?
  16969. if(el.xtype){
  16970. this.addField(Ext.ComponentMgr.create(el, 'button'));
  16971. }else{
  16972. this.addButton(el);
  16973. }
  16974. }
  16975. }
  16976. },
  16977. addSeparator : function(){
  16978. return this.addItem(new T.Separator());
  16979. },
  16980. addSpacer : function(){
  16981. return this.addItem(new T.Spacer());
  16982. },
  16983. addFill : function(){
  16984. return this.addItem(new T.Fill());
  16985. },
  16986. addElement : function(el){
  16987. return this.addItem(new T.Item(el));
  16988. },
  16989. addItem : function(item){
  16990. var td = this.nextBlock();
  16991. this.initMenuTracking(item);
  16992. item.render(td);
  16993. this.items.add(item);
  16994. return item;
  16995. },
  16996. addButton : function(config){
  16997. if(Ext.isArray(config)){
  16998. var buttons = [];
  16999. for(var i = 0, len = config.length; i < len; i++) {
  17000. buttons.push(this.addButton(config[i]));
  17001. }
  17002. return buttons;
  17003. }
  17004. var b = config;
  17005. if(!(config instanceof T.Button)){
  17006. b = config.split ?
  17007. new T.SplitButton(config) :
  17008. new T.Button(config);
  17009. }
  17010. var td = this.nextBlock();
  17011. this.initMenuTracking(b);
  17012. b.render(td);
  17013. this.items.add(b);
  17014. return b;
  17015. },
  17016. // private
  17017. initMenuTracking : function(item){
  17018. if(this.trackMenus && item.menu){
  17019. item.on({
  17020. 'menutriggerover' : this.onButtonTriggerOver,
  17021. 'menushow' : this.onButtonMenuShow,
  17022. 'menuhide' : this.onButtonMenuHide,
  17023. scope: this
  17024. })
  17025. }
  17026. },
  17027. addText : function(text){
  17028. return this.addItem(new T.TextItem(text));
  17029. },
  17030. insertButton : function(index, item){
  17031. if(Ext.isArray(item)){
  17032. var buttons = [];
  17033. for(var i = 0, len = item.length; i < len; i++) {
  17034. buttons.push(this.insertButton(index + i, item[i]));
  17035. }
  17036. return buttons;
  17037. }
  17038. if (!(item instanceof T.Button)){
  17039. item = new T.Button(item);
  17040. }
  17041. var td = document.createElement("td");
  17042. this.tr.insertBefore(td, this.tr.childNodes[index]);
  17043. this.initMenuTracking(item);
  17044. item.render(td);
  17045. this.items.insert(index, item);
  17046. return item;
  17047. },
  17048. addDom : function(config, returnEl){
  17049. var td = this.nextBlock();
  17050. Ext.DomHelper.overwrite(td, config);
  17051. var ti = new T.Item(td.firstChild);
  17052. ti.render(td);
  17053. this.items.add(ti);
  17054. return ti;
  17055. },
  17056. addField : function(field){
  17057. var td = this.nextBlock();
  17058. field.render(td);
  17059. var ti = new T.Item(td.firstChild);
  17060. ti.render(td);
  17061. this.items.add(field);
  17062. return ti;
  17063. },
  17064. // private
  17065. nextBlock : function(){
  17066. var td = document.createElement("td");
  17067. this.tr.appendChild(td);
  17068. return td;
  17069. },
  17070. // private
  17071. onDestroy : function(){
  17072. Ext.Toolbar.superclass.onDestroy.call(this);
  17073. if(this.rendered){
  17074. if(this.items){ // rendered?
  17075. Ext.destroy.apply(Ext, this.items.items);
  17076. }
  17077. Ext.Element.uncache(this.tr);
  17078. }
  17079. },
  17080. // private
  17081. onDisable : function(){
  17082. this.items.each(function(item){
  17083. if(item.disable){
  17084. item.disable();
  17085. }
  17086. });
  17087. },
  17088. // private
  17089. onEnable : function(){
  17090. this.items.each(function(item){
  17091. if(item.enable){
  17092. item.enable();
  17093. }
  17094. });
  17095. },
  17096. // private
  17097. onButtonTriggerOver : function(btn){
  17098. if(this.activeMenuBtn && this.activeMenuBtn != btn){
  17099. this.activeMenuBtn.hideMenu();
  17100. btn.showMenu();
  17101. this.activeMenuBtn = btn;
  17102. }
  17103. },
  17104. // private
  17105. onButtonMenuShow : function(btn){
  17106. this.activeMenuBtn = btn;
  17107. },
  17108. // private
  17109. onButtonMenuHide : function(btn){
  17110. delete this.activeMenuBtn;
  17111. }
  17112. });
  17113. Ext.reg('toolbar', Ext.Toolbar);
  17114. T.Item = function(el){
  17115. this.el = Ext.getDom(el);
  17116. this.id = Ext.id(this.el);
  17117. this.hidden = false;
  17118. };
  17119. T.Item.prototype = {
  17120. getEl : function(){
  17121. return this.el;
  17122. },
  17123. // private
  17124. render : function(td){
  17125. this.td = td;
  17126. td.appendChild(this.el);
  17127. },
  17128. destroy : function(){
  17129. if(this.el){
  17130. var el = Ext.get(this.el);
  17131. Ext.destroy(el);
  17132. }
  17133. Ext.removeNode(this.td);
  17134. },
  17135. show: function(){
  17136. this.hidden = false;
  17137. this.td.style.display = "";
  17138. },
  17139. hide: function(){
  17140. this.hidden = true;
  17141. this.td.style.display = "none";
  17142. },
  17143. setVisible: function(visible){
  17144. if(visible) {
  17145. this.show();
  17146. }else{
  17147. this.hide();
  17148. }
  17149. },
  17150. focus : function(){
  17151. Ext.fly(this.el).focus();
  17152. },
  17153. disable : function(){
  17154. Ext.fly(this.td).addClass("x-item-disabled");
  17155. this.disabled = true;
  17156. this.el.disabled = true;
  17157. },
  17158. enable : function(){
  17159. Ext.fly(this.td).removeClass("x-item-disabled");
  17160. this.disabled = false;
  17161. this.el.disabled = false;
  17162. }
  17163. };
  17164. Ext.reg('tbitem', T.Item);
  17165. T.Separator = function(){
  17166. var s = document.createElement("span");
  17167. s.className = "ytb-sep";
  17168. T.Separator.superclass.constructor.call(this, s);
  17169. };
  17170. Ext.extend(T.Separator, T.Item, {
  17171. enable:Ext.emptyFn,
  17172. disable:Ext.emptyFn,
  17173. focus:Ext.emptyFn
  17174. });
  17175. Ext.reg('tbseparator', T.Separator);
  17176. T.Spacer = function(){
  17177. var s = document.createElement("div");
  17178. s.className = "ytb-spacer";
  17179. T.Spacer.superclass.constructor.call(this, s);
  17180. };
  17181. Ext.extend(T.Spacer, T.Item, {
  17182. enable:Ext.emptyFn,
  17183. disable:Ext.emptyFn,
  17184. focus:Ext.emptyFn
  17185. });
  17186. Ext.reg('tbspacer', T.Spacer);
  17187. T.Fill = Ext.extend(T.Spacer, {
  17188. // private
  17189. render : function(td){
  17190. td.style.width = '100%';
  17191. T.Fill.superclass.render.call(this, td);
  17192. }
  17193. });
  17194. Ext.reg('tbfill', T.Fill);
  17195. T.TextItem = function(t){
  17196. var s = document.createElement("span");
  17197. s.className = "ytb-text";
  17198. s.innerHTML = t.text ? t.text : t;
  17199. T.TextItem.superclass.constructor.call(this, s);
  17200. };
  17201. Ext.extend(T.TextItem, T.Item, {
  17202. enable:Ext.emptyFn,
  17203. disable:Ext.emptyFn,
  17204. focus:Ext.emptyFn
  17205. });
  17206. Ext.reg('tbtext', T.TextItem);
  17207. T.Button = Ext.extend(Ext.Button, {
  17208. hideParent : true,
  17209. onDestroy : function(){
  17210. T.Button.superclass.onDestroy.call(this);
  17211. if(this.container){
  17212. this.container.remove();
  17213. }
  17214. }
  17215. });
  17216. Ext.reg('tbbutton', T.Button);
  17217. T.SplitButton = Ext.extend(Ext.SplitButton, {
  17218. hideParent : true,
  17219. onDestroy : function(){
  17220. T.SplitButton.superclass.onDestroy.call(this);
  17221. if(this.container){
  17222. this.container.remove();
  17223. }
  17224. }
  17225. });
  17226. Ext.reg('tbsplit', T.SplitButton);
  17227. // backwards compat
  17228. T.MenuButton = T.SplitButton;
  17229. })();
  17230. Ext.PagingToolbar = Ext.extend(Ext.Toolbar, {
  17231. pageSize: 20,
  17232. displayMsg : 'Displaying {0} - {1} of {2}',
  17233. emptyMsg : 'No data to display',
  17234. beforePageText : "Page",
  17235. afterPageText : "of {0}",
  17236. firstText : "First Page",
  17237. prevText : "Previous Page",
  17238. nextText : "Next Page",
  17239. lastText : "Last Page",
  17240. refreshText : "Refresh",
  17241. paramNames : {start: 'start', limit: 'limit'},
  17242. // private
  17243. initComponent : function(){
  17244. this.addEvents(
  17245. 'change',
  17246. 'beforechange'
  17247. );
  17248. Ext.PagingToolbar.superclass.initComponent.call(this);
  17249. this.cursor = 0;
  17250. this.bind(this.store);
  17251. },
  17252. // private
  17253. onRender : function(ct, position){
  17254. Ext.PagingToolbar.superclass.onRender.call(this, ct, position);
  17255. this.first = this.addButton({
  17256. tooltip: this.firstText,
  17257. iconCls: "x-tbar-page-first",
  17258. disabled: true,
  17259. handler: this.onClick.createDelegate(this, ["first"])
  17260. });
  17261. this.prev = this.addButton({
  17262. tooltip: this.prevText,
  17263. iconCls: "x-tbar-page-prev",
  17264. disabled: true,
  17265. handler: this.onClick.createDelegate(this, ["prev"])
  17266. });
  17267. this.addSeparator();
  17268. this.add(this.beforePageText);
  17269. this.field = Ext.get(this.addDom({
  17270. tag: "input",
  17271. type: "text",
  17272. size: "3",
  17273. value: "1",
  17274. cls: "x-tbar-page-number"
  17275. }).el);
  17276. this.field.on("keydown", this.onPagingKeydown, this);
  17277. this.field.on("focus", function(){this.dom.select();});
  17278. this.field.on("blur", this.onPagingBlur, this);
  17279. this.afterTextEl = this.addText(String.format(this.afterPageText, 1));
  17280. this.field.setHeight(18);
  17281. this.addSeparator();
  17282. this.next = this.addButton({
  17283. tooltip: this.nextText,
  17284. iconCls: "x-tbar-page-next",
  17285. disabled: true,
  17286. handler: this.onClick.createDelegate(this, ["next"])
  17287. });
  17288. this.last = this.addButton({
  17289. tooltip: this.lastText,
  17290. iconCls: "x-tbar-page-last",
  17291. disabled: true,
  17292. handler: this.onClick.createDelegate(this, ["last"])
  17293. });
  17294. this.addSeparator();
  17295. this.loading = this.addButton({
  17296. tooltip: this.refreshText,
  17297. iconCls: "x-tbar-loading",
  17298. handler: this.onClick.createDelegate(this, ["refresh"])
  17299. });
  17300. if(this.displayInfo){
  17301. this.displayEl = Ext.fly(this.el.dom).createChild({cls:'x-paging-info'});
  17302. }
  17303. if(this.dsLoaded){
  17304. this.onLoad.apply(this, this.dsLoaded);
  17305. }
  17306. },
  17307. // private
  17308. updateInfo : function(){
  17309. if(this.displayEl){
  17310. var count = this.store.getCount();
  17311. var msg = count == 0 ?
  17312. this.emptyMsg :
  17313. String.format(
  17314. this.displayMsg,
  17315. this.cursor+1, this.cursor+count, this.store.getTotalCount()
  17316. );
  17317. this.displayEl.update(msg);
  17318. }
  17319. },
  17320. // private
  17321. onLoad : function(store, r, o){
  17322. if(!this.rendered){
  17323. this.dsLoaded = [store, r, o];
  17324. return;
  17325. }
  17326. this.cursor = o.params ? o.params[this.paramNames.start] : 0;
  17327. var d = this.getPageData(), ap = d.activePage, ps = d.pages;
  17328. this.afterTextEl.el.innerHTML = String.format(this.afterPageText, d.pages);
  17329. this.field.dom.value = ap;
  17330. this.first.setDisabled(ap == 1);
  17331. this.prev.setDisabled(ap == 1);
  17332. this.next.setDisabled(ap == ps);
  17333. this.last.setDisabled(ap == ps);
  17334. this.loading.enable();
  17335. this.updateInfo();
  17336. this.fireEvent('change', this, d);
  17337. },
  17338. // private
  17339. getPageData : function(){
  17340. var total = this.store.getTotalCount();
  17341. return {
  17342. total : total,
  17343. activePage : Math.ceil((this.cursor+this.pageSize)/this.pageSize),
  17344. pages : total < this.pageSize ? 1 : Math.ceil(total/this.pageSize)
  17345. };
  17346. },
  17347. // private
  17348. onLoadError : function(){
  17349. if(!this.rendered){
  17350. return;
  17351. }
  17352. this.loading.enable();
  17353. },
  17354. // private
  17355. readPage : function(d){
  17356. var v = this.field.dom.value, pageNum;
  17357. if (!v || isNaN(pageNum = parseInt(v, 10))) {
  17358. this.field.dom.value = d.activePage;
  17359. return false;
  17360. }
  17361. return pageNum;
  17362. },
  17363. //private
  17364. onPagingBlur: function(e){
  17365. this.field.dom.value = this.getPageData().activePage;
  17366. },
  17367. // private
  17368. onPagingKeydown : function(e){
  17369. var k = e.getKey(), d = this.getPageData(), pageNum;
  17370. if (k == e.RETURN) {
  17371. e.stopEvent();
  17372. pageNum = this.readPage(d);
  17373. if(pageNum !== false){
  17374. pageNum = Math.min(Math.max(1, pageNum), d.pages) - 1;
  17375. this.doLoad(pageNum * this.pageSize);
  17376. }
  17377. }else if (k == e.HOME || k == e.END){
  17378. e.stopEvent();
  17379. pageNum = k == e.HOME ? 1 : d.pages;
  17380. this.field.dom.value = pageNum;
  17381. }else if (k == e.UP || k == e.PAGEUP || k == e.DOWN || k == e.PAGEDOWN){
  17382. e.stopEvent();
  17383. if(pageNum = this.readPage(d)){
  17384. var increment = e.shiftKey ? 10 : 1;
  17385. if(k == e.DOWN || k == e.PAGEDOWN){
  17386. increment *= -1;
  17387. }
  17388. pageNum += increment;
  17389. if(pageNum >= 1 & pageNum <= d.pages){
  17390. this.field.dom.value = pageNum;
  17391. }
  17392. }
  17393. }
  17394. },
  17395. // private
  17396. beforeLoad : function(){
  17397. if(this.rendered && this.loading){
  17398. this.loading.disable();
  17399. }
  17400. },
  17401. // private
  17402. doLoad : function(start){
  17403. var o = {}, pn = this.paramNames;
  17404. o[pn.start] = start;
  17405. o[pn.limit] = this.pageSize;
  17406. if(this.fireEvent('beforechange', this, o) !== false){
  17407. this.store.load({params:o});
  17408. }
  17409. },
  17410. changePage: function(page){
  17411. this.doLoad(((page-1) * this.pageSize).constrain(0, this.store.getTotalCount()));
  17412. },
  17413. // private
  17414. onClick : function(which){
  17415. var store = this.store;
  17416. switch(which){
  17417. case "first":
  17418. this.doLoad(0);
  17419. break;
  17420. case "prev":
  17421. this.doLoad(Math.max(0, this.cursor-this.pageSize));
  17422. break;
  17423. case "next":
  17424. this.doLoad(this.cursor+this.pageSize);
  17425. break;
  17426. case "last":
  17427. var total = store.getTotalCount();
  17428. var extra = total % this.pageSize;
  17429. var lastStart = extra ? (total - extra) : total-this.pageSize;
  17430. this.doLoad(lastStart);
  17431. break;
  17432. case "refresh":
  17433. this.doLoad(this.cursor);
  17434. break;
  17435. }
  17436. },
  17437. unbind : function(store){
  17438. store = Ext.StoreMgr.lookup(store);
  17439. store.un("beforeload", this.beforeLoad, this);
  17440. store.un("load", this.onLoad, this);
  17441. store.un("loadexception", this.onLoadError, this);
  17442. this.store = undefined;
  17443. },
  17444. bind : function(store){
  17445. store = Ext.StoreMgr.lookup(store);
  17446. store.on("beforeload", this.beforeLoad, this);
  17447. store.on("load", this.onLoad, this);
  17448. store.on("loadexception", this.onLoadError, this);
  17449. this.store = store;
  17450. },
  17451. // private
  17452. onDestroy : function(){
  17453. if(this.store){
  17454. this.unbind(this.store);
  17455. }
  17456. Ext.PagingToolbar.superclass.onDestroy.call(this);
  17457. }
  17458. });
  17459. Ext.reg('paging', Ext.PagingToolbar);
  17460. Ext.Resizable = function(el, config){
  17461. this.el = Ext.get(el);
  17462. if(config && config.wrap){
  17463. config.resizeChild = this.el;
  17464. this.el = this.el.wrap(typeof config.wrap == "object" ? config.wrap : {cls:"xresizable-wrap"});
  17465. this.el.id = this.el.dom.id = config.resizeChild.id + "-rzwrap";
  17466. this.el.setStyle("overflow", "hidden");
  17467. this.el.setPositioning(config.resizeChild.getPositioning());
  17468. config.resizeChild.clearPositioning();
  17469. if(!config.width || !config.height){
  17470. var csize = config.resizeChild.getSize();
  17471. this.el.setSize(csize.width, csize.height);
  17472. }
  17473. if(config.pinned && !config.adjustments){
  17474. config.adjustments = "auto";
  17475. }
  17476. }
  17477. this.proxy = this.el.createProxy({tag: "div", cls: "x-resizable-proxy", id: this.el.id + "-rzproxy"}, Ext.getBody());
  17478. this.proxy.unselectable();
  17479. this.proxy.enableDisplayMode('block');
  17480. Ext.apply(this, config);
  17481. if(this.pinned){
  17482. this.disableTrackOver = true;
  17483. this.el.addClass("x-resizable-pinned");
  17484. }
  17485. // if the element isn't positioned, make it relative
  17486. var position = this.el.getStyle("position");
  17487. if(position != "absolute" && position != "fixed"){
  17488. this.el.setStyle("position", "relative");
  17489. }
  17490. if(!this.handles){ // no handles passed, must be legacy style
  17491. this.handles = 's,e,se';
  17492. if(this.multiDirectional){
  17493. this.handles += ',n,w';
  17494. }
  17495. }
  17496. if(this.handles == "all"){
  17497. this.handles = "n s e w ne nw se sw";
  17498. }
  17499. var hs = this.handles.split(/\s*?[,;]\s*?| /);
  17500. var ps = Ext.Resizable.positions;
  17501. for(var i = 0, len = hs.length; i < len; i++){
  17502. if(hs[i] && ps[hs[i]]){
  17503. var pos = ps[hs[i]];
  17504. this[pos] = new Ext.Resizable.Handle(this, pos, this.disableTrackOver, this.transparent);
  17505. }
  17506. }
  17507. // legacy
  17508. this.corner = this.southeast;
  17509. if(this.handles.indexOf("n") != -1 || this.handles.indexOf("w") != -1){
  17510. this.updateBox = true;
  17511. }
  17512. this.activeHandle = null;
  17513. if(this.resizeChild){
  17514. if(typeof this.resizeChild == "boolean"){
  17515. this.resizeChild = Ext.get(this.el.dom.firstChild, true);
  17516. }else{
  17517. this.resizeChild = Ext.get(this.resizeChild, true);
  17518. }
  17519. }
  17520. if(this.adjustments == "auto"){
  17521. var rc = this.resizeChild;
  17522. var hw = this.west, he = this.east, hn = this.north, hs = this.south;
  17523. if(rc && (hw || hn)){
  17524. rc.position("relative");
  17525. rc.setLeft(hw ? hw.el.getWidth() : 0);
  17526. rc.setTop(hn ? hn.el.getHeight() : 0);
  17527. }
  17528. this.adjustments = [
  17529. (he ? -he.el.getWidth() : 0) + (hw ? -hw.el.getWidth() : 0),
  17530. (hn ? -hn.el.getHeight() : 0) + (hs ? -hs.el.getHeight() : 0) -1
  17531. ];
  17532. }
  17533. if(this.draggable){
  17534. this.dd = this.dynamic ?
  17535. this.el.initDD(null) : this.el.initDDProxy(null, {dragElId: this.proxy.id});
  17536. this.dd.setHandleElId(this.resizeChild ? this.resizeChild.id : this.el.id);
  17537. }
  17538. // public events
  17539. this.addEvents(
  17540. "beforeresize",
  17541. "resize"
  17542. );
  17543. if(this.width !== null && this.height !== null){
  17544. this.resizeTo(this.width, this.height);
  17545. }else{
  17546. this.updateChildSize();
  17547. }
  17548. if(Ext.isIE){
  17549. this.el.dom.style.zoom = 1;
  17550. }
  17551. Ext.Resizable.superclass.constructor.call(this);
  17552. };
  17553. Ext.extend(Ext.Resizable, Ext.util.Observable, {
  17554. resizeChild : false,
  17555. adjustments : [0, 0],
  17556. minWidth : 5,
  17557. minHeight : 5,
  17558. maxWidth : 10000,
  17559. maxHeight : 10000,
  17560. enabled : true,
  17561. animate : false,
  17562. duration : .35,
  17563. dynamic : false,
  17564. handles : false,
  17565. multiDirectional : false,
  17566. disableTrackOver : false,
  17567. easing : 'easeOutStrong',
  17568. widthIncrement : 0,
  17569. heightIncrement : 0,
  17570. pinned : false,
  17571. width : null,
  17572. height : null,
  17573. preserveRatio : false,
  17574. transparent: false,
  17575. minX: 0,
  17576. minY: 0,
  17577. draggable: false,
  17578. resizeTo : function(width, height){
  17579. this.el.setSize(width, height);
  17580. this.updateChildSize();
  17581. this.fireEvent("resize", this, width, height, null);
  17582. },
  17583. // private
  17584. startSizing : function(e, handle){
  17585. this.fireEvent("beforeresize", this, e);
  17586. if(this.enabled){ // 2nd enabled check in case disabled before beforeresize handler
  17587. if(!this.overlay){
  17588. this.overlay = this.el.createProxy({tag: "div", cls: "x-resizable-overlay", html: "&#160;"}, Ext.getBody());
  17589. this.overlay.unselectable();
  17590. this.overlay.enableDisplayMode("block");
  17591. this.overlay.on("mousemove", this.onMouseMove, this);
  17592. this.overlay.on("mouseup", this.onMouseUp, this);
  17593. }
  17594. this.overlay.setStyle("cursor", handle.el.getStyle("cursor"));
  17595. this.resizing = true;
  17596. this.startBox = this.el.getBox();
  17597. this.startPoint = e.getXY();
  17598. this.offsets = [(this.startBox.x + this.startBox.width) - this.startPoint[0],
  17599. (this.startBox.y + this.startBox.height) - this.startPoint[1]];
  17600. this.overlay.setSize(Ext.lib.Dom.getViewWidth(true), Ext.lib.Dom.getViewHeight(true));
  17601. this.overlay.show();
  17602. if(this.constrainTo) {
  17603. var ct = Ext.get(this.constrainTo);
  17604. this.resizeRegion = ct.getRegion().adjust(
  17605. ct.getFrameWidth('t'),
  17606. ct.getFrameWidth('l'),
  17607. -ct.getFrameWidth('b'),
  17608. -ct.getFrameWidth('r')
  17609. );
  17610. }
  17611. this.proxy.setStyle('visibility', 'hidden'); // workaround display none
  17612. this.proxy.show();
  17613. this.proxy.setBox(this.startBox);
  17614. if(!this.dynamic){
  17615. this.proxy.setStyle('visibility', 'visible');
  17616. }
  17617. }
  17618. },
  17619. // private
  17620. onMouseDown : function(handle, e){
  17621. if(this.enabled){
  17622. e.stopEvent();
  17623. this.activeHandle = handle;
  17624. this.startSizing(e, handle);
  17625. }
  17626. },
  17627. // private
  17628. onMouseUp : function(e){
  17629. var size = this.resizeElement();
  17630. this.resizing = false;
  17631. this.handleOut();
  17632. this.overlay.hide();
  17633. this.proxy.hide();
  17634. this.fireEvent("resize", this, size.width, size.height, e);
  17635. },
  17636. // private
  17637. updateChildSize : function(){
  17638. if(this.resizeChild){
  17639. var el = this.el;
  17640. var child = this.resizeChild;
  17641. var adj = this.adjustments;
  17642. if(el.dom.offsetWidth){
  17643. var b = el.getSize(true);
  17644. child.setSize(b.width+adj[0], b.height+adj[1]);
  17645. }
  17646. // Second call here for IE
  17647. // The first call enables instant resizing and
  17648. // the second call corrects scroll bars if they
  17649. // exist
  17650. if(Ext.isIE){
  17651. setTimeout(function(){
  17652. if(el.dom.offsetWidth){
  17653. var b = el.getSize(true);
  17654. child.setSize(b.width+adj[0], b.height+adj[1]);
  17655. }
  17656. }, 10);
  17657. }
  17658. }
  17659. },
  17660. // private
  17661. snap : function(value, inc, min){
  17662. if(!inc || !value) return value;
  17663. var newValue = value;
  17664. var m = value % inc;
  17665. if(m > 0){
  17666. if(m > (inc/2)){
  17667. newValue = value + (inc-m);
  17668. }else{
  17669. newValue = value - m;
  17670. }
  17671. }
  17672. return Math.max(min, newValue);
  17673. },
  17674. resizeElement : function(){
  17675. var box = this.proxy.getBox();
  17676. if(this.updateBox){
  17677. this.el.setBox(box, false, this.animate, this.duration, null, this.easing);
  17678. }else{
  17679. this.el.setSize(box.width, box.height, this.animate, this.duration, null, this.easing);
  17680. }
  17681. this.updateChildSize();
  17682. if(!this.dynamic){
  17683. this.proxy.hide();
  17684. }
  17685. return box;
  17686. },
  17687. // private
  17688. constrain : function(v, diff, m, mx){
  17689. if(v - diff < m){
  17690. diff = v - m;
  17691. }else if(v - diff > mx){
  17692. diff = mx - v;
  17693. }
  17694. return diff;
  17695. },
  17696. // private
  17697. onMouseMove : function(e){
  17698. if(this.enabled){
  17699. try{// try catch so if something goes wrong the user doesn't get hung
  17700. if(this.resizeRegion && !this.resizeRegion.contains(e.getPoint())) {
  17701. return;
  17702. }
  17703. //var curXY = this.startPoint;
  17704. var curSize = this.curSize || this.startBox;
  17705. var x = this.startBox.x, y = this.startBox.y;
  17706. var ox = x, oy = y;
  17707. var w = curSize.width, h = curSize.height;
  17708. var ow = w, oh = h;
  17709. var mw = this.minWidth, mh = this.minHeight;
  17710. var mxw = this.maxWidth, mxh = this.maxHeight;
  17711. var wi = this.widthIncrement;
  17712. var hi = this.heightIncrement;
  17713. var eventXY = e.getXY();
  17714. var diffX = -(this.startPoint[0] - Math.max(this.minX, eventXY[0]));
  17715. var diffY = -(this.startPoint[1] - Math.max(this.minY, eventXY[1]));
  17716. var pos = this.activeHandle.position;
  17717. switch(pos){
  17718. case "east":
  17719. w += diffX;
  17720. w = Math.min(Math.max(mw, w), mxw);
  17721. break;
  17722. case "south":
  17723. h += diffY;
  17724. h = Math.min(Math.max(mh, h), mxh);
  17725. break;
  17726. case "southeast":
  17727. w += diffX;
  17728. h += diffY;
  17729. w = Math.min(Math.max(mw, w), mxw);
  17730. h = Math.min(Math.max(mh, h), mxh);
  17731. break;
  17732. case "north":
  17733. diffY = this.constrain(h, diffY, mh, mxh);
  17734. y += diffY;
  17735. h -= diffY;
  17736. break;
  17737. case "west":
  17738. diffX = this.constrain(w, diffX, mw, mxw);
  17739. x += diffX;
  17740. w -= diffX;
  17741. break;
  17742. case "northeast":
  17743. w += diffX;
  17744. w = Math.min(Math.max(mw, w), mxw);
  17745. diffY = this.constrain(h, diffY, mh, mxh);
  17746. y += diffY;
  17747. h -= diffY;
  17748. break;
  17749. case "northwest":
  17750. diffX = this.constrain(w, diffX, mw, mxw);
  17751. diffY = this.constrain(h, diffY, mh, mxh);
  17752. y += diffY;
  17753. h -= diffY;
  17754. x += diffX;
  17755. w -= diffX;
  17756. break;
  17757. case "southwest":
  17758. diffX = this.constrain(w, diffX, mw, mxw);
  17759. h += diffY;
  17760. h = Math.min(Math.max(mh, h), mxh);
  17761. x += diffX;
  17762. w -= diffX;
  17763. break;
  17764. }
  17765. var sw = this.snap(w, wi, mw);
  17766. var sh = this.snap(h, hi, mh);
  17767. if(sw != w || sh != h){
  17768. switch(pos){
  17769. case "northeast":
  17770. y -= sh - h;
  17771. break;
  17772. case "north":
  17773. y -= sh - h;
  17774. break;
  17775. case "southwest":
  17776. x -= sw - w;
  17777. break;
  17778. case "west":
  17779. x -= sw - w;
  17780. break;
  17781. case "northwest":
  17782. x -= sw - w;
  17783. y -= sh - h;
  17784. break;
  17785. }
  17786. w = sw;
  17787. h = sh;
  17788. }
  17789. if(this.preserveRatio){
  17790. switch(pos){
  17791. case "southeast":
  17792. case "east":
  17793. h = oh * (w/ow);
  17794. h = Math.min(Math.max(mh, h), mxh);
  17795. w = ow * (h/oh);
  17796. break;
  17797. case "south":
  17798. w = ow * (h/oh);
  17799. w = Math.min(Math.max(mw, w), mxw);
  17800. h = oh * (w/ow);
  17801. break;
  17802. case "northeast":
  17803. w = ow * (h/oh);
  17804. w = Math.min(Math.max(mw, w), mxw);
  17805. h = oh * (w/ow);
  17806. break;
  17807. case "north":
  17808. var tw = w;
  17809. w = ow * (h/oh);
  17810. w = Math.min(Math.max(mw, w), mxw);
  17811. h = oh * (w/ow);
  17812. x += (tw - w) / 2;
  17813. break;
  17814. case "southwest":
  17815. h = oh * (w/ow);
  17816. h = Math.min(Math.max(mh, h), mxh);
  17817. var tw = w;
  17818. w = ow * (h/oh);
  17819. x += tw - w;
  17820. break;
  17821. case "west":
  17822. var th = h;
  17823. h = oh * (w/ow);
  17824. h = Math.min(Math.max(mh, h), mxh);
  17825. y += (th - h) / 2;
  17826. var tw = w;
  17827. w = ow * (h/oh);
  17828. x += tw - w;
  17829. break;
  17830. case "northwest":
  17831. var tw = w;
  17832. var th = h;
  17833. h = oh * (w/ow);
  17834. h = Math.min(Math.max(mh, h), mxh);
  17835. w = ow * (h/oh);
  17836. y += th - h;
  17837. x += tw - w;
  17838. break;
  17839. }
  17840. }
  17841. this.proxy.setBounds(x, y, w, h);
  17842. if(this.dynamic){
  17843. this.resizeElement();
  17844. }
  17845. }catch(e){}
  17846. }
  17847. },
  17848. // private
  17849. handleOver : function(){
  17850. if(this.enabled){
  17851. this.el.addClass("x-resizable-over");
  17852. }
  17853. },
  17854. // private
  17855. handleOut : function(){
  17856. if(!this.resizing){
  17857. this.el.removeClass("x-resizable-over");
  17858. }
  17859. },
  17860. getEl : function(){
  17861. return this.el;
  17862. },
  17863. getResizeChild : function(){
  17864. return this.resizeChild;
  17865. },
  17866. destroy : function(removeEl){
  17867. if(this.dd){
  17868. this.dd.destroy();
  17869. }
  17870. if(this.overlay){
  17871. Ext.destroy(this.overlay);
  17872. this.overlay = null;
  17873. }
  17874. Ext.destroy(this.proxy);
  17875. this.proxy = null;
  17876. var ps = Ext.Resizable.positions;
  17877. for(var k in ps){
  17878. if(typeof ps[k] != "function" && this[ps[k]]){
  17879. this[ps[k]].destroy();
  17880. }
  17881. }
  17882. if(removeEl){
  17883. this.el.update("");
  17884. Ext.destroy(this.el);
  17885. this.el = null;
  17886. }
  17887. },
  17888. syncHandleHeight : function(){
  17889. var h = this.el.getHeight(true);
  17890. if(this.west){
  17891. this.west.el.setHeight(h);
  17892. }
  17893. if(this.east){
  17894. this.east.el.setHeight(h);
  17895. }
  17896. }
  17897. });
  17898. // private
  17899. // hash to map config positions to true positions
  17900. Ext.Resizable.positions = {
  17901. n: "north", s: "south", e: "east", w: "west", se: "southeast", sw: "southwest", nw: "northwest", ne: "northeast"
  17902. };
  17903. // private
  17904. Ext.Resizable.Handle = function(rz, pos, disableTrackOver, transparent){
  17905. if(!this.tpl){
  17906. // only initialize the template if resizable is used
  17907. var tpl = Ext.DomHelper.createTemplate(
  17908. {tag: "div", cls: "x-resizable-handle x-resizable-handle-{0}"}
  17909. );
  17910. tpl.compile();
  17911. Ext.Resizable.Handle.prototype.tpl = tpl;
  17912. }
  17913. this.position = pos;
  17914. this.rz = rz;
  17915. this.el = this.tpl.append(rz.el.dom, [this.position], true);
  17916. this.el.unselectable();
  17917. if(transparent){
  17918. this.el.setOpacity(0);
  17919. }
  17920. this.el.on("mousedown", this.onMouseDown, this);
  17921. if(!disableTrackOver){
  17922. this.el.on("mouseover", this.onMouseOver, this);
  17923. this.el.on("mouseout", this.onMouseOut, this);
  17924. }
  17925. };
  17926. // private
  17927. Ext.Resizable.Handle.prototype = {
  17928. // private
  17929. afterResize : function(rz){
  17930. // do nothing
  17931. },
  17932. // private
  17933. onMouseDown : function(e){
  17934. this.rz.onMouseDown(this, e);
  17935. },
  17936. // private
  17937. onMouseOver : function(e){
  17938. this.rz.handleOver(this, e);
  17939. },
  17940. // private
  17941. onMouseOut : function(e){
  17942. this.rz.handleOut(this, e);
  17943. },
  17944. // private
  17945. destroy : function(){
  17946. Ext.destroy(this.el);
  17947. this.el = null;
  17948. }
  17949. };
  17950. Ext.Editor = function(field, config){
  17951. this.field = field;
  17952. Ext.Editor.superclass.constructor.call(this, config);
  17953. };
  17954. Ext.extend(Ext.Editor, Ext.Component, {
  17955. value : "",
  17956. alignment: "c-c?",
  17957. shadow : "frame",
  17958. constrain : false,
  17959. swallowKeys : true,
  17960. completeOnEnter : false,
  17961. cancelOnEsc : false,
  17962. updateEl : false,
  17963. initComponent : function(){
  17964. Ext.Editor.superclass.initComponent.call(this);
  17965. this.addEvents(
  17966. "beforestartedit",
  17967. "startedit",
  17968. "beforecomplete",
  17969. "complete",
  17970. "canceledit",
  17971. "specialkey"
  17972. );
  17973. },
  17974. // private
  17975. onRender : function(ct, position){
  17976. this.el = new Ext.Layer({
  17977. shadow: this.shadow,
  17978. cls: "x-editor",
  17979. parentEl : ct,
  17980. shim : this.shim,
  17981. shadowOffset:4,
  17982. id: this.id,
  17983. constrain: this.constrain
  17984. });
  17985. this.el.setStyle("overflow", Ext.isGecko ? "auto" : "hidden");
  17986. if(this.field.msgTarget != 'title'){
  17987. this.field.msgTarget = 'qtip';
  17988. }
  17989. this.field.inEditor = true;
  17990. this.field.render(this.el);
  17991. if(Ext.isGecko){
  17992. this.field.el.dom.setAttribute('autocomplete', 'off');
  17993. }
  17994. this.field.on("specialkey", this.onSpecialKey, this);
  17995. if(this.swallowKeys){
  17996. this.field.el.swallowEvent(['keydown','keypress']);
  17997. }
  17998. this.field.show();
  17999. this.field.on("blur", this.onBlur, this);
  18000. if(this.field.grow){
  18001. this.field.on("autosize", this.el.sync, this.el, {delay:1});
  18002. }
  18003. },
  18004. // private
  18005. onSpecialKey : function(field, e){
  18006. var key = e.getKey();
  18007. if(this.completeOnEnter && key == e.ENTER){
  18008. e.stopEvent();
  18009. this.completeEdit();
  18010. }else if(this.cancelOnEsc && key == e.ESC){
  18011. this.cancelEdit();
  18012. }else{
  18013. this.fireEvent('specialkey', field, e);
  18014. }
  18015. if(this.field.triggerBlur && (key == e.ENTER || key == e.ESC || key == e.TAB)){
  18016. this.field.triggerBlur();
  18017. }
  18018. },
  18019. startEdit : function(el, value){
  18020. if(this.editing){
  18021. this.completeEdit();
  18022. }
  18023. this.boundEl = Ext.get(el);
  18024. var v = value !== undefined ? value : this.boundEl.dom.innerHTML;
  18025. if(!this.rendered){
  18026. this.render(this.parentEl || document.body);
  18027. }
  18028. if(this.fireEvent("beforestartedit", this, this.boundEl, v) === false){
  18029. return;
  18030. }
  18031. this.startValue = v;
  18032. this.field.setValue(v);
  18033. this.doAutoSize();
  18034. this.el.alignTo(this.boundEl, this.alignment);
  18035. this.editing = true;
  18036. this.show();
  18037. },
  18038. // private
  18039. doAutoSize : function(){
  18040. if(this.autoSize){
  18041. var sz = this.boundEl.getSize();
  18042. switch(this.autoSize){
  18043. case "width":
  18044. this.setSize(sz.width, "");
  18045. break;
  18046. case "height":
  18047. this.setSize("", sz.height);
  18048. break;
  18049. default:
  18050. this.setSize(sz.width, sz.height);
  18051. }
  18052. }
  18053. },
  18054. setSize : function(w, h){
  18055. delete this.field.lastSize;
  18056. this.field.setSize(w, h);
  18057. if(this.el){
  18058. if(Ext.isGecko2 || Ext.isOpera){
  18059. // prevent layer scrollbars
  18060. this.el.setSize(w, h);
  18061. }
  18062. this.el.sync();
  18063. }
  18064. },
  18065. realign : function(){
  18066. this.el.alignTo(this.boundEl, this.alignment);
  18067. },
  18068. completeEdit : function(remainVisible){
  18069. if(!this.editing){
  18070. return;
  18071. }
  18072. var v = this.getValue();
  18073. if(this.revertInvalid !== false && !this.field.isValid()){
  18074. v = this.startValue;
  18075. this.cancelEdit(true);
  18076. }
  18077. if(String(v) === String(this.startValue) && this.ignoreNoChange){
  18078. this.editing = false;
  18079. this.hide();
  18080. return;
  18081. }
  18082. if(this.fireEvent("beforecomplete", this, v, this.startValue) !== false){
  18083. this.editing = false;
  18084. if(this.updateEl && this.boundEl){
  18085. this.boundEl.update(v);
  18086. }
  18087. if(remainVisible !== true){
  18088. this.hide();
  18089. }
  18090. this.fireEvent("complete", this, v, this.startValue);
  18091. }
  18092. },
  18093. // private
  18094. onShow : function(){
  18095. this.el.show();
  18096. if(this.hideEl !== false){
  18097. this.boundEl.hide();
  18098. }
  18099. this.field.show();
  18100. if(Ext.isIE && !this.fixIEFocus){ // IE has problems with focusing the first time
  18101. this.fixIEFocus = true;
  18102. this.deferredFocus.defer(50, this);
  18103. }else{
  18104. this.field.focus();
  18105. }
  18106. this.fireEvent("startedit", this.boundEl, this.startValue);
  18107. },
  18108. deferredFocus : function(){
  18109. if(this.editing){
  18110. this.field.focus();
  18111. }
  18112. },
  18113. cancelEdit : function(remainVisible){
  18114. if(this.editing){
  18115. var v = this.getValue();
  18116. this.setValue(this.startValue);
  18117. if(remainVisible !== true){
  18118. this.hide();
  18119. }
  18120. this.fireEvent("canceledit", this, v, this.startValue);
  18121. }
  18122. },
  18123. // private
  18124. onBlur : function(){
  18125. if(this.allowBlur !== true && this.editing){
  18126. this.completeEdit();
  18127. }
  18128. },
  18129. // private
  18130. onHide : function(){
  18131. if(this.editing){
  18132. this.completeEdit();
  18133. return;
  18134. }
  18135. this.field.blur();
  18136. if(this.field.collapse){
  18137. this.field.collapse();
  18138. }
  18139. this.el.hide();
  18140. if(this.hideEl !== false){
  18141. this.boundEl.show();
  18142. }
  18143. },
  18144. setValue : function(v){
  18145. this.field.setValue(v);
  18146. },
  18147. getValue : function(){
  18148. return this.field.getValue();
  18149. },
  18150. beforeDestroy : function(){
  18151. Ext.destroy(this.field);
  18152. this.field = null;
  18153. }
  18154. });
  18155. Ext.reg('editor', Ext.Editor);
  18156. Ext.MessageBox = function(){
  18157. var dlg, opt, mask, waitTimer;
  18158. var bodyEl, msgEl, textboxEl, textareaEl, progressBar, pp, iconEl, spacerEl;
  18159. var buttons, activeTextEl, bwidth, iconCls = '';
  18160. // private
  18161. var handleButton = function(button){
  18162. if(dlg.isVisible()){
  18163. dlg.hide();
  18164. Ext.callback(opt.fn, opt.scope||window, [button, activeTextEl.dom.value, opt], 1);
  18165. }
  18166. };
  18167. // private
  18168. var handleHide = function(){
  18169. if(opt && opt.cls){
  18170. dlg.el.removeClass(opt.cls);
  18171. }
  18172. progressBar.reset();
  18173. };
  18174. // private
  18175. var handleEsc = function(d, k, e){
  18176. if(opt && opt.closable !== false){
  18177. dlg.hide();
  18178. }
  18179. if(e){
  18180. e.stopEvent();
  18181. }
  18182. };
  18183. // private
  18184. var updateButtons = function(b){
  18185. var width = 0;
  18186. if(!b){
  18187. buttons["ok"].hide();
  18188. buttons["cancel"].hide();
  18189. buttons["yes"].hide();
  18190. buttons["no"].hide();
  18191. return width;
  18192. }
  18193. dlg.footer.dom.style.display = '';
  18194. for(var k in buttons){
  18195. if(typeof buttons[k] != "function"){
  18196. if(b[k]){
  18197. buttons[k].show();
  18198. buttons[k].setText(typeof b[k] == "string" ? b[k] : Ext.MessageBox.buttonText[k]);
  18199. width += buttons[k].el.getWidth()+15;
  18200. }else{
  18201. buttons[k].hide();
  18202. }
  18203. }
  18204. }
  18205. return width;
  18206. };
  18207. return {
  18208. getDialog : function(titleText){
  18209. if(!dlg){
  18210. dlg = new Ext.Window({
  18211. autoCreate : true,
  18212. title:titleText,
  18213. resizable:false,
  18214. constrain:true,
  18215. constrainHeader:true,
  18216. minimizable : false,
  18217. maximizable : false,
  18218. stateful: false,
  18219. modal: true,
  18220. shim:true,
  18221. buttonAlign:"center",
  18222. width:400,
  18223. height:100,
  18224. minHeight: 80,
  18225. plain:true,
  18226. footer:true,
  18227. closable:true,
  18228. close : function(){
  18229. if(opt && opt.buttons && opt.buttons.no && !opt.buttons.cancel){
  18230. handleButton("no");
  18231. }else{
  18232. handleButton("cancel");
  18233. }
  18234. }
  18235. });
  18236. buttons = {};
  18237. var bt = this.buttonText;
  18238. //TODO: refactor this block into a buttons config to pass into the Window constructor
  18239. buttons["ok"] = dlg.addButton(bt["ok"], handleButton.createCallback("ok"));
  18240. buttons["yes"] = dlg.addButton(bt["yes"], handleButton.createCallback("yes"));
  18241. buttons["no"] = dlg.addButton(bt["no"], handleButton.createCallback("no"));
  18242. buttons["cancel"] = dlg.addButton(bt["cancel"], handleButton.createCallback("cancel"));
  18243. buttons["ok"].hideMode = buttons["yes"].hideMode = buttons["no"].hideMode = buttons["cancel"].hideMode = 'offsets';
  18244. dlg.render(document.body);
  18245. dlg.getEl().addClass('x-window-dlg');
  18246. mask = dlg.mask;
  18247. bodyEl = dlg.body.createChild({
  18248. html:'<div class="ext-mb-icon"></div><div class="ext-mb-content"><span class="ext-mb-text"></span><br /><div class="ext-mb-fix-cursor"><input type="text" class="ext-mb-input" /><textarea class="ext-mb-textarea"></textarea></div></div>'
  18249. });
  18250. iconEl = Ext.get(bodyEl.dom.firstChild);
  18251. var contentEl = bodyEl.dom.childNodes[1];
  18252. msgEl = Ext.get(contentEl.firstChild);
  18253. textboxEl = Ext.get(contentEl.childNodes[2].firstChild);
  18254. textboxEl.enableDisplayMode();
  18255. textboxEl.addKeyListener([10,13], function(){
  18256. if(dlg.isVisible() && opt && opt.buttons){
  18257. if(opt.buttons.ok){
  18258. handleButton("ok");
  18259. }else if(opt.buttons.yes){
  18260. handleButton("yes");
  18261. }
  18262. }
  18263. });
  18264. textareaEl = Ext.get(contentEl.childNodes[2].childNodes[1]);
  18265. textareaEl.enableDisplayMode();
  18266. progressBar = new Ext.ProgressBar({
  18267. renderTo:bodyEl
  18268. });
  18269. bodyEl.createChild({cls:'x-clear'});
  18270. }
  18271. return dlg;
  18272. },
  18273. updateText : function(text){
  18274. if(!dlg.isVisible() && !opt.width){
  18275. dlg.setSize(this.maxWidth, 100); // resize first so content is never clipped from previous shows
  18276. }
  18277. msgEl.update(text || '&#160;');
  18278. var iw = iconCls != '' ? (iconEl.getWidth() + iconEl.getMargins('lr')) : 0;
  18279. var mw = msgEl.getWidth() + msgEl.getMargins('lr');
  18280. var fw = dlg.getFrameWidth('lr');
  18281. var bw = dlg.body.getFrameWidth('lr');
  18282. if (Ext.isIE && iw > 0){
  18283. //3 pixels get subtracted in the icon CSS for an IE margin issue,
  18284. //so we have to add it back here for the overall width to be consistent
  18285. iw += 3;
  18286. }
  18287. var w = Math.max(Math.min(opt.width || iw+mw+fw+bw, this.maxWidth),
  18288. Math.max(opt.minWidth || this.minWidth, bwidth || 0));
  18289. if(opt.prompt === true){
  18290. activeTextEl.setWidth(w-iw-fw-bw);
  18291. }
  18292. if(opt.progress === true || opt.wait === true){
  18293. progressBar.setSize(w-iw-fw-bw);
  18294. }
  18295. if(Ext.isIE && w == bwidth){
  18296. w += 4; //Add offset when the content width is smaller than the buttons.
  18297. }
  18298. dlg.setSize(w, 'auto').center();
  18299. return this;
  18300. },
  18301. updateProgress : function(value, progressText, msg){
  18302. progressBar.updateProgress(value, progressText);
  18303. if(msg){
  18304. this.updateText(msg);
  18305. }
  18306. return this;
  18307. },
  18308. isVisible : function(){
  18309. return dlg && dlg.isVisible();
  18310. },
  18311. hide : function(){
  18312. var proxy = dlg.activeGhost;
  18313. if(this.isVisible() || proxy) {
  18314. dlg.hide();
  18315. handleHide();
  18316. if (proxy) {
  18317. proxy.hide();
  18318. }
  18319. }
  18320. return this;
  18321. },
  18322. show : function(options){
  18323. if(this.isVisible()){
  18324. this.hide();
  18325. }
  18326. opt = options;
  18327. var d = this.getDialog(opt.title || "&#160;");
  18328. d.setTitle(opt.title || "&#160;");
  18329. var allowClose = (opt.closable !== false && opt.progress !== true && opt.wait !== true);
  18330. d.tools.close.setDisplayed(allowClose);
  18331. activeTextEl = textboxEl;
  18332. opt.prompt = opt.prompt || (opt.multiline ? true : false);
  18333. if(opt.prompt){
  18334. if(opt.multiline){
  18335. textboxEl.hide();
  18336. textareaEl.show();
  18337. textareaEl.setHeight(typeof opt.multiline == "number" ?
  18338. opt.multiline : this.defaultTextHeight);
  18339. activeTextEl = textareaEl;
  18340. }else{
  18341. textboxEl.show();
  18342. textareaEl.hide();
  18343. }
  18344. }else{
  18345. textboxEl.hide();
  18346. textareaEl.hide();
  18347. }
  18348. activeTextEl.dom.value = opt.value || "";
  18349. if(opt.prompt){
  18350. d.focusEl = activeTextEl;
  18351. }else{
  18352. var bs = opt.buttons;
  18353. var db = null;
  18354. if(bs && bs.ok){
  18355. db = buttons["ok"];
  18356. }else if(bs && bs.yes){
  18357. db = buttons["yes"];
  18358. }
  18359. if (db){
  18360. d.focusEl = db;
  18361. }
  18362. }
  18363. if(opt.iconCls){
  18364. d.setIconClass(opt.iconCls);
  18365. }
  18366. this.setIcon(opt.icon);
  18367. bwidth = updateButtons(opt.buttons);
  18368. progressBar.setVisible(opt.progress === true || opt.wait === true);
  18369. this.updateProgress(0, opt.progressText);
  18370. this.updateText(opt.msg);
  18371. if(opt.cls){
  18372. d.el.addClass(opt.cls);
  18373. }
  18374. d.proxyDrag = opt.proxyDrag === true;
  18375. d.modal = opt.modal !== false;
  18376. d.mask = opt.modal !== false ? mask : false;
  18377. if(!d.isVisible()){
  18378. // force it to the end of the z-index stack so it gets a cursor in FF
  18379. document.body.appendChild(dlg.el.dom);
  18380. d.setAnimateTarget(opt.animEl);
  18381. d.show(opt.animEl);
  18382. }
  18383. //workaround for window internally enabling keymap in afterShow
  18384. d.on('show', function(){
  18385. if(allowClose === true){
  18386. d.keyMap.enable();
  18387. }else{
  18388. d.keyMap.disable();
  18389. }
  18390. }, this, {single:true});
  18391. if(opt.wait === true){
  18392. progressBar.wait(opt.waitConfig);
  18393. }
  18394. return this;
  18395. },
  18396. setIcon : function(icon){
  18397. if(icon && icon != ''){
  18398. iconEl.removeClass('x-hidden');
  18399. iconEl.replaceClass(iconCls, icon);
  18400. iconCls = icon;
  18401. }else{
  18402. iconEl.replaceClass(iconCls, 'x-hidden');
  18403. iconCls = '';
  18404. }
  18405. return this;
  18406. },
  18407. progress : function(title, msg, progressText){
  18408. this.show({
  18409. title : title,
  18410. msg : msg,
  18411. buttons: false,
  18412. progress:true,
  18413. closable:false,
  18414. minWidth: this.minProgressWidth,
  18415. progressText: progressText
  18416. });
  18417. return this;
  18418. },
  18419. wait : function(msg, title, config){
  18420. this.show({
  18421. title : title,
  18422. msg : msg,
  18423. buttons: false,
  18424. closable:false,
  18425. wait:true,
  18426. modal:true,
  18427. minWidth: this.minProgressWidth,
  18428. waitConfig: config
  18429. });
  18430. return this;
  18431. },
  18432. alert : function(title, msg, fn, scope){
  18433. this.show({
  18434. title : title,
  18435. msg : msg,
  18436. buttons: this.OK,
  18437. fn: fn,
  18438. scope : scope
  18439. });
  18440. return this;
  18441. },
  18442. confirm : function(title, msg, fn, scope){
  18443. this.show({
  18444. title : title,
  18445. msg : msg,
  18446. buttons: this.YESNO,
  18447. fn: fn,
  18448. scope : scope,
  18449. icon: this.QUESTION
  18450. });
  18451. return this;
  18452. },
  18453. prompt : function(title, msg, fn, scope, multiline, value){
  18454. this.show({
  18455. title : title,
  18456. msg : msg,
  18457. buttons: this.OKCANCEL,
  18458. fn: fn,
  18459. minWidth:250,
  18460. scope : scope,
  18461. prompt:true,
  18462. multiline: multiline,
  18463. value: value
  18464. });
  18465. return this;
  18466. },
  18467. OK : {ok:true},
  18468. CANCEL : {cancel:true},
  18469. OKCANCEL : {ok:true, cancel:true},
  18470. YESNO : {yes:true, no:true},
  18471. YESNOCANCEL : {yes:true, no:true, cancel:true},
  18472. INFO : 'ext-mb-info',
  18473. WARNING : 'ext-mb-warning',
  18474. QUESTION : 'ext-mb-question',
  18475. ERROR : 'ext-mb-error',
  18476. defaultTextHeight : 75,
  18477. maxWidth : 600,
  18478. minWidth : 100,
  18479. minProgressWidth : 250,
  18480. buttonText : {
  18481. ok : "OK",
  18482. cancel : "Cancel",
  18483. yes : "Yes",
  18484. no : "No"
  18485. }
  18486. };
  18487. }();
  18488. Ext.Msg = Ext.MessageBox;
  18489. Ext.Tip = Ext.extend(Ext.Panel, {
  18490. minWidth : 40,
  18491. maxWidth : 300,
  18492. shadow : "sides",
  18493. defaultAlign : "tl-bl?",
  18494. autoRender: true,
  18495. quickShowInterval : 250,
  18496. // private panel overrides
  18497. frame:true,
  18498. hidden:true,
  18499. baseCls: 'x-tip',
  18500. floating:{shadow:true,shim:true,useDisplay:true,constrain:false},
  18501. autoHeight:true,
  18502. // private
  18503. initComponent : function(){
  18504. Ext.Tip.superclass.initComponent.call(this);
  18505. if(this.closable && !this.title){
  18506. this.elements += ',header';
  18507. }
  18508. },
  18509. // private
  18510. afterRender : function(){
  18511. Ext.Tip.superclass.afterRender.call(this);
  18512. if(this.closable){
  18513. this.addTool({
  18514. id: 'close',
  18515. handler: this.hide,
  18516. scope: this
  18517. });
  18518. }
  18519. },
  18520. showAt : function(xy){
  18521. Ext.Tip.superclass.show.call(this);
  18522. if(this.measureWidth !== false && (!this.initialConfig || typeof this.initialConfig.width != 'number')){
  18523. this.doAutoWidth();
  18524. }
  18525. if(this.constrainPosition){
  18526. xy = this.el.adjustForConstraints(xy);
  18527. }
  18528. this.setPagePosition(xy[0], xy[1]);
  18529. },
  18530. // protected
  18531. doAutoWidth : function(){
  18532. var bw = this.body.getTextWidth();
  18533. if(this.title){
  18534. bw = Math.max(bw, this.header.child('span').getTextWidth(this.title));
  18535. }
  18536. bw += this.getFrameWidth() + (this.closable ? 20 : 0) + this.body.getPadding("lr");
  18537. this.setWidth(bw.constrain(this.minWidth, this.maxWidth));
  18538. // IE7 repaint bug on initial show
  18539. if(Ext.isIE7 && !this.repainted){
  18540. this.el.repaint();
  18541. this.repainted = true;
  18542. }
  18543. },
  18544. showBy : function(el, pos){
  18545. if(!this.rendered){
  18546. this.render(Ext.getBody());
  18547. }
  18548. this.showAt(this.el.getAlignToXY(el, pos || this.defaultAlign));
  18549. },
  18550. initDraggable : function(){
  18551. this.dd = new Ext.Tip.DD(this, typeof this.draggable == 'boolean' ? null : this.draggable);
  18552. this.header.addClass('x-tip-draggable');
  18553. }
  18554. });
  18555. // private - custom Tip DD implementation
  18556. Ext.Tip.DD = function(tip, config){
  18557. Ext.apply(this, config);
  18558. this.tip = tip;
  18559. Ext.Tip.DD.superclass.constructor.call(this, tip.el.id, 'WindowDD-'+tip.id);
  18560. this.setHandleElId(tip.header.id);
  18561. this.scroll = false;
  18562. };
  18563. Ext.extend(Ext.Tip.DD, Ext.dd.DD, {
  18564. moveOnly:true,
  18565. scroll:false,
  18566. headerOffsets:[100, 25],
  18567. startDrag : function(){
  18568. this.tip.el.disableShadow();
  18569. },
  18570. endDrag : function(e){
  18571. this.tip.el.enableShadow(true);
  18572. }
  18573. });
  18574. Ext.ToolTip = Ext.extend(Ext.Tip, {
  18575. showDelay: 500,
  18576. hideDelay: 200,
  18577. dismissDelay: 5000,
  18578. mouseOffset: [15,18],
  18579. trackMouse : false,
  18580. constrainPosition: true,
  18581. // private
  18582. initComponent: function(){
  18583. Ext.ToolTip.superclass.initComponent.call(this);
  18584. this.lastActive = new Date();
  18585. this.initTarget();
  18586. },
  18587. // private
  18588. initTarget : function(){
  18589. if(this.target){
  18590. this.target = Ext.get(this.target);
  18591. this.target.on('mouseover', this.onTargetOver, this);
  18592. this.target.on('mouseout', this.onTargetOut, this);
  18593. this.target.on('mousemove', this.onMouseMove, this);
  18594. }
  18595. },
  18596. // private
  18597. onMouseMove : function(e){
  18598. this.targetXY = e.getXY();
  18599. if(!this.hidden && this.trackMouse){
  18600. this.setPagePosition(this.getTargetXY());
  18601. }
  18602. },
  18603. // private
  18604. getTargetXY : function(){
  18605. return [this.targetXY[0]+this.mouseOffset[0], this.targetXY[1]+this.mouseOffset[1]];
  18606. },
  18607. // private
  18608. onTargetOver : function(e){
  18609. if(this.disabled || e.within(this.target.dom, true)){
  18610. return;
  18611. }
  18612. this.clearTimer('hide');
  18613. this.targetXY = e.getXY();
  18614. this.delayShow();
  18615. },
  18616. // private
  18617. delayShow : function(){
  18618. if(this.hidden && !this.showTimer){
  18619. if(this.lastActive.getElapsed() < this.quickShowInterval){
  18620. this.show();
  18621. }else{
  18622. this.showTimer = this.show.defer(this.showDelay, this);
  18623. }
  18624. }else if(!this.hidden && this.autoHide !== false){
  18625. this.show();
  18626. }
  18627. },
  18628. // private
  18629. onTargetOut : function(e){
  18630. if(this.disabled || e.within(this.target.dom, true)){
  18631. return;
  18632. }
  18633. this.clearTimer('show');
  18634. if(this.autoHide !== false){
  18635. this.delayHide();
  18636. }
  18637. },
  18638. // private
  18639. delayHide : function(){
  18640. if(!this.hidden && !this.hideTimer){
  18641. this.hideTimer = this.hide.defer(this.hideDelay, this);
  18642. }
  18643. },
  18644. hide: function(){
  18645. this.clearTimer('dismiss');
  18646. this.lastActive = new Date();
  18647. Ext.ToolTip.superclass.hide.call(this);
  18648. },
  18649. show : function(){
  18650. this.showAt(this.getTargetXY());
  18651. },
  18652. // inherit docs
  18653. showAt : function(xy){
  18654. this.lastActive = new Date();
  18655. this.clearTimers();
  18656. Ext.ToolTip.superclass.showAt.call(this, xy);
  18657. if(this.dismissDelay && this.autoHide !== false){
  18658. this.dismissTimer = this.hide.defer(this.dismissDelay, this);
  18659. }
  18660. },
  18661. // private
  18662. clearTimer : function(name){
  18663. name = name + 'Timer';
  18664. clearTimeout(this[name]);
  18665. delete this[name];
  18666. },
  18667. // private
  18668. clearTimers : function(){
  18669. this.clearTimer('show');
  18670. this.clearTimer('dismiss');
  18671. this.clearTimer('hide');
  18672. },
  18673. // private
  18674. onShow : function(){
  18675. Ext.ToolTip.superclass.onShow.call(this);
  18676. Ext.getDoc().on('mousedown', this.onDocMouseDown, this);
  18677. },
  18678. // private
  18679. onHide : function(){
  18680. Ext.ToolTip.superclass.onHide.call(this);
  18681. Ext.getDoc().un('mousedown', this.onDocMouseDown, this);
  18682. },
  18683. // private
  18684. onDocMouseDown : function(e){
  18685. if(this.autoHide !== false && !e.within(this.el.dom)){
  18686. this.disable();
  18687. this.enable.defer(100, this);
  18688. }
  18689. },
  18690. // private
  18691. onDisable : function(){
  18692. this.clearTimers();
  18693. this.hide();
  18694. },
  18695. // private
  18696. adjustPosition : function(x, y){
  18697. // keep the position from being under the mouse
  18698. var ay = this.targetXY[1], h = this.getSize().height;
  18699. if(this.constrainPosition && y <= ay && (y+h) >= ay){
  18700. y = ay-h-5;
  18701. }
  18702. return {x : x, y: y};
  18703. },
  18704. // private
  18705. onDestroy : function(){
  18706. Ext.ToolTip.superclass.onDestroy.call(this);
  18707. if(this.target){
  18708. this.target.un('mouseover', this.onTargetOver, this);
  18709. this.target.un('mouseout', this.onTargetOut, this);
  18710. this.target.un('mousemove', this.onMouseMove, this);
  18711. }
  18712. }
  18713. });
  18714. Ext.QuickTip = Ext.extend(Ext.ToolTip, {
  18715. interceptTitles : false,
  18716. // private
  18717. tagConfig : {
  18718. namespace : "ext",
  18719. attribute : "qtip",
  18720. width : "qwidth",
  18721. target : "target",
  18722. title : "qtitle",
  18723. hide : "hide",
  18724. cls : "qclass",
  18725. align : "qalign"
  18726. },
  18727. // private
  18728. initComponent : function(){
  18729. this.target = this.target || Ext.getDoc();
  18730. this.targets = this.targets || {};
  18731. Ext.QuickTip.superclass.initComponent.call(this);
  18732. },
  18733. register : function(config){
  18734. var cs = Ext.isArray(config) ? config : arguments;
  18735. for(var i = 0, len = cs.length; i < len; i++){
  18736. var c = cs[i];
  18737. var target = c.target;
  18738. if(target){
  18739. if(Ext.isArray(target)){
  18740. for(var j = 0, jlen = target.length; j < jlen; j++){
  18741. this.targets[Ext.id(target[j])] = c;
  18742. }
  18743. } else{
  18744. this.targets[Ext.id(target)] = c;
  18745. }
  18746. }
  18747. }
  18748. },
  18749. unregister : function(el){
  18750. delete this.targets[Ext.id(el)];
  18751. },
  18752. // private
  18753. onTargetOver : function(e){
  18754. if(this.disabled){
  18755. return;
  18756. }
  18757. this.targetXY = e.getXY();
  18758. var t = e.getTarget();
  18759. if(!t || t.nodeType !== 1 || t == document || t == document.body){
  18760. return;
  18761. }
  18762. if(this.activeTarget && t == this.activeTarget.el){
  18763. this.clearTimer('hide');
  18764. this.show();
  18765. return;
  18766. }
  18767. if(t && this.targets[t.id]){
  18768. this.activeTarget = this.targets[t.id];
  18769. this.activeTarget.el = t;
  18770. this.delayShow();
  18771. return;
  18772. }
  18773. var ttp, et = Ext.fly(t), cfg = this.tagConfig;
  18774. var ns = cfg.namespace;
  18775. if(this.interceptTitles && t.title){
  18776. ttp = t.title;
  18777. t.qtip = ttp;
  18778. t.removeAttribute("title");
  18779. e.preventDefault();
  18780. } else{
  18781. ttp = t.qtip || et.getAttributeNS(ns, cfg.attribute);
  18782. }
  18783. if(ttp){
  18784. var autoHide = et.getAttributeNS(ns, cfg.hide);
  18785. this.activeTarget = {
  18786. el: t,
  18787. text: ttp,
  18788. width: et.getAttributeNS(ns, cfg.width),
  18789. autoHide: autoHide != "user" && autoHide !== 'false',
  18790. title: et.getAttributeNS(ns, cfg.title),
  18791. cls: et.getAttributeNS(ns, cfg.cls),
  18792. align: et.getAttributeNS(ns, cfg.align)
  18793. };
  18794. this.delayShow();
  18795. }
  18796. },
  18797. // private
  18798. onTargetOut : function(e){
  18799. this.clearTimer('show');
  18800. if(this.autoHide !== false){
  18801. this.delayHide();
  18802. }
  18803. },
  18804. // inherit docs
  18805. showAt : function(xy){
  18806. var t = this.activeTarget;
  18807. if(t){
  18808. if(!this.rendered){
  18809. this.render(Ext.getBody());
  18810. this.activeTarget = t;
  18811. }
  18812. if(t.width){
  18813. this.setWidth(t.width);
  18814. this.body.setWidth(this.adjustBodyWidth(t.width - this.getFrameWidth()));
  18815. this.measureWidth = false;
  18816. } else{
  18817. this.measureWidth = true;
  18818. }
  18819. this.setTitle(t.title || '');
  18820. this.body.update(t.text);
  18821. this.autoHide = t.autoHide;
  18822. this.dismissDelay = t.dismissDelay || this.dismissDelay;
  18823. if(this.lastCls){
  18824. this.el.removeClass(this.lastCls);
  18825. delete this.lastCls;
  18826. }
  18827. if(t.cls){
  18828. this.el.addClass(t.cls);
  18829. this.lastCls = t.cls;
  18830. }
  18831. if(t.align){ // TODO: this doesn't seem to work consistently
  18832. xy = this.el.getAlignToXY(t.el, t.align);
  18833. this.constrainPosition = false;
  18834. } else{
  18835. this.constrainPosition = true;
  18836. }
  18837. }
  18838. Ext.QuickTip.superclass.showAt.call(this, xy);
  18839. },
  18840. // inherit docs
  18841. hide: function(){
  18842. delete this.activeTarget;
  18843. Ext.QuickTip.superclass.hide.call(this);
  18844. }
  18845. });
  18846. Ext.QuickTips = function(){
  18847. var tip, locks = [];
  18848. return {
  18849. init : function(autoRender){
  18850. if(!tip){
  18851. if(!Ext.isReady){
  18852. Ext.onReady(function(){
  18853. Ext.QuickTips.init(autoRender);
  18854. });
  18855. return;
  18856. }
  18857. tip = new Ext.QuickTip({elements:'header,body'});
  18858. if(autoRender !== false){
  18859. tip.render(Ext.getBody());
  18860. }
  18861. }
  18862. },
  18863. enable : function(){
  18864. if(tip){
  18865. locks.pop();
  18866. if(locks.length < 1){
  18867. tip.enable();
  18868. }
  18869. }
  18870. },
  18871. disable : function(){
  18872. if(tip){
  18873. tip.disable();
  18874. }
  18875. locks.push(1);
  18876. },
  18877. isEnabled : function(){
  18878. return tip !== undefined && !tip.disabled;
  18879. },
  18880. getQuickTip : function(){
  18881. return tip;
  18882. },
  18883. register : function(){
  18884. tip.register.apply(tip, arguments);
  18885. },
  18886. unregister : function(){
  18887. tip.unregister.apply(tip, arguments);
  18888. },
  18889. tips :function(){
  18890. tip.register.apply(tip, arguments);
  18891. }
  18892. }
  18893. }();
  18894. Ext.tree.TreePanel = Ext.extend(Ext.Panel, {
  18895. rootVisible : true,
  18896. animate: Ext.enableFx,
  18897. lines : true,
  18898. enableDD : false,
  18899. hlDrop : Ext.enableFx,
  18900. pathSeparator: "/",
  18901. initComponent : function(){
  18902. Ext.tree.TreePanel.superclass.initComponent.call(this);
  18903. if(!this.eventModel){
  18904. this.eventModel = new Ext.tree.TreeEventModel(this);
  18905. }
  18906. // initialize the loader
  18907. var l = this.loader;
  18908. if(!l){
  18909. l = new Ext.tree.TreeLoader({
  18910. dataUrl: this.dataUrl
  18911. });
  18912. }else if(typeof l == 'object' && !l.load){
  18913. l = new Ext.tree.TreeLoader(l);
  18914. }
  18915. this.loader = l;
  18916. this.nodeHash = {};
  18917. if(this.root){
  18918. this.setRootNode(this.root);
  18919. }
  18920. this.addEvents(
  18921. "append",
  18922. "remove",
  18923. "movenode",
  18924. "insert",
  18925. "beforeappend",
  18926. "beforeremove",
  18927. "beforemovenode",
  18928. "beforeinsert",
  18929. "beforeload",
  18930. "load",
  18931. "textchange",
  18932. "beforeexpandnode",
  18933. "beforecollapsenode",
  18934. "expandnode",
  18935. "disabledchange",
  18936. "collapsenode",
  18937. "beforeclick",
  18938. "click",
  18939. "checkchange",
  18940. "dblclick",
  18941. "contextmenu",
  18942. "beforechildrenrendered",
  18943. "startdrag",
  18944. "enddrag",
  18945. "dragdrop",
  18946. "beforenodedrop",
  18947. "nodedrop",
  18948. "nodedragover"
  18949. );
  18950. if(this.singleExpand){
  18951. this.on("beforeexpandnode", this.restrictExpand, this);
  18952. }
  18953. },
  18954. // private
  18955. proxyNodeEvent : function(ename, a1, a2, a3, a4, a5, a6){
  18956. if(ename == 'collapse' || ename == 'expand' || ename == 'beforecollapse' || ename == 'beforeexpand' || ename == 'move' || ename == 'beforemove'){
  18957. ename = ename+'node';
  18958. }
  18959. // args inline for performance while bubbling events
  18960. return this.fireEvent(ename, a1, a2, a3, a4, a5, a6);
  18961. },
  18962. getRootNode : function(){
  18963. return this.root;
  18964. },
  18965. setRootNode : function(node){
  18966. if(!node.render){ // attributes passed
  18967. node = this.loader.createNode(node);
  18968. }
  18969. this.root = node;
  18970. node.ownerTree = this;
  18971. node.isRoot = true;
  18972. this.registerNode(node);
  18973. if(!this.rootVisible){
  18974. var uiP = node.attributes.uiProvider;
  18975. node.ui = uiP ? new uiP(node) : new Ext.tree.RootTreeNodeUI(node);
  18976. }
  18977. return node;
  18978. },
  18979. getNodeById : function(id){
  18980. return this.nodeHash[id];
  18981. },
  18982. // private
  18983. registerNode : function(node){
  18984. this.nodeHash[node.id] = node;
  18985. },
  18986. // private
  18987. unregisterNode : function(node){
  18988. delete this.nodeHash[node.id];
  18989. },
  18990. // private
  18991. toString : function(){
  18992. return "[Tree"+(this.id?" "+this.id:"")+"]";
  18993. },
  18994. // private
  18995. restrictExpand : function(node){
  18996. var p = node.parentNode;
  18997. if(p){
  18998. if(p.expandedChild && p.expandedChild.parentNode == p){
  18999. p.expandedChild.collapse();
  19000. }
  19001. p.expandedChild = node;
  19002. }
  19003. },
  19004. getChecked : function(a, startNode){
  19005. startNode = startNode || this.root;
  19006. var r = [];
  19007. var f = function(){
  19008. if(this.attributes.checked){
  19009. r.push(!a ? this : (a == 'id' ? this.id : this.attributes[a]));
  19010. }
  19011. }
  19012. startNode.cascade(f);
  19013. return r;
  19014. },
  19015. getEl : function(){
  19016. return this.el;
  19017. },
  19018. getLoader : function(){
  19019. return this.loader;
  19020. },
  19021. expandAll : function(){
  19022. this.root.expand(true);
  19023. },
  19024. collapseAll : function(){
  19025. this.root.collapse(true);
  19026. },
  19027. getSelectionModel : function(){
  19028. if(!this.selModel){
  19029. this.selModel = new Ext.tree.DefaultSelectionModel();
  19030. }
  19031. return this.selModel;
  19032. },
  19033. expandPath : function(path, attr, callback){
  19034. attr = attr || "id";
  19035. var keys = path.split(this.pathSeparator);
  19036. var curNode = this.root;
  19037. if(curNode.attributes[attr] != keys[1]){ // invalid root
  19038. if(callback){
  19039. callback(false, null);
  19040. }
  19041. return;
  19042. }
  19043. var index = 1;
  19044. var f = function(){
  19045. if(++index == keys.length){
  19046. if(callback){
  19047. callback(true, curNode);
  19048. }
  19049. return;
  19050. }
  19051. var c = curNode.findChild(attr, keys[index]);
  19052. if(!c){
  19053. if(callback){
  19054. callback(false, curNode);
  19055. }
  19056. return;
  19057. }
  19058. curNode = c;
  19059. c.expand(false, false, f);
  19060. };
  19061. curNode.expand(false, false, f);
  19062. },
  19063. selectPath : function(path, attr, callback){
  19064. attr = attr || "id";
  19065. var keys = path.split(this.pathSeparator);
  19066. var v = keys.pop();
  19067. if(keys.length > 0){
  19068. var f = function(success, node){
  19069. if(success && node){
  19070. var n = node.findChild(attr, v);
  19071. if(n){
  19072. n.select();
  19073. if(callback){
  19074. callback(true, n);
  19075. }
  19076. }else if(callback){
  19077. callback(false, n);
  19078. }
  19079. }else{
  19080. if(callback){
  19081. callback(false, n);
  19082. }
  19083. }
  19084. };
  19085. this.expandPath(keys.join(this.pathSeparator), attr, f);
  19086. }else{
  19087. this.root.select();
  19088. if(callback){
  19089. callback(true, this.root);
  19090. }
  19091. }
  19092. },
  19093. getTreeEl : function(){
  19094. return this.body;
  19095. },
  19096. // private
  19097. onRender : function(ct, position){
  19098. Ext.tree.TreePanel.superclass.onRender.call(this, ct, position);
  19099. this.el.addClass('x-tree');
  19100. this.innerCt = this.body.createChild({tag:"ul",
  19101. cls:"x-tree-root-ct " +
  19102. (this.useArrows ? 'x-tree-arrows' : this.lines ? "x-tree-lines" : "x-tree-no-lines")});
  19103. },
  19104. // private
  19105. initEvents : function(){
  19106. Ext.tree.TreePanel.superclass.initEvents.call(this);
  19107. if(this.containerScroll){
  19108. Ext.dd.ScrollManager.register(this.body);
  19109. }
  19110. if((this.enableDD || this.enableDrop) && !this.dropZone){
  19111. this.dropZone = new Ext.tree.TreeDropZone(this, this.dropConfig || {
  19112. ddGroup: this.ddGroup || "TreeDD", appendOnly: this.ddAppendOnly === true
  19113. });
  19114. }
  19115. if((this.enableDD || this.enableDrag) && !this.dragZone){
  19116. this.dragZone = new Ext.tree.TreeDragZone(this, this.dragConfig || {
  19117. ddGroup: this.ddGroup || "TreeDD",
  19118. scroll: this.ddScroll
  19119. });
  19120. }
  19121. this.getSelectionModel().init(this);
  19122. },
  19123. // private
  19124. afterRender : function(){
  19125. Ext.tree.TreePanel.superclass.afterRender.call(this);
  19126. this.root.render();
  19127. if(!this.rootVisible){
  19128. this.root.renderChildren();
  19129. }
  19130. },
  19131. onDestroy : function(){
  19132. if(this.rendered){
  19133. this.body.removeAllListeners();
  19134. Ext.dd.ScrollManager.unregister(this.body);
  19135. if(this.dropZone){
  19136. this.dropZone.unreg();
  19137. }
  19138. if(this.dragZone){
  19139. this.dragZone.unreg();
  19140. }
  19141. }
  19142. this.root.destroy();
  19143. this.nodeHash = null;
  19144. Ext.tree.TreePanel.superclass.onDestroy.call(this);
  19145. }
  19146. });
  19147. Ext.tree.TreePanel.nodeTypes = {};
  19148. Ext.reg('treepanel', Ext.tree.TreePanel);
  19149. Ext.tree.TreeEventModel = function(tree){
  19150. this.tree = tree;
  19151. this.tree.on('render', this.initEvents, this);
  19152. }
  19153. Ext.tree.TreeEventModel.prototype = {
  19154. initEvents : function(){
  19155. var el = this.tree.getTreeEl();
  19156. el.on('click', this.delegateClick, this);
  19157. if(this.tree.trackMouseOver !== false){
  19158. el.on('mouseover', this.delegateOver, this);
  19159. el.on('mouseout', this.delegateOut, this);
  19160. }
  19161. el.on('dblclick', this.delegateDblClick, this);
  19162. el.on('contextmenu', this.delegateContextMenu, this);
  19163. },
  19164. getNode : function(e){
  19165. var t;
  19166. if(t = e.getTarget('.x-tree-node-el', 10)){
  19167. var id = Ext.fly(t, '_treeEvents').getAttributeNS('ext', 'tree-node-id');
  19168. if(id){
  19169. return this.tree.getNodeById(id);
  19170. }
  19171. }
  19172. return null;
  19173. },
  19174. getNodeTarget : function(e){
  19175. var t = e.getTarget('.x-tree-node-icon', 1);
  19176. if(!t){
  19177. t = e.getTarget('.x-tree-node-el', 6);
  19178. }
  19179. return t;
  19180. },
  19181. delegateOut : function(e, t){
  19182. if(!this.beforeEvent(e)){
  19183. return;
  19184. }
  19185. if(e.getTarget('.x-tree-ec-icon', 1)){
  19186. var n = this.getNode(e);
  19187. this.onIconOut(e, n);
  19188. if(n == this.lastEcOver){
  19189. delete this.lastEcOver;
  19190. }
  19191. }
  19192. if((t = this.getNodeTarget(e)) && !e.within(t, true)){
  19193. this.onNodeOut(e, this.getNode(e));
  19194. }
  19195. },
  19196. delegateOver : function(e, t){
  19197. if(!this.beforeEvent(e)){
  19198. return;
  19199. }
  19200. if(this.lastEcOver){ // prevent hung highlight
  19201. this.onIconOut(e, this.lastEcOver);
  19202. delete this.lastEcOver;
  19203. }
  19204. if(e.getTarget('.x-tree-ec-icon', 1)){
  19205. this.lastEcOver = this.getNode(e);
  19206. this.onIconOver(e, this.lastEcOver);
  19207. }
  19208. if(t = this.getNodeTarget(e)){
  19209. this.onNodeOver(e, this.getNode(e));
  19210. }
  19211. },
  19212. delegateClick : function(e, t){
  19213. if(!this.beforeEvent(e)){
  19214. return;
  19215. }
  19216. if(e.getTarget('input[type=checkbox]', 1)){
  19217. this.onCheckboxClick(e, this.getNode(e));
  19218. }
  19219. else if(e.getTarget('.x-tree-ec-icon', 1)){
  19220. this.onIconClick(e, this.getNode(e));
  19221. }
  19222. else if(this.getNodeTarget(e)){
  19223. this.onNodeClick(e, this.getNode(e));
  19224. }
  19225. },
  19226. delegateDblClick : function(e, t){
  19227. if(this.beforeEvent(e) && this.getNodeTarget(e)){
  19228. this.onNodeDblClick(e, this.getNode(e));
  19229. }
  19230. },
  19231. delegateContextMenu : function(e, t){
  19232. if(this.beforeEvent(e) && this.getNodeTarget(e)){
  19233. this.onNodeContextMenu(e, this.getNode(e));
  19234. }
  19235. },
  19236. onNodeClick : function(e, node){
  19237. node.ui.onClick(e);
  19238. },
  19239. onNodeOver : function(e, node){
  19240. node.ui.onOver(e);
  19241. },
  19242. onNodeOut : function(e, node){
  19243. node.ui.onOut(e);
  19244. },
  19245. onIconOver : function(e, node){
  19246. node.ui.addClass('x-tree-ec-over');
  19247. },
  19248. onIconOut : function(e, node){
  19249. node.ui.removeClass('x-tree-ec-over');
  19250. },
  19251. onIconClick : function(e, node){
  19252. node.ui.ecClick(e);
  19253. },
  19254. onCheckboxClick : function(e, node){
  19255. node.ui.onCheckChange(e);
  19256. },
  19257. onNodeDblClick : function(e, node){
  19258. node.ui.onDblClick(e);
  19259. },
  19260. onNodeContextMenu : function(e, node){
  19261. node.ui.onContextMenu(e);
  19262. },
  19263. beforeEvent : function(e){
  19264. if(this.disabled){
  19265. e.stopEvent();
  19266. return false;
  19267. }
  19268. return true;
  19269. },
  19270. disable: function(){
  19271. this.disabled = true;
  19272. },
  19273. enable: function(){
  19274. this.disabled = false;
  19275. }
  19276. };
  19277. Ext.tree.DefaultSelectionModel = function(config){
  19278. this.selNode = null;
  19279. this.addEvents(
  19280. "selectionchange",
  19281. "beforeselect"
  19282. );
  19283. Ext.apply(this, config);
  19284. Ext.tree.DefaultSelectionModel.superclass.constructor.call(this);
  19285. };
  19286. Ext.extend(Ext.tree.DefaultSelectionModel, Ext.util.Observable, {
  19287. init : function(tree){
  19288. this.tree = tree;
  19289. tree.getTreeEl().on("keydown", this.onKeyDown, this);
  19290. tree.on("click", this.onNodeClick, this);
  19291. },
  19292. onNodeClick : function(node, e){
  19293. this.select(node);
  19294. },
  19295. select : function(node){
  19296. var last = this.selNode;
  19297. if(last != node && this.fireEvent('beforeselect', this, node, last) !== false){
  19298. if(last){
  19299. last.ui.onSelectedChange(false);
  19300. }
  19301. this.selNode = node;
  19302. node.ui.onSelectedChange(true);
  19303. this.fireEvent("selectionchange", this, node, last);
  19304. }
  19305. return node;
  19306. },
  19307. unselect : function(node){
  19308. if(this.selNode == node){
  19309. this.clearSelections();
  19310. }
  19311. },
  19312. clearSelections : function(){
  19313. var n = this.selNode;
  19314. if(n){
  19315. n.ui.onSelectedChange(false);
  19316. this.selNode = null;
  19317. this.fireEvent("selectionchange", this, null);
  19318. }
  19319. return n;
  19320. },
  19321. getSelectedNode : function(){
  19322. return this.selNode;
  19323. },
  19324. isSelected : function(node){
  19325. return this.selNode == node;
  19326. },
  19327. selectPrevious : function(){
  19328. var s = this.selNode || this.lastSelNode;
  19329. if(!s){
  19330. return null;
  19331. }
  19332. var ps = s.previousSibling;
  19333. if(ps){
  19334. if(!ps.isExpanded() || ps.childNodes.length < 1){
  19335. return this.select(ps);
  19336. } else{
  19337. var lc = ps.lastChild;
  19338. while(lc && lc.isExpanded() && lc.childNodes.length > 0){
  19339. lc = lc.lastChild;
  19340. }
  19341. return this.select(lc);
  19342. }
  19343. } else if(s.parentNode && (this.tree.rootVisible || !s.parentNode.isRoot)){
  19344. return this.select(s.parentNode);
  19345. }
  19346. return null;
  19347. },
  19348. selectNext : function(){
  19349. var s = this.selNode || this.lastSelNode;
  19350. if(!s){
  19351. return null;
  19352. }
  19353. if(s.firstChild && s.isExpanded()){
  19354. return this.select(s.firstChild);
  19355. }else if(s.nextSibling){
  19356. return this.select(s.nextSibling);
  19357. }else if(s.parentNode){
  19358. var newS = null;
  19359. s.parentNode.bubble(function(){
  19360. if(this.nextSibling){
  19361. newS = this.getOwnerTree().selModel.select(this.nextSibling);
  19362. return false;
  19363. }
  19364. });
  19365. return newS;
  19366. }
  19367. return null;
  19368. },
  19369. onKeyDown : function(e){
  19370. var s = this.selNode || this.lastSelNode;
  19371. // undesirable, but required
  19372. var sm = this;
  19373. if(!s){
  19374. return;
  19375. }
  19376. var k = e.getKey();
  19377. switch(k){
  19378. case e.DOWN:
  19379. e.stopEvent();
  19380. this.selectNext();
  19381. break;
  19382. case e.UP:
  19383. e.stopEvent();
  19384. this.selectPrevious();
  19385. break;
  19386. case e.RIGHT:
  19387. e.preventDefault();
  19388. if(s.hasChildNodes()){
  19389. if(!s.isExpanded()){
  19390. s.expand();
  19391. }else if(s.firstChild){
  19392. this.select(s.firstChild, e);
  19393. }
  19394. }
  19395. break;
  19396. case e.LEFT:
  19397. e.preventDefault();
  19398. if(s.hasChildNodes() && s.isExpanded()){
  19399. s.collapse();
  19400. }else if(s.parentNode && (this.tree.rootVisible || s.parentNode != this.tree.getRootNode())){
  19401. this.select(s.parentNode, e);
  19402. }
  19403. break;
  19404. };
  19405. }
  19406. });
  19407. Ext.tree.MultiSelectionModel = function(config){
  19408. this.selNodes = [];
  19409. this.selMap = {};
  19410. this.addEvents(
  19411. "selectionchange"
  19412. );
  19413. Ext.apply(this, config);
  19414. Ext.tree.MultiSelectionModel.superclass.constructor.call(this);
  19415. };
  19416. Ext.extend(Ext.tree.MultiSelectionModel, Ext.util.Observable, {
  19417. init : function(tree){
  19418. this.tree = tree;
  19419. tree.getTreeEl().on("keydown", this.onKeyDown, this);
  19420. tree.on("click", this.onNodeClick, this);
  19421. },
  19422. onNodeClick : function(node, e){
  19423. this.select(node, e, e.ctrlKey);
  19424. },
  19425. select : function(node, e, keepExisting){
  19426. if(keepExisting !== true){
  19427. this.clearSelections(true);
  19428. }
  19429. if(this.isSelected(node)){
  19430. this.lastSelNode = node;
  19431. return node;
  19432. }
  19433. this.selNodes.push(node);
  19434. this.selMap[node.id] = node;
  19435. this.lastSelNode = node;
  19436. node.ui.onSelectedChange(true);
  19437. this.fireEvent("selectionchange", this, this.selNodes);
  19438. return node;
  19439. },
  19440. unselect : function(node){
  19441. if(this.selMap[node.id]){
  19442. node.ui.onSelectedChange(false);
  19443. var sn = this.selNodes;
  19444. var index = sn.indexOf(node);
  19445. if(index != -1){
  19446. this.selNodes.splice(index, 1);
  19447. }
  19448. delete this.selMap[node.id];
  19449. this.fireEvent("selectionchange", this, this.selNodes);
  19450. }
  19451. },
  19452. clearSelections : function(suppressEvent){
  19453. var sn = this.selNodes;
  19454. if(sn.length > 0){
  19455. for(var i = 0, len = sn.length; i < len; i++){
  19456. sn[i].ui.onSelectedChange(false);
  19457. }
  19458. this.selNodes = [];
  19459. this.selMap = {};
  19460. if(suppressEvent !== true){
  19461. this.fireEvent("selectionchange", this, this.selNodes);
  19462. }
  19463. }
  19464. },
  19465. isSelected : function(node){
  19466. return this.selMap[node.id] ? true : false;
  19467. },
  19468. getSelectedNodes : function(){
  19469. return this.selNodes;
  19470. },
  19471. onKeyDown : Ext.tree.DefaultSelectionModel.prototype.onKeyDown,
  19472. selectNext : Ext.tree.DefaultSelectionModel.prototype.selectNext,
  19473. selectPrevious : Ext.tree.DefaultSelectionModel.prototype.selectPrevious
  19474. });
  19475. Ext.tree.TreeNode = function(attributes){
  19476. attributes = attributes || {};
  19477. if(typeof attributes == "string"){
  19478. attributes = {text: attributes};
  19479. }
  19480. this.childrenRendered = false;
  19481. this.rendered = false;
  19482. Ext.tree.TreeNode.superclass.constructor.call(this, attributes);
  19483. this.expanded = attributes.expanded === true;
  19484. this.isTarget = attributes.isTarget !== false;
  19485. this.draggable = attributes.draggable !== false && attributes.allowDrag !== false;
  19486. this.allowChildren = attributes.allowChildren !== false && attributes.allowDrop !== false;
  19487. this.text = attributes.text;
  19488. this.disabled = attributes.disabled === true;
  19489. this.addEvents(
  19490. "textchange",
  19491. "beforeexpand",
  19492. "beforecollapse",
  19493. "expand",
  19494. "disabledchange",
  19495. "collapse",
  19496. "beforeclick",
  19497. "click",
  19498. "checkchange",
  19499. "dblclick",
  19500. "contextmenu",
  19501. "beforechildrenrendered"
  19502. );
  19503. var uiClass = this.attributes.uiProvider || this.defaultUI || Ext.tree.TreeNodeUI;
  19504. this.ui = new uiClass(this);
  19505. };
  19506. Ext.extend(Ext.tree.TreeNode, Ext.data.Node, {
  19507. preventHScroll: true,
  19508. isExpanded : function(){
  19509. return this.expanded;
  19510. },
  19511. getUI : function(){
  19512. return this.ui;
  19513. },
  19514. getLoader : function(){
  19515. var owner;
  19516. return this.loader || ((owner = this.getOwnerTree()) && owner.loader ? owner.loader : new Ext.tree.TreeLoader());
  19517. },
  19518. // private override
  19519. setFirstChild : function(node){
  19520. var of = this.firstChild;
  19521. Ext.tree.TreeNode.superclass.setFirstChild.call(this, node);
  19522. if(this.childrenRendered && of && node != of){
  19523. of.renderIndent(true, true);
  19524. }
  19525. if(this.rendered){
  19526. this.renderIndent(true, true);
  19527. }
  19528. },
  19529. // private override
  19530. setLastChild : function(node){
  19531. var ol = this.lastChild;
  19532. Ext.tree.TreeNode.superclass.setLastChild.call(this, node);
  19533. if(this.childrenRendered && ol && node != ol){
  19534. ol.renderIndent(true, true);
  19535. }
  19536. if(this.rendered){
  19537. this.renderIndent(true, true);
  19538. }
  19539. },
  19540. // these methods are overridden to provide lazy rendering support
  19541. // private override
  19542. appendChild : function(n){
  19543. if(!n.render && !Ext.isArray(n)){
  19544. n = this.getLoader().createNode(n);
  19545. }
  19546. var node = Ext.tree.TreeNode.superclass.appendChild.call(this, n);
  19547. if(node && this.childrenRendered){
  19548. node.render();
  19549. }
  19550. this.ui.updateExpandIcon();
  19551. return node;
  19552. },
  19553. // private override
  19554. removeChild : function(node){
  19555. this.ownerTree.getSelectionModel().unselect(node);
  19556. Ext.tree.TreeNode.superclass.removeChild.apply(this, arguments);
  19557. // if it's been rendered remove dom node
  19558. if(this.childrenRendered){
  19559. node.ui.remove();
  19560. }
  19561. if(this.childNodes.length < 1){
  19562. this.collapse(false, false);
  19563. }else{
  19564. this.ui.updateExpandIcon();
  19565. }
  19566. if(!this.firstChild && !this.isHiddenRoot()) {
  19567. this.childrenRendered = false;
  19568. }
  19569. return node;
  19570. },
  19571. // private override
  19572. insertBefore : function(node, refNode){
  19573. if(!node.render){
  19574. node = this.getLoader().createNode(node);
  19575. }
  19576. var newNode = Ext.tree.TreeNode.superclass.insertBefore.apply(this, arguments);
  19577. if(newNode && refNode && this.childrenRendered){
  19578. node.render();
  19579. }
  19580. this.ui.updateExpandIcon();
  19581. return newNode;
  19582. },
  19583. setText : function(text){
  19584. var oldText = this.text;
  19585. this.text = text;
  19586. this.attributes.text = text;
  19587. if(this.rendered){ // event without subscribing
  19588. this.ui.onTextChange(this, text, oldText);
  19589. }
  19590. this.fireEvent("textchange", this, text, oldText);
  19591. },
  19592. select : function(){
  19593. this.getOwnerTree().getSelectionModel().select(this);
  19594. },
  19595. unselect : function(){
  19596. this.getOwnerTree().getSelectionModel().unselect(this);
  19597. },
  19598. isSelected : function(){
  19599. return this.getOwnerTree().getSelectionModel().isSelected(this);
  19600. },
  19601. expand : function(deep, anim, callback){
  19602. if(!this.expanded){
  19603. if(this.fireEvent("beforeexpand", this, deep, anim) === false){
  19604. return;
  19605. }
  19606. if(!this.childrenRendered){
  19607. this.renderChildren();
  19608. }
  19609. this.expanded = true;
  19610. if(!this.isHiddenRoot() && (this.getOwnerTree().animate && anim !== false) || anim){
  19611. this.ui.animExpand(function(){
  19612. this.fireEvent("expand", this);
  19613. if(typeof callback == "function"){
  19614. callback(this);
  19615. }
  19616. if(deep === true){
  19617. this.expandChildNodes(true);
  19618. }
  19619. }.createDelegate(this));
  19620. return;
  19621. }else{
  19622. this.ui.expand();
  19623. this.fireEvent("expand", this);
  19624. if(typeof callback == "function"){
  19625. callback(this);
  19626. }
  19627. }
  19628. }else{
  19629. if(typeof callback == "function"){
  19630. callback(this);
  19631. }
  19632. }
  19633. if(deep === true){
  19634. this.expandChildNodes(true);
  19635. }
  19636. },
  19637. isHiddenRoot : function(){
  19638. return this.isRoot && !this.getOwnerTree().rootVisible;
  19639. },
  19640. collapse : function(deep, anim){
  19641. if(this.expanded && !this.isHiddenRoot()){
  19642. if(this.fireEvent("beforecollapse", this, deep, anim) === false){
  19643. return;
  19644. }
  19645. this.expanded = false;
  19646. if((this.getOwnerTree().animate && anim !== false) || anim){
  19647. this.ui.animCollapse(function(){
  19648. this.fireEvent("collapse", this);
  19649. if(deep === true){
  19650. this.collapseChildNodes(true);
  19651. }
  19652. }.createDelegate(this));
  19653. return;
  19654. }else{
  19655. this.ui.collapse();
  19656. this.fireEvent("collapse", this);
  19657. }
  19658. }
  19659. if(deep === true){
  19660. var cs = this.childNodes;
  19661. for(var i = 0, len = cs.length; i < len; i++) {
  19662. cs[i].collapse(true, false);
  19663. }
  19664. }
  19665. },
  19666. // private
  19667. delayedExpand : function(delay){
  19668. if(!this.expandProcId){
  19669. this.expandProcId = this.expand.defer(delay, this);
  19670. }
  19671. },
  19672. // private
  19673. cancelExpand : function(){
  19674. if(this.expandProcId){
  19675. clearTimeout(this.expandProcId);
  19676. }
  19677. this.expandProcId = false;
  19678. },
  19679. toggle : function(){
  19680. if(this.expanded){
  19681. this.collapse();
  19682. }else{
  19683. this.expand();
  19684. }
  19685. },
  19686. ensureVisible : function(callback){
  19687. var tree = this.getOwnerTree();
  19688. tree.expandPath(this.parentNode ? this.parentNode.getPath() : this.getPath(), false, function(){
  19689. var node = tree.getNodeById(this.id); // Somehow if we don't do this, we lose changes that happened to node in the meantime
  19690. tree.getTreeEl().scrollChildIntoView(node.ui.anchor);
  19691. Ext.callback(callback);
  19692. }.createDelegate(this));
  19693. },
  19694. expandChildNodes : function(deep){
  19695. var cs = this.childNodes;
  19696. for(var i = 0, len = cs.length; i < len; i++) {
  19697. cs[i].expand(deep);
  19698. }
  19699. },
  19700. collapseChildNodes : function(deep){
  19701. var cs = this.childNodes;
  19702. for(var i = 0, len = cs.length; i < len; i++) {
  19703. cs[i].collapse(deep);
  19704. }
  19705. },
  19706. disable : function(){
  19707. this.disabled = true;
  19708. this.unselect();
  19709. if(this.rendered && this.ui.onDisableChange){ // event without subscribing
  19710. this.ui.onDisableChange(this, true);
  19711. }
  19712. this.fireEvent("disabledchange", this, true);
  19713. },
  19714. enable : function(){
  19715. this.disabled = false;
  19716. if(this.rendered && this.ui.onDisableChange){ // event without subscribing
  19717. this.ui.onDisableChange(this, false);
  19718. }
  19719. this.fireEvent("disabledchange", this, false);
  19720. },
  19721. // private
  19722. renderChildren : function(suppressEvent){
  19723. if(suppressEvent !== false){
  19724. this.fireEvent("beforechildrenrendered", this);
  19725. }
  19726. var cs = this.childNodes;
  19727. for(var i = 0, len = cs.length; i < len; i++){
  19728. cs[i].render(true);
  19729. }
  19730. this.childrenRendered = true;
  19731. },
  19732. // private
  19733. sort : function(fn, scope){
  19734. Ext.tree.TreeNode.superclass.sort.apply(this, arguments);
  19735. if(this.childrenRendered){
  19736. var cs = this.childNodes;
  19737. for(var i = 0, len = cs.length; i < len; i++){
  19738. cs[i].render(true);
  19739. }
  19740. }
  19741. },
  19742. // private
  19743. render : function(bulkRender){
  19744. this.ui.render(bulkRender);
  19745. if(!this.rendered){
  19746. // make sure it is registered
  19747. this.getOwnerTree().registerNode(this);
  19748. this.rendered = true;
  19749. if(this.expanded){
  19750. this.expanded = false;
  19751. this.expand(false, false);
  19752. }
  19753. }
  19754. },
  19755. // private
  19756. renderIndent : function(deep, refresh){
  19757. if(refresh){
  19758. this.ui.childIndent = null;
  19759. }
  19760. this.ui.renderIndent();
  19761. if(deep === true && this.childrenRendered){
  19762. var cs = this.childNodes;
  19763. for(var i = 0, len = cs.length; i < len; i++){
  19764. cs[i].renderIndent(true, refresh);
  19765. }
  19766. }
  19767. },
  19768. beginUpdate : function(){
  19769. this.childrenRendered = false;
  19770. },
  19771. endUpdate : function(){
  19772. if(this.expanded && this.rendered){
  19773. this.renderChildren();
  19774. }
  19775. },
  19776. destroy : function(){
  19777. if(this.childNodes){
  19778. for(var i = 0,l = this.childNodes.length; i < l; i++){
  19779. this.childNodes[i].destroy();
  19780. }
  19781. this.childNodes = null;
  19782. }
  19783. if(this.ui.destroy){
  19784. this.ui.destroy();
  19785. }
  19786. }
  19787. });
  19788. Ext.tree.TreePanel.nodeTypes.node = Ext.tree.TreeNode;
  19789. Ext.tree.AsyncTreeNode = function(config){
  19790. this.loaded = config && config.loaded === true;
  19791. this.loading = false;
  19792. Ext.tree.AsyncTreeNode.superclass.constructor.apply(this, arguments);
  19793. this.addEvents('beforeload', 'load');
  19794. };
  19795. Ext.extend(Ext.tree.AsyncTreeNode, Ext.tree.TreeNode, {
  19796. expand : function(deep, anim, callback){
  19797. if(this.loading){ // if an async load is already running, waiting til it's done
  19798. var timer;
  19799. var f = function(){
  19800. if(!this.loading){ // done loading
  19801. clearInterval(timer);
  19802. this.expand(deep, anim, callback);
  19803. }
  19804. }.createDelegate(this);
  19805. timer = setInterval(f, 200);
  19806. return;
  19807. }
  19808. if(!this.loaded){
  19809. if(this.fireEvent("beforeload", this) === false){
  19810. return;
  19811. }
  19812. this.loading = true;
  19813. this.ui.beforeLoad(this);
  19814. var loader = this.loader || this.attributes.loader || this.getOwnerTree().getLoader();
  19815. if(loader){
  19816. loader.load(this, this.loadComplete.createDelegate(this, [deep, anim, callback]));
  19817. return;
  19818. }
  19819. }
  19820. Ext.tree.AsyncTreeNode.superclass.expand.call(this, deep, anim, callback);
  19821. },
  19822. isLoading : function(){
  19823. return this.loading;
  19824. },
  19825. loadComplete : function(deep, anim, callback){
  19826. this.loading = false;
  19827. this.loaded = true;
  19828. this.ui.afterLoad(this);
  19829. this.fireEvent("load", this);
  19830. this.expand(deep, anim, callback);
  19831. },
  19832. isLoaded : function(){
  19833. return this.loaded;
  19834. },
  19835. hasChildNodes : function(){
  19836. if(!this.isLeaf() && !this.loaded){
  19837. return true;
  19838. }else{
  19839. return Ext.tree.AsyncTreeNode.superclass.hasChildNodes.call(this);
  19840. }
  19841. },
  19842. reload : function(callback){
  19843. this.collapse(false, false);
  19844. while(this.firstChild){
  19845. this.removeChild(this.firstChild).destroy();
  19846. }
  19847. this.childrenRendered = false;
  19848. this.loaded = false;
  19849. if(this.isHiddenRoot()){
  19850. this.expanded = false;
  19851. }
  19852. this.expand(false, false, callback);
  19853. }
  19854. });
  19855. Ext.tree.TreePanel.nodeTypes.async = Ext.tree.AsyncTreeNode;
  19856. Ext.tree.TreeNodeUI = function(node){
  19857. this.node = node;
  19858. this.rendered = false;
  19859. this.animating = false;
  19860. this.wasLeaf = true;
  19861. this.ecc = 'x-tree-ec-icon x-tree-elbow';
  19862. this.emptyIcon = Ext.BLANK_IMAGE_URL;
  19863. };
  19864. Ext.tree.TreeNodeUI.prototype = {
  19865. // private
  19866. removeChild : function(node){
  19867. if(this.rendered){
  19868. this.ctNode.removeChild(node.ui.getEl());
  19869. }
  19870. },
  19871. // private
  19872. beforeLoad : function(){
  19873. this.addClass("x-tree-node-loading");
  19874. },
  19875. // private
  19876. afterLoad : function(){
  19877. this.removeClass("x-tree-node-loading");
  19878. },
  19879. // private
  19880. onTextChange : function(node, text, oldText){
  19881. if(this.rendered){
  19882. this.textNode.innerHTML = text;
  19883. }
  19884. },
  19885. // private
  19886. onDisableChange : function(node, state){
  19887. this.disabled = state;
  19888. if (this.checkbox) {
  19889. this.checkbox.disabled = state;
  19890. }
  19891. if(state){
  19892. this.addClass("x-tree-node-disabled");
  19893. }else{
  19894. this.removeClass("x-tree-node-disabled");
  19895. }
  19896. },
  19897. // private
  19898. onSelectedChange : function(state){
  19899. if(state){
  19900. this.focus();
  19901. this.addClass("x-tree-selected");
  19902. }else{
  19903. //this.blur();
  19904. this.removeClass("x-tree-selected");
  19905. }
  19906. },
  19907. // private
  19908. onMove : function(tree, node, oldParent, newParent, index, refNode){
  19909. this.childIndent = null;
  19910. if(this.rendered){
  19911. var targetNode = newParent.ui.getContainer();
  19912. if(!targetNode){//target not rendered
  19913. this.holder = document.createElement("div");
  19914. this.holder.appendChild(this.wrap);
  19915. return;
  19916. }
  19917. var insertBefore = refNode ? refNode.ui.getEl() : null;
  19918. if(insertBefore){
  19919. targetNode.insertBefore(this.wrap, insertBefore);
  19920. }else{
  19921. targetNode.appendChild(this.wrap);
  19922. }
  19923. this.node.renderIndent(true);
  19924. }
  19925. },
  19926. addClass : function(cls){
  19927. if(this.elNode){
  19928. Ext.fly(this.elNode).addClass(cls);
  19929. }
  19930. },
  19931. removeClass : function(cls){
  19932. if(this.elNode){
  19933. Ext.fly(this.elNode).removeClass(cls);
  19934. }
  19935. },
  19936. // private
  19937. remove : function(){
  19938. if(this.rendered){
  19939. this.holder = document.createElement("div");
  19940. this.holder.appendChild(this.wrap);
  19941. }
  19942. },
  19943. // private
  19944. fireEvent : function(){
  19945. return this.node.fireEvent.apply(this.node, arguments);
  19946. },
  19947. // private
  19948. initEvents : function(){
  19949. this.node.on("move", this.onMove, this);
  19950. if(this.node.disabled){
  19951. this.addClass("x-tree-node-disabled");
  19952. if (this.checkbox) {
  19953. this.checkbox.disabled = true;
  19954. }
  19955. }
  19956. if(this.node.hidden){
  19957. this.hide();
  19958. }
  19959. var ot = this.node.getOwnerTree();
  19960. var dd = ot.enableDD || ot.enableDrag || ot.enableDrop;
  19961. if(dd && (!this.node.isRoot || ot.rootVisible)){
  19962. Ext.dd.Registry.register(this.elNode, {
  19963. node: this.node,
  19964. handles: this.getDDHandles(),
  19965. isHandle: false
  19966. });
  19967. }
  19968. },
  19969. // private
  19970. getDDHandles : function(){
  19971. return [this.iconNode, this.textNode, this.elNode];
  19972. },
  19973. hide : function(){
  19974. this.node.hidden = true;
  19975. if(this.wrap){
  19976. this.wrap.style.display = "none";
  19977. }
  19978. },
  19979. show : function(){
  19980. this.node.hidden = false;
  19981. if(this.wrap){
  19982. this.wrap.style.display = "";
  19983. }
  19984. },
  19985. // private
  19986. onContextMenu : function(e){
  19987. if (this.node.hasListener("contextmenu") || this.node.getOwnerTree().hasListener("contextmenu")) {
  19988. e.preventDefault();
  19989. this.focus();
  19990. this.fireEvent("contextmenu", this.node, e);
  19991. }
  19992. },
  19993. // private
  19994. onClick : function(e){
  19995. if(this.dropping){
  19996. e.stopEvent();
  19997. return;
  19998. }
  19999. if(this.fireEvent("beforeclick", this.node, e) !== false){
  20000. var a = e.getTarget('a');
  20001. if(!this.disabled && this.node.attributes.href && a){
  20002. this.fireEvent("click", this.node, e);
  20003. return;
  20004. }else if(a && e.ctrlKey){
  20005. e.stopEvent();
  20006. }
  20007. e.preventDefault();
  20008. if(this.disabled){
  20009. return;
  20010. }
  20011. if(this.node.attributes.singleClickExpand && !this.animating && this.node.isExpandable()){
  20012. this.node.toggle();
  20013. }
  20014. this.fireEvent("click", this.node, e);
  20015. }else{
  20016. e.stopEvent();
  20017. }
  20018. },
  20019. // private
  20020. onDblClick : function(e){
  20021. e.preventDefault();
  20022. if(this.disabled){
  20023. return;
  20024. }
  20025. if(this.checkbox){
  20026. this.toggleCheck();
  20027. }
  20028. if(!this.animating && this.node.isExpandable()){
  20029. this.node.toggle();
  20030. }
  20031. this.fireEvent("dblclick", this.node, e);
  20032. },
  20033. onOver : function(e){
  20034. this.addClass('x-tree-node-over');
  20035. },
  20036. onOut : function(e){
  20037. this.removeClass('x-tree-node-over');
  20038. },
  20039. // private
  20040. onCheckChange : function(){
  20041. var checked = this.checkbox.checked;
  20042. // fix for IE6
  20043. this.checkbox.defaultChecked = checked;
  20044. this.node.attributes.checked = checked;
  20045. this.fireEvent('checkchange', this.node, checked);
  20046. },
  20047. // private
  20048. ecClick : function(e){
  20049. if(!this.animating && this.node.isExpandable()){
  20050. this.node.toggle();
  20051. }
  20052. },
  20053. // private
  20054. startDrop : function(){
  20055. this.dropping = true;
  20056. },
  20057. // delayed drop so the click event doesn't get fired on a drop
  20058. endDrop : function(){
  20059. setTimeout(function(){
  20060. this.dropping = false;
  20061. }.createDelegate(this), 50);
  20062. },
  20063. // private
  20064. expand : function(){
  20065. this.updateExpandIcon();
  20066. this.ctNode.style.display = "";
  20067. },
  20068. // private
  20069. focus : function(){
  20070. if(!this.node.preventHScroll){
  20071. try{this.anchor.focus();
  20072. }catch(e){}
  20073. }else{
  20074. try{
  20075. var noscroll = this.node.getOwnerTree().getTreeEl().dom;
  20076. var l = noscroll.scrollLeft;
  20077. this.anchor.focus();
  20078. noscroll.scrollLeft = l;
  20079. }catch(e){}
  20080. }
  20081. },
  20082. toggleCheck : function(value){
  20083. var cb = this.checkbox;
  20084. if(cb){
  20085. cb.checked = (value === undefined ? !cb.checked : value);
  20086. this.onCheckChange();
  20087. }
  20088. },
  20089. // private
  20090. blur : function(){
  20091. try{
  20092. this.anchor.blur();
  20093. }catch(e){}
  20094. },
  20095. // private
  20096. animExpand : function(callback){
  20097. var ct = Ext.get(this.ctNode);
  20098. ct.stopFx();
  20099. if(!this.node.isExpandable()){
  20100. this.updateExpandIcon();
  20101. this.ctNode.style.display = "";
  20102. Ext.callback(callback);
  20103. return;
  20104. }
  20105. this.animating = true;
  20106. this.updateExpandIcon();
  20107. ct.slideIn('t', {
  20108. callback : function(){
  20109. this.animating = false;
  20110. Ext.callback(callback);
  20111. },
  20112. scope: this,
  20113. duration: this.node.ownerTree.duration || .25
  20114. });
  20115. },
  20116. // private
  20117. highlight : function(){
  20118. var tree = this.node.getOwnerTree();
  20119. Ext.fly(this.wrap).highlight(
  20120. tree.hlColor || "C3DAF9",
  20121. {endColor: tree.hlBaseColor}
  20122. );
  20123. },
  20124. // private
  20125. collapse : function(){
  20126. this.updateExpandIcon();
  20127. this.ctNode.style.display = "none";
  20128. },
  20129. // private
  20130. animCollapse : function(callback){
  20131. var ct = Ext.get(this.ctNode);
  20132. ct.enableDisplayMode('block');
  20133. ct.stopFx();
  20134. this.animating = true;
  20135. this.updateExpandIcon();
  20136. ct.slideOut('t', {
  20137. callback : function(){
  20138. this.animating = false;
  20139. Ext.callback(callback);
  20140. },
  20141. scope: this,
  20142. duration: this.node.ownerTree.duration || .25
  20143. });
  20144. },
  20145. // private
  20146. getContainer : function(){
  20147. return this.ctNode;
  20148. },
  20149. // private
  20150. getEl : function(){
  20151. return this.wrap;
  20152. },
  20153. // private
  20154. appendDDGhost : function(ghostNode){
  20155. ghostNode.appendChild(this.elNode.cloneNode(true));
  20156. },
  20157. // private
  20158. getDDRepairXY : function(){
  20159. return Ext.lib.Dom.getXY(this.iconNode);
  20160. },
  20161. // private
  20162. onRender : function(){
  20163. this.render();
  20164. },
  20165. // private
  20166. render : function(bulkRender){
  20167. var n = this.node, a = n.attributes;
  20168. var targetNode = n.parentNode ?
  20169. n.parentNode.ui.getContainer() : n.ownerTree.innerCt.dom;
  20170. if(!this.rendered){
  20171. this.rendered = true;
  20172. this.renderElements(n, a, targetNode, bulkRender);
  20173. if(a.qtip){
  20174. if(this.textNode.setAttributeNS){
  20175. this.textNode.setAttributeNS("ext", "qtip", a.qtip);
  20176. if(a.qtipTitle){
  20177. this.textNode.setAttributeNS("ext", "qtitle", a.qtipTitle);
  20178. }
  20179. }else{
  20180. this.textNode.setAttribute("ext:qtip", a.qtip);
  20181. if(a.qtipTitle){
  20182. this.textNode.setAttribute("ext:qtitle", a.qtipTitle);
  20183. }
  20184. }
  20185. }else if(a.qtipCfg){
  20186. a.qtipCfg.target = Ext.id(this.textNode);
  20187. Ext.QuickTips.register(a.qtipCfg);
  20188. }
  20189. this.initEvents();
  20190. if(!this.node.expanded){
  20191. this.updateExpandIcon(true);
  20192. }
  20193. }else{
  20194. if(bulkRender === true) {
  20195. targetNode.appendChild(this.wrap);
  20196. }
  20197. }
  20198. },
  20199. // private
  20200. renderElements : function(n, a, targetNode, bulkRender){
  20201. // add some indent caching, this helps performance when rendering a large tree
  20202. this.indentMarkup = n.parentNode ? n.parentNode.ui.getChildIndent() : '';
  20203. var cb = typeof a.checked == 'boolean';
  20204. var href = a.href ? a.href : Ext.isGecko ? "" : "#";
  20205. var buf = ['<li class="x-tree-node"><div ext:tree-node-id="',n.id,'" class="x-tree-node-el x-tree-node-leaf x-unselectable ', a.cls,'" unselectable="on">',
  20206. '<span class="x-tree-node-indent">',this.indentMarkup,"</span>",
  20207. '<img src="', this.emptyIcon, '" class="x-tree-ec-icon x-tree-elbow" />',
  20208. '<img src="', a.icon || this.emptyIcon, '" class="x-tree-node-icon',(a.icon ? " x-tree-node-inline-icon" : ""),(a.iconCls ? " "+a.iconCls : ""),'" unselectable="on" />',
  20209. cb ? ('<input class="x-tree-node-cb" type="checkbox" ' + (a.checked ? 'checked="checked" />' : '/>')) : '',
  20210. '<a hidefocus="on" class="x-tree-node-anchor" href="',href,'" tabIndex="1" ',
  20211. a.hrefTarget ? ' target="'+a.hrefTarget+'"' : "", '><span unselectable="on">',n.text,"</span></a></div>",
  20212. '<ul class="x-tree-node-ct" style="display:none;"></ul>',
  20213. "</li>"].join('');
  20214. var nel;
  20215. if(bulkRender !== true && n.nextSibling && (nel = n.nextSibling.ui.getEl())){
  20216. this.wrap = Ext.DomHelper.insertHtml("beforeBegin", nel, buf);
  20217. }else{
  20218. this.wrap = Ext.DomHelper.insertHtml("beforeEnd", targetNode, buf);
  20219. }
  20220. this.elNode = this.wrap.childNodes[0];
  20221. this.ctNode = this.wrap.childNodes[1];
  20222. var cs = this.elNode.childNodes;
  20223. this.indentNode = cs[0];
  20224. this.ecNode = cs[1];
  20225. this.iconNode = cs[2];
  20226. var index = 3;
  20227. if(cb){
  20228. this.checkbox = cs[3];
  20229. // fix for IE6
  20230. this.checkbox.defaultChecked = this.checkbox.checked;
  20231. index++;
  20232. }
  20233. this.anchor = cs[index];
  20234. this.textNode = cs[index].firstChild;
  20235. },
  20236. getAnchor : function(){
  20237. return this.anchor;
  20238. },
  20239. getTextEl : function(){
  20240. return this.textNode;
  20241. },
  20242. getIconEl : function(){
  20243. return this.iconNode;
  20244. },
  20245. isChecked : function(){
  20246. return this.checkbox ? this.checkbox.checked : false;
  20247. },
  20248. // private
  20249. updateExpandIcon : function(){
  20250. if(this.rendered){
  20251. var n = this.node, c1, c2;
  20252. var cls = n.isLast() ? "x-tree-elbow-end" : "x-tree-elbow";
  20253. if(n.isExpandable()){
  20254. if(n.expanded){
  20255. cls += "-minus";
  20256. c1 = "x-tree-node-collapsed";
  20257. c2 = "x-tree-node-expanded";
  20258. }else{
  20259. cls += "-plus";
  20260. c1 = "x-tree-node-expanded";
  20261. c2 = "x-tree-node-collapsed";
  20262. }
  20263. if(this.wasLeaf){
  20264. this.removeClass("x-tree-node-leaf");
  20265. this.wasLeaf = false;
  20266. }
  20267. if(this.c1 != c1 || this.c2 != c2){
  20268. Ext.fly(this.elNode).replaceClass(c1, c2);
  20269. this.c1 = c1; this.c2 = c2;
  20270. }
  20271. }else{
  20272. if(!this.wasLeaf){
  20273. Ext.fly(this.elNode).replaceClass("x-tree-node-expanded", "x-tree-node-leaf");
  20274. delete this.c1;
  20275. delete this.c2;
  20276. this.wasLeaf = true;
  20277. }
  20278. }
  20279. var ecc = "x-tree-ec-icon "+cls;
  20280. if(this.ecc != ecc){
  20281. this.ecNode.className = ecc;
  20282. this.ecc = ecc;
  20283. }
  20284. }
  20285. },
  20286. // private
  20287. getChildIndent : function(){
  20288. if(!this.childIndent){
  20289. var buf = [];
  20290. var p = this.node;
  20291. while(p){
  20292. if(!p.isRoot || (p.isRoot && p.ownerTree.rootVisible)){
  20293. if(!p.isLast()) {
  20294. buf.unshift('<img src="'+this.emptyIcon+'" class="x-tree-elbow-line" />');
  20295. } else {
  20296. buf.unshift('<img src="'+this.emptyIcon+'" class="x-tree-icon" />');
  20297. }
  20298. }
  20299. p = p.parentNode;
  20300. }
  20301. this.childIndent = buf.join("");
  20302. }
  20303. return this.childIndent;
  20304. },
  20305. // private
  20306. renderIndent : function(){
  20307. if(this.rendered){
  20308. var indent = "";
  20309. var p = this.node.parentNode;
  20310. if(p){
  20311. indent = p.ui.getChildIndent();
  20312. }
  20313. if(this.indentMarkup != indent){ // don't rerender if not required
  20314. this.indentNode.innerHTML = indent;
  20315. this.indentMarkup = indent;
  20316. }
  20317. this.updateExpandIcon();
  20318. }
  20319. },
  20320. destroy : function(){
  20321. if(this.elNode){
  20322. Ext.dd.Registry.unregister(this.elNode.id);
  20323. }
  20324. delete this.elNode;
  20325. delete this.ctNode;
  20326. delete this.indentNode;
  20327. delete this.ecNode;
  20328. delete this.iconNode;
  20329. delete this.checkbox;
  20330. delete this.anchor;
  20331. delete this.textNode;
  20332. if (this.holder){
  20333. delete this.wrap;
  20334. Ext.removeNode(this.holder);
  20335. delete this.holder;
  20336. }else{
  20337. Ext.removeNode(this.wrap);
  20338. delete this.wrap;
  20339. }
  20340. }
  20341. };
  20342. Ext.tree.RootTreeNodeUI = Ext.extend(Ext.tree.TreeNodeUI, {
  20343. // private
  20344. render : function(){
  20345. if(!this.rendered){
  20346. var targetNode = this.node.ownerTree.innerCt.dom;
  20347. this.node.expanded = true;
  20348. targetNode.innerHTML = '<div class="x-tree-root-node"></div>';
  20349. this.wrap = this.ctNode = targetNode.firstChild;
  20350. }
  20351. },
  20352. collapse : Ext.emptyFn,
  20353. expand : Ext.emptyFn
  20354. });
  20355. Ext.tree.TreeLoader = function(config){
  20356. this.baseParams = {};
  20357. Ext.apply(this, config);
  20358. this.addEvents(
  20359. "beforeload",
  20360. "load",
  20361. "loadexception"
  20362. );
  20363. Ext.tree.TreeLoader.superclass.constructor.call(this);
  20364. };
  20365. Ext.extend(Ext.tree.TreeLoader, Ext.util.Observable, {
  20366. uiProviders : {},
  20367. clearOnLoad : true,
  20368. load : function(node, callback){
  20369. if(this.clearOnLoad){
  20370. while(node.firstChild){
  20371. node.removeChild(node.firstChild);
  20372. }
  20373. }
  20374. if(this.doPreload(node)){ // preloaded json children
  20375. if(typeof callback == "function"){
  20376. callback();
  20377. }
  20378. }else if(this.dataUrl||this.url){
  20379. this.requestData(node, callback);
  20380. }
  20381. },
  20382. doPreload : function(node){
  20383. if(node.attributes.children){
  20384. if(node.childNodes.length < 1){ // preloaded?
  20385. var cs = node.attributes.children;
  20386. node.beginUpdate();
  20387. for(var i = 0, len = cs.length; i < len; i++){
  20388. var cn = node.appendChild(this.createNode(cs[i]));
  20389. if(this.preloadChildren){
  20390. this.doPreload(cn);
  20391. }
  20392. }
  20393. node.endUpdate();
  20394. }
  20395. return true;
  20396. }else {
  20397. return false;
  20398. }
  20399. },
  20400. getParams: function(node){
  20401. var buf = [], bp = this.baseParams;
  20402. for(var key in bp){
  20403. if(typeof bp[key] != "function"){
  20404. buf.push(encodeURIComponent(key), "=", encodeURIComponent(bp[key]), "&");
  20405. }
  20406. }
  20407. buf.push("node=", encodeURIComponent(node.id));
  20408. return buf.join("");
  20409. },
  20410. requestData : function(node, callback){
  20411. if(this.fireEvent("beforeload", this, node, callback) !== false){
  20412. this.transId = Ext.Ajax.request({
  20413. method:this.requestMethod,
  20414. url: this.dataUrl||this.url,
  20415. success: this.handleResponse,
  20416. failure: this.handleFailure,
  20417. scope: this,
  20418. argument: {callback: callback, node: node},
  20419. params: this.getParams(node)
  20420. });
  20421. }else{
  20422. // if the load is cancelled, make sure we notify
  20423. // the node that we are done
  20424. if(typeof callback == "function"){
  20425. callback();
  20426. }
  20427. }
  20428. },
  20429. isLoading : function(){
  20430. return !!this.transId;
  20431. },
  20432. abort : function(){
  20433. if(this.isLoading()){
  20434. Ext.Ajax.abort(this.transId);
  20435. }
  20436. },
  20437. createNode : function(attr){
  20438. // apply baseAttrs, nice idea Corey!
  20439. if(this.baseAttrs){
  20440. Ext.applyIf(attr, this.baseAttrs);
  20441. }
  20442. if(this.applyLoader !== false){
  20443. attr.loader = this;
  20444. }
  20445. if(typeof attr.uiProvider == 'string'){
  20446. attr.uiProvider = this.uiProviders[attr.uiProvider] || eval(attr.uiProvider);
  20447. }
  20448. if(attr.nodeType){
  20449. return new Ext.tree.TreePanel.nodeTypes[attr.nodeType](attr);
  20450. }else{
  20451. return attr.leaf ?
  20452. new Ext.tree.TreeNode(attr) :
  20453. new Ext.tree.AsyncTreeNode(attr);
  20454. }
  20455. },
  20456. processResponse : function(response, node, callback){
  20457. var json = response.responseText;
  20458. try {
  20459. var o = eval("("+json+")");
  20460. node.beginUpdate();
  20461. for(var i = 0, len = o.length; i < len; i++){
  20462. var n = this.createNode(o[i]);
  20463. if(n){
  20464. node.appendChild(n);
  20465. }
  20466. }
  20467. node.endUpdate();
  20468. if(typeof callback == "function"){
  20469. callback(this, node);
  20470. }
  20471. }catch(e){
  20472. this.handleFailure(response);
  20473. }
  20474. },
  20475. handleResponse : function(response){
  20476. this.transId = false;
  20477. var a = response.argument;
  20478. this.processResponse(response, a.node, a.callback);
  20479. this.fireEvent("load", this, a.node, response);
  20480. },
  20481. handleFailure : function(response){
  20482. this.transId = false;
  20483. var a = response.argument;
  20484. this.fireEvent("loadexception", this, a.node, response);
  20485. if(typeof a.callback == "function"){
  20486. a.callback(this, a.node);
  20487. }
  20488. }
  20489. });
  20490. Ext.tree.TreeFilter = function(tree, config){
  20491. this.tree = tree;
  20492. this.filtered = {};
  20493. Ext.apply(this, config);
  20494. };
  20495. Ext.tree.TreeFilter.prototype = {
  20496. clearBlank:false,
  20497. reverse:false,
  20498. autoClear:false,
  20499. remove:false,
  20500. filter : function(value, attr, startNode){
  20501. attr = attr || "text";
  20502. var f;
  20503. if(typeof value == "string"){
  20504. var vlen = value.length;
  20505. // auto clear empty filter
  20506. if(vlen == 0 && this.clearBlank){
  20507. this.clear();
  20508. return;
  20509. }
  20510. value = value.toLowerCase();
  20511. f = function(n){
  20512. return n.attributes[attr].substr(0, vlen).toLowerCase() == value;
  20513. };
  20514. }else if(value.exec){ // regex?
  20515. f = function(n){
  20516. return value.test(n.attributes[attr]);
  20517. };
  20518. }else{
  20519. throw 'Illegal filter type, must be string or regex';
  20520. }
  20521. this.filterBy(f, null, startNode);
  20522. },
  20523. filterBy : function(fn, scope, startNode){
  20524. startNode = startNode || this.tree.root;
  20525. if(this.autoClear){
  20526. this.clear();
  20527. }
  20528. var af = this.filtered, rv = this.reverse;
  20529. var f = function(n){
  20530. if(n == startNode){
  20531. return true;
  20532. }
  20533. if(af[n.id]){
  20534. return false;
  20535. }
  20536. var m = fn.call(scope || n, n);
  20537. if(!m || rv){
  20538. af[n.id] = n;
  20539. n.ui.hide();
  20540. return false;
  20541. }
  20542. return true;
  20543. };
  20544. startNode.cascade(f);
  20545. if(this.remove){
  20546. for(var id in af){
  20547. if(typeof id != "function"){
  20548. var n = af[id];
  20549. if(n && n.parentNode){
  20550. n.parentNode.removeChild(n);
  20551. }
  20552. }
  20553. }
  20554. }
  20555. },
  20556. clear : function(){
  20557. var t = this.tree;
  20558. var af = this.filtered;
  20559. for(var id in af){
  20560. if(typeof id != "function"){
  20561. var n = af[id];
  20562. if(n){
  20563. n.ui.show();
  20564. }
  20565. }
  20566. }
  20567. this.filtered = {};
  20568. }
  20569. };
  20570. Ext.tree.TreeSorter = function(tree, config){
  20571. Ext.apply(this, config);
  20572. tree.on("beforechildrenrendered", this.doSort, this);
  20573. tree.on("append", this.updateSort, this);
  20574. tree.on("insert", this.updateSort, this);
  20575. tree.on("textchange", this.updateSortParent, this);
  20576. var dsc = this.dir && this.dir.toLowerCase() == "desc";
  20577. var p = this.property || "text";
  20578. var sortType = this.sortType;
  20579. var fs = this.folderSort;
  20580. var cs = this.caseSensitive === true;
  20581. var leafAttr = this.leafAttr || 'leaf';
  20582. this.sortFn = function(n1, n2){
  20583. if(fs){
  20584. if(n1.attributes[leafAttr] && !n2.attributes[leafAttr]){
  20585. return 1;
  20586. }
  20587. if(!n1.attributes[leafAttr] && n2.attributes[leafAttr]){
  20588. return -1;
  20589. }
  20590. }
  20591. var v1 = sortType ? sortType(n1) : (cs ? n1.attributes[p] : n1.attributes[p].toUpperCase());
  20592. var v2 = sortType ? sortType(n2) : (cs ? n2.attributes[p] : n2.attributes[p].toUpperCase());
  20593. if(v1 < v2){
  20594. return dsc ? +1 : -1;
  20595. }else if(v1 > v2){
  20596. return dsc ? -1 : +1;
  20597. }else{
  20598. return 0;
  20599. }
  20600. };
  20601. };
  20602. Ext.tree.TreeSorter.prototype = {
  20603. doSort : function(node){
  20604. node.sort(this.sortFn);
  20605. },
  20606. compareNodes : function(n1, n2){
  20607. return (n1.text.toUpperCase() > n2.text.toUpperCase() ? 1 : -1);
  20608. },
  20609. updateSort : function(tree, node){
  20610. if(node.childrenRendered){
  20611. this.doSort.defer(1, this, [node]);
  20612. }
  20613. },
  20614. updateSortParent : function(node){
  20615. var p = node.parentNode;
  20616. if(p && p.childrenRendered){
  20617. this.doSort.defer(1, this, [p]);
  20618. }
  20619. }
  20620. };
  20621. if(Ext.dd.DropZone){
  20622. Ext.tree.TreeDropZone = function(tree, config){
  20623. this.allowParentInsert = false;
  20624. this.allowContainerDrop = false;
  20625. this.appendOnly = false;
  20626. Ext.tree.TreeDropZone.superclass.constructor.call(this, tree.innerCt, config);
  20627. this.tree = tree;
  20628. this.dragOverData = {};
  20629. // private
  20630. this.lastInsertClass = "x-tree-no-status";
  20631. };
  20632. Ext.extend(Ext.tree.TreeDropZone, Ext.dd.DropZone, {
  20633. ddGroup : "TreeDD",
  20634. expandDelay : 1000,
  20635. // private
  20636. expandNode : function(node){
  20637. if(node.hasChildNodes() && !node.isExpanded()){
  20638. node.expand(false, null, this.triggerCacheRefresh.createDelegate(this));
  20639. }
  20640. },
  20641. // private
  20642. queueExpand : function(node){
  20643. this.expandProcId = this.expandNode.defer(this.expandDelay, this, [node]);
  20644. },
  20645. // private
  20646. cancelExpand : function(){
  20647. if(this.expandProcId){
  20648. clearTimeout(this.expandProcId);
  20649. this.expandProcId = false;
  20650. }
  20651. },
  20652. // private
  20653. isValidDropPoint : function(n, pt, dd, e, data){
  20654. if(!n || !data){ return false; }
  20655. var targetNode = n.node;
  20656. var dropNode = data.node;
  20657. // default drop rules
  20658. if(!(targetNode && targetNode.isTarget && pt)){
  20659. return false;
  20660. }
  20661. if(pt == "append" && targetNode.allowChildren === false){
  20662. return false;
  20663. }
  20664. if((pt == "above" || pt == "below") && (targetNode.parentNode && targetNode.parentNode.allowChildren === false)){
  20665. return false;
  20666. }
  20667. if(dropNode && (targetNode == dropNode || dropNode.contains(targetNode))){
  20668. return false;
  20669. }
  20670. // reuse the object
  20671. var overEvent = this.dragOverData;
  20672. overEvent.tree = this.tree;
  20673. overEvent.target = targetNode;
  20674. overEvent.data = data;
  20675. overEvent.point = pt;
  20676. overEvent.source = dd;
  20677. overEvent.rawEvent = e;
  20678. overEvent.dropNode = dropNode;
  20679. overEvent.cancel = false;
  20680. var result = this.tree.fireEvent("nodedragover", overEvent);
  20681. return overEvent.cancel === false && result !== false;
  20682. },
  20683. // private
  20684. getDropPoint : function(e, n, dd){
  20685. var tn = n.node;
  20686. if(tn.isRoot){
  20687. return tn.allowChildren !== false ? "append" : false; // always append for root
  20688. }
  20689. var dragEl = n.ddel;
  20690. var t = Ext.lib.Dom.getY(dragEl), b = t + dragEl.offsetHeight;
  20691. var y = Ext.lib.Event.getPageY(e);
  20692. var noAppend = tn.allowChildren === false || tn.isLeaf();
  20693. if(this.appendOnly || tn.parentNode.allowChildren === false){
  20694. return noAppend ? false : "append";
  20695. }
  20696. var noBelow = false;
  20697. if(!this.allowParentInsert){
  20698. noBelow = tn.hasChildNodes() && tn.isExpanded();
  20699. }
  20700. var q = (b - t) / (noAppend ? 2 : 3);
  20701. if(y >= t && y < (t + q)){
  20702. return "above";
  20703. }else if(!noBelow && (noAppend || y >= b-q && y <= b)){
  20704. return "below";
  20705. }else{
  20706. return "append";
  20707. }
  20708. },
  20709. // private
  20710. onNodeEnter : function(n, dd, e, data){
  20711. this.cancelExpand();
  20712. },
  20713. // private
  20714. onNodeOver : function(n, dd, e, data){
  20715. var pt = this.getDropPoint(e, n, dd);
  20716. var node = n.node;
  20717. // auto node expand check
  20718. if(!this.expandProcId && pt == "append" && node.hasChildNodes() && !n.node.isExpanded()){
  20719. this.queueExpand(node);
  20720. }else if(pt != "append"){
  20721. this.cancelExpand();
  20722. }
  20723. // set the insert point style on the target node
  20724. var returnCls = this.dropNotAllowed;
  20725. if(this.isValidDropPoint(n, pt, dd, e, data)){
  20726. if(pt){
  20727. var el = n.ddel;
  20728. var cls;
  20729. if(pt == "above"){
  20730. returnCls = n.node.isFirst() ? "x-tree-drop-ok-above" : "x-tree-drop-ok-between";
  20731. cls = "x-tree-drag-insert-above";
  20732. }else if(pt == "below"){
  20733. returnCls = n.node.isLast() ? "x-tree-drop-ok-below" : "x-tree-drop-ok-between";
  20734. cls = "x-tree-drag-insert-below";
  20735. }else{
  20736. returnCls = "x-tree-drop-ok-append";
  20737. cls = "x-tree-drag-append";
  20738. }
  20739. if(this.lastInsertClass != cls){
  20740. Ext.fly(el).replaceClass(this.lastInsertClass, cls);
  20741. this.lastInsertClass = cls;
  20742. }
  20743. }
  20744. }
  20745. return returnCls;
  20746. },
  20747. // private
  20748. onNodeOut : function(n, dd, e, data){
  20749. this.cancelExpand();
  20750. this.removeDropIndicators(n);
  20751. },
  20752. // private
  20753. onNodeDrop : function(n, dd, e, data){
  20754. var point = this.getDropPoint(e, n, dd);
  20755. var targetNode = n.node;
  20756. targetNode.ui.startDrop();
  20757. if(!this.isValidDropPoint(n, point, dd, e, data)){
  20758. targetNode.ui.endDrop();
  20759. return false;
  20760. }
  20761. // first try to find the drop node
  20762. var dropNode = data.node || (dd.getTreeNode ? dd.getTreeNode(data, targetNode, point, e) : null);
  20763. var dropEvent = {
  20764. tree : this.tree,
  20765. target: targetNode,
  20766. data: data,
  20767. point: point,
  20768. source: dd,
  20769. rawEvent: e,
  20770. dropNode: dropNode,
  20771. cancel: !dropNode,
  20772. dropStatus: false
  20773. };
  20774. var retval = this.tree.fireEvent("beforenodedrop", dropEvent);
  20775. if(retval === false || dropEvent.cancel === true || !dropEvent.dropNode){
  20776. targetNode.ui.endDrop();
  20777. return dropEvent.dropStatus;
  20778. }
  20779. // allow target changing
  20780. targetNode = dropEvent.target;
  20781. if(point == "append" && !targetNode.isExpanded()){
  20782. targetNode.expand(false, null, function(){
  20783. this.completeDrop(dropEvent);
  20784. }.createDelegate(this));
  20785. }else{
  20786. this.completeDrop(dropEvent);
  20787. }
  20788. return true;
  20789. },
  20790. // private
  20791. completeDrop : function(de){
  20792. var ns = de.dropNode, p = de.point, t = de.target;
  20793. if(!Ext.isArray(ns)){
  20794. ns = [ns];
  20795. }
  20796. var n;
  20797. for(var i = 0, len = ns.length; i < len; i++){
  20798. n = ns[i];
  20799. if(p == "above"){
  20800. t.parentNode.insertBefore(n, t);
  20801. }else if(p == "below"){
  20802. t.parentNode.insertBefore(n, t.nextSibling);
  20803. }else{
  20804. t.appendChild(n);
  20805. }
  20806. }
  20807. n.ui.focus();
  20808. if(Ext.enableFx && this.tree.hlDrop){
  20809. n.ui.highlight();
  20810. }
  20811. t.ui.endDrop();
  20812. this.tree.fireEvent("nodedrop", de);
  20813. },
  20814. // private
  20815. afterNodeMoved : function(dd, data, e, targetNode, dropNode){
  20816. if(Ext.enableFx && this.tree.hlDrop){
  20817. dropNode.ui.focus();
  20818. dropNode.ui.highlight();
  20819. }
  20820. this.tree.fireEvent("nodedrop", this.tree, targetNode, data, dd, e);
  20821. },
  20822. // private
  20823. getTree : function(){
  20824. return this.tree;
  20825. },
  20826. // private
  20827. removeDropIndicators : function(n){
  20828. if(n && n.ddel){
  20829. var el = n.ddel;
  20830. Ext.fly(el).removeClass([
  20831. "x-tree-drag-insert-above",
  20832. "x-tree-drag-insert-below",
  20833. "x-tree-drag-append"]);
  20834. this.lastInsertClass = "_noclass";
  20835. }
  20836. },
  20837. // private
  20838. beforeDragDrop : function(target, e, id){
  20839. this.cancelExpand();
  20840. return true;
  20841. },
  20842. // private
  20843. afterRepair : function(data){
  20844. if(data && Ext.enableFx){
  20845. data.node.ui.highlight();
  20846. }
  20847. this.hideProxy();
  20848. }
  20849. });
  20850. }
  20851. if(Ext.dd.DragZone){
  20852. Ext.tree.TreeDragZone = function(tree, config){
  20853. Ext.tree.TreeDragZone.superclass.constructor.call(this, tree.getTreeEl(), config);
  20854. this.tree = tree;
  20855. };
  20856. Ext.extend(Ext.tree.TreeDragZone, Ext.dd.DragZone, {
  20857. ddGroup : "TreeDD",
  20858. // private
  20859. onBeforeDrag : function(data, e){
  20860. var n = data.node;
  20861. return n && n.draggable && !n.disabled;
  20862. },
  20863. // private
  20864. onInitDrag : function(e){
  20865. var data = this.dragData;
  20866. this.tree.getSelectionModel().select(data.node);
  20867. this.tree.eventModel.disable();
  20868. this.proxy.update("");
  20869. data.node.ui.appendDDGhost(this.proxy.ghost.dom);
  20870. this.tree.fireEvent("startdrag", this.tree, data.node, e);
  20871. },
  20872. // private
  20873. getRepairXY : function(e, data){
  20874. return data.node.ui.getDDRepairXY();
  20875. },
  20876. // private
  20877. onEndDrag : function(data, e){
  20878. this.tree.eventModel.enable.defer(100, this.tree.eventModel);
  20879. this.tree.fireEvent("enddrag", this.tree, data.node, e);
  20880. },
  20881. // private
  20882. onValidDrop : function(dd, e, id){
  20883. this.tree.fireEvent("dragdrop", this.tree, this.dragData.node, dd, e);
  20884. this.hideProxy();
  20885. },
  20886. // private
  20887. beforeInvalidDrop : function(e, id){
  20888. // this scrolls the original position back into view
  20889. var sm = this.tree.getSelectionModel();
  20890. sm.clearSelections();
  20891. sm.select(this.dragData.node);
  20892. },
  20893. // private
  20894. afterRepair : function(){
  20895. if (Ext.enableFx && this.tree.hlDrop) {
  20896. Ext.Element.fly(this.dragData.ddel).highlight(this.hlColor || "c3daf9");
  20897. }
  20898. this.dragging = false;
  20899. }
  20900. });
  20901. }
  20902. Ext.tree.TreeEditor = function(tree, fc, config){
  20903. fc = fc || {};
  20904. var field = fc.events ? fc : new Ext.form.TextField(fc);
  20905. Ext.tree.TreeEditor.superclass.constructor.call(this, field, config);
  20906. this.tree = tree;
  20907. if(!tree.rendered){
  20908. tree.on('render', this.initEditor, this);
  20909. }else{
  20910. this.initEditor(tree);
  20911. }
  20912. };
  20913. Ext.extend(Ext.tree.TreeEditor, Ext.Editor, {
  20914. alignment: "l-l",
  20915. // inherit
  20916. autoSize: false,
  20917. hideEl : false,
  20918. cls: "x-small-editor x-tree-editor",
  20919. shim:false,
  20920. // inherit
  20921. shadow:"frame",
  20922. maxWidth: 250,
  20923. editDelay : 350,
  20924. initEditor : function(tree){
  20925. tree.on('beforeclick', this.beforeNodeClick, this);
  20926. tree.on('dblclick', this.onNodeDblClick, this);
  20927. this.on('complete', this.updateNode, this);
  20928. this.on('beforestartedit', this.fitToTree, this);
  20929. this.on('startedit', this.bindScroll, this, {delay:10});
  20930. this.on('specialkey', this.onSpecialKey, this);
  20931. },
  20932. // private
  20933. fitToTree : function(ed, el){
  20934. var td = this.tree.getTreeEl().dom, nd = el.dom;
  20935. if(td.scrollLeft > nd.offsetLeft){ // ensure the node left point is visible
  20936. td.scrollLeft = nd.offsetLeft;
  20937. }
  20938. var w = Math.min(
  20939. this.maxWidth,
  20940. (td.clientWidth > 20 ? td.clientWidth : td.offsetWidth) - Math.max(0, nd.offsetLeft-td.scrollLeft) - 5);
  20941. this.setSize(w, '');
  20942. },
  20943. // private
  20944. triggerEdit : function(node, defer){
  20945. this.completeEdit();
  20946. if(node.attributes.editable !== false){
  20947. this.editNode = node;
  20948. if(this.tree.autoScroll){
  20949. node.ui.getEl().scrollIntoView(this.tree.body);
  20950. }
  20951. this.autoEditTimer = this.startEdit.defer(this.editDelay, this, [node.ui.textNode, node.text]);
  20952. return false;
  20953. }
  20954. },
  20955. // private
  20956. bindScroll : function(){
  20957. this.tree.getTreeEl().on('scroll', this.cancelEdit, this);
  20958. },
  20959. // private
  20960. beforeNodeClick : function(node, e){
  20961. clearTimeout(this.autoEditTimer);
  20962. if(this.tree.getSelectionModel().isSelected(node)){
  20963. e.stopEvent();
  20964. return this.triggerEdit(node);
  20965. }
  20966. },
  20967. onNodeDblClick : function(node, e){
  20968. clearTimeout(this.autoEditTimer);
  20969. },
  20970. // private
  20971. updateNode : function(ed, value){
  20972. this.tree.getTreeEl().un('scroll', this.cancelEdit, this);
  20973. this.editNode.setText(value);
  20974. },
  20975. // private
  20976. onHide : function(){
  20977. Ext.tree.TreeEditor.superclass.onHide.call(this);
  20978. if(this.editNode){
  20979. this.editNode.ui.focus.defer(50, this.editNode.ui);
  20980. }
  20981. },
  20982. // private
  20983. onSpecialKey : function(field, e){
  20984. var k = e.getKey();
  20985. if(k == e.ESC){
  20986. e.stopEvent();
  20987. this.cancelEdit();
  20988. }else if(k == e.ENTER && !e.hasModifier()){
  20989. e.stopEvent();
  20990. this.completeEdit();
  20991. }
  20992. }
  20993. });
  20994. Ext.menu.Menu = function(config){
  20995. if(Ext.isArray(config)){
  20996. config = {items:config};
  20997. }
  20998. Ext.apply(this, config);
  20999. this.id = this.id || Ext.id();
  21000. this.addEvents(
  21001. 'beforeshow',
  21002. 'beforehide',
  21003. 'show',
  21004. 'hide',
  21005. 'click',
  21006. 'mouseover',
  21007. 'mouseout',
  21008. 'itemclick'
  21009. );
  21010. Ext.menu.MenuMgr.register(this);
  21011. Ext.menu.Menu.superclass.constructor.call(this);
  21012. var mis = this.items;
  21013. this.items = new Ext.util.MixedCollection();
  21014. if(mis){
  21015. this.add.apply(this, mis);
  21016. }
  21017. };
  21018. Ext.extend(Ext.menu.Menu, Ext.util.Observable, {
  21019. minWidth : 120,
  21020. shadow : "sides",
  21021. subMenuAlign : "tl-tr?",
  21022. defaultAlign : "tl-bl?",
  21023. allowOtherMenus : false,
  21024. ignoreParentClicks : false,
  21025. // private
  21026. hidden:true,
  21027. // private
  21028. createEl : function(){
  21029. return new Ext.Layer({
  21030. cls: "x-menu",
  21031. shadow:this.shadow,
  21032. constrain: false,
  21033. parentEl: this.parentEl || document.body,
  21034. zindex:15000
  21035. });
  21036. },
  21037. // private
  21038. render : function(){
  21039. if(this.el){
  21040. return;
  21041. }
  21042. var el = this.el = this.createEl();
  21043. if(!this.keyNav){
  21044. this.keyNav = new Ext.menu.MenuNav(this);
  21045. }
  21046. if(this.plain){
  21047. el.addClass("x-menu-plain");
  21048. }
  21049. if(this.cls){
  21050. el.addClass(this.cls);
  21051. }
  21052. // generic focus element
  21053. this.focusEl = el.createChild({
  21054. tag: "a", cls: "x-menu-focus", href: "#", onclick: "return false;", tabIndex:"-1"
  21055. });
  21056. var ul = el.createChild({tag: "ul", cls: "x-menu-list"});
  21057. ul.on("click", this.onClick, this);
  21058. ul.on("mouseover", this.onMouseOver, this);
  21059. ul.on("mouseout", this.onMouseOut, this);
  21060. this.items.each(function(item){
  21061. var li = document.createElement("li");
  21062. li.className = "x-menu-list-item";
  21063. ul.dom.appendChild(li);
  21064. item.render(li, this);
  21065. }, this);
  21066. this.ul = ul;
  21067. this.autoWidth();
  21068. },
  21069. // private
  21070. autoWidth : function(){
  21071. var el = this.el, ul = this.ul;
  21072. if(!el){
  21073. return;
  21074. }
  21075. var w = this.width;
  21076. if(w){
  21077. el.setWidth(w);
  21078. }else if(Ext.isIE){
  21079. el.setWidth(this.minWidth);
  21080. var t = el.dom.offsetWidth; // force recalc
  21081. el.setWidth(ul.getWidth()+el.getFrameWidth("lr"));
  21082. }
  21083. },
  21084. // private
  21085. delayAutoWidth : function(){
  21086. if(this.el){
  21087. if(!this.awTask){
  21088. this.awTask = new Ext.util.DelayedTask(this.autoWidth, this);
  21089. }
  21090. this.awTask.delay(20);
  21091. }
  21092. },
  21093. // private
  21094. findTargetItem : function(e){
  21095. var t = e.getTarget(".x-menu-list-item", this.ul, true);
  21096. if(t && t.menuItemId){
  21097. return this.items.get(t.menuItemId);
  21098. }
  21099. },
  21100. // private
  21101. onClick : function(e){
  21102. var t;
  21103. if(t = this.findTargetItem(e)){
  21104. if(t.menu && this.ignoreParentClicks){
  21105. t.expandMenu();
  21106. }else{
  21107. t.onClick(e);
  21108. this.fireEvent("click", this, t, e);
  21109. }
  21110. }
  21111. },
  21112. // private
  21113. setActiveItem : function(item, autoExpand){
  21114. if(item != this.activeItem){
  21115. if(this.activeItem){
  21116. this.activeItem.deactivate();
  21117. }
  21118. this.activeItem = item;
  21119. item.activate(autoExpand);
  21120. }else if(autoExpand){
  21121. item.expandMenu();
  21122. }
  21123. },
  21124. // private
  21125. tryActivate : function(start, step){
  21126. var items = this.items;
  21127. for(var i = start, len = items.length; i >= 0 && i < len; i+= step){
  21128. var item = items.get(i);
  21129. if(!item.disabled && item.canActivate){
  21130. this.setActiveItem(item, false);
  21131. return item;
  21132. }
  21133. }
  21134. return false;
  21135. },
  21136. // private
  21137. onMouseOver : function(e){
  21138. var t;
  21139. if(t = this.findTargetItem(e)){
  21140. if(t.canActivate && !t.disabled){
  21141. this.setActiveItem(t, true);
  21142. }
  21143. }
  21144. this.over = true;
  21145. this.fireEvent("mouseover", this, e, t);
  21146. },
  21147. // private
  21148. onMouseOut : function(e){
  21149. var t;
  21150. if(t = this.findTargetItem(e)){
  21151. if(t == this.activeItem && t.shouldDeactivate(e)){
  21152. this.activeItem.deactivate();
  21153. delete this.activeItem;
  21154. }
  21155. }
  21156. this.over = false;
  21157. this.fireEvent("mouseout", this, e, t);
  21158. },
  21159. isVisible : function(){
  21160. return this.el && !this.hidden;
  21161. },
  21162. show : function(el, pos, parentMenu){
  21163. this.parentMenu = parentMenu;
  21164. if(!this.el){
  21165. this.render();
  21166. }
  21167. this.fireEvent("beforeshow", this);
  21168. this.showAt(this.el.getAlignToXY(el, pos || this.defaultAlign), parentMenu, false);
  21169. },
  21170. showAt : function(xy, parentMenu, _e){
  21171. this.parentMenu = parentMenu;
  21172. if(!this.el){
  21173. this.render();
  21174. }
  21175. if(_e !== false){
  21176. this.fireEvent("beforeshow", this);
  21177. xy = this.el.adjustForConstraints(xy);
  21178. }
  21179. this.el.setXY(xy);
  21180. this.el.show();
  21181. this.hidden = false;
  21182. this.focus();
  21183. this.fireEvent("show", this);
  21184. },
  21185. focus : function(){
  21186. if(!this.hidden){
  21187. this.doFocus.defer(50, this);
  21188. }
  21189. },
  21190. doFocus : function(){
  21191. if(!this.hidden){
  21192. this.focusEl.focus();
  21193. }
  21194. },
  21195. hide : function(deep){
  21196. if(this.el && this.isVisible()){
  21197. this.fireEvent("beforehide", this);
  21198. if(this.activeItem){
  21199. this.activeItem.deactivate();
  21200. this.activeItem = null;
  21201. }
  21202. this.el.hide();
  21203. this.hidden = true;
  21204. this.fireEvent("hide", this);
  21205. }
  21206. if(deep === true && this.parentMenu){
  21207. this.parentMenu.hide(true);
  21208. }
  21209. },
  21210. add : function(){
  21211. var a = arguments, l = a.length, item;
  21212. for(var i = 0; i < l; i++){
  21213. var el = a[i];
  21214. if(el.render){ // some kind of Item
  21215. item = this.addItem(el);
  21216. }else if(typeof el == "string"){ // string
  21217. if(el == "separator" || el == "-"){
  21218. item = this.addSeparator();
  21219. }else{
  21220. item = this.addText(el);
  21221. }
  21222. }else if(el.tagName || el.el){ // element
  21223. item = this.addElement(el);
  21224. }else if(typeof el == "object"){ // must be menu item config?
  21225. Ext.applyIf(el, this.defaults);
  21226. item = this.addMenuItem(el);
  21227. }
  21228. }
  21229. return item;
  21230. },
  21231. getEl : function(){
  21232. if(!this.el){
  21233. this.render();
  21234. }
  21235. return this.el;
  21236. },
  21237. addSeparator : function(){
  21238. return this.addItem(new Ext.menu.Separator());
  21239. },
  21240. addElement : function(el){
  21241. return this.addItem(new Ext.menu.BaseItem(el));
  21242. },
  21243. addItem : function(item){
  21244. this.items.add(item);
  21245. if(this.ul){
  21246. var li = document.createElement("li");
  21247. li.className = "x-menu-list-item";
  21248. this.ul.dom.appendChild(li);
  21249. item.render(li, this);
  21250. this.delayAutoWidth();
  21251. }
  21252. return item;
  21253. },
  21254. addMenuItem : function(config){
  21255. if(!(config instanceof Ext.menu.Item)){
  21256. if(typeof config.checked == "boolean"){ // must be check menu item config?
  21257. config = new Ext.menu.CheckItem(config);
  21258. }else{
  21259. config = new Ext.menu.Item(config);
  21260. }
  21261. }
  21262. return this.addItem(config);
  21263. },
  21264. addText : function(text){
  21265. return this.addItem(new Ext.menu.TextItem(text));
  21266. },
  21267. insert : function(index, item){
  21268. this.items.insert(index, item);
  21269. if(this.ul){
  21270. var li = document.createElement("li");
  21271. li.className = "x-menu-list-item";
  21272. this.ul.dom.insertBefore(li, this.ul.dom.childNodes[index]);
  21273. item.render(li, this);
  21274. this.delayAutoWidth();
  21275. }
  21276. return item;
  21277. },
  21278. remove : function(item){
  21279. this.items.removeKey(item.id);
  21280. item.destroy();
  21281. },
  21282. removeAll : function(){
  21283. if(this.items){
  21284. var f;
  21285. while(f = this.items.first()){
  21286. this.remove(f);
  21287. }
  21288. }
  21289. },
  21290. destroy : function(){
  21291. this.beforeDestroy();
  21292. Ext.menu.MenuMgr.unregister(this);
  21293. if (this.keyNav) {
  21294. this.keyNav.disable();
  21295. }
  21296. this.removeAll();
  21297. if (this.ul) {
  21298. this.ul.removeAllListeners();
  21299. }
  21300. if (this.el) {
  21301. this.el.destroy();
  21302. }
  21303. },
  21304. // private
  21305. beforeDestroy : Ext.emptyFn
  21306. });
  21307. // MenuNav is a private utility class used internally by the Menu
  21308. Ext.menu.MenuNav = function(menu){
  21309. Ext.menu.MenuNav.superclass.constructor.call(this, menu.el);
  21310. this.scope = this.menu = menu;
  21311. };
  21312. Ext.extend(Ext.menu.MenuNav, Ext.KeyNav, {
  21313. doRelay : function(e, h){
  21314. var k = e.getKey();
  21315. if(!this.menu.activeItem && e.isNavKeyPress() && k != e.SPACE && k != e.RETURN){
  21316. this.menu.tryActivate(0, 1);
  21317. return false;
  21318. }
  21319. return h.call(this.scope || this, e, this.menu);
  21320. },
  21321. up : function(e, m){
  21322. if(!m.tryActivate(m.items.indexOf(m.activeItem)-1, -1)){
  21323. m.tryActivate(m.items.length-1, -1);
  21324. }
  21325. },
  21326. down : function(e, m){
  21327. if(!m.tryActivate(m.items.indexOf(m.activeItem)+1, 1)){
  21328. m.tryActivate(0, 1);
  21329. }
  21330. },
  21331. right : function(e, m){
  21332. if(m.activeItem){
  21333. m.activeItem.expandMenu(true);
  21334. }
  21335. },
  21336. left : function(e, m){
  21337. m.hide();
  21338. if(m.parentMenu && m.parentMenu.activeItem){
  21339. m.parentMenu.activeItem.activate();
  21340. }
  21341. },
  21342. enter : function(e, m){
  21343. if(m.activeItem){
  21344. e.stopPropagation();
  21345. m.activeItem.onClick(e);
  21346. m.fireEvent("click", this, m.activeItem);
  21347. return true;
  21348. }
  21349. }
  21350. });
  21351. Ext.menu.MenuMgr = function(){
  21352. var menus, active, groups = {}, attached = false, lastShow = new Date();
  21353. // private - called when first menu is created
  21354. function init(){
  21355. menus = {};
  21356. active = new Ext.util.MixedCollection();
  21357. Ext.getDoc().addKeyListener(27, function(){
  21358. if(active.length > 0){
  21359. hideAll();
  21360. }
  21361. });
  21362. }
  21363. // private
  21364. function hideAll(){
  21365. if(active && active.length > 0){
  21366. var c = active.clone();
  21367. c.each(function(m){
  21368. m.hide();
  21369. });
  21370. }
  21371. }
  21372. // private
  21373. function onHide(m){
  21374. active.remove(m);
  21375. if(active.length < 1){
  21376. Ext.getDoc().un("mousedown", onMouseDown);
  21377. attached = false;
  21378. }
  21379. }
  21380. // private
  21381. function onShow(m){
  21382. var last = active.last();
  21383. lastShow = new Date();
  21384. active.add(m);
  21385. if(!attached){
  21386. Ext.getDoc().on("mousedown", onMouseDown);
  21387. attached = true;
  21388. }
  21389. if(m.parentMenu){
  21390. m.getEl().setZIndex(parseInt(m.parentMenu.getEl().getStyle("z-index"), 10) + 3);
  21391. m.parentMenu.activeChild = m;
  21392. }else if(last && last.isVisible()){
  21393. m.getEl().setZIndex(parseInt(last.getEl().getStyle("z-index"), 10) + 3);
  21394. }
  21395. }
  21396. // private
  21397. function onBeforeHide(m){
  21398. if(m.activeChild){
  21399. m.activeChild.hide();
  21400. }
  21401. if(m.autoHideTimer){
  21402. clearTimeout(m.autoHideTimer);
  21403. delete m.autoHideTimer;
  21404. }
  21405. }
  21406. // private
  21407. function onBeforeShow(m){
  21408. var pm = m.parentMenu;
  21409. if(!pm && !m.allowOtherMenus){
  21410. hideAll();
  21411. }else if(pm && pm.activeChild){
  21412. pm.activeChild.hide();
  21413. }
  21414. }
  21415. // private
  21416. function onMouseDown(e){
  21417. if(lastShow.getElapsed() > 50 && active.length > 0 && !e.getTarget(".x-menu")){
  21418. hideAll();
  21419. }
  21420. }
  21421. // private
  21422. function onBeforeCheck(mi, state){
  21423. if(state){
  21424. var g = groups[mi.group];
  21425. for(var i = 0, l = g.length; i < l; i++){
  21426. if(g[i] != mi){
  21427. g[i].setChecked(false);
  21428. }
  21429. }
  21430. }
  21431. }
  21432. return {
  21433. hideAll : function(){
  21434. hideAll();
  21435. },
  21436. // private
  21437. register : function(menu){
  21438. if(!menus){
  21439. init();
  21440. }
  21441. menus[menu.id] = menu;
  21442. menu.on("beforehide", onBeforeHide);
  21443. menu.on("hide", onHide);
  21444. menu.on("beforeshow", onBeforeShow);
  21445. menu.on("show", onShow);
  21446. var g = menu.group;
  21447. if(g && menu.events["checkchange"]){
  21448. if(!groups[g]){
  21449. groups[g] = [];
  21450. }
  21451. groups[g].push(menu);
  21452. menu.on("checkchange", onCheck);
  21453. }
  21454. },
  21455. get : function(menu){
  21456. if(typeof menu == "string"){ // menu id
  21457. if(!menus){ // not initialized, no menus to return
  21458. return null;
  21459. }
  21460. return menus[menu];
  21461. }else if(menu.events){ // menu instance
  21462. return menu;
  21463. }else if(typeof menu.length == 'number'){ // array of menu items?
  21464. return new Ext.menu.Menu({items:menu});
  21465. }else{ // otherwise, must be a config
  21466. return new Ext.menu.Menu(menu);
  21467. }
  21468. },
  21469. // private
  21470. unregister : function(menu){
  21471. delete menus[menu.id];
  21472. menu.un("beforehide", onBeforeHide);
  21473. menu.un("hide", onHide);
  21474. menu.un("beforeshow", onBeforeShow);
  21475. menu.un("show", onShow);
  21476. var g = menu.group;
  21477. if(g && menu.events["checkchange"]){
  21478. groups[g].remove(menu);
  21479. menu.un("checkchange", onCheck);
  21480. }
  21481. },
  21482. // private
  21483. registerCheckable : function(menuItem){
  21484. var g = menuItem.group;
  21485. if(g){
  21486. if(!groups[g]){
  21487. groups[g] = [];
  21488. }
  21489. groups[g].push(menuItem);
  21490. menuItem.on("beforecheckchange", onBeforeCheck);
  21491. }
  21492. },
  21493. // private
  21494. unregisterCheckable : function(menuItem){
  21495. var g = menuItem.group;
  21496. if(g){
  21497. groups[g].remove(menuItem);
  21498. menuItem.un("beforecheckchange", onBeforeCheck);
  21499. }
  21500. },
  21501. getCheckedItem : function(groupId){
  21502. var g = groups[groupId];
  21503. if(g){
  21504. for(var i = 0, l = g.length; i < l; i++){
  21505. if(g[i].checked){
  21506. return g[i];
  21507. }
  21508. }
  21509. }
  21510. return null;
  21511. },
  21512. setCheckedItem : function(groupId, itemId){
  21513. var g = groups[groupId];
  21514. if(g){
  21515. for(var i = 0, l = g.length; i < l; i++){
  21516. if(g[i].id == itemId){
  21517. g[i].setChecked(true);
  21518. }
  21519. }
  21520. }
  21521. return null;
  21522. }
  21523. };
  21524. }();
  21525. Ext.menu.BaseItem = function(config){
  21526. Ext.menu.BaseItem.superclass.constructor.call(this, config);
  21527. this.addEvents(
  21528. 'click',
  21529. 'activate',
  21530. 'deactivate'
  21531. );
  21532. if(this.handler){
  21533. this.on("click", this.handler, this.scope);
  21534. }
  21535. };
  21536. Ext.extend(Ext.menu.BaseItem, Ext.Component, {
  21537. canActivate : false,
  21538. activeClass : "x-menu-item-active",
  21539. hideOnClick : true,
  21540. hideDelay : 100,
  21541. // private
  21542. ctype: "Ext.menu.BaseItem",
  21543. // private
  21544. actionMode : "container",
  21545. // private
  21546. render : function(container, parentMenu){
  21547. this.parentMenu = parentMenu;
  21548. Ext.menu.BaseItem.superclass.render.call(this, container);
  21549. this.container.menuItemId = this.id;
  21550. },
  21551. // private
  21552. onRender : function(container, position){
  21553. this.el = Ext.get(this.el);
  21554. if(this.id){
  21555. this.el.id = this.id;
  21556. }
  21557. container.dom.appendChild(this.el.dom);
  21558. },
  21559. setHandler : function(handler, scope){
  21560. if(this.handler){
  21561. this.un("click", this.handler, this.scope);
  21562. }
  21563. this.on("click", this.handler = handler, this.scope = scope);
  21564. },
  21565. // private
  21566. onClick : function(e){
  21567. if(!this.disabled && this.fireEvent("click", this, e) !== false
  21568. && this.parentMenu.fireEvent("itemclick", this, e) !== false){
  21569. this.handleClick(e);
  21570. }else{
  21571. e.stopEvent();
  21572. }
  21573. },
  21574. // private
  21575. activate : function(){
  21576. if(this.disabled){
  21577. return false;
  21578. }
  21579. var li = this.container;
  21580. li.addClass(this.activeClass);
  21581. this.region = li.getRegion().adjust(2, 2, -2, -2);
  21582. this.fireEvent("activate", this);
  21583. return true;
  21584. },
  21585. // private
  21586. deactivate : function(){
  21587. this.container.removeClass(this.activeClass);
  21588. this.fireEvent("deactivate", this);
  21589. },
  21590. // private
  21591. shouldDeactivate : function(e){
  21592. return !this.region || !this.region.contains(e.getPoint());
  21593. },
  21594. // private
  21595. handleClick : function(e){
  21596. if(this.hideOnClick){
  21597. this.parentMenu.hide.defer(this.hideDelay, this.parentMenu, [true]);
  21598. }
  21599. },
  21600. // private
  21601. expandMenu : function(autoActivate){
  21602. // do nothing
  21603. },
  21604. // private
  21605. hideMenu : function(){
  21606. // do nothing
  21607. }
  21608. });
  21609. Ext.menu.TextItem = function(cfg){
  21610. if(typeof cfg == 'string'){
  21611. cfg = {text: cfg}
  21612. }
  21613. Ext.menu.TextItem.superclass.constructor.call(this, cfg);
  21614. };
  21615. Ext.extend(Ext.menu.TextItem, Ext.menu.BaseItem, {
  21616. hideOnClick : false,
  21617. itemCls : "x-menu-text",
  21618. // private
  21619. onRender : function(){
  21620. var s = document.createElement("span");
  21621. s.className = this.itemCls;
  21622. s.innerHTML = this.text;
  21623. this.el = s;
  21624. Ext.menu.TextItem.superclass.onRender.apply(this, arguments);
  21625. }
  21626. });
  21627. Ext.menu.Separator = function(config){
  21628. Ext.menu.Separator.superclass.constructor.call(this, config);
  21629. };
  21630. Ext.extend(Ext.menu.Separator, Ext.menu.BaseItem, {
  21631. itemCls : "x-menu-sep",
  21632. hideOnClick : false,
  21633. // private
  21634. onRender : function(li){
  21635. var s = document.createElement("span");
  21636. s.className = this.itemCls;
  21637. s.innerHTML = "&#160;";
  21638. this.el = s;
  21639. li.addClass("x-menu-sep-li");
  21640. Ext.menu.Separator.superclass.onRender.apply(this, arguments);
  21641. }
  21642. });
  21643. Ext.menu.Item = function(config){
  21644. Ext.menu.Item.superclass.constructor.call(this, config);
  21645. if(this.menu){
  21646. this.menu = Ext.menu.MenuMgr.get(this.menu);
  21647. }
  21648. };
  21649. Ext.extend(Ext.menu.Item, Ext.menu.BaseItem, {
  21650. itemCls : "x-menu-item",
  21651. canActivate : true,
  21652. showDelay: 200,
  21653. // doc'd in BaseItem
  21654. hideDelay: 200,
  21655. // private
  21656. ctype: "Ext.menu.Item",
  21657. // private
  21658. onRender : function(container, position){
  21659. var el = document.createElement("a");
  21660. el.hideFocus = true;
  21661. el.unselectable = "on";
  21662. el.href = this.href || "#";
  21663. if(this.hrefTarget){
  21664. el.target = this.hrefTarget;
  21665. }
  21666. el.className = this.itemCls + (this.menu ? " x-menu-item-arrow" : "") + (this.cls ? " " + this.cls : "");
  21667. el.innerHTML = String.format(
  21668. '<img src="{0}" class="x-menu-item-icon {2}" />{1}',
  21669. this.icon || Ext.BLANK_IMAGE_URL, this.itemText||this.text, this.iconCls || '');
  21670. this.el = el;
  21671. Ext.menu.Item.superclass.onRender.call(this, container, position);
  21672. },
  21673. setText : function(text){
  21674. this.text = text;
  21675. if(this.rendered){
  21676. this.el.update(String.format(
  21677. '<img src="{0}" class="x-menu-item-icon {2}">{1}',
  21678. this.icon || Ext.BLANK_IMAGE_URL, this.text, this.iconCls || ''));
  21679. this.parentMenu.autoWidth();
  21680. }
  21681. },
  21682. setIconClass : function(cls){
  21683. var oldCls = this.iconCls;
  21684. this.iconCls = cls;
  21685. if(this.rendered){
  21686. this.el.child('img.x-menu-item-icon').replaceClass(oldCls, this.iconCls);
  21687. }
  21688. },
  21689. //private
  21690. beforeDestroy: function(){
  21691. if (this.menu){
  21692. this.menu.destroy();
  21693. }
  21694. Ext.menu.Item.superclass.beforeDestroy.call(this);
  21695. },
  21696. // private
  21697. handleClick : function(e){
  21698. if(!this.href){ // if no link defined, stop the event automatically
  21699. e.stopEvent();
  21700. }
  21701. Ext.menu.Item.superclass.handleClick.apply(this, arguments);
  21702. },
  21703. // private
  21704. activate : function(autoExpand){
  21705. if(Ext.menu.Item.superclass.activate.apply(this, arguments)){
  21706. this.focus();
  21707. if(autoExpand){
  21708. this.expandMenu();
  21709. }
  21710. }
  21711. return true;
  21712. },
  21713. // private
  21714. shouldDeactivate : function(e){
  21715. if(Ext.menu.Item.superclass.shouldDeactivate.call(this, e)){
  21716. if(this.menu && this.menu.isVisible()){
  21717. return !this.menu.getEl().getRegion().contains(e.getPoint());
  21718. }
  21719. return true;
  21720. }
  21721. return false;
  21722. },
  21723. // private
  21724. deactivate : function(){
  21725. Ext.menu.Item.superclass.deactivate.apply(this, arguments);
  21726. this.hideMenu();
  21727. },
  21728. // private
  21729. expandMenu : function(autoActivate){
  21730. if(!this.disabled && this.menu){
  21731. clearTimeout(this.hideTimer);
  21732. delete this.hideTimer;
  21733. if(!this.menu.isVisible() && !this.showTimer){
  21734. this.showTimer = this.deferExpand.defer(this.showDelay, this, [autoActivate]);
  21735. }else if (this.menu.isVisible() && autoActivate){
  21736. this.menu.tryActivate(0, 1);
  21737. }
  21738. }
  21739. },
  21740. // private
  21741. deferExpand : function(autoActivate){
  21742. delete this.showTimer;
  21743. this.menu.show(this.container, this.parentMenu.subMenuAlign || "tl-tr?", this.parentMenu);
  21744. if(autoActivate){
  21745. this.menu.tryActivate(0, 1);
  21746. }
  21747. },
  21748. // private
  21749. hideMenu : function(){
  21750. clearTimeout(this.showTimer);
  21751. delete this.showTimer;
  21752. if(!this.hideTimer && this.menu && this.menu.isVisible()){
  21753. this.hideTimer = this.deferHide.defer(this.hideDelay, this);
  21754. }
  21755. },
  21756. // private
  21757. deferHide : function(){
  21758. delete this.hideTimer;
  21759. if(this.menu.over){
  21760. this.parentMenu.setActiveItem(this, false);
  21761. }else{
  21762. this.menu.hide();
  21763. }
  21764. }
  21765. });
  21766. Ext.menu.CheckItem = function(config){
  21767. Ext.menu.CheckItem.superclass.constructor.call(this, config);
  21768. this.addEvents(
  21769. "beforecheckchange" ,
  21770. "checkchange"
  21771. );
  21772. if(this.checkHandler){
  21773. this.on('checkchange', this.checkHandler, this.scope);
  21774. }
  21775. Ext.menu.MenuMgr.registerCheckable(this);
  21776. };
  21777. Ext.extend(Ext.menu.CheckItem, Ext.menu.Item, {
  21778. itemCls : "x-menu-item x-menu-check-item",
  21779. groupClass : "x-menu-group-item",
  21780. checked: false,
  21781. // private
  21782. ctype: "Ext.menu.CheckItem",
  21783. // private
  21784. onRender : function(c){
  21785. Ext.menu.CheckItem.superclass.onRender.apply(this, arguments);
  21786. if(this.group){
  21787. this.el.addClass(this.groupClass);
  21788. }
  21789. if(this.checked){
  21790. this.checked = false;
  21791. this.setChecked(true, true);
  21792. }
  21793. },
  21794. // private
  21795. destroy : function(){
  21796. Ext.menu.MenuMgr.unregisterCheckable(this);
  21797. Ext.menu.CheckItem.superclass.destroy.apply(this, arguments);
  21798. },
  21799. setChecked : function(state, suppressEvent){
  21800. if(this.checked != state && this.fireEvent("beforecheckchange", this, state) !== false){
  21801. if(this.container){
  21802. this.container[state ? "addClass" : "removeClass"]("x-menu-item-checked");
  21803. }
  21804. this.checked = state;
  21805. if(suppressEvent !== true){
  21806. this.fireEvent("checkchange", this, state);
  21807. }
  21808. }
  21809. },
  21810. // private
  21811. handleClick : function(e){
  21812. if(!this.disabled && !(this.checked && this.group)){// disable unselect on radio item
  21813. this.setChecked(!this.checked);
  21814. }
  21815. Ext.menu.CheckItem.superclass.handleClick.apply(this, arguments);
  21816. }
  21817. });
  21818. Ext.menu.Adapter = function(component, config){
  21819. Ext.menu.Adapter.superclass.constructor.call(this, config);
  21820. this.component = component;
  21821. };
  21822. Ext.extend(Ext.menu.Adapter, Ext.menu.BaseItem, {
  21823. // private
  21824. canActivate : true,
  21825. // private
  21826. onRender : function(container, position){
  21827. this.component.render(container);
  21828. this.el = this.component.getEl();
  21829. },
  21830. // private
  21831. activate : function(){
  21832. if(this.disabled){
  21833. return false;
  21834. }
  21835. this.component.focus();
  21836. this.fireEvent("activate", this);
  21837. return true;
  21838. },
  21839. // private
  21840. deactivate : function(){
  21841. this.fireEvent("deactivate", this);
  21842. },
  21843. // private
  21844. disable : function(){
  21845. this.component.disable();
  21846. Ext.menu.Adapter.superclass.disable.call(this);
  21847. },
  21848. // private
  21849. enable : function(){
  21850. this.component.enable();
  21851. Ext.menu.Adapter.superclass.enable.call(this);
  21852. }
  21853. });
  21854. Ext.menu.DateItem = function(config){
  21855. Ext.menu.DateItem.superclass.constructor.call(this, new Ext.DatePicker(config), config);
  21856. this.picker = this.component;
  21857. this.addEvents('select');
  21858. this.picker.on("render", function(picker){
  21859. picker.getEl().swallowEvent("click");
  21860. picker.container.addClass("x-menu-date-item");
  21861. });
  21862. this.picker.on("select", this.onSelect, this);
  21863. };
  21864. Ext.extend(Ext.menu.DateItem, Ext.menu.Adapter, {
  21865. // private
  21866. onSelect : function(picker, date){
  21867. this.fireEvent("select", this, date, picker);
  21868. Ext.menu.DateItem.superclass.handleClick.call(this);
  21869. }
  21870. });
  21871. Ext.menu.ColorItem = function(config){
  21872. Ext.menu.ColorItem.superclass.constructor.call(this, new Ext.ColorPalette(config), config);
  21873. this.palette = this.component;
  21874. this.relayEvents(this.palette, ["select"]);
  21875. if(this.selectHandler){
  21876. this.on('select', this.selectHandler, this.scope);
  21877. }
  21878. };
  21879. Ext.extend(Ext.menu.ColorItem, Ext.menu.Adapter);
  21880. Ext.menu.DateMenu = function(config){
  21881. Ext.menu.DateMenu.superclass.constructor.call(this, config);
  21882. this.plain = true;
  21883. var di = new Ext.menu.DateItem(config);
  21884. this.add(di);
  21885. this.picker = di.picker;
  21886. this.relayEvents(di, ["select"]);
  21887. this.on('beforeshow', function(){
  21888. if(this.picker){
  21889. this.picker.hideMonthPicker(true);
  21890. }
  21891. }, this);
  21892. };
  21893. Ext.extend(Ext.menu.DateMenu, Ext.menu.Menu, {
  21894. cls:'x-date-menu',
  21895. // private
  21896. beforeDestroy : function() {
  21897. this.picker.destroy();
  21898. }
  21899. });
  21900. Ext.menu.ColorMenu = function(config){
  21901. Ext.menu.ColorMenu.superclass.constructor.call(this, config);
  21902. this.plain = true;
  21903. var ci = new Ext.menu.ColorItem(config);
  21904. this.add(ci);
  21905. this.palette = ci.palette;
  21906. this.relayEvents(ci, ["select"]);
  21907. };
  21908. Ext.extend(Ext.menu.ColorMenu, Ext.menu.Menu, {
  21909. //private
  21910. beforeDestroy: function(){
  21911. this.palette.destroy();
  21912. }
  21913. });
  21914. Ext.form.Field = Ext.extend(Ext.BoxComponent, {
  21915. invalidClass : "x-form-invalid",
  21916. invalidText : "The value in this field is invalid",
  21917. focusClass : "x-form-focus",
  21918. validationEvent : "keyup",
  21919. validateOnBlur : true,
  21920. validationDelay : 250,
  21921. defaultAutoCreate : {tag: "input", type: "text", size: "20", autocomplete: "off"},
  21922. fieldClass : "x-form-field",
  21923. msgTarget : 'qtip',
  21924. msgFx : 'normal',
  21925. readOnly : false,
  21926. disabled : false,
  21927. // private
  21928. isFormField : true,
  21929. // private
  21930. hasFocus : false,
  21931. // private
  21932. initComponent : function(){
  21933. Ext.form.Field.superclass.initComponent.call(this);
  21934. this.addEvents(
  21935. 'focus',
  21936. 'blur',
  21937. 'specialkey',
  21938. 'change',
  21939. 'invalid',
  21940. 'valid'
  21941. );
  21942. },
  21943. getName: function(){
  21944. return this.rendered && this.el.dom.name ? this.el.dom.name : (this.hiddenName || '');
  21945. },
  21946. // private
  21947. onRender : function(ct, position){
  21948. Ext.form.Field.superclass.onRender.call(this, ct, position);
  21949. if(!this.el){
  21950. var cfg = this.getAutoCreate();
  21951. if(!cfg.name){
  21952. cfg.name = this.name || this.id;
  21953. }
  21954. if(this.inputType){
  21955. cfg.type = this.inputType;
  21956. }
  21957. this.el = ct.createChild(cfg, position);
  21958. }
  21959. var type = this.el.dom.type;
  21960. if(type){
  21961. if(type == 'password'){
  21962. type = 'text';
  21963. }
  21964. this.el.addClass('x-form-'+type);
  21965. }
  21966. if(this.readOnly){
  21967. this.el.dom.readOnly = true;
  21968. }
  21969. if(this.tabIndex !== undefined){
  21970. this.el.dom.setAttribute('tabIndex', this.tabIndex);
  21971. }
  21972. this.el.addClass([this.fieldClass, this.cls]);
  21973. },
  21974. // private
  21975. initValue : function(){
  21976. if(this.value !== undefined){
  21977. this.setValue(this.value);
  21978. }else if(this.el.dom.value.length > 0 && this.el.dom.value != this.emptyText){
  21979. this.setValue(this.el.dom.value);
  21980. }
  21981. // reference to original value for reset
  21982. this.originalValue = this.getValue();
  21983. },
  21984. isDirty : function() {
  21985. if(this.disabled) {
  21986. return false;
  21987. }
  21988. return String(this.getValue()) !== String(this.originalValue);
  21989. },
  21990. // private
  21991. afterRender : function(){
  21992. Ext.form.Field.superclass.afterRender.call(this);
  21993. this.initEvents();
  21994. this.initValue();
  21995. },
  21996. // private
  21997. fireKey : function(e){
  21998. if(e.isSpecialKey()){
  21999. this.fireEvent("specialkey", this, e);
  22000. }
  22001. },
  22002. reset : function(){
  22003. this.setValue(this.originalValue);
  22004. this.clearInvalid();
  22005. },
  22006. // private
  22007. initEvents : function(){
  22008. this.el.on(Ext.isIE || Ext.isSafari3 ? "keydown" : "keypress", this.fireKey, this);
  22009. this.el.on("focus", this.onFocus, this);
  22010. // fix weird FF/Win editor issue when changing OS window focus
  22011. var o = this.inEditor && Ext.isWindows && Ext.isGecko ? {buffer:10} : null;
  22012. this.el.on("blur", this.onBlur, this, o);
  22013. },
  22014. // private
  22015. onFocus : function(){
  22016. if(this.focusClass){
  22017. this.el.addClass(this.focusClass);
  22018. }
  22019. if(!this.hasFocus){
  22020. this.hasFocus = true;
  22021. this.startValue = this.getValue();
  22022. this.fireEvent("focus", this);
  22023. }
  22024. },
  22025. // private
  22026. beforeBlur : Ext.emptyFn,
  22027. // private
  22028. onBlur : function(){
  22029. this.beforeBlur();
  22030. if(this.focusClass){
  22031. this.el.removeClass(this.focusClass);
  22032. }
  22033. this.hasFocus = false;
  22034. if(this.validationEvent !== false && this.validateOnBlur && this.validationEvent != "blur"){
  22035. this.validate();
  22036. }
  22037. var v = this.getValue();
  22038. if(String(v) !== String(this.startValue)){
  22039. this.fireEvent('change', this, v, this.startValue);
  22040. }
  22041. this.fireEvent("blur", this);
  22042. },
  22043. isValid : function(preventMark){
  22044. if(this.disabled){
  22045. return true;
  22046. }
  22047. var restore = this.preventMark;
  22048. this.preventMark = preventMark === true;
  22049. var v = this.validateValue(this.processValue(this.getRawValue()));
  22050. this.preventMark = restore;
  22051. return v;
  22052. },
  22053. validate : function(){
  22054. if(this.disabled || this.validateValue(this.processValue(this.getRawValue()))){
  22055. this.clearInvalid();
  22056. return true;
  22057. }
  22058. return false;
  22059. },
  22060. // protected - should be overridden by subclasses if necessary to prepare raw values for validation
  22061. processValue : function(value){
  22062. return value;
  22063. },
  22064. // private
  22065. // Subclasses should provide the validation implementation by overriding this
  22066. validateValue : function(value){
  22067. return true;
  22068. },
  22069. markInvalid : function(msg){
  22070. if(!this.rendered || this.preventMark){ // not rendered
  22071. return;
  22072. }
  22073. this.el.addClass(this.invalidClass);
  22074. msg = msg || this.invalidText;
  22075. switch(this.msgTarget){
  22076. case 'qtip':
  22077. this.el.dom.qtip = msg;
  22078. this.el.dom.qclass = 'x-form-invalid-tip';
  22079. if(Ext.QuickTips){ // fix for floating editors interacting with DND
  22080. Ext.QuickTips.enable();
  22081. }
  22082. break;
  22083. case 'title':
  22084. this.el.dom.title = msg;
  22085. break;
  22086. case 'under':
  22087. if(!this.errorEl){
  22088. var elp = this.getErrorCt();
  22089. if(!elp){ // field has no container el
  22090. this.el.dom.title = msg;
  22091. break;
  22092. }
  22093. this.errorEl = elp.createChild({cls:'x-form-invalid-msg'});
  22094. this.errorEl.setWidth(elp.getWidth(true)-20);
  22095. }
  22096. this.errorEl.update(msg);
  22097. Ext.form.Field.msgFx[this.msgFx].show(this.errorEl, this);
  22098. break;
  22099. case 'side':
  22100. if(!this.errorIcon){
  22101. var elp = this.getErrorCt();
  22102. if(!elp){ // field has no container el
  22103. this.el.dom.title = msg;
  22104. break;
  22105. }
  22106. this.errorIcon = elp.createChild({cls:'x-form-invalid-icon'});
  22107. }
  22108. this.alignErrorIcon();
  22109. this.errorIcon.dom.qtip = msg;
  22110. this.errorIcon.dom.qclass = 'x-form-invalid-tip';
  22111. this.errorIcon.show();
  22112. this.on('resize', this.alignErrorIcon, this);
  22113. break;
  22114. default:
  22115. var t = Ext.getDom(this.msgTarget);
  22116. t.innerHTML = msg;
  22117. t.style.display = this.msgDisplay;
  22118. break;
  22119. }
  22120. this.fireEvent('invalid', this, msg);
  22121. },
  22122. // private
  22123. getErrorCt : function(){
  22124. return this.el.findParent('.x-form-element', 5, true) || // use form element wrap if available
  22125. this.el.findParent('.x-form-field-wrap', 5, true); // else direct field wrap
  22126. },
  22127. // private
  22128. alignErrorIcon : function(){
  22129. this.errorIcon.alignTo(this.el, 'tl-tr', [2, 0]);
  22130. },
  22131. clearInvalid : function(){
  22132. if(!this.rendered || this.preventMark){ // not rendered
  22133. return;
  22134. }
  22135. this.el.removeClass(this.invalidClass);
  22136. switch(this.msgTarget){
  22137. case 'qtip':
  22138. this.el.dom.qtip = '';
  22139. break;
  22140. case 'title':
  22141. this.el.dom.title = '';
  22142. break;
  22143. case 'under':
  22144. if(this.errorEl){
  22145. Ext.form.Field.msgFx[this.msgFx].hide(this.errorEl, this);
  22146. }
  22147. break;
  22148. case 'side':
  22149. if(this.errorIcon){
  22150. this.errorIcon.dom.qtip = '';
  22151. this.errorIcon.hide();
  22152. this.un('resize', this.alignErrorIcon, this);
  22153. }
  22154. break;
  22155. default:
  22156. var t = Ext.getDom(this.msgTarget);
  22157. t.innerHTML = '';
  22158. t.style.display = 'none';
  22159. break;
  22160. }
  22161. this.fireEvent('valid', this);
  22162. },
  22163. getRawValue : function(){
  22164. var v = this.rendered ? this.el.getValue() : Ext.value(this.value, '');
  22165. if(v === this.emptyText){
  22166. v = '';
  22167. }
  22168. return v;
  22169. },
  22170. getValue : function(){
  22171. if(!this.rendered) {
  22172. return this.value;
  22173. }
  22174. var v = this.el.getValue();
  22175. if(v === this.emptyText || v === undefined){
  22176. v = '';
  22177. }
  22178. return v;
  22179. },
  22180. setRawValue : function(v){
  22181. return this.el.dom.value = (v === null || v === undefined ? '' : v);
  22182. },
  22183. setValue : function(v){
  22184. this.value = v;
  22185. if(this.rendered){
  22186. this.el.dom.value = (v === null || v === undefined ? '' : v);
  22187. this.validate();
  22188. }
  22189. },
  22190. // private
  22191. adjustSize : function(w, h){
  22192. var s = Ext.form.Field.superclass.adjustSize.call(this, w, h);
  22193. s.width = this.adjustWidth(this.el.dom.tagName, s.width);
  22194. return s;
  22195. },
  22196. // private
  22197. adjustWidth : function(tag, w){
  22198. tag = tag.toLowerCase();
  22199. if(typeof w == 'number' && !Ext.isSafari){
  22200. if(Ext.isIE && (tag == 'input' || tag == 'textarea')){
  22201. if(tag == 'input' && !Ext.isStrict){
  22202. return this.inEditor ? w : w - 3;
  22203. }
  22204. if(tag == 'input' && Ext.isStrict){
  22205. return w - (Ext.isIE6 ? 4 : 1);
  22206. }
  22207. if(tag == 'textarea' && Ext.isStrict){
  22208. return w-2;
  22209. }
  22210. }else if(Ext.isOpera && Ext.isStrict){
  22211. if(tag == 'input'){
  22212. return w + 2;
  22213. }
  22214. if(tag == 'textarea'){
  22215. return w-2;
  22216. }
  22217. }
  22218. }
  22219. return w;
  22220. }
  22221. });
  22222. Ext.form.MessageTargets = {
  22223. 'qtip' : {
  22224. mark: function(f){
  22225. this.el.dom.qtip = msg;
  22226. this.el.dom.qclass = 'x-form-invalid-tip';
  22227. if(Ext.QuickTips){ // fix for floating editors interacting with DND
  22228. Ext.QuickTips.enable();
  22229. }
  22230. },
  22231. clear: function(f){
  22232. this.el.dom.qtip = '';
  22233. }
  22234. },
  22235. 'title' : {
  22236. mark: function(f){
  22237. this.el.dom.title = msg;
  22238. },
  22239. clear: function(f){
  22240. this.el.dom.title = '';
  22241. }
  22242. },
  22243. 'under' : {
  22244. mark: function(f){
  22245. if(!this.errorEl){
  22246. var elp = this.getErrorCt();
  22247. if(!elp){ // field has no container el
  22248. this.el.dom.title = msg;
  22249. return;
  22250. }
  22251. this.errorEl = elp.createChild({cls:'x-form-invalid-msg'});
  22252. this.errorEl.setWidth(elp.getWidth(true)-20);
  22253. }
  22254. this.errorEl.update(msg);
  22255. Ext.form.Field.msgFx[this.msgFx].show(this.errorEl, this);
  22256. },
  22257. clear: function(f){
  22258. if(this.errorEl){
  22259. Ext.form.Field.msgFx[this.msgFx].hide(this.errorEl, this);
  22260. }else{
  22261. this.el.dom.title = '';
  22262. }
  22263. }
  22264. },
  22265. 'side' : {
  22266. mark: function(f){
  22267. if(!this.errorIcon){
  22268. var elp = this.getErrorCt();
  22269. if(!elp){ // field has no container el
  22270. this.el.dom.title = msg;
  22271. return;
  22272. }
  22273. this.errorIcon = elp.createChild({cls:'x-form-invalid-icon'});
  22274. }
  22275. this.alignErrorIcon();
  22276. this.errorIcon.dom.qtip = msg;
  22277. this.errorIcon.dom.qclass = 'x-form-invalid-tip';
  22278. this.errorIcon.show();
  22279. this.on('resize', this.alignErrorIcon, this);
  22280. },
  22281. clear: function(f){
  22282. if(this.errorIcon){
  22283. this.errorIcon.dom.qtip = '';
  22284. this.errorIcon.hide();
  22285. this.un('resize', this.alignErrorIcon, this);
  22286. }else{
  22287. this.el.dom.title = '';
  22288. }
  22289. }
  22290. },
  22291. 'around' : {
  22292. mark: function(f){
  22293. },
  22294. clear: function(f){
  22295. }
  22296. }
  22297. };
  22298. // anything other than normal should be considered experimental
  22299. Ext.form.Field.msgFx = {
  22300. normal : {
  22301. show: function(msgEl, f){
  22302. msgEl.setDisplayed('block');
  22303. },
  22304. hide : function(msgEl, f){
  22305. msgEl.setDisplayed(false).update('');
  22306. }
  22307. },
  22308. slide : {
  22309. show: function(msgEl, f){
  22310. msgEl.slideIn('t', {stopFx:true});
  22311. },
  22312. hide : function(msgEl, f){
  22313. msgEl.slideOut('t', {stopFx:true,useDisplay:true});
  22314. }
  22315. },
  22316. slideRight : {
  22317. show: function(msgEl, f){
  22318. msgEl.fixDisplay();
  22319. msgEl.alignTo(f.el, 'tl-tr');
  22320. msgEl.slideIn('l', {stopFx:true});
  22321. },
  22322. hide : function(msgEl, f){
  22323. msgEl.slideOut('l', {stopFx:true,useDisplay:true});
  22324. }
  22325. }
  22326. };
  22327. Ext.reg('field', Ext.form.Field);
  22328. Ext.form.TextField = Ext.extend(Ext.form.Field, {
  22329. grow : false,
  22330. growMin : 30,
  22331. growMax : 800,
  22332. vtype : null,
  22333. maskRe : null,
  22334. disableKeyFilter : false,
  22335. allowBlank : true,
  22336. minLength : 0,
  22337. maxLength : Number.MAX_VALUE,
  22338. minLengthText : "The minimum length for this field is {0}",
  22339. maxLengthText : "The maximum length for this field is {0}",
  22340. selectOnFocus : false,
  22341. blankText : "This field is required",
  22342. validator : null,
  22343. regex : null,
  22344. regexText : "",
  22345. emptyText : null,
  22346. emptyClass : 'x-form-empty-field',
  22347. initComponent : function(){
  22348. Ext.form.TextField.superclass.initComponent.call(this);
  22349. this.addEvents(
  22350. 'autosize',
  22351. 'keydown',
  22352. 'keyup',
  22353. 'keypress'
  22354. );
  22355. },
  22356. // private
  22357. initEvents : function(){
  22358. Ext.form.TextField.superclass.initEvents.call(this);
  22359. if(this.validationEvent == 'keyup'){
  22360. this.validationTask = new Ext.util.DelayedTask(this.validate, this);
  22361. this.el.on('keyup', this.filterValidation, this);
  22362. }
  22363. else if(this.validationEvent !== false){
  22364. this.el.on(this.validationEvent, this.validate, this, {buffer: this.validationDelay});
  22365. }
  22366. if(this.selectOnFocus || this.emptyText){
  22367. this.on("focus", this.preFocus, this);
  22368. this.el.on('mousedown', function(){
  22369. if(!this.hasFocus){
  22370. this.el.on('mouseup', function(e){
  22371. e.preventDefault();
  22372. }, this, {single:true});
  22373. }
  22374. }, this);
  22375. if(this.emptyText){
  22376. this.on('blur', this.postBlur, this);
  22377. this.applyEmptyText();
  22378. }
  22379. }
  22380. if(this.maskRe || (this.vtype && this.disableKeyFilter !== true && (this.maskRe = Ext.form.VTypes[this.vtype+'Mask']))){
  22381. this.el.on("keypress", this.filterKeys, this);
  22382. }
  22383. if(this.grow){
  22384. this.el.on("keyup", this.onKeyUpBuffered, this, {buffer:50});
  22385. this.el.on("click", this.autoSize, this);
  22386. }
  22387. if(this.enableKeyEvents){
  22388. this.el.on("keyup", this.onKeyUp, this);
  22389. this.el.on("keydown", this.onKeyDown, this);
  22390. this.el.on("keypress", this.onKeyPress, this);
  22391. }
  22392. },
  22393. processValue : function(value){
  22394. if(this.stripCharsRe){
  22395. var newValue = value.replace(this.stripCharsRe, '');
  22396. if(newValue !== value){
  22397. this.setRawValue(newValue);
  22398. return newValue;
  22399. }
  22400. }
  22401. return value;
  22402. },
  22403. filterValidation : function(e){
  22404. if(!e.isNavKeyPress()){
  22405. this.validationTask.delay(this.validationDelay);
  22406. }
  22407. },
  22408. //private
  22409. onDisable: function(){
  22410. Ext.form.TextField.superclass.onDisable.call(this);
  22411. if(Ext.isIE){
  22412. this.el.dom.unselectable = 'on';
  22413. }
  22414. },
  22415. //private
  22416. onEnable: function(){
  22417. Ext.form.TextField.superclass.onEnable.call(this);
  22418. if(Ext.isIE){
  22419. this.el.dom.unselectable = '';
  22420. }
  22421. },
  22422. // private
  22423. onKeyUpBuffered : function(e){
  22424. if(!e.isNavKeyPress()){
  22425. this.autoSize();
  22426. }
  22427. },
  22428. // private
  22429. onKeyUp : function(e){
  22430. this.fireEvent('keyup', this, e);
  22431. },
  22432. // private
  22433. onKeyDown : function(e){
  22434. this.fireEvent('keydown', this, e);
  22435. },
  22436. // private
  22437. onKeyPress : function(e){
  22438. this.fireEvent('keypress', this, e);
  22439. },
  22440. reset : function(){
  22441. Ext.form.TextField.superclass.reset.call(this);
  22442. this.applyEmptyText();
  22443. },
  22444. applyEmptyText : function(){
  22445. if(this.rendered && this.emptyText && this.getRawValue().length < 1 && !this.hasFocus){
  22446. this.setRawValue(this.emptyText);
  22447. this.el.addClass(this.emptyClass);
  22448. }
  22449. },
  22450. // private
  22451. preFocus : function(){
  22452. if(this.emptyText){
  22453. if(this.el.dom.value == this.emptyText){
  22454. this.setRawValue('');
  22455. }
  22456. this.el.removeClass(this.emptyClass);
  22457. }
  22458. if(this.selectOnFocus){
  22459. this.el.dom.select();
  22460. }
  22461. },
  22462. // private
  22463. postBlur : function(){
  22464. this.applyEmptyText();
  22465. },
  22466. // private
  22467. filterKeys : function(e){
  22468. if(e.ctrlKey){
  22469. return;
  22470. }
  22471. var k = e.getKey();
  22472. if(Ext.isGecko && (e.isNavKeyPress() || k == e.BACKSPACE || (k == e.DELETE && e.button == -1))){
  22473. return;
  22474. }
  22475. var c = e.getCharCode(), cc = String.fromCharCode(c);
  22476. if(!Ext.isGecko && e.isSpecialKey() && !cc){
  22477. return;
  22478. }
  22479. if(!this.maskRe.test(cc)){
  22480. e.stopEvent();
  22481. }
  22482. },
  22483. setValue : function(v){
  22484. if(this.emptyText && this.el && v !== undefined && v !== null && v !== ''){
  22485. this.el.removeClass(this.emptyClass);
  22486. }
  22487. Ext.form.TextField.superclass.setValue.apply(this, arguments);
  22488. this.applyEmptyText();
  22489. this.autoSize();
  22490. },
  22491. validateValue : function(value){
  22492. if(value.length < 1 || value === this.emptyText){ // if it's blank
  22493. if(this.allowBlank){
  22494. this.clearInvalid();
  22495. return true;
  22496. }else{
  22497. this.markInvalid(this.blankText);
  22498. return false;
  22499. }
  22500. }
  22501. if(value.length < this.minLength){
  22502. this.markInvalid(String.format(this.minLengthText, this.minLength));
  22503. return false;
  22504. }
  22505. if(value.length > this.maxLength){
  22506. this.markInvalid(String.format(this.maxLengthText, this.maxLength));
  22507. return false;
  22508. }
  22509. if(this.vtype){
  22510. var vt = Ext.form.VTypes;
  22511. if(!vt[this.vtype](value, this)){
  22512. this.markInvalid(this.vtypeText || vt[this.vtype +'Text']);
  22513. return false;
  22514. }
  22515. }
  22516. if(typeof this.validator == "function"){
  22517. var msg = this.validator(value);
  22518. if(msg !== true){
  22519. this.markInvalid(msg);
  22520. return false;
  22521. }
  22522. }
  22523. if(this.regex && !this.regex.test(value)){
  22524. this.markInvalid(this.regexText);
  22525. return false;
  22526. }
  22527. return true;
  22528. },
  22529. selectText : function(start, end){
  22530. var v = this.getRawValue();
  22531. var doFocus = false;
  22532. if(v.length > 0){
  22533. start = start === undefined ? 0 : start;
  22534. end = end === undefined ? v.length : end;
  22535. var d = this.el.dom;
  22536. if(d.setSelectionRange){
  22537. d.setSelectionRange(start, end);
  22538. }else if(d.createTextRange){
  22539. var range = d.createTextRange();
  22540. range.moveStart("character", start);
  22541. range.moveEnd("character", end-v.length);
  22542. range.select();
  22543. }
  22544. doFocus = Ext.isGecko || Ext.isOpera;
  22545. }else{
  22546. doFocus = true;
  22547. }
  22548. if(doFocus){
  22549. this.focus();
  22550. }
  22551. },
  22552. autoSize : function(){
  22553. if(!this.grow || !this.rendered){
  22554. return;
  22555. }
  22556. if(!this.metrics){
  22557. this.metrics = Ext.util.TextMetrics.createInstance(this.el);
  22558. }
  22559. var el = this.el;
  22560. var v = el.dom.value;
  22561. var d = document.createElement('div');
  22562. d.appendChild(document.createTextNode(v));
  22563. v = d.innerHTML;
  22564. Ext.removeNode(d);
  22565. d = null;
  22566. v += "&#160;";
  22567. var w = Math.min(this.growMax, Math.max(this.metrics.getWidth(v) + 10, this.growMin));
  22568. this.el.setWidth(w);
  22569. this.fireEvent("autosize", this, w);
  22570. }
  22571. });
  22572. Ext.reg('textfield', Ext.form.TextField);
  22573. Ext.form.TriggerField = Ext.extend(Ext.form.TextField, {
  22574. defaultAutoCreate : {tag: "input", type: "text", size: "16", autocomplete: "off"},
  22575. hideTrigger:false,
  22576. autoSize: Ext.emptyFn,
  22577. // private
  22578. monitorTab : true,
  22579. // private
  22580. deferHeight : true,
  22581. // private
  22582. mimicing : false,
  22583. // private
  22584. onResize : function(w, h){
  22585. Ext.form.TriggerField.superclass.onResize.call(this, w, h);
  22586. if(typeof w == 'number'){
  22587. this.el.setWidth(this.adjustWidth('input', w - this.trigger.getWidth()));
  22588. }
  22589. this.wrap.setWidth(this.el.getWidth()+this.trigger.getWidth());
  22590. },
  22591. // private
  22592. adjustSize : Ext.BoxComponent.prototype.adjustSize,
  22593. // private
  22594. getResizeEl : function(){
  22595. return this.wrap;
  22596. },
  22597. // private
  22598. getPositionEl : function(){
  22599. return this.wrap;
  22600. },
  22601. // private
  22602. alignErrorIcon : function(){
  22603. if(this.wrap){
  22604. this.errorIcon.alignTo(this.wrap, 'tl-tr', [2, 0]);
  22605. }
  22606. },
  22607. // private
  22608. onRender : function(ct, position){
  22609. Ext.form.TriggerField.superclass.onRender.call(this, ct, position);
  22610. this.wrap = this.el.wrap({cls: "x-form-field-wrap"});
  22611. this.trigger = this.wrap.createChild(this.triggerConfig ||
  22612. {tag: "img", src: Ext.BLANK_IMAGE_URL, cls: "x-form-trigger " + this.triggerClass});
  22613. if(this.hideTrigger){
  22614. this.trigger.setDisplayed(false);
  22615. }
  22616. this.initTrigger();
  22617. if(!this.width){
  22618. this.wrap.setWidth(this.el.getWidth()+this.trigger.getWidth());
  22619. }
  22620. },
  22621. afterRender : function(){
  22622. Ext.form.TriggerField.superclass.afterRender.call(this);
  22623. var y;
  22624. if(Ext.isIE && !this.hideTrigger && this.el.getY() != (y = this.trigger.getY())){
  22625. this.el.position();
  22626. this.el.setY(y);
  22627. }
  22628. },
  22629. // private
  22630. initTrigger : function(){
  22631. this.trigger.on("click", this.onTriggerClick, this, {preventDefault:true});
  22632. this.trigger.addClassOnOver('x-form-trigger-over');
  22633. this.trigger.addClassOnClick('x-form-trigger-click');
  22634. },
  22635. // private
  22636. onDestroy : function(){
  22637. if(this.trigger){
  22638. this.trigger.removeAllListeners();
  22639. this.trigger.remove();
  22640. }
  22641. if(this.wrap){
  22642. this.wrap.remove();
  22643. }
  22644. Ext.form.TriggerField.superclass.onDestroy.call(this);
  22645. },
  22646. // private
  22647. onFocus : function(){
  22648. Ext.form.TriggerField.superclass.onFocus.call(this);
  22649. if(!this.mimicing){
  22650. this.wrap.addClass('x-trigger-wrap-focus');
  22651. this.mimicing = true;
  22652. Ext.get(Ext.isIE ? document.body : document).on("mousedown", this.mimicBlur, this, {delay: 10});
  22653. if(this.monitorTab){
  22654. this.el.on("keydown", this.checkTab, this);
  22655. }
  22656. }
  22657. },
  22658. // private
  22659. checkTab : function(e){
  22660. if(e.getKey() == e.TAB){
  22661. this.triggerBlur();
  22662. }
  22663. },
  22664. // private
  22665. onBlur : function(){
  22666. // do nothing
  22667. },
  22668. // private
  22669. mimicBlur : function(e){
  22670. if(!this.wrap.contains(e.target) && this.validateBlur(e)){
  22671. this.triggerBlur();
  22672. }
  22673. },
  22674. // private
  22675. triggerBlur : function(){
  22676. this.mimicing = false;
  22677. Ext.get(Ext.isIE ? document.body : document).un("mousedown", this.mimicBlur, this);
  22678. if(this.monitorTab && this.el){
  22679. this.el.un("keydown", this.checkTab, this);
  22680. }
  22681. this.beforeBlur();
  22682. if(this.wrap){
  22683. this.wrap.removeClass('x-trigger-wrap-focus');
  22684. }
  22685. Ext.form.TriggerField.superclass.onBlur.call(this);
  22686. },
  22687. beforeBlur : Ext.emptyFn,
  22688. // private
  22689. // This should be overriden by any subclass that needs to check whether or not the field can be blurred.
  22690. validateBlur : function(e){
  22691. return true;
  22692. },
  22693. // private
  22694. onDisable : function(){
  22695. Ext.form.TriggerField.superclass.onDisable.call(this);
  22696. if(this.wrap){
  22697. this.wrap.addClass(this.disabledClass);
  22698. this.el.removeClass(this.disabledClass);
  22699. }
  22700. },
  22701. // private
  22702. onEnable : function(){
  22703. Ext.form.TriggerField.superclass.onEnable.call(this);
  22704. if(this.wrap){
  22705. this.wrap.removeClass(this.disabledClass);
  22706. }
  22707. },
  22708. // private
  22709. onShow : function(){
  22710. if(this.wrap){
  22711. this.wrap.dom.style.display = '';
  22712. this.wrap.dom.style.visibility = 'visible';
  22713. }
  22714. },
  22715. // private
  22716. onHide : function(){
  22717. this.wrap.dom.style.display = 'none';
  22718. },
  22719. onTriggerClick : Ext.emptyFn
  22720. });
  22721. // TwinTriggerField is not a public class to be used directly. It is meant as an abstract base class
  22722. // to be extended by an implementing class. For an example of implementing this class, see the custom
  22723. // SearchField implementation here: http://extjs.com/deploy/ext/examples/form/custom.html
  22724. Ext.form.TwinTriggerField = Ext.extend(Ext.form.TriggerField, {
  22725. initComponent : function(){
  22726. Ext.form.TwinTriggerField.superclass.initComponent.call(this);
  22727. this.triggerConfig = {
  22728. tag:'span', cls:'x-form-twin-triggers', cn:[
  22729. {tag: "img", src: Ext.BLANK_IMAGE_URL, cls: "x-form-trigger " + this.trigger1Class},
  22730. {tag: "img", src: Ext.BLANK_IMAGE_URL, cls: "x-form-trigger " + this.trigger2Class}
  22731. ]};
  22732. },
  22733. getTrigger : function(index){
  22734. return this.triggers[index];
  22735. },
  22736. initTrigger : function(){
  22737. var ts = this.trigger.select('.x-form-trigger', true);
  22738. this.wrap.setStyle('overflow', 'hidden');
  22739. var triggerField = this;
  22740. ts.each(function(t, all, index){
  22741. t.hide = function(){
  22742. var w = triggerField.wrap.getWidth();
  22743. this.dom.style.display = 'none';
  22744. triggerField.el.setWidth(w-triggerField.trigger.getWidth());
  22745. };
  22746. t.show = function(){
  22747. var w = triggerField.wrap.getWidth();
  22748. this.dom.style.display = '';
  22749. triggerField.el.setWidth(w-triggerField.trigger.getWidth());
  22750. };
  22751. var triggerIndex = 'Trigger'+(index+1);
  22752. if(this['hide'+triggerIndex]){
  22753. t.dom.style.display = 'none';
  22754. }
  22755. t.on("click", this['on'+triggerIndex+'Click'], this, {preventDefault:true});
  22756. t.addClassOnOver('x-form-trigger-over');
  22757. t.addClassOnClick('x-form-trigger-click');
  22758. }, this);
  22759. this.triggers = ts.elements;
  22760. },
  22761. onTrigger1Click : Ext.emptyFn,
  22762. onTrigger2Click : Ext.emptyFn
  22763. });
  22764. Ext.reg('trigger', Ext.form.TriggerField);
  22765. Ext.form.TextArea = Ext.extend(Ext.form.TextField, {
  22766. growMin : 60,
  22767. growMax: 1000,
  22768. growAppend : '&#160;\n&#160;',
  22769. growPad : 0,
  22770. enterIsSpecial : false,
  22771. preventScrollbars: false,
  22772. // private
  22773. onRender : function(ct, position){
  22774. if(!this.el){
  22775. this.defaultAutoCreate = {
  22776. tag: "textarea",
  22777. style:"width:100px;height:60px;",
  22778. autocomplete: "off"
  22779. };
  22780. }
  22781. Ext.form.TextArea.superclass.onRender.call(this, ct, position);
  22782. if(this.grow){
  22783. this.textSizeEl = Ext.DomHelper.append(document.body, {
  22784. tag: "pre", cls: "x-form-grow-sizer"
  22785. });
  22786. if(this.preventScrollbars){
  22787. this.el.setStyle("overflow", "hidden");
  22788. }
  22789. this.el.setHeight(this.growMin);
  22790. }
  22791. },
  22792. onDestroy : function(){
  22793. if(this.textSizeEl){
  22794. Ext.removeNode(this.textSizeEl);
  22795. }
  22796. Ext.form.TextArea.superclass.onDestroy.call(this);
  22797. },
  22798. fireKey : function(e){
  22799. if(e.isSpecialKey() && (this.enterIsSpecial || (e.getKey() != e.ENTER || e.hasModifier()))){
  22800. this.fireEvent("specialkey", this, e);
  22801. }
  22802. },
  22803. // private
  22804. onKeyUp : function(e){
  22805. if(!e.isNavKeyPress() || e.getKey() == e.ENTER){
  22806. this.autoSize();
  22807. }
  22808. Ext.form.TextArea.superclass.onKeyUp.call(this, e);
  22809. },
  22810. autoSize : function(){
  22811. if(!this.grow || !this.textSizeEl){
  22812. return;
  22813. }
  22814. var el = this.el;
  22815. var v = el.dom.value;
  22816. var ts = this.textSizeEl;
  22817. ts.innerHTML = '';
  22818. ts.appendChild(document.createTextNode(v));
  22819. v = ts.innerHTML;
  22820. Ext.fly(ts).setWidth(this.el.getWidth());
  22821. if(v.length < 1){
  22822. v = "&#160;&#160;";
  22823. }else{
  22824. if(Ext.isIE){
  22825. v = v.replace(/\n/g, '<p>&#160;</p>');
  22826. }
  22827. v += this.growAppend;
  22828. }
  22829. ts.innerHTML = v;
  22830. var h = Math.min(this.growMax, Math.max(ts.offsetHeight, this.growMin)+this.growPad);
  22831. if(h != this.lastHeight){
  22832. this.lastHeight = h;
  22833. this.el.setHeight(h);
  22834. this.fireEvent("autosize", this, h);
  22835. }
  22836. }
  22837. });
  22838. Ext.reg('textarea', Ext.form.TextArea);
  22839. Ext.form.NumberField = Ext.extend(Ext.form.TextField, {
  22840. fieldClass: "x-form-field x-form-num-field",
  22841. allowDecimals : true,
  22842. decimalSeparator : ".",
  22843. decimalPrecision : 2,
  22844. allowNegative : true,
  22845. minValue : Number.NEGATIVE_INFINITY,
  22846. maxValue : Number.MAX_VALUE,
  22847. minText : "The minimum value for this field is {0}",
  22848. maxText : "The maximum value for this field is {0}",
  22849. nanText : "{0} is not a valid number",
  22850. baseChars : "0123456789",
  22851. // private
  22852. initEvents : function(){
  22853. Ext.form.NumberField.superclass.initEvents.call(this);
  22854. var allowed = this.baseChars+'';
  22855. if(this.allowDecimals){
  22856. allowed += this.decimalSeparator;
  22857. }
  22858. if(this.allowNegative){
  22859. allowed += "-";
  22860. }
  22861. this.stripCharsRe = new RegExp('[^'+allowed+']', 'gi');
  22862. var keyPress = function(e){
  22863. var k = e.getKey();
  22864. if(!Ext.isIE && (e.isSpecialKey() || k == e.BACKSPACE || k == e.DELETE)){
  22865. return;
  22866. }
  22867. var c = e.getCharCode();
  22868. if(allowed.indexOf(String.fromCharCode(c)) === -1){
  22869. e.stopEvent();
  22870. }
  22871. };
  22872. this.el.on("keypress", keyPress, this);
  22873. },
  22874. // private
  22875. validateValue : function(value){
  22876. if(!Ext.form.NumberField.superclass.validateValue.call(this, value)){
  22877. return false;
  22878. }
  22879. if(value.length < 1){ // if it's blank and textfield didn't flag it then it's valid
  22880. return true;
  22881. }
  22882. value = String(value).replace(this.decimalSeparator, ".");
  22883. if(isNaN(value)){
  22884. this.markInvalid(String.format(this.nanText, value));
  22885. return false;
  22886. }
  22887. var num = this.parseValue(value);
  22888. if(num < this.minValue){
  22889. this.markInvalid(String.format(this.minText, this.minValue));
  22890. return false;
  22891. }
  22892. if(num > this.maxValue){
  22893. this.markInvalid(String.format(this.maxText, this.maxValue));
  22894. return false;
  22895. }
  22896. return true;
  22897. },
  22898. getValue : function(){
  22899. return this.fixPrecision(this.parseValue(Ext.form.NumberField.superclass.getValue.call(this)));
  22900. },
  22901. setValue : function(v){
  22902. v = typeof v == 'number' ? v : parseFloat(String(v).replace(this.decimalSeparator, "."));
  22903. v = isNaN(v) ? '' : String(v).replace(".", this.decimalSeparator);
  22904. Ext.form.NumberField.superclass.setValue.call(this, v);
  22905. },
  22906. // private
  22907. parseValue : function(value){
  22908. value = parseFloat(String(value).replace(this.decimalSeparator, "."));
  22909. return isNaN(value) ? '' : value;
  22910. },
  22911. // private
  22912. fixPrecision : function(value){
  22913. var nan = isNaN(value);
  22914. if(!this.allowDecimals || this.decimalPrecision == -1 || nan || !value){
  22915. return nan ? '' : value;
  22916. }
  22917. return parseFloat(parseFloat(value).toFixed(this.decimalPrecision));
  22918. },
  22919. beforeBlur : function(){
  22920. var v = this.parseValue(this.getRawValue());
  22921. if(v || v === 0){
  22922. this.setValue(this.fixPrecision(v));
  22923. }
  22924. }
  22925. });
  22926. Ext.reg('numberfield', Ext.form.NumberField);
  22927. Ext.form.DateField = Ext.extend(Ext.form.TriggerField, {
  22928. format : "m/d/Y",
  22929. altFormats : "m/d/Y|n/j/Y|n/j/y|m/j/y|n/d/y|m/j/Y|n/d/Y|m-d-y|m-d-Y|m/d|m-d|md|mdy|mdY|d|Y-m-d",
  22930. disabledDaysText : "Disabled",
  22931. disabledDatesText : "Disabled",
  22932. minText : "The date in this field must be equal to or after {0}",
  22933. maxText : "The date in this field must be equal to or before {0}",
  22934. invalidText : "{0} is not a valid date - it must be in the format {1}",
  22935. triggerClass : 'x-form-date-trigger',
  22936. showToday : true,
  22937. // private
  22938. defaultAutoCreate : {tag: "input", type: "text", size: "10", autocomplete: "off"},
  22939. initComponent : function(){
  22940. Ext.form.DateField.superclass.initComponent.call(this);
  22941. this.addEvents(
  22942. 'select'
  22943. );
  22944. if(typeof this.minValue == "string"){
  22945. this.minValue = this.parseDate(this.minValue);
  22946. }
  22947. if(typeof this.maxValue == "string"){
  22948. this.maxValue = this.parseDate(this.maxValue);
  22949. }
  22950. this.disabledDatesRE = null;
  22951. this.initDisabledDays();
  22952. },
  22953. // private
  22954. initDisabledDays : function(){
  22955. if(this.disabledDates){
  22956. var dd = this.disabledDates;
  22957. var re = "(?:";
  22958. for(var i = 0; i < dd.length; i++){
  22959. re += dd[i];
  22960. if(i != dd.length-1) re += "|";
  22961. }
  22962. this.disabledDatesRE = new RegExp(re + ")");
  22963. }
  22964. },
  22965. setDisabledDates : function(dd){
  22966. this.disabledDates = dd;
  22967. this.initDisabledDays();
  22968. if(this.menu){
  22969. this.menu.picker.setDisabledDates(this.disabledDatesRE);
  22970. }
  22971. },
  22972. setDisabledDays : function(dd){
  22973. this.disabledDays = dd;
  22974. if(this.menu){
  22975. this.menu.picker.setDisabledDays(dd);
  22976. }
  22977. },
  22978. setMinValue : function(dt){
  22979. this.minValue = (typeof dt == "string" ? this.parseDate(dt) : dt);
  22980. if(this.menu){
  22981. this.menu.picker.setMinDate(this.minValue);
  22982. }
  22983. },
  22984. setMaxValue : function(dt){
  22985. this.maxValue = (typeof dt == "string" ? this.parseDate(dt) : dt);
  22986. if(this.menu){
  22987. this.menu.picker.setMaxDate(this.maxValue);
  22988. }
  22989. },
  22990. // private
  22991. validateValue : function(value){
  22992. value = this.formatDate(value);
  22993. if(!Ext.form.DateField.superclass.validateValue.call(this, value)){
  22994. return false;
  22995. }
  22996. if(value.length < 1){ // if it's blank and textfield didn't flag it then it's valid
  22997. return true;
  22998. }
  22999. var svalue = value;
  23000. value = this.parseDate(value);
  23001. if(!value){
  23002. this.markInvalid(String.format(this.invalidText, svalue, this.format));
  23003. return false;
  23004. }
  23005. var time = value.getTime();
  23006. if(this.minValue && time < this.minValue.getTime()){
  23007. this.markInvalid(String.format(this.minText, this.formatDate(this.minValue)));
  23008. return false;
  23009. }
  23010. if(this.maxValue && time > this.maxValue.getTime()){
  23011. this.markInvalid(String.format(this.maxText, this.formatDate(this.maxValue)));
  23012. return false;
  23013. }
  23014. if(this.disabledDays){
  23015. var day = value.getDay();
  23016. for(var i = 0; i < this.disabledDays.length; i++) {
  23017. if(day === this.disabledDays[i]){
  23018. this.markInvalid(this.disabledDaysText);
  23019. return false;
  23020. }
  23021. }
  23022. }
  23023. var fvalue = this.formatDate(value);
  23024. if(this.disabledDatesRE && this.disabledDatesRE.test(fvalue)){
  23025. this.markInvalid(String.format(this.disabledDatesText, fvalue));
  23026. return false;
  23027. }
  23028. return true;
  23029. },
  23030. // private
  23031. // Provides logic to override the default TriggerField.validateBlur which just returns true
  23032. validateBlur : function(){
  23033. return !this.menu || !this.menu.isVisible();
  23034. },
  23035. getValue : function(){
  23036. return this.parseDate(Ext.form.DateField.superclass.getValue.call(this)) || "";
  23037. },
  23038. setValue : function(date){
  23039. Ext.form.DateField.superclass.setValue.call(this, this.formatDate(this.parseDate(date)));
  23040. },
  23041. // private
  23042. parseDate : function(value){
  23043. if(!value || Ext.isDate(value)){
  23044. return value;
  23045. }
  23046. var v = Date.parseDate(value, this.format);
  23047. if(!v && this.altFormats){
  23048. if(!this.altFormatsArray){
  23049. this.altFormatsArray = this.altFormats.split("|");
  23050. }
  23051. for(var i = 0, len = this.altFormatsArray.length; i < len && !v; i++){
  23052. v = Date.parseDate(value, this.altFormatsArray[i]);
  23053. }
  23054. }
  23055. return v;
  23056. },
  23057. // private
  23058. onDestroy : function(){
  23059. if(this.menu) {
  23060. this.menu.destroy();
  23061. }
  23062. if(this.wrap){
  23063. this.wrap.remove();
  23064. }
  23065. Ext.form.DateField.superclass.onDestroy.call(this);
  23066. },
  23067. // private
  23068. formatDate : function(date){
  23069. return Ext.isDate(date) ? date.dateFormat(this.format) : date;
  23070. },
  23071. // private
  23072. menuListeners : {
  23073. select: function(m, d){
  23074. this.setValue(d);
  23075. this.fireEvent('select', this, d);
  23076. },
  23077. show : function(){ // retain focus styling
  23078. this.onFocus();
  23079. },
  23080. hide : function(){
  23081. this.focus.defer(10, this);
  23082. var ml = this.menuListeners;
  23083. this.menu.un("select", ml.select, this);
  23084. this.menu.un("show", ml.show, this);
  23085. this.menu.un("hide", ml.hide, this);
  23086. }
  23087. },
  23088. // private
  23089. // Implements the default empty TriggerField.onTriggerClick function to display the DatePicker
  23090. onTriggerClick : function(){
  23091. if(this.disabled){
  23092. return;
  23093. }
  23094. if(this.menu == null){
  23095. this.menu = new Ext.menu.DateMenu();
  23096. }
  23097. Ext.apply(this.menu.picker, {
  23098. minDate : this.minValue,
  23099. maxDate : this.maxValue,
  23100. disabledDatesRE : this.disabledDatesRE,
  23101. disabledDatesText : this.disabledDatesText,
  23102. disabledDays : this.disabledDays,
  23103. disabledDaysText : this.disabledDaysText,
  23104. format : this.format,
  23105. showToday : this.showToday,
  23106. minText : String.format(this.minText, this.formatDate(this.minValue)),
  23107. maxText : String.format(this.maxText, this.formatDate(this.maxValue))
  23108. });
  23109. this.menu.on(Ext.apply({}, this.menuListeners, {
  23110. scope:this
  23111. }));
  23112. this.menu.picker.setValue(this.getValue() || new Date());
  23113. this.menu.show(this.el, "tl-bl?");
  23114. },
  23115. // private
  23116. beforeBlur : function(){
  23117. var v = this.parseDate(this.getRawValue());
  23118. if(v){
  23119. this.setValue(v);
  23120. }
  23121. }
  23122. });
  23123. Ext.reg('datefield', Ext.form.DateField);
  23124. Ext.form.ComboBox = Ext.extend(Ext.form.TriggerField, {
  23125. // private
  23126. defaultAutoCreate : {tag: "input", type: "text", size: "24", autocomplete: "off"},
  23127. listClass: '',
  23128. selectedClass: 'x-combo-selected',
  23129. triggerClass : 'x-form-arrow-trigger',
  23130. shadow:'sides',
  23131. listAlign: 'tl-bl?',
  23132. maxHeight: 300,
  23133. minHeight: 90,
  23134. triggerAction: 'query',
  23135. minChars : 4,
  23136. typeAhead: false,
  23137. queryDelay: 500,
  23138. pageSize: 0,
  23139. selectOnFocus:false,
  23140. queryParam: 'query',
  23141. loadingText: 'Loading...',
  23142. resizable: false,
  23143. handleHeight : 8,
  23144. editable: true,
  23145. allQuery: '',
  23146. mode: 'remote',
  23147. minListWidth : 70,
  23148. forceSelection:false,
  23149. typeAheadDelay : 250,
  23150. lazyInit : true,
  23151. // private
  23152. initComponent : function(){
  23153. Ext.form.ComboBox.superclass.initComponent.call(this);
  23154. this.addEvents(
  23155. 'expand',
  23156. 'collapse',
  23157. 'beforeselect',
  23158. 'select',
  23159. 'beforequery'
  23160. );
  23161. if(this.transform){
  23162. this.allowDomMove = false;
  23163. var s = Ext.getDom(this.transform);
  23164. if(!this.hiddenName){
  23165. this.hiddenName = s.name;
  23166. }
  23167. if(!this.store){
  23168. this.mode = 'local';
  23169. var d = [], opts = s.options;
  23170. for(var i = 0, len = opts.length;i < len; i++){
  23171. var o = opts[i];
  23172. var value = (Ext.isIE ? o.getAttributeNode('value').specified : o.hasAttribute('value')) ? o.value : o.text;
  23173. if(o.selected) {
  23174. this.value = value;
  23175. }
  23176. d.push([value, o.text]);
  23177. }
  23178. this.store = new Ext.data.SimpleStore({
  23179. 'id': 0,
  23180. fields: ['value', 'text'],
  23181. data : d
  23182. });
  23183. this.valueField = 'value';
  23184. this.displayField = 'text';
  23185. }
  23186. s.name = Ext.id(); // wipe out the name in case somewhere else they have a reference
  23187. if(!this.lazyRender){
  23188. this.target = true;
  23189. this.el = Ext.DomHelper.insertBefore(s, this.autoCreate || this.defaultAutoCreate);
  23190. Ext.removeNode(s); // remove it
  23191. this.render(this.el.parentNode);
  23192. }else{
  23193. Ext.removeNode(s); // remove it
  23194. }
  23195. }
  23196. //auto-configure store from local array data
  23197. else if(Ext.isArray(this.store)){
  23198. if (Ext.isArray(this.store[0])){
  23199. this.store = new Ext.data.SimpleStore({
  23200. fields: ['value','text'],
  23201. data: this.store
  23202. });
  23203. this.valueField = 'value';
  23204. }else{
  23205. this.store = new Ext.data.SimpleStore({
  23206. fields: ['text'],
  23207. data: this.store,
  23208. expandData: true
  23209. });
  23210. this.valueField = 'text';
  23211. }
  23212. this.displayField = 'text';
  23213. this.mode = 'local';
  23214. }
  23215. this.selectedIndex = -1;
  23216. if(this.mode == 'local'){
  23217. if(this.initialConfig.queryDelay === undefined){
  23218. this.queryDelay = 10;
  23219. }
  23220. if(this.initialConfig.minChars === undefined){
  23221. this.minChars = 0;
  23222. }
  23223. }
  23224. },
  23225. // private
  23226. onRender : function(ct, position){
  23227. Ext.form.ComboBox.superclass.onRender.call(this, ct, position);
  23228. if(this.hiddenName){
  23229. this.hiddenField = this.el.insertSibling({tag:'input', type:'hidden', name: this.hiddenName,
  23230. id: (this.hiddenId||this.hiddenName)}, 'before', true);
  23231. // prevent input submission
  23232. this.el.dom.removeAttribute('name');
  23233. }
  23234. if(Ext.isGecko){
  23235. this.el.dom.setAttribute('autocomplete', 'off');
  23236. }
  23237. if(!this.lazyInit){
  23238. this.initList();
  23239. }else{
  23240. this.on('focus', this.initList, this, {single: true});
  23241. }
  23242. if(!this.editable){
  23243. this.editable = true;
  23244. this.setEditable(false);
  23245. }
  23246. },
  23247. // private
  23248. initValue : function(){
  23249. Ext.form.ComboBox.superclass.initValue.call(this);
  23250. if(this.hiddenField){
  23251. this.hiddenField.value =
  23252. this.hiddenValue !== undefined ? this.hiddenValue :
  23253. this.value !== undefined ? this.value : '';
  23254. }
  23255. },
  23256. // private
  23257. initList : function(){
  23258. if(!this.list){
  23259. var cls = 'x-combo-list';
  23260. this.list = new Ext.Layer({
  23261. shadow: this.shadow, cls: [cls, this.listClass].join(' '), constrain:false
  23262. });
  23263. var lw = this.listWidth || Math.max(this.wrap.getWidth(), this.minListWidth);
  23264. this.list.setWidth(lw);
  23265. this.list.swallowEvent('mousewheel');
  23266. this.assetHeight = 0;
  23267. if(this.title){
  23268. this.header = this.list.createChild({cls:cls+'-hd', html: this.title});
  23269. this.assetHeight += this.header.getHeight();
  23270. }
  23271. this.innerList = this.list.createChild({cls:cls+'-inner'});
  23272. this.innerList.on('mouseover', this.onViewOver, this);
  23273. this.innerList.on('mousemove', this.onViewMove, this);
  23274. this.innerList.setWidth(lw - this.list.getFrameWidth('lr'));
  23275. if(this.pageSize){
  23276. this.footer = this.list.createChild({cls:cls+'-ft'});
  23277. this.pageTb = new Ext.PagingToolbar({
  23278. store:this.store,
  23279. pageSize: this.pageSize,
  23280. renderTo:this.footer
  23281. });
  23282. this.assetHeight += this.footer.getHeight();
  23283. }
  23284. if(!this.tpl){
  23285. this.tpl = '<tpl for="."><div class="'+cls+'-item">{' + this.displayField + '}</div></tpl>';
  23286. }
  23287. this.view = new Ext.DataView({
  23288. applyTo: this.innerList,
  23289. tpl: this.tpl,
  23290. singleSelect: true,
  23291. selectedClass: this.selectedClass,
  23292. itemSelector: this.itemSelector || '.' + cls + '-item'
  23293. });
  23294. this.view.on('click', this.onViewClick, this);
  23295. this.bindStore(this.store, true);
  23296. if(this.resizable){
  23297. this.resizer = new Ext.Resizable(this.list, {
  23298. pinned:true, handles:'se'
  23299. });
  23300. this.resizer.on('resize', function(r, w, h){
  23301. this.maxHeight = h-this.handleHeight-this.list.getFrameWidth('tb')-this.assetHeight;
  23302. this.listWidth = w;
  23303. this.innerList.setWidth(w - this.list.getFrameWidth('lr'));
  23304. this.restrictHeight();
  23305. }, this);
  23306. this[this.pageSize?'footer':'innerList'].setStyle('margin-bottom', this.handleHeight+'px');
  23307. }
  23308. }
  23309. },
  23310. getStore : function(){
  23311. return this.store;
  23312. },
  23313. // private
  23314. bindStore : function(store, initial){
  23315. if(this.store && !initial){
  23316. this.store.un('beforeload', this.onBeforeLoad, this);
  23317. this.store.un('load', this.onLoad, this);
  23318. this.store.un('loadexception', this.collapse, this);
  23319. if(!store){
  23320. this.store = null;
  23321. if(this.view){
  23322. this.view.setStore(null);
  23323. }
  23324. }
  23325. }
  23326. if(store){
  23327. this.store = Ext.StoreMgr.lookup(store);
  23328. this.store.on('beforeload', this.onBeforeLoad, this);
  23329. this.store.on('load', this.onLoad, this);
  23330. this.store.on('loadexception', this.collapse, this);
  23331. if(this.view){
  23332. this.view.setStore(store);
  23333. }
  23334. }
  23335. },
  23336. // private
  23337. initEvents : function(){
  23338. Ext.form.ComboBox.superclass.initEvents.call(this);
  23339. this.keyNav = new Ext.KeyNav(this.el, {
  23340. "up" : function(e){
  23341. this.inKeyMode = true;
  23342. this.selectPrev();
  23343. },
  23344. "down" : function(e){
  23345. if(!this.isExpanded()){
  23346. this.onTriggerClick();
  23347. }else{
  23348. this.inKeyMode = true;
  23349. this.selectNext();
  23350. }
  23351. },
  23352. "enter" : function(e){
  23353. this.onViewClick();
  23354. this.delayedCheck = true;
  23355. this.unsetDelayCheck.defer(10, this);
  23356. },
  23357. "esc" : function(e){
  23358. this.collapse();
  23359. },
  23360. "tab" : function(e){
  23361. this.onViewClick(false);
  23362. return true;
  23363. },
  23364. scope : this,
  23365. doRelay : function(foo, bar, hname){
  23366. if(hname == 'down' || this.scope.isExpanded()){
  23367. return Ext.KeyNav.prototype.doRelay.apply(this, arguments);
  23368. }
  23369. return true;
  23370. },
  23371. forceKeyDown : true
  23372. });
  23373. this.queryDelay = Math.max(this.queryDelay || 10,
  23374. this.mode == 'local' ? 10 : 250);
  23375. this.dqTask = new Ext.util.DelayedTask(this.initQuery, this);
  23376. if(this.typeAhead){
  23377. this.taTask = new Ext.util.DelayedTask(this.onTypeAhead, this);
  23378. }
  23379. if(this.editable !== false){
  23380. this.el.on("keyup", this.onKeyUp, this);
  23381. }
  23382. if(this.forceSelection){
  23383. this.on('blur', this.doForce, this);
  23384. }
  23385. },
  23386. // private
  23387. onDestroy : function(){
  23388. if(this.view){
  23389. Ext.destroy(this.view);
  23390. }
  23391. if(this.list){
  23392. if(this.innerList){
  23393. this.innerList.un('mouseover', this.onViewOver, this);
  23394. this.innerList.un('mousemove', this.onViewMove, this);
  23395. }
  23396. this.list.destroy();
  23397. }
  23398. if (this.dqTask){
  23399. this.dqTask.cancel();
  23400. this.dqTask = null;
  23401. }
  23402. this.bindStore(null);
  23403. Ext.form.ComboBox.superclass.onDestroy.call(this);
  23404. },
  23405. // private
  23406. unsetDelayCheck : function(){
  23407. delete this.delayedCheck;
  23408. },
  23409. // private
  23410. fireKey : function(e){
  23411. if(e.isNavKeyPress() && !this.isExpanded() && !this.delayedCheck){
  23412. this.fireEvent("specialkey", this, e);
  23413. }
  23414. },
  23415. // private
  23416. onResize: function(w, h){
  23417. Ext.form.ComboBox.superclass.onResize.apply(this, arguments);
  23418. if(this.list && this.listWidth === undefined){
  23419. var lw = Math.max(w, this.minListWidth);
  23420. this.list.setWidth(lw);
  23421. this.innerList.setWidth(lw - this.list.getFrameWidth('lr'));
  23422. }
  23423. },
  23424. // private
  23425. onEnable: function(){
  23426. Ext.form.ComboBox.superclass.onEnable.apply(this, arguments);
  23427. if(this.hiddenField){
  23428. this.hiddenField.disabled = false;
  23429. }
  23430. },
  23431. // private
  23432. onDisable: function(){
  23433. Ext.form.ComboBox.superclass.onDisable.apply(this, arguments);
  23434. if(this.hiddenField){
  23435. this.hiddenField.disabled = true;
  23436. }
  23437. },
  23438. setEditable : function(value){
  23439. if(value == this.editable){
  23440. return;
  23441. }
  23442. this.editable = value;
  23443. if(!value){
  23444. this.el.dom.setAttribute('readOnly', true);
  23445. this.el.on('mousedown', this.onTriggerClick, this);
  23446. this.el.addClass('x-combo-noedit');
  23447. }else{
  23448. this.el.dom.removeAttribute('readOnly');
  23449. this.el.un('mousedown', this.onTriggerClick, this);
  23450. this.el.removeClass('x-combo-noedit');
  23451. }
  23452. },
  23453. // private
  23454. onBeforeLoad : function(){
  23455. if(!this.hasFocus){
  23456. return;
  23457. }
  23458. this.innerList.update(this.loadingText ?
  23459. '<div class="loading-indicator">'+this.loadingText+'</div>' : '');
  23460. this.restrictHeight();
  23461. this.selectedIndex = -1;
  23462. },
  23463. // private
  23464. onLoad : function(){
  23465. if(!this.hasFocus){
  23466. return;
  23467. }
  23468. if(this.store.getCount() > 0){
  23469. this.expand();
  23470. this.restrictHeight();
  23471. if(this.lastQuery == this.allQuery){
  23472. if(this.editable){
  23473. this.el.dom.select();
  23474. }
  23475. if(!this.selectByValue(this.value, true)){
  23476. this.select(0, true);
  23477. }
  23478. }else{
  23479. this.selectNext();
  23480. if(this.typeAhead && this.lastKey != Ext.EventObject.BACKSPACE && this.lastKey != Ext.EventObject.DELETE){
  23481. this.taTask.delay(this.typeAheadDelay);
  23482. }
  23483. }
  23484. }else{
  23485. this.onEmptyResults();
  23486. }
  23487. //this.el.focus();
  23488. },
  23489. // private
  23490. onTypeAhead : function(){
  23491. if(this.store.getCount() > 0){
  23492. var r = this.store.getAt(0);
  23493. var newValue = r.data[this.displayField];
  23494. var len = newValue.length;
  23495. var selStart = this.getRawValue().length;
  23496. if(selStart != len){
  23497. this.setRawValue(newValue);
  23498. this.selectText(selStart, newValue.length);
  23499. }
  23500. }
  23501. },
  23502. // private
  23503. onSelect : function(record, index){
  23504. if(this.fireEvent('beforeselect', this, record, index) !== false){
  23505. this.setValue(record.data[this.valueField || this.displayField]);
  23506. this.collapse();
  23507. this.fireEvent('select', this, record, index);
  23508. }
  23509. },
  23510. getValue : function(){
  23511. if(this.valueField){
  23512. return typeof this.value != 'undefined' ? this.value : '';
  23513. }else{
  23514. return Ext.form.ComboBox.superclass.getValue.call(this);
  23515. }
  23516. },
  23517. clearValue : function(){
  23518. if(this.hiddenField){
  23519. this.hiddenField.value = '';
  23520. }
  23521. this.setRawValue('');
  23522. this.lastSelectionText = '';
  23523. this.applyEmptyText();
  23524. this.value = '';
  23525. },
  23526. setValue : function(v){
  23527. var text = v;
  23528. if(this.valueField){
  23529. var r = this.findRecord(this.valueField, v);
  23530. if(r){
  23531. text = r.data[this.displayField];
  23532. }else if(this.valueNotFoundText !== undefined){
  23533. text = this.valueNotFoundText;
  23534. }
  23535. }
  23536. this.lastSelectionText = text;
  23537. if(this.hiddenField){
  23538. this.hiddenField.value = v;
  23539. }
  23540. Ext.form.ComboBox.superclass.setValue.call(this, text);
  23541. this.value = v;
  23542. },
  23543. // private
  23544. findRecord : function(prop, value){
  23545. var record;
  23546. if(this.store.getCount() > 0){
  23547. this.store.each(function(r){
  23548. if(r.data[prop] == value){
  23549. record = r;
  23550. return false;
  23551. }
  23552. });
  23553. }
  23554. return record;
  23555. },
  23556. // private
  23557. onViewMove : function(e, t){
  23558. this.inKeyMode = false;
  23559. },
  23560. // private
  23561. onViewOver : function(e, t){
  23562. if(this.inKeyMode){ // prevent key nav and mouse over conflicts
  23563. return;
  23564. }
  23565. var item = this.view.findItemFromChild(t);
  23566. if(item){
  23567. var index = this.view.indexOf(item);
  23568. this.select(index, false);
  23569. }
  23570. },
  23571. // private
  23572. onViewClick : function(doFocus){
  23573. var index = this.view.getSelectedIndexes()[0];
  23574. var r = this.store.getAt(index);
  23575. if(r){
  23576. this.onSelect(r, index);
  23577. }
  23578. if(doFocus !== false){
  23579. this.el.focus();
  23580. }
  23581. },
  23582. // private
  23583. restrictHeight : function(){
  23584. this.innerList.dom.style.height = '';
  23585. var inner = this.innerList.dom;
  23586. var pad = this.list.getFrameWidth('tb')+(this.resizable?this.handleHeight:0)+this.assetHeight;
  23587. var h = Math.max(inner.clientHeight, inner.offsetHeight, inner.scrollHeight);
  23588. var ha = this.getPosition()[1]-Ext.getBody().getScroll().top;
  23589. var hb = Ext.lib.Dom.getViewHeight()-ha-this.getSize().height;
  23590. var space = Math.max(ha, hb, this.minHeight || 0)-this.list.shadowOffset-pad-5;
  23591. h = Math.min(h, space, this.maxHeight);
  23592. this.innerList.setHeight(h);
  23593. this.list.beginUpdate();
  23594. this.list.setHeight(h+pad);
  23595. this.list.alignTo(this.wrap, this.listAlign);
  23596. this.list.endUpdate();
  23597. },
  23598. // private
  23599. onEmptyResults : function(){
  23600. this.collapse();
  23601. },
  23602. isExpanded : function(){
  23603. return this.list && this.list.isVisible();
  23604. },
  23605. selectByValue : function(v, scrollIntoView){
  23606. if(v !== undefined && v !== null){
  23607. var r = this.findRecord(this.valueField || this.displayField, v);
  23608. if(r){
  23609. this.select(this.store.indexOf(r), scrollIntoView);
  23610. return true;
  23611. }
  23612. }
  23613. return false;
  23614. },
  23615. select : function(index, scrollIntoView){
  23616. this.selectedIndex = index;
  23617. this.view.select(index);
  23618. if(scrollIntoView !== false){
  23619. var el = this.view.getNode(index);
  23620. if(el){
  23621. this.innerList.scrollChildIntoView(el, false);
  23622. }
  23623. }
  23624. },
  23625. // private
  23626. selectNext : function(){
  23627. var ct = this.store.getCount();
  23628. if(ct > 0){
  23629. if(this.selectedIndex == -1){
  23630. this.select(0);
  23631. }else if(this.selectedIndex < ct-1){
  23632. this.select(this.selectedIndex+1);
  23633. }
  23634. }
  23635. },
  23636. // private
  23637. selectPrev : function(){
  23638. var ct = this.store.getCount();
  23639. if(ct > 0){
  23640. if(this.selectedIndex == -1){
  23641. this.select(0);
  23642. }else if(this.selectedIndex != 0){
  23643. this.select(this.selectedIndex-1);
  23644. }
  23645. }
  23646. },
  23647. // private
  23648. onKeyUp : function(e){
  23649. if(this.editable !== false && !e.isSpecialKey()){
  23650. this.lastKey = e.getKey();
  23651. this.dqTask.delay(this.queryDelay);
  23652. }
  23653. },
  23654. // private
  23655. validateBlur : function(){
  23656. return !this.list || !this.list.isVisible();
  23657. },
  23658. // private
  23659. initQuery : function(){
  23660. this.doQuery(this.getRawValue());
  23661. },
  23662. // private
  23663. doForce : function(){
  23664. if(this.el.dom.value.length > 0){
  23665. this.el.dom.value =
  23666. this.lastSelectionText === undefined ? '' : this.lastSelectionText;
  23667. this.applyEmptyText();
  23668. }
  23669. },
  23670. doQuery : function(q, forceAll){
  23671. if(q === undefined || q === null){
  23672. q = '';
  23673. }
  23674. var qe = {
  23675. query: q,
  23676. forceAll: forceAll,
  23677. combo: this,
  23678. cancel:false
  23679. };
  23680. if(this.fireEvent('beforequery', qe)===false || qe.cancel){
  23681. return false;
  23682. }
  23683. q = qe.query;
  23684. forceAll = qe.forceAll;
  23685. if(forceAll === true || (q.length >= this.minChars)){
  23686. if(this.lastQuery !== q){
  23687. this.lastQuery = q;
  23688. if(this.mode == 'local'){
  23689. this.selectedIndex = -1;
  23690. if(forceAll){
  23691. this.store.clearFilter();
  23692. }else{
  23693. this.store.filter(this.displayField, q);
  23694. }
  23695. this.onLoad();
  23696. }else{
  23697. this.store.baseParams[this.queryParam] = q;
  23698. this.store.load({
  23699. params: this.getParams(q)
  23700. });
  23701. this.expand();
  23702. }
  23703. }else{
  23704. this.selectedIndex = -1;
  23705. this.onLoad();
  23706. }
  23707. }
  23708. },
  23709. // private
  23710. getParams : function(q){
  23711. var p = {};
  23712. //p[this.queryParam] = q;
  23713. if(this.pageSize){
  23714. p.start = 0;
  23715. p.limit = this.pageSize;
  23716. }
  23717. return p;
  23718. },
  23719. collapse : function(){
  23720. if(!this.isExpanded()){
  23721. return;
  23722. }
  23723. this.list.hide();
  23724. Ext.getDoc().un('mousewheel', this.collapseIf, this);
  23725. Ext.getDoc().un('mousedown', this.collapseIf, this);
  23726. this.fireEvent('collapse', this);
  23727. },
  23728. // private
  23729. collapseIf : function(e){
  23730. if(!e.within(this.wrap) && !e.within(this.list)){
  23731. this.collapse();
  23732. }
  23733. },
  23734. expand : function(){
  23735. if(this.isExpanded() || !this.hasFocus){
  23736. return;
  23737. }
  23738. this.list.alignTo(this.wrap, this.listAlign);
  23739. this.list.show();
  23740. this.innerList.setOverflow('auto'); // necessary for FF 2.0/Mac
  23741. Ext.getDoc().on('mousewheel', this.collapseIf, this);
  23742. Ext.getDoc().on('mousedown', this.collapseIf, this);
  23743. this.fireEvent('expand', this);
  23744. },
  23745. // private
  23746. // Implements the default empty TriggerField.onTriggerClick function
  23747. onTriggerClick : function(){
  23748. if(this.disabled){
  23749. return;
  23750. }
  23751. if(this.isExpanded()){
  23752. this.collapse();
  23753. this.el.focus();
  23754. }else {
  23755. this.onFocus({});
  23756. if(this.triggerAction == 'all') {
  23757. this.doQuery(this.allQuery, true);
  23758. } else {
  23759. this.doQuery(this.getRawValue());
  23760. }
  23761. this.el.focus();
  23762. }
  23763. }
  23764. });
  23765. Ext.reg('combo', Ext.form.ComboBox);
  23766. Ext.form.Checkbox = Ext.extend(Ext.form.Field, {
  23767. checkedCls: 'x-form-check-checked',
  23768. focusCls: 'x-form-check-focus',
  23769. overCls: 'x-form-check-over',
  23770. mouseDownCls: 'x-form-check-down',
  23771. tabIndex: 0,
  23772. checked: false,
  23773. defaultAutoCreate: {tag: 'input', type: 'checkbox', autocomplete: 'off'},
  23774. // private
  23775. baseCls: 'x-form-check',
  23776. // private
  23777. initComponent : function(){
  23778. Ext.form.Checkbox.superclass.initComponent.call(this);
  23779. this.addEvents(
  23780. 'check'
  23781. );
  23782. },
  23783. // private
  23784. initEvents : function(){
  23785. Ext.form.Checkbox.superclass.initEvents.call(this);
  23786. this.initCheckEvents();
  23787. },
  23788. // private
  23789. initCheckEvents : function(){
  23790. this.innerWrap.removeAllListeners();
  23791. this.innerWrap.addClassOnOver(this.overCls);
  23792. this.innerWrap.addClassOnClick(this.mouseDownCls);
  23793. this.innerWrap.on('click', this.onClick, this);
  23794. this.innerWrap.on('keyup', this.onKeyUp, this);
  23795. },
  23796. // private
  23797. onRender : function(ct, position){
  23798. Ext.form.Checkbox.superclass.onRender.call(this, ct, position);
  23799. if(this.inputValue !== undefined){
  23800. this.el.dom.value = this.inputValue;
  23801. }
  23802. this.el.addClass('x-hidden');
  23803. this.innerWrap = this.el.wrap({
  23804. tabIndex: this.tabIndex,
  23805. cls: this.baseCls+'-wrap-inner'
  23806. });
  23807. this.wrap = this.innerWrap.wrap({cls: this.baseCls+'-wrap'});
  23808. if(this.boxLabel){
  23809. this.labelEl = this.innerWrap.createChild({
  23810. tag: 'label',
  23811. htmlFor: this.el.id,
  23812. cls: 'x-form-cb-label',
  23813. html: this.boxLabel
  23814. });
  23815. }
  23816. this.imageEl = this.innerWrap.createChild({
  23817. tag: 'img',
  23818. src: Ext.BLANK_IMAGE_URL,
  23819. cls: this.baseCls
  23820. }, this.el);
  23821. if(this.checked){
  23822. this.setValue(true);
  23823. }else{
  23824. this.checked = this.el.dom.checked;
  23825. }
  23826. this.originalValue = this.checked;
  23827. },
  23828. // private
  23829. afterRender : function(){
  23830. Ext.form.Checkbox.superclass.afterRender.call(this);
  23831. this.wrap[this.checked? 'addClass' : 'removeClass'](this.checkedCls);
  23832. },
  23833. // private
  23834. onDestroy : function(){
  23835. if(this.rendered){
  23836. Ext.destroy(this.imageEl, this.labelEl, this.innerWrap, this.wrap);
  23837. }
  23838. Ext.form.Checkbox.superclass.onDestroy.call(this);
  23839. },
  23840. // private
  23841. onFocus: function(e) {
  23842. Ext.form.Checkbox.superclass.onFocus.call(this, e);
  23843. this.el.addClass(this.focusCls);
  23844. },
  23845. // private
  23846. onBlur: function(e) {
  23847. Ext.form.Checkbox.superclass.onBlur.call(this, e);
  23848. this.el.removeClass(this.focusCls);
  23849. },
  23850. // private
  23851. onResize : function(){
  23852. Ext.form.Checkbox.superclass.onResize.apply(this, arguments);
  23853. if(!this.boxLabel && !this.fieldLabel){
  23854. this.el.alignTo(this.wrap, 'c-c');
  23855. }
  23856. },
  23857. // private
  23858. onKeyUp : function(e){
  23859. if(e.getKey() == Ext.EventObject.SPACE){
  23860. this.onClick(e);
  23861. }
  23862. },
  23863. // private
  23864. onClick : function(e){
  23865. if (!this.disabled && !this.readOnly) {
  23866. this.toggleValue();
  23867. }
  23868. e.stopEvent();
  23869. },
  23870. // private
  23871. onEnable : function(){
  23872. Ext.form.Checkbox.superclass.onEnable.call(this);
  23873. this.initCheckEvents();
  23874. },
  23875. // private
  23876. onDisable : function(){
  23877. Ext.form.Checkbox.superclass.onDisable.call(this);
  23878. this.innerWrap.removeAllListeners();
  23879. },
  23880. toggleValue : function(){
  23881. this.setValue(!this.checked);
  23882. },
  23883. // private
  23884. getResizeEl : function(){
  23885. if(!this.resizeEl){
  23886. this.resizeEl = Ext.isSafari ? this.wrap : (this.wrap.up('.x-form-element', 5) || this.wrap);
  23887. }
  23888. return this.resizeEl;
  23889. },
  23890. // private
  23891. getPositionEl : function(){
  23892. return this.wrap;
  23893. },
  23894. // private
  23895. getActionEl : function(){
  23896. return this.wrap;
  23897. },
  23898. markInvalid : Ext.emptyFn,
  23899. clearInvalid : Ext.emptyFn,
  23900. // private
  23901. initValue : Ext.emptyFn,
  23902. getValue : function(){
  23903. if(this.rendered){
  23904. return this.el.dom.checked;
  23905. }
  23906. return this.checked;
  23907. },
  23908. setValue : function(v) {
  23909. var checked = this.checked;
  23910. this.checked = (v === true || v === 'true' || v == '1' || String(v).toLowerCase() == 'on');
  23911. if(this.rendered){
  23912. this.el.dom.checked = this.checked;
  23913. this.el.dom.defaultChecked = this.checked;
  23914. this.wrap[this.checked? 'addClass' : 'removeClass'](this.checkedCls);
  23915. }
  23916. if(checked != this.checked){
  23917. this.fireEvent("check", this, this.checked);
  23918. if(this.handler){
  23919. this.handler.call(this.scope || this, this, this.checked);
  23920. }
  23921. }
  23922. }
  23923. });
  23924. Ext.reg('checkbox', Ext.form.Checkbox);
  23925. Ext.form.CheckboxGroup = Ext.extend(Ext.form.Field, {
  23926. columns : 'auto',
  23927. vertical : false,
  23928. allowBlank : true,
  23929. blankText : "You must select at least one item in this group",
  23930. // private
  23931. defaultType : 'checkbox',
  23932. // private
  23933. groupCls: 'x-form-check-group',
  23934. // private
  23935. onRender : function(ct, position){
  23936. if(!this.el){
  23937. var panelCfg = {
  23938. cls: this.groupCls,
  23939. layout: 'column',
  23940. border: false,
  23941. renderTo: ct
  23942. };
  23943. var colCfg = {
  23944. defaultType: this.defaultType,
  23945. layout: 'form',
  23946. border: false,
  23947. defaults: {
  23948. hideLabel: true,
  23949. anchor: '100%'
  23950. }
  23951. }
  23952. if(this.items[0].items){
  23953. // The container has standard ColumnLayout configs, so pass them in directly
  23954. Ext.apply(panelCfg, {
  23955. layoutConfig: {columns: this.items.length},
  23956. defaults: this.defaults,
  23957. items: this.items
  23958. })
  23959. for(var i=0, len=this.items.length; i<len; i++){
  23960. Ext.applyIf(this.items[i], colCfg);
  23961. };
  23962. }else{
  23963. // The container has field item configs, so we have to generate the column
  23964. // panels first then move the items into the columns as needed.
  23965. var numCols, cols = [];
  23966. if(typeof this.columns == 'string'){ // 'auto' so create a col per item
  23967. this.columns = this.items.length;
  23968. }
  23969. if(!Ext.isArray(this.columns)){
  23970. var cs = [];
  23971. for(var i=0; i<this.columns; i++){
  23972. cs.push((100/this.columns)*.01); // distribute by even %
  23973. }
  23974. this.columns = cs;
  23975. }
  23976. numCols = this.columns.length;
  23977. // Generate the column configs with the correct width setting
  23978. for(var i=0; i<numCols; i++){
  23979. var cc = Ext.apply({items:[]}, colCfg);
  23980. cc[this.columns[i] <= 1 ? 'columnWidth' : 'width'] = this.columns[i];
  23981. if(this.defaults){
  23982. cc.defaults = Ext.apply(cc.defaults || {}, this.defaults)
  23983. }
  23984. cols.push(cc);
  23985. };
  23986. // Distribute the original items into the columns
  23987. if(this.vertical){
  23988. var rows = Math.ceil(this.items.length / numCols), ri = 0;
  23989. for(var i=0, len=this.items.length; i<len; i++){
  23990. if(i>0 && i%rows==0){
  23991. ri++;
  23992. }
  23993. if(this.items[i].fieldLabel){
  23994. this.items[i].hideLabel = false;
  23995. }
  23996. cols[ri].items.push(this.items[i]);
  23997. };
  23998. }else{
  23999. for(var i=0, len=this.items.length; i<len; i++){
  24000. var ci = i % numCols;
  24001. if(this.items[i].fieldLabel){
  24002. this.items[i].hideLabel = false;
  24003. }
  24004. cols[ci].items.push(this.items[i]);
  24005. };
  24006. }
  24007. Ext.apply(panelCfg, {
  24008. layoutConfig: {columns: numCols},
  24009. items: cols
  24010. });
  24011. }
  24012. this.panel = new Ext.Panel(panelCfg);
  24013. this.el = this.panel.getEl();
  24014. if(this.forId && this.itemCls){
  24015. var l = this.el.up(this.itemCls).child('label', true);
  24016. if(l){
  24017. l.setAttribute('htmlFor', this.forId);
  24018. }
  24019. }
  24020. var fields = this.panel.findBy(function(c){
  24021. return c.isFormField;
  24022. }, this);
  24023. this.items = new Ext.util.MixedCollection();
  24024. this.items.addAll(fields);
  24025. }
  24026. Ext.form.CheckboxGroup.superclass.onRender.call(this, ct, position);
  24027. },
  24028. // private
  24029. validateValue : function(value){
  24030. if(!this.allowBlank){
  24031. var blank = true;
  24032. this.items.each(function(f){
  24033. if(f.checked){
  24034. return blank = false;
  24035. }
  24036. }, this);
  24037. if(blank){
  24038. this.markInvalid(this.blankText);
  24039. return false;
  24040. }
  24041. }
  24042. return true;
  24043. },
  24044. // private
  24045. onDisable : function(){
  24046. this.items.each(function(item){
  24047. item.disable();
  24048. })
  24049. },
  24050. // private
  24051. onEnable : function(){
  24052. this.items.each(function(item){
  24053. item.enable();
  24054. })
  24055. },
  24056. // private
  24057. onResize : function(w, h){
  24058. this.panel.setSize(w, h);
  24059. this.panel.doLayout();
  24060. },
  24061. // inherit docs from Field
  24062. reset : function(){
  24063. Ext.form.CheckboxGroup.superclass.reset.call(this);
  24064. this.items.each(function(c){
  24065. if(c.reset){
  24066. c.reset();
  24067. }
  24068. }, this);
  24069. },
  24070. initValue : Ext.emptyFn,
  24071. getValue : Ext.emptyFn,
  24072. getRawValue : Ext.emptyFn,
  24073. setValue : Ext.emptyFn,
  24074. setRawValue : Ext.emptyFn
  24075. });
  24076. Ext.reg('checkboxgroup', Ext.form.CheckboxGroup);
  24077. Ext.form.Radio = Ext.extend(Ext.form.Checkbox, {
  24078. // private
  24079. inputType: 'radio',
  24080. // private
  24081. baseCls: 'x-form-radio',
  24082. getGroupValue : function(){
  24083. var c = this.getParent().child('input[name='+this.el.dom.name+']:checked', true);
  24084. return c ? c.value : null;
  24085. },
  24086. // private
  24087. getParent : function(){
  24088. return this.el.up('form') || Ext.getBody();
  24089. },
  24090. // private
  24091. toggleValue : function() {
  24092. if(!this.checked){
  24093. var els = this.getParent().select('input[name='+this.el.dom.name+']');
  24094. els.each(function(el){
  24095. if(el.dom.id == this.id){
  24096. this.setValue(true);
  24097. }else{
  24098. Ext.getCmp(el.dom.id).setValue(false);
  24099. }
  24100. }, this);
  24101. }
  24102. },
  24103. setValue : function(v){
  24104. if(typeof v=='boolean') {
  24105. Ext.form.Radio.superclass.setValue.call(this, v);
  24106. }else{
  24107. var r = this.getParent().child('input[name='+this.el.dom.name+'][value='+v+']', true);
  24108. if(r && !r.checked){
  24109. Ext.getCmp(r.id).toggleValue();
  24110. };
  24111. }
  24112. },
  24113. markInvalid : Ext.emptyFn,
  24114. clearInvalid : Ext.emptyFn
  24115. });
  24116. Ext.reg('radio', Ext.form.Radio);
  24117. Ext.form.RadioGroup = Ext.extend(Ext.form.CheckboxGroup, {
  24118. allowBlank : true,
  24119. blankText : "You must select one item in this group",
  24120. // private
  24121. defaultType : 'radio',
  24122. // private
  24123. groupCls: 'x-form-radio-group'
  24124. });
  24125. Ext.reg('radiogroup', Ext.form.RadioGroup);
  24126. Ext.form.Hidden = Ext.extend(Ext.form.Field, {
  24127. // private
  24128. inputType : 'hidden',
  24129. // private
  24130. onRender : function(){
  24131. Ext.form.Hidden.superclass.onRender.apply(this, arguments);
  24132. },
  24133. // private
  24134. initEvents : function(){
  24135. this.originalValue = this.getValue();
  24136. },
  24137. // These are all private overrides
  24138. setSize : Ext.emptyFn,
  24139. setWidth : Ext.emptyFn,
  24140. setHeight : Ext.emptyFn,
  24141. setPosition : Ext.emptyFn,
  24142. setPagePosition : Ext.emptyFn,
  24143. markInvalid : Ext.emptyFn,
  24144. clearInvalid : Ext.emptyFn
  24145. });
  24146. Ext.reg('hidden', Ext.form.Hidden);
  24147. Ext.form.BasicForm = function(el, config){
  24148. Ext.apply(this, config);
  24149. this.items = new Ext.util.MixedCollection(false, function(o){
  24150. return o.id || (o.id = Ext.id());
  24151. });
  24152. this.addEvents(
  24153. 'beforeaction',
  24154. 'actionfailed',
  24155. 'actioncomplete'
  24156. );
  24157. if(el){
  24158. this.initEl(el);
  24159. }
  24160. Ext.form.BasicForm.superclass.constructor.call(this);
  24161. };
  24162. Ext.extend(Ext.form.BasicForm, Ext.util.Observable, {
  24163. timeout: 30,
  24164. // private
  24165. activeAction : null,
  24166. trackResetOnLoad : false,
  24167. // private
  24168. initEl : function(el){
  24169. this.el = Ext.get(el);
  24170. this.id = this.el.id || Ext.id();
  24171. if(!this.standardSubmit){
  24172. this.el.on('submit', this.onSubmit, this);
  24173. }
  24174. this.el.addClass('x-form');
  24175. },
  24176. getEl: function(){
  24177. return this.el;
  24178. },
  24179. // private
  24180. onSubmit : function(e){
  24181. e.stopEvent();
  24182. },
  24183. // private
  24184. destroy: function() {
  24185. this.items.each(function(f){
  24186. Ext.destroy(f);
  24187. });
  24188. if(this.el){
  24189. this.el.removeAllListeners();
  24190. this.el.remove();
  24191. }
  24192. this.purgeListeners();
  24193. },
  24194. isValid : function(){
  24195. var valid = true;
  24196. this.items.each(function(f){
  24197. if(!f.validate()){
  24198. valid = false;
  24199. }
  24200. });
  24201. return valid;
  24202. },
  24203. isDirty : function(){
  24204. var dirty = false;
  24205. this.items.each(function(f){
  24206. if(f.isDirty()){
  24207. dirty = true;
  24208. return false;
  24209. }
  24210. });
  24211. return dirty;
  24212. },
  24213. doAction : function(action, options){
  24214. if(typeof action == 'string'){
  24215. action = new Ext.form.Action.ACTION_TYPES[action](this, options);
  24216. }
  24217. if(this.fireEvent('beforeaction', this, action) !== false){
  24218. this.beforeAction(action);
  24219. action.run.defer(100, action);
  24220. }
  24221. return this;
  24222. },
  24223. submit : function(options){
  24224. if(this.standardSubmit){
  24225. var v = this.isValid();
  24226. if(v){
  24227. this.el.dom.submit();
  24228. }
  24229. return v;
  24230. }
  24231. this.doAction('submit', options);
  24232. return this;
  24233. },
  24234. load : function(options){
  24235. this.doAction('load', options);
  24236. return this;
  24237. },
  24238. updateRecord : function(record){
  24239. record.beginEdit();
  24240. var fs = record.fields;
  24241. fs.each(function(f){
  24242. var field = this.findField(f.name);
  24243. if(field){
  24244. record.set(f.name, field.getValue());
  24245. }
  24246. }, this);
  24247. record.endEdit();
  24248. return this;
  24249. },
  24250. loadRecord : function(record){
  24251. this.setValues(record.data);
  24252. return this;
  24253. },
  24254. // private
  24255. beforeAction : function(action){
  24256. var o = action.options;
  24257. if(o.waitMsg){
  24258. if(this.waitMsgTarget === true){
  24259. this.el.mask(o.waitMsg, 'x-mask-loading');
  24260. }else if(this.waitMsgTarget){
  24261. this.waitMsgTarget = Ext.get(this.waitMsgTarget);
  24262. this.waitMsgTarget.mask(o.waitMsg, 'x-mask-loading');
  24263. }else{
  24264. Ext.MessageBox.wait(o.waitMsg, o.waitTitle || this.waitTitle || 'Please Wait...');
  24265. }
  24266. }
  24267. },
  24268. // private
  24269. afterAction : function(action, success){
  24270. this.activeAction = null;
  24271. var o = action.options;
  24272. if(o.waitMsg){
  24273. if(this.waitMsgTarget === true){
  24274. this.el.unmask();
  24275. }else if(this.waitMsgTarget){
  24276. this.waitMsgTarget.unmask();
  24277. }else{
  24278. Ext.MessageBox.updateProgress(1);
  24279. Ext.MessageBox.hide();
  24280. }
  24281. }
  24282. if(success){
  24283. if(o.reset){
  24284. this.reset();
  24285. }
  24286. Ext.callback(o.success, o.scope, [this, action]);
  24287. this.fireEvent('actioncomplete', this, action);
  24288. }else{
  24289. Ext.callback(o.failure, o.scope, [this, action]);
  24290. this.fireEvent('actionfailed', this, action);
  24291. }
  24292. },
  24293. findField : function(id){
  24294. var field = this.items.get(id);
  24295. if(!field){
  24296. this.items.each(function(f){
  24297. if(f.isFormField && (f.dataIndex == id || f.id == id || f.getName() == id)){
  24298. field = f;
  24299. return false;
  24300. }
  24301. });
  24302. }
  24303. return field || null;
  24304. },
  24305. markInvalid : function(errors){
  24306. if(Ext.isArray(errors)){
  24307. for(var i = 0, len = errors.length; i < len; i++){
  24308. var fieldError = errors[i];
  24309. var f = this.findField(fieldError.id);
  24310. if(f){
  24311. f.markInvalid(fieldError.msg);
  24312. }
  24313. }
  24314. }else{
  24315. var field, id;
  24316. for(id in errors){
  24317. if(typeof errors[id] != 'function' && (field = this.findField(id))){
  24318. field.markInvalid(errors[id]);
  24319. }
  24320. }
  24321. }
  24322. return this;
  24323. },
  24324. setValues : function(values){
  24325. if(Ext.isArray(values)){ // array of objects
  24326. for(var i = 0, len = values.length; i < len; i++){
  24327. var v = values[i];
  24328. var f = this.findField(v.id);
  24329. if(f){
  24330. f.setValue(v.value);
  24331. if(this.trackResetOnLoad){
  24332. f.originalValue = f.getValue();
  24333. }
  24334. }
  24335. }
  24336. }else{ // object hash
  24337. var field, id;
  24338. for(id in values){
  24339. if(typeof values[id] != 'function' && (field = this.findField(id))){
  24340. field.setValue(values[id]);
  24341. if(this.trackResetOnLoad){
  24342. field.originalValue = field.getValue();
  24343. }
  24344. }
  24345. }
  24346. }
  24347. return this;
  24348. },
  24349. getValues : function(asString){
  24350. var fs = Ext.lib.Ajax.serializeForm(this.el.dom);
  24351. if(asString === true){
  24352. return fs;
  24353. }
  24354. return Ext.urlDecode(fs);
  24355. },
  24356. clearInvalid : function(){
  24357. this.items.each(function(f){
  24358. f.clearInvalid();
  24359. });
  24360. return this;
  24361. },
  24362. reset : function(){
  24363. this.items.each(function(f){
  24364. f.reset();
  24365. });
  24366. return this;
  24367. },
  24368. add : function(){
  24369. this.items.addAll(Array.prototype.slice.call(arguments, 0));
  24370. return this;
  24371. },
  24372. remove : function(field){
  24373. this.items.remove(field);
  24374. return this;
  24375. },
  24376. render : function(){
  24377. this.items.each(function(f){
  24378. if(f.isFormField && !f.rendered && document.getElementById(f.id)){ // if the element exists
  24379. f.applyToMarkup(f.id);
  24380. }
  24381. });
  24382. return this;
  24383. },
  24384. applyToFields : function(o){
  24385. this.items.each(function(f){
  24386. Ext.apply(f, o);
  24387. });
  24388. return this;
  24389. },
  24390. applyIfToFields : function(o){
  24391. this.items.each(function(f){
  24392. Ext.applyIf(f, o);
  24393. });
  24394. return this;
  24395. }
  24396. });
  24397. // back compat
  24398. Ext.BasicForm = Ext.form.BasicForm;
  24399. Ext.FormPanel = Ext.extend(Ext.Panel, {
  24400. buttonAlign:'center',
  24401. minButtonWidth:75,
  24402. labelAlign:'left',
  24403. monitorValid : false,
  24404. monitorPoll : 200,
  24405. layout: 'form',
  24406. // private
  24407. initComponent :function(){
  24408. this.form = this.createForm();
  24409. this.bodyCfg = {
  24410. tag: 'form',
  24411. cls: this.baseCls + '-body',
  24412. method : this.method || 'POST',
  24413. id : this.formId || Ext.id()
  24414. };
  24415. if(this.fileUpload) {
  24416. this.bodyCfg.enctype = 'multipart/form-data';
  24417. }
  24418. Ext.FormPanel.superclass.initComponent.call(this);
  24419. this.initItems();
  24420. this.addEvents(
  24421. 'clientvalidation'
  24422. );
  24423. this.relayEvents(this.form, ['beforeaction', 'actionfailed', 'actioncomplete']);
  24424. },
  24425. // private
  24426. createForm: function(){
  24427. delete this.initialConfig.listeners;
  24428. return new Ext.form.BasicForm(null, this.initialConfig);
  24429. },
  24430. // private
  24431. initFields : function(){
  24432. var f = this.form;
  24433. var formPanel = this;
  24434. var fn = function(c){
  24435. if(c.isFormField){
  24436. f.add(c);
  24437. }else if(c.doLayout && c != formPanel){
  24438. Ext.applyIf(c, {
  24439. labelAlign: c.ownerCt.labelAlign,
  24440. labelWidth: c.ownerCt.labelWidth,
  24441. itemCls: c.ownerCt.itemCls
  24442. });
  24443. if(c.items){
  24444. c.items.each(fn);
  24445. }
  24446. }
  24447. }
  24448. this.items.each(fn);
  24449. },
  24450. // private
  24451. getLayoutTarget : function(){
  24452. return this.form.el;
  24453. },
  24454. getForm : function(){
  24455. return this.form;
  24456. },
  24457. // private
  24458. onRender : function(ct, position){
  24459. this.initFields();
  24460. Ext.FormPanel.superclass.onRender.call(this, ct, position);
  24461. this.form.initEl(this.body);
  24462. },
  24463. // private
  24464. beforeDestroy: function(){
  24465. Ext.FormPanel.superclass.beforeDestroy.call(this);
  24466. this.stopMonitoring();
  24467. Ext.destroy(this.form);
  24468. },
  24469. // private
  24470. initEvents : function(){
  24471. Ext.FormPanel.superclass.initEvents.call(this);
  24472. this.items.on('remove', this.onRemove, this);
  24473. this.items.on('add', this.onAdd, this);
  24474. if(this.monitorValid){ // initialize after render
  24475. this.startMonitoring();
  24476. }
  24477. },
  24478. // private
  24479. onAdd : function(ct, c) {
  24480. if (c.isFormField) {
  24481. this.form.add(c);
  24482. }
  24483. },
  24484. // private
  24485. onRemove : function(c) {
  24486. if (c.isFormField) {
  24487. Ext.destroy(c.container.up('.x-form-item'));
  24488. this.form.remove(c);
  24489. }
  24490. },
  24491. startMonitoring : function(){
  24492. if(!this.bound){
  24493. this.bound = true;
  24494. Ext.TaskMgr.start({
  24495. run : this.bindHandler,
  24496. interval : this.monitorPoll || 200,
  24497. scope: this
  24498. });
  24499. }
  24500. },
  24501. stopMonitoring : function(){
  24502. this.bound = false;
  24503. },
  24504. load : function(){
  24505. this.form.load.apply(this.form, arguments);
  24506. },
  24507. // private
  24508. onDisable : function(){
  24509. Ext.FormPanel.superclass.onDisable.call(this);
  24510. if(this.form){
  24511. this.form.items.each(function(){
  24512. this.disable();
  24513. });
  24514. }
  24515. },
  24516. // private
  24517. onEnable : function(){
  24518. Ext.FormPanel.superclass.onEnable.call(this);
  24519. if(this.form){
  24520. this.form.items.each(function(){
  24521. this.enable();
  24522. });
  24523. }
  24524. },
  24525. // private
  24526. bindHandler : function(){
  24527. if(!this.bound){
  24528. return false; // stops binding
  24529. }
  24530. var valid = true;
  24531. this.form.items.each(function(f){
  24532. if(!f.isValid(true)){
  24533. valid = false;
  24534. return false;
  24535. }
  24536. });
  24537. if(this.buttons){
  24538. for(var i = 0, len = this.buttons.length; i < len; i++){
  24539. var btn = this.buttons[i];
  24540. if(btn.formBind === true && btn.disabled === valid){
  24541. btn.setDisabled(!valid);
  24542. }
  24543. }
  24544. }
  24545. this.fireEvent('clientvalidation', this, valid);
  24546. }
  24547. });
  24548. Ext.reg('form', Ext.FormPanel);
  24549. Ext.form.FormPanel = Ext.FormPanel;
  24550. Ext.form.FieldSet = Ext.extend(Ext.Panel, {
  24551. baseCls:'x-fieldset',
  24552. layout: 'form',
  24553. animCollapse: false,
  24554. // private
  24555. onRender : function(ct, position){
  24556. if(!this.el){
  24557. this.el = document.createElement('fieldset');
  24558. this.el.id = this.id;
  24559. if (this.title || this.header || this.checkboxToggle) {
  24560. this.el.appendChild(document.createElement('legend')).className = 'x-fieldset-header';
  24561. }
  24562. }
  24563. Ext.form.FieldSet.superclass.onRender.call(this, ct, position);
  24564. if(this.checkboxToggle){
  24565. var o = typeof this.checkboxToggle == 'object' ?
  24566. this.checkboxToggle :
  24567. {tag: 'input', type: 'checkbox', name: this.checkboxName || this.id+'-checkbox'};
  24568. this.checkbox = this.header.insertFirst(o);
  24569. this.checkbox.dom.checked = !this.collapsed;
  24570. this.checkbox.on('click', this.onCheckClick, this);
  24571. }
  24572. },
  24573. // private
  24574. onCollapse : function(doAnim, animArg){
  24575. if(this.checkbox){
  24576. this.checkbox.dom.checked = false;
  24577. }
  24578. Ext.form.FieldSet.superclass.onCollapse.call(this, doAnim, animArg);
  24579. },
  24580. // private
  24581. onExpand : function(doAnim, animArg){
  24582. if(this.checkbox){
  24583. this.checkbox.dom.checked = true;
  24584. }
  24585. Ext.form.FieldSet.superclass.onExpand.call(this, doAnim, animArg);
  24586. },
  24587. onCheckClick : function(){
  24588. this[this.checkbox.dom.checked ? 'expand' : 'collapse']();
  24589. },
  24590. // private
  24591. beforeDestroy : function(){
  24592. if(this.checkbox){
  24593. this.checkbox.un('click', this.onCheckClick, this);
  24594. }
  24595. Ext.form.FieldSet.superclass.beforeDestroy.call(this);
  24596. }
  24597. });
  24598. Ext.reg('fieldset', Ext.form.FieldSet);
  24599. Ext.form.HtmlEditor = Ext.extend(Ext.form.Field, {
  24600. enableFormat : true,
  24601. enableFontSize : true,
  24602. enableColors : true,
  24603. enableAlignments : true,
  24604. enableLists : true,
  24605. enableSourceEdit : true,
  24606. enableLinks : true,
  24607. enableFont : true,
  24608. createLinkText : 'Please enter the URL for the link:',
  24609. defaultLinkValue : 'http:/'+'/',
  24610. fontFamilies : [
  24611. 'Arial',
  24612. 'Courier New',
  24613. 'Tahoma',
  24614. 'Times New Roman',
  24615. 'Verdana'
  24616. ],
  24617. defaultFont: 'tahoma',
  24618. // private properties
  24619. validationEvent : false,
  24620. deferHeight: true,
  24621. initialized : false,
  24622. activated : false,
  24623. sourceEditMode : false,
  24624. onFocus : Ext.emptyFn,
  24625. iframePad:3,
  24626. hideMode:'offsets',
  24627. defaultAutoCreate : {
  24628. tag: "textarea",
  24629. style:"width:500px;height:300px;",
  24630. autocomplete: "off"
  24631. },
  24632. // private
  24633. initComponent : function(){
  24634. this.addEvents(
  24635. 'initialize',
  24636. 'activate',
  24637. 'beforesync',
  24638. 'beforepush',
  24639. 'sync',
  24640. 'push',
  24641. 'editmodechange'
  24642. )
  24643. },
  24644. // private
  24645. createFontOptions : function(){
  24646. var buf = [], fs = this.fontFamilies, ff, lc;
  24647. for(var i = 0, len = fs.length; i< len; i++){
  24648. ff = fs[i];
  24649. lc = ff.toLowerCase();
  24650. buf.push(
  24651. '<option value="',lc,'" style="font-family:',ff,';"',
  24652. (this.defaultFont == lc ? ' selected="true">' : '>'),
  24653. ff,
  24654. '</option>'
  24655. );
  24656. }
  24657. return buf.join('');
  24658. },
  24659. createToolbar : function(editor){
  24660. var tipsEnabled = Ext.QuickTips && Ext.QuickTips.isEnabled();
  24661. function btn(id, toggle, handler){
  24662. return {
  24663. itemId : id,
  24664. cls : 'x-btn-icon x-edit-'+id,
  24665. enableToggle:toggle !== false,
  24666. scope: editor,
  24667. handler:handler||editor.relayBtnCmd,
  24668. clickEvent:'mousedown',
  24669. tooltip: tipsEnabled ? editor.buttonTips[id] || undefined : undefined,
  24670. tabIndex:-1
  24671. };
  24672. }
  24673. // build the toolbar
  24674. var tb = new Ext.Toolbar({
  24675. renderTo:this.wrap.dom.firstChild
  24676. });
  24677. // stop form submits
  24678. tb.el.on('click', function(e){
  24679. e.preventDefault();
  24680. });
  24681. if(this.enableFont && !Ext.isSafari2){
  24682. this.fontSelect = tb.el.createChild({
  24683. tag:'select',
  24684. cls:'x-font-select',
  24685. html: this.createFontOptions()
  24686. });
  24687. this.fontSelect.on('change', function(){
  24688. var font = this.fontSelect.dom.value;
  24689. this.relayCmd('fontname', font);
  24690. this.deferFocus();
  24691. }, this);
  24692. tb.add(
  24693. this.fontSelect.dom,
  24694. '-'
  24695. );
  24696. };
  24697. if(this.enableFormat){
  24698. tb.add(
  24699. btn('bold'),
  24700. btn('italic'),
  24701. btn('underline')
  24702. );
  24703. };
  24704. if(this.enableFontSize){
  24705. tb.add(
  24706. '-',
  24707. btn('increasefontsize', false, this.adjustFont),
  24708. btn('decreasefontsize', false, this.adjustFont)
  24709. );
  24710. };
  24711. if(this.enableColors){
  24712. tb.add(
  24713. '-', {
  24714. itemId:'forecolor',
  24715. cls:'x-btn-icon x-edit-forecolor',
  24716. clickEvent:'mousedown',
  24717. tooltip: tipsEnabled ? editor.buttonTips['forecolor'] || undefined : undefined,
  24718. tabIndex:-1,
  24719. menu : new Ext.menu.ColorMenu({
  24720. allowReselect: true,
  24721. focus: Ext.emptyFn,
  24722. value:'000000',
  24723. plain:true,
  24724. selectHandler: function(cp, color){
  24725. this.execCmd('forecolor', Ext.isSafari || Ext.isIE ? '#'+color : color);
  24726. this.deferFocus();
  24727. },
  24728. scope: this,
  24729. clickEvent:'mousedown'
  24730. })
  24731. }, {
  24732. itemId:'backcolor',
  24733. cls:'x-btn-icon x-edit-backcolor',
  24734. clickEvent:'mousedown',
  24735. tooltip: tipsEnabled ? editor.buttonTips['backcolor'] || undefined : undefined,
  24736. tabIndex:-1,
  24737. menu : new Ext.menu.ColorMenu({
  24738. focus: Ext.emptyFn,
  24739. value:'FFFFFF',
  24740. plain:true,
  24741. allowReselect: true,
  24742. selectHandler: function(cp, color){
  24743. if(Ext.isGecko){
  24744. this.execCmd('useCSS', false);
  24745. this.execCmd('hilitecolor', color);
  24746. this.execCmd('useCSS', true);
  24747. this.deferFocus();
  24748. }else{
  24749. this.execCmd(Ext.isOpera ? 'hilitecolor' : 'backcolor', Ext.isSafari || Ext.isIE ? '#'+color : color);
  24750. this.deferFocus();
  24751. }
  24752. },
  24753. scope:this,
  24754. clickEvent:'mousedown'
  24755. })
  24756. }
  24757. );
  24758. };
  24759. if(this.enableAlignments){
  24760. tb.add(
  24761. '-',
  24762. btn('justifyleft'),
  24763. btn('justifycenter'),
  24764. btn('justifyright')
  24765. );
  24766. };
  24767. if(!Ext.isSafari2){
  24768. if(this.enableLinks){
  24769. tb.add(
  24770. '-',
  24771. btn('createlink', false, this.createLink)
  24772. );
  24773. };
  24774. if(this.enableLists){
  24775. tb.add(
  24776. '-',
  24777. btn('insertorderedlist'),
  24778. btn('insertunorderedlist')
  24779. );
  24780. }
  24781. if(this.enableSourceEdit){
  24782. tb.add(
  24783. '-',
  24784. btn('sourceedit', true, function(btn){
  24785. this.toggleSourceEdit(btn.pressed);
  24786. })
  24787. );
  24788. }
  24789. }
  24790. this.tb = tb;
  24791. },
  24792. getDocMarkup : function(){
  24793. return '<html><head><style type="text/css">body{border:0;margin:0;padding:3px;height:98%;cursor:text;}</style></head><body></body></html>';
  24794. },
  24795. // private
  24796. getEditorBody : function(){
  24797. return this.doc.body || this.doc.documentElement;
  24798. },
  24799. // private
  24800. getDoc : function(){
  24801. return Ext.isIE ? this.getWin().document : (this.iframe.contentDocument || this.getWin().document);
  24802. },
  24803. // private
  24804. getWin : function(){
  24805. return Ext.isIE ? this.iframe.contentWindow : window.frames[this.iframe.name];
  24806. },
  24807. // private
  24808. onRender : function(ct, position){
  24809. Ext.form.HtmlEditor.superclass.onRender.call(this, ct, position);
  24810. this.el.dom.style.border = '0 none';
  24811. this.el.dom.setAttribute('tabIndex', -1);
  24812. this.el.addClass('x-hidden');
  24813. if(Ext.isIE){ // fix IE 1px bogus margin
  24814. this.el.applyStyles('margin-top:-1px;margin-bottom:-1px;')
  24815. }
  24816. this.wrap = this.el.wrap({
  24817. cls:'x-html-editor-wrap', cn:{cls:'x-html-editor-tb'}
  24818. });
  24819. this.createToolbar(this);
  24820. this.tb.items.each(function(item){
  24821. if(item.itemId != 'sourceedit'){
  24822. item.disable();
  24823. }
  24824. });
  24825. var iframe = document.createElement('iframe');
  24826. iframe.name = Ext.id();
  24827. iframe.frameBorder = '0';
  24828. iframe.src = Ext.isIE ? Ext.SSL_SECURE_URL : "javascript:;";
  24829. this.wrap.dom.appendChild(iframe);
  24830. this.iframe = iframe;
  24831. this.initFrame();
  24832. if(this.autoMonitorDesignMode !== false){
  24833. this.monitorTask = Ext.TaskMgr.start({
  24834. run: this.checkDesignMode,
  24835. scope: this,
  24836. interval:100
  24837. });
  24838. }
  24839. if(!this.width){
  24840. var sz = this.el.getSize();
  24841. this.setSize(sz.width, this.height || sz.height);
  24842. }
  24843. },
  24844. initFrame : function(){
  24845. this.doc = this.getDoc();
  24846. this.win = this.getWin();
  24847. this.doc.open();
  24848. this.doc.write(this.getDocMarkup());
  24849. this.doc.close();
  24850. var task = { // must defer to wait for browser to be ready
  24851. run : function(){
  24852. if(this.doc.body || this.doc.readyState == 'complete'){
  24853. Ext.TaskMgr.stop(task);
  24854. this.doc.designMode="on";
  24855. this.initEditor.defer(10, this);
  24856. }
  24857. },
  24858. interval : 10,
  24859. duration:10000,
  24860. scope: this
  24861. };
  24862. Ext.TaskMgr.start(task);
  24863. },
  24864. checkDesignMode : function(){
  24865. if(this.wrap && this.wrap.dom.offsetWidth){
  24866. var doc = this.getDoc();
  24867. if(!doc){
  24868. return;
  24869. }
  24870. if(!doc.editorInitialized || String(doc.designMode).toLowerCase() != 'on'){
  24871. this.initFrame();
  24872. }
  24873. }
  24874. },
  24875. // private
  24876. onResize : function(w, h){
  24877. Ext.form.HtmlEditor.superclass.onResize.apply(this, arguments);
  24878. if(this.el && this.iframe){
  24879. if(typeof w == 'number'){
  24880. var aw = w - this.wrap.getFrameWidth('lr');
  24881. this.el.setWidth(this.adjustWidth('textarea', aw));
  24882. this.iframe.style.width = Math.max(aw, 0) + 'px';
  24883. }
  24884. if(typeof h == 'number'){
  24885. var ah = h - this.wrap.getFrameWidth('tb') - this.tb.el.getHeight();
  24886. this.el.setHeight(this.adjustWidth('textarea', ah));
  24887. this.iframe.style.height = Math.max(ah, 0) + 'px';
  24888. if(this.doc){
  24889. this.getEditorBody().style.height = Math.max((ah - (this.iframePad*2)), 0) + 'px';
  24890. }
  24891. }
  24892. }
  24893. },
  24894. toggleSourceEdit : function(sourceEditMode){
  24895. if(sourceEditMode === undefined){
  24896. sourceEditMode = !this.sourceEditMode;
  24897. }
  24898. this.sourceEditMode = sourceEditMode === true;
  24899. var btn = this.tb.items.get('sourceedit');
  24900. if(btn.pressed !== this.sourceEditMode){
  24901. btn.toggle(this.sourceEditMode);
  24902. return;
  24903. }
  24904. if(this.sourceEditMode){
  24905. this.tb.items.each(function(item){
  24906. if(item.itemId != 'sourceedit'){
  24907. item.disable();
  24908. }
  24909. });
  24910. this.syncValue();
  24911. this.iframe.className = 'x-hidden';
  24912. this.el.removeClass('x-hidden');
  24913. this.el.dom.removeAttribute('tabIndex');
  24914. this.el.focus();
  24915. }else{
  24916. if(this.initialized){
  24917. this.tb.items.each(function(item){
  24918. item.enable();
  24919. });
  24920. }
  24921. this.pushValue();
  24922. this.iframe.className = '';
  24923. this.el.addClass('x-hidden');
  24924. this.el.dom.setAttribute('tabIndex', -1);
  24925. this.deferFocus();
  24926. }
  24927. var lastSize = this.lastSize;
  24928. if(lastSize){
  24929. delete this.lastSize;
  24930. this.setSize(lastSize);
  24931. }
  24932. this.fireEvent('editmodechange', this, this.sourceEditMode);
  24933. },
  24934. // private used internally
  24935. createLink : function(){
  24936. var url = prompt(this.createLinkText, this.defaultLinkValue);
  24937. if(url && url != 'http:/'+'/'){
  24938. this.relayCmd('createlink', url);
  24939. }
  24940. },
  24941. // private (for BoxComponent)
  24942. adjustSize : Ext.BoxComponent.prototype.adjustSize,
  24943. // private (for BoxComponent)
  24944. getResizeEl : function(){
  24945. return this.wrap;
  24946. },
  24947. // private (for BoxComponent)
  24948. getPositionEl : function(){
  24949. return this.wrap;
  24950. },
  24951. // private
  24952. initEvents : function(){
  24953. this.originalValue = this.getValue();
  24954. },
  24955. markInvalid : Ext.emptyFn,
  24956. clearInvalid : Ext.emptyFn,
  24957. // docs inherit from Field
  24958. setValue : function(v){
  24959. Ext.form.HtmlEditor.superclass.setValue.call(this, v);
  24960. this.pushValue();
  24961. },
  24962. cleanHtml : function(html){
  24963. html = String(html);
  24964. if(html.length > 5){
  24965. if(Ext.isSafari){ // strip safari nonsense
  24966. html = html.replace(/\sclass="(?:Apple-style-span|khtml-block-placeholder)"/gi, '');
  24967. }
  24968. }
  24969. if(html == '&nbsp;'){
  24970. html = '';
  24971. }
  24972. return html;
  24973. },
  24974. syncValue : function(){
  24975. if(this.initialized){
  24976. var bd = this.getEditorBody();
  24977. var html = bd.innerHTML;
  24978. if(Ext.isSafari){
  24979. var bs = bd.getAttribute('style'); // Safari puts text-align styles on the body element!
  24980. var m = bs.match(/text-align:(.*?);/i);
  24981. if(m && m[1]){
  24982. html = '<div style="'+m[0]+'">' + html + '</div>';
  24983. }
  24984. }
  24985. html = this.cleanHtml(html);
  24986. if(this.fireEvent('beforesync', this, html) !== false){
  24987. this.el.dom.value = html;
  24988. this.fireEvent('sync', this, html);
  24989. }
  24990. }
  24991. },
  24992. //docs inherit from Field
  24993. getValue : function() {
  24994. this.syncValue();
  24995. return Ext.form.HtmlEditor.superclass.getValue.call(this);
  24996. },
  24997. pushValue : function(){
  24998. if(this.initialized){
  24999. var v = this.el.dom.value;
  25000. if(!this.activated && v.length < 1){
  25001. v = '&nbsp;';
  25002. }
  25003. if(this.fireEvent('beforepush', this, v) !== false){
  25004. this.getEditorBody().innerHTML = v;
  25005. this.fireEvent('push', this, v);
  25006. }
  25007. }
  25008. },
  25009. // private
  25010. deferFocus : function(){
  25011. this.focus.defer(10, this);
  25012. },
  25013. // docs inherit from Field
  25014. focus : function(){
  25015. if(this.win && !this.sourceEditMode){
  25016. this.win.focus();
  25017. }else{
  25018. this.el.focus();
  25019. }
  25020. },
  25021. // private
  25022. initEditor : function(){
  25023. var dbody = this.getEditorBody();
  25024. var ss = this.el.getStyles('font-size', 'font-family', 'background-image', 'background-repeat');
  25025. ss['background-attachment'] = 'fixed'; // w3c
  25026. dbody.bgProperties = 'fixed'; // ie
  25027. Ext.DomHelper.applyStyles(dbody, ss);
  25028. if(this.doc){
  25029. try{
  25030. Ext.EventManager.removeAll(this.doc);
  25031. }catch(e){}
  25032. }
  25033. this.doc = this.getDoc();
  25034. Ext.EventManager.on(this.doc, {
  25035. 'mousedown': this.onEditorEvent,
  25036. 'dblclick': this.onEditorEvent,
  25037. 'click': this.onEditorEvent,
  25038. 'keyup': this.onEditorEvent,
  25039. buffer:100,
  25040. scope: this
  25041. });
  25042. if(Ext.isGecko){
  25043. Ext.EventManager.on(this.doc, 'keypress', this.applyCommand, this);
  25044. }
  25045. if(Ext.isIE || Ext.isSafari || Ext.isOpera){
  25046. Ext.EventManager.on(this.doc, 'keydown', this.fixKeys, this);
  25047. }
  25048. this.initialized = true;
  25049. this.fireEvent('initialize', this);
  25050. this.doc.editorInitialized = true;
  25051. this.pushValue();
  25052. },
  25053. // private
  25054. onDestroy : function(){
  25055. if(this.monitorTask){
  25056. Ext.TaskMgr.stop(this.monitorTask);
  25057. }
  25058. if(this.rendered){
  25059. this.tb.items.each(function(item){
  25060. if(item.menu){
  25061. item.menu.removeAll();
  25062. if(item.menu.el){
  25063. item.menu.el.destroy();
  25064. }
  25065. }
  25066. item.destroy();
  25067. });
  25068. this.wrap.dom.innerHTML = '';
  25069. this.wrap.remove();
  25070. }
  25071. },
  25072. // private
  25073. onFirstFocus : function(){
  25074. this.activated = true;
  25075. this.tb.items.each(function(item){
  25076. item.enable();
  25077. });
  25078. if(Ext.isGecko){ // prevent silly gecko errors
  25079. this.win.focus();
  25080. var s = this.win.getSelection();
  25081. if(!s.focusNode || s.focusNode.nodeType != 3){
  25082. var r = s.getRangeAt(0);
  25083. r.selectNodeContents(this.getEditorBody());
  25084. r.collapse(true);
  25085. this.deferFocus();
  25086. }
  25087. try{
  25088. this.execCmd('useCSS', true);
  25089. this.execCmd('styleWithCSS', false);
  25090. }catch(e){}
  25091. }
  25092. this.fireEvent('activate', this);
  25093. },
  25094. // private
  25095. adjustFont: function(btn){
  25096. var adjust = btn.itemId == 'increasefontsize' ? 1 : -1;
  25097. var v = parseInt(this.doc.queryCommandValue('FontSize') || 2, 10);
  25098. if(Ext.isSafari3 || Ext.isAir){
  25099. // Safari 3 values
  25100. // 1 = 10px, 2 = 13px, 3 = 16px, 4 = 18px, 5 = 24px, 6 = 32px
  25101. if(v <= 10){
  25102. v = 1 + adjust;
  25103. }else if(v <= 13){
  25104. v = 2 + adjust;
  25105. }else if(v <= 16){
  25106. v = 3 + adjust;
  25107. }else if(v <= 18){
  25108. v = 4 + adjust;
  25109. }else if(v <= 24){
  25110. v = 5 + adjust;
  25111. }else {
  25112. v = 6 + adjust;
  25113. }
  25114. v = v.constrain(1, 6);
  25115. }else{
  25116. if(Ext.isSafari){ // safari
  25117. adjust *= 2;
  25118. }
  25119. v = Math.max(1, v+adjust) + (Ext.isSafari ? 'px' : 0);
  25120. }
  25121. this.execCmd('FontSize', v);
  25122. },
  25123. // private
  25124. onEditorEvent : function(e){
  25125. this.updateToolbar();
  25126. },
  25127. updateToolbar: function(){
  25128. if(!this.activated){
  25129. this.onFirstFocus();
  25130. return;
  25131. }
  25132. var btns = this.tb.items.map, doc = this.doc;
  25133. if(this.enableFont && !Ext.isSafari2){
  25134. var name = (this.doc.queryCommandValue('FontName')||this.defaultFont).toLowerCase();
  25135. if(name != this.fontSelect.dom.value){
  25136. this.fontSelect.dom.value = name;
  25137. }
  25138. }
  25139. if(this.enableFormat){
  25140. btns.bold.toggle(doc.queryCommandState('bold'));
  25141. btns.italic.toggle(doc.queryCommandState('italic'));
  25142. btns.underline.toggle(doc.queryCommandState('underline'));
  25143. }
  25144. if(this.enableAlignments){
  25145. btns.justifyleft.toggle(doc.queryCommandState('justifyleft'));
  25146. btns.justifycenter.toggle(doc.queryCommandState('justifycenter'));
  25147. btns.justifyright.toggle(doc.queryCommandState('justifyright'));
  25148. }
  25149. if(!Ext.isSafari2 && this.enableLists){
  25150. btns.insertorderedlist.toggle(doc.queryCommandState('insertorderedlist'));
  25151. btns.insertunorderedlist.toggle(doc.queryCommandState('insertunorderedlist'));
  25152. }
  25153. Ext.menu.MenuMgr.hideAll();
  25154. this.syncValue();
  25155. },
  25156. // private
  25157. relayBtnCmd : function(btn){
  25158. this.relayCmd(btn.itemId);
  25159. },
  25160. relayCmd : function(cmd, value){
  25161. (function(){
  25162. this.focus();
  25163. this.execCmd(cmd, value);
  25164. this.updateToolbar();
  25165. }).defer(10, this);
  25166. },
  25167. execCmd : function(cmd, value){
  25168. this.doc.execCommand(cmd, false, value === undefined ? null : value);
  25169. this.syncValue();
  25170. },
  25171. // private
  25172. applyCommand : function(e){
  25173. if(e.ctrlKey){
  25174. var c = e.getCharCode(), cmd;
  25175. if(c > 0){
  25176. c = String.fromCharCode(c);
  25177. switch(c){
  25178. case 'b':
  25179. cmd = 'bold';
  25180. break;
  25181. case 'i':
  25182. cmd = 'italic';
  25183. break;
  25184. case 'u':
  25185. cmd = 'underline';
  25186. break;
  25187. }
  25188. if(cmd){
  25189. this.win.focus();
  25190. this.execCmd(cmd);
  25191. this.deferFocus();
  25192. e.preventDefault();
  25193. }
  25194. }
  25195. }
  25196. },
  25197. insertAtCursor : function(text){
  25198. if(!this.activated){
  25199. return;
  25200. }
  25201. if(Ext.isIE){
  25202. this.win.focus();
  25203. var r = this.doc.selection.createRange();
  25204. if(r){
  25205. r.collapse(true);
  25206. r.pasteHTML(text);
  25207. this.syncValue();
  25208. this.deferFocus();
  25209. }
  25210. }else if(Ext.isGecko || Ext.isOpera){
  25211. this.win.focus();
  25212. this.execCmd('InsertHTML', text);
  25213. this.deferFocus();
  25214. }else if(Ext.isSafari){
  25215. this.execCmd('InsertText', text);
  25216. this.deferFocus();
  25217. }
  25218. },
  25219. // private
  25220. fixKeys : function(){ // load time branching for fastest keydown performance
  25221. if(Ext.isIE){
  25222. return function(e){
  25223. var k = e.getKey(), r;
  25224. if(k == e.TAB){
  25225. e.stopEvent();
  25226. r = this.doc.selection.createRange();
  25227. if(r){
  25228. r.collapse(true);
  25229. r.pasteHTML('&nbsp;&nbsp;&nbsp;&nbsp;');
  25230. this.deferFocus();
  25231. }
  25232. }else if(k == e.ENTER){
  25233. r = this.doc.selection.createRange();
  25234. if(r){
  25235. var target = r.parentElement();
  25236. if(!target || target.tagName.toLowerCase() != 'li'){
  25237. e.stopEvent();
  25238. r.pasteHTML('<br />');
  25239. r.collapse(false);
  25240. r.select();
  25241. }
  25242. }
  25243. }
  25244. };
  25245. }else if(Ext.isOpera){
  25246. return function(e){
  25247. var k = e.getKey();
  25248. if(k == e.TAB){
  25249. e.stopEvent();
  25250. this.win.focus();
  25251. this.execCmd('InsertHTML','&nbsp;&nbsp;&nbsp;&nbsp;');
  25252. this.deferFocus();
  25253. }
  25254. };
  25255. }else if(Ext.isSafari){
  25256. return function(e){
  25257. var k = e.getKey();
  25258. if(k == e.TAB){
  25259. e.stopEvent();
  25260. this.execCmd('InsertText','\t');
  25261. this.deferFocus();
  25262. }
  25263. };
  25264. }
  25265. }(),
  25266. getToolbar : function(){
  25267. return this.tb;
  25268. },
  25269. buttonTips : {
  25270. bold : {
  25271. title: 'Bold (Ctrl+B)',
  25272. text: 'Make the selected text bold.',
  25273. cls: 'x-html-editor-tip'
  25274. },
  25275. italic : {
  25276. title: 'Italic (Ctrl+I)',
  25277. text: 'Make the selected text italic.',
  25278. cls: 'x-html-editor-tip'
  25279. },
  25280. underline : {
  25281. title: 'Underline (Ctrl+U)',
  25282. text: 'Underline the selected text.',
  25283. cls: 'x-html-editor-tip'
  25284. },
  25285. increasefontsize : {
  25286. title: 'Grow Text',
  25287. text: 'Increase the font size.',
  25288. cls: 'x-html-editor-tip'
  25289. },
  25290. decreasefontsize : {
  25291. title: 'Shrink Text',
  25292. text: 'Decrease the font size.',
  25293. cls: 'x-html-editor-tip'
  25294. },
  25295. backcolor : {
  25296. title: 'Text Highlight Color',
  25297. text: 'Change the background color of the selected text.',
  25298. cls: 'x-html-editor-tip'
  25299. },
  25300. forecolor : {
  25301. title: 'Font Color',
  25302. text: 'Change the color of the selected text.',
  25303. cls: 'x-html-editor-tip'
  25304. },
  25305. justifyleft : {
  25306. title: 'Align Text Left',
  25307. text: 'Align text to the left.',
  25308. cls: 'x-html-editor-tip'
  25309. },
  25310. justifycenter : {
  25311. title: 'Center Text',
  25312. text: 'Center text in the editor.',
  25313. cls: 'x-html-editor-tip'
  25314. },
  25315. justifyright : {
  25316. title: 'Align Text Right',
  25317. text: 'Align text to the right.',
  25318. cls: 'x-html-editor-tip'
  25319. },
  25320. insertunorderedlist : {
  25321. title: 'Bullet List',
  25322. text: 'Start a bulleted list.',
  25323. cls: 'x-html-editor-tip'
  25324. },
  25325. insertorderedlist : {
  25326. title: 'Numbered List',
  25327. text: 'Start a numbered list.',
  25328. cls: 'x-html-editor-tip'
  25329. },
  25330. createlink : {
  25331. title: 'Hyperlink',
  25332. text: 'Make the selected text a hyperlink.',
  25333. cls: 'x-html-editor-tip'
  25334. },
  25335. sourceedit : {
  25336. title: 'Source Edit',
  25337. text: 'Switch to source editing mode.',
  25338. cls: 'x-html-editor-tip'
  25339. }
  25340. }
  25341. // hide stuff that is not compatible
  25342. });
  25343. Ext.reg('htmleditor', Ext.form.HtmlEditor);
  25344. Ext.form.TimeField = Ext.extend(Ext.form.ComboBox, {
  25345. minValue : null,
  25346. maxValue : null,
  25347. minText : "The time in this field must be equal to or after {0}",
  25348. maxText : "The time in this field must be equal to or before {0}",
  25349. invalidText : "{0} is not a valid time",
  25350. format : "g:i A",
  25351. altFormats : "g:ia|g:iA|g:i a|g:i A|h:i|g:i|H:i|ga|ha|gA|h a|g a|g A|gi|hi|gia|hia|g|H",
  25352. increment: 15,
  25353. // private override
  25354. mode: 'local',
  25355. // private override
  25356. triggerAction: 'all',
  25357. // private override
  25358. typeAhead: false,
  25359. // private - This is the date to use when generating time values in the absence of either minValue
  25360. // or maxValue. Using the current date causes DST issues on DST boundary dates, so this is an
  25361. // arbitrary "safe" date that can be any date aside from DST boundary dates.
  25362. initDate: '1/1/2008',
  25363. // private
  25364. initComponent : function(){
  25365. Ext.form.TimeField.superclass.initComponent.call(this);
  25366. if(typeof this.minValue == "string"){
  25367. this.minValue = this.parseDate(this.minValue);
  25368. }
  25369. if(typeof this.maxValue == "string"){
  25370. this.maxValue = this.parseDate(this.maxValue);
  25371. }
  25372. if(!this.store){
  25373. var min = this.parseDate(this.minValue);
  25374. if(!min){
  25375. min = new Date(this.initDate).clearTime();
  25376. }
  25377. var max = this.parseDate(this.maxValue);
  25378. if(!max){
  25379. max = new Date(this.initDate).clearTime().add('mi', (24 * 60) - 1);
  25380. }
  25381. var times = [];
  25382. while(min <= max){
  25383. times.push([min.dateFormat(this.format)]);
  25384. min = min.add('mi', this.increment);
  25385. }
  25386. this.store = new Ext.data.SimpleStore({
  25387. fields: ['text'],
  25388. data : times
  25389. });
  25390. this.displayField = 'text';
  25391. }
  25392. },
  25393. // inherited docs
  25394. getValue : function(){
  25395. var v = Ext.form.TimeField.superclass.getValue.call(this);
  25396. return this.formatDate(this.parseDate(v)) || '';
  25397. },
  25398. // inherited docs
  25399. setValue : function(value){
  25400. Ext.form.TimeField.superclass.setValue.call(this, this.formatDate(this.parseDate(value)));
  25401. },
  25402. // private overrides
  25403. validateValue : Ext.form.DateField.prototype.validateValue,
  25404. parseDate : Ext.form.DateField.prototype.parseDate,
  25405. formatDate : Ext.form.DateField.prototype.formatDate,
  25406. // private
  25407. beforeBlur : function(){
  25408. var v = this.parseDate(this.getRawValue());
  25409. if(v){
  25410. this.setValue(v.dateFormat(this.format));
  25411. }
  25412. }
  25413. });
  25414. Ext.reg('timefield', Ext.form.TimeField);
  25415. Ext.form.Label = Ext.extend(Ext.BoxComponent, {
  25416. // private
  25417. onRender : function(ct, position){
  25418. if(!this.el){
  25419. this.el = document.createElement('label');
  25420. this.el.id = this.getId();
  25421. this.el.innerHTML = this.text ? Ext.util.Format.htmlEncode(this.text) : (this.html || '');
  25422. if(this.forId){
  25423. this.el.setAttribute('for', this.forId);
  25424. }
  25425. }
  25426. Ext.form.Label.superclass.onRender.call(this, ct, position);
  25427. },
  25428. setText: function(t, encode){
  25429. this.text = t;
  25430. if(this.rendered){
  25431. this.el.dom.innerHTML = encode !== false ? Ext.util.Format.htmlEncode(t) : t;
  25432. }
  25433. return this;
  25434. }
  25435. });
  25436. Ext.reg('label', Ext.form.Label);
  25437. Ext.form.Action = function(form, options){
  25438. this.form = form;
  25439. this.options = options || {};
  25440. };
  25441. Ext.form.Action.CLIENT_INVALID = 'client';
  25442. Ext.form.Action.SERVER_INVALID = 'server';
  25443. Ext.form.Action.CONNECT_FAILURE = 'connect';
  25444. Ext.form.Action.LOAD_FAILURE = 'load';
  25445. Ext.form.Action.prototype = {
  25446. type : 'default',
  25447. // interface method
  25448. run : function(options){
  25449. },
  25450. // interface method
  25451. success : function(response){
  25452. },
  25453. // interface method
  25454. handleResponse : function(response){
  25455. },
  25456. // default connection failure
  25457. failure : function(response){
  25458. this.response = response;
  25459. this.failureType = Ext.form.Action.CONNECT_FAILURE;
  25460. this.form.afterAction(this, false);
  25461. },
  25462. // private
  25463. processResponse : function(response){
  25464. this.response = response;
  25465. if(!response.responseText){
  25466. return true;
  25467. }
  25468. this.result = this.handleResponse(response);
  25469. return this.result;
  25470. },
  25471. // utility functions used internally
  25472. getUrl : function(appendParams){
  25473. var url = this.options.url || this.form.url || this.form.el.dom.action;
  25474. if(appendParams){
  25475. var p = this.getParams();
  25476. if(p){
  25477. url += (url.indexOf('?') != -1 ? '&' : '?') + p;
  25478. }
  25479. }
  25480. return url;
  25481. },
  25482. // private
  25483. getMethod : function(){
  25484. return (this.options.method || this.form.method || this.form.el.dom.method || 'POST').toUpperCase();
  25485. },
  25486. // private
  25487. getParams : function(){
  25488. var bp = this.form.baseParams;
  25489. var p = this.options.params;
  25490. if(p){
  25491. if(typeof p == "object"){
  25492. p = Ext.urlEncode(Ext.applyIf(p, bp));
  25493. }else if(typeof p == 'string' && bp){
  25494. p += '&' + Ext.urlEncode(bp);
  25495. }
  25496. }else if(bp){
  25497. p = Ext.urlEncode(bp);
  25498. }
  25499. return p;
  25500. },
  25501. // private
  25502. createCallback : function(opts){
  25503. var opts = opts || {};
  25504. return {
  25505. success: this.success,
  25506. failure: this.failure,
  25507. scope: this,
  25508. timeout: (opts.timeout*1000) || (this.form.timeout*1000),
  25509. upload: this.form.fileUpload ? this.success : undefined
  25510. };
  25511. }
  25512. };
  25513. Ext.form.Action.Submit = function(form, options){
  25514. Ext.form.Action.Submit.superclass.constructor.call(this, form, options);
  25515. };
  25516. Ext.extend(Ext.form.Action.Submit, Ext.form.Action, {
  25517. type : 'submit',
  25518. // private
  25519. run : function(){
  25520. var o = this.options;
  25521. var method = this.getMethod();
  25522. var isGet = method == 'GET';
  25523. if(o.clientValidation === false || this.form.isValid()){
  25524. Ext.Ajax.request(Ext.apply(this.createCallback(o), {
  25525. form:this.form.el.dom,
  25526. url:this.getUrl(isGet),
  25527. method: method,
  25528. headers: o.headers,
  25529. params:!isGet ? this.getParams() : null,
  25530. isUpload: this.form.fileUpload
  25531. }));
  25532. }else if (o.clientValidation !== false){ // client validation failed
  25533. this.failureType = Ext.form.Action.CLIENT_INVALID;
  25534. this.form.afterAction(this, false);
  25535. }
  25536. },
  25537. // private
  25538. success : function(response){
  25539. var result = this.processResponse(response);
  25540. if(result === true || result.success){
  25541. this.form.afterAction(this, true);
  25542. return;
  25543. }
  25544. if(result.errors){
  25545. this.form.markInvalid(result.errors);
  25546. this.failureType = Ext.form.Action.SERVER_INVALID;
  25547. }
  25548. this.form.afterAction(this, false);
  25549. },
  25550. // private
  25551. handleResponse : function(response){
  25552. if(this.form.errorReader){
  25553. var rs = this.form.errorReader.read(response);
  25554. var errors = [];
  25555. if(rs.records){
  25556. for(var i = 0, len = rs.records.length; i < len; i++) {
  25557. var r = rs.records[i];
  25558. errors[i] = r.data;
  25559. }
  25560. }
  25561. if(errors.length < 1){
  25562. errors = null;
  25563. }
  25564. return {
  25565. success : rs.success,
  25566. errors : errors
  25567. };
  25568. }
  25569. return Ext.decode(response.responseText);
  25570. }
  25571. });
  25572. Ext.form.Action.Load = function(form, options){
  25573. Ext.form.Action.Load.superclass.constructor.call(this, form, options);
  25574. this.reader = this.form.reader;
  25575. };
  25576. Ext.extend(Ext.form.Action.Load, Ext.form.Action, {
  25577. // private
  25578. type : 'load',
  25579. // private
  25580. run : function(){
  25581. Ext.Ajax.request(Ext.apply(
  25582. this.createCallback(this.options), {
  25583. method:this.getMethod(),
  25584. url:this.getUrl(false),
  25585. headers: this.options.headers,
  25586. params:this.getParams()
  25587. }));
  25588. },
  25589. // private
  25590. success : function(response){
  25591. var result = this.processResponse(response);
  25592. if(result === true || !result.success || !result.data){
  25593. this.failureType = Ext.form.Action.LOAD_FAILURE;
  25594. this.form.afterAction(this, false);
  25595. return;
  25596. }
  25597. this.form.clearInvalid();
  25598. this.form.setValues(result.data);
  25599. this.form.afterAction(this, true);
  25600. },
  25601. // private
  25602. handleResponse : function(response){
  25603. if(this.form.reader){
  25604. var rs = this.form.reader.read(response);
  25605. var data = rs.records && rs.records[0] ? rs.records[0].data : null;
  25606. return {
  25607. success : rs.success,
  25608. data : data
  25609. };
  25610. }
  25611. return Ext.decode(response.responseText);
  25612. }
  25613. });
  25614. Ext.form.Action.ACTION_TYPES = {
  25615. 'load' : Ext.form.Action.Load,
  25616. 'submit' : Ext.form.Action.Submit
  25617. };
  25618. Ext.form.VTypes = function(){
  25619. // closure these in so they are only created once.
  25620. var alpha = /^[a-zA-Z_]+$/;
  25621. var alphanum = /^[a-zA-Z0-9_]+$/;
  25622. var email = /^([\w]+)(\.[\w]+)*@([\w\-]+\.){1,5}([A-Za-z]){2,4}$/;
  25623. var url = /(((https?)|(ftp)):\/\/([\-\w]+\.)+\w{2,3}(\/[%\-\w]+(\.\w{2,})?)*(([\w\-\.\?\\\/+@&#;`~=%!]*)(\.\w{2,})?)*\/?)/i;
  25624. // All these messages and functions are configurable
  25625. return {
  25626. 'email' : function(v){
  25627. return email.test(v);
  25628. },
  25629. 'emailText' : 'This field should be an e-mail address in the format "user@domain.com"',
  25630. 'emailMask' : /[a-z0-9_\.\-@]/i,
  25631. 'url' : function(v){
  25632. return url.test(v);
  25633. },
  25634. 'urlText' : 'This field should be a URL in the format "http:/'+'/www.domain.com"',
  25635. 'alpha' : function(v){
  25636. return alpha.test(v);
  25637. },
  25638. 'alphaText' : 'This field should only contain letters and _',
  25639. 'alphaMask' : /[a-z_]/i,
  25640. 'alphanum' : function(v){
  25641. return alphanum.test(v);
  25642. },
  25643. 'alphanumText' : 'This field should only contain letters, numbers and _',
  25644. 'alphanumMask' : /[a-z0-9_]/i
  25645. };
  25646. }();
  25647. Ext.grid.GridPanel = Ext.extend(Ext.Panel, {
  25648. ddText : "{0} selected row{1}",
  25649. minColumnWidth : 25,
  25650. trackMouseOver : true,
  25651. enableDragDrop : false,
  25652. enableColumnMove : true,
  25653. enableColumnHide : true,
  25654. enableHdMenu : true,
  25655. stripeRows : false,
  25656. autoExpandColumn : false,
  25657. autoExpandMin : 50,
  25658. autoExpandMax : 1000,
  25659. view : null,
  25660. loadMask : false,
  25661. deferRowRender : true,
  25662. // private
  25663. rendered : false,
  25664. // private
  25665. viewReady: false,
  25666. stateEvents: ["columnmove", "columnresize", "sortchange"],
  25667. // private
  25668. initComponent : function(){
  25669. Ext.grid.GridPanel.superclass.initComponent.call(this);
  25670. // override any provided value since it isn't valid
  25671. this.autoScroll = false;
  25672. this.autoWidth = false;
  25673. if(Ext.isArray(this.columns)){
  25674. this.colModel = new Ext.grid.ColumnModel(this.columns);
  25675. delete this.columns;
  25676. }
  25677. // check and correct shorthanded configs
  25678. if(this.ds){
  25679. this.store = this.ds;
  25680. delete this.ds;
  25681. }
  25682. if(this.cm){
  25683. this.colModel = this.cm;
  25684. delete this.cm;
  25685. }
  25686. if(this.sm){
  25687. this.selModel = this.sm;
  25688. delete this.sm;
  25689. }
  25690. this.store = Ext.StoreMgr.lookup(this.store);
  25691. this.addEvents(
  25692. // raw events
  25693. "click",
  25694. "dblclick",
  25695. "contextmenu",
  25696. "mousedown",
  25697. "mouseup",
  25698. "mouseover",
  25699. "mouseout",
  25700. "keypress",
  25701. "keydown",
  25702. // custom events
  25703. "cellmousedown",
  25704. "rowmousedown",
  25705. "headermousedown",
  25706. "cellclick",
  25707. "celldblclick",
  25708. "rowclick",
  25709. "rowdblclick",
  25710. "headerclick",
  25711. "headerdblclick",
  25712. "rowcontextmenu",
  25713. "cellcontextmenu",
  25714. "headercontextmenu",
  25715. "bodyscroll",
  25716. "columnresize",
  25717. "columnmove",
  25718. "sortchange"
  25719. );
  25720. },
  25721. // private
  25722. onRender : function(ct, position){
  25723. Ext.grid.GridPanel.superclass.onRender.apply(this, arguments);
  25724. var c = this.body;
  25725. this.el.addClass('x-grid-panel');
  25726. var view = this.getView();
  25727. view.init(this);
  25728. c.on("mousedown", this.onMouseDown, this);
  25729. c.on("click", this.onClick, this);
  25730. c.on("dblclick", this.onDblClick, this);
  25731. c.on("contextmenu", this.onContextMenu, this);
  25732. c.on("keydown", this.onKeyDown, this);
  25733. this.relayEvents(c, ["mousedown","mouseup","mouseover","mouseout","keypress"]);
  25734. this.getSelectionModel().init(this);
  25735. this.view.render();
  25736. },
  25737. // private
  25738. initEvents : function(){
  25739. Ext.grid.GridPanel.superclass.initEvents.call(this);
  25740. if(this.loadMask){
  25741. this.loadMask = new Ext.LoadMask(this.bwrap,
  25742. Ext.apply({store:this.store}, this.loadMask));
  25743. }
  25744. },
  25745. initStateEvents : function(){
  25746. Ext.grid.GridPanel.superclass.initStateEvents.call(this);
  25747. this.colModel.on('hiddenchange', this.saveState, this, {delay: 100});
  25748. },
  25749. applyState : function(state){
  25750. var cm = this.colModel;
  25751. var cs = state.columns;
  25752. if(cs){
  25753. for(var i = 0, len = cs.length; i < len; i++){
  25754. var s = cs[i];
  25755. var c = cm.getColumnById(s.id);
  25756. if(c){
  25757. c.hidden = s.hidden;
  25758. c.width = s.width;
  25759. var oldIndex = cm.getIndexById(s.id);
  25760. if(oldIndex != i){
  25761. cm.moveColumn(oldIndex, i);
  25762. }
  25763. }
  25764. }
  25765. }
  25766. if(state.sort){
  25767. this.store[this.store.remoteSort ? 'setDefaultSort' : 'sort'](state.sort.field, state.sort.direction);
  25768. }
  25769. },
  25770. getState : function(){
  25771. var o = {columns: []};
  25772. for(var i = 0, c; c = this.colModel.config[i]; i++){
  25773. o.columns[i] = {
  25774. id: c.id,
  25775. width: c.width
  25776. };
  25777. if(c.hidden){
  25778. o.columns[i].hidden = true;
  25779. }
  25780. }
  25781. var ss = this.store.getSortState();
  25782. if(ss){
  25783. o.sort = ss;
  25784. }
  25785. return o;
  25786. },
  25787. // private
  25788. afterRender : function(){
  25789. Ext.grid.GridPanel.superclass.afterRender.call(this);
  25790. this.view.layout();
  25791. if(this.deferRowRender){
  25792. this.view.afterRender.defer(10, this.view);
  25793. }else{
  25794. this.view.afterRender();
  25795. }
  25796. this.viewReady = true;
  25797. },
  25798. reconfigure : function(store, colModel){
  25799. if(this.loadMask){
  25800. this.loadMask.destroy();
  25801. this.loadMask = new Ext.LoadMask(this.bwrap,
  25802. Ext.apply({store:store}, this.initialConfig.loadMask));
  25803. }
  25804. this.view.bind(store, colModel);
  25805. this.store = store;
  25806. this.colModel = colModel;
  25807. if(this.rendered){
  25808. this.view.refresh(true);
  25809. }
  25810. },
  25811. // private
  25812. onKeyDown : function(e){
  25813. this.fireEvent("keydown", e);
  25814. },
  25815. // private
  25816. onDestroy : function(){
  25817. if(this.rendered){
  25818. if(this.loadMask){
  25819. this.loadMask.destroy();
  25820. }
  25821. var c = this.body;
  25822. c.removeAllListeners();
  25823. this.view.destroy();
  25824. c.update("");
  25825. }
  25826. this.colModel.purgeListeners();
  25827. Ext.grid.GridPanel.superclass.onDestroy.call(this);
  25828. },
  25829. // private
  25830. processEvent : function(name, e){
  25831. this.fireEvent(name, e);
  25832. var t = e.getTarget();
  25833. var v = this.view;
  25834. var header = v.findHeaderIndex(t);
  25835. if(header !== false){
  25836. this.fireEvent("header" + name, this, header, e);
  25837. }else{
  25838. var row = v.findRowIndex(t);
  25839. var cell = v.findCellIndex(t);
  25840. if(row !== false){
  25841. this.fireEvent("row" + name, this, row, e);
  25842. if(cell !== false){
  25843. this.fireEvent("cell" + name, this, row, cell, e);
  25844. }
  25845. }
  25846. }
  25847. },
  25848. // private
  25849. onClick : function(e){
  25850. this.processEvent("click", e);
  25851. },
  25852. // private
  25853. onMouseDown : function(e){
  25854. this.processEvent("mousedown", e);
  25855. },
  25856. // private
  25857. onContextMenu : function(e, t){
  25858. this.processEvent("contextmenu", e);
  25859. },
  25860. // private
  25861. onDblClick : function(e){
  25862. this.processEvent("dblclick", e);
  25863. },
  25864. // private
  25865. walkCells : function(row, col, step, fn, scope){
  25866. var cm = this.colModel, clen = cm.getColumnCount();
  25867. var ds = this.store, rlen = ds.getCount(), first = true;
  25868. if(step < 0){
  25869. if(col < 0){
  25870. row--;
  25871. first = false;
  25872. }
  25873. while(row >= 0){
  25874. if(!first){
  25875. col = clen-1;
  25876. }
  25877. first = false;
  25878. while(col >= 0){
  25879. if(fn.call(scope || this, row, col, cm) === true){
  25880. return [row, col];
  25881. }
  25882. col--;
  25883. }
  25884. row--;
  25885. }
  25886. } else {
  25887. if(col >= clen){
  25888. row++;
  25889. first = false;
  25890. }
  25891. while(row < rlen){
  25892. if(!first){
  25893. col = 0;
  25894. }
  25895. first = false;
  25896. while(col < clen){
  25897. if(fn.call(scope || this, row, col, cm) === true){
  25898. return [row, col];
  25899. }
  25900. col++;
  25901. }
  25902. row++;
  25903. }
  25904. }
  25905. return null;
  25906. },
  25907. // private
  25908. getSelections : function(){
  25909. return this.selModel.getSelections();
  25910. },
  25911. // private
  25912. onResize : function(){
  25913. Ext.grid.GridPanel.superclass.onResize.apply(this, arguments);
  25914. if(this.viewReady){
  25915. this.view.layout();
  25916. }
  25917. },
  25918. getGridEl : function(){
  25919. return this.body;
  25920. },
  25921. // private for compatibility, overridden by editor grid
  25922. stopEditing : Ext.emptyFn,
  25923. getSelectionModel : function(){
  25924. if(!this.selModel){
  25925. this.selModel = new Ext.grid.RowSelectionModel(
  25926. this.disableSelection ? {selectRow: Ext.emptyFn} : null);
  25927. }
  25928. return this.selModel;
  25929. },
  25930. getStore : function(){
  25931. return this.store;
  25932. },
  25933. getColumnModel : function(){
  25934. return this.colModel;
  25935. },
  25936. getView : function(){
  25937. if(!this.view){
  25938. this.view = new Ext.grid.GridView(this.viewConfig);
  25939. }
  25940. return this.view;
  25941. },
  25942. getDragDropText : function(){
  25943. var count = this.selModel.getCount();
  25944. return String.format(this.ddText, count, count == 1 ? '' : 's');
  25945. }
  25946. });
  25947. Ext.reg('grid', Ext.grid.GridPanel);
  25948. Ext.grid.GridView = function(config){
  25949. Ext.apply(this, config);
  25950. // These events are only used internally by the grid components
  25951. this.addEvents(
  25952. "beforerowremoved",
  25953. "beforerowsinserted",
  25954. "beforerefresh",
  25955. "rowremoved",
  25956. "rowsinserted",
  25957. "rowupdated",
  25958. "refresh"
  25959. );
  25960. Ext.grid.GridView.superclass.constructor.call(this);
  25961. };
  25962. Ext.extend(Ext.grid.GridView, Ext.util.Observable, {
  25963. deferEmptyText: true,
  25964. scrollOffset: 19,
  25965. autoFill: false,
  25966. forceFit: false,
  25967. sortClasses : ["sort-asc", "sort-desc"],
  25968. sortAscText : "Sort Ascending",
  25969. sortDescText : "Sort Descending",
  25970. columnsText : "Columns",
  25971. // private
  25972. borderWidth: 2,
  25973. tdClass: 'x-grid3-cell',
  25974. hdCls: 'x-grid3-hd',
  25975. cellSelectorDepth: 4,
  25976. rowSelectorDepth: 10,
  25977. cellSelector: 'td.x-grid3-cell',
  25978. rowSelector: 'div.x-grid3-row',
  25979. // private
  25980. initTemplates : function(){
  25981. var ts = this.templates || {};
  25982. if(!ts.master){
  25983. ts.master = new Ext.Template(
  25984. '<div class="x-grid3" hidefocus="true">',
  25985. '<div class="x-grid3-viewport">',
  25986. '<div class="x-grid3-header"><div class="x-grid3-header-inner"><div class="x-grid3-header-offset">{header}</div></div><div class="x-clear"></div></div>',
  25987. '<div class="x-grid3-scroller"><div class="x-grid3-body">{body}</div><a href="#" class="x-grid3-focus" tabIndex="-1"></a></div>',
  25988. "</div>",
  25989. '<div class="x-grid3-resize-marker">&#160;</div>',
  25990. '<div class="x-grid3-resize-proxy">&#160;</div>',
  25991. "</div>"
  25992. );
  25993. }
  25994. if(!ts.header){
  25995. ts.header = new Ext.Template(
  25996. '<table border="0" cellspacing="0" cellpadding="0" style="{tstyle}">',
  25997. '<thead><tr class="x-grid3-hd-row">{cells}</tr></thead>',
  25998. "</table>"
  25999. );
  26000. }
  26001. if(!ts.hcell){
  26002. ts.hcell = new Ext.Template(
  26003. '<td class="x-grid3-hd x-grid3-cell x-grid3-td-{id} {css}" style="{style}"><div {tooltip} {attr} class="x-grid3-hd-inner x-grid3-hd-{id}" unselectable="on" style="{istyle}">', this.grid.enableHdMenu ? '<a class="x-grid3-hd-btn" href="#"></a>' : '',
  26004. '{value}<img class="x-grid3-sort-icon" src="', Ext.BLANK_IMAGE_URL, '" />',
  26005. "</div></td>"
  26006. );
  26007. }
  26008. if(!ts.body){
  26009. ts.body = new Ext.Template('{rows}');
  26010. }
  26011. if(!ts.row){
  26012. ts.row = new Ext.Template(
  26013. '<div class="x-grid3-row {alt}" style="{tstyle}"><table class="x-grid3-row-table" border="0" cellspacing="0" cellpadding="0" style="{tstyle}">',
  26014. '<tbody><tr>{cells}</tr>',
  26015. (this.enableRowBody ? '<tr class="x-grid3-row-body-tr" style="{bodyStyle}"><td colspan="{cols}" class="x-grid3-body-cell" tabIndex="0" hidefocus="on"><div class="x-grid3-row-body">{body}</div></td></tr>' : ''),
  26016. '</tbody></table></div>'
  26017. );
  26018. }
  26019. if(!ts.cell){
  26020. ts.cell = new Ext.Template(
  26021. '<td class="x-grid3-col x-grid3-cell x-grid3-td-{id} {css}" style="{style}" tabIndex="0" {cellAttr}>',
  26022. '<div class="x-grid3-cell-inner x-grid3-col-{id}" unselectable="on" {attr}>{value}</div>',
  26023. "</td>"
  26024. );
  26025. }
  26026. for(var k in ts){
  26027. var t = ts[k];
  26028. if(t && typeof t.compile == 'function' && !t.compiled){
  26029. t.disableFormats = true;
  26030. t.compile();
  26031. }
  26032. }
  26033. this.templates = ts;
  26034. this.colRe = new RegExp("x-grid3-td-([^\\s]+)", "");
  26035. },
  26036. // private
  26037. fly : function(el){
  26038. if(!this._flyweight){
  26039. this._flyweight = new Ext.Element.Flyweight(document.body);
  26040. }
  26041. this._flyweight.dom = el;
  26042. return this._flyweight;
  26043. },
  26044. // private
  26045. getEditorParent : function(){
  26046. return this.scroller.dom;
  26047. },
  26048. // private
  26049. initElements : function(){
  26050. var E = Ext.Element;
  26051. var el = this.grid.getGridEl().dom.firstChild;
  26052. var cs = el.childNodes;
  26053. this.el = new E(el);
  26054. this.mainWrap = new E(cs[0]);
  26055. this.mainHd = new E(this.mainWrap.dom.firstChild);
  26056. if(this.grid.hideHeaders){
  26057. this.mainHd.setDisplayed(false);
  26058. }
  26059. this.innerHd = this.mainHd.dom.firstChild;
  26060. this.scroller = new E(this.mainWrap.dom.childNodes[1]);
  26061. if(this.forceFit){
  26062. this.scroller.setStyle('overflow-x', 'hidden');
  26063. }
  26064. this.mainBody = new E(this.scroller.dom.firstChild);
  26065. this.focusEl = new E(this.scroller.dom.childNodes[1]);
  26066. this.focusEl.swallowEvent("click", true);
  26067. this.resizeMarker = new E(cs[1]);
  26068. this.resizeProxy = new E(cs[2]);
  26069. },
  26070. // private
  26071. getRows : function(){
  26072. return this.hasRows() ? this.mainBody.dom.childNodes : [];
  26073. },
  26074. // finder methods, used with delegation
  26075. // private
  26076. findCell : function(el){
  26077. if(!el){
  26078. return false;
  26079. }
  26080. return this.fly(el).findParent(this.cellSelector, this.cellSelectorDepth);
  26081. },
  26082. // private
  26083. findCellIndex : function(el, requiredCls){
  26084. var cell = this.findCell(el);
  26085. if(cell && (!requiredCls || this.fly(cell).hasClass(requiredCls))){
  26086. return this.getCellIndex(cell);
  26087. }
  26088. return false;
  26089. },
  26090. // private
  26091. getCellIndex : function(el){
  26092. if(el){
  26093. var m = el.className.match(this.colRe);
  26094. if(m && m[1]){
  26095. return this.cm.getIndexById(m[1]);
  26096. }
  26097. }
  26098. return false;
  26099. },
  26100. // private
  26101. findHeaderCell : function(el){
  26102. var cell = this.findCell(el);
  26103. return cell && this.fly(cell).hasClass(this.hdCls) ? cell : null;
  26104. },
  26105. // private
  26106. findHeaderIndex : function(el){
  26107. return this.findCellIndex(el, this.hdCls);
  26108. },
  26109. findRow : function(el){
  26110. if(!el){
  26111. return false;
  26112. }
  26113. return this.fly(el).findParent(this.rowSelector, this.rowSelectorDepth);
  26114. },
  26115. findRowIndex : function(el){
  26116. var r = this.findRow(el);
  26117. return r ? r.rowIndex : false;
  26118. },
  26119. // getter methods for fetching elements dynamically in the grid
  26120. getRow : function(row){
  26121. return this.getRows()[row];
  26122. },
  26123. getCell : function(row, col){
  26124. return this.getRow(row).getElementsByTagName('td')[col];
  26125. },
  26126. getHeaderCell : function(index){
  26127. return this.mainHd.dom.getElementsByTagName('td')[index];
  26128. },
  26129. // manipulating elements
  26130. // private - use getRowClass to apply custom row classes
  26131. addRowClass : function(row, cls){
  26132. var r = this.getRow(row);
  26133. if(r){
  26134. this.fly(r).addClass(cls);
  26135. }
  26136. },
  26137. // private
  26138. removeRowClass : function(row, cls){
  26139. var r = this.getRow(row);
  26140. if(r){
  26141. this.fly(r).removeClass(cls);
  26142. }
  26143. },
  26144. // private
  26145. removeRow : function(row){
  26146. Ext.removeNode(this.getRow(row));
  26147. this.syncFocusEl(row);
  26148. },
  26149. // private
  26150. removeRows : function(firstRow, lastRow){
  26151. var bd = this.mainBody.dom;
  26152. for(var rowIndex = firstRow; rowIndex <= lastRow; rowIndex++){
  26153. Ext.removeNode(bd.childNodes[firstRow]);
  26154. }
  26155. this.syncFocusEl(firstRow);
  26156. },
  26157. // scrolling stuff
  26158. // private
  26159. getScrollState : function(){
  26160. var sb = this.scroller.dom;
  26161. return {left: sb.scrollLeft, top: sb.scrollTop};
  26162. },
  26163. // private
  26164. restoreScroll : function(state){
  26165. var sb = this.scroller.dom;
  26166. sb.scrollLeft = state.left;
  26167. sb.scrollTop = state.top;
  26168. },
  26169. scrollToTop : function(){
  26170. this.scroller.dom.scrollTop = 0;
  26171. this.scroller.dom.scrollLeft = 0;
  26172. },
  26173. // private
  26174. syncScroll : function(){
  26175. this.syncHeaderScroll();
  26176. var mb = this.scroller.dom;
  26177. this.grid.fireEvent("bodyscroll", mb.scrollLeft, mb.scrollTop);
  26178. },
  26179. // private
  26180. syncHeaderScroll : function(){
  26181. var mb = this.scroller.dom;
  26182. this.innerHd.scrollLeft = mb.scrollLeft;
  26183. this.innerHd.scrollLeft = mb.scrollLeft; // second time for IE (1/2 time first fails, other browsers ignore)
  26184. },
  26185. // private
  26186. updateSortIcon : function(col, dir){
  26187. var sc = this.sortClasses;
  26188. var hds = this.mainHd.select('td').removeClass(sc);
  26189. hds.item(col).addClass(sc[dir == "DESC" ? 1 : 0]);
  26190. },
  26191. // private
  26192. updateAllColumnWidths : function(){
  26193. var tw = this.getTotalWidth();
  26194. var clen = this.cm.getColumnCount();
  26195. var ws = [];
  26196. for(var i = 0; i < clen; i++){
  26197. ws[i] = this.getColumnWidth(i);
  26198. }
  26199. this.innerHd.firstChild.firstChild.style.width = tw;
  26200. for(var i = 0; i < clen; i++){
  26201. var hd = this.getHeaderCell(i);
  26202. hd.style.width = ws[i];
  26203. }
  26204. var ns = this.getRows(), row, trow;
  26205. for(var i = 0, len = ns.length; i < len; i++){
  26206. row = ns[i];
  26207. row.style.width = tw;
  26208. if(row.firstChild){
  26209. row.firstChild.style.width = tw;
  26210. trow = row.firstChild.rows[0];
  26211. for (var j = 0; j < clen; j++) {
  26212. trow.childNodes[j].style.width = ws[j];
  26213. }
  26214. }
  26215. }
  26216. this.onAllColumnWidthsUpdated(ws, tw);
  26217. },
  26218. // private
  26219. updateColumnWidth : function(col, width){
  26220. var w = this.getColumnWidth(col);
  26221. var tw = this.getTotalWidth();
  26222. this.innerHd.firstChild.firstChild.style.width = tw;
  26223. var hd = this.getHeaderCell(col);
  26224. hd.style.width = w;
  26225. var ns = this.getRows(), row;
  26226. for(var i = 0, len = ns.length; i < len; i++){
  26227. row = ns[i];
  26228. row.style.width = tw;
  26229. if(row.firstChild){
  26230. row.firstChild.style.width = tw;
  26231. row.firstChild.rows[0].childNodes[col].style.width = w;
  26232. }
  26233. }
  26234. this.onColumnWidthUpdated(col, w, tw);
  26235. },
  26236. // private
  26237. updateColumnHidden : function(col, hidden){
  26238. var tw = this.getTotalWidth();
  26239. this.innerHd.firstChild.firstChild.style.width = tw;
  26240. var display = hidden ? 'none' : '';
  26241. var hd = this.getHeaderCell(col);
  26242. hd.style.display = display;
  26243. var ns = this.getRows(), row;
  26244. for(var i = 0, len = ns.length; i < len; i++){
  26245. row = ns[i];
  26246. row.style.width = tw;
  26247. if(row.firstChild){
  26248. row.firstChild.style.width = tw;
  26249. row.firstChild.rows[0].childNodes[col].style.display = display;
  26250. }
  26251. }
  26252. this.onColumnHiddenUpdated(col, hidden, tw);
  26253. delete this.lastViewWidth; // force recalc
  26254. this.layout();
  26255. },
  26256. // private
  26257. doRender : function(cs, rs, ds, startRow, colCount, stripe){
  26258. var ts = this.templates, ct = ts.cell, rt = ts.row, last = colCount-1;
  26259. var tstyle = 'width:'+this.getTotalWidth()+';';
  26260. // buffers
  26261. var buf = [], cb, c, p = {}, rp = {tstyle: tstyle}, r;
  26262. for(var j = 0, len = rs.length; j < len; j++){
  26263. r = rs[j]; cb = [];
  26264. var rowIndex = (j+startRow);
  26265. for(var i = 0; i < colCount; i++){
  26266. c = cs[i];
  26267. p.id = c.id;
  26268. p.css = i == 0 ? 'x-grid3-cell-first ' : (i == last ? 'x-grid3-cell-last ' : '');
  26269. p.attr = p.cellAttr = "";
  26270. p.value = c.renderer(r.data[c.name], p, r, rowIndex, i, ds);
  26271. p.style = c.style;
  26272. if(p.value == undefined || p.value === "") p.value = "&#160;";
  26273. if(r.dirty && typeof r.modified[c.name] !== 'undefined'){
  26274. p.css += ' x-grid3-dirty-cell';
  26275. }
  26276. cb[cb.length] = ct.apply(p);
  26277. }
  26278. var alt = [];
  26279. if(stripe && ((rowIndex+1) % 2 == 0)){
  26280. alt[0] = "x-grid3-row-alt";
  26281. }
  26282. if(r.dirty){
  26283. alt[1] = " x-grid3-dirty-row";
  26284. }
  26285. rp.cols = colCount;
  26286. if(this.getRowClass){
  26287. alt[2] = this.getRowClass(r, rowIndex, rp, ds);
  26288. }
  26289. rp.alt = alt.join(" ");
  26290. rp.cells = cb.join("");
  26291. buf[buf.length] = rt.apply(rp);
  26292. }
  26293. return buf.join("");
  26294. },
  26295. // private
  26296. processRows : function(startRow, skipStripe){
  26297. if(this.ds.getCount() < 1){
  26298. return;
  26299. }
  26300. skipStripe = skipStripe || !this.grid.stripeRows;
  26301. startRow = startRow || 0;
  26302. var rows = this.getRows();
  26303. var cls = ' x-grid3-row-alt ';
  26304. rows[0].className += ' x-grid3-row-first';
  26305. rows[rows.length - 1].className += ' x-grid3-row-last';
  26306. for(var i = startRow, len = rows.length; i < len; i++){
  26307. var row = rows[i];
  26308. row.rowIndex = i;
  26309. if(!skipStripe){
  26310. var isAlt = ((i+1) % 2 == 0);
  26311. var hasAlt = (' '+row.className + ' ').indexOf(cls) != -1;
  26312. if(isAlt == hasAlt){
  26313. continue;
  26314. }
  26315. if(isAlt){
  26316. row.className += " x-grid3-row-alt";
  26317. }else{
  26318. row.className = row.className.replace("x-grid3-row-alt", "");
  26319. }
  26320. }
  26321. }
  26322. },
  26323. afterRender: function(){
  26324. this.mainBody.dom.innerHTML = this.renderRows();
  26325. this.processRows(0, true);
  26326. if(this.deferEmptyText !== true){
  26327. this.applyEmptyText();
  26328. }
  26329. },
  26330. // private
  26331. renderUI : function(){
  26332. var header = this.renderHeaders();
  26333. var body = this.templates.body.apply({rows:''});
  26334. var html = this.templates.master.apply({
  26335. body: body,
  26336. header: header
  26337. });
  26338. var g = this.grid;
  26339. g.getGridEl().dom.innerHTML = html;
  26340. this.initElements();
  26341. // get mousedowns early
  26342. Ext.fly(this.innerHd).on("click", this.handleHdDown, this);
  26343. this.mainHd.on("mouseover", this.handleHdOver, this);
  26344. this.mainHd.on("mouseout", this.handleHdOut, this);
  26345. this.mainHd.on("mousemove", this.handleHdMove, this);
  26346. this.scroller.on('scroll', this.syncScroll, this);
  26347. if(g.enableColumnResize !== false){
  26348. this.splitZone = new Ext.grid.GridView.SplitDragZone(g, this.mainHd.dom);
  26349. }
  26350. if(g.enableColumnMove){
  26351. this.columnDrag = new Ext.grid.GridView.ColumnDragZone(g, this.innerHd);
  26352. this.columnDrop = new Ext.grid.HeaderDropZone(g, this.mainHd.dom);
  26353. }
  26354. if(g.enableHdMenu !== false){
  26355. if(g.enableColumnHide !== false){
  26356. this.colMenu = new Ext.menu.Menu({id:g.id + "-hcols-menu"});
  26357. this.colMenu.on("beforeshow", this.beforeColMenuShow, this);
  26358. this.colMenu.on("itemclick", this.handleHdMenuClick, this);
  26359. }
  26360. this.hmenu = new Ext.menu.Menu({id: g.id + "-hctx"});
  26361. this.hmenu.add(
  26362. {id:"asc", text: this.sortAscText, cls: "xg-hmenu-sort-asc"},
  26363. {id:"desc", text: this.sortDescText, cls: "xg-hmenu-sort-desc"}
  26364. );
  26365. if(g.enableColumnHide !== false){
  26366. this.hmenu.add('-',
  26367. {id:"columns", text: this.columnsText, menu: this.colMenu, iconCls: 'x-cols-icon'}
  26368. );
  26369. }
  26370. this.hmenu.on("itemclick", this.handleHdMenuClick, this);
  26371. //g.on("headercontextmenu", this.handleHdCtx, this);
  26372. }
  26373. if(g.trackMouseOver){
  26374. this.mainBody.on("mouseover", this.onRowOver, this);
  26375. this.mainBody.on("mouseout", this.onRowOut, this);
  26376. }
  26377. if(g.enableDragDrop || g.enableDrag){
  26378. this.dragZone = new Ext.grid.GridDragZone(g, {
  26379. ddGroup : g.ddGroup || 'GridDD'
  26380. });
  26381. }
  26382. this.updateHeaderSortState();
  26383. },
  26384. // private
  26385. layout : function(){
  26386. if(!this.mainBody){
  26387. return; // not rendered
  26388. }
  26389. var g = this.grid;
  26390. var c = g.getGridEl();
  26391. var csize = c.getSize(true);
  26392. var vw = csize.width;
  26393. if(vw < 20 || csize.height < 20){ // display: none?
  26394. return;
  26395. }
  26396. if(g.autoHeight){
  26397. this.scroller.dom.style.overflow = 'visible';
  26398. if(Ext.isSafari){
  26399. this.scroller.dom.style.position = 'static';
  26400. }
  26401. }else{
  26402. this.el.setSize(csize.width, csize.height);
  26403. var hdHeight = this.mainHd.getHeight();
  26404. var vh = csize.height - (hdHeight);
  26405. this.scroller.setSize(vw, vh);
  26406. if(this.innerHd){
  26407. this.innerHd.style.width = (vw)+'px';
  26408. }
  26409. }
  26410. if(this.forceFit){
  26411. if(this.lastViewWidth != vw){
  26412. this.fitColumns(false, false);
  26413. this.lastViewWidth = vw;
  26414. }
  26415. }else {
  26416. this.autoExpand();
  26417. this.syncHeaderScroll();
  26418. }
  26419. this.onLayout(vw, vh);
  26420. },
  26421. // template functions for subclasses and plugins
  26422. // these functions include precalculated values
  26423. onLayout : function(vw, vh){
  26424. // do nothing
  26425. },
  26426. onColumnWidthUpdated : function(col, w, tw){
  26427. //template method
  26428. this.focusEl.setWidth(tw);
  26429. },
  26430. onAllColumnWidthsUpdated : function(ws, tw){
  26431. //template method
  26432. this.focusEl.setWidth(tw);
  26433. },
  26434. onColumnHiddenUpdated : function(col, hidden, tw){
  26435. // template method
  26436. this.focusEl.setWidth(tw);
  26437. },
  26438. updateColumnText : function(col, text){
  26439. // template method
  26440. },
  26441. afterMove : function(colIndex){
  26442. // template method
  26443. },
  26444. // private
  26445. init: function(grid){
  26446. this.grid = grid;
  26447. this.initTemplates();
  26448. this.initData(grid.store, grid.colModel);
  26449. this.initUI(grid);
  26450. },
  26451. // private
  26452. getColumnId : function(index){
  26453. return this.cm.getColumnId(index);
  26454. },
  26455. // private
  26456. renderHeaders : function(){
  26457. var cm = this.cm, ts = this.templates;
  26458. var ct = ts.hcell;
  26459. var cb = [], sb = [], p = {};
  26460. var len = cm.getColumnCount();
  26461. var last = len - 1;
  26462. for(var i = 0; i < len; i++){
  26463. p.id = cm.getColumnId(i);
  26464. p.value = cm.getColumnHeader(i) || "";
  26465. p.style = this.getColumnStyle(i, true);
  26466. p.tooltip = this.getColumnTooltip(i);
  26467. p.css = i == 0 ? 'x-grid3-cell-first ' : (i == last ? 'x-grid3-cell-last ' : '');
  26468. if(cm.config[i].align == 'right'){
  26469. p.istyle = 'padding-right:16px';
  26470. } else {
  26471. delete p.istyle;
  26472. }
  26473. cb[cb.length] = ct.apply(p);
  26474. }
  26475. return ts.header.apply({cells: cb.join(""), tstyle:'width:'+this.getTotalWidth()+';'});
  26476. },
  26477. // private
  26478. getColumnTooltip : function(i){
  26479. var tt = this.cm.getColumnTooltip(i);
  26480. if(tt){
  26481. if(Ext.QuickTips.isEnabled()){
  26482. return 'ext:qtip="'+tt+'"';
  26483. }else{
  26484. return 'title="'+tt+'"';
  26485. }
  26486. }
  26487. return "";
  26488. },
  26489. // private
  26490. beforeUpdate : function(){
  26491. this.grid.stopEditing(true);
  26492. },
  26493. // private
  26494. updateHeaders : function(){
  26495. this.innerHd.firstChild.innerHTML = this.renderHeaders();
  26496. },
  26497. focusRow : function(row){
  26498. this.focusCell(row, 0, false);
  26499. },
  26500. focusCell : function(row, col, hscroll){
  26501. this.syncFocusEl(this.ensureVisible(row, col, hscroll));
  26502. if(Ext.isGecko){
  26503. this.focusEl.focus();
  26504. }else{
  26505. this.focusEl.focus.defer(1, this.focusEl);
  26506. }
  26507. },
  26508. resolveCell : function(row, col, hscroll){
  26509. if(typeof row != "number"){
  26510. row = row.rowIndex;
  26511. }
  26512. if(!this.ds){
  26513. return null;
  26514. }
  26515. if(row < 0 || row >= this.ds.getCount()){
  26516. return null;
  26517. }
  26518. col = (col !== undefined ? col : 0);
  26519. var rowEl = this.getRow(row), cellEl;
  26520. if(!(hscroll === false && col === 0)){
  26521. while(this.cm.isHidden(col)){
  26522. col++;
  26523. }
  26524. cellEl = this.getCell(row, col);
  26525. }
  26526. return {row: rowEl, cell: cellEl};
  26527. },
  26528. getResolvedXY : function(resolved){
  26529. if(!resolved){
  26530. return null;
  26531. }
  26532. var s = this.scroller.dom, c = resolved.cell, r = resolved.row;
  26533. return c ? Ext.fly(c).getXY() : [this.el.getX(), Ext.fly(r).getY()];
  26534. },
  26535. syncFocusEl : function(row, col, hscroll){
  26536. var xy = row;
  26537. if(!Ext.isArray(xy)){
  26538. row = Math.min(row, Math.max(0, this.getRows().length-1));
  26539. xy = this.getResolvedXY(this.resolveCell(row, col, hscroll));
  26540. }
  26541. this.focusEl.setXY(xy||this.scroller.getXY());
  26542. },
  26543. ensureVisible : function(row, col, hscroll){
  26544. var resolved = this.resolveCell(row, col, hscroll);
  26545. if(!resolved || !resolved.row){
  26546. return;
  26547. }
  26548. var rowEl = resolved.row, cellEl = resolved.cell;
  26549. var c = this.scroller.dom;
  26550. var ctop = 0;
  26551. var p = rowEl, stop = this.el.dom;
  26552. while(p && p != stop){
  26553. ctop += p.offsetTop;
  26554. p = p.offsetParent;
  26555. }
  26556. ctop -= this.mainHd.dom.offsetHeight;
  26557. var cbot = ctop + rowEl.offsetHeight;
  26558. var ch = c.clientHeight;
  26559. var stop = parseInt(c.scrollTop, 10);
  26560. var sbot = stop + ch;
  26561. if(ctop < stop){
  26562. c.scrollTop = ctop;
  26563. }else if(cbot > sbot){
  26564. c.scrollTop = cbot-ch;
  26565. }
  26566. if(hscroll !== false){
  26567. var cleft = parseInt(cellEl.offsetLeft, 10);
  26568. var cright = cleft + cellEl.offsetWidth;
  26569. var sleft = parseInt(c.scrollLeft, 10);
  26570. var sright = sleft + c.clientWidth;
  26571. if(cleft < sleft){
  26572. c.scrollLeft = cleft;
  26573. }else if(cright > sright){
  26574. c.scrollLeft = cright-c.clientWidth;
  26575. }
  26576. }
  26577. return this.getResolvedXY(resolved);
  26578. },
  26579. // private
  26580. insertRows : function(dm, firstRow, lastRow, isUpdate){
  26581. if(!isUpdate && firstRow === 0 && lastRow >= dm.getCount()-1){
  26582. this.refresh();
  26583. }else{
  26584. if(!isUpdate){
  26585. this.fireEvent("beforerowsinserted", this, firstRow, lastRow);
  26586. }
  26587. var html = this.renderRows(firstRow, lastRow);
  26588. var before = this.getRow(firstRow);
  26589. if(before){
  26590. Ext.DomHelper.insertHtml('beforeBegin', before, html);
  26591. }else{
  26592. Ext.DomHelper.insertHtml('beforeEnd', this.mainBody.dom, html);
  26593. }
  26594. if(!isUpdate){
  26595. this.fireEvent("rowsinserted", this, firstRow, lastRow);
  26596. this.processRows(firstRow);
  26597. }
  26598. }
  26599. this.syncFocusEl(firstRow);
  26600. },
  26601. // private
  26602. deleteRows : function(dm, firstRow, lastRow){
  26603. if(dm.getRowCount()<1){
  26604. this.refresh();
  26605. }else{
  26606. this.fireEvent("beforerowsdeleted", this, firstRow, lastRow);
  26607. this.removeRows(firstRow, lastRow);
  26608. this.processRows(firstRow);
  26609. this.fireEvent("rowsdeleted", this, firstRow, lastRow);
  26610. }
  26611. },
  26612. // private
  26613. getColumnStyle : function(col, isHeader){
  26614. var style = !isHeader ? (this.cm.config[col].css || '') : '';
  26615. style += 'width:'+this.getColumnWidth(col)+';';
  26616. if(this.cm.isHidden(col)){
  26617. style += 'display:none;';
  26618. }
  26619. var align = this.cm.config[col].align;
  26620. if(align){
  26621. style += 'text-align:'+align+';';
  26622. }
  26623. return style;
  26624. },
  26625. // private
  26626. getColumnWidth : function(col){
  26627. var w = this.cm.getColumnWidth(col);
  26628. if(typeof w == 'number'){
  26629. return (Ext.isBorderBox ? w : (w-this.borderWidth > 0 ? w-this.borderWidth:0)) + 'px';
  26630. }
  26631. return w;
  26632. },
  26633. // private
  26634. getTotalWidth : function(){
  26635. return this.cm.getTotalWidth()+'px';
  26636. },
  26637. // private
  26638. fitColumns : function(preventRefresh, onlyExpand, omitColumn){
  26639. var cm = this.cm, leftOver, dist, i;
  26640. var tw = cm.getTotalWidth(false);
  26641. var aw = this.grid.getGridEl().getWidth(true)-this.scrollOffset;
  26642. if(aw < 20){ // not initialized, so don't screw up the default widths
  26643. return;
  26644. }
  26645. var extra = aw - tw;
  26646. if(extra === 0){
  26647. return false;
  26648. }
  26649. var vc = cm.getColumnCount(true);
  26650. var ac = vc-(typeof omitColumn == 'number' ? 1 : 0);
  26651. if(ac === 0){
  26652. ac = 1;
  26653. omitColumn = undefined;
  26654. }
  26655. var colCount = cm.getColumnCount();
  26656. var cols = [];
  26657. var extraCol = 0;
  26658. var width = 0;
  26659. var w;
  26660. for (i = 0; i < colCount; i++){
  26661. if(!cm.isHidden(i) && !cm.isFixed(i) && i !== omitColumn){
  26662. w = cm.getColumnWidth(i);
  26663. cols.push(i);
  26664. extraCol = i;
  26665. cols.push(w);
  26666. width += w;
  26667. }
  26668. }
  26669. var frac = (aw - cm.getTotalWidth())/width;
  26670. while (cols.length){
  26671. w = cols.pop();
  26672. i = cols.pop();
  26673. cm.setColumnWidth(i, Math.max(this.grid.minColumnWidth, Math.floor(w + w*frac)), true);
  26674. }
  26675. if((tw = cm.getTotalWidth(false)) > aw){
  26676. var adjustCol = ac != vc ? omitColumn : extraCol;
  26677. cm.setColumnWidth(adjustCol, Math.max(1,
  26678. cm.getColumnWidth(adjustCol)- (tw-aw)), true);
  26679. }
  26680. if(preventRefresh !== true){
  26681. this.updateAllColumnWidths();
  26682. }
  26683. return true;
  26684. },
  26685. // private
  26686. autoExpand : function(preventUpdate){
  26687. var g = this.grid, cm = this.cm;
  26688. if(!this.userResized && g.autoExpandColumn){
  26689. var tw = cm.getTotalWidth(false);
  26690. var aw = this.grid.getGridEl().getWidth(true)-this.scrollOffset;
  26691. if(tw != aw){
  26692. var ci = cm.getIndexById(g.autoExpandColumn);
  26693. var currentWidth = cm.getColumnWidth(ci);
  26694. var cw = Math.min(Math.max(((aw-tw)+currentWidth), g.autoExpandMin), g.autoExpandMax);
  26695. if(cw != currentWidth){
  26696. cm.setColumnWidth(ci, cw, true);
  26697. if(preventUpdate !== true){
  26698. this.updateColumnWidth(ci, cw);
  26699. }
  26700. }
  26701. }
  26702. }
  26703. },
  26704. // private
  26705. getColumnData : function(){
  26706. // build a map for all the columns
  26707. var cs = [], cm = this.cm, colCount = cm.getColumnCount();
  26708. for(var i = 0; i < colCount; i++){
  26709. var name = cm.getDataIndex(i);
  26710. cs[i] = {
  26711. name : (typeof name == 'undefined' ? this.ds.fields.get(i).name : name),
  26712. renderer : cm.getRenderer(i),
  26713. id : cm.getColumnId(i),
  26714. style : this.getColumnStyle(i)
  26715. };
  26716. }
  26717. return cs;
  26718. },
  26719. // private
  26720. renderRows : function(startRow, endRow){
  26721. // pull in all the crap needed to render rows
  26722. var g = this.grid, cm = g.colModel, ds = g.store, stripe = g.stripeRows;
  26723. var colCount = cm.getColumnCount();
  26724. if(ds.getCount() < 1){
  26725. return "";
  26726. }
  26727. var cs = this.getColumnData();
  26728. startRow = startRow || 0;
  26729. endRow = typeof endRow == "undefined"? ds.getCount()-1 : endRow;
  26730. // records to render
  26731. var rs = ds.getRange(startRow, endRow);
  26732. return this.doRender(cs, rs, ds, startRow, colCount, stripe);
  26733. },
  26734. // private
  26735. renderBody : function(){
  26736. var markup = this.renderRows();
  26737. return this.templates.body.apply({rows: markup});
  26738. },
  26739. // private
  26740. refreshRow : function(record){
  26741. var ds = this.ds, index;
  26742. if(typeof record == 'number'){
  26743. index = record;
  26744. record = ds.getAt(index);
  26745. }else{
  26746. index = ds.indexOf(record);
  26747. }
  26748. var cls = [];
  26749. this.insertRows(ds, index, index, true);
  26750. this.getRow(index).rowIndex = index;
  26751. this.onRemove(ds, record, index+1, true);
  26752. this.fireEvent("rowupdated", this, index, record);
  26753. },
  26754. refresh : function(headersToo){
  26755. this.fireEvent("beforerefresh", this);
  26756. this.grid.stopEditing(true);
  26757. var result = this.renderBody();
  26758. this.mainBody.update(result);
  26759. if(headersToo === true){
  26760. this.updateHeaders();
  26761. this.updateHeaderSortState();
  26762. }
  26763. this.processRows(0, true);
  26764. this.layout();
  26765. this.applyEmptyText();
  26766. this.fireEvent("refresh", this);
  26767. },
  26768. // private
  26769. applyEmptyText : function(){
  26770. if(this.emptyText && !this.hasRows()){
  26771. this.mainBody.update('<div class="x-grid-empty">' + this.emptyText + '</div>');
  26772. }
  26773. },
  26774. // private
  26775. updateHeaderSortState : function(){
  26776. var state = this.ds.getSortState();
  26777. if(!state){
  26778. return;
  26779. }
  26780. if(!this.sortState || (this.sortState.field != state.field || this.sortState.direction != state.direction)){
  26781. this.grid.fireEvent('sortchange', this.grid, state);
  26782. }
  26783. this.sortState = state;
  26784. var sortColumn = this.cm.findColumnIndex(state.field);
  26785. if(sortColumn != -1){
  26786. var sortDir = state.direction;
  26787. this.updateSortIcon(sortColumn, sortDir);
  26788. }
  26789. },
  26790. // private
  26791. destroy : function(){
  26792. if(this.colMenu){
  26793. Ext.menu.MenuMgr.unregister(this.colMenu);
  26794. this.colMenu.destroy();
  26795. delete this.colMenu;
  26796. }
  26797. if(this.hmenu){
  26798. Ext.menu.MenuMgr.unregister(this.hmenu);
  26799. this.hmenu.destroy();
  26800. delete this.hmenu;
  26801. }
  26802. if(this.grid.enableColumnMove){
  26803. var dds = Ext.dd.DDM.ids['gridHeader' + this.grid.getGridEl().id];
  26804. if(dds){
  26805. for(var dd in dds){
  26806. if(!dds[dd].config.isTarget && dds[dd].dragElId){
  26807. var elid = dds[dd].dragElId;
  26808. dds[dd].unreg();
  26809. Ext.get(elid).remove();
  26810. } else if(dds[dd].config.isTarget){
  26811. dds[dd].proxyTop.remove();
  26812. dds[dd].proxyBottom.remove();
  26813. dds[dd].unreg();
  26814. }
  26815. if(Ext.dd.DDM.locationCache[dd]){
  26816. delete Ext.dd.DDM.locationCache[dd];
  26817. }
  26818. }
  26819. delete Ext.dd.DDM.ids['gridHeader' + this.grid.getGridEl().id];
  26820. }
  26821. }
  26822. if(this.dragZone){
  26823. this.dragZone.unreg();
  26824. }
  26825. Ext.fly(this.innerHd).removeAllListeners();
  26826. Ext.removeNode(this.innerHd);
  26827. Ext.destroy(this.resizeMarker, this.resizeProxy, this.focusEl, this.mainBody,
  26828. this.scroller, this.mainHd, this.mainWrap, this.dragZone,
  26829. this.splitZone, this.columnDrag, this.columnDrop);
  26830. this.initData(null, null);
  26831. Ext.EventManager.removeResizeListener(this.onWindowResize, this);
  26832. this.purgeListeners();
  26833. },
  26834. // private
  26835. onDenyColumnHide : function(){
  26836. },
  26837. // private
  26838. render : function(){
  26839. if(this.autoFill){
  26840. var ct = this.grid.ownerCt;
  26841. if (ct && ct.getLayout()){
  26842. ct.on('afterlayout', function(){
  26843. this.fitColumns(true, true);
  26844. this.updateHeaders();
  26845. }, this, {single: true});
  26846. }else{
  26847. this.fitColumns(true, true);
  26848. }
  26849. }else if(this.forceFit){
  26850. this.fitColumns(true, false);
  26851. }else if(this.grid.autoExpandColumn){
  26852. this.autoExpand(true);
  26853. }
  26854. this.renderUI();
  26855. },
  26856. // private
  26857. initData : function(ds, cm){
  26858. if(this.ds){
  26859. this.ds.un("load", this.onLoad, this);
  26860. this.ds.un("datachanged", this.onDataChange, this);
  26861. this.ds.un("add", this.onAdd, this);
  26862. this.ds.un("remove", this.onRemove, this);
  26863. this.ds.un("update", this.onUpdate, this);
  26864. this.ds.un("clear", this.onClear, this);
  26865. }
  26866. if(ds){
  26867. ds.on("load", this.onLoad, this);
  26868. ds.on("datachanged", this.onDataChange, this);
  26869. ds.on("add", this.onAdd, this);
  26870. ds.on("remove", this.onRemove, this);
  26871. ds.on("update", this.onUpdate, this);
  26872. ds.on("clear", this.onClear, this);
  26873. }
  26874. this.ds = ds;
  26875. if(this.cm){
  26876. this.cm.un("configchange", this.onColConfigChange, this);
  26877. this.cm.un("widthchange", this.onColWidthChange, this);
  26878. this.cm.un("headerchange", this.onHeaderChange, this);
  26879. this.cm.un("hiddenchange", this.onHiddenChange, this);
  26880. this.cm.un("columnmoved", this.onColumnMove, this);
  26881. this.cm.un("columnlockchange", this.onColumnLock, this);
  26882. }
  26883. if(cm){
  26884. delete this.lastViewWidth;
  26885. cm.on("configchange", this.onColConfigChange, this);
  26886. cm.on("widthchange", this.onColWidthChange, this);
  26887. cm.on("headerchange", this.onHeaderChange, this);
  26888. cm.on("hiddenchange", this.onHiddenChange, this);
  26889. cm.on("columnmoved", this.onColumnMove, this);
  26890. cm.on("columnlockchange", this.onColumnLock, this);
  26891. }
  26892. this.cm = cm;
  26893. },
  26894. // private
  26895. onDataChange : function(){
  26896. this.refresh();
  26897. this.updateHeaderSortState();
  26898. this.syncFocusEl(0);
  26899. },
  26900. // private
  26901. onClear : function(){
  26902. this.refresh();
  26903. this.syncFocusEl(0);
  26904. },
  26905. // private
  26906. onUpdate : function(ds, record){
  26907. this.refreshRow(record);
  26908. },
  26909. // private
  26910. onAdd : function(ds, records, index){
  26911. this.insertRows(ds, index, index + (records.length-1));
  26912. },
  26913. // private
  26914. onRemove : function(ds, record, index, isUpdate){
  26915. if(isUpdate !== true){
  26916. this.fireEvent("beforerowremoved", this, index, record);
  26917. }
  26918. this.removeRow(index);
  26919. if(isUpdate !== true){
  26920. this.processRows(index);
  26921. this.applyEmptyText();
  26922. this.fireEvent("rowremoved", this, index, record);
  26923. }
  26924. },
  26925. // private
  26926. onLoad : function(){
  26927. this.scrollToTop();
  26928. },
  26929. // private
  26930. onColWidthChange : function(cm, col, width){
  26931. this.updateColumnWidth(col, width);
  26932. },
  26933. // private
  26934. onHeaderChange : function(cm, col, text){
  26935. this.updateHeaders();
  26936. },
  26937. // private
  26938. onHiddenChange : function(cm, col, hidden){
  26939. this.updateColumnHidden(col, hidden);
  26940. },
  26941. // private
  26942. onColumnMove : function(cm, oldIndex, newIndex){
  26943. this.indexMap = null;
  26944. var s = this.getScrollState();
  26945. this.refresh(true);
  26946. this.restoreScroll(s);
  26947. this.afterMove(newIndex);
  26948. },
  26949. // private
  26950. onColConfigChange : function(){
  26951. delete this.lastViewWidth;
  26952. this.indexMap = null;
  26953. this.refresh(true);
  26954. },
  26955. // private
  26956. initUI : function(grid){
  26957. grid.on("headerclick", this.onHeaderClick, this);
  26958. },
  26959. // private
  26960. initEvents : function(){
  26961. },
  26962. // private
  26963. onHeaderClick : function(g, index){
  26964. if(this.headersDisabled || !this.cm.isSortable(index)){
  26965. return;
  26966. }
  26967. g.stopEditing(true);
  26968. g.store.sort(this.cm.getDataIndex(index));
  26969. },
  26970. // private
  26971. onRowOver : function(e, t){
  26972. var row;
  26973. if((row = this.findRowIndex(t)) !== false){
  26974. this.addRowClass(row, "x-grid3-row-over");
  26975. }
  26976. },
  26977. // private
  26978. onRowOut : function(e, t){
  26979. var row;
  26980. if((row = this.findRowIndex(t)) !== false && !e.within(this.getRow(row), true)){
  26981. this.removeRowClass(row, "x-grid3-row-over");
  26982. }
  26983. },
  26984. // private
  26985. handleWheel : function(e){
  26986. e.stopPropagation();
  26987. },
  26988. // private
  26989. onRowSelect : function(row){
  26990. this.addRowClass(row, "x-grid3-row-selected");
  26991. },
  26992. // private
  26993. onRowDeselect : function(row){
  26994. this.removeRowClass(row, "x-grid3-row-selected");
  26995. },
  26996. // private
  26997. onCellSelect : function(row, col){
  26998. var cell = this.getCell(row, col);
  26999. if(cell){
  27000. this.fly(cell).addClass("x-grid3-cell-selected");
  27001. }
  27002. },
  27003. // private
  27004. onCellDeselect : function(row, col){
  27005. var cell = this.getCell(row, col);
  27006. if(cell){
  27007. this.fly(cell).removeClass("x-grid3-cell-selected");
  27008. }
  27009. },
  27010. // private
  27011. onColumnSplitterMoved : function(i, w){
  27012. this.userResized = true;
  27013. var cm = this.grid.colModel;
  27014. cm.setColumnWidth(i, w, true);
  27015. if(this.forceFit){
  27016. this.fitColumns(true, false, i);
  27017. this.updateAllColumnWidths();
  27018. }else{
  27019. this.updateColumnWidth(i, w);
  27020. this.syncHeaderScroll();
  27021. }
  27022. this.grid.fireEvent("columnresize", i, w);
  27023. },
  27024. // private
  27025. handleHdMenuClick : function(item){
  27026. var index = this.hdCtxIndex;
  27027. var cm = this.cm, ds = this.ds;
  27028. switch(item.id){
  27029. case "asc":
  27030. ds.sort(cm.getDataIndex(index), "ASC");
  27031. break;
  27032. case "desc":
  27033. ds.sort(cm.getDataIndex(index), "DESC");
  27034. break;
  27035. default:
  27036. index = cm.getIndexById(item.id.substr(4));
  27037. if(index != -1){
  27038. if(item.checked && cm.getColumnsBy(this.isHideableColumn, this).length <= 1){
  27039. this.onDenyColumnHide();
  27040. return false;
  27041. }
  27042. cm.setHidden(index, item.checked);
  27043. }
  27044. }
  27045. return true;
  27046. },
  27047. // private
  27048. isHideableColumn : function(c){
  27049. return !c.hidden && !c.fixed;
  27050. },
  27051. // private
  27052. beforeColMenuShow : function(){
  27053. var cm = this.cm, colCount = cm.getColumnCount();
  27054. this.colMenu.removeAll();
  27055. for(var i = 0; i < colCount; i++){
  27056. if(cm.config[i].fixed !== true && cm.config[i].hideable !== false){
  27057. this.colMenu.add(new Ext.menu.CheckItem({
  27058. id: "col-"+cm.getColumnId(i),
  27059. text: cm.getColumnHeader(i),
  27060. checked: !cm.isHidden(i),
  27061. hideOnClick:false,
  27062. disabled: cm.config[i].hideable === false
  27063. }));
  27064. }
  27065. }
  27066. },
  27067. // private
  27068. handleHdDown : function(e, t){
  27069. if(Ext.fly(t).hasClass('x-grid3-hd-btn')){
  27070. e.stopEvent();
  27071. var hd = this.findHeaderCell(t);
  27072. Ext.fly(hd).addClass('x-grid3-hd-menu-open');
  27073. var index = this.getCellIndex(hd);
  27074. this.hdCtxIndex = index;
  27075. var ms = this.hmenu.items, cm = this.cm;
  27076. ms.get("asc").setDisabled(!cm.isSortable(index));
  27077. ms.get("desc").setDisabled(!cm.isSortable(index));
  27078. this.hmenu.on("hide", function(){
  27079. Ext.fly(hd).removeClass('x-grid3-hd-menu-open');
  27080. }, this, {single:true});
  27081. this.hmenu.show(t, "tl-bl?");
  27082. }
  27083. },
  27084. // private
  27085. handleHdOver : function(e, t){
  27086. var hd = this.findHeaderCell(t);
  27087. if(hd && !this.headersDisabled){
  27088. this.activeHd = hd;
  27089. this.activeHdIndex = this.getCellIndex(hd);
  27090. var fly = this.fly(hd);
  27091. this.activeHdRegion = fly.getRegion();
  27092. if(!this.cm.isMenuDisabled(this.activeHdIndex)){
  27093. fly.addClass("x-grid3-hd-over");
  27094. this.activeHdBtn = fly.child('.x-grid3-hd-btn');
  27095. if(this.activeHdBtn){
  27096. this.activeHdBtn.dom.style.height = (hd.firstChild.offsetHeight-1)+'px';
  27097. }
  27098. }
  27099. }
  27100. },
  27101. // private
  27102. handleHdMove : function(e, t){
  27103. if(this.activeHd && !this.headersDisabled){
  27104. var hw = this.splitHandleWidth || 5;
  27105. var r = this.activeHdRegion;
  27106. var x = e.getPageX();
  27107. var ss = this.activeHd.style;
  27108. if(x - r.left <= hw && this.cm.isResizable(this.activeHdIndex-1)){
  27109. ss.cursor = Ext.isAir ? 'move' : Ext.isSafari ? 'e-resize' : 'col-resize'; // col-resize not always supported
  27110. }else if(r.right - x <= (!this.activeHdBtn ? hw : 2) && this.cm.isResizable(this.activeHdIndex)){
  27111. ss.cursor = Ext.isAir ? 'move' : Ext.isSafari ? 'w-resize' : 'col-resize';
  27112. }else{
  27113. ss.cursor = '';
  27114. }
  27115. }
  27116. },
  27117. // private
  27118. handleHdOut : function(e, t){
  27119. var hd = this.findHeaderCell(t);
  27120. if(hd && (!Ext.isIE || !e.within(hd, true))){
  27121. this.activeHd = null;
  27122. this.fly(hd).removeClass("x-grid3-hd-over");
  27123. hd.style.cursor = '';
  27124. }
  27125. },
  27126. // private
  27127. hasRows : function(){
  27128. var fc = this.mainBody.dom.firstChild;
  27129. return fc && fc.className != 'x-grid-empty';
  27130. },
  27131. // back compat
  27132. bind : function(d, c){
  27133. this.initData(d, c);
  27134. }
  27135. });
  27136. // private
  27137. // This is a support class used internally by the Grid components
  27138. Ext.grid.GridView.SplitDragZone = function(grid, hd){
  27139. this.grid = grid;
  27140. this.view = grid.getView();
  27141. this.marker = this.view.resizeMarker;
  27142. this.proxy = this.view.resizeProxy;
  27143. Ext.grid.GridView.SplitDragZone.superclass.constructor.call(this, hd,
  27144. "gridSplitters" + this.grid.getGridEl().id, {
  27145. dragElId : Ext.id(this.proxy.dom), resizeFrame:false
  27146. });
  27147. this.scroll = false;
  27148. this.hw = this.view.splitHandleWidth || 5;
  27149. };
  27150. Ext.extend(Ext.grid.GridView.SplitDragZone, Ext.dd.DDProxy, {
  27151. b4StartDrag : function(x, y){
  27152. this.view.headersDisabled = true;
  27153. var h = this.view.mainWrap.getHeight();
  27154. this.marker.setHeight(h);
  27155. this.marker.show();
  27156. this.marker.alignTo(this.view.getHeaderCell(this.cellIndex), 'tl-tl', [-2, 0]);
  27157. this.proxy.setHeight(h);
  27158. var w = this.cm.getColumnWidth(this.cellIndex);
  27159. var minw = Math.max(w-this.grid.minColumnWidth, 0);
  27160. this.resetConstraints();
  27161. this.setXConstraint(minw, 1000);
  27162. this.setYConstraint(0, 0);
  27163. this.minX = x - minw;
  27164. this.maxX = x + 1000;
  27165. this.startPos = x;
  27166. Ext.dd.DDProxy.prototype.b4StartDrag.call(this, x, y);
  27167. },
  27168. handleMouseDown : function(e){
  27169. var t = this.view.findHeaderCell(e.getTarget());
  27170. if(t){
  27171. var xy = this.view.fly(t).getXY(), x = xy[0], y = xy[1];
  27172. var exy = e.getXY(), ex = exy[0], ey = exy[1];
  27173. var w = t.offsetWidth, adjust = false;
  27174. if((ex - x) <= this.hw){
  27175. adjust = -1;
  27176. }else if((x+w) - ex <= this.hw){
  27177. adjust = 0;
  27178. }
  27179. if(adjust !== false){
  27180. this.cm = this.grid.colModel;
  27181. var ci = this.view.getCellIndex(t);
  27182. if(adjust == -1){
  27183. if (ci + adjust < 0) {
  27184. return;
  27185. }
  27186. while(this.cm.isHidden(ci+adjust)){
  27187. --adjust;
  27188. if(ci+adjust < 0){
  27189. return;
  27190. }
  27191. }
  27192. }
  27193. this.cellIndex = ci+adjust;
  27194. this.split = t.dom;
  27195. if(this.cm.isResizable(this.cellIndex) && !this.cm.isFixed(this.cellIndex)){
  27196. Ext.grid.GridView.SplitDragZone.superclass.handleMouseDown.apply(this, arguments);
  27197. }
  27198. }else if(this.view.columnDrag){
  27199. this.view.columnDrag.callHandleMouseDown(e);
  27200. }
  27201. }
  27202. },
  27203. endDrag : function(e){
  27204. this.marker.hide();
  27205. var v = this.view;
  27206. var endX = Math.max(this.minX, e.getPageX());
  27207. var diff = endX - this.startPos;
  27208. v.onColumnSplitterMoved(this.cellIndex, this.cm.getColumnWidth(this.cellIndex)+diff);
  27209. setTimeout(function(){
  27210. v.headersDisabled = false;
  27211. }, 50);
  27212. },
  27213. autoOffset : function(){
  27214. this.setDelta(0,0);
  27215. }
  27216. });
  27217. Ext.grid.GroupingView = Ext.extend(Ext.grid.GridView, {
  27218. hideGroupedColumn:false,
  27219. showGroupName:true,
  27220. startCollapsed:false,
  27221. enableGrouping:true,
  27222. enableGroupingMenu:true,
  27223. enableNoGroups:true,
  27224. emptyGroupText : '(None)',
  27225. ignoreAdd: false,
  27226. groupTextTpl : '{text}',
  27227. // private
  27228. gidSeed : 1000,
  27229. // private
  27230. initTemplates : function(){
  27231. Ext.grid.GroupingView.superclass.initTemplates.call(this);
  27232. this.state = {};
  27233. var sm = this.grid.getSelectionModel();
  27234. sm.on(sm.selectRow ? 'beforerowselect' : 'beforecellselect',
  27235. this.onBeforeRowSelect, this);
  27236. if(!this.startGroup){
  27237. this.startGroup = new Ext.XTemplate(
  27238. '<div id="{groupId}" class="x-grid-group {cls}">',
  27239. '<div id="{groupId}-hd" class="x-grid-group-hd" style="{style}"><div>', this.groupTextTpl ,'</div></div>',
  27240. '<div id="{groupId}-bd" class="x-grid-group-body">'
  27241. );
  27242. }
  27243. this.startGroup.compile();
  27244. this.endGroup = '</div></div>';
  27245. },
  27246. // private
  27247. findGroup : function(el){
  27248. return Ext.fly(el).up('.x-grid-group', this.mainBody.dom);
  27249. },
  27250. // private
  27251. getGroups : function(){
  27252. return this.hasRows() ? this.mainBody.dom.childNodes : [];
  27253. },
  27254. // private
  27255. onAdd : function(){
  27256. if(this.enableGrouping && !this.ignoreAdd){
  27257. var ss = this.getScrollState();
  27258. this.refresh();
  27259. this.restoreScroll(ss);
  27260. }else if(!this.enableGrouping){
  27261. Ext.grid.GroupingView.superclass.onAdd.apply(this, arguments);
  27262. }
  27263. },
  27264. // private
  27265. onRemove : function(ds, record, index, isUpdate){
  27266. Ext.grid.GroupingView.superclass.onRemove.apply(this, arguments);
  27267. var g = document.getElementById(record._groupId);
  27268. if(g && g.childNodes[1].childNodes.length < 1){
  27269. Ext.removeNode(g);
  27270. }
  27271. this.applyEmptyText();
  27272. },
  27273. // private
  27274. refreshRow : function(record){
  27275. if(this.ds.getCount()==1){
  27276. this.refresh();
  27277. }else{
  27278. this.isUpdating = true;
  27279. Ext.grid.GroupingView.superclass.refreshRow.apply(this, arguments);
  27280. this.isUpdating = false;
  27281. }
  27282. },
  27283. // private
  27284. beforeMenuShow : function(){
  27285. var field = this.getGroupField();
  27286. var g = this.hmenu.items.get('groupBy');
  27287. if(g){
  27288. g.setDisabled(this.cm.config[this.hdCtxIndex].groupable === false);
  27289. }
  27290. var s = this.hmenu.items.get('showGroups');
  27291. if(s){
  27292. s.setDisabled(!field && this.cm.config[this.hdCtxIndex].groupable === false);
  27293. s.setChecked(!!field, true);
  27294. }
  27295. },
  27296. // private
  27297. renderUI : function(){
  27298. Ext.grid.GroupingView.superclass.renderUI.call(this);
  27299. this.mainBody.on('mousedown', this.interceptMouse, this);
  27300. if(this.enableGroupingMenu && this.hmenu){
  27301. this.hmenu.add('-',{
  27302. id:'groupBy',
  27303. text: this.groupByText,
  27304. handler: this.onGroupByClick,
  27305. scope: this,
  27306. iconCls:'x-group-by-icon'
  27307. });
  27308. if(this.enableNoGroups){
  27309. this.hmenu.add({
  27310. id:'showGroups',
  27311. text: this.showGroupsText,
  27312. checked: true,
  27313. checkHandler: this.onShowGroupsClick,
  27314. scope: this
  27315. });
  27316. }
  27317. this.hmenu.on('beforeshow', this.beforeMenuShow, this);
  27318. }
  27319. },
  27320. // private
  27321. onGroupByClick : function(){
  27322. this.grid.store.groupBy(this.cm.getDataIndex(this.hdCtxIndex));
  27323. this.beforeMenuShow(); // Make sure the checkboxes get properly set when changing groups
  27324. },
  27325. // private
  27326. onShowGroupsClick : function(mi, checked){
  27327. if(checked){
  27328. this.onGroupByClick();
  27329. }else{
  27330. this.grid.store.clearGrouping();
  27331. }
  27332. },
  27333. toggleGroup : function(group, expanded){
  27334. this.grid.stopEditing(true);
  27335. group = Ext.getDom(group);
  27336. var gel = Ext.fly(group);
  27337. expanded = expanded !== undefined ?
  27338. expanded : gel.hasClass('x-grid-group-collapsed');
  27339. this.state[gel.dom.id] = expanded;
  27340. gel[expanded ? 'removeClass' : 'addClass']('x-grid-group-collapsed');
  27341. },
  27342. toggleAllGroups : function(expanded){
  27343. var groups = this.getGroups();
  27344. for(var i = 0, len = groups.length; i < len; i++){
  27345. this.toggleGroup(groups[i], expanded);
  27346. }
  27347. },
  27348. expandAllGroups : function(){
  27349. this.toggleAllGroups(true);
  27350. },
  27351. collapseAllGroups : function(){
  27352. this.toggleAllGroups(false);
  27353. },
  27354. // private
  27355. interceptMouse : function(e){
  27356. var hd = e.getTarget('.x-grid-group-hd', this.mainBody);
  27357. if(hd){
  27358. e.stopEvent();
  27359. this.toggleGroup(hd.parentNode);
  27360. }
  27361. },
  27362. // private
  27363. getGroup : function(v, r, groupRenderer, rowIndex, colIndex, ds){
  27364. var g = groupRenderer ? groupRenderer(v, {}, r, rowIndex, colIndex, ds) : String(v);
  27365. if(g === ''){
  27366. g = this.cm.config[colIndex].emptyGroupText || this.emptyGroupText;
  27367. }
  27368. return g;
  27369. },
  27370. // private
  27371. getGroupField : function(){
  27372. return this.grid.store.getGroupState();
  27373. },
  27374. // private
  27375. renderRows : function(){
  27376. var groupField = this.getGroupField();
  27377. var eg = !!groupField;
  27378. // if they turned off grouping and the last grouped field is hidden
  27379. if(this.hideGroupedColumn) {
  27380. var colIndex = this.cm.findColumnIndex(groupField);
  27381. if(!eg && this.lastGroupField !== undefined) {
  27382. this.mainBody.update('');
  27383. this.cm.setHidden(this.cm.findColumnIndex(this.lastGroupField), false);
  27384. delete this.lastGroupField;
  27385. }else if (eg && this.lastGroupField === undefined) {
  27386. this.lastGroupField = groupField;
  27387. this.cm.setHidden(colIndex, true);
  27388. }else if (eg && this.lastGroupField !== undefined && groupField !== this.lastGroupField) {
  27389. this.mainBody.update('');
  27390. var oldIndex = this.cm.findColumnIndex(this.lastGroupField);
  27391. this.cm.setHidden(oldIndex, false);
  27392. this.lastGroupField = groupField;
  27393. this.cm.setHidden(colIndex, true);
  27394. }
  27395. }
  27396. return Ext.grid.GroupingView.superclass.renderRows.apply(
  27397. this, arguments);
  27398. },
  27399. // private
  27400. doRender : function(cs, rs, ds, startRow, colCount, stripe){
  27401. if(rs.length < 1){
  27402. return '';
  27403. }
  27404. var groupField = this.getGroupField();
  27405. var colIndex = this.cm.findColumnIndex(groupField);
  27406. this.enableGrouping = !!groupField;
  27407. if(!this.enableGrouping || this.isUpdating){
  27408. return Ext.grid.GroupingView.superclass.doRender.apply(
  27409. this, arguments);
  27410. }
  27411. var gstyle = 'width:'+this.getTotalWidth()+';';
  27412. var gidPrefix = this.grid.getGridEl().id;
  27413. var cfg = this.cm.config[colIndex];
  27414. var groupRenderer = cfg.groupRenderer || cfg.renderer;
  27415. var prefix = this.showGroupName ?
  27416. (cfg.groupName || cfg.header)+': ' : '';
  27417. var groups = [], curGroup, i, len, gid;
  27418. for(i = 0, len = rs.length; i < len; i++){
  27419. var rowIndex = startRow + i;
  27420. var r = rs[i],
  27421. gvalue = r.data[groupField],
  27422. g = this.getGroup(gvalue, r, groupRenderer, rowIndex, colIndex, ds);
  27423. if(!curGroup || curGroup.group != g){
  27424. gid = gidPrefix + '-gp-' + groupField + '-' + Ext.util.Format.htmlEncode(g);
  27425. // if state is defined use it, however state is in terms of expanded
  27426. // so negate it, otherwise use the default.
  27427. var isCollapsed = typeof this.state[gid] !== 'undefined' ? !this.state[gid] : this.startCollapsed;
  27428. var gcls = isCollapsed ? 'x-grid-group-collapsed' : '';
  27429. curGroup = {
  27430. group: g,
  27431. gvalue: gvalue,
  27432. text: prefix + g,
  27433. groupId: gid,
  27434. startRow: rowIndex,
  27435. rs: [r],
  27436. cls: gcls,
  27437. style: gstyle
  27438. };
  27439. groups.push(curGroup);
  27440. }else{
  27441. curGroup.rs.push(r);
  27442. }
  27443. r._groupId = gid;
  27444. }
  27445. var buf = [];
  27446. for(i = 0, len = groups.length; i < len; i++){
  27447. var g = groups[i];
  27448. this.doGroupStart(buf, g, cs, ds, colCount);
  27449. buf[buf.length] = Ext.grid.GroupingView.superclass.doRender.call(
  27450. this, cs, g.rs, ds, g.startRow, colCount, stripe);
  27451. this.doGroupEnd(buf, g, cs, ds, colCount);
  27452. }
  27453. return buf.join('');
  27454. },
  27455. getGroupId : function(value){
  27456. var gidPrefix = this.grid.getGridEl().id;
  27457. var groupField = this.getGroupField();
  27458. var colIndex = this.cm.findColumnIndex(groupField);
  27459. var cfg = this.cm.config[colIndex];
  27460. var groupRenderer = cfg.groupRenderer || cfg.renderer;
  27461. var gtext = this.getGroup(value, {data:{}}, groupRenderer, 0, colIndex, this.ds);
  27462. return gidPrefix + '-gp-' + groupField + '-' + Ext.util.Format.htmlEncode(value);
  27463. },
  27464. // private
  27465. doGroupStart : function(buf, g, cs, ds, colCount){
  27466. buf[buf.length] = this.startGroup.apply(g);
  27467. },
  27468. // private
  27469. doGroupEnd : function(buf, g, cs, ds, colCount){
  27470. buf[buf.length] = this.endGroup;
  27471. },
  27472. // private
  27473. getRows : function(){
  27474. if(!this.enableGrouping){
  27475. return Ext.grid.GroupingView.superclass.getRows.call(this);
  27476. }
  27477. var r = [];
  27478. var g, gs = this.getGroups();
  27479. for(var i = 0, len = gs.length; i < len; i++){
  27480. g = gs[i].childNodes[1].childNodes;
  27481. for(var j = 0, jlen = g.length; j < jlen; j++){
  27482. r[r.length] = g[j];
  27483. }
  27484. }
  27485. return r;
  27486. },
  27487. // private
  27488. updateGroupWidths : function(){
  27489. if(!this.enableGrouping || !this.hasRows()){
  27490. return;
  27491. }
  27492. var tw = Math.max(this.cm.getTotalWidth(), this.el.dom.offsetWidth-this.scrollOffset) +'px';
  27493. var gs = this.getGroups();
  27494. for(var i = 0, len = gs.length; i < len; i++){
  27495. gs[i].firstChild.style.width = tw;
  27496. }
  27497. },
  27498. // private
  27499. onColumnWidthUpdated : function(col, w, tw){
  27500. Ext.grid.GroupingView.superclass.onColumnWidthUpdated.call(this, col, w, tw);
  27501. this.updateGroupWidths();
  27502. },
  27503. // private
  27504. onAllColumnWidthsUpdated : function(ws, tw){
  27505. Ext.grid.GroupingView.superclass.onAllColumnWidthsUpdated.call(this, ws, tw);
  27506. this.updateGroupWidths();
  27507. },
  27508. // private
  27509. onColumnHiddenUpdated : function(col, hidden, tw){
  27510. Ext.grid.GroupingView.superclass.onColumnHiddenUpdated.call(this, col, hidden, tw);
  27511. this.updateGroupWidths();
  27512. },
  27513. // private
  27514. onLayout : function(){
  27515. this.updateGroupWidths();
  27516. },
  27517. // private
  27518. onBeforeRowSelect : function(sm, rowIndex){
  27519. if(!this.enableGrouping){
  27520. return;
  27521. }
  27522. var row = this.getRow(rowIndex);
  27523. if(row && !row.offsetParent){
  27524. var g = this.findGroup(row);
  27525. this.toggleGroup(g, true);
  27526. }
  27527. },
  27528. groupByText: 'Group By This Field',
  27529. showGroupsText: 'Show in Groups'
  27530. });
  27531. // private
  27532. Ext.grid.GroupingView.GROUP_ID = 1000;
  27533. // private
  27534. // This is a support class used internally by the Grid components
  27535. Ext.grid.HeaderDragZone = function(grid, hd, hd2){
  27536. this.grid = grid;
  27537. this.view = grid.getView();
  27538. this.ddGroup = "gridHeader" + this.grid.getGridEl().id;
  27539. Ext.grid.HeaderDragZone.superclass.constructor.call(this, hd);
  27540. if(hd2){
  27541. this.setHandleElId(Ext.id(hd));
  27542. this.setOuterHandleElId(Ext.id(hd2));
  27543. }
  27544. this.scroll = false;
  27545. };
  27546. Ext.extend(Ext.grid.HeaderDragZone, Ext.dd.DragZone, {
  27547. maxDragWidth: 120,
  27548. getDragData : function(e){
  27549. var t = Ext.lib.Event.getTarget(e);
  27550. var h = this.view.findHeaderCell(t);
  27551. if(h){
  27552. return {ddel: h.firstChild, header:h};
  27553. }
  27554. return false;
  27555. },
  27556. onInitDrag : function(e){
  27557. this.view.headersDisabled = true;
  27558. var clone = this.dragData.ddel.cloneNode(true);
  27559. clone.id = Ext.id();
  27560. clone.style.width = Math.min(this.dragData.header.offsetWidth,this.maxDragWidth) + "px";
  27561. this.proxy.update(clone);
  27562. return true;
  27563. },
  27564. afterValidDrop : function(){
  27565. var v = this.view;
  27566. setTimeout(function(){
  27567. v.headersDisabled = false;
  27568. }, 50);
  27569. },
  27570. afterInvalidDrop : function(){
  27571. var v = this.view;
  27572. setTimeout(function(){
  27573. v.headersDisabled = false;
  27574. }, 50);
  27575. }
  27576. });
  27577. // private
  27578. // This is a support class used internally by the Grid components
  27579. Ext.grid.HeaderDropZone = function(grid, hd, hd2){
  27580. this.grid = grid;
  27581. this.view = grid.getView();
  27582. // split the proxies so they don't interfere with mouse events
  27583. this.proxyTop = Ext.DomHelper.append(document.body, {
  27584. cls:"col-move-top", html:"&#160;"
  27585. }, true);
  27586. this.proxyBottom = Ext.DomHelper.append(document.body, {
  27587. cls:"col-move-bottom", html:"&#160;"
  27588. }, true);
  27589. this.proxyTop.hide = this.proxyBottom.hide = function(){
  27590. this.setLeftTop(-100,-100);
  27591. this.setStyle("visibility", "hidden");
  27592. };
  27593. this.ddGroup = "gridHeader" + this.grid.getGridEl().id;
  27594. // temporarily disabled
  27595. //Ext.dd.ScrollManager.register(this.view.scroller.dom);
  27596. Ext.grid.HeaderDropZone.superclass.constructor.call(this, grid.getGridEl().dom);
  27597. };
  27598. Ext.extend(Ext.grid.HeaderDropZone, Ext.dd.DropZone, {
  27599. proxyOffsets : [-4, -9],
  27600. fly: Ext.Element.fly,
  27601. getTargetFromEvent : function(e){
  27602. var t = Ext.lib.Event.getTarget(e);
  27603. var cindex = this.view.findCellIndex(t);
  27604. if(cindex !== false){
  27605. return this.view.getHeaderCell(cindex);
  27606. }
  27607. },
  27608. nextVisible : function(h){
  27609. var v = this.view, cm = this.grid.colModel;
  27610. h = h.nextSibling;
  27611. while(h){
  27612. if(!cm.isHidden(v.getCellIndex(h))){
  27613. return h;
  27614. }
  27615. h = h.nextSibling;
  27616. }
  27617. return null;
  27618. },
  27619. prevVisible : function(h){
  27620. var v = this.view, cm = this.grid.colModel;
  27621. h = h.prevSibling;
  27622. while(h){
  27623. if(!cm.isHidden(v.getCellIndex(h))){
  27624. return h;
  27625. }
  27626. h = h.prevSibling;
  27627. }
  27628. return null;
  27629. },
  27630. positionIndicator : function(h, n, e){
  27631. var x = Ext.lib.Event.getPageX(e);
  27632. var r = Ext.lib.Dom.getRegion(n.firstChild);
  27633. var px, pt, py = r.top + this.proxyOffsets[1];
  27634. if((r.right - x) <= (r.right-r.left)/2){
  27635. px = r.right+this.view.borderWidth;
  27636. pt = "after";
  27637. }else{
  27638. px = r.left;
  27639. pt = "before";
  27640. }
  27641. var oldIndex = this.view.getCellIndex(h);
  27642. var newIndex = this.view.getCellIndex(n);
  27643. if(this.grid.colModel.isFixed(newIndex)){
  27644. return false;
  27645. }
  27646. var locked = this.grid.colModel.isLocked(newIndex);
  27647. if(pt == "after"){
  27648. newIndex++;
  27649. }
  27650. if(oldIndex < newIndex){
  27651. newIndex--;
  27652. }
  27653. if(oldIndex == newIndex && (locked == this.grid.colModel.isLocked(oldIndex))){
  27654. return false;
  27655. }
  27656. px += this.proxyOffsets[0];
  27657. this.proxyTop.setLeftTop(px, py);
  27658. this.proxyTop.show();
  27659. if(!this.bottomOffset){
  27660. this.bottomOffset = this.view.mainHd.getHeight();
  27661. }
  27662. this.proxyBottom.setLeftTop(px, py+this.proxyTop.dom.offsetHeight+this.bottomOffset);
  27663. this.proxyBottom.show();
  27664. return pt;
  27665. },
  27666. onNodeEnter : function(n, dd, e, data){
  27667. if(data.header != n){
  27668. this.positionIndicator(data.header, n, e);
  27669. }
  27670. },
  27671. onNodeOver : function(n, dd, e, data){
  27672. var result = false;
  27673. if(data.header != n){
  27674. result = this.positionIndicator(data.header, n, e);
  27675. }
  27676. if(!result){
  27677. this.proxyTop.hide();
  27678. this.proxyBottom.hide();
  27679. }
  27680. return result ? this.dropAllowed : this.dropNotAllowed;
  27681. },
  27682. onNodeOut : function(n, dd, e, data){
  27683. this.proxyTop.hide();
  27684. this.proxyBottom.hide();
  27685. },
  27686. onNodeDrop : function(n, dd, e, data){
  27687. var h = data.header;
  27688. if(h != n){
  27689. var cm = this.grid.colModel;
  27690. var x = Ext.lib.Event.getPageX(e);
  27691. var r = Ext.lib.Dom.getRegion(n.firstChild);
  27692. var pt = (r.right - x) <= ((r.right-r.left)/2) ? "after" : "before";
  27693. var oldIndex = this.view.getCellIndex(h);
  27694. var newIndex = this.view.getCellIndex(n);
  27695. var locked = cm.isLocked(newIndex);
  27696. if(pt == "after"){
  27697. newIndex++;
  27698. }
  27699. if(oldIndex < newIndex){
  27700. newIndex--;
  27701. }
  27702. if(oldIndex == newIndex && (locked == cm.isLocked(oldIndex))){
  27703. return false;
  27704. }
  27705. cm.setLocked(oldIndex, locked, true);
  27706. cm.moveColumn(oldIndex, newIndex);
  27707. this.grid.fireEvent("columnmove", oldIndex, newIndex);
  27708. return true;
  27709. }
  27710. return false;
  27711. }
  27712. });
  27713. Ext.grid.GridView.ColumnDragZone = function(grid, hd){
  27714. Ext.grid.GridView.ColumnDragZone.superclass.constructor.call(this, grid, hd, null);
  27715. this.proxy.el.addClass('x-grid3-col-dd');
  27716. };
  27717. Ext.extend(Ext.grid.GridView.ColumnDragZone, Ext.grid.HeaderDragZone, {
  27718. handleMouseDown : function(e){
  27719. },
  27720. callHandleMouseDown : function(e){
  27721. Ext.grid.GridView.ColumnDragZone.superclass.handleMouseDown.call(this, e);
  27722. }
  27723. });
  27724. // private
  27725. // This is a support class used internally by the Grid components
  27726. Ext.grid.SplitDragZone = function(grid, hd, hd2){
  27727. this.grid = grid;
  27728. this.view = grid.getView();
  27729. this.proxy = this.view.resizeProxy;
  27730. Ext.grid.SplitDragZone.superclass.constructor.call(this, hd,
  27731. "gridSplitters" + this.grid.getGridEl().id, {
  27732. dragElId : Ext.id(this.proxy.dom), resizeFrame:false
  27733. });
  27734. this.setHandleElId(Ext.id(hd));
  27735. this.setOuterHandleElId(Ext.id(hd2));
  27736. this.scroll = false;
  27737. };
  27738. Ext.extend(Ext.grid.SplitDragZone, Ext.dd.DDProxy, {
  27739. fly: Ext.Element.fly,
  27740. b4StartDrag : function(x, y){
  27741. this.view.headersDisabled = true;
  27742. this.proxy.setHeight(this.view.mainWrap.getHeight());
  27743. var w = this.cm.getColumnWidth(this.cellIndex);
  27744. var minw = Math.max(w-this.grid.minColumnWidth, 0);
  27745. this.resetConstraints();
  27746. this.setXConstraint(minw, 1000);
  27747. this.setYConstraint(0, 0);
  27748. this.minX = x - minw;
  27749. this.maxX = x + 1000;
  27750. this.startPos = x;
  27751. Ext.dd.DDProxy.prototype.b4StartDrag.call(this, x, y);
  27752. },
  27753. handleMouseDown : function(e){
  27754. ev = Ext.EventObject.setEvent(e);
  27755. var t = this.fly(ev.getTarget());
  27756. if(t.hasClass("x-grid-split")){
  27757. this.cellIndex = this.view.getCellIndex(t.dom);
  27758. this.split = t.dom;
  27759. this.cm = this.grid.colModel;
  27760. if(this.cm.isResizable(this.cellIndex) && !this.cm.isFixed(this.cellIndex)){
  27761. Ext.grid.SplitDragZone.superclass.handleMouseDown.apply(this, arguments);
  27762. }
  27763. }
  27764. },
  27765. endDrag : function(e){
  27766. this.view.headersDisabled = false;
  27767. var endX = Math.max(this.minX, Ext.lib.Event.getPageX(e));
  27768. var diff = endX - this.startPos;
  27769. this.view.onColumnSplitterMoved(this.cellIndex, this.cm.getColumnWidth(this.cellIndex)+diff);
  27770. },
  27771. autoOffset : function(){
  27772. this.setDelta(0,0);
  27773. }
  27774. });
  27775. Ext.grid.GridDragZone = function(grid, config){
  27776. this.view = grid.getView();
  27777. Ext.grid.GridDragZone.superclass.constructor.call(this, this.view.mainBody.dom, config);
  27778. if(this.view.lockedBody){
  27779. this.setHandleElId(Ext.id(this.view.mainBody.dom));
  27780. this.setOuterHandleElId(Ext.id(this.view.lockedBody.dom));
  27781. }
  27782. this.scroll = false;
  27783. this.grid = grid;
  27784. this.ddel = document.createElement('div');
  27785. this.ddel.className = 'x-grid-dd-wrap';
  27786. };
  27787. Ext.extend(Ext.grid.GridDragZone, Ext.dd.DragZone, {
  27788. ddGroup : "GridDD",
  27789. getDragData : function(e){
  27790. var t = Ext.lib.Event.getTarget(e);
  27791. var rowIndex = this.view.findRowIndex(t);
  27792. if(rowIndex !== false){
  27793. var sm = this.grid.selModel;
  27794. if(!sm.isSelected(rowIndex) || e.hasModifier()){
  27795. sm.handleMouseDown(this.grid, rowIndex, e);
  27796. }
  27797. return {grid: this.grid, ddel: this.ddel, rowIndex: rowIndex, selections:sm.getSelections()};
  27798. }
  27799. return false;
  27800. },
  27801. onInitDrag : function(e){
  27802. var data = this.dragData;
  27803. this.ddel.innerHTML = this.grid.getDragDropText();
  27804. this.proxy.update(this.ddel);
  27805. // fire start drag?
  27806. },
  27807. afterRepair : function(){
  27808. this.dragging = false;
  27809. },
  27810. getRepairXY : function(e, data){
  27811. return false;
  27812. },
  27813. onEndDrag : function(data, e){
  27814. // fire end drag?
  27815. },
  27816. onValidDrop : function(dd, e, id){
  27817. // fire drag drop?
  27818. this.hideProxy();
  27819. },
  27820. beforeInvalidDrop : function(e, id){
  27821. }
  27822. });
  27823. Ext.grid.ColumnModel = function(config){
  27824. this.defaultWidth = 100;
  27825. this.defaultSortable = false;
  27826. if(config.columns){
  27827. Ext.apply(this, config);
  27828. this.setConfig(config.columns, true);
  27829. }else{
  27830. this.setConfig(config, true);
  27831. }
  27832. this.addEvents(
  27833. "widthchange",
  27834. "headerchange",
  27835. "hiddenchange",
  27836. "columnmoved",
  27837. // deprecated - to be removed
  27838. "columnlockchange",
  27839. "configchange"
  27840. );
  27841. Ext.grid.ColumnModel.superclass.constructor.call(this);
  27842. };
  27843. Ext.extend(Ext.grid.ColumnModel, Ext.util.Observable, {
  27844. getColumnId : function(index){
  27845. return this.config[index].id;
  27846. },
  27847. setConfig : function(config, initial){
  27848. if(!initial){ // cleanup
  27849. delete this.totalWidth;
  27850. for(var i = 0, len = this.config.length; i < len; i++){
  27851. var c = this.config[i];
  27852. if(c.editor){
  27853. c.editor.destroy();
  27854. }
  27855. }
  27856. }
  27857. this.config = config;
  27858. this.lookup = {};
  27859. // if no id, create one
  27860. for(var i = 0, len = config.length; i < len; i++){
  27861. var c = config[i];
  27862. if(typeof c.renderer == "string"){
  27863. c.renderer = Ext.util.Format[c.renderer];
  27864. }
  27865. if(typeof c.id == "undefined"){
  27866. c.id = i;
  27867. }
  27868. if(c.editor && c.editor.isFormField){
  27869. c.editor = new Ext.grid.GridEditor(c.editor);
  27870. }
  27871. this.lookup[c.id] = c;
  27872. }
  27873. if(!initial){
  27874. this.fireEvent('configchange', this);
  27875. }
  27876. },
  27877. getColumnById : function(id){
  27878. return this.lookup[id];
  27879. },
  27880. getIndexById : function(id){
  27881. for(var i = 0, len = this.config.length; i < len; i++){
  27882. if(this.config[i].id == id){
  27883. return i;
  27884. }
  27885. }
  27886. return -1;
  27887. },
  27888. moveColumn : function(oldIndex, newIndex){
  27889. var c = this.config[oldIndex];
  27890. this.config.splice(oldIndex, 1);
  27891. this.config.splice(newIndex, 0, c);
  27892. this.dataMap = null;
  27893. this.fireEvent("columnmoved", this, oldIndex, newIndex);
  27894. },
  27895. // deprecated - to be removed
  27896. isLocked : function(colIndex){
  27897. return this.config[colIndex].locked === true;
  27898. },
  27899. // deprecated - to be removed
  27900. setLocked : function(colIndex, value, suppressEvent){
  27901. if(this.isLocked(colIndex) == value){
  27902. return;
  27903. }
  27904. this.config[colIndex].locked = value;
  27905. if(!suppressEvent){
  27906. this.fireEvent("columnlockchange", this, colIndex, value);
  27907. }
  27908. },
  27909. // deprecated - to be removed
  27910. getTotalLockedWidth : function(){
  27911. var totalWidth = 0;
  27912. for(var i = 0; i < this.config.length; i++){
  27913. if(this.isLocked(i) && !this.isHidden(i)){
  27914. this.totalWidth += this.getColumnWidth(i);
  27915. }
  27916. }
  27917. return totalWidth;
  27918. },
  27919. // deprecated - to be removed
  27920. getLockedCount : function(){
  27921. for(var i = 0, len = this.config.length; i < len; i++){
  27922. if(!this.isLocked(i)){
  27923. return i;
  27924. }
  27925. }
  27926. },
  27927. getColumnCount : function(visibleOnly){
  27928. if(visibleOnly === true){
  27929. var c = 0;
  27930. for(var i = 0, len = this.config.length; i < len; i++){
  27931. if(!this.isHidden(i)){
  27932. c++;
  27933. }
  27934. }
  27935. return c;
  27936. }
  27937. return this.config.length;
  27938. },
  27939. getColumnsBy : function(fn, scope){
  27940. var r = [];
  27941. for(var i = 0, len = this.config.length; i < len; i++){
  27942. var c = this.config[i];
  27943. if(fn.call(scope||this, c, i) === true){
  27944. r[r.length] = c;
  27945. }
  27946. }
  27947. return r;
  27948. },
  27949. isSortable : function(col){
  27950. if(typeof this.config[col].sortable == "undefined"){
  27951. return this.defaultSortable;
  27952. }
  27953. return this.config[col].sortable;
  27954. },
  27955. isMenuDisabled : function(col){
  27956. return !!this.config[col].menuDisabled;
  27957. },
  27958. getRenderer : function(col){
  27959. if(!this.config[col].renderer){
  27960. return Ext.grid.ColumnModel.defaultRenderer;
  27961. }
  27962. return this.config[col].renderer;
  27963. },
  27964. setRenderer : function(col, fn){
  27965. this.config[col].renderer = fn;
  27966. },
  27967. getColumnWidth : function(col){
  27968. return this.config[col].width || this.defaultWidth;
  27969. },
  27970. setColumnWidth : function(col, width, suppressEvent){
  27971. this.config[col].width = width;
  27972. this.totalWidth = null;
  27973. if(!suppressEvent){
  27974. this.fireEvent("widthchange", this, col, width);
  27975. }
  27976. },
  27977. getTotalWidth : function(includeHidden){
  27978. if(!this.totalWidth){
  27979. this.totalWidth = 0;
  27980. for(var i = 0, len = this.config.length; i < len; i++){
  27981. if(includeHidden || !this.isHidden(i)){
  27982. this.totalWidth += this.getColumnWidth(i);
  27983. }
  27984. }
  27985. }
  27986. return this.totalWidth;
  27987. },
  27988. getColumnHeader : function(col){
  27989. return this.config[col].header;
  27990. },
  27991. setColumnHeader : function(col, header){
  27992. this.config[col].header = header;
  27993. this.fireEvent("headerchange", this, col, header);
  27994. },
  27995. getColumnTooltip : function(col){
  27996. return this.config[col].tooltip;
  27997. },
  27998. setColumnTooltip : function(col, tooltip){
  27999. this.config[col].tooltip = tooltip;
  28000. },
  28001. getDataIndex : function(col){
  28002. return this.config[col].dataIndex;
  28003. },
  28004. setDataIndex : function(col, dataIndex){
  28005. this.config[col].dataIndex = dataIndex;
  28006. },
  28007. findColumnIndex : function(dataIndex){
  28008. var c = this.config;
  28009. for(var i = 0, len = c.length; i < len; i++){
  28010. if(c[i].dataIndex == dataIndex){
  28011. return i;
  28012. }
  28013. }
  28014. return -1;
  28015. },
  28016. isCellEditable : function(colIndex, rowIndex){
  28017. return (this.config[colIndex].editable || (typeof this.config[colIndex].editable == "undefined" && this.config[colIndex].editor)) ? true : false;
  28018. },
  28019. getCellEditor : function(colIndex, rowIndex){
  28020. return this.config[colIndex].editor;
  28021. },
  28022. setEditable : function(col, editable){
  28023. this.config[col].editable = editable;
  28024. },
  28025. isHidden : function(colIndex){
  28026. return this.config[colIndex].hidden;
  28027. },
  28028. isFixed : function(colIndex){
  28029. return this.config[colIndex].fixed;
  28030. },
  28031. isResizable : function(colIndex){
  28032. return colIndex >= 0 && this.config[colIndex].resizable !== false && this.config[colIndex].fixed !== true;
  28033. },
  28034. setHidden : function(colIndex, hidden){
  28035. var c = this.config[colIndex];
  28036. if(c.hidden !== hidden){
  28037. c.hidden = hidden;
  28038. this.totalWidth = null;
  28039. this.fireEvent("hiddenchange", this, colIndex, hidden);
  28040. }
  28041. },
  28042. setEditor : function(col, editor){
  28043. this.config[col].editor = editor;
  28044. }
  28045. });
  28046. // private
  28047. Ext.grid.ColumnModel.defaultRenderer = function(value){
  28048. if(typeof value == "string" && value.length < 1){
  28049. return "&#160;";
  28050. }
  28051. return value;
  28052. };
  28053. // Alias for backwards compatibility
  28054. Ext.grid.DefaultColumnModel = Ext.grid.ColumnModel;
  28055. Ext.grid.AbstractSelectionModel = function(){
  28056. this.locked = false;
  28057. Ext.grid.AbstractSelectionModel.superclass.constructor.call(this);
  28058. };
  28059. Ext.extend(Ext.grid.AbstractSelectionModel, Ext.util.Observable, {
  28060. init : function(grid){
  28061. this.grid = grid;
  28062. this.initEvents();
  28063. },
  28064. lock : function(){
  28065. this.locked = true;
  28066. },
  28067. unlock : function(){
  28068. this.locked = false;
  28069. },
  28070. isLocked : function(){
  28071. return this.locked;
  28072. }
  28073. });
  28074. Ext.grid.RowSelectionModel = function(config){
  28075. Ext.apply(this, config);
  28076. this.selections = new Ext.util.MixedCollection(false, function(o){
  28077. return o.id;
  28078. });
  28079. this.last = false;
  28080. this.lastActive = false;
  28081. this.addEvents(
  28082. "selectionchange",
  28083. "beforerowselect",
  28084. "rowselect",
  28085. "rowdeselect"
  28086. );
  28087. Ext.grid.RowSelectionModel.superclass.constructor.call(this);
  28088. };
  28089. Ext.extend(Ext.grid.RowSelectionModel, Ext.grid.AbstractSelectionModel, {
  28090. singleSelect : false,
  28091. // private
  28092. initEvents : function(){
  28093. if(!this.grid.enableDragDrop && !this.grid.enableDrag){
  28094. this.grid.on("rowmousedown", this.handleMouseDown, this);
  28095. }else{ // allow click to work like normal
  28096. this.grid.on("rowclick", function(grid, rowIndex, e) {
  28097. if(e.button === 0 && !e.shiftKey && !e.ctrlKey) {
  28098. this.selectRow(rowIndex, false);
  28099. grid.view.focusRow(rowIndex);
  28100. }
  28101. }, this);
  28102. }
  28103. this.rowNav = new Ext.KeyNav(this.grid.getGridEl(), {
  28104. "up" : function(e){
  28105. if(!e.shiftKey || this.singleSelect){
  28106. this.selectPrevious(false);
  28107. }else if(this.last !== false && this.lastActive !== false){
  28108. var last = this.last;
  28109. this.selectRange(this.last, this.lastActive-1);
  28110. this.grid.getView().focusRow(this.lastActive);
  28111. if(last !== false){
  28112. this.last = last;
  28113. }
  28114. }else{
  28115. this.selectFirstRow();
  28116. }
  28117. },
  28118. "down" : function(e){
  28119. if(!e.shiftKey || this.singleSelect){
  28120. this.selectNext(false);
  28121. }else if(this.last !== false && this.lastActive !== false){
  28122. var last = this.last;
  28123. this.selectRange(this.last, this.lastActive+1);
  28124. this.grid.getView().focusRow(this.lastActive);
  28125. if(last !== false){
  28126. this.last = last;
  28127. }
  28128. }else{
  28129. this.selectFirstRow();
  28130. }
  28131. },
  28132. scope: this
  28133. });
  28134. var view = this.grid.view;
  28135. view.on("refresh", this.onRefresh, this);
  28136. view.on("rowupdated", this.onRowUpdated, this);
  28137. view.on("rowremoved", this.onRemove, this);
  28138. },
  28139. // private
  28140. onRefresh : function(){
  28141. var ds = this.grid.store, index;
  28142. var s = this.getSelections();
  28143. this.clearSelections(true);
  28144. for(var i = 0, len = s.length; i < len; i++){
  28145. var r = s[i];
  28146. if((index = ds.indexOfId(r.id)) != -1){
  28147. this.selectRow(index, true);
  28148. }
  28149. }
  28150. if(s.length != this.selections.getCount()){
  28151. this.fireEvent("selectionchange", this);
  28152. }
  28153. },
  28154. // private
  28155. onRemove : function(v, index, r){
  28156. if(this.selections.remove(r) !== false){
  28157. this.fireEvent('selectionchange', this);
  28158. }
  28159. },
  28160. // private
  28161. onRowUpdated : function(v, index, r){
  28162. if(this.isSelected(r)){
  28163. v.onRowSelect(index);
  28164. }
  28165. },
  28166. selectRecords : function(records, keepExisting){
  28167. if(!keepExisting){
  28168. this.clearSelections();
  28169. }
  28170. var ds = this.grid.store;
  28171. for(var i = 0, len = records.length; i < len; i++){
  28172. this.selectRow(ds.indexOf(records[i]), true);
  28173. }
  28174. },
  28175. getCount : function(){
  28176. return this.selections.length;
  28177. },
  28178. selectFirstRow : function(){
  28179. this.selectRow(0);
  28180. },
  28181. selectLastRow : function(keepExisting){
  28182. this.selectRow(this.grid.store.getCount() - 1, keepExisting);
  28183. },
  28184. selectNext : function(keepExisting){
  28185. if(this.hasNext()){
  28186. this.selectRow(this.last+1, keepExisting);
  28187. this.grid.getView().focusRow(this.last);
  28188. return true;
  28189. }
  28190. return false;
  28191. },
  28192. selectPrevious : function(keepExisting){
  28193. if(this.hasPrevious()){
  28194. this.selectRow(this.last-1, keepExisting);
  28195. this.grid.getView().focusRow(this.last);
  28196. return true;
  28197. }
  28198. return false;
  28199. },
  28200. hasNext : function(){
  28201. return this.last !== false && (this.last+1) < this.grid.store.getCount();
  28202. },
  28203. hasPrevious : function(){
  28204. return !!this.last;
  28205. },
  28206. getSelections : function(){
  28207. return [].concat(this.selections.items);
  28208. },
  28209. getSelected : function(){
  28210. return this.selections.itemAt(0);
  28211. },
  28212. each : function(fn, scope){
  28213. var s = this.getSelections();
  28214. for(var i = 0, len = s.length; i < len; i++){
  28215. if(fn.call(scope || this, s[i], i) === false){
  28216. return false;
  28217. }
  28218. }
  28219. return true;
  28220. },
  28221. clearSelections : function(fast){
  28222. if(this.isLocked()) return;
  28223. if(fast !== true){
  28224. var ds = this.grid.store;
  28225. var s = this.selections;
  28226. s.each(function(r){
  28227. this.deselectRow(ds.indexOfId(r.id));
  28228. }, this);
  28229. s.clear();
  28230. }else{
  28231. this.selections.clear();
  28232. }
  28233. this.last = false;
  28234. },
  28235. selectAll : function(){
  28236. if(this.isLocked()) return;
  28237. this.selections.clear();
  28238. for(var i = 0, len = this.grid.store.getCount(); i < len; i++){
  28239. this.selectRow(i, true);
  28240. }
  28241. },
  28242. hasSelection : function(){
  28243. return this.selections.length > 0;
  28244. },
  28245. isSelected : function(index){
  28246. var r = typeof index == "number" ? this.grid.store.getAt(index) : index;
  28247. return (r && this.selections.key(r.id) ? true : false);
  28248. },
  28249. isIdSelected : function(id){
  28250. return (this.selections.key(id) ? true : false);
  28251. },
  28252. // private
  28253. handleMouseDown : function(g, rowIndex, e){
  28254. if(e.button !== 0 || this.isLocked()){
  28255. return;
  28256. };
  28257. var view = this.grid.getView();
  28258. if(e.shiftKey && !this.singleSelect && this.last !== false){
  28259. var last = this.last;
  28260. this.selectRange(last, rowIndex, e.ctrlKey);
  28261. this.last = last; // reset the last
  28262. view.focusRow(rowIndex);
  28263. }else{
  28264. var isSelected = this.isSelected(rowIndex);
  28265. if(e.ctrlKey && isSelected){
  28266. this.deselectRow(rowIndex);
  28267. }else if(!isSelected || this.getCount() > 1){
  28268. this.selectRow(rowIndex, e.ctrlKey || e.shiftKey);
  28269. view.focusRow(rowIndex);
  28270. }
  28271. }
  28272. },
  28273. selectRows : function(rows, keepExisting){
  28274. if(!keepExisting){
  28275. this.clearSelections();
  28276. }
  28277. for(var i = 0, len = rows.length; i < len; i++){
  28278. this.selectRow(rows[i], true);
  28279. }
  28280. },
  28281. selectRange : function(startRow, endRow, keepExisting){
  28282. if(this.isLocked()) return;
  28283. if(!keepExisting){
  28284. this.clearSelections();
  28285. }
  28286. if(startRow <= endRow){
  28287. for(var i = startRow; i <= endRow; i++){
  28288. this.selectRow(i, true);
  28289. }
  28290. }else{
  28291. for(var i = startRow; i >= endRow; i--){
  28292. this.selectRow(i, true);
  28293. }
  28294. }
  28295. },
  28296. deselectRange : function(startRow, endRow, preventViewNotify){
  28297. if(this.isLocked()) return;
  28298. for(var i = startRow; i <= endRow; i++){
  28299. this.deselectRow(i, preventViewNotify);
  28300. }
  28301. },
  28302. selectRow : function(index, keepExisting, preventViewNotify){
  28303. if(this.isLocked() || (index < 0 || index >= this.grid.store.getCount()) || this.isSelected(index)) return;
  28304. var r = this.grid.store.getAt(index);
  28305. if(r && this.fireEvent("beforerowselect", this, index, keepExisting, r) !== false){
  28306. if(!keepExisting || this.singleSelect){
  28307. this.clearSelections();
  28308. }
  28309. this.selections.add(r);
  28310. this.last = this.lastActive = index;
  28311. if(!preventViewNotify){
  28312. this.grid.getView().onRowSelect(index);
  28313. }
  28314. this.fireEvent("rowselect", this, index, r);
  28315. this.fireEvent("selectionchange", this);
  28316. }
  28317. },
  28318. deselectRow : function(index, preventViewNotify){
  28319. if(this.isLocked()) return;
  28320. if(this.last == index){
  28321. this.last = false;
  28322. }
  28323. if(this.lastActive == index){
  28324. this.lastActive = false;
  28325. }
  28326. var r = this.grid.store.getAt(index);
  28327. if(r){
  28328. this.selections.remove(r);
  28329. if(!preventViewNotify){
  28330. this.grid.getView().onRowDeselect(index);
  28331. }
  28332. this.fireEvent("rowdeselect", this, index, r);
  28333. this.fireEvent("selectionchange", this);
  28334. }
  28335. },
  28336. // private
  28337. restoreLast : function(){
  28338. if(this._last){
  28339. this.last = this._last;
  28340. }
  28341. },
  28342. // private
  28343. acceptsNav : function(row, col, cm){
  28344. return !cm.isHidden(col) && cm.isCellEditable(col, row);
  28345. },
  28346. // private
  28347. onEditorKey : function(field, e){
  28348. var k = e.getKey(), newCell, g = this.grid, ed = g.activeEditor;
  28349. var shift = e.shiftKey;
  28350. if(k == e.TAB){
  28351. e.stopEvent();
  28352. ed.completeEdit();
  28353. if(shift){
  28354. newCell = g.walkCells(ed.row, ed.col-1, -1, this.acceptsNav, this);
  28355. }else{
  28356. newCell = g.walkCells(ed.row, ed.col+1, 1, this.acceptsNav, this);
  28357. }
  28358. }else if(k == e.ENTER){
  28359. e.stopEvent();
  28360. ed.completeEdit();
  28361. if(this.moveEditorOnEnter !== false){
  28362. if(shift){
  28363. newCell = g.walkCells(ed.row - 1, ed.col, -1, this.acceptsNav, this);
  28364. }else{
  28365. newCell = g.walkCells(ed.row + 1, ed.col, 1, this.acceptsNav, this);
  28366. }
  28367. }
  28368. }else if(k == e.ESC){
  28369. ed.cancelEdit();
  28370. }
  28371. if(newCell){
  28372. g.startEditing(newCell[0], newCell[1]);
  28373. }
  28374. }
  28375. });
  28376. Ext.grid.CellSelectionModel = function(config){
  28377. Ext.apply(this, config);
  28378. this.selection = null;
  28379. this.addEvents(
  28380. "beforecellselect",
  28381. "cellselect",
  28382. "selectionchange"
  28383. );
  28384. Ext.grid.CellSelectionModel.superclass.constructor.call(this);
  28385. };
  28386. Ext.extend(Ext.grid.CellSelectionModel, Ext.grid.AbstractSelectionModel, {
  28387. initEvents : function(){
  28388. this.grid.on("cellmousedown", this.handleMouseDown, this);
  28389. this.grid.getGridEl().on(Ext.isIE || Ext.isSafari3 ? "keydown" : "keypress", this.handleKeyDown, this);
  28390. var view = this.grid.view;
  28391. view.on("refresh", this.onViewChange, this);
  28392. view.on("rowupdated", this.onRowUpdated, this);
  28393. view.on("beforerowremoved", this.clearSelections, this);
  28394. view.on("beforerowsinserted", this.clearSelections, this);
  28395. if(this.grid.isEditor){
  28396. this.grid.on("beforeedit", this.beforeEdit, this);
  28397. }
  28398. },
  28399. //private
  28400. beforeEdit : function(e){
  28401. this.select(e.row, e.column, false, true, e.record);
  28402. },
  28403. //private
  28404. onRowUpdated : function(v, index, r){
  28405. if(this.selection && this.selection.record == r){
  28406. v.onCellSelect(index, this.selection.cell[1]);
  28407. }
  28408. },
  28409. //private
  28410. onViewChange : function(){
  28411. this.clearSelections(true);
  28412. },
  28413. getSelectedCell : function(){
  28414. return this.selection ? this.selection.cell : null;
  28415. },
  28416. clearSelections : function(preventNotify){
  28417. var s = this.selection;
  28418. if(s){
  28419. if(preventNotify !== true){
  28420. this.grid.view.onCellDeselect(s.cell[0], s.cell[1]);
  28421. }
  28422. this.selection = null;
  28423. this.fireEvent("selectionchange", this, null);
  28424. }
  28425. },
  28426. hasSelection : function(){
  28427. return this.selection ? true : false;
  28428. },
  28429. handleMouseDown : function(g, row, cell, e){
  28430. if(e.button !== 0 || this.isLocked()){
  28431. return;
  28432. };
  28433. this.select(row, cell);
  28434. },
  28435. select : function(rowIndex, colIndex, preventViewNotify, preventFocus, r){
  28436. if(this.fireEvent("beforecellselect", this, rowIndex, colIndex) !== false){
  28437. this.clearSelections();
  28438. r = r || this.grid.store.getAt(rowIndex);
  28439. this.selection = {
  28440. record : r,
  28441. cell : [rowIndex, colIndex]
  28442. };
  28443. if(!preventViewNotify){
  28444. var v = this.grid.getView();
  28445. v.onCellSelect(rowIndex, colIndex);
  28446. if(preventFocus !== true){
  28447. v.focusCell(rowIndex, colIndex);
  28448. }
  28449. }
  28450. this.fireEvent("cellselect", this, rowIndex, colIndex);
  28451. this.fireEvent("selectionchange", this, this.selection);
  28452. }
  28453. },
  28454. //private
  28455. isSelectable : function(rowIndex, colIndex, cm){
  28456. return !cm.isHidden(colIndex);
  28457. },
  28458. handleKeyDown : function(e){
  28459. if(!e.isNavKeyPress()){
  28460. return;
  28461. }
  28462. var g = this.grid, s = this.selection;
  28463. if(!s){
  28464. e.stopEvent();
  28465. var cell = g.walkCells(0, 0, 1, this.isSelectable, this);
  28466. if(cell){
  28467. this.select(cell[0], cell[1]);
  28468. }
  28469. return;
  28470. }
  28471. var sm = this;
  28472. var walk = function(row, col, step){
  28473. return g.walkCells(row, col, step, sm.isSelectable, sm);
  28474. };
  28475. var k = e.getKey(), r = s.cell[0], c = s.cell[1];
  28476. var newCell;
  28477. switch(k){
  28478. case e.TAB:
  28479. if(e.shiftKey){
  28480. newCell = walk(r, c-1, -1);
  28481. }else{
  28482. newCell = walk(r, c+1, 1);
  28483. }
  28484. break;
  28485. case e.DOWN:
  28486. newCell = walk(r+1, c, 1);
  28487. break;
  28488. case e.UP:
  28489. newCell = walk(r-1, c, -1);
  28490. break;
  28491. case e.RIGHT:
  28492. newCell = walk(r, c+1, 1);
  28493. break;
  28494. case e.LEFT:
  28495. newCell = walk(r, c-1, -1);
  28496. break;
  28497. case e.ENTER:
  28498. if(g.isEditor && !g.editing){
  28499. g.startEditing(r, c);
  28500. e.stopEvent();
  28501. return;
  28502. }
  28503. break;
  28504. };
  28505. if(newCell){
  28506. this.select(newCell[0], newCell[1]);
  28507. e.stopEvent();
  28508. }
  28509. },
  28510. acceptsNav : function(row, col, cm){
  28511. return !cm.isHidden(col) && cm.isCellEditable(col, row);
  28512. },
  28513. onEditorKey : function(field, e){
  28514. var k = e.getKey(), newCell, g = this.grid, ed = g.activeEditor;
  28515. if(k == e.TAB){
  28516. if(e.shiftKey){
  28517. newCell = g.walkCells(ed.row, ed.col-1, -1, this.acceptsNav, this);
  28518. }else{
  28519. newCell = g.walkCells(ed.row, ed.col+1, 1, this.acceptsNav, this);
  28520. }
  28521. e.stopEvent();
  28522. }else if(k == e.ENTER){
  28523. ed.completeEdit();
  28524. e.stopEvent();
  28525. }else if(k == e.ESC){
  28526. e.stopEvent();
  28527. ed.cancelEdit();
  28528. }
  28529. if(newCell){
  28530. g.startEditing(newCell[0], newCell[1]);
  28531. }
  28532. }
  28533. });
  28534. Ext.grid.EditorGridPanel = Ext.extend(Ext.grid.GridPanel, {
  28535. clicksToEdit: 2,
  28536. // private
  28537. isEditor : true,
  28538. // private
  28539. detectEdit: false,
  28540. autoEncode : false,
  28541. // private
  28542. trackMouseOver: false, // causes very odd FF errors
  28543. // private
  28544. initComponent : function(){
  28545. Ext.grid.EditorGridPanel.superclass.initComponent.call(this);
  28546. if(!this.selModel){
  28547. this.selModel = new Ext.grid.CellSelectionModel();
  28548. }
  28549. this.activeEditor = null;
  28550. this.addEvents(
  28551. "beforeedit",
  28552. "afteredit",
  28553. "validateedit"
  28554. );
  28555. },
  28556. // private
  28557. initEvents : function(){
  28558. Ext.grid.EditorGridPanel.superclass.initEvents.call(this);
  28559. this.on("bodyscroll", this.stopEditing, this, [true]);
  28560. this.on("columnresize", this.stopEditing, this, [true]);
  28561. if(this.clicksToEdit == 1){
  28562. this.on("cellclick", this.onCellDblClick, this);
  28563. }else {
  28564. if(this.clicksToEdit == 'auto' && this.view.mainBody){
  28565. this.view.mainBody.on("mousedown", this.onAutoEditClick, this);
  28566. }
  28567. this.on("celldblclick", this.onCellDblClick, this);
  28568. }
  28569. },
  28570. // private
  28571. onCellDblClick : function(g, row, col){
  28572. this.startEditing(row, col);
  28573. },
  28574. // private
  28575. onAutoEditClick : function(e, t){
  28576. if(e.button !== 0){
  28577. return;
  28578. }
  28579. var row = this.view.findRowIndex(t);
  28580. var col = this.view.findCellIndex(t);
  28581. if(row !== false && col !== false){
  28582. this.stopEditing();
  28583. if(this.selModel.getSelectedCell){ // cell sm
  28584. var sc = this.selModel.getSelectedCell();
  28585. if(sc && sc.cell[0] === row && sc.cell[1] === col){
  28586. this.startEditing(row, col);
  28587. }
  28588. }else{
  28589. if(this.selModel.isSelected(row)){
  28590. this.startEditing(row, col);
  28591. }
  28592. }
  28593. }
  28594. },
  28595. // private
  28596. onEditComplete : function(ed, value, startValue){
  28597. this.editing = false;
  28598. this.activeEditor = null;
  28599. ed.un("specialkey", this.selModel.onEditorKey, this.selModel);
  28600. var r = ed.record;
  28601. var field = this.colModel.getDataIndex(ed.col);
  28602. value = this.postEditValue(value, startValue, r, field);
  28603. if(String(value) !== String(startValue)){
  28604. var e = {
  28605. grid: this,
  28606. record: r,
  28607. field: field,
  28608. originalValue: startValue,
  28609. value: value,
  28610. row: ed.row,
  28611. column: ed.col,
  28612. cancel:false
  28613. };
  28614. if(this.fireEvent("validateedit", e) !== false && !e.cancel){
  28615. r.set(field, e.value);
  28616. delete e.cancel;
  28617. this.fireEvent("afteredit", e);
  28618. }
  28619. }
  28620. this.view.focusCell(ed.row, ed.col);
  28621. },
  28622. startEditing : function(row, col){
  28623. this.stopEditing();
  28624. if(this.colModel.isCellEditable(col, row)){
  28625. this.view.ensureVisible(row, col, true);
  28626. var r = this.store.getAt(row);
  28627. var field = this.colModel.getDataIndex(col);
  28628. var e = {
  28629. grid: this,
  28630. record: r,
  28631. field: field,
  28632. value: r.data[field],
  28633. row: row,
  28634. column: col,
  28635. cancel:false
  28636. };
  28637. if(this.fireEvent("beforeedit", e) !== false && !e.cancel){
  28638. this.editing = true;
  28639. var ed = this.colModel.getCellEditor(col, row);
  28640. if(!ed.rendered){
  28641. ed.render(this.view.getEditorParent(ed));
  28642. }
  28643. (function(){ // complex but required for focus issues in safari, ie and opera
  28644. ed.row = row;
  28645. ed.col = col;
  28646. ed.record = r;
  28647. ed.on("complete", this.onEditComplete, this, {single: true});
  28648. ed.on("specialkey", this.selModel.onEditorKey, this.selModel);
  28649. this.activeEditor = ed;
  28650. var v = this.preEditValue(r, field);
  28651. ed.startEdit(this.view.getCell(row, col).firstChild, v === undefined ? '' : v);
  28652. }).defer(50, this);
  28653. }
  28654. }
  28655. },
  28656. // private
  28657. preEditValue : function(r, field){
  28658. var value = r.data[field];
  28659. return this.autoEncode && typeof value == 'string' ? Ext.util.Format.htmlDecode(value) : value;
  28660. },
  28661. // private
  28662. postEditValue : function(value, originalValue, r, field){
  28663. return this.autoEncode && typeof value == 'string' ? Ext.util.Format.htmlEncode(value) : value;
  28664. },
  28665. stopEditing : function(cancel){
  28666. if(this.activeEditor){
  28667. this.activeEditor[cancel === true ? 'cancelEdit' : 'completeEdit']();
  28668. }
  28669. this.activeEditor = null;
  28670. },
  28671. // private
  28672. onDestroy: function() {
  28673. if(this.rendered){
  28674. var cols = this.colModel.config;
  28675. for(var i = 0, len = cols.length; i < len; i++){
  28676. var c = cols[i];
  28677. Ext.destroy(c.editor);
  28678. }
  28679. }
  28680. Ext.grid.EditorGridPanel.superclass.onDestroy.call(this);
  28681. }
  28682. });
  28683. Ext.reg('editorgrid', Ext.grid.EditorGridPanel);
  28684. // private
  28685. // This is a support class used internally by the Grid components
  28686. Ext.grid.GridEditor = function(field, config){
  28687. Ext.grid.GridEditor.superclass.constructor.call(this, field, config);
  28688. field.monitorTab = false;
  28689. };
  28690. Ext.extend(Ext.grid.GridEditor, Ext.Editor, {
  28691. alignment: "tl-tl",
  28692. autoSize: "width",
  28693. hideEl : false,
  28694. cls: "x-small-editor x-grid-editor",
  28695. shim:false,
  28696. shadow:false
  28697. });
  28698. Ext.grid.PropertyRecord = Ext.data.Record.create([
  28699. {name:'name',type:'string'}, 'value'
  28700. ]);
  28701. Ext.grid.PropertyStore = function(grid, source){
  28702. this.grid = grid;
  28703. this.store = new Ext.data.Store({
  28704. recordType : Ext.grid.PropertyRecord
  28705. });
  28706. this.store.on('update', this.onUpdate, this);
  28707. if(source){
  28708. this.setSource(source);
  28709. }
  28710. Ext.grid.PropertyStore.superclass.constructor.call(this);
  28711. };
  28712. Ext.extend(Ext.grid.PropertyStore, Ext.util.Observable, {
  28713. // protected - should only be called by the grid. Use grid.setSource instead.
  28714. setSource : function(o){
  28715. this.source = o;
  28716. this.store.removeAll();
  28717. var data = [];
  28718. for(var k in o){
  28719. if(this.isEditableValue(o[k])){
  28720. data.push(new Ext.grid.PropertyRecord({name: k, value: o[k]}, k));
  28721. }
  28722. }
  28723. this.store.loadRecords({records: data}, {}, true);
  28724. },
  28725. // private
  28726. onUpdate : function(ds, record, type){
  28727. if(type == Ext.data.Record.EDIT){
  28728. var v = record.data['value'];
  28729. var oldValue = record.modified['value'];
  28730. if(this.grid.fireEvent('beforepropertychange', this.source, record.id, v, oldValue) !== false){
  28731. this.source[record.id] = v;
  28732. record.commit();
  28733. this.grid.fireEvent('propertychange', this.source, record.id, v, oldValue);
  28734. }else{
  28735. record.reject();
  28736. }
  28737. }
  28738. },
  28739. // private
  28740. getProperty : function(row){
  28741. return this.store.getAt(row);
  28742. },
  28743. // private
  28744. isEditableValue: function(val){
  28745. if(Ext.isDate(val)){
  28746. return true;
  28747. }else if(typeof val == 'object' || typeof val == 'function'){
  28748. return false;
  28749. }
  28750. return true;
  28751. },
  28752. // private
  28753. setValue : function(prop, value){
  28754. this.source[prop] = value;
  28755. this.store.getById(prop).set('value', value);
  28756. },
  28757. // protected - should only be called by the grid. Use grid.getSource instead.
  28758. getSource : function(){
  28759. return this.source;
  28760. }
  28761. });
  28762. Ext.grid.PropertyColumnModel = function(grid, store){
  28763. this.grid = grid;
  28764. var g = Ext.grid;
  28765. g.PropertyColumnModel.superclass.constructor.call(this, [
  28766. {header: this.nameText, width:50, sortable: true, dataIndex:'name', id: 'name', menuDisabled:true},
  28767. {header: this.valueText, width:50, resizable:false, dataIndex: 'value', id: 'value', menuDisabled:true}
  28768. ]);
  28769. this.store = store;
  28770. this.bselect = Ext.DomHelper.append(document.body, {
  28771. tag: 'select', cls: 'x-grid-editor x-hide-display', children: [
  28772. {tag: 'option', value: 'true', html: 'true'},
  28773. {tag: 'option', value: 'false', html: 'false'}
  28774. ]
  28775. });
  28776. var f = Ext.form;
  28777. var bfield = new f.Field({
  28778. el:this.bselect,
  28779. bselect : this.bselect,
  28780. autoShow: true,
  28781. getValue : function(){
  28782. return this.bselect.value == 'true';
  28783. }
  28784. });
  28785. this.editors = {
  28786. 'date' : new g.GridEditor(new f.DateField({selectOnFocus:true})),
  28787. 'string' : new g.GridEditor(new f.TextField({selectOnFocus:true})),
  28788. 'number' : new g.GridEditor(new f.NumberField({selectOnFocus:true, style:'text-align:left;'})),
  28789. 'boolean' : new g.GridEditor(bfield)
  28790. };
  28791. this.renderCellDelegate = this.renderCell.createDelegate(this);
  28792. this.renderPropDelegate = this.renderProp.createDelegate(this);
  28793. };
  28794. Ext.extend(Ext.grid.PropertyColumnModel, Ext.grid.ColumnModel, {
  28795. // private - strings used for locale support
  28796. nameText : 'Name',
  28797. valueText : 'Value',
  28798. dateFormat : 'm/j/Y',
  28799. // private
  28800. renderDate : function(dateVal){
  28801. return dateVal.dateFormat(this.dateFormat);
  28802. },
  28803. // private
  28804. renderBool : function(bVal){
  28805. return bVal ? 'true' : 'false';
  28806. },
  28807. // private
  28808. isCellEditable : function(colIndex, rowIndex){
  28809. return colIndex == 1;
  28810. },
  28811. // private
  28812. getRenderer : function(col){
  28813. return col == 1 ?
  28814. this.renderCellDelegate : this.renderPropDelegate;
  28815. },
  28816. // private
  28817. renderProp : function(v){
  28818. return this.getPropertyName(v);
  28819. },
  28820. // private
  28821. renderCell : function(val){
  28822. var rv = val;
  28823. if(Ext.isDate(val)){
  28824. rv = this.renderDate(val);
  28825. }else if(typeof val == 'boolean'){
  28826. rv = this.renderBool(val);
  28827. }
  28828. return Ext.util.Format.htmlEncode(rv);
  28829. },
  28830. // private
  28831. getPropertyName : function(name){
  28832. var pn = this.grid.propertyNames;
  28833. return pn && pn[name] ? pn[name] : name;
  28834. },
  28835. // private
  28836. getCellEditor : function(colIndex, rowIndex){
  28837. var p = this.store.getProperty(rowIndex);
  28838. var n = p.data['name'], val = p.data['value'];
  28839. if(this.grid.customEditors[n]){
  28840. return this.grid.customEditors[n];
  28841. }
  28842. if(Ext.isDate(val)){
  28843. return this.editors['date'];
  28844. }else if(typeof val == 'number'){
  28845. return this.editors['number'];
  28846. }else if(typeof val == 'boolean'){
  28847. return this.editors['boolean'];
  28848. }else{
  28849. return this.editors['string'];
  28850. }
  28851. }
  28852. });
  28853. Ext.grid.PropertyGrid = Ext.extend(Ext.grid.EditorGridPanel, {
  28854. // private config overrides
  28855. enableColumnMove:false,
  28856. stripeRows:false,
  28857. trackMouseOver: false,
  28858. clicksToEdit:1,
  28859. enableHdMenu : false,
  28860. viewConfig : {
  28861. forceFit:true
  28862. },
  28863. // private
  28864. initComponent : function(){
  28865. this.customEditors = this.customEditors || {};
  28866. this.lastEditRow = null;
  28867. var store = new Ext.grid.PropertyStore(this);
  28868. this.propStore = store;
  28869. var cm = new Ext.grid.PropertyColumnModel(this, store);
  28870. store.store.sort('name', 'ASC');
  28871. this.addEvents(
  28872. 'beforepropertychange',
  28873. 'propertychange'
  28874. );
  28875. this.cm = cm;
  28876. this.ds = store.store;
  28877. Ext.grid.PropertyGrid.superclass.initComponent.call(this);
  28878. this.selModel.on('beforecellselect', function(sm, rowIndex, colIndex){
  28879. if(colIndex === 0){
  28880. this.startEditing.defer(200, this, [rowIndex, 1]);
  28881. return false;
  28882. }
  28883. }, this);
  28884. },
  28885. // private
  28886. onRender : function(){
  28887. Ext.grid.PropertyGrid.superclass.onRender.apply(this, arguments);
  28888. this.getGridEl().addClass('x-props-grid');
  28889. },
  28890. // private
  28891. afterRender: function(){
  28892. Ext.grid.PropertyGrid.superclass.afterRender.apply(this, arguments);
  28893. if(this.source){
  28894. this.setSource(this.source);
  28895. }
  28896. },
  28897. setSource : function(source){
  28898. this.propStore.setSource(source);
  28899. },
  28900. getSource : function(){
  28901. return this.propStore.getSource();
  28902. }
  28903. });
  28904. Ext.reg("propertygrid", Ext.grid.PropertyGrid);
  28905. Ext.grid.RowNumberer = function(config){
  28906. Ext.apply(this, config);
  28907. if(this.rowspan){
  28908. this.renderer = this.renderer.createDelegate(this);
  28909. }
  28910. };
  28911. Ext.grid.RowNumberer.prototype = {
  28912. header: "",
  28913. width: 23,
  28914. sortable: false,
  28915. // private
  28916. fixed:true,
  28917. menuDisabled:true,
  28918. dataIndex: '',
  28919. id: 'numberer',
  28920. rowspan: undefined,
  28921. // private
  28922. renderer : function(v, p, record, rowIndex){
  28923. if(this.rowspan){
  28924. p.cellAttr = 'rowspan="'+this.rowspan+'"';
  28925. }
  28926. return rowIndex+1;
  28927. }
  28928. };
  28929. Ext.grid.CheckboxSelectionModel = Ext.extend(Ext.grid.RowSelectionModel, {
  28930. header: '<div class="x-grid3-hd-checker">&#160;</div>',
  28931. width: 20,
  28932. sortable: false,
  28933. // private
  28934. menuDisabled:true,
  28935. fixed:true,
  28936. dataIndex: '',
  28937. id: 'checker',
  28938. // private
  28939. initEvents : function(){
  28940. Ext.grid.CheckboxSelectionModel.superclass.initEvents.call(this);
  28941. this.grid.on('render', function(){
  28942. var view = this.grid.getView();
  28943. view.mainBody.on('mousedown', this.onMouseDown, this);
  28944. Ext.fly(view.innerHd).on('mousedown', this.onHdMouseDown, this);
  28945. }, this);
  28946. },
  28947. // private
  28948. onMouseDown : function(e, t){
  28949. if(e.button === 0 && t.className == 'x-grid3-row-checker'){ // Only fire if left-click
  28950. e.stopEvent();
  28951. var row = e.getTarget('.x-grid3-row');
  28952. if(row){
  28953. var index = row.rowIndex;
  28954. if(this.isSelected(index)){
  28955. this.deselectRow(index);
  28956. }else{
  28957. this.selectRow(index, true);
  28958. }
  28959. }
  28960. }
  28961. },
  28962. // private
  28963. onHdMouseDown : function(e, t){
  28964. if(t.className == 'x-grid3-hd-checker'){
  28965. e.stopEvent();
  28966. var hd = Ext.fly(t.parentNode);
  28967. var isChecked = hd.hasClass('x-grid3-hd-checker-on');
  28968. if(isChecked){
  28969. hd.removeClass('x-grid3-hd-checker-on');
  28970. this.clearSelections();
  28971. }else{
  28972. hd.addClass('x-grid3-hd-checker-on');
  28973. this.selectAll();
  28974. }
  28975. }
  28976. },
  28977. // private
  28978. renderer : function(v, p, record){
  28979. return '<div class="x-grid3-row-checker">&#160;</div>';
  28980. }
  28981. });
  28982. Ext.LoadMask = function(el, config){
  28983. this.el = Ext.get(el);
  28984. Ext.apply(this, config);
  28985. if(this.store){
  28986. this.store.on('beforeload', this.onBeforeLoad, this);
  28987. this.store.on('load', this.onLoad, this);
  28988. this.store.on('loadexception', this.onLoad, this);
  28989. this.removeMask = Ext.value(this.removeMask, false);
  28990. }else{
  28991. var um = this.el.getUpdater();
  28992. um.showLoadIndicator = false; // disable the default indicator
  28993. um.on('beforeupdate', this.onBeforeLoad, this);
  28994. um.on('update', this.onLoad, this);
  28995. um.on('failure', this.onLoad, this);
  28996. this.removeMask = Ext.value(this.removeMask, true);
  28997. }
  28998. };
  28999. Ext.LoadMask.prototype = {
  29000. msg : 'Loading...',
  29001. msgCls : 'x-mask-loading',
  29002. disabled: false,
  29003. disable : function(){
  29004. this.disabled = true;
  29005. },
  29006. enable : function(){
  29007. this.disabled = false;
  29008. },
  29009. // private
  29010. onLoad : function(){
  29011. this.el.unmask(this.removeMask);
  29012. },
  29013. // private
  29014. onBeforeLoad : function(){
  29015. if(!this.disabled){
  29016. this.el.mask(this.msg, this.msgCls);
  29017. }
  29018. },
  29019. show: function(){
  29020. this.onBeforeLoad();
  29021. },
  29022. hide: function(){
  29023. this.onLoad();
  29024. },
  29025. // private
  29026. destroy : function(){
  29027. if(this.store){
  29028. this.store.un('beforeload', this.onBeforeLoad, this);
  29029. this.store.un('load', this.onLoad, this);
  29030. this.store.un('loadexception', this.onLoad, this);
  29031. }else{
  29032. var um = this.el.getUpdater();
  29033. um.un('beforeupdate', this.onBeforeLoad, this);
  29034. um.un('update', this.onLoad, this);
  29035. um.un('failure', this.onLoad, this);
  29036. }
  29037. }
  29038. };
  29039. Ext.ProgressBar = Ext.extend(Ext.BoxComponent, {
  29040. baseCls : 'x-progress',
  29041. animate : false,
  29042. // private
  29043. waitTimer : null,
  29044. // private
  29045. initComponent : function(){
  29046. Ext.ProgressBar.superclass.initComponent.call(this);
  29047. this.addEvents(
  29048. "update"
  29049. );
  29050. },
  29051. // private
  29052. onRender : function(ct, position){
  29053. Ext.ProgressBar.superclass.onRender.call(this, ct, position);
  29054. var tpl = new Ext.Template(
  29055. '<div class="{cls}-wrap">',
  29056. '<div class="{cls}-inner">',
  29057. '<div class="{cls}-bar">',
  29058. '<div class="{cls}-text">',
  29059. '<div>&#160;</div>',
  29060. '</div>',
  29061. '</div>',
  29062. '<div class="{cls}-text {cls}-text-back">',
  29063. '<div>&#160;</div>',
  29064. '</div>',
  29065. '</div>',
  29066. '</div>'
  29067. );
  29068. if(position){
  29069. this.el = tpl.insertBefore(position, {cls: this.baseCls}, true);
  29070. }else{
  29071. this.el = tpl.append(ct, {cls: this.baseCls}, true);
  29072. }
  29073. if(this.id){
  29074. this.el.dom.id = this.id;
  29075. }
  29076. var inner = this.el.dom.firstChild;
  29077. this.progressBar = Ext.get(inner.firstChild);
  29078. if(this.textEl){
  29079. //use an external text el
  29080. this.textEl = Ext.get(this.textEl);
  29081. delete this.textTopEl;
  29082. }else{
  29083. //setup our internal layered text els
  29084. this.textTopEl = Ext.get(this.progressBar.dom.firstChild);
  29085. var textBackEl = Ext.get(inner.childNodes[1]);
  29086. this.textTopEl.setStyle("z-index", 99).addClass('x-hidden');
  29087. this.textEl = new Ext.CompositeElement([this.textTopEl.dom.firstChild, textBackEl.dom.firstChild]);
  29088. this.textEl.setWidth(inner.offsetWidth);
  29089. }
  29090. this.progressBar.setHeight(inner.offsetHeight);
  29091. },
  29092. // private
  29093. afterRender : function(){
  29094. Ext.ProgressBar.superclass.afterRender.call(this);
  29095. if(this.value){
  29096. this.updateProgress(this.value, this.text);
  29097. }else{
  29098. this.updateText(this.text);
  29099. }
  29100. },
  29101. updateProgress : function(value, text, animate){
  29102. this.value = value || 0;
  29103. if(text){
  29104. this.updateText(text);
  29105. }
  29106. if(this.rendered){
  29107. var w = Math.floor(value*this.el.dom.firstChild.offsetWidth);
  29108. this.progressBar.setWidth(w, animate === true || (animate !== false && this.animate));
  29109. if(this.textTopEl){
  29110. //textTopEl should be the same width as the bar so overflow will clip as the bar moves
  29111. this.textTopEl.removeClass('x-hidden').setWidth(w);
  29112. }
  29113. }
  29114. this.fireEvent('update', this, value, text);
  29115. return this;
  29116. },
  29117. wait : function(o){
  29118. if(!this.waitTimer){
  29119. var scope = this;
  29120. o = o || {};
  29121. this.updateText(o.text);
  29122. this.waitTimer = Ext.TaskMgr.start({
  29123. run: function(i){
  29124. var inc = o.increment || 10;
  29125. this.updateProgress(((((i+inc)%inc)+1)*(100/inc))*.01, null, o.animate);
  29126. },
  29127. interval: o.interval || 1000,
  29128. duration: o.duration,
  29129. onStop: function(){
  29130. if(o.fn){
  29131. o.fn.apply(o.scope || this);
  29132. }
  29133. this.reset();
  29134. },
  29135. scope: scope
  29136. });
  29137. }
  29138. return this;
  29139. },
  29140. isWaiting : function(){
  29141. return this.waitTimer != null;
  29142. },
  29143. updateText : function(text){
  29144. this.text = text || '&#160;';
  29145. if(this.rendered){
  29146. this.textEl.update(this.text);
  29147. }
  29148. return this;
  29149. },
  29150. syncProgressBar : function(){
  29151. if(this.value){
  29152. this.updateProgress(this.value, this.text);
  29153. }
  29154. return this;
  29155. },
  29156. setSize : function(w, h){
  29157. Ext.ProgressBar.superclass.setSize.call(this, w, h);
  29158. if(this.textTopEl){
  29159. var inner = this.el.dom.firstChild;
  29160. this.textEl.setSize(inner.offsetWidth, inner.offsetHeight);
  29161. }
  29162. this.syncProgressBar();
  29163. return this;
  29164. },
  29165. reset : function(hide){
  29166. this.updateProgress(0);
  29167. if(this.textTopEl){
  29168. this.textTopEl.addClass('x-hidden');
  29169. }
  29170. if(this.waitTimer){
  29171. this.waitTimer.onStop = null; //prevent recursion
  29172. Ext.TaskMgr.stop(this.waitTimer);
  29173. this.waitTimer = null;
  29174. }
  29175. if(hide === true){
  29176. this.hide();
  29177. }
  29178. return this;
  29179. }
  29180. });
  29181. Ext.reg('progress', Ext.ProgressBar);
  29182. Ext.Slider = Ext.extend(Ext.BoxComponent, {
  29183. vertical: false,
  29184. minValue: 0,
  29185. maxValue: 100,
  29186. keyIncrement: 1,
  29187. increment: 0,
  29188. // private
  29189. clickRange: [5,15],
  29190. clickToChange : true,
  29191. animate: true,
  29192. dragging: false,
  29193. // private override
  29194. initComponent : function(){
  29195. if(this.value === undefined){
  29196. this.value = this.minValue;
  29197. }
  29198. Ext.Slider.superclass.initComponent.call(this);
  29199. this.keyIncrement = Math.max(this.increment, this.keyIncrement);
  29200. this.addEvents(
  29201. 'beforechange',
  29202. 'change',
  29203. 'changecomplete',
  29204. 'dragstart',
  29205. 'drag',
  29206. 'dragend'
  29207. );
  29208. if(this.vertical){
  29209. Ext.apply(this, Ext.Slider.Vertical);
  29210. }
  29211. },
  29212. // private override
  29213. onRender : function(){
  29214. this.autoEl = {
  29215. cls: 'x-slider ' + (this.vertical ? 'x-slider-vert' : 'x-slider-horz'),
  29216. cn:{cls:'x-slider-end',cn:{cls:'x-slider-inner',cn:[{cls:'x-slider-thumb'},{tag:'a', cls:'x-slider-focus', href:"#", tabIndex: '-1', hidefocus:'on'}]}}
  29217. };
  29218. Ext.Slider.superclass.onRender.apply(this, arguments);
  29219. this.endEl = this.el.first();
  29220. this.innerEl = this.endEl.first();
  29221. this.thumb = this.innerEl.first();
  29222. this.halfThumb = (this.vertical ? this.thumb.getHeight() : this.thumb.getWidth())/2;
  29223. this.focusEl = this.thumb.next();
  29224. this.initEvents();
  29225. },
  29226. // private override
  29227. initEvents : function(){
  29228. this.thumb.addClassOnOver('x-slider-thumb-over');
  29229. this.mon(this.el, 'mousedown', this.onMouseDown, this);
  29230. this.mon(this.el, 'keydown', this.onKeyDown, this);
  29231. this.focusEl.swallowEvent("click", true);
  29232. this.tracker = new Ext.dd.DragTracker({
  29233. onBeforeStart: this.onBeforeDragStart.createDelegate(this),
  29234. onStart: this.onDragStart.createDelegate(this),
  29235. onDrag: this.onDrag.createDelegate(this),
  29236. onEnd: this.onDragEnd.createDelegate(this),
  29237. tolerance: 3,
  29238. autoStart: 300
  29239. });
  29240. this.tracker.initEl(this.thumb);
  29241. this.on('beforedestroy', this.tracker.destroy, this.tracker);
  29242. },
  29243. // private override
  29244. onMouseDown : function(e){
  29245. if(this.disabled) {return;}
  29246. if(this.clickToChange && e.target != this.thumb.dom){
  29247. var local = this.innerEl.translatePoints(e.getXY());
  29248. this.onClickChange(local);
  29249. }
  29250. this.focus();
  29251. },
  29252. // private
  29253. onClickChange : function(local){
  29254. if(local.top > this.clickRange[0] && local.top < this.clickRange[1]){
  29255. this.setValue(Math.round(this.reverseValue(local.left)), undefined, true);
  29256. }
  29257. },
  29258. // private
  29259. onKeyDown : function(e){
  29260. if(this.disabled){e.preventDefault();return;}
  29261. var k = e.getKey();
  29262. switch(k){
  29263. case e.UP:
  29264. case e.RIGHT:
  29265. e.stopEvent();
  29266. if(e.ctrlKey){
  29267. this.setValue(this.maxValue, undefined, true);
  29268. }else{
  29269. this.setValue(this.value+this.keyIncrement, undefined, true);
  29270. }
  29271. break;
  29272. case e.DOWN:
  29273. case e.LEFT:
  29274. e.stopEvent();
  29275. if(e.ctrlKey){
  29276. this.setValue(this.minValue, undefined, true);
  29277. }else{
  29278. this.setValue(this.value-this.keyIncrement, undefined, true);
  29279. }
  29280. break;
  29281. default:
  29282. e.preventDefault();
  29283. }
  29284. },
  29285. // private
  29286. doSnap : function(value){
  29287. if(!this.increment || this.increment == 1 || !value) {
  29288. return value;
  29289. }
  29290. var newValue = value, inc = this.increment;
  29291. var m = value % inc;
  29292. if(m > 0){
  29293. if(m > (inc/2)){
  29294. newValue = value + (inc-m);
  29295. }else{
  29296. newValue = value - m;
  29297. }
  29298. }
  29299. return newValue.constrain(this.minValue, this.maxValue);
  29300. },
  29301. // private
  29302. afterRender : function(){
  29303. Ext.Slider.superclass.afterRender.apply(this, arguments);
  29304. if(this.value !== undefined){
  29305. var v = this.normalizeValue(this.value);
  29306. if(v !== this.value){
  29307. delete this.value;
  29308. this.setValue(v, false);
  29309. }else{
  29310. this.moveThumb(this.translateValue(v), false);
  29311. }
  29312. }
  29313. },
  29314. // private
  29315. getRatio : function(){
  29316. var w = this.innerEl.getWidth();
  29317. var v = this.maxValue - this.minValue;
  29318. return v == 0 ? w : (w/v);
  29319. },
  29320. // private
  29321. normalizeValue : function(v){
  29322. if(typeof v != 'number'){
  29323. v = parseInt(v);
  29324. }
  29325. v = Math.round(v);
  29326. v = this.doSnap(v);
  29327. v = v.constrain(this.minValue, this.maxValue);
  29328. return v;
  29329. },
  29330. setValue : function(v, animate, changeComplete){
  29331. v = this.normalizeValue(v);
  29332. if(v !== this.value && this.fireEvent('beforechange', this, v, this.value) !== false){
  29333. this.value = v;
  29334. this.moveThumb(this.translateValue(v), animate !== false);
  29335. this.fireEvent('change', this, v);
  29336. if(changeComplete){
  29337. this.fireEvent('changecomplete', this, v);
  29338. }
  29339. }
  29340. },
  29341. // private
  29342. translateValue : function(v){
  29343. var ratio = this.getRatio();
  29344. return (v * ratio)-(this.minValue * ratio)-this.halfThumb;
  29345. },
  29346. reverseValue : function(pos){
  29347. var ratio = this.getRatio();
  29348. return (pos+this.halfThumb+(this.minValue * ratio))/ratio;
  29349. },
  29350. // private
  29351. moveThumb: function(v, animate){
  29352. if(!animate || this.animate === false){
  29353. this.thumb.setLeft(v);
  29354. }else{
  29355. this.thumb.shift({left: v, stopFx: true, duration:.35});
  29356. }
  29357. },
  29358. // private
  29359. focus : function(){
  29360. this.focusEl.focus(10);
  29361. },
  29362. // private
  29363. onBeforeDragStart : function(e){
  29364. return !this.disabled;
  29365. },
  29366. // private
  29367. onDragStart: function(e){
  29368. this.thumb.addClass('x-slider-thumb-drag');
  29369. this.dragging = true;
  29370. this.dragStartValue = this.value;
  29371. this.fireEvent('dragstart', this, e);
  29372. },
  29373. // private
  29374. onDrag: function(e){
  29375. var pos = this.innerEl.translatePoints(this.tracker.getXY());
  29376. this.setValue(Math.round(this.reverseValue(pos.left)), false);
  29377. this.fireEvent('drag', this, e);
  29378. },
  29379. // private
  29380. onDragEnd: function(e){
  29381. this.thumb.removeClass('x-slider-thumb-drag');
  29382. this.dragging = false;
  29383. this.fireEvent('dragend', this, e);
  29384. if(this.dragStartValue != this.value){
  29385. this.fireEvent('changecomplete', this, this.value);
  29386. }
  29387. },
  29388. //private
  29389. onDisable: function(){
  29390. Ext.Slider.superclass.onDisable.call(this);
  29391. this.thumb.addClass(this.disabledClass);
  29392. if(Ext.isIE){
  29393. //IE breaks when using overflow visible and opacity other than 1.
  29394. //Create a place holder for the thumb and display it.
  29395. var xy = this.thumb.getXY();
  29396. this.thumb.hide();
  29397. this.innerEl.addClass(this.disabledClass).dom.disabled = true;
  29398. if (!this.thumbHolder){
  29399. this.thumbHolder = this.endEl.createChild({cls: 'x-slider-thumb ' + this.disabledClass});
  29400. }
  29401. this.thumbHolder.show().setXY(xy);
  29402. }
  29403. },
  29404. //private
  29405. onEnable: function(){
  29406. Ext.Slider.superclass.onEnable.call(this);
  29407. this.thumb.removeClass(this.disabledClass);
  29408. if(Ext.isIE){
  29409. this.innerEl.removeClass(this.disabledClass).dom.disabled = false;
  29410. if (this.thumbHolder){
  29411. this.thumbHolder.hide();
  29412. }
  29413. this.thumb.show();
  29414. this.syncThumb();
  29415. }
  29416. },
  29417. // private
  29418. onResize : function(w, h){
  29419. this.innerEl.setWidth(w - (this.el.getPadding('l') + this.endEl.getPadding('r')));
  29420. this.syncThumb();
  29421. },
  29422. syncThumb : function(){
  29423. if(this.rendered){
  29424. this.moveThumb(this.translateValue(this.value));
  29425. }
  29426. },
  29427. getValue : function(){
  29428. return this.value;
  29429. }
  29430. });
  29431. Ext.reg('slider', Ext.Slider);
  29432. // private class to support vertical sliders
  29433. Ext.Slider.Vertical = {
  29434. onResize : function(w, h){
  29435. this.innerEl.setHeight(h - (this.el.getPadding('t') + this.endEl.getPadding('b')));
  29436. this.syncThumb();
  29437. },
  29438. getRatio : function(){
  29439. var h = this.innerEl.getHeight();
  29440. var v = this.maxValue - this.minValue;
  29441. return h/v;
  29442. },
  29443. moveThumb: function(v, animate){
  29444. if(!animate || this.animate === false){
  29445. this.thumb.setBottom(v);
  29446. }else{
  29447. this.thumb.shift({bottom: v, stopFx: true, duration:.35});
  29448. }
  29449. },
  29450. onDrag: function(e){
  29451. var pos = this.innerEl.translatePoints(this.tracker.getXY());
  29452. var bottom = this.innerEl.getHeight()-pos.top;
  29453. this.setValue(this.minValue + Math.round(bottom/this.getRatio()), false);
  29454. this.fireEvent('drag', this, e);
  29455. },
  29456. onClickChange : function(local){
  29457. if(local.left > this.clickRange[0] && local.left < this.clickRange[1]){
  29458. var bottom = this.innerEl.getHeight()-local.top;
  29459. this.setValue(this.minValue + Math.round(bottom/this.getRatio()), undefined, true);
  29460. }
  29461. }
  29462. };
  29463. Ext.StatusBar = Ext.extend(Ext.Toolbar, {
  29464. cls : 'x-statusbar',
  29465. busyIconCls : 'x-status-busy',
  29466. busyText : 'Loading...',
  29467. autoClear : 5000,
  29468. // private
  29469. activeThreadId : 0,
  29470. // private
  29471. initComponent : function(){
  29472. if(this.statusAlign=='right'){
  29473. this.cls += ' x-status-right';
  29474. }
  29475. Ext.StatusBar.superclass.initComponent.call(this);
  29476. },
  29477. // private
  29478. afterRender : function(){
  29479. Ext.StatusBar.superclass.afterRender.call(this);
  29480. var right = this.statusAlign=='right',
  29481. td = Ext.get(this.nextBlock());
  29482. if(right){
  29483. this.tr.appendChild(td.dom);
  29484. }else{
  29485. td.insertBefore(this.tr.firstChild);
  29486. }
  29487. this.statusEl = td.createChild({
  29488. cls: 'x-status-text ' + (this.iconCls || this.defaultIconCls || ''),
  29489. html: this.text || this.defaultText || ''
  29490. });
  29491. this.statusEl.unselectable();
  29492. this.spacerEl = td.insertSibling({
  29493. tag: 'td',
  29494. style: 'width:100%',
  29495. cn: [{cls:'ytb-spacer'}]
  29496. }, right ? 'before' : 'after');
  29497. },
  29498. setStatus : function(o){
  29499. o = o || {};
  29500. if(typeof o == 'string'){
  29501. o = {text:o};
  29502. }
  29503. if(o.text !== undefined){
  29504. this.setText(o.text);
  29505. }
  29506. if(o.iconCls !== undefined){
  29507. this.setIcon(o.iconCls);
  29508. }
  29509. if(o.clear){
  29510. var c = o.clear,
  29511. wait = this.autoClear,
  29512. defaults = {useDefaults: true, anim: true};
  29513. if(typeof c == 'object'){
  29514. c = Ext.applyIf(c, defaults);
  29515. if(c.wait){
  29516. wait = c.wait;
  29517. }
  29518. }else if(typeof c == 'number'){
  29519. wait = c;
  29520. c = defaults;
  29521. }else if(typeof c == 'boolean'){
  29522. c = defaults;
  29523. }
  29524. c.threadId = this.activeThreadId;
  29525. this.clearStatus.defer(wait, this, [c]);
  29526. }
  29527. return this;
  29528. },
  29529. clearStatus : function(o){
  29530. o = o || {};
  29531. if(o.threadId && o.threadId !== this.activeThreadId){
  29532. // this means the current call was made internally, but a newer
  29533. // thread has set a message since this call was deferred. Since
  29534. // we don't want to overwrite a newer message just ignore.
  29535. return this;
  29536. }
  29537. var text = o.useDefaults ? this.defaultText : '',
  29538. iconCls = o.useDefaults ? (this.defaultIconCls ? this.defaultIconCls : '') : '';
  29539. if(o.anim){
  29540. this.statusEl.fadeOut({
  29541. remove: false,
  29542. useDisplay: true,
  29543. scope: this,
  29544. callback: function(){
  29545. this.setStatus({
  29546. text: text,
  29547. iconCls: iconCls
  29548. });
  29549. this.statusEl.show();
  29550. }
  29551. });
  29552. }else{
  29553. // hide/show the el to avoid jumpy text or icon
  29554. this.statusEl.hide();
  29555. this.setStatus({
  29556. text: text,
  29557. iconCls: iconCls
  29558. });
  29559. this.statusEl.show();
  29560. }
  29561. return this;
  29562. },
  29563. setText : function(text){
  29564. this.activeThreadId++;
  29565. this.text = text || '';
  29566. if(this.rendered){
  29567. this.statusEl.update(this.text);
  29568. }
  29569. return this;
  29570. },
  29571. getText : function(){
  29572. return this.text;
  29573. },
  29574. setIcon : function(cls){
  29575. this.activeThreadId++;
  29576. cls = cls || '';
  29577. if(this.rendered){
  29578. if(this.currIconCls){
  29579. this.statusEl.removeClass(this.currIconCls);
  29580. this.currIconCls = null;
  29581. }
  29582. if(cls.length > 0){
  29583. this.statusEl.addClass(cls);
  29584. this.currIconCls = cls;
  29585. }
  29586. }else{
  29587. this.currIconCls = cls;
  29588. }
  29589. return this;
  29590. },
  29591. showBusy : function(o){
  29592. if(typeof o == 'string'){
  29593. o = {text:o};
  29594. }
  29595. o = Ext.applyIf(o || {}, {
  29596. text: this.busyText,
  29597. iconCls: this.busyIconCls
  29598. });
  29599. return this.setStatus(o);
  29600. }
  29601. });
  29602. Ext.reg('statusbar', Ext.StatusBar);
  29603. Ext.History = (function () {
  29604. var iframe, hiddenField;
  29605. var ready = false;
  29606. var currentToken;
  29607. function getHash() {
  29608. var href = top.location.href, i = href.indexOf("#");
  29609. return i >= 0 ? href.substr(i + 1) : null;
  29610. }
  29611. function doSave() {
  29612. hiddenField.value = currentToken;
  29613. }
  29614. function handleStateChange(token) {
  29615. currentToken = token;
  29616. Ext.History.fireEvent('change', token);
  29617. }
  29618. function updateIFrame (token) {
  29619. var html = ['<html><body><div id="state">',token,'</div></body></html>'].join('');
  29620. try {
  29621. var doc = iframe.contentWindow.document;
  29622. doc.open();
  29623. doc.write(html);
  29624. doc.close();
  29625. return true;
  29626. } catch (e) {
  29627. return false;
  29628. }
  29629. }
  29630. function checkIFrame() {
  29631. if (!iframe.contentWindow || !iframe.contentWindow.document) {
  29632. setTimeout(checkIFrame, 10);
  29633. return;
  29634. }
  29635. var doc = iframe.contentWindow.document;
  29636. var elem = doc.getElementById("state");
  29637. var token = elem ? elem.innerText : null;
  29638. var hash = getHash();
  29639. setInterval(function () {
  29640. doc = iframe.contentWindow.document;
  29641. elem = doc.getElementById("state");
  29642. var newtoken = elem ? elem.innerText : null;
  29643. var newHash = getHash();
  29644. if (newtoken !== token) {
  29645. token = newtoken;
  29646. handleStateChange(token);
  29647. top.location.hash = token;
  29648. hash = token;
  29649. doSave();
  29650. } else if (newHash !== hash) {
  29651. hash = newHash;
  29652. updateIFrame(newHash);
  29653. }
  29654. }, 50);
  29655. ready = true;
  29656. Ext.History.fireEvent('ready', Ext.History);
  29657. }
  29658. function startUp() {
  29659. currentToken = hiddenField.value ? hiddenField.value : getHash();
  29660. if (Ext.isIE) {
  29661. checkIFrame();
  29662. } else {
  29663. var hash = getHash();
  29664. setInterval(function () {
  29665. var newHash = getHash();
  29666. if (newHash !== hash) {
  29667. hash = newHash;
  29668. handleStateChange(hash);
  29669. doSave();
  29670. }
  29671. }, 50);
  29672. ready = true;
  29673. Ext.History.fireEvent('ready', Ext.History);
  29674. }
  29675. }
  29676. return {
  29677. fieldId: 'x-history-field',
  29678. iframeId: 'x-history-frame',
  29679. events:{},
  29680. init: function (onReady, scope) {
  29681. if(ready) {
  29682. Ext.callback(onReady, scope, [this]);
  29683. return;
  29684. }
  29685. if(!Ext.isReady){
  29686. Ext.onReady(function(){
  29687. Ext.History.init(onReady, scope);
  29688. });
  29689. return;
  29690. }
  29691. hiddenField = Ext.getDom(Ext.History.fieldId);
  29692. if (Ext.isIE) {
  29693. iframe = Ext.getDom(Ext.History.iframeId);
  29694. }
  29695. this.addEvents('ready', 'change');
  29696. if(onReady){
  29697. this.on('ready', onReady, scope, {single:true});
  29698. }
  29699. startUp();
  29700. },
  29701. add: function (token, preventDup) {
  29702. if(preventDup !== false){
  29703. if(this.getToken() == token){
  29704. return true;
  29705. }
  29706. }
  29707. if (Ext.isIE) {
  29708. return updateIFrame(token);
  29709. } else {
  29710. top.location.hash = token;
  29711. return true;
  29712. }
  29713. },
  29714. back: function(){
  29715. history.go(-1);
  29716. },
  29717. forward: function(){
  29718. history.go(1);
  29719. },
  29720. getToken: function() {
  29721. return ready ? currentToken : getHash();
  29722. }
  29723. };
  29724. })();
  29725. Ext.apply(Ext.History, new Ext.util.Observable());
  29726. Ext.debug = {};
  29727. (function(){
  29728. var cp;
  29729. function createConsole(){
  29730. var scriptPanel = new Ext.debug.ScriptsPanel();
  29731. var logView = new Ext.debug.LogPanel();
  29732. var tree = new Ext.debug.DomTree();
  29733. var tabs = new Ext.TabPanel({
  29734. activeTab: 0,
  29735. border: false,
  29736. tabPosition: 'bottom',
  29737. items: [{
  29738. title: 'Debug Console',
  29739. layout:'border',
  29740. items: [logView, scriptPanel]
  29741. },{
  29742. title: 'DOM Inspector',
  29743. layout:'border',
  29744. items: [tree]
  29745. }]
  29746. });
  29747. cp = new Ext.Panel({
  29748. id: 'x-debug-browser',
  29749. title: 'Console',
  29750. collapsible: true,
  29751. animCollapse: false,
  29752. style: 'position:absolute;left:0;bottom:0;',
  29753. height:200,
  29754. logView: logView,
  29755. layout: 'fit',
  29756. tools:[{
  29757. id: 'close',
  29758. handler: function(){
  29759. cp.destroy();
  29760. cp = null;
  29761. Ext.EventManager.removeResizeListener(handleResize);
  29762. }
  29763. }],
  29764. items: tabs
  29765. });
  29766. cp.render(document.body);
  29767. cp.resizer = new Ext.Resizable(cp.el, {
  29768. minHeight:50,
  29769. handles: "n",
  29770. pinned: true,
  29771. transparent:true,
  29772. resizeElement : function(){
  29773. var box = this.proxy.getBox();
  29774. this.proxy.hide();
  29775. cp.setHeight(box.height);
  29776. return box;
  29777. }
  29778. });
  29779. function handleResize(){
  29780. cp.setWidth(Ext.getBody().getViewSize().width);
  29781. }
  29782. Ext.EventManager.onWindowResize(handleResize);
  29783. handleResize();
  29784. }
  29785. Ext.apply(Ext, {
  29786. log : function(){
  29787. if(!cp){
  29788. createConsole();
  29789. }
  29790. cp.logView.log.apply(cp.logView, arguments);
  29791. },
  29792. logf : function(format, arg1, arg2, etc){
  29793. Ext.log(String.format.apply(String, arguments));
  29794. },
  29795. dump : function(o){
  29796. if(typeof o == 'string' || typeof o == 'number' || typeof o == 'undefined' || Ext.isDate(o)){
  29797. Ext.log(o);
  29798. }else if(!o){
  29799. Ext.log("null");
  29800. }else if(typeof o != "object"){
  29801. Ext.log('Unknown return type');
  29802. }else if(Ext.isArray(o)){
  29803. Ext.log('['+o.join(',')+']');
  29804. }else{
  29805. var b = ["{\n"];
  29806. for(var key in o){
  29807. var to = typeof o[key];
  29808. if(to != "function" && to != "object"){
  29809. b.push(String.format(" {0}: {1},\n", key, o[key]));
  29810. }
  29811. }
  29812. var s = b.join("");
  29813. if(s.length > 3){
  29814. s = s.substr(0, s.length-2);
  29815. }
  29816. Ext.log(s + "\n}");
  29817. }
  29818. },
  29819. _timers : {},
  29820. time : function(name){
  29821. name = name || "def";
  29822. Ext._timers[name] = new Date().getTime();
  29823. },
  29824. timeEnd : function(name, printResults){
  29825. var t = new Date().getTime();
  29826. name = name || "def";
  29827. var v = String.format("{0} ms", t-Ext._timers[name]);
  29828. Ext._timers[name] = new Date().getTime();
  29829. if(printResults !== false){
  29830. Ext.log('Timer ' + (name == "def" ? v : name + ": " + v));
  29831. }
  29832. return v;
  29833. }
  29834. });
  29835. })();
  29836. Ext.debug.ScriptsPanel = Ext.extend(Ext.Panel, {
  29837. id:'x-debug-scripts',
  29838. region: 'east',
  29839. minWidth: 200,
  29840. split: true,
  29841. width: 350,
  29842. border: false,
  29843. layout:'anchor',
  29844. style:'border-width:0 0 0 1px;',
  29845. initComponent : function(){
  29846. this.scriptField = new Ext.form.TextArea({
  29847. anchor: '100% -26',
  29848. style:'border-width:0;'
  29849. });
  29850. this.trapBox = new Ext.form.Checkbox({
  29851. id: 'console-trap',
  29852. boxLabel: 'Trap Errors',
  29853. checked: true
  29854. });
  29855. this.toolbar = new Ext.Toolbar([{
  29856. text: 'Run',
  29857. scope: this,
  29858. handler: this.evalScript
  29859. },{
  29860. text: 'Clear',
  29861. scope: this,
  29862. handler: this.clear
  29863. },
  29864. '->',
  29865. this.trapBox,
  29866. ' ', ' '
  29867. ]);
  29868. this.items = [this.toolbar, this.scriptField];
  29869. Ext.debug.ScriptsPanel.superclass.initComponent.call(this);
  29870. },
  29871. evalScript : function(){
  29872. var s = this.scriptField.getValue();
  29873. if(this.trapBox.getValue()){
  29874. try{
  29875. var rt = eval(s);
  29876. Ext.dump(rt === undefined? '(no return)' : rt);
  29877. }catch(e){
  29878. Ext.log(e.message || e.descript);
  29879. }
  29880. }else{
  29881. var rt = eval(s);
  29882. Ext.dump(rt === undefined? '(no return)' : rt);
  29883. }
  29884. },
  29885. clear : function(){
  29886. this.scriptField.setValue('');
  29887. this.scriptField.focus();
  29888. }
  29889. });
  29890. Ext.debug.LogPanel = Ext.extend(Ext.Panel, {
  29891. autoScroll: true,
  29892. region: 'center',
  29893. border: false,
  29894. style:'border-width:0 1px 0 0',
  29895. log : function(){
  29896. var markup = [ '<div style="padding:5px !important;border-bottom:1px solid #ccc;">',
  29897. Ext.util.Format.htmlEncode(Array.prototype.join.call(arguments, ', ')).replace(/\n/g, '<br />').replace(/\s/g, '&#160;'),
  29898. '</div>'].join('');
  29899. this.body.insertHtml('beforeend', markup);
  29900. this.body.scrollTo('top', 100000);
  29901. },
  29902. clear : function(){
  29903. this.body.update('');
  29904. this.body.dom.scrollTop = 0;
  29905. }
  29906. });
  29907. Ext.debug.DomTree = Ext.extend(Ext.tree.TreePanel, {
  29908. enableDD:false ,
  29909. lines:false,
  29910. rootVisible:false,
  29911. animate:false,
  29912. hlColor:'ffff9c',
  29913. autoScroll: true,
  29914. region:'center',
  29915. border:false,
  29916. initComponent : function(){
  29917. Ext.debug.DomTree.superclass.initComponent.call(this);
  29918. // tree related stuff
  29919. var styles = false, hnode;
  29920. var nonSpace = /^\s*$/;
  29921. var html = Ext.util.Format.htmlEncode;
  29922. var ellipsis = Ext.util.Format.ellipsis;
  29923. var styleRe = /\s?([a-z\-]*)\:([^;]*)(?:[;\s\n\r]*)/gi;
  29924. function findNode(n){
  29925. if(!n || n.nodeType != 1 || n == document.body || n == document){
  29926. return false;
  29927. }
  29928. var pn = [n], p = n;
  29929. while((p = p.parentNode) && p.nodeType == 1 && p.tagName.toUpperCase() != 'HTML'){
  29930. pn.unshift(p);
  29931. }
  29932. var cn = hnode;
  29933. for(var i = 0, len = pn.length; i < len; i++){
  29934. cn.expand();
  29935. cn = cn.findChild('htmlNode', pn[i]);
  29936. if(!cn){ // in this dialog?
  29937. return false;
  29938. }
  29939. }
  29940. cn.select();
  29941. var a = cn.ui.anchor;
  29942. treeEl.dom.scrollTop = Math.max(0 ,a.offsetTop-10);
  29943. //treeEl.dom.scrollLeft = Math.max(0 ,a.offsetLeft-10); no likey
  29944. cn.highlight();
  29945. return true;
  29946. }
  29947. function nodeTitle(n){
  29948. var s = n.tagName;
  29949. if(n.id){
  29950. s += '#'+n.id;
  29951. }else if(n.className){
  29952. s += '.'+n.className;
  29953. }
  29954. return s;
  29955. }
  29956. function onNodeSelect(t, n, last){
  29957. return;
  29958. if(last && last.unframe){
  29959. last.unframe();
  29960. }
  29961. var props = {};
  29962. if(n && n.htmlNode){
  29963. if(frameEl.pressed){
  29964. n.frame();
  29965. }
  29966. if(inspecting){
  29967. return;
  29968. }
  29969. addStyle.enable();
  29970. reload.setDisabled(n.leaf);
  29971. var dom = n.htmlNode;
  29972. stylePanel.setTitle(nodeTitle(dom));
  29973. if(styles && !showAll.pressed){
  29974. var s = dom.style ? dom.style.cssText : '';
  29975. if(s){
  29976. var m;
  29977. while ((m = styleRe.exec(s)) != null){
  29978. props[m[1].toLowerCase()] = m[2];
  29979. }
  29980. }
  29981. }else if(styles){
  29982. var cl = Ext.debug.cssList;
  29983. var s = dom.style, fly = Ext.fly(dom);
  29984. if(s){
  29985. for(var i = 0, len = cl.length; i<len; i++){
  29986. var st = cl[i];
  29987. var v = s[st] || fly.getStyle(st);
  29988. if(v != undefined && v !== null && v !== ''){
  29989. props[st] = v;
  29990. }
  29991. }
  29992. }
  29993. }else{
  29994. for(var a in dom){
  29995. var v = dom[a];
  29996. if((isNaN(a+10)) && v != undefined && v !== null && v !== '' && !(Ext.isGecko && a[0] == a[0].toUpperCase())){
  29997. props[a] = v;
  29998. }
  29999. }
  30000. }
  30001. }else{
  30002. if(inspecting){
  30003. return;
  30004. }
  30005. addStyle.disable();
  30006. reload.disabled();
  30007. }
  30008. stylesGrid.setSource(props);
  30009. stylesGrid.treeNode = n;
  30010. stylesGrid.view.fitColumns();
  30011. }
  30012. this.loader = new Ext.tree.TreeLoader();
  30013. this.loader.load = function(n, cb){
  30014. var isBody = n.htmlNode == document.body;
  30015. var cn = n.htmlNode.childNodes;
  30016. for(var i = 0, c; c = cn[i]; i++){
  30017. if(isBody && c.id == 'x-debug-browser'){
  30018. continue;
  30019. }
  30020. if(c.nodeType == 1){
  30021. n.appendChild(new Ext.debug.HtmlNode(c));
  30022. }else if(c.nodeType == 3 && !nonSpace.test(c.nodeValue)){
  30023. n.appendChild(new Ext.tree.TreeNode({
  30024. text:'<em>' + ellipsis(html(String(c.nodeValue)), 35) + '</em>',
  30025. cls: 'x-tree-noicon'
  30026. }));
  30027. }
  30028. }
  30029. cb();
  30030. };
  30031. //tree.getSelectionModel().on('selectionchange', onNodeSelect, null, {buffer:250});
  30032. this.root = this.setRootNode(new Ext.tree.TreeNode('Ext'));
  30033. hnode = this.root.appendChild(new Ext.debug.HtmlNode(
  30034. document.getElementsByTagName('html')[0]
  30035. ));
  30036. }
  30037. });
  30038. // highly unusual class declaration
  30039. Ext.debug.HtmlNode = function(){
  30040. var html = Ext.util.Format.htmlEncode;
  30041. var ellipsis = Ext.util.Format.ellipsis;
  30042. var nonSpace = /^\s*$/;
  30043. var attrs = [
  30044. {n: 'id', v: 'id'},
  30045. {n: 'className', v: 'class'},
  30046. {n: 'name', v: 'name'},
  30047. {n: 'type', v: 'type'},
  30048. {n: 'src', v: 'src'},
  30049. {n: 'href', v: 'href'}
  30050. ];
  30051. function hasChild(n){
  30052. for(var i = 0, c; c = n.childNodes[i]; i++){
  30053. if(c.nodeType == 1){
  30054. return true;
  30055. }
  30056. }
  30057. return false;
  30058. }
  30059. function renderNode(n, leaf){
  30060. var tag = n.tagName.toLowerCase();
  30061. var s = '&lt;' + tag;
  30062. for(var i = 0, len = attrs.length; i < len; i++){
  30063. var a = attrs[i];
  30064. var v = n[a.n];
  30065. if(v && !nonSpace.test(v)){
  30066. s += ' ' + a.v + '=&quot;<i>' + html(v) +'</i>&quot;';
  30067. }
  30068. }
  30069. var style = n.style ? n.style.cssText : '';
  30070. if(style){
  30071. s += ' style=&quot;<i>' + html(style.toLowerCase()) +'</i>&quot;';
  30072. }
  30073. if(leaf && n.childNodes.length > 0){
  30074. s+='&gt;<em>' + ellipsis(html(String(n.innerHTML)), 35) + '</em>&lt;/'+tag+'&gt;';
  30075. }else if(leaf){
  30076. s += ' /&gt;';
  30077. }else{
  30078. s += '&gt;';
  30079. }
  30080. return s;
  30081. }
  30082. var HtmlNode = function(n){
  30083. var leaf = !hasChild(n);
  30084. this.htmlNode = n;
  30085. this.tagName = n.tagName.toLowerCase();
  30086. var attr = {
  30087. text : renderNode(n, leaf),
  30088. leaf : leaf,
  30089. cls: 'x-tree-noicon'
  30090. };
  30091. HtmlNode.superclass.constructor.call(this, attr);
  30092. this.attributes.htmlNode = n; // for searching
  30093. if(!leaf){
  30094. this.on('expand', this.onExpand, this);
  30095. this.on('collapse', this.onCollapse, this);
  30096. }
  30097. };
  30098. Ext.extend(HtmlNode, Ext.tree.AsyncTreeNode, {
  30099. cls: 'x-tree-noicon',
  30100. preventHScroll: true,
  30101. refresh : function(highlight){
  30102. var leaf = !hasChild(this.htmlNode);
  30103. this.setText(renderNode(this.htmlNode, leaf));
  30104. if(highlight){
  30105. Ext.fly(this.ui.textNode).highlight();
  30106. }
  30107. },
  30108. onExpand : function(){
  30109. if(!this.closeNode && this.parentNode){
  30110. this.closeNode = this.parentNode.insertBefore(new Ext.tree.TreeNode({
  30111. text:'&lt;/' + this.tagName + '&gt;',
  30112. cls: 'x-tree-noicon'
  30113. }), this.nextSibling);
  30114. }else if(this.closeNode){
  30115. this.closeNode.ui.show();
  30116. }
  30117. },
  30118. onCollapse : function(){
  30119. if(this.closeNode){
  30120. this.closeNode.ui.hide();
  30121. }
  30122. },
  30123. render : function(bulkRender){
  30124. HtmlNode.superclass.render.call(this, bulkRender);
  30125. },
  30126. highlightNode : function(){
  30127. //Ext.fly(this.htmlNode).highlight();
  30128. },
  30129. highlight : function(){
  30130. //Ext.fly(this.ui.textNode).highlight();
  30131. },
  30132. frame : function(){
  30133. this.htmlNode.style.border = '1px solid #0000ff';
  30134. //this.highlightNode();
  30135. },
  30136. unframe : function(){
  30137. //Ext.fly(this.htmlNode).removeClass('x-debug-frame');
  30138. this.htmlNode.style.border = '';
  30139. }
  30140. });
  30141. return HtmlNode;
  30142. }();