如何用easyui+JAVA 实现动态拼凑datagrid表格

先给大家看一看效果,最近一段时间都在研究这个东西。

如果我把日期间隔选宽呢?比如5月日到5月5日?下面给大家看看效果,不用担心哦

看到了吧,哈哈,这个日期都是动态生成的,下面就来跟大家分享一下这个的实现方法。

本人是用JAVA EE的后台实现的,

先来贴HTML代码:

 1 <div>站点:<input class="easyui-combobox" width="200px" id="stnmCombo">&nbsp;
 2 起始时间:<input id="StartTime" class="easyui-datebox"  editable="false" />
 3 &nbsp; 结束时间:<input id="EndTime" class="easyui-datebox" editable="false" />
 4 <a id="btnSearch" href="#" class="easyui-linkbutton" data-options="iconCls:‘icon-search‘">查询</a> &nbsp;
 5 <a id="export" href="#" class="easyui-linkbutton" data-options="iconCls:‘icon-search‘">导出</a>
 6 </div>
 7
 8 <div class="easyui-layout" fit="true">
 9     <table id="dg"></table>
10 </div>

HTML代码非常的简单,其中关键的datagrid只有一个TABLE,其实关键在于JS代码哦

下面就把代码发出来:

我来给大家解释下几个关键的地方以及思路吧,代码不是特别的复杂。

  1. formLoader.load(param1,param2,function(s){})这个方法第一个参数就是controller的RequestMapping的名字,因为是用的MVC三层构架弄的,第二个参数可以是字符串的,也可以是一个JSON对象,此方法返回的是一个JSON对象,如果alert(s)就会看到结果,这个公司框架的一个方法,所以大家不用再找,我只是分享思路。
  2. 本例子主要是后台构造动态列,使用得比较多的是PUSH方法,用PUSH方法把JSON对象存到数组里面去。

其中有几点需要解释一下:表头名称title,field(JSON对象返回到的对应的Key),field给大家放张图片就知道了

下面是具体的代码:

var gv=$("#dg");
var today=new Date();

//动态生成列
var dynamicCols=[];
var dynamicItems=[];
var dynamicItemsAfter=[];
var dynamicItemsEnd=[];

$(function(){
    $("#StartTime").datebox(‘setValue‘,today.getFullYear()+"-"+(today.getMonth()+1)+"-"+(today.getDate()-1));
    $("#EndTime").datebox(‘setValue‘,today.getFullYear()+"-"+(today.getMonth()+1)+"-"+(today.getDate()));

    //绑定空数据
    gv.datagrid( "dataBind" ,
            {
                autoHeight : 46 ,
                datas      : [],
                striped:true,
                pagination : true,
                autoRowHeight:false

            });
    //绑定空列
    gv.datagrid({
        columns:[[
                  {title:‘时间‘,width:150,sortable:true},
                  {title:‘站点1‘,width:150,sortable:true},
                  {title:‘站点2‘,width:150,sortable:true},
                  {title:‘站点3‘,width:500,sortable:true},
                  ]]

    });

});

//列元素(动态)
//序号
var stcd={
           field: ‘Stcd‘,
           title: ‘序号‘,
          // width: 150,
           rowspan:3,
           sortable:true
}

//站名
var stnm={
       field: ‘Stnm‘,
       title: ‘站名‘,
      // width: 150,
       rowspan:3,
       sortable:true
}

//平均值
var avg={
        title:‘平均值‘,
        //width:500,
        colspan:2
}

//库水位
var rz={
    title:‘库水位‘,
    //width:150 /*PS:动态列中不适宜固定宽度,其他同样的*/
}

//库容
var rv={
        title:‘库容‘,
        width:150
}

//库容(平均)
var rvAvg={
        title:‘库容‘,
        field:"rvAvg2",
        //width:500
        formatter:function(value,row,index)
        {
            return "-";
        }
}

