mousheng / lowcoder_CN

🔥🔥🔥开源Retool, Tooljet和Appsmith的替代方案,码匠的开源版
GNU Affero General Public License v3.0
159 stars 47 forks source link

[Feat]:通过docxtemplater库生成docx文件示例 #67

Open exqmjmz opened 10 months ago

exqmjmz commented 10 months ago

在企业应用中绕不过去生成docx文件,本次示例为使用lowcoder直接引用应用内数据,通过调用docxtemplater库生成docx文件 docxtemplater是一个引用word模版,在模版中定义好数据占位符,并通过占位符替换生成docx文件的javascript库

需引入以下两个第三方库 1、docxtemplater 项目地址:https://github.com/open-xml-templating/docxtemplater 安装地址:https://cdn.jsdelivr.net/npm/docxtemplater@3.42.1/build/docxtemplater.min.js 2、PizZip 项目地址:https://github.com/open-xml-templating/pizzip 安装地址:https://unpkg.com/pizzip@3.1.4/dist/pizzip.min.js 3、FileSaver.js 项目地址:https://github.com/eligrey/FileSaver.js 安装地址:https://unpkg.com/file-saver@2.0.5/dist/FileSaver.min.js

导入完成以上库后,在应用界面导入以下应用json文件

image 生成订单DOCX文件.json

image

DOCX模版 image DEMO DOCX模版 订单模版.docx

生成DOCX文件效果 image 生成的DEMO DOCX文件 output (13).docx

demo代码

const docxTemplateBase64 = '模版文件Base64'

//获取表单信息
const invoiceData = JSON.parse(JSON.stringify(form1.data))
//获取订单表格信息
invoiceData.orderinfos = table1.data
//计算总价
invoiceData.totalPrice = (invoiceData.totalIncludingTax-invoiceData.totalIncludingTax*invoiceData.discount).toFixed(2)
invoiceData.invoiceDate = dateRange1.start
invoiceData.endDate = dateRange1.end
//转成100%,系统内实际存储的是真实数值
invoiceData.taxRate = invoiceData.taxRate*100
invoiceData.discount = invoiceData.discount*100

//Base64转ArrayBuffer
function base64ToArrayBuffer(base64) {
    var binaryString = atob(base64);
    var bytes = new Uint8Array(binaryString.length);
    for (var i = 0; i < binaryString.length; i++) {
        bytes[i] = binaryString.charCodeAt(i);
    }
    return bytes.buffer;
}
const docxArrayBuffer = base64ToArrayBuffer(docxTemplateBase64)
const zip = window.PizZip(docxArrayBuffer);
const doc = new window.docxtemplater(zip, {
    paragraphLoop: true,
    linebreaks: true,
});

// demo数据格式
// {
//   "invoice": "7d320457",
//   "phone": "1145141919810",
//   "city": "第三新东京市",
//   "address": "萝莉岛",
//   "name": "JOJO哒",
//   "taxRate": 3,
//   "totalIncludingTax": "0.00",
//   "discount": 3,
//   "subTotal": "0.00",
//   "orderinfos": [
//     {
//       "description": "",
//       "total": 0
//     }
//   ],
//   "totalPrice": "0.00",
//   "invoiceDate": "2023-11-24",
//   "endDate": "2023-12-01"
// }
//渲染,传入需生成文件的对象
doc.render(invoiceData);

const blob = doc.getZip().generate({
    type: "blob",
    mimeType:
        "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
    // compression: DEFLATE adds a compression step.
    // For a 50MB output document, expect 500ms additional CPU time
    compression: "DEFLATE",
});
// Output the document using Data-URI
window.saveAs(blob, "output.docx");

demo代码根据docxtemplater示例进行了修改,原有的docxtemplater示例是需要远程加载文件,由于lowcoder的第三方库运行于沙盒中,执行不了一些浏览器内置的请求方法。 所以采用了手动设置模版的方式,通过将模版文件转成base64数据,然后再转换成ArrayBuffer交由PizZip进行压缩。 文件转换成base64工具地址 https://www.browserling.com/tools/file-to-base64

mousheng commented 10 months ago

感谢分享,晚点我会测试的