概述
为了提高开发效率,减少重复的页面多次开发,提高系统的可配置性和代码的可复用性,也是为了展示struts、hibernate框架,设计原则是降低显示逻辑和数据的耦合,达到显示逻辑和数据完全分离,即相同的数据使用不同的显示逻辑,无须修改显示逻辑,只需置换不同的显示模版即可。
实现机制

其中Sturts  Action是具体的需要调用列表的Action类,TempDataMap类是具体的列表数据的封装类,TempData类是具体的表记录类,即TempDataMap来适配TempData,把表记录适配成我们需要的列表显示类。
调用示例:
Action:
 
//获取数据库数据
listRowCount  = query.findPayItemByParam(paramInfo,paramForm.getPageSize(),paramForm.getPageNo());
                     list = listRowCount.getList();
//调用列表组件
if(list != null && list.size() > 0)
ColDataMgr    mgr = new ColDataMgr(getDataMaps(list));
//获取列表的表列信息,数据信息
ArrayList colMetaInfos = mgr.getColMetaInfos();
ArrayList datas = mgr.getData();
// 将列表信息传到List页面
                     request.setAttribute(CoreConstant.WEB_DISPLAY_COL_METAT_INFOS_KEY, colMetaInfos);
                     request.setAttribute(CoreConstant.WEB_DISPLAY_DATAS_KEY, datas);
 
同样道理,给出的数据可以分发给打印组件和导出excel列表组件,根据列表的列信息和数据信息,导出excel和打印。
 
具体的map类的内容可参照附件ReceiveItemAmountQueryMap.java文件。
获取显示列信息:
/**
  *返回的list中每个元素是列元信息类对象,列元信息类对象包括列名称,列显示名称,
  *列显示格式,其中列名称是key
  * 导出excel和打印是同样的道理
  */
public ArrayList getColMetaInfos()
       {
 
              ArrayList list = new ArrayList();
              list.add(new ColMetaInfo("transCode", " 单据编号 ", true, "height="20" align="center" nowrap"));
              list.add(new ColMetaInfo("transDate", " 单据日期 ", false, "height="20" align="center" nowrap"));
              list.add(new ColMetaInfo("transTypeName", " 业务类型 ", false, "height="20" align="left" nowrap"));
              list.add(new ColMetaInfo("receiveOrgName", " 收款单位 ", false, "height="20" align="left" nowrap"));
              list.add(new ColMetaInfo("receiveAccountNo", " 收款账户号 ", false, "height="20" align="center" nowrap"));
              list.add(new ColMetaInfo("receiveBankName", " 收款银行 ", false, "height="20" align="left" nowrap"));
              list.add(new ColMetaInfo("extAccountNo", " 付款账户 ", false, "height="20" align="center" nowrap"));
              list.add(new ColMetaInfo("extBankName", " 付款银行 ", false, "height="20" align="left" nowrap"));
              list.add(new ColMetaInfo("amount", " 金    额 ", false, "height="20" align="right" nowrap"));
              list.add(new ColMetaInfo("memo", " 摘    要 ", false, "height="20" align="left" nowrap"));
              
              return list;
       }
//适配数据,根据数据的类型如日期型,装换成需要的字符串形式,金额类数据也转换成相//应的字符串格式,保存到HashMap中。
public HashMap getColData()
       {
 
               StringBuffer sb = new StringBuffer("receiveItemAmountQueryAction.do?operation=");
               sb.append(CoreConstant.WEB_OPERATION_TYPE_TO_UPDATE_KEY);
               sb.append("&id=");
               sb.append(String.valueOf(form.getTransApplyItem().getTransApplyID().longValue()));
               String link = sb.toString();
 
              HashMap hm = new HashMap();
              hm.put("transCode"," "+IDataFormat.formatString(form.getTransCode()));
              hm.put("transDate", " "+IDateFormat.toDateString(form.getTransDate()));
              hm.put("transTypeName", " "+IDataFormat.formatString(form.getTransTypeName()));
              hm.put("receiveOrgName", " "+IDataFormat.formatString(form.getReceiveOrgName()));
              hm.put("receiveAccountNo", " "+IDataFormat.formatString(form.getReceiveAccountNo()));
              hm.put("receiveBankName", " "+IDataFormat.formatString(form.getReceiveBankName()));
              hm.put("extAccountNo", " "+IDataFormat.formatString(form.getTransApplyItem().getExtAccountNo()));
              hm.put("extBankName", " "+IDataFormat.formatString(form.getTransApplyItem().getExtBankName()));
              
              if (form.getTransApplyItem().getAmount() != null)
              {
                     String sAmount = " "+IDataFormat.formatDisabledAmount(form.getTransApplyItem().getAmount().doubleValue() );
                     hm.put("amount", sAmount);
              }
              else
              {
                     hm.put("amount", "0.00");
              }
              
              hm.put("memo", " "+IDataFormat.formatString(form.getTransApplyItem().getMemo()));
               hm.put("SUPERLINK", link);
 
              return hm;
       }
