/** * Created by Zhong on 2018/1/19. **/ const locked = lockUtil.getLocked(); $(document).ready(function () { feeItemObj.buildSheet(); const lockedSpreads = [feeItemObj.workBook, sectionObj.workBook, feeRuleObj.workBook]; lockUtil.lockSpreads(lockedSpreads, locked); $("#sectionTreeModal").on("shown.bs.modal", function (e) { batchSectionObj.workBook.refresh(); //bind confirm btn batchSectionObj.onConfirmBtn(); }); $("#sectionTreeModal").on("hidden.bs.modal", function () { batchSectionObj.clearChecked(); }); $("#delConfirm").click(function () { if (curDeleteType === feeItemObj.deleteType) { let me = feeItemObj, se = sectionObj, fr = feeRuleObj; let fiPostData = [], sePostData = []; let sels = me.workBook.getSheet(0).getSelections(); for (let i = 0, len = sels.length; i < len; i++) { let sel = sels[i]; //delete if (sel.colCount === me.setting.header.length) { for (let j = 0, jLen = sel.rowCount; j < jLen; j++) { let row = sel.row + j; let feeItem = me.cache[row]; //有数据,删除数据 if (me.isDef(feeItem)) { fiPostData.push({ updateType: me.updateType.update, updateData: { ID: feeItem.ID, deleted: true } }); //delete feeItem section for (let section of feeItem.section) { sePostData.push({ updateType: me.updateType.update, updateData: { ID: section.ID, deleted: true } }); } } } //front delete me.cache.splice(sel.row, sel.rowCount); } } //update currentFeeItem me.currentFeeItem = me.getCurrentData(me.sheet, me.cache); se.cache = me.isDef(me.currentFeeItem) ? me.currentFeeItem.section : []; if (fiPostData.length > 0) { me.updateFeeItem(fiPostData, function () { me.sheet.setRowCount(me.cache.length + 10); sheetCommonObj.showData(me.sheet, me.setting, me.cache); $("#delAlert").modal("hide"); }); if (sePostData.length > 0) { se.updateSection(sePostData); } sheetCommonObj.cleanData(se.sheet, se.setting, 10); sheetCommonObj.cleanData(fr.sheet, fr.setting, 10); } else { $("#delAlert").modal("hide"); } } else if (curDeleteType === sectionObj.deleteType) { let me = sectionObj, fi = feeItemObj, fr = feeRuleObj; let sePostData = [], fiPostData = []; let sels = me.workBook.getSheet(0).getSelections(); for (let i = 0, len = sels.length; i < len; i++) { let sel = sels[i]; //delete // if (sel.colCount === me.setting.header.length) { for (let j = 0, jLen = sel.rowCount; j < jLen; j++) { let row = sel.row + j; let section = me.cache[row]; //有数据,删除数据 if (me.isDef(section)) { sePostData.push({ updateType: me.updateType.del, updateData: { ID: section.ID, deleted: true } }); fiPostData.push({ updateType: me.updateType.update, updateData: { ID: fi.currentFeeItem.ID, $pull: { section: { ID: section.ID } } } }); } } //front delete me.cache.splice(sel.row, sel.rowCount); // } } //update currentSection me.currentSection = fi.getCurrentData(me.sheet, me.cache); fr.cache = me.isDef(me.currentSection) ? me.currentSection.feeRule : []; if (sePostData.length > 0) { me.updateSection(sePostData, function () { me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); $("#delAlert").modal("hide"); }); if (fiPostData.length > 0) { fi.updateFeeItem(fiPostData); } sheetCommonObj.cleanData(fr.sheet, fr.setting, 10); } else { $("#delAlert").modal("hide"); } } }); }); let curDeleteType = null; //费用项 let feeItemObj = { rationRepId: null, workBook: null, sheet: null, cache: [], currentFeeItem: null, feeType: { ZM: "子目费用", FX: "分项费用", CS: "措施费用" }, updateType: { update: "update", new: "new" }, deleteType: "feeItem", setting: { header: [ { headerName: "费用项", headerWidth: 200, dataCode: "feeItem", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center" }, { headerName: "费用类型", headerWidth: 80, dataCode: "feeType", dataType: "String", hAlign: "center", vAlign: "center" }, { headerName: "记取位置", headerWidth: 100, dataCode: "position", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center" }, { headerName: "序号", headerWidth: 50, dataCode: "seq", dataType: "Number", hAlign: "center", vAlign: "center" }, ], view: { lockColumns: [] }, comboItems: { feeType: ["子目费用", "分项费用", "措施费用"] }, options: { tabStripVisible: false, allowCopyPasteExcelStyle: false, allowExtendPasteRange: true, allowUserDragDrop: false, allowUserDragFill: false, scrollbarMaxAlign: true, }, }, isDef: function (v) { return v !== undefined && v !== null; }, //sheet things setOptions: function (workbook, opts) { for (let opt in opts) { workbook.options[opt] = opts[opt]; } }, setCombo: function (sheet, col, comboItems) { let combo = sheetCommonObj.getDynamicCombo(); combo.items(comboItems).editable = false; sheet.getRange(-1, col, -1, 1).cellType(combo); }, getCurrentData: function (sheet, cache) { let acRow = sheet.getActiveRowIndex(); return this.isDef(cache[acRow]) ? cache[acRow] : null; }, buildSheet: function () { let me = this, se = sectionObj, fr = feeRuleObj, bs = batchSectionObj; if (!this.isDef(this.workBook)) { this.workBook = sheetCommonObj.buildSheet($("#feeItemSpread")[0], this.setting, 10); this.sheet = this.workBook.getActiveSheet(); sheetCommonObj.bindEscKey(this.workBook, [{ sheet: this.sheet, editStarting: me.onEditStarting, editEnded: me.onEditEnded }]); this.setOptions(this.workBook, this.setting.options); this.sheet.options.clipBoardOptions = GC.Spread.Sheets.ClipboardPasteOptions.values; this.bindEvents(this.sheet); this.rationRepId = parseInt(getQueryString("repository")); //init combo this.setCombo(this.sheet, 1, this.setting.comboItems.feeType); //init sectionSpread se.buildSheet(); //init feeRuleSpread fr.buildSheet(); //init installation this.getInstallation(this.rationRepId, function (rstData) { me.cache = rstData; me.sheet.setRowCount(me.cache.length + 10); sheetCommonObj.showData(me.sheet, me.setting, me.cache); me.initSelection(me.cache[0]); }); //init batchSectionSpread bs.getSectionTree(this.rationRepId); } }, bindEvents: function (sheet) { let me = this; const Events = GC.Spread.Sheets.Events; sheet.bind(Events.SelectionChanged, me.onSelectionChanged); sheet.bind(Events.EnterCell, me.onEnterCell); sheet.bind(Events.EditStarting, me.onEditStarting); sheet.bind(Events.EditEnded, me.onEditEnded); sheet.bind(Events.ClipboardPasting, me.onClipboardPasting); sheet.bind(Events.ClipboardPasted, me.onClipboardPasted); me.feeItemDelOpr(); }, initSelection: function (feeItem) { let me = this, se = sectionObj, fr = feeRuleObj; sheetCommonObj.cleanSheet(se.sheet, se.setting, -1); sheetCommonObj.cleanSheet(fr.sheet, fr.setting, -1); if (!me.isDef(feeItem)) { me.workBook.focus(true); me.currentFeeItem = null; se.cache = []; return; } fr.addObj = null; fr.updateObj = null; me.currentFeeItem = feeItem; se.cache = me.currentFeeItem.section; se.sheet.setRowCount(se.cache.length + 5); sheetCommonObj.showData(se.sheet, se.setting, se.cache); se.initSelection(se.cache[0]); me.workBook.focus(true); }, onSelectionChanged: function (sender, info) { let me = feeItemObj; if (!info.oldSelections || (info.oldSelections.length === 0 && info.newSelections.length > 0) || info.oldSelections[0].row !== info.newSelections[0].row) { let row = info.newSelections[0].row; let node = me.cache[row]; me.initSelection(node); } }, onEnterCell: function (sender, args) { let me = feeItemObj; me.sheet.repaint(); }, onEditStarting: function (sender, args) { let me = feeItemObj; //费用类型为子目时,记取位置不可编辑 let feeItem = me.cache[args.row]; if (me.isDef(feeItem) && (feeItem.feeType === me.feeType.ZM || !me.isDef(feeItem.feeType) || feeItem.feeType == "") && args.col === 2) { args.cancel = true; } }, onEditEnded: function (sender, args) { debugger; let me = feeItemObj, se = sectionObj; let v = me.isDef(args.editingText) ? args.editingText.toString().trim() : ""; let feeItem = me.cache[args.row]; let updateObj = { updateType: "", updateData: {} }; //update if (me.isDef(feeItem)) { feeItem[me.setting.header[args.col]["dataCode"]] = !me.isDef(feeItem[me.setting.header[args.col]["dataCode"]]) ? "" : feeItem[me.setting.header[args.col]["dataCode"]]; if (v == feeItem[me.setting.header[args.col]["dataCode"]]) { return; } updateObj.updateType = me.updateType.update; //当费用类型切换为子目费用时,自动清空记取位置 if (args.col === 1 && v === me.feeType.ZM) { feeItem.position = ""; args.sheet.setValue(args.row, 2, ""); updateObj.updateData.position = ""; } feeItem[me.setting.header[args.col]["dataCode"]] = v; updateObj.updateData.ID = feeItem.ID; updateObj.updateData[me.setting.header[args.col]["dataCode"]] = v; } //insert else { if (v === "") { return; } updateObj.updateType = me.updateType.new; updateObj.updateData[me.setting.header[args.col]["dataCode"]] = v; updateObj.updateData.rationRepId = me.rationRepId; updateObj.updateData.ID = uuid.v1(); updateObj.updateData.section = []; me.cache.push(updateObj.updateData); me.currentFeeItem = updateObj.updateData; se.cache = me.currentFeeItem.section; } me.sheet.setRowCount(me.cache.length + 10); sheetCommonObj.showData(me.sheet, me.setting, me.cache); //ajax me.updateFeeItem([updateObj]); }, onClipboardPasting: function (sender, info) { let me = feeItemObj; if (info.cellRange.col + info.cellRange.colCount > me.setting.header.length) { info.cancel = true; } }, onClipboardPasted: function (sender, info) { let me = feeItemObj, se = sectionObj; let postData = []; let items = sheetCommonObj.analyzePasteData(me.setting, info); for (let i = 0, len = items.length; i < len; i++) { let row = info.cellRange.row + i; let feeItem = me.cache[row]; //update if (me.isDef(feeItem)) { if (me.validData(items[i])) { for (let attr in items[i]) { feeItem[attr] = items[i][attr]; } postData.push(me.getUpdateObj(me.updateType.update, feeItem)); } } //insert else { if (me.validData(items[i])) { items[i].ID = uuid.v1(); items[i].rationRepId = me.rationRepId; items[i].section = []; postData.push(me.getUpdateObj(me.updateType.new, items[i])); me.cache.push(items[i]); } } } //update currentFeeItem me.currentFeeItem = me.getCurrentData(me.sheet, me.cache); se.cache = me.currentFeeItem.section; me.sheet.setRowCount(me.cache.length + 10); sheetCommonObj.showData(me.sheet, me.setting, me.cache); if (postData.length > 0) { //ajax then refresh me.updateFeeItem(postData); } }, feeItemDelOpr: function () { if (locked) { return; } let me = this; me.workBook.commandManager().register("feeItemDel", function () { curDeleteType = me.deleteType; let sels = me.workBook.getSheet(0).getSelections(); for (let i = 0, len = sels.length; i < len; i++) { let sel = sels[i]; //delete if (sel.colCount === me.setting.header.length) { $("#delAlert").modal("show"); break; } } }); me.workBook.commandManager().setShortcutKey(null, GC.Spread.Commands.Key.del, false, false, false, false); me.workBook.commandManager().setShortcutKey("feeItemDel", GC.Spread.Commands.Key.del, false, false, false, false); }, getUpdateObj: function (updateType, data) { let rst = { updateType: "", updateData: {} }; rst.updateType = updateType; for (let attr in data) { rst.updateData[attr] = data[attr]; } return rst; }, validData: function (pasteData) { if (this.isDef(pasteData.feeType)) { if (this.setting.comboItems.feeType.indexOf(pasteData.feeType) < 0) { return false; } //费用类型为子目时,不可有记取位置 if (pasteData.feeType === this.feeType.ZM && this.isDef(pasteData.position) && pasteData.position !== "") { return false; } } return true; }, getInstallation: function (rationRepId, callback) { let me = this; CommonAjax.post("/rationRepository/api/getInstallation", { rationRepId: rationRepId }, function (rstData) { // 数据排序 CSL console.log(rstData); rstData.sort((a, b) => a.seq - b.seq); for (const item of rstData) { const section = item.section; section.sort((a, b) => a.seq - b.seq); } console.log(rstData); me.cache = rstData; if (callback) { callback(rstData); } }); }, updateFeeItem: function (updateData, callback) { let me = this; CommonAjax.post("/rationRepository/api/updateFeeItem", { updateData: updateData }, function (rstData) { if (callback) { callback(); } }); }, }; //分册章节 let sectionObj = { workBook: null, sheet: null, cache: [], currentSection: null, updateType: { update: "update", new: "new", del: 'delete' }, deleteType: "section", setting: { header: [ { headerName: "分册章节", headerWidth: 330, dataCode: "name", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center" }, { headerName: "序号", headerWidth: 50, dataCode: "seq", dataType: "Number", hAlign: "center", vAlign: "center" }, ], view: { lockColumns: [] }, options: { tabStripVisible: false, allowCopyPasteExcelStyle: false, allowExtendPasteRange: true, allowUserDragDrop: false, allowUserDragFill: false, scrollbarMaxAlign: true, }, }, isDef: function (v) { return v !== undefined && v !== null; }, //sheet things setOptions: function (workbook, opts) { for (let opt in opts) { workbook.options[opt] = opts[opt]; } }, renderFunc: function (sheet, func) { sheet.suspendPaint(); sheet.suspendEvent(); if (this.isFunc(func)) { func(); } sheet.resumePaint(); sheet.resumeEvent(); }, buildSheet: function () { if (!this.isDef(this.workBook)) { this.workBook = sheetCommonObj.buildSheet($("#instSectionSpread")[0], this.setting, 10); this.sheet = this.workBook.getActiveSheet(); sheetCommonObj.bindEscKey(this.workBook, [{ sheet: this.sheet, editStarting: this.onEditStarting, editEnded: this.onEditEnded }]); this.setOptions(this.workBook, this.setting.options); this.sheet.options.clipBoardOptions = GC.Spread.Sheets.ClipboardPasteOptions.values; this.bindEvents(this.sheet); } }, bindEvents: function (sheet) { let me = sectionObj; const Events = GC.Spread.Sheets.Events; sheet.bind(Events.SelectionChanged, me.onSelectionChanged); sheet.bind(Events.EditStarting, me.onEditStarting); sheet.bind(Events.EditEnded, me.onEditEnded); sheet.bind(Events.ClipboardPasting, me.onClipboardPasting); sheet.bind(Events.ClipboardPasted, me.onClipboardPasted); me.sectionDelOpr(); me.onContextmenuOpr(); }, initSelection: function (section) { let me = sectionObj, fr = feeRuleObj; sheetCommonObj.cleanSheet(fr.sheet, fr.setting, -1); this.workBook.focus(true); if (!this.isDef(section)) { me.currentSection = null; return; } me.currentSection = section; fr.addObj = null; fr.updateObj = null; fr.cache = section.feeRule; fr.sheet.setRowCount(fr.cache.length + 5); sheetCommonObj.showData(fr.sheet, fr.setting, fr.cache); }, onContextmenuOpr: function () { let me = this; $.contextMenu({ selector: "#instSectionSpread", build: function ($triggerElement, e) { //控制允许右键菜单在哪个位置出现 let sheet = me.sheet; let offset = $("#instSectionSpread").offset(), x = e.pageX - offset.left, y = e.pageY - offset.top; let target = sheet.hitTest(x, y); if (target.hitTestType === 3 && me.isDef(target.row) && me.isDef(target.col)) { //在表格内 sheet.setActiveCell(target.row, target.col); me.initSelection(me.cache[target.row]); return { callback: function () {}, items: { ref: { name: "批量关联至定额", disabled: function () { const inValidCell = !commonUtil.isDef(target.row) || !commonUtil.isDef(target.col); const inValidData = target.row >= me.cache.length; return locked || inValidCell || inValidData; }, icon: "fa-arrow-left", callback: function (key, opt) { $("#sectionTreeModal").modal("show"); }, }, del: { name: "删除章节", disabled: function () { const inValidCell = !commonUtil.isDef(target.row) || !commonUtil.isDef(target.col); const inValidData = target.row >= me.cache.length; return locked || inValidCell || inValidData; }, icon: "fa-times", callback: function (key, opt) { curDeleteType = me.deleteType; $("#delAlert").modal("show"); }, }, }, }; } else { return false; } }, }); }, onSelectionChanged: function (sender, info) { let me = sectionObj; if ((info.oldSelections && info.oldSelections.length === 0 && info.newSelections.length > 0) || info.oldSelections[0].row !== info.newSelections[0].row) { let row = info.newSelections[0].row; let section = me.cache[row]; me.initSelection(section); } }, onEditStarting: function (sender, args) { let me = sectionObj, fi = feeItemObj; if (!me.isDef(fi.currentFeeItem)) { args.cancel = true; } }, onEditEnded: function (sender, args) { let me = sectionObj, fi = feeItemObj, fr = feeRuleObj; let v = me.isDef(args.editingText) ? args.editingText.toString().trim() : ""; let section = me.cache[args.row]; let updateObj = { updateType: "", updateData: {} }; //update if (me.isDef(section)) { debugger; updateObj.updateType = me.updateType.update; updateObj.updateData.ID = section.ID; if (args.col === 0) { section.name = !me.isDef(section.name) ? "" : section.name; if (section.name === v) { return; } if (v === "") { me.sheet.setValue(args.row, args.col, section.name); return; } section.name = v; updateObj.updateData.name = v; } else if (args.col === 1) { section.seq = !me.isDef(section.seq) ? "" : section.seq; if (section.seq === v) { return; } if (v === "") { me.sheet.setValue(args.row, args.col, section.seq); return; } section.seq = v; updateObj.updateData.seq = v; } } //insert else { if (v === "") { return; } updateObj.updateType = me.updateType.new; updateObj.updateData.ID = uuid.v1(); updateObj.updateData.rationRepId = fi.rationRepId; updateObj.updateData.name = v; updateObj.updateData.feeItemId = fi.currentFeeItem.ID; updateObj.updateData.feeRule = []; me.cache.push(updateObj.updateData); me.currentSection = updateObj.updateData; fr.cache = me.currentSection.feeRule; } me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); me.updateSection([updateObj]); fi.updateFeeItem([{ updateType: fi.updateType.update, updateData: { ID: fi.currentFeeItem.ID, $addToSet: { section: { ID: updateObj.updateData.ID } } } }]); }, onClipboardPasting: function (sender, info) { let me = sectionObj, fi = feeItemObj; if (info.cellRange.col + info.cellRange.colCount > me.setting.header.length || !me.isDef(fi.currentFeeItem)) { info.cancel = true; } }, onClipboardPasted: function (sender, info) { let me = sectionObj, fi = feeItemObj, fr = feeRuleObj; let sePostData = [], fiPostData = []; let items = sheetCommonObj.analyzePasteData(me.setting, info); for (let i = 0, len = items.length; i < len; i++) { let row = info.cellRange.row + i; let section = me.cache[row]; //update if (me.isDef(section)) { section.name = items[i].name; let updateObj = { updateType: me.updateType.update, updateData: { ID: section.ID, name: items[i].name } }; sePostData.push(updateObj); } //insert else { let updateObj = { updateType: me.updateType.new, updateData: { ID: uuid.v1(), rationRepId: fi.rationRepId, name: items[i].name, feeItemId: fi.currentFeeItem.ID, feeRule: [] }, }; sePostData.push(updateObj); me.cache.push(updateObj.updateData); fiPostData.push({ updateType: fi.updateType.update, updateData: { ID: fi.currentFeeItem.ID, $addToSet: { section: { ID: updateObj.updateData.ID } } }, }); } } //update currentSection me.currentSection = fi.getCurrentData(me.sheet, me.cache); fr.cache = me.currentSection.feeRule; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); if (sePostData.length > 0) { me.updateSection(sePostData); if (fiPostData.length > 0) { fi.updateFeeItem(fiPostData); } } }, sectionDelOpr: function () { if (locked) { return; } let me = this; me.workBook.commandManager().register("sectionDel", function () { curDeleteType = me.deleteType; let sels = me.workBook.getSheet(0).getSelections(); for (let i = 0, len = sels.length; i < len; i++) { let sel = sels[i]; //delete if (sel.colCount === me.setting.header.length) { $("#delAlert").modal("show"); break; } } }); me.workBook.commandManager().setShortcutKey(null, GC.Spread.Commands.Key.del, false, false, false, false); me.workBook.commandManager().setShortcutKey("sectionDel", GC.Spread.Commands.Key.del, false, false, false, false); }, updateSection: function (updateData, callback) { CommonAjax.post("/rationRepository/api/updateSection", { updateData: updateData, libID: feeItemObj.rationRepId }, function (rstData) { if (callback) { callback(); } }); }, }; //费用规则 let feeRuleObj = { workBook: null, sheet: null, addObj: null, updateObj: null, avtiveCell: { row: 0, col: 0 }, cache: [], base: { RCJ: "分别按人材机乘系数", RG: "人工", CL: "材料", JX: "机械" }, setting: { header: [ { headerName: "编码", headerWidth: 80, dataCode: "code", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center", span: { row: 0, rowCount: 2, colCount: 1 }, }, { headerName: "费用规则", headerWidth: 280, dataCode: "rule", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center", span: { row: 0, rowCount: 2, colCount: 1 }, }, { headerName: "基数", headerWidth: 140, dataCode: "base", dataType: "String", formatter: "@", hAlign: "left", vAlign: "center", span: { row: 0, rowCount: 2, colCount: 1 }, }, { headerName: "费率(%)", headerWidth: 70, dataCode: "feeRate", dataType: "String", formatter: "@", hAlign: "center", vAlign: "center", span: { row: 0, rowCount: 2, colCount: 1 }, }, { headerName: "人工(%)", headerWidth: 70, dataCode: "labour", dataType: "String", formatter: "@", hAlign: "center", vAlign: "center", span: { row: 1, rowCount: 1, colCount: 1 }, }, { headerName: "材料(%)", headerWidth: 70, dataCode: "material", dataType: "String", formatter: "@", hAlign: "center", vAlign: "center", span: { row: 1, rowCount: 1, colCount: 1 }, }, { headerName: "机械(%)", headerWidth: 70, dataCode: "machine", dataType: "String", formatter: "@", hAlign: "center", vAlign: "center", span: { row: 1, rowCount: 1, colCount: 1 }, }, ], view: { lockColumns: [] }, comboItems: { base: ["分别按人材机乘系数", "人工", "材料", "机械"] }, options: { tabStripVisible: false, allowCopyPasteExcelStyle: false, allowExtendPasteRange: true, allowUserDragDrop: false, allowUserDragFill: false, scrollbarMaxAlign: true, }, }, isDef: function (v) { return v !== undefined && v !== null; }, //sheet things setOptions: function (workbook, opts) { for (let opt in opts) { workbook.options[opt] = opts[opt]; } }, buildHeader: function () { if (!this.sheet) { return; } this.sheet.suspendPaint(); this.sheet.suspendEvent(); let ch = GC.Spread.Sheets.SheetArea.colHeader; this.sheet.setRowCount(2, ch); for (let i = 0; i < this.setting.header.length; i++) { let header = this.setting.header[i]; this.sheet.addSpan(header.span.row, i, header.span.rowCount, header.span.colCount, ch); this.sheet.setValue(header.span.row, i, header.headerName, ch); if (header.dataCode === "feeRate") { this.sheet.addSpan(header.span.row, i + 1, 1, 3, ch); this.sheet.setValue(header.span.row, i + 1, "其中", ch); } } this.sheet.resumePaint(); this.sheet.resumeEvent(); }, buildSheet: function () { let fi = feeItemObj; if (!this.isDef(this.workBook)) { this.workBook = sheetCommonObj.buildSheet($("#instFeeRuleSpread")[0], this.setting, 10); this.sheet = this.workBook.getActiveSheet(); this.buildHeader(); this.sheet.setRowCount(); this.sheet.options.allowCellOverflow = false; sheetCommonObj.bindEscKey(this.workBook, [{ sheet: this.sheet, editStarting: this.onEditStarting, editEnded: this.onEditEnded }]); this.setOptions(this.workBook, this.setting.options); this.sheet.options.clipBoardOptions = GC.Spread.Sheets.ClipboardPasteOptions.values; this.bindEvents(this.sheet); //init combo fi.setCombo(this.sheet, 2, this.setting.comboItems.base); } }, bindEvents: function (sheet) { let me = feeRuleObj; const Events = GC.Spread.Sheets.Events; sheet.bind(Events.SelectionChanged, me.onSelectionChanged); sheet.bind(Events.EnterCell, me.onEnterCell); sheet.bind(Events.EditStarting, me.onEditStarting); sheet.bind(Events.EditEnded, me.onEditEnded); sheet.bind(Events.ClipboardPasting, me.onClipboardPasting); sheet.bind(Events.ClipboardPasted, me.onClipboardPasted); me.feeRuleDelOpr(); }, canSave: function (addObj) { return this.isDef(addObj.code) && addObj.code !== "" && !this.hasCode(addObj) && this.validRCJ(addObj); }, hasCode: function (obj) { let fi = feeItemObj; for (let feeItem of fi.cache) { for (let section of feeItem.section) { for (let feeRule of section.feeRule) { if (obj.code == feeRule.code && ((this.isDef(obj.ID) && obj.ID !== feeRule.ID) || !this.isDef(obj.ID))) { return true; } } } } return false; }, //费用类型为人、材、机时人材机总和一定要为100 validRCJ: function (feeRule) { if (!this.isDef(feeRule.base) || feeRule.base === this.base.RCJ) { return true; } let sum = 0; if (this.isDef(feeRule.labour)) { sum = parseFloat(sum + feeRule.labour).toDecimal(2); } if (this.isDef(feeRule.material)) { sum = parseFloat(sum + feeRule.material).toDecimal(2); } if (this.isDef(feeRule.machine)) { sum = parseFloat(sum + feeRule.machine).toDecimal(2); } return sum == 100; }, validPasteData: function (data) { //插入须有编码 if (!this.isDef(data.code)) { alert("粘贴时,编码不能为空,或者粘贴的数据中需包含编码"); return false; } //编码须唯一 if (this.isDef(data.code) && this.hasCode(data)) { alert("编码须唯一!"); return false; } //基数要合法 if (this.isDef(data.base) && this.setting.comboItems.base.indexOf(data.base) < 0) { alert("基数不正确!"); return false; } //费率、人工、材料、机械,须数字 if (this.isDef(data.feeRate) && isNaN(data.feeRate)) { alert("费率须为数字!"); return false; } if (this.isDef(data.labour) && isNaN(data.labour)) { alert("人工须为数字!"); return false; } if (this.isDef(data.material) && isNaN(data.material)) { alert("材料须为数字!"); return false; } if (this.isDef(data.machine) && isNaN(data.machine)) { alert("机械须为数字!"); return false; } //基数为分别按人材机时,费率须为空 if (this.isDef(data.base) && data.base === this.base.RCJ && this.isDef(data.feeRate) && data.feeRate !== "") { alert("基数为分别按人材机时,费率须为空!"); return false; } //基数为 人工、材料、机械时 三者之和须为100 if (this.isDef(data.base) && data.base !== this.base.RCJ && this.validRCJ(data)) { alert("基数为 人工、材料、机械时 三者之和须为100"); return false; } return true; }, decimalPasteData: function (data) { if (this.isDef(data.feeRate) && isNaN(data.feeRate)) { data.feeRate = parseFloat(data.feeRate).toDecimal(2); } if (this.isDef(data.labour) && isNaN(data.labour)) { data.labour = parseFloat(data.labour).toDecimal(2); } if (this.isDef(data.material) && isNaN(data.material)) { data.material = parseFloat(data.material).toDecimal(2); } if (this.isDef(data.machine) && isNaN(data.machine)) { data.machine = parseFloat(data.machine).toDecimal(2); } }, getFocusToCol: function (feeRule) { if (!this.isDef(feeRule.labour) || feeRule.labour === "" || feeRule.labour > 100 || feeRule.labour == 0) { return 4; } if (!this.isDef(feeRule.material) || feeRule.material === "" || feeRule.material > 100 || feeRule.material == 0) { return 5; } if (!this.isDef(feeRule.machine) || feeRule.machine === "" || feeRule.machine > 100 || feeRule.machine == 0) { return 6; } return 4; }, onSelectionChanged: function (sender, info) { let me = feeRuleObj, se = sectionObj; if ((info.oldSelections && info.oldSelections.length === 0 && info.newSelections.length > 0) || info.oldSelections[0].row !== info.newSelections[0].row) { if (me.isDef(me.updateObj) && !me.validRCJ(me.updateObj)) { $("#rcjAlert").modal("show"); $("#aleCanceBtn").bind("click", function () { me.updateObj.base = me.base.RCJ; me.updateObj.labour = 0; me.updateObj.material = 0; me.updateObj.machine = 0; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); se.updateSection([{ updateType: se.updateType.update, updateData: se.currentSection }]); $(this).unbind(); }); $("#aleConfBtn").bind("click", function () { me.sheet.setActiveCell(me.avtiveCell.row, me.getFocusToCol(me.updateObj)); $(this).unbind(); }); } if (me.isDef(me.addObj)) { if (!me.isDef(me.addObj.code) || me.addObj.code === "") { $("#alertText").text("请输入编码"); $("#codeAlert").modal("show"); $("#codAleClose").click(function () { me.addObj.code = ""; me.sheet.setActiveCell(me.avtiveCell.row, 0); $(this).unbind(); }); $("#codAlertQR").click(function () { me.addObj.code = ""; me.sheet.setActiveCell(me.avtiveCell.row, 0); $(this).unbind(); }); //取消插入 $("#codAlertQX").click(function () { me.addObj = null; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); $(this).unbind(); }); } else if (me.isDef(me.addObj.code) && me.hasCode(me.addObj)) { $("#alertText").text("输入的编号已存在,请重新输入"); $("#codeAlert").modal("show"); $("#codAleClose").click(function () { me.addObj.code = ""; me.sheet.setValue(me.avtiveCell.row, 0, ""); me.sheet.setActiveCell(me.avtiveCell.row, 0); $(this).unbind(); }); $("#codAlertQR").click(function () { me.addObj.code = ""; me.sheet.setValue(me.avtiveCell.row, 0, ""); me.sheet.setActiveCell(me.avtiveCell.row, 0); $(this).unbind(); }); //取消插入 $("#codAlertQX").click(function () { me.addObj = null; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); $(this).unbind(); }); } else if (!me.validRCJ(me.addObj)) { $("#rcjAlert").modal("show"); $("#aleCanceBtn").bind("click", function () { me.addObj = null; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); $(this).unbind(); }); $("#aleConfBtn").bind("click", function () { me.sheet.setActiveCell(me.avtiveCell.row, me.getFocusToCol(me.addObj)); $(this).unbind(); }); } } } }, onEnterCell: function (sender, args) { let me = feeRuleObj; me.sheet.repaint(); }, onEditStarting: function (sender, args) { let me = feeRuleObj, se = sectionObj; let feeRule = me.cache[args.row]; let rcjCols = [4, 5, 6]; if (!me.isDef(se.currentSection)) { args.cancel = true; } if (me.isDef(feeRule) && me.isDef(feeRule.base) && feeRule.base === me.base.RCJ && args.col === 3) { args.cancel = true; } else if (!me.isDef(feeRule) && rcjCols.indexOf(args.col) > 0) { args.cancel = true; } }, onEditEnded: function (sender, args) { let me = feeRuleObj, se = sectionObj; let v = me.isDef(args.editingText) ? args.editingText.toString().trim() : ""; let updateObj = { updateType: "", updateData: {} }; let feeRule = me.cache[args.row]; let field = me.setting.header[args.col]["dataCode"]; let orgV = me.isDef(feeRule) && me.isDef(feeRule[field]) ? feeRule[field] : ""; me.updateObj = feeRule; me.avtiveCell.row = args.row; me.avtiveCell.col = args.col; //update if (me.isDef(feeRule)) { feeRule[field] = me.isDef(feeRule[field]) ? feeRule[field] : ""; if (v === feeRule[field]) { return; } if (field === "base" && v === me.base.RCJ) { //基数为人材机时,费率清空 feeRule.feeRate = ""; me.sheet.setValue(args.row, 3, ""); } else if (field === "base" && (v === me.base.RG || v === me.base.CL || v === me.base.JX)) { if (!me.validRCJ(feeRule)) { //基数变为人工、材料、机械时,若人材机之和不为100,则清空 feeRule.labour = 0; feeRule.material = 0; feeRule.machine = 0; } } else if (field === "labour" || field === "material" || field === "machine" || field === "feeRate") { if (isNaN(v)) { alert("只能输入数值"); me.sheet.setValue(args.row, args.col, orgV); return; } v = parseFloat(v).toDecimal(2); me.sheet.setValue(args.row, args.col, v); } feeRule[field] = v; //编码重复,不可更新 if (field === "code") { if (v == "") { me.sheet.setValue(args.row, args.col, orgV); return; feeRule[field] = orgV; } if (me.hasCode(feeRule)) { $("#codeAlert").modal("show"); $("#codAleClose").bind("click", function () { me.sheet.setActiveCell(args.row, 0); me.sheet.setValue(args.row, args.col, orgV); }); $("#codAlertQR").bind("click", function () { me.sheet.setActiveCell(args.row, 0); me.sheet.setValue(args.row, args.col, orgV); }); feeRule[field] = orgV; return; } } //是否能更新 //人材机之和不为100,不解决之和为100取消操作的话,则基数自动换成分别按人材机 if (!me.validRCJ(feeRule)) { return; } updateObj.updateType = se.updateType.update; updateObj.updateData.ID = se.currentSection.ID; updateObj.updateData.feeRule = me.cache; me.updateObj = null; se.updateSection([{ updateType: se.updateType.update, updateData: se.currentSection }]); } //insert else { if (v === "") { return; } if (!me.isDef(me.addObj)) { me.addObj = Object.create(null); } me.addObj[me.setting.header[args.col]["dataCode"]] = v; if (me.canSave(me.addObj)) { me.addObj.ID = uuid.v1(); me.cache.push(me.addObj); updateObj.updateType = se.updateType.update; updateObj.updateData.ID = se.currentSection.ID; updateObj.updateData.feeRule = me.cache; me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); se.updateSection([{ updateType: se.updateType.update, updateData: se.currentSection }]); me.addObj = null; } } }, onClipboardPasting: function (sender, info) { let me = feeRuleObj, se = sectionObj; if (info.cellRange.col + info.cellRange.colCount > me.setting.header.length) { info.cancel = true; } if (!me.isDef(se.currentSection)) { info.cancel = true; } }, onClipboardPasted: function (sender, info) { let me = feeRuleObj, se = sectionObj, fi = feeItemObj; let items = sheetCommonObj.analyzePasteData(me.setting, info); me.toUpdate = false; for (let i = 0, len = items.length; i < len; i++) { let row = info.cellRange.row + i; let feeRule = me.cache[row]; //update if (me.isDef(feeRule)) { let tempObj = {}; for (let attr in feeRule) { tempObj[attr] = feeRule[attr]; } for (let attr in items[i]) { tempObj[attr] = items[i][attr]; } if (me.validPasteData(tempObj)) { me.decimalPasteData(tempObj); //front me.cache[row] = tempObj; me.toUpdate = true; } } else { // //insert if (me.validPasteData(items[i])) { me.decimalPasteData(items[i]); items[i].ID = uuid.v1(); //front me.cache.push(items[i]); me.toUpdate = true; } } } me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); if (me.toUpdate) { se.updateSection([{ updateType: se.updateType.update, updateData: se.currentSection }]); } }, feeRuleDelOpr: function () { if (locked) { return; } let me = feeRuleObj, se = sectionObj; me.workBook.commandManager().register("feeRuleDel", function () { me.toUpdate = false; let sels = me.workBook.getSheet(0).getSelections(); for (let i = 0, len = sels.length; i < len; i++) { let sel = sels[i]; //delete if (sel.colCount === me.setting.header.length) { for (let j = 0, jLen = sel.rowCount; j < jLen; j++) { let row = sel.row + j; let feeRule = me.cache[row]; //有数据,删除数据 if (me.isDef(feeRule)) { me.toUpdate = true; } } //front delete me.cache.splice(sel.row, sel.rowCount); } } if (me.toUpdate) { se.updateSection([{ updateType: se.updateType.update, updateData: se.currentSection }], function () { me.sheet.setRowCount(me.cache.length + 5); sheetCommonObj.showData(me.sheet, me.setting, me.cache); }); } }); me.workBook.commandManager().setShortcutKey(null, GC.Spread.Commands.Key.del, false, false, false, false); me.workBook.commandManager().setShortcutKey("feeRuleDel", GC.Spread.Commands.Key.del, false, false, false, false); }, }; let batchSectionObj = { cache: null, tree: null, controller: null, workBook: null, sheet: null, IDRowMapping: null, //树节点ID与行号映射 setting: { sheet: { cols: [ { head: { titleNames: ["选择"], spanCols: [1], spanRows: [2], vAlign: [1, 1], hAlign: [1, 1], font: "Arial", }, data: { field: "select", vAlign: 1, hAlign: 0, font: "Arial", }, width: 50, }, { head: { titleNames: ["名称"], spanCols: [1], spanRows: [2], vAlign: [1, 1], hAlign: [1, 1], font: "Arial", }, data: { field: "name", vAlign: 1, hAlign: 0, font: "Arial", }, width: 400, }, ], headRows: 1, headRowHeight: [47], emptyRows: 0, treeCol: 1, }, tree: { id: "ID", pid: "ParentID", nid: "NextSiblingID", rootId: -1, }, options: { tabStripVisible: false, allowCopyPasteExcelStyle: false, allowExtendPasteRange: true, allowUserDragDrop: false, allowUserDragFill: false, scrollbarMaxAlign: true, }, }, isDef: function (v) { return v !== undefined && v !== null; }, renderFunc: function (sheet, func) { sheet.suspendPaint(); sheet.suspendEvent(); if (func) { func(); } sheet.resumePaint(); sheet.resumeEvent(); }, setOptions: function (workbook, opts) { for (let opt in opts) { workbook.options[opt] = opts[opt]; } }, buildSheet: function () { if (!this.isDef(this.workBook)) { this.workBook = new GC.Spread.Sheets.Workbook($("#batchSectionSpread")[0], { sheetCount: 1 }); this.sheet = this.workBook.getActiveSheet(); this.setOptions(this.workBook, this.setting.options); this.bindEvents(this.sheet); } }, bindEvents: function (sheet) { let me = this; const Events = GC.Spread.Sheets.Events; sheet.bind(Events.EditStarting, me.onEditStarting); sheet.bind(Events.EditEnded, me.onEditEnded); sheet.bind(Events.ClipboardPasting, me.onClipboardPasting); me.workBook.bind(Events.ButtonClicked, me.onButtonClicked); //复选框点击事件 }, getSectionTree: function (repId) { let me = this; let url = "api/getRationTree"; let postData = { rationLibId: repId }; let sucFunc = function (rstData) { //init me.buildSheet(); me.initTree(rstData); me.buildMapping(me.tree.items); me.cache = me.tree.items; me.initController(me.tree, me.sheet, me.setting.sheet); me.controller.showTreeData(); me.sheet.setFormatter(-1, 1, "@"); //init checkBox let checkBox = new GC.Spread.Sheets.CellTypes.CheckBox(); me.sheet.getRange(-1, 0, -1, 1).cellType(checkBox); me.sheet.getRange(-1, 0, -1, 1).hAlign(GC.Spread.Sheets.HorizontalAlign.center); }; let errFunc = function () {}; CommonAjax.post(url, postData, sucFunc, errFunc); }, buildMapping: function (items) { this.IDRowMapping = {}; for (let i = 0, len = items.length; i < len; i++) { this.IDRowMapping[items[i].data.ID] = i; } }, initTree: function (datas) { this.tree = idTree.createNew(this.setting.tree); this.tree.loadDatas(datas); this.tree.selected = this.tree.items.length > 0 ? this.tree.items[0] : null; }, initController: function (tree, sheet, setting) { this.controller = TREE_SHEET_CONTROLLER.createNew(tree, sheet, setting); }, onEditStarting: function (sender, args) { args.cancel = true; }, onButtonClicked: function (sender, args) { let me = batchSectionObj; if (args.sheet.isEditing()) { args.sheet.endEdit(true); } let node = me.cache[args.row]; let checked = args.sheet.getValue(args.row, args.col); if (!me.isDef(node)) { return; } let rows = me.getChildRows(node); me.setChecked(rows, checked); }, onClipboardPasting: function (sender, info) { info.cancel = true; }, getChildRows: function (node) { let rst = [], ids = []; getChildIds(node); for (id of ids) { let row = this.IDRowMapping[id]; if (this.isDef(row)) { rst.push(row); } } return rst; function getChildIds(node) { ids.push(node.data.ID); for (let child of node.children) { getChildIds(child); } } }, //设置勾选,跟随父节点 setChecked: function (rows, checked) { let me = this; this.renderFunc(this.sheet, function () { for (let row of rows) { me.sheet.setValue(row, 0, checked); } }); }, //获得勾选的章节ID getCheckedSection: function (sheet) { let rst = []; let rowCount = sheet.getRowCount(); for (let i = 0, len = rowCount; i < len; i++) { let checked = sheet.getValue(i, 0); //只返回叶子节点 if (this.isDef(checked) && checked == true && this.isDef(this.cache[i]) && this.isDef(this.cache[i].data.ID) && this.cache[i].children.length === 0) { rst.push(this.cache[i].data.ID); } } return Array.from(new Set(rst)); }, clearChecked: function () { let me = this; this.renderFunc(this.sheet, function () { let rowCount = me.sheet.getRowCount(); for (let i = 0, len = rowCount; i < len; i++) { me.sheet.setValue(i, 0, false); } }); }, onConfirmBtn: function () { let me = this, fi = feeItemObj, se = sectionObj; $("#bsTree_conf").bind("click", function () { let feeItemId = fi.currentFeeItem.ID; let sectionId = se.currentSection.ID; let rationSection = me.getCheckedSection(me.sheet); me.batchUpdate(feeItemId, sectionId, rationSection); $(this).unbind(); }); }, //inst: 定额安装费用, rationSection: 定额章节树IDs batchUpdate: function (feeItemId, sectionId, rationSection) { CommonAjax.post( "/rationRepository/api/batchUpdateInst", { inst: { feeItemId: feeItemId, sectionId: sectionId }, rationSection: rationSection }, function (rstData) { $("#sectionTreeModal").modal("hide"); } ); }, };