打印經常需要根據用戶需求自定義,整個問題解決思路是:
把打印內看成三個部分,頭部、明細區、腳步;
根據選中的元數據,輸出界面內容:
<ul class="print-head" style="margin:0;padding:0;height:100px;display: flex;justify-content:space-between;flex-flow: wrap row;align-items:flex-start;list-style:none;">
<li v-for="(item,i) in checkedPrintHead" :key="i" class="print-item" style="margin:0;padding:0;margin-bottom:5px;flex:0 0 33.3%;display:flex;justify-content:space-between">
<span style="margin:0;padding:0;flex:0 0 40%">{{ item.text }}:</span>
<span class="hidden" style="margin:0;padding:0;flex:1 1 60%">{{ item.value }}</span>
</li>
</ul>
....
<table style="margin:0 auto;border: 1px solid #000;border-collapse: collapse" class="print-table">
<thead>
<tr>
<!-- v-dragging="{item:item,list:checkedTableHead,group:'tbHead'}" -->
<th v-for="(item,i) in checkedTableHead" :key="i" :style="`width:${item.width}px;border: 1px solid #000;border-collapse: collapse`">{{ item.text }}</th>
</tr>
</thead>
<tbody class="none">
<tr v-for="(rowData,i) in printData" :key="i">
<td v-for="(item ,index) in checkedTableHead" :key="index" :style="`width:${item.width}px;border: 1px solid #000;border-collapse: collapse;vertical-align:middle;`" align="center">
{{ $getCodeLabel(rowData[item.key]) === null ? '-' : $getCodeLabel(rowData[item.key]) }}
</td>
</tr>
<tr>
<td v-for="(item ,index) in checkedTableHead" :key="index" :style="`width:${item.width}px;border: 1px solid #000;border-collapse: collapse;text-align:center;padding-left:${totalTextArrayBool(item)?item.width:'0'}px`" :tdata="totalTextArrayBool(item)?'AllSum':''" format="#.###" >
{{ getTfootHtmlByItem(item,index) }}
</td>
</tr>
</tbody>
<tfoot>
<!-- <tr>
<td v-for="(item ,index) in checkedTableHead" :key="index" :style="`width:${item.width}px;border: 1px solid #000;border-collapse: collapse;text-align:center;padding-left:${(item.text ==='份數' || item.text === '本數')?item.width:'0'}px`" :tdata="(item.text ==='份數' || item.text === '本數')?'AllSum':''" format="#.###" >
{{ getTfootHtmlByItem(item,index) }}
</td>
</tr> -->
</tfoot>
</table>
...
看看效果:
頁面需要自定義打印。
設置即是設置打印模板:
這個模板分爲三個區域:
表頭區、表尾區、中間明細區。
點擊打印預覽:
這裏,我們寫了一個打印組件,實現上述功能。
組件接受三個參數:
表頭、明細數據、模板數據
props: {
formPrintData: { // 表單參數數據。
type: Array,
required: false,
default() {
return []
}
},
printData: {
type: Array,
required: false,
default() {
return []
}
},
templateData: {
type: Array,
default() {
return []
}
},
defaultData: { //這個沒有用到
type: Array,
default() {
return []
}
}
},
組件接受到模板參數後,對其進行相關處理:
employTemplateData: { // 當前應用模板
get() {
// var target = this.templateData.find(item => item.isdefault === 1)
// if (!target) {
// target = this.templateData.find(item => item.isstandardtemplage === 1)
// }
var target = ''
var targetList = this.templateData.filter(item => +item.isdefault === 1)
// 沒有isdefault = 1,取isstandardtemplage = 1
if (targetList.length === 0) {
target = this.templateData[0]
} else { // 有isdefault等於1時,要判斷isstandardtemplage,有爲0的情況就取0,沒有就取1,即默認的標準模板。
var customerTemplate = targetList.find(item => +item.isstandardtemplage === 0)
if (customerTemplate) target = customerTemplate
else target = targetList[0]
}
if (target) {
if (typeof (target.templatecontent) === 'string') {
target.templatecontent = JSON.parse(target.templatecontent)
}
if (this.formPrintData.length > 0) {
console.log('target', target)
// target.templatecontent.printHead = JSON.parse(JSON.stringify(this.formPrintData))
// target.templatecontent.printFoot = JSON.parse(JSON.stringify(this.formPrintData))
// 這裏的代碼是因爲模板有時候沒有傳遞printData這些字段,避免undefined報錯。
if (!target.templatecontent.printHead) {
target.templatecontent.printHead = []
}
if (!target.templatecontent.printFoot) {
target.templatecontent.printFoot = []
}
// 這裏由於開始的設計有誤,沒有將顯示的表單信息和渲染數據的表單信息分開,合在一起了。
// 所以需要根據模板裏面的表單的值,對比傳遞進來的表單,找到對應的值即可。
console.log('target.templatecontent.printFoot:', target.templatecontent.printFoot)
target.templatecontent.printHead.forEach(item => {
var matchedItem = this.formPrintData.find(dataItem => dataItem.text === item.text)
item.value = matchedItem === undefined ? item.value : matchedItem.value
})
target.templatecontent.printFoot.forEach(item => {
var matchedItem = this.formPrintData.find(dataItem => dataItem.text === item.text)
item.value = matchedItem === undefined ? item.value : matchedItem.value
})
}
return target
}
},
set(val) {
return val
}
},
ps:
- 這裏var targetList = this.templateData.filter(item => +item.isdefault === 1) “+“是類型轉換,把字符串轉換爲int類型。
- item.value = matchedItem === undefined ? item.value : matchedItem.value 這句話是根據條件判斷對item.value進行賦值。
組件的結構:
<!-- 表格打印設置組件 -->
<template>
//模板...
</template>
<script>
import printItemControl from './printItemControl'
import Bus from '@/utils/Bus'
import { getLodop } from '@/assets/LodopFuncsNew' // 導入模塊
import { savePrintTemplateData, removePrintTemplateData } from '@/api/webPrint'
// import { deepClone } from '@/utils/Common'
export default {
components: {
printItemControl
},
props: {
//父表單傳遞的參數
},
data() {
return {
updateTitleVisible: false,
updateTitleError: true,
updateTitleName: '',
selectedItem: {},
updateError: true,
updateTempLateName: '',
updateBoxVisible: false,
alertBoxVisible: false,
errMessage: true,
addTempLateName: '',
messageBoxVisible: false,
// direction: 1, // 1豎,2橫
// templateData
// checkedTexts: [],
// printHeadHeight: '10',
dialogTableVisible: false,
LODOP: '' // 準備用來調用getLodop獲取LODOP對象
}
},
computed: {
employTemplateData: {
//把模板和數據綁定
},
......
},
watch: {
dialogTableVisible(newVal, oldVal) {
if (newVal === false) {
Bus.$emit('getPrintDataAdd')
}
}
},
created() {
// 下面這條句子應該放在請求的then裏面。
// this.checkedTexts = this.employTemplateData.templatecontent.printHead.filter(item => item.checked === true).map(item => item.text)
Bus.$off('addExport')
Bus.$on('addExport', () => {
this.addExport()
})
Bus.$off('addPreview')
Bus.$on('addPreview', () => {
this.addPreview()
})
Bus.$off('addPrint')
Bus.$on('addPrint', () => {
this.addPrint()
})
Bus.$off('addSet')
Bus.$on('addSet', () => {
this.addSet()
})
},
mounted() {
},
methods: {
...
}
}
</script>
<style rel='stylesheet/scss' lang='scss' scoped>
....
</style>
注意修改標題代碼 用到$set()方法:
代碼:
confirmTitle() {
if (this.updateTitleName) {
// this.validatorUpdate()
this.updateTitleError = true
this.updateTitleVisible = false
this.$set(this.employTemplateData.templatecontent, 'title', this.updateTitleName)
} else {
this.updateTitleError = '打印表頭名稱不能爲空!'
}
},
打印模板組件的使用:
從業務上要理解上面的代碼,先看看系統模板初始化:(這個在這個打印組件以外)。
templateInitData: {
// add
guid: "",
userid: null,
templatecontent: {
// 註釋 title標題
title: "財政審批退付申請",
direction: 2,
printHeadHeight: 50, // 打印頭部區域的高度,單位mm
printHead: [
// 註釋 表格上面內容
// { text: "製表人", checked: true },
{ text: "資金退付書編號", checked: true },
{ text: "開具日期", checked: true },
{ text: "原繳款書編號", checked: true },
{ text: "執收單位", checked: true },
{ text: "繳款人名稱", checked: true },
{ text: "繳款人賬號", checked: true },
{ text: "繳款人開戶行", checked: true },
{ text: "收款人名稱", checked: true },
{ text: "收款人賬號", checked: true },
{ text: "收款人開戶行", checked: true },
{ text: "退付原因", checked: true }
],
tableHead: [
// 註釋 表格內容
{
text: "收費項目編碼",
key: "nontaxcode",
width: "200",
checked: true
},
{
text: "收費項目名稱",
key: "nontaxname",
width: "200",
checked: true
},
{ text: "收費金額", key: "amt", width: "200", checked: true },
{
text: "退付金額",
key: "rfdamt",
width: "200",
checked: true
}
],
printFoot: [
// 註釋 表格下面內容
{
text: "製表人",
value: this.$store.state.user.name,
checked: true
},
{
text: "打印時間",
value: new Date().toLocaleString(),
checked: true
}
]
},
isdefault: 1, // 是否現在使用的模板
templatecode: this.$route.path + "/add",
templatename: "標準模板",
isstandardtemplage: 1 // 是否標準模板
},
數據中的幾個變量名稱對應的內容圖示:
後端相關查詢的數據(例子):
{"code":"200","data":[{"guid":"8a8181846d80e0ea016d80fe1a050006","year":"2019","admdivcode":"420822","userid":"F77F3055AABCE8803C29DF683825B7BF","templatecode":"/czzsgl/fssrtfgl/dwlrtfsq/add","templatename":"222","isstandardtemplage":0,"templatecontent":"{\"title\":\"單位錄入退付申請\",\"direction\":2,\"printHeadHeight\":50,\"printHead\":[{\"text\":\"資金退付書編號\",\"checked\":true,\"value\":\"RFD20190930000001\"},{\"text\":\"開具日期\",\"checked\":true,\"value\":\"2019-09-30 00:00:00\"},{\"text\":\"原繳款書編號\",\"checked\":true,\"value\":\"0011687662\"},{\"text\":\"執收單位\",\"checked\":true,\"value\":\"湖北省國土資源廳沙洋監獄管理局國土資源局\"},{\"text\":\"退款人名稱\",\"checked\":true,\"value\":\"申雯鳳\"},{\"text\":\"退款人賬號\",\"checked\":true,\"value\":null},{\"text\":\"退款人開戶行\",\"checked\":true,\"value\":null},{\"text\":\"收款人名稱\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"收款人賬號\",\"checked\":true,\"value\":\"1755 4101 0400 0353 1\"},{\"text\":\"收款人開戶行\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"退付原因\",\"checked\":true,\"value\":\"沙洋縣支行退付\"}],\"tableHead\":[{\"text\":\"收費項目編碼\",\"key\":\"nontaxcode\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費項目名稱\",\"key\":\"nontaxname\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費金額\",\"key\":\"amt\",\"width\":\"200\",\"checked\":true},{\"text\":\"退付金額\",\"key\":\"rfdamt\",\"width\":\"200\",\"checked\":true}],\"printFoot\":[{\"text\":\"製表人\",\"value\":\"王鳳霞\",\"checked\":true},{\"text\":\"打印時間\",\"value\":\"2019/9/30 下午3:04:53\",\"checked\":true}]}","isdefault":0,"remark":null,"isenabled":1},{"guid":"8a8181846d80e0ea016d80ffbb0a0007","year":"2019","admdivcode":"420822","userid":"F77F3055AABCE8803C29DF683825B7BF","templatecode":"/czzsgl/fssrtfgl/dwlrtfsq/add","templatename":"333","isstandardtemplage":0,"templatecontent":"{\"title\":\"單位錄入退付申請\",\"direction\":2,\"printHeadHeight\":50,\"printHead\":[{\"text\":\"資金退付書編號\",\"checked\":true,\"value\":\"RFD20190930000001\"},{\"text\":\"開具日期\",\"checked\":true,\"value\":\"2019-09-30 00:00:00\"},{\"text\":\"原繳款書編號\",\"checked\":true,\"value\":\"0011687662\"},{\"text\":\"執收單位\",\"checked\":true,\"value\":\"湖北省國土資源廳沙洋監獄管理局國土資源局\"},{\"text\":\"退款人名稱\",\"checked\":true,\"value\":\"申雯鳳\"},{\"text\":\"退款人賬號\",\"checked\":true,\"value\":null},{\"text\":\"退款人開戶行\",\"checked\":true,\"value\":null},{\"text\":\"收款人名稱\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"收款人賬號\",\"checked\":true,\"value\":\"1755 4101 0400 0353 1\"},{\"text\":\"收款人開戶行\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"退付原因\",\"checked\":true,\"value\":\"沙洋縣支行退付\"}],\"tableHead\":[{\"text\":\"收費項目編碼\",\"key\":\"nontaxcode\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費項目名稱\",\"key\":\"nontaxname\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費金額\",\"key\":\"amt\",\"width\":\"200\",\"checked\":true},{\"text\":\"退付金額\",\"key\":\"rfdamt\",\"width\":\"200\",\"checked\":true}],\"printFoot\":[{\"text\":\"製表人\",\"value\":\"王鳳霞\",\"checked\":true},{\"text\":\"打印時間\",\"value\":\"2019/9/30 下午3:04:53\",\"checked\":true}]}","isdefault":1,"remark":null,"isenabled":1},{"guid":"8a8181846d80e0ea016d80fc8c600004","year":"2019","admdivcode":"420822","userid":null,"templatecode":"/czzsgl/fssrtfgl/dwlrtfsq/add","templatename":"標準模板","isstandardtemplage":1,"templatecontent":"{\"title\":\"單位錄入退付申請\",\"direction\":2,\"printHeadHeight\":50,\"printHead\":[{\"text\":\"資金退付書編號\",\"checked\":true},{\"text\":\"開具日期\",\"checked\":true},{\"text\":\"原繳款書編號\",\"checked\":true},{\"text\":\"執收單位\",\"checked\":true},{\"text\":\"退款人名稱\",\"checked\":true},{\"text\":\"退款人賬號\",\"checked\":true},{\"text\":\"退款人開戶行\",\"checked\":true},{\"text\":\"收款人名稱\",\"checked\":true},{\"text\":\"收款人賬號\",\"checked\":true},{\"text\":\"收款人開戶行\",\"checked\":true},{\"text\":\"退付原因\",\"checked\":true}],\"tableHead\":[{\"text\":\"收費項目編碼\",\"key\":\"nontaxcode\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費項目名稱\",\"key\":\"nontaxname\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費金額\",\"key\":\"amt\",\"width\":\"200\",\"checked\":true},{\"text\":\"退付金額\",\"key\":\"rfdamt\",\"width\":\"200\",\"checked\":true}],\"printFoot\":[{\"text\":\"製表人\",\"value\":\"王鳳霞\",\"checked\":true},{\"text\":\"打印時間\",\"value\":\"2019/9/30 下午3:04:53\",\"checked\":true}]}","isdefault":0,"remark":null,"isenabled":1},{"guid":"8a8181846d80e0ea016d80fd0c430005","year":"2019","admdivcode":"420822","userid":"F77F3055AABCE8803C29DF683825B7BF","templatecode":"/czzsgl/fssrtfgl/dwlrtfsq/add","templatename":"111","isstandardtemplage":0,"templatecontent":"{\"title\":\"單位錄入退付申請\",\"direction\":2,\"printHeadHeight\":50,\"printHead\":[{\"text\":\"資金退付書編號\",\"checked\":true,\"value\":\"RFD20190930000001\"},{\"text\":\"開具日期\",\"checked\":true,\"value\":\"2019-09-30 00:00:00\"},{\"text\":\"原繳款書編號\",\"checked\":true,\"value\":\"0011687662\"},{\"text\":\"執收單位\",\"checked\":true,\"value\":\"湖北省國土資源廳沙洋監獄管理局國土資源局\"},{\"text\":\"退款人名稱\",\"checked\":true,\"value\":\"申雯鳳\"},{\"text\":\"退款人賬號\",\"checked\":true,\"value\":null},{\"text\":\"退款人開戶行\",\"checked\":true,\"value\":null},{\"text\":\"收款人名稱\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"收款人賬號\",\"checked\":true,\"value\":\"1755 4101 0400 0353 1\"},{\"text\":\"收款人開戶行\",\"checked\":true,\"value\":\"農行沙洋縣支行\"},{\"text\":\"退付原因\",\"checked\":true,\"value\":\"沙洋縣支行退付\"}],\"tableHead\":[{\"text\":\"收費項目編碼\",\"key\":\"nontaxcode\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費項目名稱\",\"key\":\"nontaxname\",\"width\":\"200\",\"checked\":true},{\"text\":\"收費金額\",\"key\":\"amt\",\"width\":\"200\",\"checked\":true},{\"text\":\"退付金額\",\"key\":\"rfdamt\",\"width\":\"200\",\"checked\":true}],\"printFoot\":[{\"text\":\"製表人\",\"value\":\"王鳳霞\",\"checked\":true},{\"text\":\"打印時間\",\"value\":\"2019/9/30 下午3:04:53\",\"checked\":true}]}","isdefault":0,"remark":null,"isenabled":1}]}
引入模板組件:
<tablePrintSetAdd
:print-data="currentRow.details"
:template-data="templateDataList"
:form-print-data="formPrintData"
/>
調用的例子(結構):
export default {
components: {
toolBar,
layer,
tablePrintSetAdd // 表格打印設置組件。add
},
data() {
//數據...
},
computed: {
// 註釋 表單數據
formPrintData() {
return [
{
text: "資金退付書編號",
value: this.currentRow.rfdbillno,
checked: true
},
{ text: "開具日期", value: this.currentRow.rfdbilldate, checked: true },
{
text: "原繳款書編號",
value: this.currentRow.paybillno,
checked: true
...
];
}
},
watch: {
// 是否獲取模板 打開這dialog時候,獲取模板
dialogTableVisible(n) {
if (n) {
this.whetherGetPrintTemplate();
}
}
},
created() { //在渲染html前,給工具條綁定事件
// 關閉
Bus.$off("billClose");
Bus.$on("billClose", () => {
Bus.$emit("onSubmit");
this.dialogTableVisible = false;
});
// 保存
Bus.$off("billSave");
Bus.$on("billSave", () => {
this.save();
});
// 修改
Bus.$off("billUpdate2");
Bus.$on("billUpdate2", () => {
this.billUpdate2();
});
// 取消
Bus.$off("billAbolish");
Bus.$on("billAbolish", () => {
this.dialogTableVisible = false;
});
// 設置
// 組件創建時,立即獲取打印模板數據。
// this.getPrintData()// add
Bus.$off("getPrintDataAdd");
Bus.$on("getPrintDataAdd", () => {
this.getPrintData();
});
// 打印
Bus.$off("getPrintDataAdd");
Bus.$on("getPrintDataAdd", () => {
this.getPrintData();
});
},
mounted() {
// console.log("掛載完成!");
},
updated() {},
methods: {
//各類操作方法
}
};
watch 當中加載模板(模板畢竟只是開始加載一次);
模板與數據:
點擊工具類相關按鈕的時候,先激發一個事件
這裏addset改變一個變量;
在打印組件中:這個變量控制一個div
模板設置和打印輸出用的是同一個頁面。
但設置的時候,是不用顯示數據的?
這裏應用了class樣式,頁面上是不顯示的,但給lodop的時候,lodop 是不知道這個class的,這樣,通過lodop預覽的時候,數據就顯示出來了。
lodop打印:
printSet() {
this.LODOP = getLodop()
this.LODOP.PRINT_INIT('表格預覽')
console.log(111,this.employTemplateData);
this.LODOP.SET_PRINT_PAGESIZE(this.employTemplateData.templatecontent.direction, 0, 0, 'A4')
// console.log('當前設置的高度是:', this.employTemplateData.templatecontent.printHeadHeight)
var printHeadHeight = +this.employTemplateData.templatecontent.printHeadHeight
var strStyle = '<style> table,td,th {border: 1px solid #000;border-collapse: collapse;}</style>'
this.LODOP.ADD_PRINT_TABLE(`${printHeadHeight + 10}mm`, '5%', '95%', `90%`, strStyle + this.$refs.div2.innerHTML)
this.LODOP.SET_PRINT_STYLEA(0, 'Vorient', 3)
this.LODOP.SET_PRINT_STYLEA(0, 'Offset2Top', `${-printHeadHeight}mm`) // 表示從次頁開始的上邊距偏移量
this.LODOP.ADD_PRINT_HTM('1%', '2%', '95%', `${printHeadHeight}mm`, this.$refs.div1.innerHTML)
// this.LODOP.SET_PRINT_STYLEA(0, 'ItemType', 1) // 此行代碼的作用是使得div1中的內容隨着分頁反覆出現,相當於是頁眉。
this.LODOP.ADD_PRINT_HTM('2%', '0%', '95%', '10%', this.$refs.div3.innerHTML)
this.LODOP.SET_PRINT_STYLEA(0, 'LinkedItem', 1) // 內容項與別人關聯後,會緊跟被關聯者之後打印,位置和區域大小隨被關聯項而定,此時其Top和left不再是上邊距和左邊距,而是與關聯項的間隔空隙及左邊距偏移。0表示自己,1表示第一個,-1表示自己的前一個。
},