使用itext获取pdf模板,生成pdf

发布时间 2023-05-05 01:00:08作者: WonderC

前置

使用itext前请往pom中管理相关依赖包

 <!-- 生成pdf -->
        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itextpdf</artifactId>
            <version>5.5.10</version>
            <!--            <version>5.5.13</version>-->
        </dependency>
        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itext-asian</artifactId>
            <version>5.2.0</version>
        </dependency>
        <dependency>
            <groupId>org.apache.pdfbox</groupId>
            <artifactId>pdfbox</artifactId>
            <version>2.0.11</version>
            <scope>compile</scope>
        </dependency>

利用itext在线获取pdf模板,并通过反射进行相关模板值的插入

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.lang.reflect.Field;
import java.net.URL;
import java.util.Map;

import javax.servlet.http.HttpServletResponse;

import org.apache.commons.io.IOUtils;
import org.springframework.http.MediaType;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;

import com.itextpdf.text.Document;
import com.itextpdf.text.pdf.AcroFields;
import com.itextpdf.text.pdf.BaseFont;
import com.itextpdf.text.pdf.PdfCopy;
import com.itextpdf.text.pdf.PdfReader;
import com.itextpdf.text.pdf.PdfStamper;

@Controller
public class PdfController {

    @GetMapping("/generate-pdf")
    public void generatePdf(HttpServletResponse response) throws Exception {
        // 从网站上获取PDF文件的URL
        String pdfUrl = "http://example.com/sample.pdf";
        URL url = new URL(pdfUrl);

        // 读取PDF文件
        InputStream input = url.openStream();
        PdfReader reader = new PdfReader(input);
        input.close();

        // 填充表单
        ByteArrayOutputStream output = new ByteArrayOutputStream();
        PdfStamper stamper = new PdfStamper(reader, output);
        AcroFields form = stamper.getAcroFields();

      
        //设置中文
        // 设置中文字体并嵌入到PDF文件中
        BaseFont bf = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);
        ArrayList<BaseFont> fontList = new ArrayList<BaseFont>();
        fontList.add(bf);
        //取出报表模板中的所有字段
        AcroFields fields = stamper.getAcroFields();
        fields.setSubstitutionFonts(fontList);

        // 获取实体类属性与PDF表单字段的映射关系
        Map<String, String> fieldMappings = getFieldMappings();

        // 从MyBatis查询得到实体类
        MyEntity entity = mybatisMapper.getEntityById(1L);

        // 使用反射机制填充表单
        for (Field field : entity.getClass().getDeclaredFields()) {
            String fieldName = field.getName();
            String pdfFieldName = fieldMappings.get(fieldName);
            if (pdfFieldName != null && form.getFieldType(pdfFieldName) == AcroFields.FIELD_TYPE_TEXT) {
                field.setAccessible(true);
                String value = String.valueOf(field.get(entity));
                form.setField(pdfFieldName, value);
            }
        }

        stamper.setFormFlattening(true);
        stamper.close();

        // 输出PDF文件
        ByteArrayInputStream bais = new ByteArrayInputStream(output.toByteArray());
        IOUtils.copy(bais, response.getOutputStream());
        response.setContentType(MediaType.APPLICATION_PDF_VALUE);
        response.setHeader("Content-Disposition", "attachment; filename=sample-filled.pdf");
        response.flushBuffer();
        bais.close();
    }

    private Map<String, String> getFieldMappings() {
        // 这里返回实体类属性与PDF表单字段的映射关系
        // 左侧是实体类字段 右侧是对应pdf字段
        // 例如:Map<String, String> fieldMappings = new HashMap<>();
        // fieldMappings.put("name", "nameField");
        // fieldMappings.put("email", "emailField");
        // return fieldMappings;
    }
}

利用反射机制优化iText生成PDF文件