ソースを参照

电子签名打印预览

TonyKang 5 年 前
コミット
499e5f326f

+ 4 - 0
app/controller/report_controller.js

@@ -6,6 +6,7 @@
 
 const tenderMenu = require('../../config/menu').tenderMenu;
 const measureType = require('../const/tender').measureType;
+const accountGroup = require('../const/account_group').group;
 const JpcEx = require('../reports/rpt_component/jpc_ex');
 const JV = require('../reports/rpt_component/jpc_value_define');
 const rpt_xl_util = require('../reports/util/rpt_excel_util');
@@ -44,6 +45,9 @@ module.exports = app => {
                     stage_times = stage.times;
                     stage_status = stage.status;
                 }
+                for (const prjAcc of prjAccList) {
+                    prjAcc.account_group = accountGroup[prjAcc.account_group];
+                }
                 const renderData = {
                     tender: tender.data,
                     tenderInfo: tender.info,

+ 22 - 1
app/public/report/js/rpt_jspdf.js

@@ -79,6 +79,14 @@ let JpcJsPDFHelper = {
                     let cell = page.cells[j];
                     private_drawCell(doc, ctx, cell, fonts, styles, controls, newPageMergeBand);
                 }
+                // 计量有电子签名,要单独处理
+                for (let cell of page.signature_cells) {
+                    private_drawSignature(doc, ctx, cell, styles, controls, newPageMergeBand);
+                }
+                // 计量有电子签名日期,在处理上与cells一样
+                for (let cell of page.signature_date_cells) {
+                    private_drawCell(doc, ctx, cell, fonts, styles, controls, newPageMergeBand);
+                }
             }
         }
         doc.save(newName + '.pdf');
@@ -92,6 +100,20 @@ let JpcJsPDFHelper = {
             return rst;
         }
 