//查询按钮
$("#btnSearch").click(function(){

    //得到开始日期和结束日期之间的天数之差
    var ipt1=$("#StartTime").datebox(‘getValue‘);
    var ipt2=$("#EndTime").datebox(‘getValue‘);

    var arr1 = ipt1.split("-");
    var arr2 = ipt2.split("-"); 

    var dt1 = new Date();
    dt1.setFullYear(arr1[0]);
    dt1.setMonth(arr1[1] - 1);
    dt1.setDate(arr1[2]);
    var dt2 = new Date();
    dt2.setFullYear(arr2[0]);
    dt2.setMonth(arr2[1] - 1);
    dt2.setDate(arr2[2]);
    var dif = dt2.getTime() - dt1.getTime();
    var days = dif / (24 * 60 * 60 * 1000); 

    //再次初始化,避免数组的堆积
     dynamicCols=[];
     dynamicItems=[];
     dynamicItemsAfter=[];
     dynamicItemsEnd=[];

    //前部
    dynamicItems.push(stcd);
    dynamicItems.push(stnm);

    //查询条件数据
    var datas={
            "Stcd":$("#stnmCombo").combobox(‘getValue‘),
            "StartTime":$("#StartTime").datebox(‘getValue‘),
            "EndTime":$("#EndTime").datebox(‘getValue‘)

    }

    //查询具体的数据
    formLoader.load("querydata",datas,function(s){

        //空白SPAN
        var blank={
                title:‘ ‘,
                colspan:days*2+4 //动态得到COLSPAN的跨度,根据天数

        }

        dynamicItems.push(blank);
        //var sss = s;
        //遍历动态数组
//        for(j=0;j<s.length;j++)
//        {
        //alert(s.DaynamicList[1].z0);

            //alert(s[7].DynamicList.z0);

        //动态载入库水位数据
        //库水位
           rz={
            title:‘库水位‘,
            field:"DynamicList",
            formatter:function(value,row,index){
                //alert(row);
                //return value.z1; //因为这是一个对象DynamicList,所以返回对象的值
                //alert(value);
                var temp;
                $.each(value,function(i,option){
                        //alert(option);
                        temp=option;
                    });

                return  temp;
            }

        }

        //alert(s);
           //拼凑表头
            $.each(s[0].DynamicList, function(i,option){

                //alert(i);

                   //alert(i);
                    rv={
                            title:‘库容‘,
                            field:"DynamicList2",
                            formatter:function(value,row,index)
                            {
                                return "-";
                            }

                    }

                 //详细数据
                   var k=0; //设定一个值,匹配Z0,Z1,Z2。。。。。

                   var d = new Date($("#StartTime").datebox(‘getValue‘));
                   do{
                       //alert(i.substring(1));
                       d.setDate(d.getDate()+parseInt(i.substring(1))); //转换成INT类型的

                       var RealDate=d.getFullYear()+"-"+(d.getMonth()+1)+"-"+d.getDate(); //动态得到日期值

                       var details2={
                           title:RealDate,
                       //    width:150,
                           colspan:2

                       }

                       dynamicItemsAfter.push(details2);
                      k+=2;
                      break; //这里因为会执行i此结果 ,所以 BREAK掉
                   }while(days>k)

                   //dynamicItemsAfter.push(details2);

//                   dynamicItemsEnd.push(rz);
//                   dynamicItemsEnd.push(rv);
                   dynamicItemsEnd.push(rz);
                   dynamicItemsEnd.push(rv);

                   //dynamicItemsAfter.push(details2);

            });

//        }

         //库水位(平均)
       var rzAvg={
               title:‘库水位‘,
               field:"DynamicList5", //这里随便设一个Field
               formatter:function(value,row,index)
               {

                   var k=row.DynamicList;
                   //alert(k);
                   //算出平均值
                   var temp=0;
                   $.each(k,function(i,option){
                       //alert(option);
                       //alert(i);
                       temp+=Number(option);
                       //alert(temp);
                   });
                   //alert(temp);
                   //return 0;
                   //alert(temp);

                   return temp/(days+1);
               }

               //width:150

       }

        //alert(s[0].Stcd);
            dynamicItemsAfter.push(avg);
            dynamicItemsEnd.push(rzAvg);
            dynamicItemsEnd.push(rvAvg);

        dynamicCols.push(dynamicItems);
        dynamicCols.push(dynamicItemsAfter);
        dynamicCols.push(dynamicItemsEnd);
        //绑定动态列
        gv.datagrid({
            columns:dynamicCols,

        });

        gv.datagrid( "dataBind" ,
                {
                    datas      : s,
                    striped:true,
                    pagination : true,
                    pageSize:15

                });

        //total();

    });

});

//得到测站编码
var dataCount=0;
formLoader.load("getstnm","",function(data){

    data.unshift({Stnm : "全部" , Stcd : "" });
    $("#stnmCombo").combobox({
        data:data,
        valueField:"Stcd",
        textField:"Stnm",
        editable:false,
        //panelHeight:"auto",

        onLoadSuccess:function()
        {
            //alert(‘1‘);
            //alert(data[0].Stcd);
            $("#stnmCombo").combobox(‘setValue‘,data[0].Stcd);
            dataCount=data.length;

        },
        onShowPanel:function()
        {
            if(dataCount.length>10)
            {
                $(this).combobox(‘panel‘).height(251);

            }    

        }
    });
});

本例的难点在于,要构建一个动态的DTO实体类,因为我返回的是一个LIST<DTO的名称>,因为列是不固定的,所以这个是一个难点,这个怎么实现呢?

其实大家细心的注意到了有一个Field叫做DynamicList我们把这个DYNAMICLIST打开看看里面的内部结构。

