您现在的位置是:首页 > 文章详情

使用 flex4 开发通用统计系统,发布源代码至github

日期:2014-09-07点击:408

1,关于flex4 

很老的技术,我居然还再研究使用这个东西,自己想想都不敢相信。

技术存在总是有他的理由的。之所以想用flex4 开发一个通用统计系统,还是有几个有点的:

a,组件比较全,比较全,基本上省去了自己开发

b,在局域网下一次获取大量json数据并解析展示到flex里面速度比html快,图标效果比较好

c,开发系统一个人就够了,浏览器兼容比较好,只要安装flash就行,尤其要做成产品给xp系统的使用那个IE兼容性痛苦啊

当然也有缺点,技术学习成本不低,属于不流行的没落的技术。

但这个不影响做项目,项目的技术选型要合理,维护成本低,综合考虑,而不是所有的全部用新技术,把自己玩死。

存在就有他的意义,不影响做项目,不影响挣钱。

2,系统设计原理

统计系统,设计的不是解决某一个统计问题,而是做一个统计的展示界面,把统计的sql都做xml配置起来。


系统展示界面展示效果:


其中系统的左侧菜单是menu.xml进行控制的

<?xml version="1.0" encoding="utf-8"?> <!-- 定义左侧菜单: --> <menus> <menu label="用户数据统计"> <menu label="用户注册统计" module="/assets/flex/DataGrid.swf" id="stat-demo"/> <menu label="用户登陆统计" module="/assets/flex/DataGrid.swf" id="stat-user-reg"/> </menu> <menu label="系统设置"> <menu label="菜单管理" module="/assets/flex/DataMenu.swf" /> <menu label="数据管理" module="/assets/flex/DataCRUD.swf" /> </menu> </menus>

通过配置不同的flash文件可以展示不同的配置显示。

通过扩展module可以扩展展示效果。

stat-user-reg.xml配置,显示查询数据

<?xml version="1.0" encoding="UTF-8"?> <stats> <!-- 统计数据xml 按照id进行查找。--> <stat id="stat-demo-1"> <!-- 展示数据 --> <list> <column field="id" text="id"/> <column field="name" text="注册姓名"/> <column field="sex" text="注册性别"/> <column field="city" text="注册城市"/> <column field="phone" text="注册电话"/> </list> <sql><![CDATA[ select id,`name`,sex,city,phone,address,qq,email from stat_demo_01 limit 10 ]]></sql> </stat> </stats>

显示效果如下:

目前已经完成数据显示。但没有数据查询和分页配置,继续开发。

3,服务端代码

服务端,读取xml中的sql语句和配置,拼接成json数据。

