Kaynağa Gözat

单价变更

MaiXinRong 2 yıl önce
ebeveyn
işleme
d354275919

+ 58 - 6
app/lib/ledger.js

@@ -54,6 +54,30 @@ class baseTree {
     getParent (node) {
         return this.getItems(node[this.setting.pid]);
     };
+    getTopParent(node) {
+        const parents = this.getAllParents(node);
+        return parents[0];
+    };
+    getAllParents(node) {
+        const parents = [];
+        if (!node) return parents;
+
+        if (node[this.setting.fullPath] && node[this.setting.fullPath] !== '') {
+            const parentIds = node[this.setting.fullPath].split('-');
+            for (const id of parentIds) {
+                if (id !== node[this.setting.id]) {
+                    parents.push(this.getItems(id));
+                }
+            }
+        } else {
+            let vP = this.getParent(node);
+            while (vP) {
+                parents.unshift(vP);
+                vP = this.getParent(vP);
+            }
+        }
+        return parents;
+    }
     /**
      * 查询node的已下载子节点
      * @param {Object} node
@@ -66,7 +90,7 @@ class baseTree {
             return x[setting.pid] === pid;
         });
         children.sort(function (a, b) {
-            return a.order - b.order;
+            return a[setting.order] - b[setting.order];
         });
         return children;
     };
@@ -84,6 +108,7 @@ class baseTree {
      */
     sortTreeNode (isResort) {
         const self = this;
+        const setting = this.setting;
         const addSortNodes = function (nodes) {
             if (!nodes) { return }
             for (let i = 0; i < nodes.length; i++) {
@@ -93,7 +118,7 @@ class baseTree {
                     nodes[i].children = self.getChildren(nodes[i]);
                 } else {
                     nodes[i].children.sort(function (a, b) {
-                        return a.order - b.order;
+                        return a[setting.order] - b[setting.order];
                     })
                 }
                 addSortNodes(nodes[i].children);
@@ -104,7 +129,7 @@ class baseTree {
             this.children = this.getChildren();
         } else {
             this.children.sort(function (a, b) {
-                return a.order - b.order;
+                return a[setting.order] - b[setting.order];
             })
         }
         addSortNodes(this.children);
@@ -119,9 +144,10 @@ class baseTree {
         this.nodes = [];
         this.datas = [];
         this.children = [];
+        const setting = this.setting;
         // 加载全部数据
         datas.sort(function (a, b) {
-            return a.level - b.level;
+            return a[setting.level] - b[setting.level];
         });
         for (const data of datas) {
             const keyName = itemsPre + data[this.setting.id];
@@ -143,7 +169,7 @@ class baseTree {
             }
         }
         this.children.sort(function (a, b) {
-            return a.order - b.order;
+            return a[setting.order] - b[setting.order];
         });
         this.sortTreeNode(true);
     }
@@ -1017,10 +1043,36 @@ class reviseTree extends billsTree {
     loadRevisePrice(price, decimal) {
         this.decimal = decimal;
         this.price = price || [];
+        this.rela_price = [];
+        this.common_price = [];
+        this.price.forEach(x => {
+            if (x.rela_lid) {
+                x.rela_lid = x.rela_lid.split(',');
+                this.rela_price.push(x);
+            } else {
+                this.common_price.push(x);
+            }
+        });
     }
     checkRevisePrice(d) {
         const helper = this.ctx.helper;
-        const p = this.price.find(x => {
+        const setting = this.setting;
+        const pid = this.getAllParents(d).map(x => { return x[setting.id] + ''; });
+        const checkRela = function(rela_lid) {
+            if (!rela_lid || rela_lid.length === 0) return false;
+            for (const lid of rela_lid) {
+                if (pid.indexOf(lid) >= 0) return true;
+            }
+            return false;
+        };
+        let p = this.rela_price.find(x => {
+            return x.b_code === d.b_code &&
+                ((!x.name && !d.name) || x.name === d.name) &&
+                ((!x.unit && !d.unit) || x.unit === d.unit) &&
+                helper.checkZero(x.org_price - d.unit_price) &&
+                checkRela(x.rela_lid);
+        });
+        if (!p) p = this.common_price.find(x => {
             return x.b_code === d.b_code &&
                 ((!x.name && !d.name) || x.name === d.name) &&
                 ((!x.unit && !d.unit) || x.unit === d.unit) &&

+ 29 - 6
app/lib/revise_price.js

@@ -22,9 +22,32 @@ class revisePriceCalc {
         this.ctx = ctx;
     }
 
-    findPrice(b_code, name, unit, unit_price) {
+    set price(price) {
+        this._price = price;
+        this.common_price_c = [];
+        this.rela_price_c = [];
+        price.forEach(x => {
+            x.rela_lid = x.rela_lid ? x.rela_lid.split(',') : [];
+            if (x.rela_cid) {
+                x.rela_cid = x.rela_cid.split(',');
+                this.rela_price_c.push(x);
+            } else {
+                this.common_price_c.push(x);
+            }
+        });
+    }
+    get price() {
+        return this._price;
+    }
+
+    findChangeBillsPrice(b_code, name, unit, unit_price, cid) {
         const helper = this.ctx.helper;
-        return this.price.find(x => {
+        const p = this.rela_price_c.find(x => {
+            return b_code === x.b_code && name === x.name && unit === x.unit && helper.numEqual(unit_price, x.org_price) && x.rela_cid.indexOf(cid) >= 0;
+        });
+        if (p) return p;
+
+        return this.common_price_c.find(x => {
             return b_code === x.b_code && name === x.name && unit === x.unit && helper.numEqual(unit_price, x.org_price);
         });
     }
@@ -37,8 +60,8 @@ class revisePriceCalc {
      */
     async newStagePriceChange(newStage, preStage, transaction) {
         // 获取未执行的单价变更,无单价变更不执行
-        const price = await this.ctx.service.revisePrice.getAllDataByCondition({ where: { tid: newStage.tid, valid: 1, use_stage: 0 } });
-        if (price.length === 0) return;
+        this.price = await this.ctx.service.revisePrice.getAllDataByCondition({ where: { tid: newStage.tid, valid: 1, use_stage: 0 } });
+        if (this.price.length === 0) return;
         // 无截止上期数据不执行
         const preBillsData = await this.ctx.service.stageBillsFinal.getAllDataByCondition({ where: { sid: preStage.id } });
         if (preBillsData.length === 0) return;
@@ -94,7 +117,7 @@ class revisePriceCalc {
      */
     async stageCheckAgainPriceChange(stage, auditOrder, transaction) {
         // 获取未执行的单价变更,无单价变更不执行
-        const price = await this.ctx.service.revisePrice.getAllDataByCondition({ where: { tid: stage.tid, valid: 1, use_stage: 0 } });
+        this.price = await this.ctx.service.revisePrice.getAllDataByCondition({ where: { tid: stage.tid, valid: 1, use_stage: 0 } });
         if (price.length === 0) return;
 
         const curBillsData = await this.ctx.service.stageBills.getLastestStageData2(stage.tid, stage.id);
@@ -181,7 +204,7 @@ class revisePriceCalc {
         const updateBills = [];
         let total_price = 0, positive_tp = 0, negative_tp = 0;
         for (const b of changeBills) {
-            const p = this.findPrice(b.code, b.name, b.unit, b.unit_price);
+            const p = this.findChangeBillsPrice(b.code, b.name, b.unit, b.unit_price, change.cid);
             let bills_tp;
             if (p) {
                 updateBills.push({ id: b.id, unit_price: p.new_price });

+ 6 - 2
app/lib/stage_im.js

@@ -70,7 +70,9 @@ class StageIm {
 
     // 加载数据
     async _loadMainData() {
-        const billsData = await this.ctx.service.ledger.getData(this.ctx.tender.id);
+        const billsData = this.ctx.stage.ledgerHis
+            ? await this.ctx.helper.loadLedgerDataFromOss(this.ctx.stage.ledgerHis.bills_file)
+            : await this.ctx.service.ledger.getData(this.ctx.tender.id);
         const curStage = this.ctx.stage.readOnly
             ? await this.ctx.service.stageBills.getAuditorStageData2(this.ctx.tender.id,
                 this.ctx.stage.id, this.ctx.stage.curTimes, this.ctx.stage.curOrder)
@@ -86,7 +88,9 @@ class StageIm {
         this.billsTree.loadDatas(billsData);
         this.billsTree.calculateAll();
 
-        const posData = await this.ctx.service.pos.getAllDataByCondition({ where: { tid: this.ctx.tender.id } });
+        const posData = this.ctx.stage.ledgerHis
+            ? await this.ctx.helper.loadLedgerDataFromOss(this.ctx.stage.ledgerHis.pos_file)
+            : await this.ctx.service.pos.getAllDataByCondition({ where: { tid: this.ctx.tender.id } });
         const curPosStage = this.ctx.stage.readOnly
             ? await this.ctx.service.stagePos.getAuditorStageData2(this.ctx.tender.id,
                 this.ctx.stage.id, this.ctx.stage.curTimes, this.ctx.stage.curOrder)

+ 2 - 1
app/public/js/path_tree.js

@@ -420,6 +420,7 @@ const createNewPathTree = function (type, setting) {
 
             if (node.full_path && node.full_path !== '') {
                 const parentIds = node.full_path.split('-');
+                parentIds.length = parentIds.length - 1;
                 for (const id of parentIds) {
                     if (id !== node[this.setting.id]) {
                         parents.push(this.getItems(id));
@@ -1190,7 +1191,7 @@ const createNewPathTree = function (type, setting) {
         }
         checkRevisePrice(d) {
             const setting = this.setting;
-            const pid = this.getAllParents(d).map(x => { return x[setting.pid] + ''; });
+            const pid = this.getAllParents(d).map(x => { return x[setting.id] + ''; });
             const checkRela = function(rela_lid) {
                 if (!rela_lid || rela_lid.length === 0) return false;
                 for (const lid of rela_lid) {

+ 139 - 21
app/public/js/revise_price.js

@@ -80,7 +80,7 @@ $(document).ready(() => {
         font: '12px 微软雅黑',
         readOnly,
         getColor: function (sheet, data, row, col, defaultColor) {
-            if (!data || data.rela_lid) return defaultColor;
+            if (!data || (data.rela_lid && data.rela_cid)) return defaultColor;
 
             const samePrice = sheet.zh_data.find(x => {
                 return x.b_code === data.b_code && x.name === data.name && x.unit === data.unit && x.org_price === data.org_price;
@@ -102,7 +102,10 @@ $(document).ready(() => {
         headerFont: '12px 微软雅黑',
         font: '12px 微软雅黑',
         readOnly: true,
-        getColor: function (sheet, data, row, col, defaultColor) {
+        // getColor: function (sheet, data, row, col, defaultColor) {
+        //     return data && data.valid ? defaultColor : '#ddd';
+        // },
+        getForeColor: function (sheet, data, row, col, defaultColor) {
             return data && data.valid ? defaultColor : '#ddd';
         },
     };
@@ -120,8 +123,8 @@ $(document).ready(() => {
         headerFont: '12px 微软雅黑',
         font: '12px 微软雅黑',
         readOnly: true,
-        getColor: function (sheet, data, row, col, defaultColor) {
-            return data && data.rela ? defaultColor : '#ddd';
+        getForeColor: function (sheet, data, row, col, defaultColor) {
+            return data && data.valid ? defaultColor : '#ddd';
         },
     };
     autoFlashHeight();
@@ -168,9 +171,6 @@ $(document).ready(() => {
             this.data = datas;
             this.tree.loadDatas(treeData);
             this.resortData();
-            for (const d of this.data) {
-                this.analysisRelaLid(d);
-            }
             this.change = changeData;
             if (this.data.length > 0) this.refreshRela(this.data[0]);
         }
@@ -178,7 +178,6 @@ $(document).ready(() => {
             if (updateData.add) {
                 for (const a of updateData.add) {
                     this.data.push(a);
-                    this.analysisRelaLid(a);
                 }
             }
             if (updateData.update) {
@@ -191,7 +190,6 @@ $(document).ready(() => {
                     } else {
                         this.data.push(d);
                     }
-                    this.analysisRelaLid(d);
                 }
             }
             if (updateData.del) {
@@ -235,6 +233,7 @@ $(document).ready(() => {
                 const choose = price.rela_cid.split(',');
                 for (const c of this.change) {
                     c.rela = choose.indexOf(c.cid + '') >= 0;
+                    c.valid = c.rela;
                 }
             } else {
                 const invalid = [];
@@ -243,7 +242,15 @@ $(document).ready(() => {
                     invalid.push(...cid);
                 }
                 for (const c of this.change) {
-                    c.rela = invalid.indexOf(c.cid + '') < 0;
+                    c.rela = invalid.indexOf(c.cid + '') >= 0;
+                    if (c.rela) {
+                        c.valid = 0;
+                    } else {
+                        const exist = c.bills.find(x => {
+                            return x.code === price.b_code && x.name === price.name && x.unit === price.unit && x.unit_price === price.org_price;
+                        });
+                        c.valid = exist;
+                    }
                 }
             }
         }
@@ -440,14 +447,21 @@ $(document).ready(() => {
             const data = { update: { id: price.id, rela_lid } };
             postData(window.location.pathname + '/update', data, function (result) {
                 revisePrice.loadUpdateData(result);
-                SpreadJsObj.reLoadSheetData(priceSheet);
+            });
+        },
+        updateRelaCid: function (price, rela_cid) {
+            const data = { update: { id: price.id, rela_cid } };
+            postData(window.location.pathname + '/update', data, function (result) {
+                revisePrice.loadUpdateData(result);
             });
         },
         selectionChanged: function () {
             const price = SpreadJsObj.getSelectObject(priceSheet);
             revisePrice.refreshRela(price);
-            SpreadJsObj.reloadRowBackColor(priceBwSheet, 0, priceBwSheet.getRowCount());
-            SpreadJsObj.reloadRowBackColor(priceChangeSheet, 0, priceChangeSheet.getRowCount());
+            // SpreadJsObj.reloadRowBackColor(priceBwSheet, 0, priceBwSheet.getRowCount());
+            // SpreadJsObj.reloadRowBackColor(priceChangeSheet, 0, priceChangeSheet.getRowCount());
+            SpreadJsObj.reloadRowForeColor(priceBwSheet, 0, priceBwSheet.getRowCount());
+            SpreadJsObj.reloadRowForeColor(priceChangeSheet, 0, priceChangeSheet.getRowCount());
         },
     };
     if (!readOnly) {
@@ -535,8 +549,7 @@ $(document).ready(() => {
                     callback: function (key, opt) {
                         const price = SpreadJsObj.getSelectObject(priceSheet);
                         const samePrice = revisePrice.getSamePrice(price);
-                        // todo
-                        // chooseRelaChange.show(price, samePrice);
+                        chooseRelaChange.show(price, samePrice);
                     },
                     disabled: function (key, opt) {
                         const node = SpreadJsObj.getSelectObject(priceSheet);
@@ -611,6 +624,8 @@ $(document).ready(() => {
             autoFlashHeight();
             priceSpread.refresh();
             ledgerGcl.spread.refresh();
+            priceBwSpread.refresh();
+            priceChangeSpread.refresh();
         }
     });
 
@@ -675,11 +690,11 @@ $(document).ready(() => {
             this.sheet = this.spread.getActiveSheet();
             const spreadSetting = {
                 cols: [
-                    {title: '选择', colSpan: '1', rowSpan: '1', field: 'check', hAlign: 1, width: 50, formatter: '@', readOnly: true, cellType: 'checkbox'},
-                    {title: '项目节编号', colSpan: '1', rowSpan: '1', field: 'code', hAlign: 0, width: 150, formatter: '@', readOnly: true, cellType: 'tree'},
-                    {title: '清单编号', colSpan: '1', rowSpan: '1', field: 'b_code', hAlign: 0, width: 80, formatter: '@', readOnly: true},
-                    {title: '名称', colSpan: '1', rowSpan: '1', field: 'name', hAlign: 0, width: 230, formatter: '@', readOnly: true},
-                    {title: '单位', colSpan: '1', rowSpan: '1', field: 'unit', hAlign: 1, width: 60, formatter: '@', readOnly: true},
+                    {title: '选择', colSpan: '1', rowSpan: '1', field: 'check', hAlign: 1, width: 50, formatter: '@', cellType: 'checkbox'},
+                    {title: '项目节编号', colSpan: '1', rowSpan: '1', field: 'code', hAlign: 0, width: 150, formatter: '@', cellType: 'tree'},
+                    {title: '清单编号', colSpan: '1', rowSpan: '1', field: 'b_code', hAlign: 0, width: 80, formatter: '@'},
+                    {title: '名称', colSpan: '1', rowSpan: '1', field: 'name', hAlign: 0, width: 230, formatter: '@'},
+                    {title: '单位', colSpan: '1', rowSpan: '1', field: 'unit', hAlign: 1, width: 60, formatter: '@'},
                 ],
                 headRows: 1,
                 emptyRows: 0,
@@ -687,6 +702,7 @@ $(document).ready(() => {
                 defaultRowHeight: 21,
                 headerFont: '12px 微软雅黑',
                 font: '12px 微软雅黑',
+                readOnly: true,
                 getColor: function (sheet, data, row, col, defaultColor) {
                     return data && data.invalid ? '#dddddd' : defaultColor;
                 }
@@ -807,12 +823,104 @@ $(document).ready(() => {
         }
     }
     const chooseRelaBw = new ChooseRelaBw();
+    class ChooseRelaChange {
+        constructor (){
+            const self = this;
+            $('#choose-rela-change').on('shown.bs.modal', function() {
+                self.initSpread();
+                SpreadJsObj.reloadColData(self.sheet, 0, 1);
+                SpreadJsObj.reloadRowBackColor(self.sheet, 0, self.change.length);
+            });
+            $('#choose-rela-change-ok').click(function() {
+                const choose_cid = [];
+                self.change.forEach(x => {
+                    if (x.check) choose_cid.push(x.cid);
+                });
+                priceOprObj.updateRelaCid(self.price, choose_cid.join(','));
+                $('#choose-rela-change').modal('hide');
+            });
+        }
+        initSpread() {
+            if (this.spread) return;
+
+            this.spread = SpreadJsObj.createNewSpread($('#rela-change-spread')[0]);
+            this.sheet = this.spread.getActiveSheet();
+            const spreadSetting = {
+                cols: [
+                    {title: '选择', colSpan: '1', rowSpan: '1', field: 'check', hAlign: 1, width: 50, formatter: '@',  cellType: 'checkbox'},
+                    {title: '变更令', colSpan: '1', rowSpan: '1', field: 'code', hAlign: 0, width: 150, formatter: '@'},
+                    {title: '名称', colSpan: '1', rowSpan: '1', field: 'name', hAlign: 0, width: 230, formatter: '@'},
+                    {title: '单位', colSpan: '1', rowSpan: '1', field: 'unit', hAlign: 1, width: 60, formatter: '@'},
+                ],
+                headRows: 1,
+                emptyRows: 0,
+                headRowHeight: [25],
+                defaultRowHeight: 21,
+                headerFont: '12px 微软雅黑',
+                font: '12px 微软雅黑',
+                readOnly: true,
+                getColor: function (sheet, data, row, col, defaultColor) {
+                    return data && data.invalid ? '#dddddd' : defaultColor;
+                }
+            };
+            SpreadJsObj.initSheet(this.sheet, spreadSetting);
+            const self = this;
+            this.spread.bind(spreadNS.Events.ButtonClicked, function (e, info) {
+                const sheet = info.sheet, cellType = sheet.getCellType(info.row, info.col);
+                if (!sheet.zh_setting) return;
+
+                if (cellType instanceof spreadNS.CellTypes.CheckBox) {
+                    if (sheet.isEditing()) sheet.endEdit(true);
+                }
+
+                const col = sheet.zh_setting.cols[info.col];
+                if (col.field !== 'check') return;
+
+                const node = SpreadJsObj.getSelectObject(sheet);
+
+                if (!node.check) {
+                    if (node.invalid) return;
+                    node.check = true;
+                    SpreadJsObj.reLoadRowsData(info.sheet, [info.row]);
+                } else {
+                    node.check = false;
+                    SpreadJsObj.reLoadRowsData(info.sheet, [info.row]);
+                }
+            });
+            SpreadJsObj.loadSheetData(this.sheet, SpreadJsObj.DataType.Data, this.change);
+        }
+        loadChange(data) {
+            this.change = data;
+        }
+        show(price, samePrice) {
+            this.price = price;
+            this.choose = price.rela_cid ? price.rela_cid.split(',') : [];
+            this.invalid = [];
+            for (const sp of samePrice) {
+                const cid = sp.rela_cid ? sp.rela_cid.split(',') : [];
+                this.invalid.push(...cid);
+            }
+            for (const c of this.change) {
+                c.check = this.choose.indexOf(c.cid + '') >= 0;
+                c.invalid = this.invalid.indexOf(c.cid + '') >= 0;
+                if (!c.check && c.invalid) {
+                    const exist = c.bills.find(x => {
+                        return x.code === price.b_code && x.name === price.name && x.unit === price.unit && x.unit_price === price.org_price;
+                    });
+                    c.invalid = !exist;
+                }
+            }
+            $('#choose-rela-change').modal('show');
+        }
+    }
+    const chooseRelaChange = new ChooseRelaChange();
 
     postData('load', { filter: 'bills;pos;price;change' }, result => {
         revisePrice.loadDatas(result.price, result.bills, result.change);
         SpreadJsObj.loadSheetData(priceSheet, SpreadJsObj.DataType.Data, revisePrice.data);
         ledgerGcl.loadData(result.bills, result.pos);
         chooseRelaBw.loadTree(result.bills);
+        chooseRelaChange.loadChange(result.change);
         SpreadJsObj.loadSheetData(priceBwSheet, SpreadJsObj.DataType.Tree, revisePrice.tree);
         SpreadJsObj.loadSheetData(priceChangeSheet, SpreadJsObj.DataType.Data, revisePrice.change);
         $("[content='#ledgerGcl']").click();
@@ -825,7 +933,7 @@ $(document).ready(() => {
         if (!tab.hasClass('active')) {
             $('a', '#side-menu').removeClass('active');
             tab.addClass('active');
-            $('.tab-content .tab-pane').removeClass('active');
+            $('#right-view .tab-pane').removeClass('active');
             tabPanel.addClass('active');
             showSideTools(tab.hasClass('active'));
             ledgerGcl.spread.refresh();
@@ -836,5 +944,15 @@ $(document).ready(() => {
             showSideTools(tab.hasClass('active'));
         }
         priceSpread.refresh();
+        priceBwSpread.refresh();
+        priceChangeSpread.refresh();
+    });
+    $('a', '.bcontent-wrap').click(function() {
+        $('[name=priceRela]').removeClass('active');
+        $(this).addClass('active');
+        $('#priceRelaTab').children().removeClass('active');
+        $(this.getAttribute('href')).addClass('active');
+        priceBwSpread.refresh();
+        priceChangeSpread.refresh();
     });
 });

+ 54 - 12
app/public/js/spreadjs_rela/spreadjs_zh.js

@@ -436,14 +436,6 @@ const SpreadJsObj = {
         }
         cell.font(font);
 
-        if (col.foreColor) {
-            if (Object.prototype.toString.apply(col.foreColor) === "[object Function]") {
-                cell.foreColor(col.foreColor(data, sheet.getDefaultStyle().foreColor));
-            } else {
-                cell.foreColor(col.foreColor);
-            }
-        }
-
         if (col.readOnly && Object.prototype.toString.apply(col.readOnly) === "[object Function]") {
             cell.locked(col.readOnly(data) || sheet.zh_setting.readOnly || false).vAlign(1).hAlign(col.hAlign);
         } else {
@@ -461,9 +453,20 @@ const SpreadJsObj = {
         }
 
         cell.backColor(SpreadJsObj._getBackColor(sheet, data, iRow, col));
+        cell.foreColor(SpreadJsObj._getForeColor(sheet, data, iRow, col));
 
         cell.setBorder(sheet.borderLine, {all: true});
     },
+    _getForeColor: function (sheet, data, row, col) {
+        let foreColor = sheet.getDefaultStyle().foreColor;
+        if (sheet.zh_setting.tree.getForeColor && Object.prototype.toString.apply(sheet.zh_setting.tree.getForeColor) === "[object Function]") {
+            foreColor = sheet.zh_setting.tree.getColor(sheet, data, row, col, foreColor);
+        }
+        if (sheet.zh_setting.getForeColor && Object.prototype.toString.apply(sheet.zh_setting.getForeColor) === "[object Function]") {
+            foreColor = sheet.zh_setting.getForeColor(sheet, data, row, col, foreColor);
+        }
+        return foreColor;
+    },
     _getBackColor: function (sheet, data, row, col) {
         let backColor = sheet.getDefaultStyle().backColor;
         let sels = sheet.getSelections();
@@ -487,10 +490,6 @@ const SpreadJsObj = {
                 cell.font(col.font);
             }
 
-            if (col.foreColor && Object.prototype.toString.apply(col.foreColor) !== "[object Function]") {
-                cell.foreColor(col.foreColor);
-            }
-
             const readOnly1 = (sheet.zh_setting.readOnly && Object.prototype.toString.apply(sheet.zh_setting.readOnly) === "[object Function]")
                 ? sheet.zh_setting.readOnly(data) : (sheet.zh_setting.readOnly || false);
             const readOnly2 = (col.readOnly && Object.prototype.toString.apply(col.readOnly) === "[object Function]")
@@ -559,6 +558,7 @@ const SpreadJsObj = {
             }
 
             cell.backColor(SpreadJsObj._getBackColor(sheet, data, row, col));
+            cell.foreColor(SpreadJsObj._getForeColor(sheet, data, row, col));
 
             cell.setBorder(sheet.borderLine, {all: true});
             data.waitingLoading = false;
@@ -823,6 +823,40 @@ const SpreadJsObj = {
             this.endMassOperation(sheet);
         }
     },
+    reloadRowForeColor: function (sheet, row, count) {
+        const sortData = sheet.zh_dataType === 'tree' ? sheet.zh_tree.nodes : sheet.zh_data;
+
+        this.beginMassOperation(sheet);
+        try {
+            for (let i = row; i < row + count; i++) {
+                if (i < 0) { continue; }
+                const data = sortData[i];
+                for (const [iCol, col] of sheet.zh_setting.cols.entries()) {
+                    sheet.getCell(i, iCol).foreColor(SpreadJsObj._getForeColor(sheet, data, i, col));
+                }
+            };
+            this.endMassOperation(sheet);
+        } catch (err) {
+            this.endMassOperation(sheet);
+        }
+    },
+    reloadRowsForeColor: function (sheet, rows) {
+        const sortData = sheet.zh_dataType === 'tree' ? sheet.zh_tree.nodes : sheet.zh_data;
+
+        this.beginMassOperation(sheet);
+        try {
+            for (const row of rows) {
+                if (row < 0) { continue; }
+                const data = sortData[row];
+                for (const [iCol, col] of sheet.zh_setting.cols.entries()) {
+                    sheet.getCell(row, iCol).foreColor(SpreadJsObj._getForeColor(sheet, data, row, col));
+                }
+            };
+            this.endMassOperation(sheet);
+        } catch (err) {
+            this.endMassOperation(sheet);
+        }
+    },
     reloadRowBackColor: function (sheet, row, count) {
         const sortData = sheet.zh_dataType === 'tree' ? sheet.zh_tree.nodes : sheet.zh_data;
 
@@ -1365,8 +1399,10 @@ const SpreadJsObj = {
                                 const x1 = centerX + indent / 2;
                                 if (dotLine) {
                                     drawDotLine(canvas, centerX, centerY, Math.min(x1, x + w), centerY, lineColor);
+                                    // drawDotLine(canvas, centerX, centerY, Math.min(x1, x + w), centerY, style.foreColor);
                                 } else {
                                     drawLine(canvas, centerX, centerY, Math.min(x1, x + w), centerY, lineColor);
+                                    // drawLine(canvas, centerX, centerY, Math.min(x1, x + w), centerY, style.foreColor);
                                 }
                             }
                             // Draw Vertical Line
@@ -1377,14 +1413,18 @@ const SpreadJsObj = {
                                 if (node.order === 1 && !parent) {
                                     if (dotLine) {
                                         drawDotLine(canvas, centerX, centerY, centerX, y1, lineColor);
+                                        // drawDotLine(canvas, centerX, centerY, centerX, y1, style.foreColor);
                                     } else {
                                         drawLine(canvas, centerX, centerY, centerX, y1, lineColor);
+                                        // drawLine(canvas, centerX, centerY, centerX, y1, style.foreColor);
                                     }
                                 } else {
                                     if (dotLine) {
                                         drawDotLine(canvas, centerX, y, centerX, y1, lineColor);
+                                        // drawDotLine(canvas, centerX, y, centerX, y1, style.foreColor);
                                     } else {
                                         drawLine(canvas, centerX, y, centerX, y1, lineColor);
+                                        // drawLine(canvas, centerX, y, centerX, y1, style.foreColor);
                                     }
                                 }
                             }
@@ -1401,8 +1441,10 @@ const SpreadJsObj = {
                                     if (parentCenterX < x + w) {
                                         if (dotLine) {
                                             drawDotLine(canvas, parentCenterX, y, parentCenterX, y + h, lineColor);
+                                            // drawDotLine(canvas, parentCenterX, y, parentCenterX, y + h, style.foreColor);
                                         } else {
                                             drawLine(canvas, parentCenterX, y, parentCenterX, y + h, lineColor);
+                                            // drawLine(canvas, parentCenterX, y, parentCenterX, y + h, style.foreColor);
                                         }
                                     }
                                 }

+ 10 - 0
app/public/js/stage_compare.js

@@ -341,4 +341,14 @@ $(document).ready(function () {
 
         SpreadExcelObj.exportSimpleXlsxSheet(ledgerSpreadSetting, data, $('.sidebar-title').attr('data-original-title') + "-审核比较.xlsx");
     });
+    $('[name=compareType]').click(function () {
+        $('[name=compareType]').removeClass('active');
+        $(this).addClass('active');
+        $('#compareType').children().removeClass('active');
+        $(this.getAttribute('href')).addClass('active');
+        xmjSpread.refresh();
+        posSpread.refresh();
+        gclSpread.refresh();
+        leafXmjSpread.refresh();
+    });
 });

+ 1 - 0
app/service/revise_price.js

@@ -70,6 +70,7 @@ module.exports = app => {
                 }
                 if (d.memo !== undefined) nd.memo = d.memo;
                 if (d.rela_lid !== undefined) nd.rela_lid = d.rela_lid;
+                if (d.rela_cid !== undefined) nd.rela_cid = d.rela_cid;
                 uDatas.push(nd);
             }
             if (uDatas.length > 0) {

+ 3 - 3
app/view/revise/price.ejs

@@ -20,14 +20,14 @@
                     <div class="bc-bar mb-1">
                         <ul class="nav nav-tabs">
                             <li class="nav-item">
-                                <a class="nav-link active" data-toggle="tab" href="#price-bw" role="tab">应用部位</a>
+                                <a class="nav-link active" href="#price-bw" name="priceRela">应用部位</a>
                             </li>
                             <li class="nav-item">
-                                <a class="nav-link" data-toggle="tab" href="#price-change" role="tab">应用变更令</a>
+                                <a class="nav-link" href="#price-change" name="priceRela">应用变更令</a>
                             </li>
                         </ul>
                     </div>
-                    <div class="tab-content">
+                    <div class="tab-content" id="priceRelaTab">
                         <div class="tab-pane active" id="price-bw">
                             <div class="sp-wrap" id="price-bw-spread">
                             </div>

+ 19 - 0
app/view/revise/price_modal.ejs

@@ -25,4 +25,23 @@
             </div>
         </div>
     </div>
+</div>
+<div class="modal fade" id="choose-rela-change" data-backdrop="static">
+    <div class="modal-dialog modal-lg" role="document">
+        <div class="modal-content">
+            <div class="modal-header">
+                <h5 class="modal-title">选择应用变更令</h5>
+            </div>
+            <div class="modal-body">
+                <div class="modal-height-500" id="rela-change-spread">
+                </div>
+            </div>
+            <div class="modal-footer">
+                <button type="button" class="btn btn-secondary btn-sm" data-dismiss="modal">关闭</button>
+                <% if (!ctx.revise.readOnly) { %>
+                <button type="button" class="btn btn-primary btn-sm" id="choose-rela-change-ok">确定</button>
+                <% } %>
+            </div>
+        </div>
+    </div>
 </div>

+ 4 - 1
sql/update.sql

@@ -1,4 +1,7 @@
 ALTER TABLE `zh_project_account` CHANGE `stamp_path` `stamp_path` VARCHAR(5000) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '用户签章oss地址';
 
 ALTER TABLE `zh_revise_price`
-ADD COLUMN `rela_lid`  varchar(1000) NOT NULL DEFAULT '' COMMENT '关联台账id(zh_ledger.ledger_id)' AFTER `use_stage_order`;
+ADD COLUMN `rela_lid`  varchar(1000) NOT NULL DEFAULT '' COMMENT '关联台账id(zh_ledger.ledger_id)' AFTER `use_stage_order`;
+
+ALTER TABLE `zh_revise_price`
+ADD COLUMN `rela_cid`  varchar(5000) NOT NULL DEFAULT '' COMMENT '关联变更令id(zh_change.cid)' AFTER `rela_lid`;