Upgrade to ExtJS 3.2.0 - Released 03/30/2010
[extjs.git] / docs / source / TreeSelectionModel.html
1 <html>
2 <head>
3   <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />    
4   <title>The source code</title>
5     <link href="../resources/prettify/prettify.css" type="text/css" rel="stylesheet" />
6     <script type="text/javascript" src="../resources/prettify/prettify.js"></script>
7 </head>
8 <body  onload="prettyPrint();">
9     <pre class="prettyprint lang-js">/*!
10  * Ext JS Library 3.2.0
11  * Copyright(c) 2006-2010 Ext JS, Inc.
12  * licensing@extjs.com
13  * http://www.extjs.com/license
14  */
15 <div id="cls-Ext.tree.DefaultSelectionModel"></div>/**
16  * @class Ext.tree.DefaultSelectionModel
17  * @extends Ext.util.Observable
18  * The default single selection for a TreePanel.
19  */
20 Ext.tree.DefaultSelectionModel = function(config){
21    this.selNode = null;
22    
23    this.addEvents(
24        <div id="event-Ext.tree.DefaultSelectionModel-selectionchange"></div>/**
25         * @event selectionchange
26         * Fires when the selected node changes
27         * @param {DefaultSelectionModel} this
28         * @param {TreeNode} node the new selection
29         */
30        'selectionchange',
31
32        <div id="event-Ext.tree.DefaultSelectionModel-beforeselect"></div>/**
33         * @event beforeselect
34         * Fires before the selected node changes, return false to cancel the change
35         * @param {DefaultSelectionModel} this
36         * @param {TreeNode} node the new selection
37         * @param {TreeNode} node the old selection
38         */
39        'beforeselect'
40    );
41
42     Ext.apply(this, config);
43     Ext.tree.DefaultSelectionModel.superclass.constructor.call(this);
44 };
45
46 Ext.extend(Ext.tree.DefaultSelectionModel, Ext.util.Observable, {
47     init : function(tree){
48         this.tree = tree;
49         tree.mon(tree.getTreeEl(), 'keydown', this.onKeyDown, this);
50         tree.on('click', this.onNodeClick, this);
51     },
52     
53     onNodeClick : function(node, e){
54         this.select(node);
55     },
56     
57     <div id="method-Ext.tree.DefaultSelectionModel-select"></div>/**
58      * Select a node.
59      * @param {TreeNode} node The node to select
60      * @return {TreeNode} The selected node
61      */
62     select : function(node, /* private*/ selectNextNode){
63         // If node is hidden, select the next node in whatever direction was being moved in.
64         if (!Ext.fly(node.ui.wrap).isVisible() && selectNextNode) {
65             return selectNextNode.call(this, node);
66         }
67         var last = this.selNode;
68         if(node == last){
69             node.ui.onSelectedChange(true);
70         }else if(this.fireEvent('beforeselect', this, node, last) !== false){
71             if(last && last.ui){
72                 last.ui.onSelectedChange(false);
73             }
74             this.selNode = node;
75             node.ui.onSelectedChange(true);
76             this.fireEvent('selectionchange', this, node, last);
77         }
78         return node;
79     },
80     
81     <div id="method-Ext.tree.DefaultSelectionModel-unselect"></div>/**
82      * Deselect a node.
83      * @param {TreeNode} node The node to unselect
84      * @param {Boolean} silent True to stop the selectionchange event from firing.
85      */
86     unselect : function(node, silent){
87         if(this.selNode == node){
88             this.clearSelections(silent);
89         }    
90     },
91     
92     <div id="method-Ext.tree.DefaultSelectionModel-clearSelections"></div>/**
93      * Clear all selections
94      * @param {Boolean} silent True to stop the selectionchange event from firing.
95      */
96     clearSelections : function(silent){
97         var n = this.selNode;
98         if(n){
99             n.ui.onSelectedChange(false);
100             this.selNode = null;
101             if(silent !== true){
102                 this.fireEvent('selectionchange', this, null);
103             }
104         }
105         return n;
106     },
107     
108     <div id="method-Ext.tree.DefaultSelectionModel-getSelectedNode"></div>/**
109      * Get the selected node
110      * @return {TreeNode} The selected node
111      */
112     getSelectedNode : function(){
113         return this.selNode;    
114     },
115     
116     <div id="method-Ext.tree.DefaultSelectionModel-isSelected"></div>/**
117      * Returns true if the node is selected
118      * @param {TreeNode} node The node to check
119      * @return {Boolean}
120      */
121     isSelected : function(node){
122         return this.selNode == node;  
123     },
124
125     <div id="method-Ext.tree.DefaultSelectionModel-selectPrevious"></div>/**
126      * Selects the node above the selected node in the tree, intelligently walking the nodes
127      * @return TreeNode The new selection
128      */
129     selectPrevious : function(/* private */ s){
130         if(!(s = s || this.selNode || this.lastSelNode)){
131             return null;
132         }
133         // Here we pass in the current function to select to indicate the direction we're moving
134         var ps = s.previousSibling;
135         if(ps){
136             if(!ps.isExpanded() || ps.childNodes.length < 1){
137                 return this.select(ps, this.selectPrevious);
138             } else{
139                 var lc = ps.lastChild;
140                 while(lc && lc.isExpanded() && Ext.fly(lc.ui.wrap).isVisible() && lc.childNodes.length > 0){
141                     lc = lc.lastChild;
142                 }
143                 return this.select(lc, this.selectPrevious);
144             }
145         } else if(s.parentNode && (this.tree.rootVisible || !s.parentNode.isRoot)){
146             return this.select(s.parentNode, this.selectPrevious);
147         }
148         return null;
149     },
150
151     <div id="method-Ext.tree.DefaultSelectionModel-selectNext"></div>/**
152      * Selects the node above the selected node in the tree, intelligently walking the nodes
153      * @return TreeNode The new selection
154      */
155     selectNext : function(/* private */ s){
156         if(!(s = s || this.selNode || this.lastSelNode)){
157             return null;
158         }
159         // Here we pass in the current function to select to indicate the direction we're moving
160         if(s.firstChild && s.isExpanded() && Ext.fly(s.ui.wrap).isVisible()){
161              return this.select(s.firstChild, this.selectNext);
162          }else if(s.nextSibling){
163              return this.select(s.nextSibling, this.selectNext);
164          }else if(s.parentNode){
165             var newS = null;
166             s.parentNode.bubble(function(){
167                 if(this.nextSibling){
168                     newS = this.getOwnerTree().selModel.select(this.nextSibling, this.selectNext);
169                     return false;
170                 }
171             });
172             return newS;
173          }
174         return null;
175     },
176
177     onKeyDown : function(e){
178         var s = this.selNode || this.lastSelNode;
179         // undesirable, but required
180         var sm = this;
181         if(!s){
182             return;
183         }
184         var k = e.getKey();
185         switch(k){
186              case e.DOWN:
187                  e.stopEvent();
188                  this.selectNext();
189              break;
190              case e.UP:
191                  e.stopEvent();
192                  this.selectPrevious();
193              break;
194              case e.RIGHT:
195                  e.preventDefault();
196                  if(s.hasChildNodes()){
197                      if(!s.isExpanded()){
198                          s.expand();
199                      }else if(s.firstChild){
200                          this.select(s.firstChild, e);
201                      }
202                  }
203              break;
204              case e.LEFT:
205                  e.preventDefault();
206                  if(s.hasChildNodes() && s.isExpanded()){
207                      s.collapse();
208                  }else if(s.parentNode && (this.tree.rootVisible || s.parentNode != this.tree.getRootNode())){
209                      this.select(s.parentNode, e);
210                  }
211              break;
212         };
213     }
214 });
215
216 <div id="cls-Ext.tree.MultiSelectionModel"></div>/**
217  * @class Ext.tree.MultiSelectionModel
218  * @extends Ext.util.Observable
219  * Multi selection for a TreePanel.
220  */
221 Ext.tree.MultiSelectionModel = function(config){
222    this.selNodes = [];
223    this.selMap = {};
224    this.addEvents(
225        <div id="event-Ext.tree.MultiSelectionModel-selectionchange"></div>/**
226         * @event selectionchange
227         * Fires when the selected nodes change
228         * @param {MultiSelectionModel} this
229         * @param {Array} nodes Array of the selected nodes
230         */
231        'selectionchange'
232    );
233     Ext.apply(this, config);
234     Ext.tree.MultiSelectionModel.superclass.constructor.call(this);
235 };
236
237 Ext.extend(Ext.tree.MultiSelectionModel, Ext.util.Observable, {
238     init : function(tree){
239         this.tree = tree;
240         tree.mon(tree.getTreeEl(), 'keydown', this.onKeyDown, this);
241         tree.on('click', this.onNodeClick, this);
242     },
243     
244     onNodeClick : function(node, e){
245         if(e.ctrlKey && this.isSelected(node)){
246             this.unselect(node);
247         }else{
248             this.select(node, e, e.ctrlKey);
249         }
250     },
251     
252     <div id="method-Ext.tree.MultiSelectionModel-select"></div>/**
253      * Select a node.
254      * @param {TreeNode} node The node to select
255      * @param {EventObject} e (optional) An event associated with the selection
256      * @param {Boolean} keepExisting True to retain existing selections
257      * @return {TreeNode} The selected node
258      */
259     select : function(node, e, keepExisting){
260         if(keepExisting !== true){
261             this.clearSelections(true);
262         }
263         if(this.isSelected(node)){
264             this.lastSelNode = node;
265             return node;
266         }
267         this.selNodes.push(node);
268         this.selMap[node.id] = node;
269         this.lastSelNode = node;
270         node.ui.onSelectedChange(true);
271         this.fireEvent('selectionchange', this, this.selNodes);
272         return node;
273     },
274     
275     <div id="method-Ext.tree.MultiSelectionModel-unselect"></div>/**
276      * Deselect a node.
277      * @param {TreeNode} node The node to unselect
278      */
279     unselect : function(node){
280         if(this.selMap[node.id]){
281             node.ui.onSelectedChange(false);
282             var sn = this.selNodes;
283             var index = sn.indexOf(node);
284             if(index != -1){
285                 this.selNodes.splice(index, 1);
286             }
287             delete this.selMap[node.id];
288             this.fireEvent('selectionchange', this, this.selNodes);
289         }
290     },
291     
292     <div id="method-Ext.tree.MultiSelectionModel-clearSelections"></div>/**
293      * Clear all selections
294      */
295     clearSelections : function(suppressEvent){
296         var sn = this.selNodes;
297         if(sn.length > 0){
298             for(var i = 0, len = sn.length; i < len; i++){
299                 sn[i].ui.onSelectedChange(false);
300             }
301             this.selNodes = [];
302             this.selMap = {};
303             if(suppressEvent !== true){
304                 this.fireEvent('selectionchange', this, this.selNodes);
305             }
306         }
307     },
308     
309     <div id="method-Ext.tree.MultiSelectionModel-isSelected"></div>/**
310      * Returns true if the node is selected
311      * @param {TreeNode} node The node to check
312      * @return {Boolean}
313      */
314     isSelected : function(node){
315         return this.selMap[node.id] ? true : false;  
316     },
317     
318     <div id="method-Ext.tree.MultiSelectionModel-getSelectedNodes"></div>/**
319      * Returns an array of the selected nodes
320      * @return {Array}
321      */
322     getSelectedNodes : function(){
323         return this.selNodes;    
324     },
325
326     onKeyDown : Ext.tree.DefaultSelectionModel.prototype.onKeyDown,
327
328     selectNext : Ext.tree.DefaultSelectionModel.prototype.selectNext,
329
330     selectPrevious : Ext.tree.DefaultSelectionModel.prototype.selectPrevious
331 });</pre>    
332 </body>
333 </html>