Java用itext5导出pdf前后端实现

遇到一个需求,要将页面上展示的表格数据导出成一个pdf,查了资料决定用itext来做,记录一下前后端实现和自己遇到的问题

前端:

<button type="button" class="btn btn-primary" id="confirm-export">导出</button>

$('#confirm-export').click(function () {
    var serialize = $("#processForm").serialize();
    //创建一个a标签
    var a = document.createElement('a');
    operName = $("#merchantName").val();
    //调用接口
    a.href = "url?"+serialize;
    //下载文件命名
    a.download = operName + '结算汇总.pdf';
    a.click();
    return false;
});

后端:

jar包版本如下:

<dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itextpdf</artifactId>
            <version>5.5.13.1</version>
        </dependency

        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itext-asian</artifactId>
            <version>5.2.0</version>
        </dependency>

Util工具类:

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.MalformedURLException;

import com.itextpdf.text.*;
import com.itextpdf.text.pdf.*;

/**
 * pdf工具类
 * @author wangyuanchao
 */
public class PdfUtil extends PdfPageEventHelper{

    /**
     * 定义静态变量,用于生成水印文件名称
     */
    private final static String RESULT_FILE = "C:/Users/sungm/Desktop/Test/GCX-creditreport-template.pdf";
    /**
     * 页眉
     */
    public String header = "xxxx";

    /**
     * 文档字体大小,页脚页眉最好和文本大小一致
     */
    public int presentFontSize = 12;

    /**
     * 文档页面大小,最好前面传入,否则默认为A4纸张
     */
    public Rectangle pageSize = PageSize.A4;
    /**
     * 基础字体对象
     */
    public BaseFont bf = null;
    /**
     * 利用基础字体生成的字体对象,一般用于生成中文文字
     */
    public Font fontDetail = null;
    // 模板
    public PdfTemplate total;

	/**
	*  返回一个暂无数据的pdf文件
	**/
    public static void nullPdf(OutputStream out)throws MalformedURLException, IOException, DocumentException {
        //①建立com.lowagie.text.Document对象的实例。
        Document doc = new Document(PageSize.A4,20,20,30,30);
        PdfWriter instance = PdfWriter.getInstance(doc, out);
        //③打开文档。
        doc.open();

        //创建字体
        BaseFont baseFont = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H",BaseFont.NOT_EMBEDDED);
        //字体对象
        //大小为10的正常字体
        Font size10font = new Font(baseFont,10,Font.NORMAL);
        //大小为12的粗体
        Font size14bold = new Font(baseFont,12,Font.BOLD);

        // 准备工作结束,进行文档内容填充:
        // 第一页,结算汇总信息
        doc.newPage();
        doc.add(new Paragraph("暂无数据",size10font));
        doc.close();
        instance.close();
    }

    /**
     *
     * @param str 字符串
     * @param font 字体
     * @param high 表格高度
     * @Param alignCenter 是否水平居中
     * @Param alignMidde  是否垂直居中
     * @return
     */
    public static PdfPCell  mircoSoftFont(String str,Font font,int high,boolean alignCenter,boolean alignMidde){
        PdfPCell pdfPCell  = new PdfPCell(new Phrase(str,font));
        pdfPCell.setMinimumHeight(high);
        // 设置可以居中
        pdfPCell.setUseAscender(true);
        if (alignCenter){
            // 设置水平居中
            pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        }
        if (alignMidde){
            // 设置垂直居中
            pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        }
        return pdfPCell;
    }

    /**
     * 给pdf文件添加水印
     *
     * @param InPdfFile
     *            要加水印的原pdf文件路径
     * @param outPdfFile
     *            加了水印后要输出的路径
     * @param readpicturepath
     *            水印图片路径
     * @throws Exception
     */
    public static void addPdfMark(String InPdfFile, String outPdfFile, String readpicturepath) throws Exception {
        PdfReader reader = new PdfReader(InPdfFile);
        int pageSize = reader.getNumberOfPages();
        PdfStamper stamp = new PdfStamper(reader, new FileOutputStream(outPdfFile));
        // 插入水印
        Image img = Image.getInstance(readpicturepath);
        img.setAbsolutePosition(0, 0);
        for (int i = 1; i <= pageSize; i++) {
            PdfContentByte under = stamp.getUnderContent(i);
            under.addImage(img);
        }
        stamp.close();// 关闭
        File tempfile = new File(InPdfFile);
        if (tempfile.exists()) {
            tempfile.delete();
        }
    }