这里其实是因为我选择了8个日期间隔的时间,所以就有8个元素在里面,如果我选择了4天时间间隔呢?

这个是怎么实现的呢?

下面进入后台时间,其实后台是拼接的SQL,先给大家看看查询SQL是怎么拼凑出来的。

public String querySql(ReservoirDayReportParam param)
    {
        StringBuffer sb=new StringBuffer();
        sb.append("select b.STNM,r.STCD,");

        //开始时间和结束时间
        String startTime=param.getStartTime();
        String endTime=param.getEndTime();

        SimpleDateFormat format =new SimpleDateFormat("yyyy-mm-dd");
        Calendar start=Calendar.getInstance();
        Calendar end=Calendar.getInstance();
        try
        {
            start.setTime(format.parse(startTime));
            end.setTime(format.parse(endTime));

        }
        catch(Exception e)
        {
            e.printStackTrace();
        }

        //遍历出时间
        int count=0;
        while(start.compareTo((end))<=0)
        {

            String time=format.format(start.getTime());
            String finalStart=time.concat(" 00:00:00");    //最终获得的每天的开始时间
            String finalEnd=time.concat(" 23:59:59"); //最终获得的每天的结束时间

            sb.append("max(case when r.TM between ‘"+finalStart+"‘ and ‘"+finalEnd+"‘ then  r.RZ else 0 end) as z"+count+",");
            count++;
            start.add(Calendar.DAY_OF_MONTH, 1);
            //列的别名
        }
        String tempBuffer=sb.substring(0,sb.length()-1); //把获得的值的最后一个逗号去掉
        StringBuffer lastBuff=new StringBuffer(); //新建一个字符串
        lastBuff.append(tempBuffer);

        lastBuff.append(" from ST_RSVR_R r,ST_STBPRP_B b where r.stcd=b.stcd");
        if(!param.getStcd().equals(""))
        {
            lastBuff.append(" and r.STCD=‘"+param.getStcd()+"‘");
        }

        lastBuff.append(" group by b.STNM,r.STCD");
        return lastBuff.toString();
    }
    
  其中的ReservoirDayReportParam 是一个实体类,代码都有注释的,我就说说关键的,其实的动态列(水位)这一列,其实是根据传入的开始时间和结束时间,来循环去把SQL拼凑出来,代码不是太难,中间使用到了一个count的变量,用来给列起别名,比如z0,z1,z2,z3...等等。

  那么这样就实现了动态的拼接SQL,就是我有选择了多少个日期间隔,就会在后台AS出多少个动态列,下面先给大家看看实体模型吧。
    //开始时间和结束时间
    private String startTime;
    private String endTime;

    public  Map getDynamicList() {
        return dynamicList;
    }
    public void setDynamicList(Map  dynamicList) {
        this.dynamicList = dynamicList;
    }
    //动态实体类
    private Map dynamicList;

  其中的dynamicList就是动态的,为什么是Map类型的?那是因为可以添加键值对。把形如z0,z1这样的添加到里面去,这就实现了动态化。

开始已经说过了formLoader方法,那么我们要执行的这个方法,在后台优势什么样呢?

