写了个类似TreeGrid的控件

来源:互联网 发布:网络割接是什么意思 编辑:程序博客网 时间:2024/05/17 07:03

最近公司要求写个类似TreeGrid的控件,先上效果图:
这里写图片描述

其实就是传入一个tree数据集合,将需要合并的数据进行合并展示。合并的列可能是一列也可能是多列。

这里写图片描述

提前申明 需要依赖jquery

调用代码:

  initQueryGrid:function(){        //获取表格展示的列        function getColumn() {            var arr = [                {display: "序号", width: 60, type: "sysOrderNum", name: null, textAlign: "center"},                {display: "分类", width: 180, type: "treeLevel", name: "type", textAlign: "center"},                {display: "流程模板名称", width: 129, type: "content", name: "workflowSubject", textAlign: "left"},                {display: "对应表单", width: 139, type: "content", name: "formSubject", textAlign: "left"},                {display: "所属人", width: '*', type: "content", name: "memberName", textAlign: "left"},                {display: "流程归属部门", width: 179, type: "content", name: "workflowDepartmentName", textAlign: "left"}            ];            return arr;        }        var grid = new GoTreeGrid({            parent: "queryGrid",            width: (document.body.clientWidth-228)*0.98,            managerName: "test",            managerMethod: "test",            colModel: getColumn()        });        grid.addTreeRows(returnVal);    },

组件代码如下:

//GoTreeGrid对象function GoTreeGrid(options) {    this.parent = options["parent"];    this.managerName = options["managerName"];    this.managerMethod = options["managerMethod"];    //放置后台列名称,主要是用于从后台返回数据中获取相应字段的值    this.colNames = [];    this.alignCols = [];    this.colTypes = [];    //每列的列宽    this.colWidths = [];    this.rowIndex = 0;    this.colIndex = 0;    this.levelColWid = 100;    this.tableId = __uid();    //当前所有列对应的宽度 包含分类列    this.curColWid = 0;    this.contentCols = [];    if (options["width"] && (options["width"] + "").indexOf("%") < 0) {        this.pWidth = parseFloat(options["width"]);    } else {        //如果为空则设置为100%        if(options["width"]==null){            options["width"]='100%';        }        $('<table class="goTreeGrid" id="test_header" style="width: '+options["width"]+'%"><tbody><tr><td>#</td></tr></tbody></table>').appendTo($("#" + this.parent));        this.pWidth = $("#test_header").get(0).offsetWidth;        $("#test_header").remove();        alert( this.pWidth)    }    //初始化标头数组    this.columns = this.initTreeLevels(options["colModel"]);    this.starsCols = [];    this._createGridHeader();    this._createGridBody();    ////表格的头进行合并操作后,会有像素差,所有需要进行修正    if (_isIE8) {        this._initColspanWidth();    }}/** * 动态追加5列 层级作为分类使用 * @param colModels * @returns {Array} */GoTreeGrid.prototype.initTreeLevels = function (colModels) {    var newColumns = [];    this.conStartColNum = 0;    for (var num = 0; num < colModels.length; num++) {        newColumns.push(colModels[num]);        if (colModels[num]["type"] == "treeLevel") {            this.levelColWid = colModels[num]["width"];            this.addNewColspan(newColumns, 5);            this.conStartColNum = num + 5;        }    }    return newColumns;}GoTreeGrid.prototype.addNewColspan = function (newColumns, nums) {    for (var num = 0; num < nums; num++) {        newColumns.push({display: "#cspan", width: 0, type: "colspanCol", name: null, textAlign: "center"})    }}/* * 表格的头进行合并操作后,会有像素差,所有需要进行修正 * */GoTreeGrid.prototype._initColspanWidth = function () {    var gridObj = this;    $(".header td").each(function () {        var colSpan = $(this).prop("colspan");        if (colSpan != null && colSpan > 1) {            var colIndex = $(this).attr("colIndex");            var oldWidth = gridObj.colWidths[colIndex - 1];            $($(this).parent().prev().find("th").get(colIndex - 1)).css("width", parseFloat(oldWidth) + parseFloat((colSpan - 2)));        }    })}//创建grid表格头GoTreeGrid.prototype._createGridHeader = function () {    var gridObj = this;    var htmls = [], headerLabel = [], headerLabels = []    htmls.push('<table class="goTreeGrid" style="table-layout: fixed;width:' + this.pWidth + 'px;" id="' + this.tableId + '_header"  cellpadding="0" cellspacing="0" ><tbody>');    htmls.push('<tr style="height: auto;">');    $.each(this.columns, function (index, item) {        if (item["type"] === "content") {            gridObj.contentCols.push(item);        }        //获取每列的列宽        var colWidth = gridObj.getColWidth(item["width"], index);        //缓存起每列的列宽信息        gridObj.colWidths.push(colWidth);        gridObj.colNames.push(item["name"]);        if (item["type"] == "colspanCol") {            htmls.push('<th class="colspanCol" colIndex="' + (index + 1) + '" style="height: 0px; width: ' + colWidth + 'px;"></th>');        } else {            htmls.push('<th colIndex="' + (index + 1) + '" style="height: 0px; width: ' + colWidth + 'px;"></th>');        }    });    htmls.push('</tr>');    htmls.push('<tr class="header">');    $.each(this.columns, function (index, item) {        gridObj.colIndex = ++gridObj.colIndex;        var textStr = item["textAlign"] ? "style='text-align:" + item["textAlign"] + "'" : "";        //将字体的摆放位置缓存起来        gridObj.alignCols.push(textStr);        //将每列的数据类型存放起来        gridObj.colTypes.push(item["type"] || "field");        if (item["display"] === "#cspan") {            htmls.push('<td colIndex="' + (index + 1) + '" class="_cspan_col" ' + textStr + '><div>' + item["display"] + '</div></td>');        } else {            htmls.push('<td colIndex="' + (index + 1) + '" ' + textStr + '><div>' + item["display"] + '</div></td>');        }    });    htmls.push('</tr>');    htmls.push('</tbody></table>');    $(htmls.join("")).appendTo($("#" + this.parent));    ////如果传入的列中包含*号的列 则需要重新计算    if (this.starsCols.length > 0) {        this._initStartsColWidth();    }    this._initHeaderLabel();}/* * 初始化表格头的label 因为可能存在列头的合并操作 * */GoTreeGrid.prototype._initHeaderLabel = function () {    $("._cspan_col").each(function () {        var prevObj = $(this).prev();        var colSpan = prevObj.attr("colspan") || 1;        prevObj.attr("colSpan", ++colSpan);        $(this).remove();    });}/* * 因为有列宽设置了* 则需要重新计算*号对应的列 需要将剩余的宽度都分给相应的*号列 * */GoTreeGrid.prototype._initStartsColWidth = function () {    //只有有剩余列宽才需要重新计算    var gridObj = this;    var syWid = parseFloat(this.pWidth) - this.curColWid;    if (syWid > 0) {        var colSyWid = syWid / this.starsCols.length;        var newWidth = (100 + colSyWid);        $.each(this.starsCols, function (index, colIndex) {            $($("#" + gridObj.tableId + '_header').find("th").get(colIndex)).css("width", newWidth + "px");            gridObj.colWidths[colIndex] = newWidth;            newWidth = null;        })    }}//获取列宽GoTreeGrid.prototype.getColWidth = function (width, colIndex) {    if (width == parseFloat(width)) {        this.curColWid = this.curColWid + parseFloat(width) + 1;        return width;    } else {        this.starsCols.push(colIndex);        this.curColWid = this.curColWid + parseFloat(100);        return 100;    }}GoTreeGrid.prototype._createGridBody = function () {    var gridObj = this;    var htmls = [];    var headerHt = $($("#" + this.tableId + '_header').find("tr").get(0));    htmls.push('<table style="table-layout: fixed;width:' + this.pWidth + 'px;" class="goTreeGridBody" id="' + this.tableId + '_body"  cellpadding="0" cellspacing="0" ><tbody>');    htmls.push('<tr style="height: auto;">' + headerHt.html() + '</tr>');    htmls.push('</tbody></table>');    $(htmls.join("")).appendTo($("#" + this.parent));    //如果传入的列中包含*号的列 则需要重新计算    if (this.starsCols.length > 0) {        this._initStartsColWidth();    }}//添加一行数据GoTreeGrid.prototype.addRow = function (rowsData) {    var htmls = [];    this._addRow(htmls, [rowsData], 0);    $(htmls.join()).appendTo($("#" + this.tableId + '_body'))}GoTreeGrid.prototype.getEmptyRow = function (rowsData) {    var htmls = [];    for (var num = 0; num < this.colNames.length; num++) {        htmls.push(" ");    }    return htmls.join("");}GoTreeGrid.prototype.addEmptyRow = function (rowSize) {    var htmls = [];    var rowIds = [];    for (var num = 0; num < rowSize; num++) {        rowIds.push(this._addRow(htmls, [this.getEmptyRow()], 0));    }    $(htmls.join("")).appendTo($("#" + this.tableId + '_body'));    return rowIds;}/* * 添加行数据 * */GoTreeGrid.prototype._addRow = function (htmls, rowsDataAry, rowIndex) {    this.rowIndex = ++this.rowIndex;    var odd = this.rowIndex % 2 == 1 ? "even" : "odd";    var rowId = __uid();    var gridObj = this;    htmls.push('<tr class="dataTr ' + odd + '" id="' + rowId + '" rowIndex="' + this.rowIndex + '">');    $.each(rowsDataAry[rowIndex], function (index, item) {        //获取当前列的 字体摆放样式        var colStyle = gridObj.alignCols[index];        //获取当前列的类型        var curColType = gridObj.colTypes[index];        if (curColType == "sysOrderNum") {            htmls.push('<td id="' + rowId + '_' + index + '" ' + colStyle + '><div>' + gridObj.rowIndex + '</div></td>');        } else {            htmls.push('<td id="' + rowId + '_' + index + '" ' + colStyle + '><div>' + item + '</div></td>');        }    });    htmls.push('</tr>');    gridObj = null;    htmls = null;    return rowId;}//添加多行数据GoTreeGrid.prototype.addRows = function (rowsDataAry) {    var htmls = [];    for (var num = 0; num < rowsDataAry.length; num++) {        this._addRow(htmls, rowsDataAry, num);    }    $(htmls.join()).appendTo($("#" + this.tableId + '_body'))}/* * 根据colNum来进行列分组操作 * */function rowSpanToPre(trObjs, startNum, colIndex, index) {    if (startNum - 2 - index >= 0) {        var theLastTrId = $(trObjs[startNum - 1 - index]).attr("id");        var theLastTd = $("#" + theLastTrId + "_" + colIndex);        var preTrId = $(trObjs[startNum - 2 - index]).attr("id");        var preTd = $("#" + preTrId + "_" + colIndex);        if (theLastTd.html() != null && theLastTd.html() == preTd.html()) {            preTd.attr("rowspan", parseFloat(parseFloat(theLastTd.attr("rowspan") || 1) + parseFloat(preTd.attr("rowspan") || 1)));            theLastTd.remove();        }    }}/* * 对行内内容进行分组 * */GoTreeGrid.prototype.groupBy = function (colIndex) {    var trObjs = $("#" + this.tableId + '_body .dataTr');    var startNum = trObjs.length;    var index = 0;    for (var num = startNum; num >= 0; num--) {        rowSpanToPre(trObjs, startNum, colIndex, index);        index = index + 1;    }};/* * 添加数据进body * */GoTreeGrid.prototype._addRowToBody = function (para) {    //加载数据    this.populate(para);};/* ajax数据加载 * */GoTreeGrid.prototype.ajaxgridLoad = function (para) {    //加载数据    this.populate(para);};GoTreeGrid.prototype.populate = function (tempMap, backFun) { // get latest data    if (this.loading) {        return true;    }    var pageSize = ($.ctx && $.ctx._pageSize) ? $.ctx._pageSize : 20;    var fp = {        page: 1,        size: pageSize    };    var gridObj = this;    this.loading = true;    callBackendMethod(this.managerName, this.managerMethod, tempMap, {        success: function (returnVal) {            //gridObj.addRows(returnVal);            if (backFun != null) {                backFun();            } else {                gridObj.addTreeRows(returnVal);            }        }    });};GoTreeGrid.prototype._getNodeMaxSize = function (jsonObj) {    return jsonObj["allCount"];};GoTreeGrid.prototype.getMaxRecordSize = function (itemObj, sonFields, jsonObj) {    var sonList = itemObj[sonFields];    var obj = this;    if (sonList != null && sonList.length > 0) {        if (sonList.length > jsonObj["maxRecordSize"]) {            jsonObj["maxRecordSize"] = sonList.length;        }        $.each(sonList, function (index, item) {            obj.getMaxRecordSize(item, sonFields, jsonObj);        });    }};GoTreeGrid.prototype._addSonTreeRows = function (treeObj, sonFields, rowIds, parentNode) {    var marRowSize = this._getNodeMaxSize(treeObj, sonFields, treeObj);    var startNum = parentNode["startNum"];    for (var num1 = startNum; num1 < startNum + marRowSize; num1++) {        $("#" + rowIds[num1] + "_" + treeObj["level"]).html(treeObj["name"]);        ++parentNode["startNum"];        var obj = this;        treeObj["startNum"] = 0;        var sonList = treeObj[sonFields];        if (sonList != null && sonList.length > 0) {            $.each(sonList, function (index, item) {                if (item.type == "category") {                    obj._addSonTreeRows(item, sonFields, rowIds, treeObj);                } else {                    //如果是模板界面 则需要加载模板字段信息                    for (var cols = 0; cols < obj.contentCols.length; cols++) {                        obj.setCellValue(rowIds[startNum] + "_" + obj.getContentColIndex(cols), obj.getContent(item, cols));                    }                }                treeObj["startNum"] = ++treeObj["startNum"];            });        }    }};GoTreeGrid.prototype._addTreeRows = function (treeObj, sonFields) {    treeObj["startNum"] = 0;    treeObj["maxRecordSize"] = 1;    var marRowSize = this._getNodeMaxSize(treeObj, sonFields, treeObj);    var rowIds = this.addEmptyRow(3);    for (var num1 = 0; num1 < rowIds.length; num1++) {        $("#" + rowIds[num1] + "_" + treeObj["level"]).html(treeObj["name"]);    }    var obj = this;    var sonList = treeObj[sonFields];    if (sonList != null && sonList.length > 0) {        $.each(sonList, function (index, item) {            if (item.type == "category") {                obj._addSonTreeRows(item, sonFields, rowIds, treeObj);            } else {                //如果是模板界面 则需要加载模板字段信息                for (var cols = 0; cols < obj.contentCols.length; cols++) {                    obj.setCellValue(rowIds[treeObj["startNum"]] + "_" + obj.getContentColIndex(cols), obj.getContent(item, cols));                }            }        });    }};/* * 根据序号获取当前对象对应字段的值 * */GoTreeGrid.prototype.getContent = function (itemobj, cols) {    var field = this.contentCols[cols];    return itemobj[field["name"]];};GoTreeGrid.prototype.getContentColIndex = function (cols) {    return parseFloat(this.conStartColNum) + cols + 1;};/* * 设置cell的value * */GoTreeGrid.prototype.setCellValue = function (cellId, cellContent) {    if (cellContent == null || cellContent == "null") {        cellContent = "";    }    $("#" + cellId).html(cellContent);};/** * 获取当前行数据 从json对象中获取 * @param jsonObj */GoTreeGrid.prototype.getRowData = function (jsonObj) {};GoTreeGrid.prototype.getMaxLevel = function (itemObj, sonFields) {    if (this.datas[itemObj["level"]] == null) {        this.datas[itemObj["level"]] = [];    }    this.datas[itemObj["level"]].push(itemObj);    var obj = this;    var sonList = itemObj[sonFields];    if (sonList != null && sonList.length > 0) {        var sonLevel = itemObj["level"] + 1;        if (sonLevel > obj.level) {            obj.level = sonLevel;        }        $.each(sonList, function (index, item) {            item["level"] = sonLevel;            obj.getMaxLevel(item,sonFields);        });    }};/** * 清空所有数据 并将表格信息还原 * @param jsonObj */GoTreeGrid.prototype.clearAll = function () {    var index = 0;    //只有body的行数大于1 才需要进行移除操作    if ($("#" + this.tableId + "_body tr").length > 1) {        $("#" + this.tableId + "_body tr").each(function (els) {            if (index != 0) {                $(this).remove();            }            index++;        })    }    //重新定义列表头信息    this._initThAgain(this.typeLevel - 1, 0);};GoTreeGrid.prototype.addTreeRows = function (treeRecords) {    this.clearAll();    var obj = this;    obj.typeLevel = 1;    this.datas = {};    this.level = 0;    //循环计算出最大的层级    $.each(treeRecords, function (index, itemObj) {        treeRecords[index]["level"] = 1;        obj.getMaxLevel(treeRecords[index], "childWorkflowPropertyList");    });    //如果层级大于3 是需要进行特殊显示处理。 类别的层级为最大层级减1    if (obj.level > 1) {        obj.typeLevel = obj.level - 1;        obj._initThAgain(this.typeLevel - 1, obj.levelColWid);    }    $.each(treeRecords, function (index, itemObj) {        obj._addTreeRows(treeRecords[index], "childWorkflowPropertyList");    });    //对分类信息进行分组操作。    for (var num = 1; num <= obj.typeLevel; num++) {        obj.groupBy(num);    }};/** * 重新定义表格头的信息 * @private */GoTreeGrid.prototype._initThAgain = function (colspanCols, colspanWidth) {    //调整colspan信息    var colSpanCols = $("#" + this.tableId + "_header").find(".colspanCol");    for (var num = 0; num < colspanCols; num++) {        //如果传入的宽度 不等于本身宽度 则需要进行修改        var elOldWid = $(colSpanCols.get(num)).css("width");        if (elOldWid != colspanWidth) {            $(colSpanCols.get(num)).css("width", colspanWidth);            //计算this.curColWid的目的是 为了重新计算*号列的列宽            this.curColWid = this.curColWid + parseFloat(colspanWidth);        }    }    //重新计算*号对应的列宽    this._initStartsColWidth();    var headerHt = $($("#" + this.tableId + '_header').find("tr").get(0));    //移除以前的标头信息 再追加最新th信息    $($("#" + this.tableId + "_body").find("tr").get(0)).remove();    $('<tr style="height: auto;">' + headerHt.html() + '</tr>').appendTo($("#" + this.tableId + "_body tbody"));};
阅读全文
0 0
原创粉丝点击