需求:想要一个分类归纳的表单,横纵项不固定,每一个行列组合的单元格中不是数字,而是具体的项目清单.
效果类似下面这种
活动 | 第一列 | 第二列 | 第三列 | 第四列 |
---|---|---|---|---|
第一行 | 项目一 | 项目 | 项目 | 项目 |
第二行 | 项目 | 项目 | 项目 | 项目 |
第三行 | 项目 | 项目 | 项目 | 项目 |
第四行 | 项目 | 项目 | 项目 | 项目 |
由于之前做的统计几乎都是统计数量,所以这玩意儿是第一次接触.上网找了一段时间,没有找到现成的例子,只能硬着头皮做了.当然,我的做法是根据我的项目来的,只供参考.
这个分类归纳的项目,是按照状态来过滤的,而项目的状态不是实时更新,而是定时更新的.所以,这个归纳表单自然也就不是实时数据,而是定时数据,在短期(一天)内是属于静态数据,所以我使用了缓存功能.
具体思路:
1.先分归类字段是多值还是单值,比如项目一对应的是只有第一行第一列,还是有第二行第二列.
我的项目的归类字段是多值的
2.如果多值,先将多值转成单值,
3.使用Map<String,List
4.在查询时,先得到表单中所有的行列组合,利用行列组合作为key,去Map中取对应数据,
5.前端展示
List<Map> listMap = getListMap(sql, conn);//获取原始数据
Map<String, String> mapZ = new HashMap<String, String>();
String html = "";
String url ="";
if (listMap != null && listMap.size() > 0) {
for (Map map : listMap) {
String keyList = (String) map.get("keyList");//分类字段值
int i = 0;
for (String key : keyList.split(",")) {
//将分类字段值的多值变成单值,然胡存入list中,我这边不想再遍历,直接将数据拼成 //html存储
html = "<a href=\"" + url+ "\" target=\"_blank\" style=\"display:block;\">" + map.get("name")
+ "</a>";
if (mapZ.keySet().contains(key)) {
mapZ.put(key, mapZ.get(key) + "<br/>" + html);
} else {
mapZ.put(key, html);
}
}
}
}
String htmlSql=
String html=getValueBySql(htmlSql);//获取已经存储过的html
if (html为空) {
//如果html为空,画表单
Connection conn = ;
//输出页面
html="<!DOCTYPE html><html><head><title>分类归纳</title>";
html+="head信息";
html+="<body>";
// 画表单
html+= "<table id=\"report_2\" style=\"width: 100%; font-size: 9pt; border-collapse: collapse;\" border=\"1\" cellspacing=\"1\" data-sort=\"sortDisabled\">"
+ "<tbody>";
String rowSql = ;// 行
String colSql = ;// 列
List<Map> colList =getListMap(colSql, conn);
List<Map> rowList =getListMap(rowSql, conn);
int width=100/(colList.size()+1);//列宽
// 首行
html += " <tr class=\"firstRow\" style=\"height:40px\"><td align=\"center\" valign=\"middle\" style=\"width:"+width+"%;background: rgb(249, 249, 249);\">活动</td>";
for (Map map : colList) {
html += " <td align=\"center\" valign=\"middle\" style=\"width:"+width+"%;background: rgb(249, 249, 249);\" >"
+ map.get("name") + "</td>";//
}
html += "</tr>";
// 其它行
String dataSql = "";
Map<String, String> mp = getList(dataSql, conn, "key");//之前的缓存数据
for (Map map : rowList) {
html += " <tr style=\"height:40px\"><td align=\"center\" valign=\"middle\" style=\"background: rgb(249, 249, 249);\">"
+ map.get("name") + "</td>";//行名称(1列)
for (Map map2 : colList) {
// fileID
String key = map.get("FILEID") + "/" + map2.get("FILEID");//行列组合成唯一key
String td = mp.get(key);//获取缓存数据中对应数据
if(td不为空) {
td = decodeWebEditor(td);//由于之前是编码后存储的,现在需要解码
}else {
td="";
}
html += " <td align=\"center\" valign=\"middle\">"
+ td + "</td>";//表单列添加
}
html += "</tr>";//一行结束
}
html += "</tbody>" + "</table>";
html+="</body></html>";
//由于我这边是短期静态数据,所以我接下来是将画好的表单直接存入缓存中,下次直接取出来,不需要再画
}else{
//有已经画好的表单
html=decodeWebEditor(html);//直接取出来使用
}
//接下来就是返回前端展示,因为我使用的工具的特殊性,是直接将画好的表单返回,而不是在前端取值赋值
// 编码
private String EncodeWebEditor(String fdValue) throws Exception {
String newfdValue = new String(Base64.encodeBase64Chunked(fdValue.getBytes()));
return newfdValue;
}
// 解码
private String decodeWebEditor(String fdValue) throws Exception {
return new String(Base64.decodeBase64(fdValue.getBytes()));
}