附录:
 
DataMap接口:
/**
 * @author lijj
 *
 * To change the template for this generated type comment go to
 * Window - Preferences - Java - Code Generation - Code and Comments
 */
public interface DataMap {
       public ArrayList getColMetaInfos();
       public ArrayList getExeclColMetaInfos();
       public ArrayList getPrintColMetaInfos();
       public ArrayList getColSearchs();
       public HashMap getQueryData();
       public String getSearchUrl();
       public HashMap getColData();
}
 
抽象实现类DefaultDataMap
import java.util.ArrayList;
import java.util.HashMap;
 
 
 
/**
 * @author lijj
 *
 * To change the template for this generated type comment go to
 * Window - Preferences - Java - Code Generation - Code and Comments
 */
public abstract class DefaultDataMap implements DataMap{
       public abstract ArrayList getColMetaInfos();       
       public abstract HashMap getColData();
       public ArrayList getExeclColMetaInfos()
       {
              return new ArrayList();
       }
       public ArrayList getPrintColMetaInfos()
       {
              return new ArrayList();
       }
       public String getSearchUrl()
       {
              return null;
       }
       public HashMap getQueryData()
       {
              return null;
       }
       public ArrayList getColSearchs()
       {
              ArrayList retList = new ArrayList();
              return retList;
       }
       
}
ColDataMgr管理类:
import java.util.ArrayList;
import java.util.HashMap;
 
/**
 * @author lijj
 * 
 * To change the template for this generated type comment go to Window - Preferences - Java - Code Generation - Code and
 * Comments
 */
public class ColDataMgr
{
 
       ArrayList list   = null;
 
       DataMap        map        = null;
 
       public ColDataMgr(ArrayList list)
       {
 
              this.list = list;
       }
 
       public ColDataMgr(DataMap map)
       {
 
              this.map = map;
       }
 
       public ArrayList getColMetaInfos()
       {
 
              if (list != null)
              {
                     return ((DataMap) list.get(0)).getColMetaInfos();
              }
              else
              {
                     return this.map.getColMetaInfos();
              }
       }
 
       public ArrayList getExeclColMetaInfos()
       {
 
              if (list != null)
              {
                     return ((DataMap) list.get(0)).getExeclColMetaInfos();
              }
              else
              {
                     return this.map.getExeclColMetaInfos();
              }
       }
 
       public ArrayList getPrintColMetaInfos()
       {
 
              if (list != null)
              {
                     return ((DataMap) list.get(0)).getPrintColMetaInfos();
              }
              else
              {
                     return this.map.getPrintColMetaInfos();
              }
       }
 
       public ArrayList getData()
       {
 
              ArrayList retList = new ArrayList();
              DataMap dataMap = null;
              if (list != null)
              {
                     for (int i = 0; i < list.size(); i++)
                     {
                            dataMap = (DataMap) list.get(i);
                            retList.add(dataMap.getColData());
                     }
              }
              return retList;
       }
 
       public ArrayList getSearchInfos()
       {
 
              return getDataMap().getColSearchs();
       }
 
       public String getSearchUrl()
       {
 
              return getDataMap().getSearchUrl();
       }
 
       public HashMap getQueryData()
       {
 
              return getDataMap().getQueryData();
       }
 
       private DataMap getDataMap()
       {
 
              if (this.map != null)
              {
                     return map;
              }
              else
              {
                     return ((DataMap) list.get(0));
              }
       }
}
列元信息类 ColMetaInfo
/**
 * @author lijj
 * 
 * To change the template for this generated type comment go to Window - Preferences - Java - Code Generation - Code and
 * Comments
 */
public class ColMetaInfo
{
 
       private String  name;
 
       private String  displayName;
 
       private boolean       isLink;
 
       private String property;
       
       
       public ColMetaInfo(String name, String displayName, boolean isLink, String property)
       {
 
              this.name = name;
              this.displayName = displayName;
              this.isLink = isLink;
              this.property = property;
       }
       