+        function private_drawSignature(doc, ctx, cell, styles, controls, mergeBand) {
+            ctx.beginPath();
+            let style = styles[cell[JV.PROP_STYLE]];
+            if (style) {
+                let isNeedMergeBand = private_chkIfInMergedBand(mergedBand, cell);
+                private_drawLine(cell, doc, ctx, style, JV.PROP_TOP, [JV.PROP_LEFT, JV.PROP_TOP],[JV.PROP_RIGHT, JV.PROP_TOP], mergedBand, styles, isNeedMergeBand);
+                private_drawLine(cell, doc, ctx, style, JV.PROP_RIGHT, [JV.PROP_RIGHT, JV.PROP_TOP],[JV.PROP_RIGHT, JV.PROP_BOTTOM], mergedBand, styles, isNeedMergeBand);
+                private_drawLine(cell, doc, ctx, style, JV.PROP_BOTTOM, [JV.PROP_RIGHT, JV.PROP_BOTTOM],[JV.PROP_LEFT, JV.PROP_BOTTOM], mergedBand, styles, isNeedMergeBand);
+                private_drawLine(cell, doc, ctx, style, JV.PROP_LEFT, [JV.PROP_LEFT, JV.PROP_BOTTOM],[JV.PROP_LEFT, JV.PROP_TOP], mergedBand, styles, isNeedMergeBand);
+            }
+            // private_drawCellText(doc, ctx, cell, fonts, controls);
+            ctx.closePath();
+        }
+
         function private_drawCell(doc, ctx, cell, fonts, styles, controls, mergedBand) {
             ctx.beginPath();
             let style = styles[cell[JV.PROP_STYLE]];
@@ -104,7 +126,6 @@ let JpcJsPDFHelper = {
             }
             private_drawCellText(doc, ctx, cell, fonts, controls);
             ctx.closePath();
-
         }
 
         function private_drawLine(cell, doc, ctx, style, styleBorderDest, startP, destP, mergedBand, styles, isNeedMergeBand) {

+ 13 - 12
app/public/report/js/rpt_main.js

@@ -285,18 +285,19 @@ let zTreeOprObj = {
                     rptSignatureHelper.originalRoleRelList = JSON.parse(result.signatureRelInfo[0].rel_content);
                     STAGE_AUDIT = result.stageAudit;
                     rptSignatureHelper.mergeSignDate();
-                    for (const page of pageRst.items) {
-                        if (page.signature_cells) {
-                            for (const sCell of page.signature_cells) {
-                                for (const role_rel of ROLE_REL_LIST) {
-                                    if (role_rel.signature_name === sCell.signature_name) {
-                                        sCell.path = role_rel.sign_path;
-                                        sCell.pre_path = role_rel.sign_path;
-                                    }
-                                }
-                            }
-                        }
-                    }
+                    rptSignatureHelper.mergeSignature(pageRst);
+                    // for (const page of pageRst.items) {
+                    //     if (page.signature_cells) {
+                    //         for (const sCell of page.signature_cells) {
+                    //             for (const role_rel of ROLE_REL_LIST) {
+                    //                 if (role_rel.signature_name === sCell.signature_name) {
+                    //                     sCell.path = role_rel.sign_path;
+                    //                     sCell.pre_path = role_rel.sign_path;
+                    //                 }
+                    //             }
+                    //         }
+                    //     }
+                    // }
                 } else {
                     CURRENT_ROLE_REL_ID = -1;
                     ROLE_REL_LIST = [];

+ 1 - 0
app/public/report/js/rpt_preview_common.js

@@ -17,6 +17,7 @@ function printPageLoading() {
             let svgArr = rptPrintHelper.buildSvgArr(pageData, actArea, G_OFFSET_X, G_OFFSET_Y);
             //let orientation = (pageData[JV.NODE_PAGE_INFO][JV.NODE_PAGE_SIZE][0] < pageData[JV.NODE_PAGE_INFO][JV.NODE_PAGE_SIZE][1])?"纵向":"横向";
             let orientation = "纵向";
+            // showPreviewData(svgArr, actArea, scaleFactor, sessionStorage.pageSize, orientation, orgPixelSize);
             showPreviewData(svgArr, actArea, scaleFactor, sessionStorage.pageSize, orientation, orgPixelSize);
         }
         window.print();

+ 129 - 1
app/public/report/js/rpt_print.js

@@ -10,7 +10,9 @@ let rptPrintHelper = {
             let params = rptControlObj.creatCommonExportParam(refRptTplIds);
             CommonAjax.postXsrfEx("/tender/report_api/getMultiReports", params, 60000, true, getCookie('csrfToken'),
                 function(result){
-                    //sessionStorage.currentPageData = JSON.stringify(zTreeOprObj.currentRptPageRst);
+                    for (let idx = 0; idx < result.data.length; idx++) {
+                        rptSignatureHelper.mergeSignature(result.data[idx]);
+                    }
                     sessionStorage.multiRptsData = JSON.stringify(result.data);
                     sessionStorage.pageSize = rptControlObj.getCurrentPageSize();
                     sessionStorage.orientation = rptControlObj.getCurrentOrientation();
@@ -68,6 +70,16 @@ let rptPrintHelper = {
                 svgPageArr.push(buildCellSvg(cell, fonts, styles, controls, page[JV.PROP_PAGE_MERGE_BORDER], pagesData[JV.BAND_PROP_MERGE_BAND],
                     offsetX - actAreaOffsetX, offsetY - actAreaOffsetY, adjustY, canvas, isHtoV, pixelSize, actAreaArr[idx]));
             }
+            // 计量有电子签名,要单独处理
+            for (let cell of page.signature_cells) {
+                svgPageArr.push(buildSignatureCellSvg(cell, styles, controls, page[JV.PROP_PAGE_MERGE_BORDER], pagesData[JV.BAND_PROP_MERGE_BAND],
+                    offsetX - actAreaOffsetX, offsetY - actAreaOffsetY, adjustY, canvas, isHtoV, pixelSize, actAreaArr[idx]));
+            }
+            // 计量有电子签名日期,在处理上与cells一样
+            for (let cell of page.signature_date_cells) {
+                svgPageArr.push(buildCellSvg(cell, fonts, styles, controls, page[JV.PROP_PAGE_MERGE_BORDER], pagesData[JV.BAND_PROP_MERGE_BAND],
+                    offsetX - actAreaOffsetX, offsetY - actAreaOffsetY, adjustY, canvas, isHtoV, pixelSize, actAreaArr[idx]));
+            }
             svgPageArr.push("</svg>");
             rst.push(svgPageArr);
         }
@@ -95,6 +107,70 @@ function getActualBorderStyle(cell, styles, mergeBorderStyle, pageBorderArea, bo
     return rst;
 }
 
+function buildSignatureCellSvg(cell, styles, controls, pageMergeBorder, rptMergeBorder, offsetX, offsetY, adjustY, canvas, isHtoV, pixelSize, actArea) {
+    let rst = [];
+    let style = styles[cell[JV.PROP_STYLE]];
+    let mergeBandStyle = null;
+    if (rptMergeBorder) {
+        mergeBandStyle = styles[rptMergeBorder[JV.PROP_STYLE][JV.PROP_ID]];
+    }
+    let font = cell[JV.PROP_FONT];
+    if (typeof font === 'string') {
+        font = fonts[cell[JV.PROP_FONT]];
+    }
+    let left = parseInt(cell[JV.PROP_AREA][JV.PROP_LEFT]) + offsetX + 0.5,
+        right = parseInt(cell[JV.PROP_AREA][JV.PROP_RIGHT]) + offsetX + 0.5,
+        top = parseInt(cell[JV.PROP_AREA][JV.PROP_TOP]) + offsetY + adjustY,
+        bottom = parseInt(cell[JV.PROP_AREA][JV.PROP_BOTTOM]) + offsetY + adjustY
+    ;
+    let HtoVStr = "";
+    if (isHtoV) {
+        //HtoVStr = ` transform="translate(`+ pixelSize[1] + `,0) rotate(90)"`;
+        // HtoVStr = ` transform="translate(`+ (actArea.Bottom - actArea.Top + 5) + `,0) rotate(90)"`;
+        HtoVStr = ` transform="translate(`+ (actArea.Bottom - actArea.Top + 5) + `,` + (actArea.Left - actArea.Top ) + `) rotate(90)"`;
+        //console.log(actArea);
+    }
+    if (style) {
+        let leftBS = getActualBorderStyle(cell, styles, mergeBandStyle, (pageMergeBorder)?pageMergeBorder:rptMergeBorder[JV.PROP_AREA], JV.PROP_LEFT);
+        // if (style[JV.PROP_LEFT] && parseFloat(style[JV.PROP_LEFT][JV.PROP_LINE_WEIGHT]) > 0) {
+        if (leftBS && parseFloat(leftBS[JV.PROP_LINE_WEIGHT]) > 0) {
+            rst.push("<line x1='" + left + "' y1='" + top +
+                "' x2='" + left + "' y2='" + bottom +
+                "' style='stroke:rgb(0,0,0);stroke-width:" + leftBS[JV.PROP_LINE_WEIGHT] + "'" + HtoVStr + "/>")
+        }
+        let rightBS = getActualBorderStyle(cell, styles, mergeBandStyle, (pageMergeBorder)?pageMergeBorder:rptMergeBorder[JV.PROP_AREA], JV.PROP_RIGHT);
+        // if (style[JV.PROP_RIGHT] && parseFloat(style[JV.PROP_RIGHT][JV.PROP_LINE_WEIGHT]) > 0) {
+        if (rightBS && parseFloat(rightBS[JV.PROP_LINE_WEIGHT]) > 0) {
+            rst.push("<line x1='" + right + "' y1='" + top +
+                "' x2='" + right + "' y2='" + bottom +
+                "' style='stroke:rgb(0,0,0);stroke-width:" + rightBS[JV.PROP_LINE_WEIGHT] +"'" + HtoVStr + "/>")
+        }
+        let topBS = getActualBorderStyle(cell, styles, mergeBandStyle, (pageMergeBorder)?pageMergeBorder:rptMergeBorder[JV.PROP_AREA], JV.PROP_TOP);
+        // if (style[JV.PROP_TOP] && parseFloat(style[JV.PROP_TOP][JV.PROP_LINE_WEIGHT]) > 0) {
+        if (topBS && parseFloat(topBS[JV.PROP_LINE_WEIGHT]) > 0) {
+            rst.push("<line x1='" + left + "' y1='" + top +
+                "' x2='" + right + "' y2='" + top +
+                "' style='stroke:rgb(0,0,0);stroke-width:" + topBS[JV.PROP_LINE_WEIGHT] +"'" + HtoVStr + "/>")
+        }
+        let bottomBS = getActualBorderStyle(cell, styles, mergeBandStyle, (pageMergeBorder)?pageMergeBorder:rptMergeBorder[JV.PROP_AREA], JV.PROP_BOTTOM);
+        // if (style[JV.PROP_BOTTOM] && parseFloat(style[JV.PROP_BOTTOM][JV.PROP_LINE_WEIGHT]) > 0) {
+        if (bottomBS && parseFloat(bottomBS[JV.PROP_LINE_WEIGHT]) > 0) {
+            rst.push("<line x1='" + left + "' y1='" + bottom +
+                "' x2='" + right + "' y2='" + bottom +
+                "' style='stroke:rgb(0,0,0);stroke-width:" + bottomBS[JV.PROP_LINE_WEIGHT] +"'" + HtoVStr + "/>")
+        }
+    }
+    let control = cell[JV.PROP_CONTROL];
+    if (typeof control === 'string') {
+        control = controls[cell[JV.PROP_CONTROL]];
+    }
+    if (cell.pic || cell.path) {
+        buildImage(rst, cell, control, offsetX, offsetY, adjustY, isHtoV, HtoVStr);
+    }
+
+    return rst.join("");
+}
+
 function buildCellSvg(cell, fonts, styles, controls, pageMergeBorder, rptMergeBorder, offsetX, offsetY, adjustY, canvas, isHtoV, pixelSize, actArea) {
     let rst = [];
     let style = styles[cell[JV.PROP_STYLE]];
@@ -157,6 +233,58 @@ function buildCellSvg(cell, fonts, styles, controls, pageMergeBorder, rptMergeBo
     return rst.join("");
 }
 
+function buildImage(destRst, cell, control, offsetX, offsetY, adjustY, isHtoV, HtoVStr) {
+    let href = '';
+    if (cell.pic) {
+        href = 'href="' + cell.pic +'"';
+    } else {
+        href = 'xlink:href="' + cell.path +'"';
+    }
+    const area = getProperSignatureArea(cell, control, offsetX, offsetY);
+    destRst.push('<image x="' + area[0] + '" y="' + area[1] + '" width="' + (area[2] - area[0]) + '" height="' + (area[3] - area[1]) + '" ');
+    destRst.push(href + HtoVStr + ' />');
+}
+
+function getProperSignatureArea(cell, control, offsetX, offsetY) {
+    // 约定默认长宽比例是2:1,图片分辨率是600*300
+    const rst = [0, 0, 0, 0]; // left, top, right, bottom
+    if (cell && cell[JV.PROP_AREA]) {
+        let width = cell[JV.PROP_AREA][JV.PROP_RIGHT] - cell[JV.PROP_AREA][JV.PROP_LEFT],
+            height = cell[JV.PROP_AREA][JV.PROP_BOTTOM] - cell[JV.PROP_AREA][JV.PROP_TOP];
+        if (width > height * 2) {
+            width = height * 2;
+        } else {
+            height = width / 2;
+        }
+        switch (control[JV.CONTROL_PROPS[JV.CONTROL_PROP_IDX_HORIZON]]) {
+            case 'left':
+                rst[0] = cell[JV.PROP_AREA][JV.PROP_LEFT];
+                rst[1] = cell[JV.PROP_AREA][JV.PROP_TOP];
+                rst[2] = rst[0] + width;
+                rst[3] = rst[1] + height;
+                break;
+            case 'right':
+                rst[2] = cell[JV.PROP_AREA][JV.PROP_RIGHT];
+                rst[3] = cell[JV.PROP_AREA][JV.PROP_BOTTOM];
+                rst[0] = rst[2] - width;
+                rst[1] = rst[3] - height;
+                break;
+            default:
+                //center
+                rst[0] = (cell[JV.PROP_AREA][JV.PROP_LEFT] + cell[JV.PROP_AREA][JV.PROP_RIGHT] - width) / 2;
+                rst[1] = cell[JV.PROP_AREA][JV.PROP_TOP];
+                rst[2] = rst[0] + width;
+                rst[3] = rst[1] + height;
+                break;
+        }
+    }
+    rst[0] = rst[0] + offsetX;
+    rst[2] = rst[2] + offsetX;
+    rst[1] = rst[1] + offsetY;
+    rst[3] = rst[3] + offsetY;
+    return rst;
+}
+
 function buildText(destRst, cell, font, control, offsetX, offsetY, adjustY, canvas, isHtoV, HtoVStr) {
     let orgFontHeight = parseInt(font[JV.FONT_PROPS[JV.FONT_PROP_IDX_HEIGHT]]);
     let fontWeight = (font[JV.FONT_PROPS[JV.FONT_PROP_IDX_BOLD]] === 'T')?"bold":"normal";

+ 23 - 7
app/public/report/js/rpt_signature.js

@@ -4,6 +4,8 @@
 
 'use strict'
 
+const DFT_ROLE_NAME = '';
+
 let rptSignatureHelper = {
     currentSelectedESignAccDom: null,
     currentSelectedESignAccIdx: -1,
@@ -23,13 +25,13 @@ let rptSignatureHelper = {
         const acc_role_keys = [];
         for (let accIdx = 0; accIdx < PRJ_ACCOUNT_LIST.length; accIdx++) {
             const prjAccount = PRJ_ACCOUNT_LIST[accIdx];
-            let companyKey = prjAccount.company;
+            let companyKey = prjAccount.account_group;
             let roleKey = prjAccount.role;
             if (companyKey === '') {
                 companyKey = '其他单位';
             }
             if (roleKey === '') {
-                roleKey = '工程师';
+                roleKey = DFT_ROLE_NAME;
             }
             let keyIdx = acc_role_keys.indexOf(companyKey);
             if (keyIdx < 0) {
@@ -102,7 +104,7 @@ let rptSignatureHelper = {
                 roleRelObj.user_name = userAcc.name;
                 roleRelObj.acc_id = userAcc.id;
                 roleRelObj.type = '用户';
-                roleRelObj.role = (userAcc.role === '')?"工程师":userAcc.role;
+                roleRelObj.role = (userAcc.role === '')?DFT_ROLE_NAME:userAcc.role;
                 ROLE_REL_LIST.push(roleRelObj);
             } else if (roleAcc) {
                 // 创建相关dom元素
@@ -116,7 +118,7 @@ let rptSignatureHelper = {
                 roleRelObj.user_name = userAcc.name;
                 roleRelObj.acc_id = userAcc.id;
                 roleRelObj.type = '角色';
-                roleRelObj.role = (userAcc.role === '')?"工程师":userAcc.role;
+                roleRelObj.role = (userAcc.role === '')?DFT_ROLE_NAME:userAcc.role;
                 roleRelObj.role_name = roleAcc.name;
                 ROLE_REL_LIST.push(roleRelObj);
             }
@@ -234,7 +236,7 @@ let rptSignatureHelper = {
     },
     pushDomElementByUser: function (elementsStrArr, userName, userRole) {
         elementsStrArr.push('<p class=" d-flex justify-content-between m-0"><span>' + userName +
-            '-<small class="text-muted">' + ((userRole === '')?"工程师":userRole) +
+            '-<small class="text-muted">' + ((userRole === '')?DFT_ROLE_NAME:userRole) +
             '</small></span><a onclick="rptSignatureHelper.removeSignature(this)" class="text-danger"><i class="fa fa-remove" title="移除签名"></i></a></p>');
         // rptSignatureHelper.pushDatePickerDom(elementsStrArr);
     },
@@ -366,7 +368,7 @@ let rptSignatureHelper = {
             const params = {};
             params.name = $('#acc_role_name')[0].value;
             const selectedAcc = PRJ_ACCOUNT_LIST[$('#project_account_select_dom')[0].selectedOptions[0].value];
-            const roleName = (selectedAcc.role === '')?'工程师':selectedAcc.role;
+            const roleName = (selectedAcc.role === '')?DFT_ROLE_NAME:selectedAcc.role;
             params.bind_acc_id = selectedAcc.id;
             params.prj_id = PROJECT_ID;
             params.tender_id = TENDER_ID;
@@ -419,7 +421,7 @@ let rptSignatureHelper = {
             domArr.push('</a>');
             //3. 显示名称
             let acc = rptSignatureHelper.getUserAccount(role.bind_acc_id);
-            domArr.push('<i class="fa fa-user"></i> ' + role.name + '<p>' + acc.name + '-<small class="text-muted">' + ((acc.role === '')?"工程师":acc.role) + '</small></p>');
+            domArr.push('<i class="fa fa-user"></i> ' + role.name + '<p>' + acc.name + '-<small class="text-muted">' + ((acc.role === '')?DFT_ROLE_NAME:acc.role) + '</small></p>');
             ulDom.append(domArr.join(' '));
         }
     },
@@ -433,6 +435,20 @@ let rptSignatureHelper = {
         }
         return rst;
     },
+    mergeSignature: function (pageData) {
+        for (const page of pageData.items) {
+            if (page.signature_cells) {
+                for (const sCell of page.signature_cells) {
+                    for (const role_rel of ROLE_REL_LIST) {
+                        if (role_rel.signature_name === sCell.signature_name) {
+                            sCell.path = role_rel.sign_path;
+                            sCell.pre_path = role_rel.sign_path;
+                        }
+                    }
+                }
+            }
+        }
+    },
     mergeSignDate: function () {
         if (ROLE_REL_LIST && ROLE_REL_LIST.length > 0 && STAGE_AUDIT && STAGE_AUDIT.length > 0) {
             for (let rridx = 0; rridx < ROLE_REL_LIST.length; rridx++) {

+ 2 - 2
app/service/project_account.js

@@ -208,7 +208,7 @@ module.exports = app => {
          */
         async getAccountByProjectId(projectId) {
             const condition = {
-                columns: ['id', 'account', 'name', 'company', 'role', 'mobile', 'telephone', 'enable', 'permission', 'sign_path'],
+                columns: ['id', 'account', 'name', 'company', 'account_group', 'role', 'mobile', 'telephone', 'enable', 'permission', 'sign_path'],
                 where: { project_id: projectId, is_admin: 0 },
             };
             const accountList = await this.getAllDataByCondition(condition);
@@ -224,7 +224,7 @@ module.exports = app => {
          */
         async getAllAccountByProjectId(projectId) {
             const condition = {
-                columns: ['id', 'account', 'name', 'company', 'role', 'mobile', 'telephone', 'enable', 'permission', 'sign_path'],
+                columns: ['id', 'account', 'name', 'company', 'account_group', 'role', 'mobile', 'telephone', 'enable', 'permission', 'sign_path'],
                 where: { project_id: projectId},
             };
             const accountList = await this.getAllDataByCondition(condition);