|
@@ -1,96 +1,87 @@
|
|
|
-import Docxtemplater from 'docxtemplater'
|
|
|
-import PizZip from 'pizzip'
|
|
|
-import JSZipUtils from 'jszip-utils'
|
|
|
-import { saveAs } from 'file-saver'
|
|
|
+import JSZip from 'jszip';
|
|
|
+import { saveAs } from 'file-saver';
|
|
|
+import JSZipUtils from 'jszip-utils';
|
|
|
+import PizZip from 'pizzip';
|
|
|
+import Docxtemplater from 'docxtemplater';
|
|
|
import ImageModule from 'docxtemplater-image-module-free'
|
|
|
-import expressions from 'angular-expressions'
|
|
|
-
|
|
|
-/**
|
|
|
- 4. 导出docx
|
|
|
- 5. @param { String } tempDocxPath 模板文件路径
|
|
|
- 6. @param { Object } data 文件中传入的数据
|
|
|
- 7. @param { String } fileName 导出文件名称
|
|
|
-*/
|
|
|
|
|
|
-export const exportDocx = (tempDocxPath, data, fileName) => {
|
|
|
- // 读取并获得模板文件的二进制内容
|
|
|
- JSZipUtils.getBinaryContent(tempDocxPath, (error, content) => {
|
|
|
- if (error) {
|
|
|
- console.error("获取文件时出现错误:", error);
|
|
|
- throw error;
|
|
|
- }
|
|
|
- console.log("Content type:", typeof content);
|
|
|
- console.log("获取到的内容:", content);
|
|
|
- console.log("获取到的内容长度:", content.byteLength);
|
|
|
- const uint8Array = new Uint8Array(content);
|
|
|
- console.log("文件内容字节:", uint8Array);
|
|
|
- const zip = new PizZip(content)
|
|
|
- // 处理图片
|
|
|
- const imageModule = new ImageModule({
|
|
|
- getImage: async (tagValue) => {
|
|
|
- if (tagValue.startsWith('studentSignature')) {
|
|
|
- const imagePath = data.images[tagValue]; // 获取学生签名路径
|
|
|
- console.log(`学生签名路径: ${imagePath}`);
|
|
|
- return await loadImage(imagePath);
|
|
|
- } else if (tagValue.startsWith('supervisorSignature')) {
|
|
|
- const imagePath = data.images[tagValue]; // 获取导师签名路径
|
|
|
- console.log(`导师签名路径: ${imagePath}`);
|
|
|
- return await loadImage(imagePath);
|
|
|
+// function base64ToUint8Array(base64) {
|
|
|
+// const base64Data = base64.split(',')[1]; // 去掉前缀 "data:image/png;base64,"
|
|
|
+// const binaryString = atob(base64Data); // 解码 Base64
|
|
|
+// const length = binaryString.length;
|
|
|
+// const uint8Array = new Uint8Array(length);
|
|
|
+// for (let i = 0; i < length; i++) {
|
|
|
+// uint8Array[i] = binaryString.charCodeAt(i);
|
|
|
+// }
|
|
|
+// return uint8Array;
|
|
|
+// }
|
|
|
+export const exportDocx = async (tempDocxPath, dataList, zipFileName) => {
|
|
|
+ try {
|
|
|
+ // 加载模板文件
|
|
|
+ const content = await new Promise((resolve, reject) => {
|
|
|
+ JSZipUtils.getBinaryContent(tempDocxPath, (error, content) => {
|
|
|
+ if (error) {
|
|
|
+ reject(error);
|
|
|
+ } else {
|
|
|
+ resolve(content);
|
|
|
}
|
|
|
- console.error(`未找到图片路径: ${tagValue}`);
|
|
|
- return null;
|
|
|
- },
|
|
|
- getSize: (img, tagValue) => {
|
|
|
- return [100, 100]; // 宽高调整
|
|
|
- }
|
|
|
+ });
|
|
|
});
|
|
|
- const doc = new Docxtemplater().loadZip(zip)
|
|
|
- console.log(doc)
|
|
|
- doc.setData(data)
|
|
|
- try {
|
|
|
- // render the document (replace all occurences of {first_name} by John, {last_name} by Doe, ...)
|
|
|
- doc.render()
|
|
|
- } catch (error) {
|
|
|
- const e = {
|
|
|
- message: error.message,
|
|
|
- name: error.name,
|
|
|
- stack: error.stack,
|
|
|
- properties: error.properties
|
|
|
+
|
|
|
+ // 初始化 JSZip 实例,用于打包多个文件
|
|
|
+ const zip = new JSZip();
|
|
|
+
|
|
|
+ // 遍历每一条数据,生成单独的 .docx 文件
|
|
|
+ for (let i = 0; i < dataList.length; i++) {
|
|
|
+ const data = dataList[i];
|
|
|
+ // if (data.studentSignature) {
|
|
|
+ // data.studentSignature = {
|
|
|
+ // data: base64ToUint8Array(data.studentSignature),
|
|
|
+ // width: 100, // 图片宽度(单位:像素)
|
|
|
+ // height: 50, // 图片高度(单位:像素)
|
|
|
+ // };
|
|
|
+ // }
|
|
|
+ // if (data.supervisorSignature) {
|
|
|
+ // data.supervisorSignature = {
|
|
|
+ // data: base64ToUint8Array(data.supervisorSignature),
|
|
|
+ // width: 100, // 图片宽度(单位:像素)
|
|
|
+ // height: 50, // 图片高度(单位:像素)
|
|
|
+ // };
|
|
|
+ // }
|
|
|
+ const zipInstance = new PizZip(content);
|
|
|
+ const doc = new Docxtemplater().loadZip(zipInstance);
|
|
|
+ // 加载图片模块
|
|
|
+ // const imageModule = new ImageModule({
|
|
|
+ // centered: false, // 图片是否居中
|
|
|
+ // getImage: (tagValue) => tagValue.data, // 获取图片数据
|
|
|
+ // getSize: (tagValue) => [tagValue.width, tagValue.height], // 获取图片尺寸
|
|
|
+ // });
|
|
|
+ // doc.attachModule(imageModule);
|
|
|
+ doc.setData(data);
|
|
|
+
|
|
|
+ try {
|
|
|
+ doc.render(); // 渲染模板
|
|
|
+ } catch (error) {
|
|
|
+ console.error(`渲染第 ${i + 1} 条数据时出错:`, error);
|
|
|
+ throw error;
|
|
|
}
|
|
|
- console.log({
|
|
|
- error: e
|
|
|
- })
|
|
|
- // The error thrown here contains additional information when logged with JSON.stringify (it contains a property object).
|
|
|
- throw error
|
|
|
- }
|
|
|
- const out = doc.getZip().generate({
|
|
|
- type: 'blob',
|
|
|
- mimeType: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'
|
|
|
- }) // Output the document using Data-URI
|
|
|
- saveAs(out, fileName)
|
|
|
- })
|
|
|
-}
|
|
|
-/**
|
|
|
- * 加载图片
|
|
|
- * @param { String } url 图片的 URL 或 Base64 编码
|
|
|
- * @returns { Promise<Uint8Array> } 图片的 Uint8Array 数据
|
|
|
- */
|
|
|
-const loadImage = async (url) => {
|
|
|
- if (url.startsWith('data:image')) {
|
|
|
- // 处理 Base64 编码
|
|
|
- const base64Data = url.split(',')[1];
|
|
|
- const byteCharacters = atob(base64Data);
|
|
|
- const byteNumbers = new Array(byteCharacters.length);
|
|
|
- for (let i = 0; i < byteCharacters.length; i++) {
|
|
|
- byteNumbers[i] = byteCharacters.charCodeAt(i);
|
|
|
- }
|
|
|
- return new Uint8Array(byteNumbers);
|
|
|
- } else {
|
|
|
- // 处理 URL
|
|
|
- const response = await fetch(url);
|
|
|
- if (!response.ok) {
|
|
|
- throw new Error(`加载图片时出现错误: ${response.statusText}`);
|
|
|
+
|
|
|
+ // 生成 .docx 文件
|
|
|
+ const out = doc.getZip().generate({
|
|
|
+ type: 'blob',
|
|
|
+ mimeType: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
|
|
|
+ });
|
|
|
+
|
|
|
+ // 将生成的 .docx 文件添加到 zip 包中
|
|
|
+ zip.file(`document_${i + 1}.docx`, out);
|
|
|
}
|
|
|
- return new Uint8Array(await response.arrayBuffer());
|
|
|
+
|
|
|
+ // 生成 zip 文件并保存
|
|
|
+ const zipBlob = await zip.generateAsync({ type: 'blob' });
|
|
|
+ saveAs(zipBlob, zipFileName);
|
|
|
+ console.log(`文件已成功生成并打包为 ${zipFileName}`);
|
|
|
+ } catch (error) {
|
|
|
+ console.error('导出文件时出错:', error);
|
|
|
+ throw error;
|
|
|
}
|
|
|
-}
|
|
|
+};
|