    /**
     * paragraph的格式
     * @param paragraph
     * @param doc
     * @throws DocumentException
     */
    public static void geshi1(Paragraph paragraph, Document doc) throws DocumentException {// 段落的格式
        paragraph.setIndentationLeft(30);
        paragraph.setIndentationRight(30);
        paragraph.setFirstLineIndent(20f);
        paragraph.setSpacingAfter(10f);
        paragraph.setSpacingBefore(10f);
        doc.add(paragraph);
    }

    /**
     * 居中无边框的cell
     * @param cell
     * @param table
     * @throws DocumentException
     */
    public static void geshi2(PdfPCell cell, PdfPTable table) throws DocumentException {// 表格的格式
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        cell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        cell.setVerticalAlignment(PdfPCell.ALIGN_CENTER);
        table.addCell(cell);
    }

    // 不居中无边框的cell
    public static void geshi12(PdfPCell cell, PdfPTable table) throws DocumentException {// 表格的格式
        cell.setBorder(PdfPCell.NO_BORDER);
        table.addCell(cell);
    }

    // 居中有边框的cell
    public static void geshi22(PdfPCell cell, PdfPTable table) throws DocumentException {// 表格的格式
        cell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        cell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        cell.setVerticalAlignment(PdfPCell.ALIGN_CENTER);
        table.addCell(cell);
    }

    // 居中有边框的cell
    public static void geshi32(PdfPCell cell, PdfPTable table) throws DocumentException {// 表格的格式
        cell.setColspan(3);
        cell.setBorder(0);
        table.addCell(cell);
    }

    /**
     *
     * TODO 文档打开时创建模板
     *
     * @see com.itextpdf.text.pdf.PdfPageEventHelper#onOpenDocument(com.itextpdf.text.pdf.PdfWriter, com.itextpdf.text.Document)
     */
    @Override
    public void onOpenDocument(PdfWriter writer, Document document) {
        // 共 页 的矩形的长宽高
        total = writer.getDirectContent().createTemplate(50, 50);
    }

    /**
     *
     * Creates a new instance of PdfReportM1HeaderFooter 构造方法.
     *  @param yeMei
     *            页眉字符串
     * @param presentFontSize
     *            数据体字体大小
     * @param pageSize
     */
    public PdfUtil(String yeMei, int presentFontSize, Rectangle pageSize) {
        this.header = yeMei;
        this.presentFontSize = presentFontSize;
        this.pageSize = pageSize;
    }


    /**
     *
     * TODO 关闭每页的时候,写入页眉,写入'第几页'这几个字。
     *
     * @see com.itextpdf.text.pdf.PdfPageEventHelper#onEndPage(com.itextpdf.text.pdf.PdfWriter, com.itextpdf.text.Document)
     */
    @Override
    public void onEndPage(PdfWriter writer, Document document) {

        try {
            if (bf == null) {
                bf = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);
            }
            if (fontDetail == null) {
                // 数据体字体
                fontDetail = new Font(bf, presentFontSize, Font.NORMAL);
            }
        } catch (DocumentException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

        // 1.写入页眉
        ColumnText.showTextAligned(writer.getDirectContent(), Element.ALIGN_CENTER, new Phrase(header, fontDetail), document.getPageSize().getRight()/2, document.getPageSize().getTop()-36, 0);
//		  没有需要写页脚的需求,先注释起来,后续有需求再调试
//        2.写入前半部分的 第 X页/共
//        int pageS = writer.getPageNumber();
//        String foot1 = "第 " + pageS + " 页";
//        Phrase footer = new Phrase(foot1, fontDetail);

//        // 3.计算前半部分的foot1的长度,后面好定位最后一部分的'Y页'这俩字的x轴坐标,字体长度也要计算进去 = len
//        float len = bf.getWidthPoint(foot1, presentFontSize);

//        // 4.拿到当前的PdfContentByte
//        PdfContentByte cb = writer.getDirectContent();

//        // 5.写入页脚1,x轴就是(右margin+左margin + right() -left()- len)/2.0F 再给偏移20F适合人类视觉感受,否则肉眼看上去就太偏左了 ,y轴就是底边界-20,否则就贴边重叠到数据体里了就不是页脚了;注意Y轴是从下往上累加的,最上方的Top值是大于Bottom好几百开外的。
//        ColumnText.showTextAligned(cb, Element.ALIGN_CENTER, footer, (document.rightMargin() + document.right() + document.leftMargin() - document.left() - len) / 2.0F + 20F, document.bottom() - 20, 0);
//
//        // 6.写入页脚2的模板(就是页脚的Y页这俩字)添加到文档中,计算模板的和Y轴,X=(右边界-左边界 - 前半部分的len值)/2.0F + len , y 轴和之前的保持一致,底边界-20
//        // 调节模版显示的位置
//        cb.addTemplate(total, (document.rightMargin() + document.right() + document.leftMargin() - document.left()) / 2.0F + 20F, document.bottom() - 20);

    }