/** * User: freewebsys.com */ @Service("statBaseService") public class StatBaseServiceImpl implements StatBaseService { @Autowired private StatBaseDao statBaseDao; //读取xml文件返回Document。 private Document xmlReader(String confXml) { try { SAXReader reader = new SAXReader(); return reader.read(IOUtils.toInputStream(confXml)); } catch (DocumentException e) { e.printStackTrace(); return null; } } //主函数,负责循环处理节点。 public String findStat(String confXml) { Document document = xmlReader(confXml); System.out.println(document); List<DefaultElement> list = document.selectNodes("/stats/stat"); for (DefaultElement element : list) { mergeStatElement(element); } return document.asXML(); } private DefaultElement mergeStatElement(DefaultElement element) { System.out.println(element); //处理查询出所有列表显示的元素。 List<DefaultElement> columnList = element.selectNodes("list/column"); //找到查询sql。 Node sqlNode = element.selectSingleNode("sql"); String sql = sqlNode.getText(); //获取数据后将节点删除。在客户端不显示。 element.remove(sqlNode); System.out.println(sql); List<Map<String, Object>> list = statBaseDao.findStat(sql, null); JSONArray jsonArray = new JSONArray(); for (Map<String, Object> tmpData : list) { JSONObject jsonObject = new JSONObject(); for (DefaultElement column : columnList) { System.out.println(column); String columnName = column.attributeValue("field"); Object objValue = tmpData.get(columnName); jsonObject.put(columnName, objValue); //将一行数据组织成对象,放到数组里面。 } jsonArray.add(jsonObject); } DefaultElement elementData = new DefaultElement("data"); elementData.add(new DefaultCDATA(jsonArray.toJSONString())); //增加data字段,保存json数据。 element.add(elementData); return element; } //读取配置文件。 public String readConfFile(String configName) { String basePath = StatBaseServiceImpl.class.getResource("/") .toString().replace("file:", ""); try { return FileUtils.readFileToString(new File(basePath + configName), "utf-8"); } catch (IOException e) { e.printStackTrace(); return ""; } } }

通过读取xml配置文件,将数据返回

<?xml version="1.0" encoding="UTF-8"?> <stats> <!-- 统计数据xml 按照id进行查找。--> <stat id="stat-demo-1"> <!-- 展示数据 --> <list> <column field="id" text="id"/> <column field="name" text="注册姓名"/> <column field="sex" text="注册性别"/> <column field="city" text="注册城市"/> <column field="phone" text="注册电话"/> </list> <data><![CDATA[[{"city":"city_222","id":1,"name":"222","phone":"1222","sex":"1"}, {"city":"city_33","id":2,"name":"33","phone":"233","sex":"0"}, {"city":"city_33","id":3,"name":"33","phone":"333","sex":"1"}, {"city":"city_45","id":4,"name":"45","phone":"445","sex":"0"}, {"city":"city_6","id":5,"name":"6","phone":"56","sex":"1"}, {"city":"city_7","id":6,"name":"7","phone":"67","sex":"0"}, {"city":"city_8","id":7,"name":"8","phone":"78","sex":"1"}, {"city":"city_9","id":8,"name":"9","phone":"89","sex":"0"}, {"city":"city_9","id":9,"name":"9","phone":"99","sex":"1"}, {"city":"city_11","id":10,"name":"11","phone":"1011","sex":"0"}]]]></data></stat> </stats>

数据包括配置的xml和返回的数据。

4,客户端flex4代码

跟新xml返回的数据,动态生成AdvancedDataGridColumn,并添加到 AdvancedDataGrid里面。

<?xml version="1.0" encoding="utf-8"?> <mx:Module xmlns:fx="http://ns.adobe.com/mxml/2009" xmlns:s="library://ns.adobe.com/flex/spark" xmlns:mx="library://ns.adobe.com/flex/mx" width="100%" height="100%" initialize="initApp();"> <fx:Style source="./assets/main.css" /> <fx:Declarations> <mx:HTTPService id="moduleService" method="GET" resultFormat="e4x" result="resultHandler();"/> </fx:Declarations> <fx:Style> @namespace s "library://ns.adobe.com/flex/spark"; @namespace mx "library://ns.adobe.com/flex/mx"; mx|Text.headLabelStyle{fontSize:20;fontWeight:bold;} </fx:Style> <fx:Script> <![CDATA[ import mx.collections.*; import mx.controls.*; import mx.controls.advancedDataGridClasses.*; import mx.utils.*; import spark.components.*; private function initApp():void{ try { /* 删除问号前面的所有内容,包括问号。 */ var myPattern:RegExp = /.*\?/; var url:String = this.loaderInfo.url.toString(); //Alert.show(this.loaderInfo.height+","+this.loaderInfo.width); dataGridGroup.width = this.loaderInfo.width; //dataGridGroup.height = this.loaderInfo.height; url = url.replace(myPattern, ""); /* 创建一个形如name=value字符串数组 */ var params:Array = url.split("&"); /* 输出数组中的参数,找到moduleId,这个参数,其他参数类似。 */ var moduleId:String = ""; for (var key:String in params) { var value:String = String(params[key]); if(value.indexOf("moduleId=") >= 0){ moduleId = value.replace("moduleId=",""); break; } } //Alert.show(moduleId); //设置请求地址获取模块参数配置。 moduleService.url = "/stat/module/data.do?moduleId="+moduleId; moduleService.send(); } catch (e:Error) { trace(e); } /* 显示loaderInfo的一些有用的信息 */ trace("AS version: " + this.loaderInfo.actionScriptVersion); //trace("App height: " + this.loaderIno.height); //trace("App width: " + this.loaderInffo.width); trace("App bytes: " + this.loaderInfo.bytesTotal); } private function genWhere(dataXml:XML):HGroup{ var hgroup:HGroup = new HGroup(); //保证居中和左对齐。 hgroup.verticalAlign="middle" hgroup.horizontalAlign = "left"; //Alert.show(dataXml.where.column); for each(var objWhere:Object in dataXml.where.column){ var field:String = objWhere.@field; var text:String = objWhere.@text; var inputLabel:spark.components.Label = new spark.components.Label(); inputLabel.text = text; hgroup.addElement(inputLabel); var input:spark.components.TextInput = new spark.components.TextInput(); input.id = field; hgroup.addElement(input); var sp:Spacer = new Spacer(); sp.width = 10; hgroup.addElement(sp); } //如果存在where数据则增加查询按钮。 if(dataXml.where.column.length() > 0){ var search:spark.components.Button = new spark.components.Button(); search.label = "查询"; hgroup.addElement(search); } return hgroup; } //动态生成 AdvancedDataGrid 数据表单. private function genAdvancedDataGrid(dataXml:XML):AdvancedDataGrid{ //Alert.show(menuList.source.columns.column); //Alert.show(menuList.source.data); //格式化json数据。将数据转换成数组。放到DataGrid里面。 var tmpArray:Array = (JSON.parse(dataXml.data) as Array); //Alert.show(array.length()); var dataArray:ArrayCollection = new ArrayCollection(tmpArray); //#######################设置列表显示顶部标题. var columnArray:Array = new Array(); for each(var objColumn:Object in dataXml.list.column){ var dataField:String = objColumn.@field; var headerText:String = objColumn.@text; var width:String = objColumn.@width; //设置DataGridColun标题,和显示属性。 var adColumn:AdvancedDataGridColumn = new AdvancedDataGridColumn(dataField); adColumn.headerText = headerText; if(width){ adColumn.width = Number(width); } columnArray.push(adColumn); } //adg1.columns(); //adg1.columnCount(); //adg1.columns(columnArray); var adg:AdvancedDataGrid = new AdvancedDataGrid(); adg.id = "adg-"+id; adg.dataProvider = dataArray; adg.columns = columnArray; adg.rowCount = tmpArray.length + 1; return adg; } //请求数据成功之后处理动态生成表格。 private function resultHandler():void{ for each(var obj:Object in moduleService.lastResult.stat){ var dataXml:XML = obj as XML; //获得模板id,标题. var id:String = dataXml.@id; var title:String = dataXml.@title; //设置 var vgroup:VGroup = new VGroup(); //设置内边距15。 vgroup.paddingTop = 15; vgroup.paddingLeft = 15; vgroup.paddingRight = 15; vgroup.paddingBottom = 15; //设置标题。 var titleText:Text = new Text(); titleText.text = title; titleText.styleName = "headLabelStyle"; vgroup.addElement(titleText); var hgroup:HGroup = genWhere(dataXml); vgroup.addElement(hgroup); //生成高级表格。 var adg:AdvancedDataGrid = genAdvancedDataGrid(dataXml); vgroup.addElement(adg); dataGridGroup.addElement(vgroup); } } ]]> </fx:Script> <!-- 设置如果超过高度滚动. --> <s:VGroup id="dataGridGroup" height="100%"/> </mx:Module>


5,后续&代码

这只是最简单的应用,功能还需要完善。

代码已经放到github上面了。  https://github.com/freewebsys/flex4-stat

工程需要使用flahs builder 打开。


原文链接:https://yq.aliyun.com/articles/138533
关注公众号

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。

持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。

转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。

文章评论

共有0条评论来说两句吧...

文章二维码

扫描即可查看该文章

点击排行

推荐阅读

最新文章