2025-06-30 11:36:11 +08:00
|
|
|
|
import top1 from '@/assets/img/captcha/top1.svg';
|
|
|
|
|
|
import top2 from '@/assets/img/captcha/top2.svg';
|
|
|
|
|
|
import top3 from '@/assets/img/captcha/top3.svg';
|
2025-07-09 15:15:16 +08:00
|
|
|
|
import { fetchUploadFile } from '@/api/all';
|
|
|
|
|
|
import { jsPDF } from 'jspdf';
|
|
|
|
|
|
import html2canvas from 'html2canvas';
|
|
|
|
|
|
import axios from 'axios';
|
2025-06-30 11:36:11 +08:00
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 根据评分获取对应的星星图标路径
|
|
|
|
|
|
* @param score 评分,范围 1 ~ 3
|
|
|
|
|
|
* @returns 对应的 SVG 图标路径
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getStarIcon(score: number): string {
|
|
|
|
|
|
switch (score) {
|
2025-07-07 20:59:54 +08:00
|
|
|
|
case 0:
|
2025-06-30 11:36:11 +08:00
|
|
|
|
return top1;
|
2025-07-07 20:59:54 +08:00
|
|
|
|
case 1:
|
2025-06-30 11:36:11 +08:00
|
|
|
|
return top2;
|
2025-07-07 20:59:54 +08:00
|
|
|
|
case 2:
|
2025-06-30 11:36:11 +08:00
|
|
|
|
return top3;
|
|
|
|
|
|
default:
|
|
|
|
|
|
return top1; // 默认返回最高分图标
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
2025-07-08 16:55:03 +08:00
|
|
|
|
|
|
|
|
|
|
// ai检测结果状态
|
|
|
|
|
|
export enum AiResultStatus {
|
|
|
|
|
|
WAIT = 0, // 待执行
|
|
|
|
|
|
PENDING = 1, // 处理中
|
|
|
|
|
|
FAILED = 2, // 失败
|
|
|
|
|
|
SUCCESS = 3, // 成功
|
|
|
|
|
|
}
|
2025-07-09 15:15:16 +08:00
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 将指定 DOM 元素导出为 PDF Blob
|
|
|
|
|
|
* @param elementSelector - 要导出的 DOM 元素选择器
|
|
|
|
|
|
*/
|
|
|
|
|
|
export const generatePDF = async (elementSelector: string): Promise<Blob> => {
|
|
|
|
|
|
const sections = document.querySelectorAll(elementSelector);
|
|
|
|
|
|
const pdf = new jsPDF('p', 'mm', 'a4');
|
|
|
|
|
|
let position = 0;
|
|
|
|
|
|
for (const section of sections) {
|
|
|
|
|
|
if ((section as HTMLElement).children.length === 0) continue;
|
|
|
|
|
|
const canvas = await html2canvas(section as HTMLElement, {
|
|
|
|
|
|
ignoreElements: (element) => element.classList.contains('ignore-export'),
|
|
|
|
|
|
scale: 2,
|
|
|
|
|
|
useCORS: true,
|
|
|
|
|
|
});
|
|
|
|
|
|
const imgData = canvas.toDataURL('image/png');
|
|
|
|
|
|
const imgProps = pdf.getImageProperties(imgData);
|
|
|
|
|
|
const pdfWidth = pdf.internal.pageSize.getWidth();
|
|
|
|
|
|
const pdfHeight = (imgProps.height * pdfWidth) / imgProps.width;
|
|
|
|
|
|
pdf.addImage(imgData, 'PNG', 0, position, pdfWidth, pdfHeight);
|
|
|
|
|
|
position += pdfHeight + 10;
|
|
|
|
|
|
}
|
|
|
|
|
|
return pdf.output('blob');
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 上传 PDF 并返回文件 URL
|
|
|
|
|
|
* @param fileName - PDF 文件名
|
|
|
|
|
|
* @param elementSelector - 要导出的 DOM 元素选择器
|
|
|
|
|
|
*/
|
|
|
|
|
|
export const uploadPdf = async (fileName: string, elementSelector: string): Promise<string> => {
|
|
|
|
|
|
const response = await fetchUploadFile({ suffix: 'pdf' });
|
|
|
|
|
|
const preSignedUrl = response?.data?.upload_url;
|
|
|
|
|
|
const fileUrl = response?.data?.file_url;
|
|
|
|
|
|
if (!preSignedUrl) {
|
|
|
|
|
|
throw new Error('未能获取有效的预签名上传地址');
|
|
|
|
|
|
}
|
|
|
|
|
|
const pdfBlob = await generatePDF(elementSelector);
|
|
|
|
|
|
await axios.put(preSignedUrl, pdfBlob, {
|
|
|
|
|
|
headers: {
|
|
|
|
|
|
'Content-Type': pdfBlob.type,
|
|
|
|
|
|
},
|
|
|
|
|
|
});
|
|
|
|
|
|
return fileUrl;
|
|
|
|
|
|
};
|