    /**
     *
     * TODO 关闭文档时,替换模板,完成整个页眉页脚组件
     *
     * @see com.itextpdf.text.pdf.PdfPageEventHelper#onCloseDocument(com.itextpdf.text.pdf.PdfWriter, com.itextpdf.text.Document)
     */
    @Override
    public void onCloseDocument(PdfWriter writer, Document document) {
        // 7.最后一步了,就是关闭文档的时候,将模板替换成实际的 Y 值,至此,page x of y 制作完毕,完美兼容各种文档size。
        total.beginText();
        // 生成的模版的字体、颜色
        total.setFontAndSize(bf, presentFontSize);
        String foot2 = " " + (writer.getPageNumber() - 1) + " 页";
        // 模版显示的内容
        total.showText(foot2);
        total.endText();
        total.closePath();
    }

    // 插入图片
    public static void addpicture(PdfPTable table, Image image, String picpath, PdfPCell cell, Document doc)
            throws MalformedURLException, IOException, DocumentException {
        image = Image.getInstance(picpath);
        cell = new PdfPCell(image);
        geshi2(cell, table);
        doc.add(table);
    }

    //非空判断
    public static String isnull(Object a) {
        if (a != null && a != "" && a != "null" && a.toString() != "null") {
            return a.toString();
        } else {
            return "";
        }
    }
}

生成pdfcontroller和实现方法:

@RequestMapping("/exportSettleFile")
    @ResponseBody
    public void exportSettleFile(ExportOrderRequest request,HttpSession session,HttpServletResponse httpResponse) throws IOException, DocumentException {
        if (RoleType.MERCHANT.getCode().equals(request.getRole())){
            User loginUser = UserUtil.getCurrentLoginUser(session);
            request.setMerchantName(loginUser.getCorporateName());
        }
        List<StationBillRecord> stationBillRecords = new ArrayList<>();

        List<AsOperator> asOperators = asOperatorRepository.queryByMerchantName(request.getMerchantName());
        request.setMerchantId(asOperators.get(0).getMerchantId());
        List<AsOrder> asOrders = orderRepository.queryOrderForExport(request);
        ExportSettleResponse response = buildBillRecord(asOrders);
        if (response.getMsg() != null){
            log.error(request.getMerchantName() + request.getBillBeginDate() + "~" + request.getBillEndDate() + response.getMsg());
            PdfUtil.nullPdf(httpResponse.getOutputStream());
            return;
        }
        response.getBillRecordResponse().setBillDate(request.getBillBeginDate() + "~" + request.getBillEndDate());
        for (StationBillRecordBO stationBillRecordBO : response.getStationBillRecordBOList()) {
            StationBillRecord stationBillRecord = new StationBillRecord();
            BeanUtils.copyProperties(stationBillRecordBO,stationBillRecord);
            stationBillRecords.add(stationBillRecord);
        }
        try {
            generateDeepthCreditReport(response.getBillRecordResponse(),stationBillRecords,httpResponse.getOutputStream());
        }catch (Exception ex){
            PdfUtil.nullPdf(httpResponse.getOutputStream());
            log.error("汇总导出异常:" + ex.getMessage());
        }
    }



