最近突发奇想,想自己写一个grid控件框架,本来想自己设计一套,尝试几次,发现自己设计样式难度挺大,毕竟自己是个程序员而不是专业美工,所以我打算临摹一下jqgrid框架。
这次开发实践的主要目的是锻炼下自己的javascript编程能力,所以我只是抠出了jqgrid的页面设计,至于javascript代码我不想借鉴,自己独立开发,所以我的代码绝对原创。
下面就是我抠出的页面代码,代码如下:
studyjqgrid.html:
![](https://i-blog.csdnimg.cn/blog_migrate/cdec0645add3fc3c328197dda5c76203.gif)
我为自己写的jqgrid框架的名称叫xjqGrid,工程的目录结构如下:
xjqGrid-1.0.css代码如下:
.ui-widget .ui-widget { font-size: 1em; } .ui-jqgrid { position: relative; } .ui-corner-all { border-radius: 5px 5px 5px 5px; } .ui-widget-content { background: url("../images/ui-bg_inset-hard_100_fcfdfd_1x100.png") repeat-x scroll 50% bottom #FCFDFD; border: 1px solid #A6C9E2; color: #222222; } .ui-widget { font-family: Lucida Grande,Lucida Sans,Arial,sans-serif; font-size: 1.1em; } .ui-jqgrid .ui-jqgrid-view { font-size: 11px; left: 0; padding: 0; position: relative; top: 0; } .ui-helper-clearfix:after { clear: both; content: "."; display: block; height: 0; visibility: hidden; } .ui-jqgrid .ui-jqgrid-titlebar { border-left: 0 none; border-right: 0 none; border-top: 0 none; padding: 0.3em 0.2em 0.2em 0.3em; position: relative; } .ui-corner-top { border-top-left-radius: 5px; border-top-right-radius: 5px; } .ui-widget-header { background: url("../images/ui-bg_gloss-wave_55_5c9ccc_500x100.png") repeat-x scroll 50% 50% #5C9CCC; border: 1px solid #4297D7; color: #FFFFFF; font-weight: bold; } .ui-helper-clearfix { display: block; } .ui-jqgrid .ui-jqgrid-titlebar-close { height: 18px; margin: -10px 0 0; padding: 1px; position: absolute; top: 50%; width: 19px; } .ui-widget-header a { color: #FFFFFF; } .ui-jqgrid .ui-jqgrid-titlebar-close span { display: block; margin: 1px; } .ui-widget-header .ui-icon { background-image: url("../images/ui-icons_d8e7f3_256x240.png"); } .ui-icon-circle-triangle-n { background-position: -96px -192px; } .ui-icon-circle-triangle-s { background-position: -64px -192px; } .ui-icon { background-repeat: no-repeat; height: 16px; width: 16px; overflow: hidden; text-indent: -99999px; } .ui-jqgrid .ui-jqgrid-title { float: left; margin: 0.1em 0 0.2em; } .ui-jqgrid .ui-jqgrid-hdiv { border-left: 0 none !important; border-right: 0 none !important; border-top: 0 none !important; margin: 0; overflow-x: hidden; padding: 0; position: relative; } .ui-state-default, .ui-widget-content .ui-state-default, .ui-widget-header .ui-state-default { background: url("../images/ui-bg_glass_85_dfeffc_1x400.png") repeat-x scroll 50% 50% #DFEFFC; border: 1px solid #C5DBEC; color: #2E6E9E; font-weight: bold; } .ui-jqgrid .ui-jqgrid-hbox { float: left; padding-right: 20px; } .ui-jqgrid .ui-jqgrid-htable { margin: 0; table-layout: fixed; } .ui-th-ltr, .ui-jqgrid .ui-jqgrid-htable th.ui-th-ltr { border-left: 0 none; } .ui-th-column, .ui-jqgrid .ui-jqgrid-htable th.ui-th-column { border-bottom: 0 none; border-top: 0 none; overflow: hidden; text-align: center; white-space: nowrap; } .ui-jqgrid .ui-jqgrid-htable th { height: 22px; padding: 0 2px; } .ui-jqgrid .ui-jqgrid-htable th div { height: 17px; overflow: hidden; position: relative; } .ui-widget input, .ui-widget select, .ui-widget textarea, .ui-widget button { font-family: Lucida Grande,Lucida Sans,Arial,sans-serif; font-size: 1em; } .ui-jqgrid .ui-jqgrid-resize { cursor: e-resize; display: inline; height: 20px !important; overflow: hidden; position: relative; } .ui-jqgrid .ui-jqgrid-resize-ltr { float: right; margin: -2px -2px -2px 0; } .ui-jqgrid .ui-jqgrid-sortable { cursor: pointer; } .ui-jqgrid .ui-jqgrid-bdiv { margin: 0; overflow: auto; padding: 0; position: relative; text-align: left; } .ui-jqgrid .ui-jqgrid-btable { margin: 0; outline-style: none; table-layout: fixed; } .ui-jqgrid tr.jqgrow { outline-style: none; } .ui-state-highlight, .ui-widget-content .ui-state-highlight, .ui-widget-header .ui-state-highlight { background: url("../images/ui-bg_flat_55_fbec88_40x100.png") repeat-x scroll 50% 50% #FBEC88; border: 1px solid #FAD42E; color: #363636; } .ui-jqgrid tr.jqgrow td { border-bottom-color: inherit; border-bottom-style: solid; border-bottom-width: 1px; font-weight: normal; height: 22px; } .ui-jqgrid tr.ui-row-ltr td { border-right-color: inherit; border-right-style: solid; border-right-width: 1px; text-align: left; } .ui-jqgrid td input, .ui-jqgrid td select .ui-jqgrid td textarea { margin: 0; } .ui-jqgrid tr.jqgfirstrow td { border-right-style: solid; border-right-width: 1px; padding: 0 0px; } .ui-state-hover, .ui-widget-content .ui-state-hover, .ui-widget-header .ui-state-hover, .ui-state-focus, .ui-widget-content .ui-state-focus, .ui-widget-header .ui-state-focus { border: 1px solid #79b7e7; background: #d0e5f5 url("..images/ui-bg_glass_75_d0e5f5_1x400.png") 50% 50% repeat-x; font-weight: bold; color: #1d5987; } .ui-state-hover .ui-icon, .ui-state-focus .ui-icon { background-image: url("../images/ui-icons_217bc0_256x240.png"); }
xjqGrid-1.0.js代码如下:
(function(window,undefined){ var document = window.document, navigator = window.navigator, location = window.location, $ = window.jQuery; var xjqGridUtils = {// 工具类 isString:function(obj){// 判断是不是String类型 return (obj != null) && (obj != undefined) && (typeof obj == 'string') && (obj.constructor == String); }, isNumber:function(obj){// 判断是否是数组 return (typeof obj == 'number') && (obj.constructor == Number); }, isDate:function(obj){// 判断是否是日期 return obj && (typeof obj == 'object') && (obj.constructor == Date); }, isArray:function(obj){//判断是否是数组 return obj && (typeof obj == 'object') && (obj.constructor == Array); }, isObject:function(obj){//判断是否是对象 return obj && (typeof obj == 'object') && (obj.constructor == Object) }, trim:function(str){// 去除左右两边空格 return str.replace(/(^\s*)|(\s*$)/, "");; } }; var xjqGrid = { jsName:"xjqGrid.js", defaultVer:"20120628", executeFlag:true, errInfo:undefined, recordGridObj:{}, targetDivId:undefined, targetDivObj:undefined, gridWidth:'100%', gridHeight:"100%", colNames:[], colModel:[], caption:"欢迎使用xjqGrid!", gridData:[], selectType:"none", init:function(dataObj){//初始化 if (xjqGridUtils.isObject(dataObj)){ this.recordGridObj = dataObj; this.targetDivId = dataObj.targetId; this.gridWidth = dataObj.width; this.gridHeight = dataObj.height; this.colNames = dataObj.colNames; this.colModel = dataObj.colModel; this.caption = dataObj.caption; this.gridData = dataObj.gridData; this.selectType = dataObj.selectType; this.targetDivObj = $("#" + this.targetDivId); return this; }else{ this.executeFlag = false; this.errInfo = "init的参数必须是javascript对象!"; } }, execute:function(){//执行方法 var gridRootObj = this.createGridRoot(); var gridCaptionObj = this.createGridCaption(); var gridHeadObj = this.createGridHead(); var gridBodyObj = this.createGridBody(); gridRootObj.append(gridCaptionObj); gridRootObj.append(gridHeadObj); gridRootObj.append(gridBodyObj); this.targetDivObj.append(gridRootObj); this.targetDivObj.addClass("ui-jqgrid"); this.targetDivObj.addClass("ui-widget"); this.targetDivObj.addClass("ui-widget-content"); this.targetDivObj.addClass("ui-corner-all"); this.targetDivObj.css("width",this.gridWidth); this.targetDivObj.attr("id","xjqbox_" + this.targetDivId); this.eventHanlding(); }, createGridRoot:function(){ var gridRootObj = $("<div></div>"); gridRootObj.addClass("ui-jqgrid-view"); gridRootObj.attr("id","xjqview_" + this.targetDivId); gridRootObj.css("width",this.gridWidth); return gridRootObj; }, createGridCaption:function(){ var gridCaptionDiv = $("<div></div>"); gridCaptionDiv.addClass("ui-jqgrid-titlebar"); gridCaptionDiv.addClass("ui-widget-header"); gridCaptionDiv.addClass("ui-corner-top"); gridCaptionDiv.addClass("ui-helper-clearfix"); var gridCaptionA = $("<a></a>"); gridCaptionA.addClass("ui-jqgrid-titlebar-close"); gridCaptionA.addClass("HeaderButton"); gridCaptionA.css("right","0px"); var gridCaptionASpan = $("<span></span>"); gridCaptionASpan.addClass("ui-icon"); gridCaptionASpan.addClass("ui-icon-circle-triangle-n"); gridCaptionA.append(gridCaptionASpan); var gridCaptionSpan = $("<span></span>"); gridCaptionSpan.text(this.caption); gridCaptionSpan.addClass("ui-jqgrid-title"); gridCaptionDiv.append(gridCaptionA); gridCaptionDiv.append(gridCaptionSpan); return gridCaptionDiv; }, createGridHead:function(){ var gridHeadDiv = $("<div></div>"); gridHeadDiv.addClass("ui-state-default"); gridHeadDiv.addClass("ui-jqgrid-hdiv"); gridHeadDiv.css("width",this.gridWidth); var gridChildHeadDiv = $("<div></div>"); gridChildHeadDiv.addClass("ui-jqgrid-hbox"); var gridHeadTbl = $("<table></table>"); gridHeadTbl.attr("cellspacing","0"); gridHeadTbl.attr("cellpadding","0"); gridHeadTbl.attr("border","0"); gridHeadTbl.css("width","682px"); var gridHeadTr = $("<tr></tr>"); gridHeadTr.addClass("ui-jqgrid-labels"); if (this.selectType){ if (this.selectType == 'checkbox'){ var gridHeadThforSel = $("<th></th>"); gridHeadThforSel.addClass("ui-th-ltr"); gridHeadThforSel.addClass("ui-th-column"); gridHeadThforSel.addClass("ui-state-default"); gridHeadThforSel.attr("name",xjqGrid.targetDivId + "_cb"); gridHeadThforSel.attr("id",xjqGrid.targetDivId + "_cb"); gridHeadThforSel.css("width","20px"); gridHeadThforSel.css("border-bottom","0 none"); gridHeadThforSel.css("border-top","0 none"); gridHeadThforSel.css("border-left","0 none"); var gridHeadThforSelDiv = $("<div></div>"); gridHeadThforSelDiv.attr("id","xjqgh_" + xjqGrid.targetDivId + "_cb"); var gridHeadThforSelChk = $("<input type='checkbox'/>"); gridHeadThforSelChk.attr("cb_" + xjqGrid.targetDivId); gridHeadThforSelChk.addClass("cbox"); gridHeadThforSelDiv.append(gridHeadThforSelChk); gridHeadThforSel.append(gridHeadThforSelDiv); gridHeadTr.append(gridHeadThforSel); } } $.each(xjqGrid.colModel,function(ind,data){ var gridHeadTh = $("<th></th>"); gridHeadTh.addClass("ui-th-ltr"); gridHeadTh.addClass("ui-th-column"); gridHeadTh.addClass("ui-state-default"); gridHeadTh.css("border-bottom","0 none"); gridHeadTh.css("border-top","0 none"); gridHeadTh.css("border-left","0 none"); if (data.name){ gridHeadTh.attr('name',xjqGrid.targetDivId + "_" + data.name); } if (data.id){ gridHeadTh.attr('id',xjqGrid.targetDivId + "_" + data.id); } if (data.width){ gridHeadTh.css('width',data.width); } gridHeadTh.text(xjqGrid.colNames[ind]); gridHeadTr.append(gridHeadTh); }); gridHeadTbl.append(gridHeadTr); gridChildHeadDiv.append(gridHeadTbl); gridHeadDiv.append(gridChildHeadDiv); return gridHeadDiv; }, createGridBody:function(){ var gridBodyDiv = $("<div></div>"); gridBodyDiv.addClass("ui-jqgrid-bdiv"); gridBodyDiv.css("width",this.gridWidth); gridBodyDiv.css("height",this.gridHeight); var gridBodyChildDiv = $("<div></div>"); gridBodyChildDiv.attr("position","relative"); gridBodyChildDiv.append("<div></div>"); var gridBodyTbl = $("<table></table>"); gridBodyTbl.attr("cellspacing","0"); gridBodyTbl.attr("cellpadding","0"); gridBodyTbl.attr("border","0"); gridBodyTbl.css("width","682px"); gridBodyTbl.addClass("ui-jqgrid-btable"); var gridBodyCellTr = $("<tr></tr>"); gridBodyCellTr.css("height","auto"); gridBodyCellTr.addClass("jqgfirstrow"); if (this.selectType){ if (this.selectType == 'checkbox'){ var gridBodyCellFirstTd = $("<td></td>"); gridBodyCellFirstTd.css("height","0px"); gridBodyCellFirstTd.css("width","20px"); gridBodyCellTr.append(gridBodyCellFirstTd); } } $.each(this.colModel,function(ind,data){ var gridBodyCellTd = $("<td></td>"); gridBodyCellTd.css("height","0px"); if (data.width){ gridBodyCellTd.css("width",data.width); } gridBodyCellTr.append(gridBodyCellTd); }); gridBodyTbl.append(gridBodyCellTr); $.each(this.gridData,function(ind,data){ var gridBodyContentTr = $("<tr></tr>"); gridBodyContentTr.addClass("ui-widget-content"); gridBodyContentTr.addClass("jqgrow"); gridBodyContentTr.addClass("ui-row-ltr"); gridBodyContentTr.attr("id",ind); if (xjqGrid.selectType){ if (xjqGrid.selectType == 'checkbox'){ var gridBodyFirstTd = $("<td></td>"); gridBodyFirstTd.css("text-align","center"); gridBodyFirstChk = $("<input type='checkbox'/>"); gridBodyFirstChk.addClass("cbox"); gridBodyFirstChk.attr("index",ind); gridBodyFirstTd.append(gridBodyFirstChk); gridBodyContentTr.append(gridBodyFirstTd); } } $.each(xjqGrid.colModel,function(colInd,colData){ var gridBodyContentTd = $("<td></td>"); if (colData.name){ gridBodyContentTd.text(data[colData.name]); gridBodyContentTd.attr("title",data[colData.name]); } gridBodyContentTr.append(gridBodyContentTd); }); gridBodyTbl.append(gridBodyContentTr); }); gridBodyChildDiv.append(gridBodyTbl); gridBodyDiv.append(gridBodyChildDiv); return gridBodyDiv; }, eventHanlding:function(){ $(".HeaderButton").bind("click",function(){ if ($(".ui-jqgrid-hdiv").css("display") == "block"){ $(".ui-jqgrid-hdiv").css("display","none"); $(".ui-jqgrid-bdiv").css("display","none"); $("span",this).removeClass("ui-icon-circle-triangle-n").addClass("ui-icon-circle-triangle-s"); }else{ $(".ui-jqgrid-hdiv").css("display","block"); $(".ui-jqgrid-bdiv").css("display","block"); $("span",this).removeClass("ui-icon-circle-triangle-s").addClass("ui-icon-circle-triangle-n"); } }); $('.HeaderButton').hover(function(){ $(this).addClass("ui-state-hover"); },function(){ $(this).removeClass("ui-state-hover"); }); $(".ui-jqgrid-bdiv table tr").hover(function(){ $(this).addClass("ui-state-hover"); },function(){ $(this).removeClass("ui-state-hover"); }); $(".ui-jqgrid-bdiv table tr input[type='checkbox']").bind("click",function(){ if ($(this).attr("checked")){ $("#" + $(this).attr("index")).addClass("ui-state-highlight"); }else{ $("#" + $(this).attr("index")).removeClass("ui-state-highlight"); } }); $(".ui-jqgrid-hbox table tr input[type='checkbox']").bind("click",function(){ if ($(this).attr("checked")){ $.each($(".ui-jqgrid-bdiv table tr input[type='checkbox']"),function(){ $(this).attr("checked","checked"); $("#" + $(this).attr("index")).addClass("ui-state-highlight"); }); }else{ $.each($(".ui-jqgrid-bdiv table tr input[type='checkbox']"),function(){ $(this).removeAttr("checked"); $("#" + $(this).attr("index")).removeClass("ui-state-highlight"); }); } }); }, errorHanldling:function(){// 错误处理 if (xjqGridUtils.isString(errObj)){ alert("错误信息:" + errObj); } } }; window.xjqGrid = xjqGrid; })(window);
xjqGridDemo1.0.html代码如下:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>xjqGrid Demo 1.0</title> </head> <link href="css/xjqGrid-1.0.css" rel="stylesheet" type="text/css" /> <script type="text/javascript" src="js/jquery-1.7.1.js"></script> <script type="text/javascript" src="js/xjqGrid-1.0.js"></script> <body> <div id="testXjqGrid"></div> </body> </html> <script type="text/javascript"> $(document).ready(function(){ xjqGrid.init({ targetId:"testXjqGrid", width:"700px", height:"250px", caption:"自己写的Grid [xjqGrid]", selectType:"checkbox", colNames:['Inv No','Date', 'Client', 'Amount','Tax','Total','Notes'], colModel:[ {name:'id',index:'id', width:60, sorttype:"int"}, {name:'invdate',index:'invdate', width:90, sorttype:"date"}, {name:'name',index:'name', width:100}, {name:'amount',index:'amount', width:80, align:"right",sorttype:"float"}, {name:'tax',index:'tax', width:80, align:"right",sorttype:"float"}, {name:'total',index:'total', width:80,align:"right",sorttype:"float"}, {name:'note',index:'note', width:150, sortable:false} ], gridData:[ {id:"1",invdate:"2007-10-01",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"2",invdate:"2007-10-02",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"3",invdate:"2007-09-01",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"}, {id:"4",invdate:"2007-10-04",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"5",invdate:"2007-10-05",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"6",invdate:"2007-09-06",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"}, {id:"7",invdate:"2007-10-04",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"8",invdate:"2007-10-03",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"9",invdate:"2007-09-01",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"} ] }).execute(); }); </script>
这里我定义了一个xjqGrid对象,这里我把xjqGrid使用的代码再贴出来,如下:
xjqGrid.init({ targetId:"testXjqGrid", width:"700px", height:"250px", caption:"自己写的Grid [xjqGrid]", selectType:"checkbox", colNames:['Inv No','Date', 'Client', 'Amount','Tax','Total','Notes'], colModel:[ {name:'id',index:'id', width:60, sorttype:"int"}, {name:'invdate',index:'invdate', width:90, sorttype:"date"}, {name:'name',index:'name', width:100}, {name:'amount',index:'amount', width:80, align:"right",sorttype:"float"}, {name:'tax',index:'tax', width:80, align:"right",sorttype:"float"}, {name:'total',index:'total', width:80,align:"right",sorttype:"float"}, {name:'note',index:'note', width:150, sortable:false} ], gridData:[ {id:"1",invdate:"2007-10-01",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"2",invdate:"2007-10-02",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"3",invdate:"2007-09-01",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"}, {id:"4",invdate:"2007-10-04",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"5",invdate:"2007-10-05",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"6",invdate:"2007-09-06",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"}, {id:"7",invdate:"2007-10-04",name:"test",note:"note",amount:"200.00",tax:"10.00",total:"210.00"}, {id:"8",invdate:"2007-10-03",name:"test2",note:"note2",amount:"300.00",tax:"20.00",total:"320.00"}, {id:"9",invdate:"2007-09-01",name:"test3",note:"note3",amount:"400.00",tax:"30.00",total:"430.00"} ] }).execute();
参数定义:
targetId:用于展示grid的div的id值;
width:设置grid的宽度;
height:设置grid的高度;
caption:设置grid的标题;
selectType:这个参数的值有三个1.checkbox,多选框,2.radio,单选框,3.none,没有选择框,现在只支持checkbox和none,radio的代码还没写;
colNames:设置grid的标题名称;
colModel:设置grid展示的字段;
gridData:设置grid展示的数据
使用方法很简单,先init一个javascript对象,然后调用execute()方法;实例代码我是init().execute(),其实先init()然后再xjqGrid.execute()也是可以的。
这个框架刚刚写,功能很单一,不过我认为架子出来了,如果想做什么新功能加进去就行,所以我在这里把代码分享下,希望感兴趣的童鞋多多指教。
运行的效果图如下:
代码下载链接:
http://files.cnblogs.com/sharpxiajun/xjqGrid.rar
转自:http://www.cnblogs.com/sharpxiajun/archive/2012/06/29/2569914.html