       public String getDisplayName()
       {
       
              return displayName;
       }
 
       
       public void setDisplayName(String displayName)
       {
       
              this.displayName = displayName;
       }
 
       
       public boolean isLink()
       {
       
              return isLink;
       }
 
       
       public void setLink(boolean isLink)
       {
       
              this.isLink = isLink;
       }
 
       
       public String getName()
       {
       
              return name;
       }
 
       
       public void setName(String name)
       {
       
              this.name = name;
       }
 
       
       public String getProperty()
       {
       
              return property;
       }
 
       
       public void setProperty(String property)
       {
       
              this.property = property;
       }
 
       
}
模版文件list.jsp
<%@ page contentType="text/html;charset=gb2312"%>
<%@ page import="java.util.ArrayList"%>
<%@ page import="java.util.HashMap"%>
<%@ page import="com.e_chinalife.ecms.frame.component.colmap.ColMetaInfo"%>
<%
       ArrayList colMetaInfos = (ArrayList) request.getAttribute("colMetaInfos");
       ArrayList datas = (ArrayList) request.getAttribute("datas");
       int colLen = colMetaInfos.size();
       int resultCount = datas.size();
%>
<table border="0" width="99%" cellspacing="1" cellpadding="0" align="center" class=ItemList>
       <TBODY>
              <TR align=center>
              <%
                     ColMetaInfo colMeta = null;
                     for (int i = 0; i < colLen; i++)
                     {
                            colMeta = (ColMetaInfo) colMetaInfos.get(i);
 
              %>
                     <TD class=ItemTitle height=20 nowrap>
                            <%=colMeta.getDisplayName()%>
                     </TD>
              <%
                     }
              %>
              </TR>
              <%
                     HashMap hm = null;
                     for (int i = 0; i < resultCount; i++)
                     {
              %>
              <TR align=center borderColor=#999999 class=ItemBody>
              <%
                            hm = (HashMap) datas.get(i);
                            for (int j = 0; j < colLen; j++)
                            {
                                   colMeta = (ColMetaInfo) colMetaInfos.get(j);
              %>
                     <TD <%=colMeta.getProperty()%> >
              <%
                                   if (colMeta.isLink() && hm.get(colMeta.getName()) != null
                                          && !((String) hm.get(colMeta.getName())).equals(""))
                                   {
 
              %>
                     <a href="<%=hm.get("SUPERLINK")%>"> <%=hm.get(colMeta.getName())%></a>
              <%
                                   } 
                                   else 
                                   {
 
              %>
                                          <%=hm.get(colMeta.getName())%>
              <%                }
 
              %>
                     </TD>
              <%
                            }
              %>
              </TR>
              <%
                     }
              %>
 
              <%
              //没有记录显示空白行
              if (resultCount == 0)
              {
              %>
              <TR align=center borderColor=#999999 class=ItemBody>
              <%
                     for (int i = 0; i < colLen; i++)
                     {
                            colMeta = (ColMetaInfo) colMetaInfos.get(i);
              %>
                     <TD height=20 nowrap class=ItemBody>&nbsp;</TD>
              <%
                     }
              }
              %>
              </TR>
       </TBODY>
</table>
 
Jsp使用列表模版的片断
<table width="80%" border="0" cellpadding="0" cellspacing="0">
<tr>
       <td>
       <table border="0" width="98%" bgcolor="#0099CC" cellspacing="1" cellpadding="0" align="center">
       <tr>
           <td width="100%" bgcolor="#EFEFEF">
                 <table border="0" width="100%" cellspacing="1" height="20">
                      <tr><td width="100%" colspan="3" height="19" class="FormTitle"><b>开户申请</b></td></tr>
               </table>
                              <hr>
                 <jsp:include page="../common/template/List.jsp" flush="true"/>
                 <jsp:include page="../common/template/PageNavigator.jsp" flush="true"/>
                  </td>
             </tr>
             <tr>
                     <td colspan="6" bgcolor="#EFEFEF">
                            <table border="0" width="100%" cellspacing="1" height="20">
                                   <tr>
                                      <td width="82%" height="30" align="right">
                                             <input type="button" value=" 新 增 " name="bt" class=button onClick="JavaScript:to_Add();">&nbsp;&nbsp;
                                       </td>
                                   </tr>
                         </table>   
                     </td>
              </tr>
       </table>
       </td>
</tr>
 
</table>
</form> 
</body>
 
结束语
Web组件的设计和使用,可能还有不尽人意的地方,我们在以后的开发中,有什么意见和要求,可以重构这些组件,以适应新的需求。Web组件的设计原则是数据和显示脱耦分离,显示逻辑由显示的模版控制,与具体的数据没有任何关系,不管数据的来源是数据库,还是文本文件,只要能适配成相关的接口,就能展现在不同风格的页面(即使用不同风格的模版)。
 
 
努力,在于我热爱我的事业,与中国的软件一起走向成熟,走向世界。