private void generateDeepthCreditReport(SettleBillRecordResponse billRecordResponse,
                                                  List<StationBillRecord> stationBillRecordList, OutputStream out)
            throws MalformedURLException, IOException, DocumentException {

        //①建立Document对象的实例。
        Document doc = new Document(PageSize.A4,20,20,30,30);
        
        //②建立一个书写器(Writer)与document对象关联,通过书写器(Writer)可以将文档写入到磁盘中。
        PdfWriter instance = PdfWriter.getInstance(doc, out);

        PdfUtil pdfUtil = new PdfUtil("xxx", 15, PageSize.A4);

        //③打开文档。
        doc.open();

        pdfUtil.onOpenDocument(instance,doc);

        //创建字体
        BaseFont baseFont = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H",BaseFont.NOT_EMBEDDED);
        //字体对象
        //大小为10的正常字体
        Font size10font = new Font(baseFont,10,Font.NORMAL);
        //大小为12的粗体
        Font size12font = new Font(baseFont,12,Font.NORMAL);

        // 准备工作结束,进行文档内容填充:
        // 第一页,结算汇总信息
        doc.newPage();
        doc.add(new Paragraph("   ",size10font));
        doc.add(new Paragraph("   ",size10font));
        doc.add(new Paragraph("   ",size10font));
        // 第一行标题
        String title = billRecordResponse.getOperName() + "汇总结算单(" + billRecordResponse.getBillDate() + ")";
        PdfPTable table = new PdfPTable(8);
        PdfPCell cell1 = new PdfPCell(new Phrase(title,size12font));
        cell1.setMinimumHeight(50);
        cell1.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        cell1.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        cell1.setColspan(8);
        table.addCell(cell1);
        doc.add(table);
        // 第二行
        PdfPTable secondRowTable = new PdfPTable(8);
        secondRowTable.addCell(PdfUtil.mircoSoftFont("分润模式",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("分润比例(%)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("充电服务费(元)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("充电电费(元)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("结算金额(元)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("总电量(kWh)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("直流电量(kWh)",size10font,40,true,true));
        secondRowTable.addCell(PdfUtil.mircoSoftFont("交流电量(kWh)",size10font,40,true,true));
        doc.add(secondRowTable);

        // 第三行
        PdfPTable thirdRowTable = new PdfPTable(8);
        //第四行
        PdfPTable fourthRowTable = new PdfPTable(8);
        fourthRowTable.addCell(PdfUtil.mircoSoftFont("备注",size10font,40,true,true));
        String remark;
        PdfPCell remarkCell = null;


        thirdRowTable.addCell(PdfUtil.mircoSoftFont(DivideModeEnum.getByCode(billRecordResponse.getDivideMode()).getMessage(),size10font,40,true,true));
        //分润比例展示
        if (DivideModeEnum.M1.getMessage().equals(DivideModeEnum.getByCode(billRecordResponse.getDivideMode()).getMessage())){
            //按电量分成
            String ratio = "直流(" + billRecordResponse.getDcChargeAttr() + ")\n" + "交流(" + billRecordResponse.getAcChargeAttr() + ")";
            remark = "直流电量*直流分润系数+交流电量*交流分润系数=结算金额";
            remarkCell = new PdfPCell(new Phrase(remark,size10font));
            thirdRowTable.addCell(PdfUtil.mircoSoftFont(ratio,size10font,40,true,true));
        } else if (DivideModeEnum.M2.getMessage().equals(DivideModeEnum.getByCode(billRecordResponse.getDivideMode()).getMessage())){
            //按服务费分成
            if ("0".equals(billRecordResponse.getDivideRatioElc()) || "0.00".equals(billRecordResponse.getDivideRatioElc())){
                thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getDivideRatio(),size10font,40,true,true));
                remark = "充电服务费*分润比例=结算金额";
                remarkCell = new PdfPCell(new Phrase(remark,size10font));
            }else if ("100".equals(billRecordResponse.getDivideRatioElc()) || "100.00".equals(billRecordResponse.getDivideRatioElc())){
                thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getDivideRatio(),size10font,40,true,true));
                remark = "充电服务费*分润比例+充电电费=结算金额";
                remarkCell = new PdfPCell(new Phrase(remark,size10font));
            }else {
                String ratio = "充电服务费(" + billRecordResponse.getDivideRatio() + ")\n" + "充电电费(" + billRecordResponse.getDivideRatioElc() + ")";
                thirdRowTable.addCell(PdfUtil.mircoSoftFont(ratio,size10font,40,true,true));
                remark = "充电服务费*服务费分润比例+充电电费*充电电费分润比例=结算金额";
                remarkCell = new PdfPCell(new Phrase(remark,size10font));
            }
        }else {
            thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getDivideRatio(),size10font,40,true,true));
            remark = "(充电服务费+充电电费)*分润比例=结算金额";
            remarkCell = new PdfPCell(new Phrase(remark,size10font));
        }
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getServiceAmt(),size10font,40,true,true));
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getChargeAmt(),size10font,40,true,true));
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getBillAmt(),size10font,40,true,true));
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getChargeEq(),size10font,40,true,true));
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getDcChargeEq(),size10font,40,true,true));
        thirdRowTable.addCell(PdfUtil.mircoSoftFont(billRecordResponse.getAcChargeEq(),size10font,40,true,true));
        doc.add(thirdRowTable);
        remarkCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        remarkCell.setColspan(7);
        fourthRowTable.addCell(remarkCell);
        doc.add(fourthRowTable);
        //第五行,盖章
        PdfPTable fifRowTable = new PdfPTable(8);
        PdfPCell gzCell1 = new PdfPCell(new Phrase("xxx\n(盖章)",size10font));
        gzCell1.setMinimumHeight(50);
        gzCell1.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        gzCell1.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        gzCell1.setBorder(PdfCell.NO_BORDER);
        gzCell1.setColspan(4);
        fifRowTable.addCell(gzCell1);
        PdfPCell gzCell2 = new PdfPCell(new Phrase(billRecordResponse.getOperName() + "\n(盖章)",size10font));
        gzCell2.setMinimumHeight(50);
        gzCell2.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        gzCell2.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        gzCell2.setBorder(PdfCell.NO_BORDER);
        gzCell2.setColspan(4);
        fifRowTable.addCell(gzCell2);
        doc.add(fifRowTable);
        pdfUtil.onEndPage(instance,doc);

        // 第二页
        doc.newPage();
        pdfUtil.onEndPage(instance,doc);
        //空行
        doc.add(new Paragraph("   ",size10font));
        doc.add(new Paragraph("   ",size10font));
        doc.add(new Paragraph("   ",size10font));
        
        PdfPTable stationTable = new PdfPTable(8);
        String stationTitle = billRecordResponse.getOperName() + "场站结算记录(" + billRecordResponse.getBillDate() + ")";
        PdfPCell stationCell = new PdfPCell(new Phrase(stationTitle,size12font));
        stationCell.setMinimumHeight(50);
        stationCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
        stationCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
        stationCell.setColspan(10);
        stationTable.addCell(stationCell);
        doc.add(stationTable);

        //第二行
        PdfPTable stationSecondRowTable = new PdfPTable(9);
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("充电站",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("充电服务费(元)",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("充电电费(元)",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("结算金额",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("订单数",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("总电量(kWh)",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("直流充电电量(kWh)",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("交流充电电量(kWh)",size10font,40,true,true));
        stationSecondRowTable.addCell(PdfUtil.mircoSoftFont("优惠金额(元)",size10font,40,true,true));
        doc.add(stationSecondRowTable);

        //循环插入场站清分信息
        for (StationBillRecord stationBillRecord : stationBillRecordList) {
            PdfPTable tempTable = new PdfPTable(9);
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getStationName(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getSrvAmt(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getElecAmt(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getSettleAmt(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getOrderNum(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getChargePq(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getZlPq(),size10font,40,true,true));
            tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getJlPq(),size10font,40,true,true));
            if (stationBillRecord.getDiscountAmt() != null && stationBillRecord.getDiscountAmt() != ""){
                tempTable.addCell(PdfUtil.mircoSoftFont(stationBillRecord.getDiscountAmt(),size10font,40,true,true));
            }else{
                tempTable.addCell(PdfUtil.mircoSoftFont("",size10font,40,true,true));
            }
            doc.add(tempTable);
        }


        doc.close();
        instance.close();
    }

数据有点复杂。写pdf有点费劲,目前满足需求了,还有比如水印或者页脚页数一类的功能,有需要再补充

参考文章:
itext5:
https://blog.csdn.net/u010067848/article/details/98203746

itext2.1.5
https://blog.csdn.net/Soulmate_Min/article/details/81707918?utm_source=app

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
前后端分离的开发中,如果需要将页面上展示的表格数据导出成一个PDF文件,可以使用itextpdf库来实现。首先,前端需要调用一个后端提供的接口来生成PDF文件。在点击事件中,可以调用import的方式引入后端提供的exportPDF方法。这个方法可以使用itextpdf库来生成PDF文件。 在后端,可以使用Spring Boot框架,并结合itext库来实现PDF导出功能。可以参考一些博客或文档,如引用所提到的博客,了解如何在Spring Boot中使用itext库来生成PDF文件。 具体实现的步骤可以包括以下几个方面: 1. 在后端的Controller中定义一个接口,用于接收前端的请求,并调用itext库来生成PDF文件。 2. 使用itext库的相关类和方法,通过读取前端传递的表格数据,将其写入PDF文件中。 3. 可以设置PDF文件的样式、布局、字体等属性,以确保生成的PDF文件满足需求。 4. 最后,将生成的PDF文件返回给前端,供用户下载或保存。 通过这种前后端分离的方式,可以实现将页面上展示的表格数据导出成一个PDF文件的功能。前端通过调用后端提供的接口来触发PDF生成的过程,后端使用itext库来生成PDF文件,并将其返回给前端。这样,用户就可以通过下载或保存来获取导出PDF文件。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *3* [SpringBoot+Vue+Itext实现前端请求文件流的方式下载PDF](https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/122823108)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] - *2* [Javaitext5导出pdf前后端实现](https://blog.csdn.net/Haqio/article/details/107057059)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值