public List<ReservoirDayReportParam> queryData(ReservoirDayReportParam param) {
        // TODO Auto-generated method stub

        String sql=querySql(param);
        List<Object[]> dataFromSTCD=this.daoHelper.findBySql(sql);
        List<ReservoirDayReportParam> arrList=new ArrayList<ReservoirDayReportParam>();
        List list = new ArrayList();
        try
        {

        for(Object[] obj:dataFromSTCD)
        {
            ReservoirDayReportParam params=new ReservoirDayReportParam();
            Map map=new LinkedHashMap(); //新建一个ARRLIST,用于存放动态列

            params.setStnm(String.valueOf(obj[0]));
            params.setStcd(String.valueOf(obj[1]));

            //把动态列存到Map中去,然后分别设定键值对

            for(int i=2;i<dataFromSTCD.get(0).length;i++)
            {
                map.put("z"+(i-2), obj[i]);
            }

            params.setDynamicList(map);

            arrList.add(params);
        }

        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
        return arrList;

    }

其中的querySql就是刚才的拼接SQL的方法。首先得到拼接的SQL,那个findbysql方法是返回一个List集合的方法,公司框架,知道意思就行,大家可以无视。具体思路就是从List中循环出结果,然后添加到实体类中去,然后再把每个实体类添加到arraylist中去,然后再返回。
时间: 2024-08-29 15:04:31

如何用easyui+JAVA 实现动态拼凑datagrid表格的相关文章

如何用easyui+JAVA 实现动态拼凑datagrid表格(续)

前面一段时间写了一篇文章: 如何用easyui+JAVA 实现动态拼凑datagrid表格 这篇文章的话,效果是可以实现,但是经过我反复试验,还是存在一些问题的. 今天这篇文章就是向大家介绍下如何避免和解决这些问题. 问题如下: 这个TEMP值其实就是上面文章提到的z1,z2,z3,z4的值,也就是说,每次进行each循环,都会查出不同的值,并返回,但是事实并不是这样的 这个TEMP返回的是EACH循环以后的最后一次的值. 记住,EACH循环本身就是一个封闭的,不会循环一次返回一个值,而是让前面

PHP+Mysql+easyui点击左侧tree菜单对应表名右侧动态生成datagrid加载表单数据(二)

关于tree菜单生成,参考我的另一篇博文地址tree 菜单 实现功能:点击左侧tree菜单中的table,右侧通过datagrid加载出该表对用的所有数据 难点:获取该表的所有列名,动态生成datagrid,并加载数据 解决办法: 使用tree菜单的onClick事件: $('#tree').tree( { url:'tree_getData.php', onClick:function(node){ //判断点击的节点是否是子节点是子节点就创建datagrid,否则就return打开这个节点

Easy-UI 动态添加DataGrid的Toolbar按钮

在前人的基础上进行的修改,不知道他是从哪里引用来的,所以没有粘贴引用地址. 原代码不支持1.3.6. 修改功能: 1.如果之前没有添加过工具,用这个方法不能添加(已修复): 2.估计是不支持1.3.6,所以在1.3.6下不能删除按钮(已修复): 3.添加了在删除最有一个按钮后把按钮容器删除掉: 插件代码: $.extend($.fn.datagrid.methods, { addToolbarItem: function (jq, items) { return jq.each(function

如何用easyui动态加载表格标题

在最近做的项目中涉及到了需要加载大量表格的功能,采用了easyui的datagrid,但是发现datdagrid表格标题需要手动写,这在表格多的情况是一件很麻烦的事情.经过了long long time 终于研究出来了动态加载表格标题的方法. 首先给下效果图. 刚开始本人用easyui最原始的方式将表格放入我需要它放置的位置.整体页面因为某些原因呢就不展示给大家看了. 首先大家可以去网上下载easyui的包以及easyui的中文文档.easyui包友情链接:http://www.jeasyui.

java的动态代理机制详解

在学习Spring的时候,我们知道Spring主要有两大思想,一个是IoC,另一个就是AOP,对于IoC,依赖注入就不用多说了,而对于 Spring的核心AOP来说,我们不但要知道怎么通过AOP来满足的我们的功能,我们更需要学习的是其底层是怎么样的一个原理,而AOP的原理就是 java的动态代理机制,所以本篇随笔就是对java的动态机制进行一个回顾. 在java的动态代理机制中,有两个重要的类或接口,一个是 InvocationHandler(Interface).另一个则是 Proxy(Cla

Java中动态加载jar文件和class文件

概述 诸如tomcat这样的服务器,在启动的时候会加载应用程序中lib目录下的jar文件以及classes目录下的class文件,另外像spring这类框架,也可以根据指定的路径扫描并加载指定的类文件,这个技术可以实现一个容器,容纳各类不同的子应用. Java类由于需要加载和编译字节码,动态加载class文件较为麻烦,不像C加载动态链接库只要一个文件名就可以搞定,但JDK仍提供了一整套方法来动态加载jar文件和class文件. 动态加载jar文件 // 系统类库路径 File libPath =

Easy-ui Datagrid表格数据的编辑与提交

前言 jQuery EasyUI是一组基于jQuery的UI 插件集合体,而jQuery EasyUI可以打造出功能更加丰富且美观的UI界面.开发者不需要了解复杂的javascript和css样式,只需要了解html标签. 一.    easy-ui基本知识 1.            easy-ui引用js顺序详解 引用Jquery的js文件: <script src="jquery-easyui-1.3.4/jquery-1.8.0.min.js" type="te

java内存动态编译执行

1.package org.jui.core.dynamic; public class DynaCompTest { public static void main(String[] args) throws Exception { String fullName = "DynaClass"; StringBuilder src = new StringBuilder(); src.append("public class DynaClass {\n"); src

OSGI(面向Java的动态模型系统)

基本简介编辑 OSGI服务平台提供在多种网络设备上无需重启的动态改变构造的功能.为了最小化耦合度和促使这些耦合度可管理,OSGi技术提供一种面向服务的架构,它能使这些组件动态地发现对方.OSGi联 OSGI 盟已经开发了为例如象HTTP服务器.配置.日志.安全.用户管理.XML等很多公共功能标准组件接口.这些组件的兼容性插件实现可以从进行了不同优化和使用代价的不同计算机服务提供商得到.然而,服务接口能够基于专有权基础上开发. 因为OSGi技术为集成提供了预建立和预测试的组件子系统,所以OSGi技