首先是項目的環境是java,用到spring3.1.2的框架,展現數據用的是 EXTJsjava
(1)js代碼中:node
{ fieldLabel: '下拉樹分類', xtype: 'combotree', name : 'categoryId', valueField :"categoryId", hiddenName: 'categoryId', tplId : 'tree_tpl', rootVisible : true, rootText : '分類', rootId:'0', root: { nodeType: 'async' }, tree : new Ext.tree.TreePanel({ loader: new Ext.tree.TreeLoader({dataUrl:'application/categoryTree.json?type=2'}), root : new Ext.tree.AsyncTreeNode({id:'0',text:'根結點'}) }), maxHeight :300, id: 'id', allowBlank: true, selectMode:'leaf', width : '200', listeners: { //設置監聽 checkchange: function(node, checked){ node.expand(); node.attributes.checked = checked; node.eachChild(function(child) { child.ui.toggleCheck(checked); child.attributes.checked = checked; child.fireEvent('checkchange', child, checked); }) }, callback:function(id,text){ alert(id); alert(text); //能夠作更多的處理。 }, afterRender: function (t) { treeP = t; }, select: function(combotree,newNode,oldNode){//選擇樹結點設值以後的事件 } } }
其中組件 xtype: 'combotree'完整的代碼:spring
Ext.namespace('Ext.ux'); Ext.ux.ComboBoxTree = function(){ this.treeId = Ext.id()+'-tree'; this.maxHeight = arguments[0].maxHeight || arguments[0].height || this.maxHeight; this.tpl = new Ext.Template('<tpl for="."><div style="height:'+this.maxHeight+'px"><div id="'+this.treeId+'"></div></div></tpl>'); this.store = new Ext.data.SimpleStore({fields:[],data:[[]]}); this.selectedClass = ''; this.mode = 'local'; this.triggerAction = 'all'; this.onSelect = Ext.emptyFn; this.editable = false; this.beforeBlur = Ext.emptyFn; //all:全部結點均可選中 //exceptRoot:除根結點,其它結點均可選(默認) //folder:只有目錄(非葉子和非根結點)可選 //leaf:只有葉子結點可選 this.selectNodeModel = arguments[0].selectNodeModel || 'exceptRoot'; /* * single單選 (默認) * multiple 多選的 */ this.selectModel = arguments[0].selectModel || 'single'; this.addEvents('afterchange'); Ext.ux.ComboBoxTree.superclass.constructor.apply(this, arguments); } Ext.extend(Ext.ux.ComboBoxTree,Ext.form.ComboBox, { expand : function(){ Ext.ux.ComboBoxTree.superclass.expand.call(this); if(this.tree.rendered){ return; } Ext.apply(this.tree,{height:this.maxHeight, width:(this.listWidth||this.width-(Ext.isIE?3:0))-2, border:false, autoScroll:true}); if(this.tree.xtype){ this.tree = Ext.ComponentMgr.create(this.tree, this.tree.xtype); } this.tree.render(this.treeId); var root = this.tree.getRootNode(); if(!root.isLoaded()) root.reload(); this.tree.on('click',function(node){ var selModel = this.selectNodeModel; var isLeaf = node.isLeaf(); if((node == root) && selModel != 'all'){ return; }else if(selModel=='folder' && isLeaf){ return; }else if(selModel=='leaf' && !isLeaf){ return; } var oldNode = this.getNode(); if(this.fireEvent('beforeselect', this, node, oldNode) !== false) { this.setValue(node); this.collapse(); this.fireEvent('select', this, node, oldNode); (oldNode !== node) ? this.fireEvent('afterchange', this, node, oldNode) : ''; } }, this); }, setValue : function(node){ this.node = node; var text = node.text; this.lastSelectionText = text; if(this.hiddenField){ this.hiddenField.value = node.id; } Ext.form.ComboBox.superclass.setValue.call(this, text); this.value = node.id; }, setDoubleValues : function(values,v){ if(values){ if(Ext.isArray(values)){ for(var i = 0, len = values.length; i < len; i++){ var v = values[i]; var f = this.findField(v.id); if(f){ f.setValue(v.value); if(this.trackResetOnLoad){ f.originalValue = f.getValue(); } } } }else{ var field, id; for(id in values){ if(!Ext.isFunction(values[id]) && (field = this.findField(id))){ field.setValue(values[id]); if(this.trackResetOnLoad){ field.originalValue = field.getValue(); } } } } return this; }else { var text = v; if(this.valueField){ var r = this.findRecord(this.valueField, v); if(r){ text = r.data[this.displayField]; }else if(Ext.isDefined(this.valueNotFoundText)){ text = this.valueNotFoundText; } } this.lastSelectionText = text; if(this.hiddenField){ this.hiddenField.value = Ext.value(v, ''); } Ext.form.ComboBox.superclass.setValue.call(this, text); this.value = v; return this; } }, //重寫comboBox組件的setValue()的方法,目的是得到組件的valueField的值 setCategoryValue : function(v){ var text = v; if(this.valueField){ var r = this.findRecord(this.valueField, v); if(r){ text = r.data[this.displayField]; }else if(Ext.isDefined(this.valueNotFoundText)){ text = this.valueNotFoundText; } } this.lastSelectionText = text; if(this.hiddenField){ this.hiddenField.value = Ext.value(v, ''); } Ext.form.ComboBox.superclass.setValue.call(this, text); this.value = v; return this; }, getValue : function(){ return typeof this.value != 'undefined' ? this.value : ''; }, getNode : function(){ return this.node; }, clearValue : function(){ Ext.ux.ComboBoxTree.superclass.clearValue.call(this); this.node = null; }, // 重寫onViewClick,使展開樹結點是不關閉下拉框 onViewClick : function(doFocus) { var index = this.view.getSelectedIndexes()[0], s = this.store, r = s.getAt(index); if (r) { this.onSelect(r, index); } if (doFocus !== false) { this.el.focus(); } }, // private destroy: function() { Ext.ux.ComboBoxTree.superclass.destroy.call(this); Ext.destroy([this.node,this.tree]); delete this.node; } }); Ext.reg('combotree', Ext.ux.ComboBoxTree);
(2) loader: new Ext.tree.TreeLoader({dataUrl:'application/categoryTree.json?type=2'})在Controller類中代碼:json
/** * 類別下拉樹列表 * @param model */ @RequestMapping("/categoryTree") public void categoryTree(Model model,Integer type) { List<TreeNode> listChildNode =applicationService.getChildNodeList(0,type==1?false:true); model.addAttribute("nodes",listChildNode); model.addAttribute(SUCCESS, true); }
(3)在Service類中:app
/** * 下拉樹形集合 * @param pid * @return */ public List<TreeNode> getChildNodeList(int pid,boolean hasChecked){ List<TreeNode> list =applicationMapper.selectChildNodeList(pid); for(TreeNode rn:list){ List<TreeNode> innerList =getChildNodeList(rn.getId(),hasChecked); rn.setChildren(innerList); if(hasChecked){ rn.setChecked(false); }; if(rn.getPid().intValue()==0){ rn.setLeaf(false);//第一級所有不是葉子 }else{ rn.setLeaf(innerList.size()==0?true:false); } } return list; }
(4)在映射類Mapper中:框架
/** * 找出子節點 * @param pid * @return */ List<TreeNode> selectChildNodeList(int pid);
(5)在XML中的SQlasync
<select id="selectChildNodeList" resultType="TreeNode" parameterType="Integer"> SELECT id,pid,name as text,type,sort FROM sb_common_category WHERE pid=#{pid} </select>
(6)最後展現的前臺的EXTjs的頁面:ui
(7)到此就是combox結合樹形的一個展現,由於以前我已經有文章介紹了樹形,全部就不說了,這裏主要的是自定了一個下拉樹的一個組件combotree 。this
(8)這裏順便說一下,若是是要根據條件下拉框去展現默認值的話,只要在請求傳一個參數過去,而且在js中要找到這個下拉框的組件,而且都給valeField和displayName賦值就好了。spa
後續有不少開發填坑的文章發佈,若是對你有幫助,請支持和加關注一下