package com.ts.taglib.html;
import java.lang.reflect.Field;
import javax.servlet.jsp.tagext.BodyTagSupport;
/**
* 事件处理
* @author 陈双
* @date 2012-09-22
* @mail chenshuang_com@sina.com
*/
public abstract class BaseHandlerTag extends BodyTagSupport{
private static final long serialVersionUID = 715968190636480266L;
private String onclick;
private String ondblclick;
private String onmouseover;
private String onmouseout;
private String onmousedown;
private String onmouseup;
private String onmousemove;
private String onkeydown;
private String onkeyup;
private String onkeypress;
private String onfocus;
private String onblur;
private String onchange;
private String onselect;
private String styleId;
private String style;
private String styleClass;
private boolean readonly;
private boolean disabled;
public BaseHandlerTag()
{
super();
init();
}
public void init()
{
οnclick=null;
οndblclick=null;
οnmοuseοver=null;
οnmοuseοut=null;
οnmοusedοwn=null;
οnmοuseup=null;
οnmοusemοve=null;
οnkeydοwn=null;
οnkeyup=null;
οnkeypress=null;
οnfοcus=null;
οnblur=null;
οnchange=null;
οnselect=null;
readonly=false;
disabled=false;
}
public String getOnclick() {
return onclick;
}
public void setOnclick(String onclick) {
this.onclick = onclick;
}
public String getOndblclick() {
return ondblclick;
}
public void setOndblclick(String ondblclick) {
this.ondblclick = ondblclick;
}
public String getOnmouseover() {
return onmouseover;
}
public void setOnmouseover(String onmouseover) {
this.onmouseover = onmouseover;
}
public String getOnmouseout() {
return onmouseout;
}
public void setOnmouseout(String onmouseout) {
this.onmouseout = onmouseout;
}
public String getOnmousedown() {
return onmousedown;
}
public void setOnmousedown(String onmousedown) {
this.onmousedown = onmousedown;
}
public String getOnmouseup() {
return onmouseup;
}
public void setOnmouseup(String onmouseup) {
this.onmouseup = onmouseup;
}
public String getOnmousemove() {
return onmousemove;
}
public void setOnmousemove(String onmousemove) {
this.onmousemove = onmousemove;
}
public String getOnkeydown() {
return onkeydown;
}
public void setOnkeydown(String onkeydown) {
this.onkeydown = onkeydown;
}
public String getOnkeyup() {
return onkeyup;
}
public void setOnkeyup(String onkeyup) {
this.onkeyup = onkeyup;
}
public String getOnkeypress() {
return onkeypress;
}
public void setOnkeypress(String onkeypress) {
this.onkeypress = onkeypress;
}
public String getOnfocus() {
return onfocus;
}
public void setOnfocus(String onfocus) {
this.onfocus = onfocus;
}
public String getOnblur() {
return onblur;
}
public void setOnblur(String onblur) {
this.onblur = onblur;
}
public String getOnchange() {
return onchange;
}
public void setOnchange(String onchange) {
this.onchange = onchange;
}
public String getOnselect() {
return onselect;
}
public void setOnselect(String onselect) {
this.onselect = onselect;
}
public String getStyleId() {
return styleId;
}
public void setStyleId(String styleId) {
this.styleId = styleId;
}
public String getStyle() {
return style;
}
public void setStyle(String style) {
this.style = style;
}
public String getStyleClass() {
return styleClass;
}
public void setStyleClass(String styleClass) {
this.styleClass = styleClass;
}
public boolean isReadonly() {
return readonly;
}
public void setReadonly(boolean readonly) {
this.readonly = readonly;
}
public boolean isDisabled() {
return disabled;
}
public void setDisabled(boolean disabled) {
this.disabled = disabled;
}
public String prepareStyles()
{
StringBuffer handlers=new StringBuffer();
prepareAttribute(handlers,"id",getStyleId());
prepareAttribute(handlers,"style",getStyle());
prepareAttribute(handlers,"class",getStyleClass());
return handlers.toString();
}
public String prepareEvents()
{
StringBuffer handlers=new StringBuffer();
prepareMouseEvents(handlers);
prepareKeyEvents(handlers);
prepareFocusEvents(handlers);
prepareTextEvents(handlers);
return handlers.toString();
}
public void prepareMouseEvents(StringBuffer handlers)
{
prepareAttribute(handlers,"onclick",getOnclick());
prepareAttribute(handlers,"ondblclick",getOndblclick());
prepareAttribute(handlers,"onmouseover",getOnmouseover());
prepareAttribute(handlers,"onmouseout",getOnmouseout());
prepareAttribute(handlers,"onmousedown",getOnmousedown());
prepareAttribute(handlers,"onmouseup",getOnmouseup());
prepareAttribute(handlers,"onmousemove",getOnmousemove());
}
public void prepareKeyEvents(StringBuffer handlers)
{
prepareAttribute(handlers,"onkeydown",getOnkeydown());
prepareAttribute(handlers,"onkeyup",getOnkeyup());
prepareAttribute(handlers,"onkeypress",getOnkeypress());
}
public void prepareFocusEvents(StringBuffer handlers)
{
prepareAttribute(handlers,"onfocus",getOnfocus());
prepareAttribute(handlers,"onblur",getOnblur());
if(isReadonly())
{
handlers.append(" readonly=\"readonly\"");
}
if(isDisabled())
{
handlers.append(" disabled=\"disabled\"");
}
}
public void prepareTextEvents(StringBuffer handlers)
{
prepareAttribute(handlers,"onselect",getOnselect());
prepareAttribute(handlers,"onchange",getOnchange());
}
public void prepareAttribute(StringBuffer handler,String property,Object value)
{
if(handler!=null&&property!=null&&value!=null)
{
handler.append(" ");
handler.append(property);
handler.append("=\"");
handler.append(value);
handler.append("\"");
}
}
/**
* 取值
* @param name
* @return
* @throws SecurityException
* @throws IllegalArgumentException
* @throws NoSuchFieldException
* @throws IllegalAccessException
*/
public Object findValue(String name) throws SecurityException, IllegalArgumentException, NoSuchFieldException, IllegalAccessException
{
String[] elements=name.split("\\.");
if(elements!=null&&elements.length>0)
{
Object bean=pageContext.getAttribute(elements[0],2);
if(elements.length>2)
{
for(int i=1;i<elements.length;i++)
{
bean=getValue(bean, elements[i]);
}
return bean;
}
else
{
return getValue(bean, elements[1]);
}
}
return null;
}
public Object getValue(Object bean,String property) throws SecurityException, NoSuchFieldException, IllegalArgumentException, IllegalAccessException
{
if(bean!=null&&property!=null)
{
Field field=bean.getClass().getDeclaredField(property);
field.setAccessible(true);
return field.get(bean);
}
return null;
}
public void release() {
// TODO Auto-generated method stub
super.release();
init();
}
}
package com.ts.taglib.html;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import javax.servlet.jsp.JspException;
import com.ts.taglib.data.Column;
import com.ts.taglib.data.DataGrid;
/**
* 表格控件
* @author 陈双
* @date 2012-09-22
* @mail chenshuang_com@sina.com
*
*/
public class TableTag extends BaseHandlerTag {
private static final long serialVersionUID = -5642687627324772161L;
private String name;//名称
private String width;//宽度
private String height;//高度
private String data;//取数
private boolean multiple;//是否多行勾选框
public TableTag()
{
super();
name=null;
width=null;
height=null;
data=null;
multiple=false;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getWidth() {
return width;
}
public void setWidth(String width) {
this.width = width;
}
public String getHeight() {
return height;
}
public void setHeight(String height) {
this.height = height;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
public boolean isMultiple() {
return multiple;
}
public void setMultiple(boolean multiple) {
this.multiple = multiple;
}
public int doEndTag() throws JspException {
try {
pageContext.getOut().print(createTable());
} catch (IOException e) {
throw new JspException(e.getMessage());
}
return 6;
}
public int doStartTag() throws JspException {
pageContext.setAttribute("columnHeader", new ArrayList(),2);
return 1;
}
/**
* 实现方式由Java构建所需的数据然后调用js创建表格
* @return
* @throws JspException
*/
public String createTable()throws JspException
{
StringBuffer handlers=new StringBuffer("<div id=\"main_grid_");
handlers.append(getName());
handlers.append("\"");
handlers.append(" style=\"border:solid 1 #cccccc;");
handlers.append("width:");
handlers.append(getWidth());
handlers.append(";height:");
handlers.append(Integer.parseInt(getHeight())+25);
handlers.append(";\">\n");
handlers.append("<script type=\"text/javascript\" charset=\"utf-8\">\n");
//处理数据
List headerList=(List) pageContext.getAttribute("columnHeader", 2);
if(headerList==null||headerList.size()==0)
{
throw new JspException("Table name is "+name+",列数必须大于0!");
}
handlers.append(getColumns(headerList));
List list=(List) pageContext.getAttribute(data, 2);
handlers.append(getRows(list));
//调用js生成表格对象
handlers.append("CreateTable('");
handlers.append(getName());
handlers.append("','main_grid_");
handlers.append(getName());
handlers.append("',");
handlers.append(getWidth());
handlers.append(",");
handlers.append(getHeight());
handlers.append(",");
handlers.append(isMultiple());
handlers.append(",getColumns_grid_");
handlers.append(getName());
handlers.append("(),getRows_grid_");
handlers.append(getName());
handlers.append("());\n</script>\n");
handlers.append("<table cellspacing=0 height=25 width=");
handlers.append(getWidth());
handlers.append(" >\n<tr>\n<td style=\"height:18px;cursor:default;font-size:12px;font-family:verdana;text-align:right;\">共");
Object total=pageContext.getAttribute("total", 2);
if(total==null)
{
total=0;
}
handlers.append(total);
handlers.append("页 当前显示第");
Object current=pageContext.getAttribute("current",2);
if(current==null)
{
current=0;
}
handlers.append(current);
handlers.append("页 <a href=\"javascript:lastPage();\">上页</a> <a href=\"javascript:nextPage();\">下页</a> <input type=\"hidden\" name=\"currentPage\"/>第<input name=\"toPage\" type=\"text\" size=3/>页</td>\n</tr>\n</table>\n");
handlers.append("</div>\n");
return handlers.toString();
}
/**
* 构建所有的列
* @param list
* @return
* @throws JspException
*/
private String getColumns(List list) throws JspException
{
StringBuffer columns=new StringBuffer();
if(list!=null&&list.size()>0)
{
columns.append("function getColumns_grid_");
columns.append(name);
columns.append("()\n{\n");
columns.append("var columns=new Array();\n");
for(int i=0;i<list.size();i++)
{
Column column=(Column) list.get(i);
columns.append("var gridColumn");
columns.append(i);
columns.append("=new GridColumn('");
columns.append(column.getName());
columns.append("','");
columns.append(column.getLabel());
columns.append("','");
columns.append(column.getType());
columns.append("',");
columns.append(column.getWidth());
columns.append(",");
columns.append(column.getHeight());
columns.append(",");
columns.append("null");
columns.append(",");
columns.append(column.isHidden());
columns.append(",");
columns.append(column.isDisabled());
columns.append(",");
columns.append(column.isSum());
columns.append(",");
columns.append(column.getSize());
columns.append(",");
columns.append(column.getColspan());
if(column.getOndblclick()!=null)
{
columns.append(",\"");
columns.append(column.getOndblclick());
columns.append("\",");
}
else
{
columns.append(",");
columns.append("null,");
}
if(column.getDrillEvent()!=null)
{
columns.append("\"");
columns.append(column.getDrillEvent());
columns.append("\");\n");
}
else
{
columns.append("null);\n");
}
columns.append("columns[");
columns.append(i);
columns.append("]=gridColumn");
columns.append(i);
columns.append(";\n");
}
columns.append("return columns;\n}");
}
return columns.toString();
}
/**
* 构建rows数据集将Java中的List<map>转成javascript中List<Map>形式
* @param list列表
* @return
*/
public String getRows(List list)
{
StringBuffer handlers=new StringBuffer("\n function getRows_grid_");
handlers.append(getName());
handlers.append("()\n{\n");
SimpleDateFormat dateFormat=new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
handlers.append("var rows=new List();\n");
if(list!=null&&list.size()>0)
{
for(int i=0;i<list.size();i++)
{
handlers.append("var map");
handlers.append(i);
handlers.append("=new Map();\n");
Map row=(Map) list.get(i);
for(Object key:row.keySet())
{
handlers.append("map");
handlers.append(i);
handlers.append(".put('");
handlers.append(key);
if(row.get(key)==null)
{
handlers.append("',");
handlers.append(row.get(key));
handlers.append(");\n");
}
else
{
Object param=row.get(key);
handlers.append("','");
if(param.getClass().getName().equals("java.sql.Timestamp")||param.getClass().getName().equals("java.util.Date"))
{
handlers.append(dateFormat.format(param));
}
else
{
handlers.append(row.get(key));
}
handlers.append("');\n");
}
}
handlers.append("rows.add(map");
handlers.append(i);
handlers.append(");\n");
}
}
handlers.append("return rows;\n");
handlers.append("\n}\n");
return handlers.toString();
}
public void release() {
super.release();
name=null;
width=null;
height=null;
data=null;
multiple=false;
}
}
package com.ts.taglib.html;
import java.util.List;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.tagext.TagSupport;
import com.ts.taglib.data.Column;
/**
* 构建列控件
* @author 陈双
* @date 2012-09-23
* @mail chenshuang_com@sina.com
*/
public class ColumnTag extends TagSupport {
private static final long serialVersionUID = 5477014869077280329L;
private String name;//名称
private String label;//标签
private String type;//类型
private String width;//宽度
private String height;//高度
private String size;//字符个数
private String data;//如果是combox时,选项取数来源
private String colspan;//跨列
private String ondblclick;//双击事件,只是针对参照列
private String drillEvent;//数据钻取时调用的函数
private boolean hidden;//是否隐藏
private boolean disabled;//是否可用
private boolean sum;//是否汇总
public ColumnTag()
{
super();
name=null;
label=null;
type=null;
width=null;
height=null;
size="14";
data=null;
colspan=null;
οndblclick=null;
drillEvent=null;
hidden=false;
disabled=false;
sum=false;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getLabel() {
return label;
}
public void setLabel(String label) {
this.label = label;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getWidth() {
return width;
}
public void setWidth(String width) {
this.width = width;
}
public String getHeight() {
return height;
}
public void setHeight(String height) {
this.height = height;
}
public String getSize() {
return size;
}
public void setSize(String size) {
this.size = size;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
public String getColspan() {
return colspan;
}
public void setColspan(String colspan) {
this.colspan = colspan;
}
public String getOndblclick() {
return ondblclick;
}
public void setOndblclick(String ondblclick) {
this.ondblclick = ondblclick;
}
public String getDrillEvent() {
return drillEvent;
}
public void setDrillEvent(String drillEvent) {
this.drillEvent = drillEvent;
}
public boolean isHidden() {
return hidden;
}
public void setHidden(boolean hidden) {
this.hidden = hidden;
}
public boolean isDisabled() {
return disabled;
}
public void setDisabled(boolean disabled) {
this.disabled = disabled;
}
public boolean isSum() {
return sum;
}
public void setSum(boolean sum) {
this.sum = sum;
}
public int doEndTag() throws JspException {
Column column=new Column();
column.setName(name);
column.setLabel(label);
column.setType(type);
column.setWidth(width);
column.setHeight(height);
column.setSize(size);
column.setData(data);
column.setColspan(colspan);
column.setOndblclick(ondblclick);
column.setDrillEvent(drillEvent);
column.setHidden(hidden);
column.setDisabled(disabled);
column.setSum(sum);
List list=(List)pageContext.getAttribute("columnHeader", 2);
list.add(column);
return 6;
}
public int doStartTag() throws JspException {
return 0;
}
public void release() {
super.release();
name=null;
label=null;
type=null;
width=null;
height=null;
data=null;
colspan=null;
size=null;
οndblclick=null;
drillEvent=null;
hidden=false;
disabled=false;
sum=false;
}
}
package com.ts.taglib.data;
import java.io.Serializable;
/**
* 列数据
* @author 陈双
* @date 2012-09-23
* @mail chenshuang_com@sina.com
*/
public class Column implements Serializable {
private static final long serialVersionUID = -2581722061552795107L;
private String name;//名称
private String label;//标签
private String type;//类型
private String width;//宽度
private String height;//高度
private String size;//字符个数
private String data;//如果是combox时,选项取数来源
private String colspan;//跨列
private String rowspan;//跨行
private String ondblclick;//双击事件,只是针对参照列
private String drillEvent;//数据钻取时调用的函数
private boolean hidden;//是否隐藏
private boolean disabled;//是否可用
private boolean sum;//是否汇总
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getLabel() {
return label;
}
public void setLabel(String label) {
this.label = label;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getWidth() {
return width;
}
public void setWidth(String width) {
this.width = width;
}
public String getHeight() {
return height;
}
public void setHeight(String height) {
this.height = height;
}
public String getSize() {
return size;
}
public void setSize(String size) {
this.size = size;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
public String getColspan() {
return colspan;
}
public void setColspan(String colspan) {
this.colspan = colspan;
}
public String getRowspan() {
return rowspan;
}
public void setRowspan(String rowspan) {
this.rowspan = rowspan;
}
public String getOndblclick() {
return ondblclick;
}
public void setOndblclick(String ondblclick) {
this.ondblclick = ondblclick;
}
public String getDrillEvent() {
return drillEvent;
}
public void setDrillEvent(String drillEvent) {
this.drillEvent = drillEvent;
}
public boolean isHidden() {
return hidden;
}
public void setHidden(boolean hidden) {
this.hidden = hidden;
}
public boolean isDisabled() {
return disabled;
}
public void setDisabled(boolean disabled) {
this.disabled = disabled;
}
public boolean isSum() {
return sum;
}
public void setSum(boolean sum) {
this.sum = sum;
}
}
package com.ts.taglib.data;
import java.io.Serializable;
import java.util.List;
import java.util.Map;
/**
* 用于构建多级表头动态列表格对象
* @author 陈双
* @date 2012-09-22
* @mail chenshuang_com@sina.com
*
*/
public class DataGrid implements Serializable {
private static final long serialVersionUID = 3814622301555705194L;
private String name;//名称
private String width;//宽度
private String height;//高度
private boolean multiple;//多行数据是否有勾选框
private List<Column[]> columns;//多级动态列
private List<Map<String,Object>> data;//行数据
private String dblclick;//双击事件
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getWidth() {
return width;
}
public void setWidth(String width) {
this.width = width;
}
public String getHeight() {
return height;
}
public void setHeight(String height) {
this.height = height;
}
public boolean isMultiple() {
return multiple;
}
public void setMultiple(boolean multiple) {
this.multiple = multiple;
}
public List<Column[]> getColumns() {
return columns;
}
public void setColumns(List<Column[]> columns) {
this.columns = columns;
}
public List<Map<String, Object>> getData() {
return data;
}
public void setData(List<Map<String, Object>> data) {
this.data = data;
}
public String getDblclick() {
return dblclick;
}
public void setDblclick(String dblclick) {
this.dblclick = dblclick;
}
}
js代码:
//===========================================================================
/**
*表格操作
*@author 陈双
*@date 2012-09-26
*@mail chenshuang_com@sina.com
*/
//===========================================================================
var globeVariable=new Map();//全局变量列表
/**
* 注册全局变量
* @param object 对象id
* @param property 变量名称
* @param value 值
* @return
*/
function put(object,property,value)
{
globeVariable.put(object+"_"+property,value);
}
/**
* 取出全局变量
* @param object 对象id
* @param property 变量名称
* @return
*/
function get(object,property)
{
return globeVariable.get(object+"_"+property);
}
/**
* 获取选中行单元格的值
* @param id 表格id
* @param cellIndex 单元格索引
* @param isMultiple 是否有勾选框
* @return Array 选中行的id值的集合
*/
function getSelectedCellValue(id,cellIndex,isMultiple){
if(!id)return null;
var values=new Array();//所有选中的id值
if(isMultiple)
{
var checkList=document.getElementsByName(id+"chbox");
var rows=new Array();//选中的行集合
var index=-1;
if(checkList && checkList.length>0)
{
for(var i=0;i<checkList.length;i++)
{
if(checkList[i].checked)
{
index++;
rows[index]=checkList[i].parentNode.parentNode;
}
}
}
if(rows.length==0)
{
alert("请选中一行!");
return null;
}
else
{
for(var i=0;i<rows.length;i++)
{
values[i]=rows[i].cells[parseInt(cellIndex)+2].innerText;
}
return values;
}
}
else
{
var _current_row=get(id,'_current_row');
if(_current_row==null)
{
alert("请选择一行!");
return null;
}
else
{
values[0]=document.getElementById(id).rows[_current_row].cells[parseInt(cellIndex)+1].innerText;
return values;
}
}
return null;
}
/**
* 创建可编辑的表格对象,并添加到指定的父节点中
* @param id 表格名称
* @param parentId 父节点id
* @param width 表格宽度
* @param height 表格高度
* @param isMultiple 多行是否有勾选框
* @param columns 表格所有的列,以数组的形式保存GridColumn对象
* @param rows 数据列表,它是以集合List的形式保存Map,其中key是name,value是值
* @param status 表格状态值: read只读,update可修改,insert新增
*/
function CreateTable(id,parentId,width,height,isMultiple,columns,rows)
{
if((!id)|(!parentId)||(!width)||(!height)||(!columns)||(!rows))
{
return;
}
var _sum_columns=null;//汇总列
var _isHbar=false;//是否有横向滚动条
var flag=false;//默认没有跨列操作
var first="";//声明第一列表
var title="";//标题表
var data="";//数据表
var sum="";//汇总表
var columnWidth=125;//默认列宽
for(var i=0;i<columns.length;i++)
{//检查是否有跨列操作
if(columns[i].colspan)
{
flag=true;
break;
}
}
put(id, 'flag', flag);
//构建标题列
if(flag)
{//有跨列操作
for(var i=0;i<2;i++)
{
if(i==0)
{
title="<tr><td class='firstcolumn' rowspan='2'> </td>";
if(isMultiple)
{
title+="<td class='column' width='30' rowspan='2' align='center'><input name='checkbox' type='checkbox' οnclick=\"checkAllForGrid(this.checked,'"+id+"chbox');\"/></td>";
}
}
else
{
title+="<tr>";
}
for(var j=0;j<columns.length;j++)
{
if(columns[j].colspan)
{//执行跨列
if(i==0)
{//第一行
title+="<td class='column' align='center' colspan='"+columns[j].colspan+"'";
if(columns[j].width)
{
title+=" width='"+(columns[j].width*parseInt(columns[j].colspan))+"'";
}
else
{
title+=" width='"+(columnWidth*parseInt(columns[j].colspan))+"'";
}
title+=">"+(columns[j].label.split(",")[0])+"</td>";
}
else
{//第二行
title+="<td class='column' align='center'";
if(columns[j].hidden)
{
columns[j].width=1;
title+=" style=\"border:none;\"";
}
if(columns[j].width)
{
title+=" width='"+columns[j].width+"'";
}
else
{
title+=" width='"+columnWidth+"'";
}
title+=">"+(columns[j].label.split(",")[1])+"</td>";
}
}
else
{//执行跨行
var rs=columns[j].label.indexOf(',');//是否是跨列
if(i==0)
{//跨行操作
if(rs==-1)
{//跨行
title+="<td class='column' align='center' rowspan='2'";
if(columns[j].hidden)
{
columns[j].width=1;
title+=" style=\"border:none;\"";
}
if(columns[j].width)
{
title+=" width='"+columns[j].width+"'";
}
else
{
title+=" width='"+columnWidth+"'";
}
title+=">"+columns[j].label+"</td>";
}
}
else
{//跨列操作
if(rs!=-1)
{//跨行
title+="<td class='column' align='center'";
if(columns[j].hidden)
{
columns[j].width=1;
title+=" style=\"border:none;\"";
}
if(columns[j].width)
{
title+=" width='"+columns[j].width+"'";
}
else
{
title+=" width='"+columnWidth+"'";
}
title+=">"+(columns[j].label.split(',')[1])+"</td>";
}
}
}
}
if(i==0)
{//最后一列
title+="<td class='lastcolumn' rowspan='2'> </td></tr>";
}
else
{
title+="</tr>";
}
}
}
else
{//正常情况
title="<tr><td class='firstcolumn'> </td>";
if(isMultiple)
{
title+="<td class='column' width='30' align='center'><input name='checkbox' type='checkbox' οnclick=\"checkAllForGrid(this.checked,'"+id+"chbox');\"/></td>";
}
for(var i=0;i<columns.length;i++)
{
title+="<td class='column' align='center'";
if(columns[i].hidden)
{
columns[i].width=1;
title+=" style=\"border:none;\"";
}
if(columns[i].width)
{
title+=" width='"+columns[i].width+"'";
}
else
{
title+=" width='"+columnWidth+"'";
}
title+=" οnclick=\"sortTableForGrid('"+id+"',"+i+","+isMultiple+");\"";
title+=">"+columns[i].label+"<span></span></td>";
}
title+="<td class='lastcolumn'> </td></tr>";
}
if(columns&&columns.length>0)
{//汇总表格
sum="<tr><td class='firstcolumn'>汇总</td>";
if(isMultiple)
{
sum+="<td class='column' width='30'> </td>";
}
for(var i=0;i<columns.length;i++)
{
sum+="<td class='column' align='center'";
if(columns[i].hidden)
{
columns[i].width=1;
sum+=" style=\"border:none;\"";
}
if(columns[i].width)
{
sum+=" width='"+columns[i].width+"'";
}
else
{
sum+=" width='"+columnWidth+"'";
}
sum+="> </td>";
}
sum+="<td class='lastcolumn'> </td></tr>";
}
if(rows&&rows.size()>0)
{//构建第一列和数据表格
if(flag)
{
first="<tr><td> </td></tr>";
first+="<tr><td> </td></tr>";
}
else
{
first="<tr><td> </td></tr>";
}
for(var i=0;i<rows.size();i++)
{
first+="<tr><td style='border-right:none;'>"+(i+1)+"</td></tr>";
data+="<tr><td class='firstcolumn' style='border-bottom-color:#cccccc;'>"+(i+1)+"</td>";
if(isMultiple)
{
data+="<td width='30' align='center'><input type='checkbox' name='"+id+"chbox'/></td>";
}
var rowId="rowid_"+(i+1);
var map=rows.get(i);
for(var j=0;j<columns.length;j++)
{
data+="<td";
if(columns[j].hidden)
{
columns[j].width=1;
data+=" style=\"border-right:none;\"";
}
if(columns[j].width)
{
data+=" width='"+columns[j].width+"'";
}
else
{
data+=" width='"+columnWidth+"'";
}
data+=">";
data+=map.get(columns[j].name)==null?" ":map.get(columns[j].name);
data+="</td>";
}
data+="<td class='lastdata'>";
data+="<input name='rowid' type='hidden' value='"+(rowId)+"'/>";
data+=" </td></tr>";
}
}
//构建汇总列
_sum_columns=new Array();//初始化
var k=0;
for(var i=0;i<columns.length;i++)
{
if(columns[i].sum&&(columns[i].type=="int"||columns[i].type=="number"))
{
if(isMultiple)
{
_sum_columns[k]=i+2;
}
else
{
_sum_columns[k]=i+1;
}
k++;
}
}
put(id,'_sum_columns',_sum_columns);
var allWidth=0;
for(var i=0;i<columns.length;i++)
{
if(columns[i].width)
{
allWidth+=parseInt(columns[i].width);
}
else
{
allWidth+=parseInt(columnWidth);
}
}
allWidth+=30;
if(isMultiple)
{
allWidth+=30;
}
var total=1;
if(allWidth>width)
{
total=2;
_isHbar=true;
}
put(id, '_isHbar', _isHbar);
//构建隐藏行
for(var i=0;i<total;i++)
{
data+="<tr><td style=\"border:0;\"> </td>";
for(var j=0;j<columns.length;j++)
{
data+="<td style=\"border:0;\"> </td>";
}
data+="<td style=\"border:0;\"> </td>";
first+="<tr><td style=\"border:0;background-color:white;\"> </td></tr>";
}
var title_html="<table id='header_"+id+"' cellspacing='0' cellpadding='0' class='titlecolumn'>"+title+"</table>";
var first_html="<table id='first_"+id+"' cellspacing='0' cellpadding='0' class='slidecolumn'>"+first+"</table>";
var data_html="<table id='"+id+"' cellspacing='0' cellpadding='0' class='datacolumn'>";
data_html+=title+data+"</table>";
var sum_html="<table id='sum_"+id+"' cellspacing='0'"+" cellpadding='0' style='width:100%;position:absolute;top:";
if(_isHbar)
{
sum_html+=+(parseInt(height)-18-17);
}
else
{
sum_html+=(parseInt(height)-17);
}
sum_html+=";left:0;z-index:4;'/>"+sum+"</table>";
_execute(id, parentId, width, height, first_html+title_html+data_html+sum_html,isMultiple);
sumRowForGrid(id);
}
/**
* 列结构
* @param name名称
* @param label 标签
* @param type 类型
* @param width 宽度
* @param height 高度
* @param data 列数据来源是一个数组
* @param hidden 是否隐藏
* @param disabled 是否可用
* @param sum 是否汇总
* @param size 字符个数
* @param colspan 跨列
* @param rowspan 跨行
* @param ondblclick 鼠标双击事件
* @param drillEvent 数据钻取处理函数
*/
function GridColumn(name,label,type,width,height,data,hidden,disabled,sum,size,colspan,ondblclick,drillEvent)
{
this.name=name;
this.label=label;
this.type=type;
this.width=width;
this.height=height;
this.data=data;
this.hidden=hidden;
this.disabled=disabled;
this.sum=sum;
this.size=size;
this.colspan=colspan;
this.οndblclick=ondblclick;
this.drillEvent=drillEvent;
}
/**
*@param 排序
*@param id为表格id
*@param index:列索引
*@param sort:asc是升序,dsc是降序
*@param isMultiple是否多行
*/
function sortTableForGrid(id,index,isMultiple)
{
var flag=get(id, 'flag');
var _isHbar=get(id, '_isHbar');
var tr=new Array();//行集合
var td=new Array();//列集合
var temp;//临时单元格
var table=document.getElementById(id);
var header=document.getElementById("header_"+id);
var sort;
if(flag)
{
return;
}
if(isMultiple)
{
index+=2;
}
else
{
index+=1;
}
var html=header.rows[0].cells[index].childNodes[1].innerHTML;
if(html=="")
{
sort="asc";
header.rows[0].cells[index].childNodes[1].innerHTML="▲";
}
else if(html=="▲")
{
sort="dsc";
header.rows[0].cells[index].childNodes[1].innerHTML="▼";
}
else if(html=="▼")
{
sort="asc";
header.rows[0].cells[index].childNodes[1].innerHTML="▲";
}
var k=1;
if(isMultiple)
{
k=2;
}
for(var i=k;i<header.rows[0].cells.length-1;i++)
{
if(i!=index)
{
header.rows[0].cells[i].childNodes[1].innerHTML="";
}
}
if(_isHbar)
{
for(var i=1;i<table.rows.length-3;i++)
{
tr[i-1]=table.rows[i];
td[i-1]=table.rows[i].cells[index];
}
}
else
{
for(var i=1;i<table.rows.length-2;i++)
{
tr[i-1]=table.rows[i];
td[i-1]=table.rows[i].cells[index];
}
}
var isNumber=false;//是数字
for(var i=0;i<td.length;i++)
{
if(!checkValueForGrid(td[i].innerHTML))
{
isNumber=true;//字符串
break;
}
}
//开始比较数据
for(var i=0;i<td.length;i++)
{
for(var j=0;j<td.length;j++)
{
if(isNumber)
{//字符串比较
if(sort=="asc")
{
if(td[i].innerHTML<td[j].innerHTML)
{
temp=td[i];
td[i]=td[j];
td[j]=temp;
}
}
else if(sort=="dsc")
{
if(td[i].innerHTML>td[j].innerHTML)
{
temp=td[i];
td[i]=td[j];
td[j]=temp;
}
}
}
else
{//数字比较
if(sort=="asc")
{
if(parseFloat(td[i].innerHTML)<parseFloat(td[j].innerHTML))
{
temp=td[i];
td[i]=td[j];
td[j]=temp;
}
}
else if(sort=="dsc")
{
if(parseFloat(td[i].innerHTML)>parseFloat(td[j].innerHTML))
{
temp=td[i];
td[i]=td[j];
td[j]=temp;
}
}
}
}
}
var cellCount=table.rows[0].cells.length;
var tempTR=new Array();//临时行
for(var i=0;i<tr.length;i++)
{
var tempTD=new Array();//临时列集合
for(var j=k;j<cellCount-1;j++)
{
tempTD[j]=td[i].parentNode.cells[j].innerHTML;
}
tempTR[i]=tempTD;
}
for(var i=0;i<tr.length;i++)
{
for(var j=k;j<cellCount-1;j++)
{
tr[i].cells[j].innerHTML=tempTR[i][j];
}
}
}
/**
*汇总行
*@param id 表格id
*@param columns 汇总列数组
*/
function sumRowForGrid(id)
{
var columns=get(id,'_sum_columns');
var _isHbar=get(id,'_isHbar');
var flag=get(id,'flag');
if(columns==undefined||columns.length==0)
{
return;
}
var sumTR=new Array();//汇总行临时数据
var table=document.getElementById(id);
var sum_table=document.getElementById("sum_"+id);
if((_isHbar&&flag==false&&table.rows.length==3)||(_isHbar&&flag&&table.rows.length==4)||(!_isHbar&&flag&&table.rows.length==3)||(!_isHbar&&!flag&&table.rows.length==2))
{
for(var i=0;i<columns.length;i++)
{
sum_table.rows[0].cells[columns[i]].innerHTML=' ';
}
return;
}
var index=1;
if(flag)
{
index=2;
}
var end=table.rows.length-1;
if(_isHbar)
{
end=table.rows.length-2;
}
for(var i=index;i<end;i++)
{
for(var j=0;j<columns.length;j++)
{
var value=table.rows[i].cells[columns[j]].innerText;
if(!checkValueForGrid(value))
{
value="0";
}
if(sumTR[j]==undefined)
{
sumTR[j]=value;
}
else if(sumTR[j]!="")
{
sumTR[j]=parseFloat(sumTR[j])+parseFloat(value);
}
}
}
//填充汇总行
for(var i=0;i<columns.length;i++)
{
sum_table.rows[0].cells[columns[i]].innerHTML=sumTR[i];
}
}
/**
*检查value是否为数字,返回true是数字,返回false为字符串
*@param value要检查的值
*/
function checkValueForGrid(value)
{
if(value && value.length>0)
{
var newValue=value.replace(/\s+/g,"");
value=newValue;
}
else
{
return false;
}
if(value.length>0 && value.indexOf('.')!=-1)
{//判断是否是小数
var express=/^\d+.\d+$/;//匹配小数
if(express.test(value)){
return true;
}
else
{
return false;
}
}
else
{
var express=/^\d+$/;
if(express.test(value))
{
return true;
}
else
{
return false;
}
}
return false;
}
/**
* 全选
*@param checked是否选中true为选中,false没选中
*@param name 名称
*/
function checkAllForGrid(checked,name)
{
var checkList=document.getElementsByName(name);
if(checkList && checkList.length>0)
{
for(var i=0;i<checkList.length;i++)
{
checkList[i].checked=checked;
}
}
}
/**
* 构建表格以及滚动条
* @param id 表格id
* @param parentId 父节点,将建构建好的表格节点添加到父节点中
* @param width 表格宽度
* @param height 表格高度
* @param ondblclick 表格双击事件
* @param html (构建好的表格=序列号表格+表头表格+数据表格+汇总表格)
* @return
*/
function _execute(id,parentId,width,height,html,isMultiple)
{
/**
* 定义构建表格需要的变量
*/
var _first_object=null;//第一列,序数表格
var _header_object=null;//表头
var _data_object=null;//数据表格
var _sum_object=null;//汇总表格
var _hbar_object=null;//横向滚动条
var _vbar_object=null;//纵向滚动条
var _current_row=null;//当前选中行
var mainFrame=document.createElement("DIV");
mainFrame.id="DIV_"+id;
mainFrame.style.width=width;
mainFrame.style.height=height;
mainFrame.className="datagrid";
mainFrame.οnmοusedοwn=function (e){//鼠标按下事件
e=e||window.event;
_selectedRow(e,id,isMultiple);//选中行
}
mainFrame.innerHTML=html;
/*
* 添加滚动事件,根据IE的冒泡特性子节点事件触发自后如果父节点也有相同的事件
* 就会接着执行父节点的事件
*/
_addScrollEvent(mainFrame,id);
//构建横向滚动条
var hbar=document.createElement("DIV");
hbar.id="hbar";
hbar.style.position="absolute";
hbar.style.width="100%";
hbar.style.height="17px";
hbar.style.overflowX="auto";
hbar.style.top=height-17;
hbar.style.zIndex="10";
hbar.οnscrοll=function(){
_h_scroll(id);//横向滚动
}
hbar.innerHTML="<div style=\"width:100%;height:1px;overflow-y:hidden;\"> </div>";
//构建纵向滚动条
var vbar=document.createElement("DIV");
vbar.id="vbar";
vbar.style.position="absolute";
vbar.style.width="17px";
vbar.style.height="100%";
vbar.style.overflowY="auto";
vbar.style.left=width-17;
vbar.style.zIndex="10";
vbar.οnscrοll=function(){
_v_scroll(id);//纵向滚动
}
vbar.innerHTML="<div style=\"width:1px;height:100%;overflow-x:hidden;\"> </div>";
//将表格和滚动条组合在一起
mainFrame.appendChild(hbar);
mainFrame.appendChild(vbar);
//将构建好的表格节点追加到父节点中
document.getElementById(parentId).appendChild(mainFrame);
_first_object=document.getElementById("first_"+id);//第一列,序数表格
_header_object=document.getElementById("header_"+id);//表头
_data_object=document.getElementById(id);//数据表格
_sum_object=document.getElementById("sum_"+id);//汇总表格
_hbar_object=hbar;//横向滚动条
_vbar_object=vbar;//纵向滚动条
/*
* 注册全局变量
*/
put(id,'_first_object',_first_object);
put(id,'_header_object',_header_object);
put(id,'_data_object',_data_object);
put(id,'_sum_object',_sum_object);
put(id,'_hbar_object',_hbar_object);
put(id,'_vbar_object',_vbar_object);
var bt=_getCurrentStyle(mainFrame,"borderTopWidth");
var bb=_getCurrentStyle(mainFrame,"borderBottomWidth");
var bl=_getCurrentStyle(mainFrame,"borderLeftWidth");
var br=_getCurrentStyle(mainFrame,"borderRightWidth");
_hbar_object.style.top=parseInt(_hbar_object.style.top)-parseInt(bt)-parseInt(bb);
_vbar_object.style.left=parseInt(_vbar_object.style.left)-parseInt(bl)-parseInt(br);
_block_scroll(id);//设置滚动块
}
/**
* 当鼠标按下时选中行
* @param e
* @return
*/
function _selectedRow(e,id,isMultiple)
{
if(isMultiple)
return;
var td_object=e.srcElement?e.srcElement:e.target;
var _data_object=get(id,'_data_object');
var table=document.getElementById(id);
if(td_object.parentNode.tagName=="TR")
{
var tr_object=td_object.parentNode;
var rowIndex=tr_object.rowIndex;//行索引
var _current_row=get(id,'_current_row');
var flag=get(id,'flag');
var _isHbar=get(id,'_isHbar');
if(flag)
{
if(rowIndex==0||rowIndex==1)
{
return;
}
}
else
{
if(rowIndex==0)
{
return;
}
}
if(_isHbar)
{
if(rowIndex==table.rows.length-1||rowIndex==table.rows.length-2)
{
return;
}
}
else
{
if(rowIndex==table.rows.length-1)
{
return;
}
}
if(_current_row!=null)
{//取消之前的选中行状态
_data_object.rows[_current_row].className="";
}
//重新设置选中行状态
_data_object.rows[rowIndex].className="selectedrow";
_current_row=rowIndex;
put(id,'_current_row',_current_row);
}
}
/**
* 添加滚动事件监听器
* @param element要添加事件的父节点
* @return
*/
function _addScrollEvent(element,id)
{
var handler=function(e)
{
_mouseScrollEvent.call(this, e,id);
}
if(document.attachEvent)
{//微软自定义的添加事件监听器
element.attachEvent("onmousewheel",handler);
}
else
{//W3C规范定义的添加事件监听器
element.addEventListener("DOMMouseScroll",handler,false);
}
}
/**
* 鼠标轮滚动事件和列表事件
* @param e
* @return
*/
function _mouseScrollEvent(e,id)
{
e=e||window.event;
var _vbar_object=get(id,'_vbar_object');
if(e.wheelDelta<=0 || e.detail>0)
{
_vbar_object.scrollTop+=18;//设置滚动步长为一行的高度
}
else
{
_vbar_object.scrollTop-=18;
}
}
/**
* 横向滚动
* @return
*/
function _h_scroll(id)
{
var _hbar_object=get(id,'_hbar_object');
var _header_object=get(id,'_header_object');
var _data_object=get(id,'_data_object');
var _sum_object=get(id,'_sum_object');
_header_object.style.left=-(_hbar_object.scrollLeft);
_data_object.style.left=-(_hbar_object.scrollLeft);
_sum_object.style.left=-(_hbar_object.scrollLeft);
}
/**
*纵向滚动
* @return
*/
function _v_scroll(id)
{
var _vbar_object=get(id,'_vbar_object');
var _first_object=get(id,'_first_object');
var _data_object=get(id,'_data_object');
_first_object.style.top=-(_vbar_object.scrollTop);
_data_object.style.top=-(_vbar_object.scrollTop);
}
/**
* 取出当前元素非style定义的样式
* @param element
* @param property
* @return
*/
function _getCurrentStyle(element,property)
{
if(element.currentStyle)
{//元素中非style定义的样式,包括内嵌样式和外部样式表中定义的样式
return element.currentStyle[property];
}
else if(window.getComputedStyle)
{//firefox的方式
property=property.replace(/([A-Z])/g, "-$1").toLowerCase();
return window.getComputedStyle(element,null).getPropertyValue(property);
}
else
{
return null;
}
}
/**
* 设置滚动块
* @return
*/
function _block_scroll(id)
{
var _hbar_object=get(id,'_hbar_object');
var _vbar_object=get(id,'_vbar_object');
var _data_object=get(id,'_data_object');
_hbar_object.style.display="block";
_vbar_object.style.display="block";
_hbar_object.childNodes[0].style.width=_data_object.offsetWidth;
_vbar_object.childNodes[0].style.height=_data_object.offsetHeight;
if(_hbar_object.childNodes[0].offsetWidth<=_hbar_object.offsetWidth)
{
_hbar_object.style.display="none";
}
if(_vbar_object.childNodes[0].offsetHeight<=_vbar_object.offsetHeight)
{
_vbar_object.style.display="none";
}
}
/
/**
* js通用对象,主要包括List和Map集合对象的定义
* @author 陈双
* @date 2012-10-01
* @mail chenshuang_com@sina.com
*/
/**
* List对象
* @return
*/
function List()
{
this.container=new Array(1000);//容器
this.index=-1;//索引
this.add=function(element){//添加元素
this.index++;
this.container[this.index]=element;
}
this.get=function(i){//获取元素
if(this.index==-1||i<0)
{
return null;
}
return this.container[i];
}
this.size=function(){//List 对象的大小
return this.index+1;
}
this.clear=function(){//清空List对象
if(this.index!=-1)
{
for(var i=0;i<=this.index;i++)
{
this.container[i]=null;
}
}
this.index=-1;
}
this.contain=function(element){//是否包含某元素
if(this.index==-1||(!element))
{
return false;
}
for(var i=0;i<=this.index;i++)
{
if(this.container[i]==element)
{
return true;
}
}
}
this.isEmpty=function(){//是否为空
return this.index==-1?true:false;
}
this.remove=function(element){//删除一个元素
if((!element)||(!this.index))
{
return;
}
var po=-1;
var flag=false;//是否移除了
for(var i=0;i<=this.index;i++)
{
if(this.container[i]==element)
{
po=i;
if(po==this.index)
{
po=-1;
}
flag=true;
}
if(po!=-1)
{
this.container[po]=this.container[po+1];
po++;
}
}
if(flag)
{
this.index=this.index-1;
}
}
this.removeIn=function(i){//删除指定位置的元素
if(i<0||this.index<0)
{
return;
}
var po=-1;
var flag=false;//是否移除了
for(var j=0;j<=this.index;j++)
{
if(j==i)
{
po=j;
if(po==this.index)
{
po=-1;
}
flag=true;
}
if(po!=-1)
{
this.container[po]=this.container[po+1];
po++;
}
}
if(flag)
{
this.index=this.index-1;
}
}
}
/**
* Map对象
* @return
*/
function Map()
{
this.index=-1;
this.entrys=new Array(1000);
this.get=function(key){//通过key映射value
if(this.index==-1)
{
return null;
}
for(var i=0;i<=this.index;i++)
{
var entry=this.entrys[i];
if(entry.key==key)
{
return entry.value;
}
}
return null;
}
this.size=function(){//返回元素个数
return this.index+1;
}
this.containsKey=function(key){//是否包含key值
if(this.index==-1)
{
return false;
}
for(var i=0;i<=this.index;i++)
{
var entry=this.entrys[i];
if(entry.key==key)
{
return true;
}
}
return false;
}
this.containsValue=function(value){//是否包含值
if(this.index==-1)
{
return false;
}
for(var i=0;i<=this.index;i++)
{
var entry=this.entrys[i];
if(entry.value==value)
{
return true;
}
}
return false;
}
this.put=function(key,value){//添加元素
if(this.containsKey(key))
{
this.remove(key);
}
this.index++;
this.entrys[this.index]=new Entry(key,value);
}
this.keySet=function(){//返回key集合
if(this.index==-1)
{
return null;
}
var keys=new List();
for(var i=0;i<=this.index;i++)
{
keys.add(this.entrys[i].key);
}
return keys;
}
this.values=function(){//返回值集合
if(this.index==-1)
{
return null;
}
var value=new List();
for(var i=0;i<=this.index;i++)
{
value.add(this.entrys[i].value);
}
return value;
}
this.clear=function(){//清空
if(this.index!=-1)
{
for(var i=0;i<=this.index;i++)
{
this.entrys[i]=null;
}
this.index=-1;
}
}
this.remove=function(key){//移除某个元素
if(this.index==-1)
{
return;
}
var po=-1;
var flag=false;
for(var i=0;i<=this.index;i++)
{
var entry=this.entrys[i];
if(entry.key==key)
{
po=i;
if(i==this.index)
{
po=-1;
}
flag=true;
}
if(po!=-1)
{
this.entrys[po]=this.entrys[po+1];
po++;
}
}
if(flag)
{
this.index=this.index-1;
}
}
this.isEmpty=function(){//是否为空
if(this.index==-1)
{
return true;
}
return false;
}
this.entrySet=function(){//返回Entry
if(this.index==-1)
{
return null;
}
var entry=new List();
for(var i=0;i<=this.index;i++)
{
entry.add(this.entrys[i]);
}
return entry;
}
}
/**
* Map中的节点对象
* @param key
* @param value
* @return
*/
function Entry(key,value)
{
this.key=key;
this.value=value;
}
css代码:
/*datagrid 大块样式*/
.datagrid {position:relative;background:white;margin:0px;padding:0px;overflow:hidden;border:1px inset;-moz-user-select:none;}
/*datagrid 表格全局样式*/
.datagrid table {table-layout:fixed;margin:0px;}
.datagrid table td {height:18px;cursor:default;font-size:12px;font-family:verdana;text-indent:2px;border-right:1px solid #cccccc;border-bottom:1px solid #cccccc;text-overflow:ellipsis;overflow:hidden;white-space:nowrap;word-break:keep-all;}
.datagrid table td .arrow {font-size:8px;color:#808080;}
.datagrid table .lastdata {border-right:none;}
.datagrid table .column {cursor:default;background:buttonface;border-top:1px solid #fff;border-right:1px solid #404040;border-bottom:1px solid #404040;border-left:1px solid #fff;}
.datagrid table .over {cursor:default;background:buttonface;border-top:1px solid #fff;border-right:1px solid #404040;border-bottom:1px solid #404040;border-left:1px solid #fff;}
.datagrid table .sortdown {cursor:default;background:buttonface;border-right:1px solid #ffffff;border-bottom:1px solid #ffffff;border-left:1px solid #404040;border-top:1px solid #404040;position:relative;left:1px;}
.datagrid table .dataover {background:#FAFAFA;}
.datagrid table .firstcolumn {width:30px;text-indent:0px;text-align:center;background:buttonface;border-top:1px solid #fff;border-right:1px solid #404040;border-bottom:1px solid #404040;border-left:1px solid #fff;}
.datagrid table .lastcolumn {width:17px;background:buttonface;border-top:1px solid #fff;border-right:1px solid #404040;border-bottom:1px solid #404040;border-left:1px solid #fff;}
/*datagrid 选定行样式*/
.datagrid table .selectedrow {background:highlight;color:white;}
/*datagrid 表头样式*/
.titlecolumn {width:100%;position:absolute;top:0px;left:0px;z-index:3;}
/*datagrid 左边栏样式*/
.slidecolumn {width:30px;position:absolute;top:0px;left:0px;z-index:2;}
.slidecolumn td {width:30px;text-indent:0px;text-align:center;background:buttonface;border-top:1px solid #fff;border-right:1px solid #404040;border-bottom:1px solid #404040;border-left:1px solid #fff;}
/*datagrid 内容表体样式*/
.datacolumn {width:100%;position:absolute;top:0px;left:0px;}
.datacolumn td {top:0px;left:0px;margin:0px;padding:0px}
.datacolumn td input {margin:0px;border:0px #cccccc solid;}
多级动态暂未实现