Combobox
加载下拉框数据
点击下拉框,数据从后台加载,是很常见的需求。如下图:
View 中下拉框
dockedItems : [ { dock : 'top', xtype : 'toolbar', items : [ { xtype : 'combobox', name : 'currYear', fieldLabel : '年度', labelAlign : 'right', labelWidth : 30, width : 100, emptyText : '', editable : false, margin : '5 5 5 5', displayField : 'year',// 显示值,因 model 中有一个 year 属性,所以数据返回到页面上,将显示值和真值,都设置为 year 字段值 valueField : 'year',// 真值 store : 'jsxm.yearStore', } ]
Store
Ext.define('MyApp.store.jsxm.yearStore', { extend : 'Ext.data.Store', model : 'MyApp.model.jsxm.yearModel', proxy : { type : 'ajax', url : 'jsxmAction!getYears', reader : { type : 'json', root : 'years'// {"years":[{"year":"全部"},{"year":"2017"},{"year":"2016"},{"year":"2015"}]} } }, autoLoad : false });
Model
Ext.define('MyApp.model.jsxm.yearModel', { extend : 'Ext.data.Model', fields : [ { name : 'year', type : 'string' } ] });
后台方法
public void getYears() { QueryDataSource qds = new QueryDataSource();// 公司接口 try { // 公司接口,查询表中 noyear 字段的值 ArrayList<String> yearList = qds.queryObjectProperty("cg_jsxm_hp", "noyear", true, "1=1 order by noyear desc"); System.out.println(yearList);// [2017, 2016, 2015, 2014, 2013, 2012, 2011, 2010, 2009, 2008] ArrayList<HashMap> list = new ArrayList<HashMap>(); HashMap<String, String> map = new HashMap<String, String>(); map.put("year", "全部"); list.add(map);// 第一个 map 放进 list 中,[{year=全部}] for (String year : yearList) { HashMap<String, String> hashMap = new HashMap<String, String>(); hashMap.put("year", year); list.add(map); } JSONArray jsonArray = JSONArray.fromObject(list); String data = "{"years":" + jsonArray.toString() + "}";// 组装 json 数据,store 中有 reader: {type: 'json', root: 'years'},root 要对应起来 System.out.println(data);// {"years":[{"year":"全部"},{"year":"2017"},{"year":"2016"},{"year":"2015"}]} send(data);// 封装的方法 public void send(String s){ServletActionContext.getResponse().getWriter().write(s)}; } catch (Exception e) { e.printStackTrace(); } }
封装的 send 方法
public void send(String s) { try { HttpServletResponse response = ServletActionContext.getResponse(); response.setCharacterEncoding("UTF-8"); response.setContentType("text/html;charset=UTF-8"); response.getWriter().write(s); } catch (Exception e) { e.printStackTrace(); } }
执行方法后,返回数据:
级联下拉框
Ext.define('MyApp.view.hdjg.hzzhdView', { extend : 'Ext.grid.Panel', alias : 'widget.hzzhdView', id : 'hzzhdView', layout : 'fit', simpleSelect : false, store : 'hdjg.hzzhdStore', autoScroll : true, initComponent : function(){ Ext.define('hdmcModel', { extend : 'Ext.data.Model', fields : [ { type : 'String', name : 'text' }, { type : 'String', name : 'value' } ] }); // hdmcStore 作为 hdmc 下拉框的 Store var hdmcStore = Ext.create('Ext.data.Store', { model : 'hdmcModel', listeners : { 'beforeload' : function() { var grid = Ext.getCmp('hzzhdView'); var tableName = 'hzz_hdydjcxx';// 实际项目里,两处(查询的表不同)用到 proxy 下的方法,所以,这里将需要查询的表,也作为参数传递进去。 if (grid) { Ext.apply(this.proxy.extraParams, { // 取参数 xsqmc : grid.down('combobox[name="xsqmc"]').getValue(), tableName : tableName }); } } }, proxy : { type : 'ajax', url : 'hdjgAction!getHdmcByXsqmc'// 级联 // 此处没有 reader 配置,无所谓,后台数据直接传一个数组即可,这里有 reader 配置的话,后台组装下 json 字符串即可,很简单。 }, autoLoad : true }); this.columns = [];// 此处代码省略 // 停靠组件部分> 搜索条件工具栏 this.dockedItems = [ { dock : 'top', xtype : 'toolbar', autoShow : true, enableOverflow : true, layout : { overflowHandler : 'Menu'// items太多溢出处理 }, items : [ { xtype : 'combobox', name : 'xsqmc', fieldLabel : '县区市', labelAlign : 'right', labelWidth : 40, width : 180, editable : false, emptyText : '<县区市名称>', store : [ '全部', '市级', '海曙区', '江北区', '镇海区', '北仑区', '鄞州区', '奉化区', '余姚市', '慈溪市', '宁海县', '象山县', '杭州湾新区', '大榭开发区', '高新区', '东钱湖旅游度假区', '典型示范河道' ], listeners : { // 监听 combobox 的 select 事件,在函数里执行加载 需要级联的 combobox 的操作 'select' : function(combo, record, index) { var relativeCombo = Ext.getCmp("hdmcStoreId"); relativeCombo.value = "";// 加载之前把,下拉框值设为 '',则会先显示 hdmcStore 的 emptyText,加载完成后,显示完整 combobox 数据 relativeCombo.store.load(); } } }, { xtype : 'combobox', id : 'hdmcStoreId',// 当前下拉框组件'id' store : hdmcStore, name : 'hdmc', fieldLabel : '河道名称', labelWidth : 60, width : 280, displayField : 'text', valueField : 'value', emptyText : '请选择<河道名称>', editable : false } ] } ]; this.callParent(arguments); } }); public void getHdmcByXsqmc() { String type = this.tableName; ArrayList<TextAndValue> list = new ArrayList<TextAndValue>(); TextAndValue temp = new TextAndValue();// 就是一实体类,属性 text、value、getter && setter方法 temp.setText("全部"); temp.setValue(""); list.add(temp); if (xsqmc != null && !"".equals(xsqmc)) { try { QueryDataSource qds = new QueryDataSource(); String sql = "select distinct hdmc from "+ type +" where 1=1 and xsqmc = '" + xsqmc + "'"; ArrayList<HashMap<Object, Object>> arrayList = qds.queryDBSQL(sql); System.out.println(arrayList);// [{HDMC=梅梁桥河}, {HDMC=槐路河}, {HDMC=黄家门前河}, {HDMC=姚江(蜀山大闸-城山渡渡口)}, {}, {}...] for(HashMap<Object, Object> map: arrayList){ TextAndValue textAndValue = new TextAndValue(); textAndValue.setText(map.get("HDMC").toString()); textAndValue.setValue(map.get("HDMC").toString()); list.add(textAndValue); } } catch (Exception e) { // TODO: handle exception e.printStackTrace(); } } String data = JSONArray.fromObject(list).toString();// [{"text":"全部","value":""},{"text":"梅梁桥河","value":"梅梁桥河"}, {}, {}...] send(data);// 将 list 转为 json 字符串对象,然后直接返回到客户端 } // 如果 store 的 proxy 配置里,有 reader 配置的话,则组装下 json 即可,没有配置 reader 的话,直接返回数组也是可以的。 reader: { type: 'json', root: 'riverName' } String data = "{"riverName":" + JSONArray.fromObject(list).toString() + "}"; send(data);// {"riverName": [{"text":"全部","value":""},{"text":"梅梁桥河","value":"梅梁桥河"}, {}, {}...]}
页面效果:
点击 县区市 下拉框后,发现,河道名称 下拉框发生了变化,级联操作,没毛病。