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.

770 lines
25 KiB

  1. /*!
  2. * Ext JS Library 3.2.0
  3. * Copyright(c) 2006-2010 Ext JS, Inc.
  4. * licensing@extjs.com
  5. * http://www.extjs.com/license
  6. */
  7. /**
  8. * @class Ext.Resizable
  9. * @extends Ext.util.Observable
  10. * <p>Applies drag handles to an element to make it resizable. The drag handles are inserted into the element
  11. * and positioned absolute. Some elements, such as a textarea or image, don't support this. To overcome that, you can wrap
  12. * the textarea in a div and set 'resizeChild' to true (or to the id of the element), <b>or</b> set wrap:true in your config and
  13. * the element will be wrapped for you automatically.</p>
  14. * <p>Here is the list of valid resize handles:</p>
  15. * <pre>
  16. Value Description
  17. ------ -------------------
  18. 'n' north
  19. 's' south
  20. 'e' east
  21. 'w' west
  22. 'nw' northwest
  23. 'sw' southwest
  24. 'se' southeast
  25. 'ne' northeast
  26. 'all' all
  27. </pre>
  28. * <p>Here's an example showing the creation of a typical Resizable:</p>
  29. * <pre><code>
  30. var resizer = new Ext.Resizable('element-id', {
  31. handles: 'all',
  32. minWidth: 200,
  33. minHeight: 100,
  34. maxWidth: 500,
  35. maxHeight: 400,
  36. pinned: true
  37. });
  38. resizer.on('resize', myHandler);
  39. </code></pre>
  40. * <p>To hide a particular handle, set its display to none in CSS, or through script:<br>
  41. * resizer.east.setDisplayed(false);</p>
  42. * @constructor
  43. * Create a new resizable component
  44. * @param {Mixed} el The id or element to resize
  45. * @param {Object} config configuration options
  46. */
  47. Ext.Resizable = Ext.extend(Ext.util.Observable, {
  48. constructor: function(el, config){
  49. this.el = Ext.get(el);
  50. if(config && config.wrap){
  51. config.resizeChild = this.el;
  52. this.el = this.el.wrap(typeof config.wrap == 'object' ? config.wrap : {cls:'xresizable-wrap'});
  53. this.el.id = this.el.dom.id = config.resizeChild.id + '-rzwrap';
  54. this.el.setStyle('overflow', 'hidden');
  55. this.el.setPositioning(config.resizeChild.getPositioning());
  56. config.resizeChild.clearPositioning();
  57. if(!config.width || !config.height){
  58. var csize = config.resizeChild.getSize();
  59. this.el.setSize(csize.width, csize.height);
  60. }
  61. if(config.pinned && !config.adjustments){
  62. config.adjustments = 'auto';
  63. }
  64. }
  65. /**
  66. * The proxy Element that is resized in place of the real Element during the resize operation.
  67. * This may be queried using {@link Ext.Element#getBox} to provide the new area to resize to.
  68. * Read only.
  69. * @type Ext.Element.
  70. * @property proxy
  71. */
  72. this.proxy = this.el.createProxy({tag: 'div', cls: 'x-resizable-proxy', id: this.el.id + '-rzproxy'}, Ext.getBody());
  73. this.proxy.unselectable();
  74. this.proxy.enableDisplayMode('block');
  75. Ext.apply(this, config);
  76. if(this.pinned){
  77. this.disableTrackOver = true;
  78. this.el.addClass('x-resizable-pinned');
  79. }
  80. // if the element isn't positioned, make it relative
  81. var position = this.el.getStyle('position');
  82. if(position != 'absolute' && position != 'fixed'){
  83. this.el.setStyle('position', 'relative');
  84. }
  85. if(!this.handles){ // no handles passed, must be legacy style
  86. this.handles = 's,e,se';
  87. if(this.multiDirectional){
  88. this.handles += ',n,w';
  89. }
  90. }
  91. if(this.handles == 'all'){
  92. this.handles = 'n s e w ne nw se sw';
  93. }
  94. var hs = this.handles.split(/\s*?[,;]\s*?| /);
  95. var ps = Ext.Resizable.positions;
  96. for(var i = 0, len = hs.length; i < len; i++){
  97. if(hs[i] && ps[hs[i]]){
  98. var pos = ps[hs[i]];
  99. this[pos] = new Ext.Resizable.Handle(this, pos, this.disableTrackOver, this.transparent, this.handleCls);
  100. }
  101. }
  102. // legacy
  103. this.corner = this.southeast;
  104. if(this.handles.indexOf('n') != -1 || this.handles.indexOf('w') != -1){
  105. this.updateBox = true;
  106. }
  107. this.activeHandle = null;
  108. if(this.resizeChild){
  109. if(typeof this.resizeChild == 'boolean'){
  110. this.resizeChild = Ext.get(this.el.dom.firstChild, true);
  111. }else{
  112. this.resizeChild = Ext.get(this.resizeChild, true);
  113. }
  114. }
  115. if(this.adjustments == 'auto'){
  116. var rc = this.resizeChild;
  117. var hw = this.west, he = this.east, hn = this.north, hs = this.south;
  118. if(rc && (hw || hn)){
  119. rc.position('relative');
  120. rc.setLeft(hw ? hw.el.getWidth() : 0);
  121. rc.setTop(hn ? hn.el.getHeight() : 0);
  122. }
  123. this.adjustments = [
  124. (he ? -he.el.getWidth() : 0) + (hw ? -hw.el.getWidth() : 0),
  125. (hn ? -hn.el.getHeight() : 0) + (hs ? -hs.el.getHeight() : 0) -1
  126. ];
  127. }
  128. if(this.draggable){
  129. this.dd = this.dynamic ?
  130. this.el.initDD(null) : this.el.initDDProxy(null, {dragElId: this.proxy.id});
  131. this.dd.setHandleElId(this.resizeChild ? this.resizeChild.id : this.el.id);
  132. if(this.constrainTo){
  133. this.dd.constrainTo(this.constrainTo);
  134. }
  135. }
  136. this.addEvents(
  137. /**
  138. * @event beforeresize
  139. * Fired before resize is allowed. Set {@link #enabled} to false to cancel resize.
  140. * @param {Ext.Resizable} this
  141. * @param {Ext.EventObject} e The mousedown event
  142. */
  143. 'beforeresize',
  144. /**
  145. * @event resize
  146. * Fired after a resize.
  147. * @param {Ext.Resizable} this
  148. * @param {Number} width The new width
  149. * @param {Number} height The new height
  150. * @param {Ext.EventObject} e The mouseup event
  151. */
  152. 'resize'
  153. );
  154. if(this.width !== null && this.height !== null){
  155. this.resizeTo(this.width, this.height);
  156. }else{
  157. this.updateChildSize();
  158. }
  159. if(Ext.isIE){
  160. this.el.dom.style.zoom = 1;
  161. }
  162. Ext.Resizable.superclass.constructor.call(this);
  163. },
  164. /**
  165. * @cfg {Array/String} adjustments String 'auto' or an array [width, height] with values to be <b>added</b> to the
  166. * resize operation's new size (defaults to <tt>[0, 0]</tt>)
  167. */
  168. adjustments : [0, 0],
  169. /**
  170. * @cfg {Boolean} animate True to animate the resize (not compatible with dynamic sizing, defaults to false)
  171. */
  172. animate : false,
  173. /**
  174. * @cfg {Mixed} constrainTo Constrain the resize to a particular element
  175. */
  176. /**
  177. * @cfg {Boolean} disableTrackOver True to disable mouse tracking. This is only applied at config time. (defaults to false)
  178. */
  179. disableTrackOver : false,
  180. /**
  181. * @cfg {Boolean} draggable Convenience to initialize drag drop (defaults to false)
  182. */
  183. draggable: false,
  184. /**
  185. * @cfg {Number} duration Animation duration if animate = true (defaults to 0.35)
  186. */
  187. duration : 0.35,
  188. /**
  189. * @cfg {Boolean} dynamic True to resize the element while dragging instead of using a proxy (defaults to false)
  190. */
  191. dynamic : false,
  192. /**
  193. * @cfg {String} easing Animation easing if animate = true (defaults to <tt>'easingOutStrong'</tt>)
  194. */
  195. easing : 'easeOutStrong',
  196. /**
  197. * @cfg {Boolean} enabled False to disable resizing (defaults to true)
  198. */
  199. enabled : true,
  200. /**
  201. * @property enabled Writable. False if resizing is disabled.
  202. * @type Boolean
  203. */
  204. /**
  205. * @cfg {String} handles String consisting of the resize handles to display (defaults to undefined).
  206. * Specify either <tt>'all'</tt> or any of <tt>'n s e w ne nw se sw'</tt>.
  207. */
  208. handles : false,
  209. /**
  210. * @cfg {Boolean} multiDirectional <b>Deprecated</b>. Deprecated style of adding multi-direction resize handles.
  211. */
  212. multiDirectional : false,
  213. /**
  214. * @cfg {Number} height The height of the element in pixels (defaults to null)
  215. */
  216. height : null,
  217. /**
  218. * @cfg {Number} width The width of the element in pixels (defaults to null)
  219. */
  220. width : null,
  221. /**
  222. * @cfg {Number} heightIncrement The increment to snap the height resize in pixels
  223. * (only applies if <code>{@link #dynamic}==true</code>). Defaults to <tt>0</tt>.
  224. */
  225. heightIncrement : 0,
  226. /**
  227. * @cfg {Number} widthIncrement The increment to snap the width resize in pixels
  228. * (only applies if <code>{@link #dynamic}==true</code>). Defaults to <tt>0</tt>.
  229. */
  230. widthIncrement : 0,
  231. /**
  232. * @cfg {Number} minHeight The minimum height for the element (defaults to 5)
  233. */
  234. minHeight : 5,
  235. /**
  236. * @cfg {Number} minWidth The minimum width for the element (defaults to 5)
  237. */
  238. minWidth : 5,
  239. /**
  240. * @cfg {Number} maxHeight The maximum height for the element (defaults to 10000)
  241. */
  242. maxHeight : 10000,
  243. /**
  244. * @cfg {Number} maxWidth The maximum width for the element (defaults to 10000)
  245. */
  246. maxWidth : 10000,
  247. /**
  248. * @cfg {Number} minX The minimum x for the element (defaults to 0)
  249. */
  250. minX: 0,
  251. /**
  252. * @cfg {Number} minY The minimum x for the element (defaults to 0)
  253. */
  254. minY: 0,
  255. /**
  256. * @cfg {Boolean} pinned True to ensure that the resize handles are always visible, false to display them only when the
  257. * user mouses over the resizable borders. This is only applied at config time. (defaults to false)
  258. */
  259. pinned : false,
  260. /**
  261. * @cfg {Boolean} preserveRatio True to preserve the original ratio between height
  262. * and width during resize (defaults to false)
  263. */
  264. preserveRatio : false,
  265. /**
  266. * @cfg {Boolean/String/Element} resizeChild True to resize the first child, or id/element to resize (defaults to false)
  267. */
  268. resizeChild : false,
  269. /**
  270. * @cfg {Boolean} transparent True for transparent handles. This is only applied at config time. (defaults to false)
  271. */
  272. transparent: false,
  273. /**
  274. * @cfg {Ext.lib.Region} resizeRegion Constrain the resize to a particular region
  275. */
  276. /**
  277. * @cfg {Boolean} wrap True to wrap an element with a div if needed (required for textareas and images, defaults to false)
  278. * in favor of the handles config option (defaults to false)
  279. */
  280. /**
  281. * @cfg {String} handleCls A css class to add to each handle. Defaults to <tt>''</tt>.
  282. */
  283. /**
  284. * Perform a manual resize and fires the 'resize' event.
  285. * @param {Number} width
  286. * @param {Number} height
  287. */
  288. resizeTo : function(width, height){
  289. this.el.setSize(width, height);
  290. this.updateChildSize();
  291. this.fireEvent('resize', this, width, height, null);
  292. },
  293. // private
  294. startSizing : function(e, handle){
  295. this.fireEvent('beforeresize', this, e);
  296. if(this.enabled){ // 2nd enabled check in case disabled before beforeresize handler
  297. if(!this.overlay){
  298. this.overlay = this.el.createProxy({tag: 'div', cls: 'x-resizable-overlay', html: '&#160;'}, Ext.getBody());
  299. this.overlay.unselectable();
  300. this.overlay.enableDisplayMode('block');
  301. this.overlay.on({
  302. scope: this,
  303. mousemove: this.onMouseMove,
  304. mouseup: this.onMouseUp
  305. });
  306. }
  307. this.overlay.setStyle('cursor', handle.el.getStyle('cursor'));
  308. this.resizing = true;
  309. this.startBox = this.el.getBox();
  310. this.startPoint = e.getXY();
  311. this.offsets = [(this.startBox.x + this.startBox.width) - this.startPoint[0],
  312. (this.startBox.y + this.startBox.height) - this.startPoint[1]];
  313. this.overlay.setSize(Ext.lib.Dom.getViewWidth(true), Ext.lib.Dom.getViewHeight(true));
  314. this.overlay.show();
  315. if(this.constrainTo) {
  316. var ct = Ext.get(this.constrainTo);
  317. this.resizeRegion = ct.getRegion().adjust(
  318. ct.getFrameWidth('t'),
  319. ct.getFrameWidth('l'),
  320. -ct.getFrameWidth('b'),
  321. -ct.getFrameWidth('r')
  322. );
  323. }
  324. this.proxy.setStyle('visibility', 'hidden'); // workaround display none
  325. this.proxy.show();
  326. this.proxy.setBox(this.startBox);
  327. if(!this.dynamic){
  328. this.proxy.setStyle('visibility', 'visible');
  329. }
  330. }
  331. },
  332. // private
  333. onMouseDown : function(handle, e){
  334. if(this.enabled){
  335. e.stopEvent();
  336. this.activeHandle = handle;
  337. this.startSizing(e, handle);
  338. }
  339. },
  340. // private
  341. onMouseUp : function(e){
  342. this.activeHandle = null;
  343. var size = this.resizeElement();
  344. this.resizing = false;
  345. this.handleOut();
  346. this.overlay.hide();
  347. this.proxy.hide();
  348. this.fireEvent('resize', this, size.width, size.height, e);
  349. },
  350. // private
  351. updateChildSize : function(){
  352. if(this.resizeChild){
  353. var el = this.el;
  354. var child = this.resizeChild;
  355. var adj = this.adjustments;
  356. if(el.dom.offsetWidth){
  357. var b = el.getSize(true);
  358. child.setSize(b.width+adj[0], b.height+adj[1]);
  359. }
  360. // Second call here for IE
  361. // The first call enables instant resizing and
  362. // the second call corrects scroll bars if they
  363. // exist
  364. if(Ext.isIE){
  365. setTimeout(function(){
  366. if(el.dom.offsetWidth){
  367. var b = el.getSize(true);
  368. child.setSize(b.width+adj[0], b.height+adj[1]);
  369. }
  370. }, 10);
  371. }
  372. }
  373. },
  374. // private
  375. snap : function(value, inc, min){
  376. if(!inc || !value){
  377. return value;
  378. }
  379. var newValue = value;
  380. var m = value % inc;
  381. if(m > 0){
  382. if(m > (inc/2)){
  383. newValue = value + (inc-m);
  384. }else{
  385. newValue = value - m;
  386. }
  387. }
  388. return Math.max(min, newValue);
  389. },
  390. /**
  391. * <p>Performs resizing of the associated Element. This method is called internally by this
  392. * class, and should not be called by user code.</p>
  393. * <p>If a Resizable is being used to resize an Element which encapsulates a more complex UI
  394. * component such as a Panel, this method may be overridden by specifying an implementation
  395. * as a config option to provide appropriate behaviour at the end of the resize operation on
  396. * mouseup, for example resizing the Panel, and relaying the Panel's content.</p>
  397. * <p>The new area to be resized to is available by examining the state of the {@link #proxy}
  398. * Element. Example:
  399. <pre><code>
  400. new Ext.Panel({
  401. title: 'Resize me',
  402. x: 100,
  403. y: 100,
  404. renderTo: Ext.getBody(),
  405. floating: true,
  406. frame: true,
  407. width: 400,
  408. height: 200,
  409. listeners: {
  410. render: function(p) {
  411. new Ext.Resizable(p.getEl(), {
  412. handles: 'all',
  413. pinned: true,
  414. transparent: true,
  415. resizeElement: function() {
  416. var box = this.proxy.getBox();
  417. p.updateBox(box);
  418. if (p.layout) {
  419. p.doLayout();
  420. }
  421. return box;
  422. }
  423. });
  424. }
  425. }
  426. }).show();
  427. </code></pre>
  428. */
  429. resizeElement : function(){
  430. var box = this.proxy.getBox();
  431. if(this.updateBox){
  432. this.el.setBox(box, false, this.animate, this.duration, null, this.easing);
  433. }else{
  434. this.el.setSize(box.width, box.height, this.animate, this.duration, null, this.easing);
  435. }
  436. this.updateChildSize();
  437. if(!this.dynamic){
  438. this.proxy.hide();
  439. }
  440. if(this.draggable && this.constrainTo){
  441. this.dd.resetConstraints();
  442. this.dd.constrainTo(this.constrainTo);
  443. }
  444. return box;
  445. },
  446. // private
  447. constrain : function(v, diff, m, mx){
  448. if(v - diff < m){
  449. diff = v - m;
  450. }else if(v - diff > mx){
  451. diff = v - mx;
  452. }
  453. return diff;
  454. },
  455. // private
  456. onMouseMove : function(e){
  457. if(this.enabled && this.activeHandle){
  458. try{// try catch so if something goes wrong the user doesn't get hung
  459. if(this.resizeRegion && !this.resizeRegion.contains(e.getPoint())) {
  460. return;
  461. }
  462. //var curXY = this.startPoint;
  463. var curSize = this.curSize || this.startBox,
  464. x = this.startBox.x, y = this.startBox.y,
  465. ox = x,
  466. oy = y,
  467. w = curSize.width,
  468. h = curSize.height,
  469. ow = w,
  470. oh = h,
  471. mw = this.minWidth,
  472. mh = this.minHeight,
  473. mxw = this.maxWidth,
  474. mxh = this.maxHeight,
  475. wi = this.widthIncrement,
  476. hi = this.heightIncrement,
  477. eventXY = e.getXY(),
  478. diffX = -(this.startPoint[0] - Math.max(this.minX, eventXY[0])),
  479. diffY = -(this.startPoint[1] - Math.max(this.minY, eventXY[1])),
  480. pos = this.activeHandle.position,
  481. tw,
  482. th;
  483. switch(pos){
  484. case 'east':
  485. w += diffX;
  486. w = Math.min(Math.max(mw, w), mxw);
  487. break;
  488. case 'south':
  489. h += diffY;
  490. h = Math.min(Math.max(mh, h), mxh);
  491. break;
  492. case 'southeast':
  493. w += diffX;
  494. h += diffY;
  495. w = Math.min(Math.max(mw, w), mxw);
  496. h = Math.min(Math.max(mh, h), mxh);
  497. break;
  498. case 'north':
  499. diffY = this.constrain(h, diffY, mh, mxh);
  500. y += diffY;
  501. h -= diffY;
  502. break;
  503. case 'west':
  504. diffX = this.constrain(w, diffX, mw, mxw);
  505. x += diffX;
  506. w -= diffX;
  507. break;
  508. case 'northeast':
  509. w += diffX;
  510. w = Math.min(Math.max(mw, w), mxw);
  511. diffY = this.constrain(h, diffY, mh, mxh);
  512. y += diffY;
  513. h -= diffY;
  514. break;
  515. case 'northwest':
  516. diffX = this.constrain(w, diffX, mw, mxw);
  517. diffY = this.constrain(h, diffY, mh, mxh);
  518. y += diffY;
  519. h -= diffY;
  520. x += diffX;
  521. w -= diffX;
  522. break;
  523. case 'southwest':
  524. diffX = this.constrain(w, diffX, mw, mxw);
  525. h += diffY;
  526. h = Math.min(Math.max(mh, h), mxh);
  527. x += diffX;
  528. w -= diffX;
  529. break;
  530. }
  531. var sw = this.snap(w, wi, mw);
  532. var sh = this.snap(h, hi, mh);
  533. if(sw != w || sh != h){
  534. switch(pos){
  535. case 'northeast':
  536. y -= sh - h;
  537. break;
  538. case 'north':
  539. y -= sh - h;
  540. break;
  541. case 'southwest':
  542. x -= sw - w;
  543. break;
  544. case 'west':
  545. x -= sw - w;
  546. break;
  547. case 'northwest':
  548. x -= sw - w;
  549. y -= sh - h;
  550. break;
  551. }
  552. w = sw;
  553. h = sh;
  554. }
  555. if(this.preserveRatio){
  556. switch(pos){
  557. case 'southeast':
  558. case 'east':
  559. h = oh * (w/ow);
  560. h = Math.min(Math.max(mh, h), mxh);
  561. w = ow * (h/oh);
  562. break;
  563. case 'south':
  564. w = ow * (h/oh);
  565. w = Math.min(Math.max(mw, w), mxw);
  566. h = oh * (w/ow);
  567. break;
  568. case 'northeast':
  569. w = ow * (h/oh);
  570. w = Math.min(Math.max(mw, w), mxw);
  571. h = oh * (w/ow);
  572. break;
  573. case 'north':
  574. tw = w;
  575. w = ow * (h/oh);
  576. w = Math.min(Math.max(mw, w), mxw);
  577. h = oh * (w/ow);
  578. x += (tw - w) / 2;
  579. break;
  580. case 'southwest':
  581. h = oh * (w/ow);
  582. h = Math.min(Math.max(mh, h), mxh);
  583. tw = w;
  584. w = ow * (h/oh);
  585. x += tw - w;
  586. break;
  587. case 'west':
  588. th = h;
  589. h = oh * (w/ow);
  590. h = Math.min(Math.max(mh, h), mxh);
  591. y += (th - h) / 2;
  592. tw = w;
  593. w = ow * (h/oh);
  594. x += tw - w;
  595. break;
  596. case 'northwest':
  597. tw = w;
  598. th = h;
  599. h = oh * (w/ow);
  600. h = Math.min(Math.max(mh, h), mxh);
  601. w = ow * (h/oh);
  602. y += th - h;
  603. x += tw - w;
  604. break;
  605. }
  606. }
  607. this.proxy.setBounds(x, y, w, h);
  608. if(this.dynamic){
  609. this.resizeElement();
  610. }
  611. }catch(ex){}
  612. }
  613. },
  614. // private
  615. handleOver : function(){
  616. if(this.enabled){
  617. this.el.addClass('x-resizable-over');
  618. }
  619. },
  620. // private
  621. handleOut : function(){
  622. if(!this.resizing){
  623. this.el.removeClass('x-resizable-over');
  624. }
  625. },
  626. /**
  627. * Returns the element this component is bound to.
  628. * @return {Ext.Element}
  629. */
  630. getEl : function(){
  631. return this.el;
  632. },
  633. /**
  634. * Returns the resizeChild element (or null).
  635. * @return {Ext.Element}
  636. */
  637. getResizeChild : function(){
  638. return this.resizeChild;
  639. },
  640. /**
  641. * Destroys this resizable. If the element was wrapped and
  642. * removeEl is not true then the element remains.
  643. * @param {Boolean} removeEl (optional) true to remove the element from the DOM
  644. */
  645. destroy : function(removeEl){
  646. Ext.destroy(this.dd, this.overlay, this.proxy);
  647. this.overlay = null;
  648. this.proxy = null;
  649. var ps = Ext.Resizable.positions;
  650. for(var k in ps){
  651. if(typeof ps[k] != 'function' && this[ps[k]]){
  652. this[ps[k]].destroy();
  653. }
  654. }
  655. if(removeEl){
  656. this.el.update('');
  657. Ext.destroy(this.el);
  658. this.el = null;
  659. }
  660. this.purgeListeners();
  661. },
  662. syncHandleHeight : function(){
  663. var h = this.el.getHeight(true);
  664. if(this.west){
  665. this.west.el.setHeight(h);
  666. }
  667. if(this.east){
  668. this.east.el.setHeight(h);
  669. }
  670. }
  671. });
  672. // private
  673. // hash to map config positions to true positions
  674. Ext.Resizable.positions = {
  675. n: 'north', s: 'south', e: 'east', w: 'west', se: 'southeast', sw: 'southwest', nw: 'northwest', ne: 'northeast'
  676. };
  677. Ext.Resizable.Handle = Ext.extend(Object, {
  678. constructor : function(rz, pos, disableTrackOver, transparent, cls){
  679. if(!this.tpl){
  680. // only initialize the template if resizable is used
  681. var tpl = Ext.DomHelper.createTemplate(
  682. {tag: 'div', cls: 'x-resizable-handle x-resizable-handle-{0}'}
  683. );
  684. tpl.compile();
  685. Ext.Resizable.Handle.prototype.tpl = tpl;
  686. }
  687. this.position = pos;
  688. this.rz = rz;
  689. this.el = this.tpl.append(rz.el.dom, [this.position], true);
  690. this.el.unselectable();
  691. if(transparent){
  692. this.el.setOpacity(0);
  693. }
  694. if(!Ext.isEmpty(cls)){
  695. this.el.addClass(cls);
  696. }
  697. this.el.on('mousedown', this.onMouseDown, this);
  698. if(!disableTrackOver){
  699. this.el.on({
  700. scope: this,
  701. mouseover: this.onMouseOver,
  702. mouseout: this.onMouseOut
  703. });
  704. }
  705. },
  706. // private
  707. afterResize : function(rz){
  708. // do nothing
  709. },
  710. // private
  711. onMouseDown : function(e){
  712. this.rz.onMouseDown(this, e);
  713. },
  714. // private
  715. onMouseOver : function(e){
  716. this.rz.handleOver(this, e);
  717. },
  718. // private
  719. onMouseOut : function(e){
  720. this.rz.handleOut(this, e);
  721. },
  722. // private
  723. destroy : function(){
  724. Ext.destroy(this.el);
  725. this.el = null;
  726. }
  727. });