栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

java实现html转PDF

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

java实现html转PDF

html转PDF方法类

import com.itextpdf.text.*;
import com.itextpdf.text.Image;
import com.itextpdf.text.Rectangle;
import com.itextpdf.text.pdf.*;
import com.itextpdf.tool.xml.XMLWorkerHelper;
import com.lingzhi.common.utils.file.FileUploadUtils;
import com.lingzhi.common.utils.html.HtmlConvertWordUtil;
import com.lowagie.text.Font;
import com.lowagie.text.pdf.BaseFont;
import com.spire.ms.System.Collections.ArrayList;
import fr.opensagres.poi.xwpf.converter.pdf.PdfConverter;
import fr.opensagres.poi.xwpf.converter.pdf.PdfOptions;
import fr.opensagres.xdocreport.itext.extension.font.IFontProvider;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Attributes;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Entities;
import org.jsoup.parser.Parser;
import org.jsoup.select.Elements;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.xhtmlrenderer.pdf.ITextFontResolver;
import org.xhtmlrenderer.pdf.ITextRenderer;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.awt.*;
import java.io.*;
import java.nio.charset.Charset;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;


public class PdfUtils {

    protected final Logger logger = LoggerFactory.getLogger(this.getClass());

    public static final String DEFAULT_ORDER_CSS = "table{border-collapse:collapse;border-spacing:0;width:100%;border-bottom:1px solid #222;border-right:1px solid #222;margin-top:20pt;margin-bottom:20pt;}*{font-size:10.5pt;font-family:SimSun;line-height:1.8}a{text-decoration:none;color:black}td,th{border-top:1px solid #222;border-left:1px solid #222;padding:8px 0;text-align:center;white-space:normal;word-wrap:break-word;word-break:break-all;}h1,h1 a,h1 a strong{font-size:29.26pt;font-weight:bold;}h2,h2 a,h2 a strong{font-size:17.56pt;font-weight:bold;}h3,h3 a,h3 a strong{font-size:15.61pt;font-weight:bold;}h4,h4 a,h4 a strong{font-size:13.66pt;font-weight:bold;}h5,h5 a,h5 a strong{font-size:11.70pt;font-weight:bold;}h6,h6 a,h6 a strong{font-size:9.75pt;font-weight:bold;}h1,h2,h3,h4,h5,h6{font-weight:bolder}h1 a,h2 a,h3 a,h4 a,h5 a,h6 a{font-weight:bolder}thead tr:nth-child(1){width:12% !important;}thead tr:nth-child(2){width:12% !important;}thead tr:nth-child(3){width:10% !important;}thead tr:nth-child(4){width:8% !important;}thead tr:nth-child(5){width:8% !important;}thead tr:nth-child(6){width:8% !important;}thead tr:nth-child(7){width:11% !important;}thead tr:nth-child(8){width:11% !important;}thead tr:nth-child(9){width:10% !important;}thead tr:nth-child(10){width:10% !important;}thead th:nth-child(1){font-weight:normal;font-size:14px;width:12% !important;}thead th:nth-child(2){font-weight:normal;font-size:14px;width:12% !important;}thead th:nth-child(3){font-weight:normal;font-size:14px;width:10% !important;}thead th:nth-child(4){font-weight:normal;font-size:14px;width:8% !important;}thead th:nth-child(5){font-weight:normal;font-size:14px;width:8% !important;}thead th:nth-child(6){font-weight:normal;font-size:14px;width:8% !important;}thead th:nth-child(7){font-weight:normal;font-size:14px;width:11% !important;}thead th:nth-child(8){font-weight:normal;font-size:14px;width:11% !important;}thead th:nth-child(9){font-weight:normal;font-size:14px;width:10% !important;}thead th:nth-child(10){font-weight:normal;font-size:14px;width:10% !important;}.left{width:100%;display:table:text-align:left;float:left}.right{width:100%;display:table:text-align:right;float:right}.none-border,.none-border td,.none-border th{border:none;}";
    final static String[] colWidth = {"12%", "12%", "10%", "8%", "8%", "8%", "12%", "10%", "10%", "10%"};

    
    public void exportPdf(HttpServletResponse response, String filename, String content, String watermark) throws Exception {
        if (content == null || content.length() <= 0) return;
        OutputStream os = null;
        OutputStream tempos = null;
        InputStream tempStream = null;

        try {
            content=content.replace("","").replace("","");
            // XML5个转义符:<,>,&,",©;的转义字符分别如下: < >& " '
            content = content.replaceAll("<","<").replaceAll(">",">").replaceAll("&","&").replaceAll(""",""").replaceAll("'","©");
            content = content.replaceAll(" ","").replaceAll(" ","").replaceAll(" ","").replaceAll(" ","").replaceAll(" ","");
            content = content.replaceAll("©","©").replaceAll("®","TM").replaceAll("×","×").replaceAll("÷","÷");

            String html="" +
                    "n" +
                    "n" +
                    "n" +
                    "  n" +
                    "  "+filename+"n" +
                    ""+
                    "n" +
                    "n" +
                    content +
                    "nn" +
                    "";

            // 通过Jsoup格式化html
            Document parse = Jsoup.parse(html);
            // 获取html中所有的标签元素
            Elements es = parse.body().getAllElements();
            List> imglist = new ArrayList();
            // 筛选标签
            java.util.List tag1 = es.stream().filter(x -> "img".equals(x.tagName())).collect(Collectors.toList());
            for (org.jsoup.nodes.Element imgElement : tag1) {
                //处理图片
                Attributes as = imgElement.attributes();
                String src = as.get("src");

                HttpServletRequest request = ServletUtils.getRequest();
                String ur = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort();
                String pictureUrl = "";
                if(src.contains("//")){
                    pictureUrl = src;
                }else{
                    pictureUrl = ur+src;
                    HashMap imgmap=new HashMap<>();
                    imgmap.put("src1",src);
                    imgmap.put("src2",pictureUrl);
                    imglist.add(imgmap);
                }
                //设置图片宽度
                int pagewidth = Math.round(PageSize.A4.getWidth());
                try
                {
                    Image img = Image.getInstance(pictureUrl);
                    if(img.getWidth()>pagewidth)
                    {
                        imgElement.attr("style","width:100%");
                    }
                } catch (Exception ex) {
                }

            }
            String _html =  parse.html();
            String xhtml = htmlToxhtml(_html);
            xhtml=xhtml.replace(" ","");
            for(HashMap item : imglist)
            {
                xhtml = xhtml.replace(item.get("src1"),item.get("src2"));
            }
            ITextRenderer renderer = new ITextRenderer();
            renderer.setDocumentFromString(xhtml);
            ITextFontResolver fontResolver = renderer.getFontResolver();
            fontResolver.addFont("/Fonts/simsun.ttc", BaseFont.IDENTITY_H, BaseFont.NOT_EMBEDDED);
            fontResolver.addFont("/Fonts/SimSun.ttf", BaseFont.IDENTITY_H, BaseFont.NOT_EMBEDDED);
            fontResolver.addFont("/Fonts/simsunbd.ttf", BaseFont.IDENTITY_H, BaseFont.NOT_EMBEDDED);
            //浏览器导出
            renderer.layout();
            response.setCharacterEncoding("utf-8");
            response.setContentType("application/pdf");
            response.setHeader("Content-disposition", "attachment;filename="+new String((filename+".pdf").getBytes("utf-8"),"ISO8859-1"));
            os = response.getOutputStream(); //创建输出流

            if(StringUtils.isEmpty(watermark))
            {
                renderer.createPDF(os);
                renderer.finishPDF();
            }
            else
            {
                //添加水印
                String tempPath = FileUploadUtils.getDefaultBaseDir()+"/Temporary";
                File file = new File(tempPath);
                if (!file.exists() && !file.isDirectory())
                {
                    file.mkdir();
                }
                String tempPath1 = tempPath+"/temp1.pdf";
                String tempPath2 = tempPath+"/temp2.pdf";
                tempos = new FileOutputStream(new File(tempPath1));
                renderer.createPDF(tempos);
                renderer.finishPDF();
                tempos.flush();
                tempos.close();

                addPdfTextMark(tempPath1,tempPath2,watermark,50,50);
                tempStream = new FileInputStream(tempPath2);
                int c = 0;
                byte[] buf = new byte[8192];
                while ((c = tempStream.read(buf, 0, buf.length)) > 0) {
                    os.write(buf, 0, c);
                    os.flush();
                }
                tempStream.close();
                FileUploadUtils.deFile(tempPath1);
                FileUploadUtils.deFile(tempPath2);
            }

            os.flush();
            os.close();
        } catch (Exception e) {
            if(os != null) os.close();
            if(tempos != null) tempos.close();
            if(tempStream != null) tempStream.close();
            throw e;
        }
    }

    public void exportPdf2(HttpServletResponse response, String filename, String content, String watermark) throws Exception {
        if (content == null || content.length() <= 0) return;
        OutputStream os = null;
        OutputStream tempos = null;
        InputStream tempStream = null;

        try {
            String tempPath = FileUploadUtils.getDefaultBaseDir()+"/Temporary";
            File file = new File(tempPath);
            if (!file.exists() && !file.isDirectory())
            {
                file.mkdir();
            }
            String tempPath1 = tempPath+"/temp1.pdf";
            String tempPath2 = tempPath+"/temp2.pdf";


            String tempPath0 = tempPath  + "/temp0.docx";
            XWPFDocument docxDocument = HtmlConvertWordUtil.htmlConvertWord(content);
            FileOutputStream out = new FileOutputStream(tempPath0);
            docxDocument.write(out);
            out.close();
            ConvertDocxToPdf(new FileInputStream(tempPath0), new FileOutputStream(tempPath1));
            tempos = new FileOutputStream(new File(tempPath1));
            tempos.flush();
            tempos.close();

            response.setCharacterEncoding("utf-8");
            response.setContentType("application/pdf");
            response.setHeader("Content-disposition", "attachment;filename="+new String((filename+".pdf").getBytes("utf-8"),"ISO8859-1"));
            os = response.getOutputStream(); //创建输出流

            createWithHtml(content,"",new FileOutputStream(new File(tempPath1)));
            if(StringUtils.isEmpty(watermark))
            {
                tempStream = new FileInputStream(tempPath1);
            }
            else
            {
                //添加水印
                addPdfTextMark(tempPath1,tempPath2,watermark,50,50);
                tempStream = new FileInputStream(tempPath2);
            }
            int c = 0;
            byte[] buf = new byte[8192];
            while ((c = tempStream.read(buf, 0, buf.length)) > 0) {
                os.write(buf, 0, c);
                os.flush();
            }
            tempStream.close();
            //FileUploadUtils.deFile(tempPath0);
            FileUploadUtils.deFile(tempPath1);
            FileUploadUtils.deFile(tempPath2);
            os.flush();
            os.close();

        } catch (Exception e) {
            if (os != null) os.close();
            if (tempos != null) tempos.close();
            if (tempStream != null) tempStream.close();
            throw e;
        }
    }

    
    public String htmlToxhtml(String html) {
        Document doc = Jsoup.parse(html);
        doc.outputSettings().syntax(Document.OutputSettings.Syntax.xml).escapeMode(Entities.EscapeMode.xhtml);
        return doc.html();
    }

    
    public void ConvertDocxToPdf(InputStream fileInputStream, OutputStream fileOutputStream){
        try {
            //添加依赖org.apache.poi.xwpf.converter.pdf和xdocreport都需要
            XWPFDocument xwpfDocument = new XWPFDocument(fileInputStream);
            PdfOptions pdfOptions = PdfOptions.create();
            //中文字体处理
            pdfOptions.fontProvider(new IFontProvider() {
                @Override
                public Font getFont(String familyName, String s1, float v, int i, Color color) {
                    try {
                        BaseFont bfChinese = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);
                        Font fontChinese = new Font(bfChinese, v, i, color);
                        if (familyName != null)
                            fontChinese.setFamily(familyName);
                        return fontChinese;
                    } catch (Exception e) {
                        e.printStackTrace();
                        return null;
                    }
                }
            });
            PdfConverter.getInstance().convert(xwpfDocument,fileOutputStream,pdfOptions);
            fileInputStream.close();
            fileOutputStream.close();
        }
        catch (Exception ex)
        {
            String aa=ex.getMessage();
        }

    }

    
    public static void addPdfTextMark(String InPdfFile, String outPdfFile, String textMark, int textWidth, int textHeight) throws Exception {
        PdfReader reader = new PdfReader(InPdfFile, "PDF".getBytes());
        PdfStamper stamp = new PdfStamper(reader, new FileOutputStream(new File(outPdfFile)));

        try
        {
            PdfContentByte under;
            PdfGState gs1 = new PdfGState();
            gs1.setFillOpacity(0.8f);// 透明度设置
            com.itextpdf.text.pdf.BaseFont font =com.itextpdf.text.pdf.BaseFont.createFont("C:/WINDOWS/Fonts/SIMSUN.TTC,1", "Identity-H", true);// 使用系统字体

            int pageSize = reader.getNumberOfPages();// 原pdf文件的总页数
            for (int i = 1; i <= pageSize; i++) {
                //under = stamp.getUnderContent(i);// 水印在之前文本下
                under = stamp.getOverContent(i);//水印在之前文本上
                under.beginText();
                under.setColorFill(new BaseColor(211,211,211));// 文字水印 颜色
                under.setGState(gs1);// 图片水印 透明度
                under.setFontAndSize(font, 32);// 文字水印 字体及字号
                under.setTextMatrix(textWidth, textHeight);// 文字水印 起始位置
                //under.showTextAligned(Element.ALIGN_CENTER, textMark, textWidth, textHeight, 45);
                for (int x = 0; x < 2; x++) {
                    for (int y = 0; y < 3; y++) {
                        under.showTextAligned(Element.ALIGN_LEFT, textMark, x*200+100, y*200+x*100, 45);
                    }
                }
                under.endText();
            }

            stamp.close();// 关闭
            reader.close();
        }
        catch (Exception e)
        {
            if(reader != null) reader.close();
            if(stamp != null) stamp.close();
            throw e;
        }

    }

    
    public static void addPdfImgMark(String InPdfFile, String outPdfFile, String markImagePath, int imgWidth, int imgHeight) throws Exception {
        PdfReader reader = new PdfReader(InPdfFile, "PDF".getBytes());
        PdfStamper stamp = new PdfStamper(reader, new FileOutputStream(new File(outPdfFile)));
        PdfContentByte under;
        PdfGState gs1 = new PdfGState();
        gs1.setFillOpacity(0.8f);// 透明度设置
        Image img = Image.getInstance(markImagePath);// 插入图片水印
        img.setAbsolutePosition(imgWidth, imgHeight); // 坐标
        img.setRotation(0);// 旋转 弧度
        img.setRotationDegrees(0);// 旋转 角度
        img.scaleAbsolute(595, 842);// 自定义大小
        // img.scalePercent(50);//依照比例缩放
        int pageSize = reader.getNumberOfPages();// 原pdf文件的总页数
        for (int i = 1; i <= pageSize; i++) {
            under = stamp.getUnderContent(i);// 水印在之前文本下
            // under = stamp.getOverContent(i);//水印在之前文本上
            under.setGState(gs1);// 图片水印 透明度
            under.addImage(img);// 图片水印
        }
        stamp.close();// 关闭
    }

    public void createWithHtml(String templateString,String extraHtml, OutputStream outputStream) throws Exception{
        com.itextpdf.text.Document document = new com.itextpdf.text.Document();
        //页面竖向
        Rectangle pageSize = new Rectangle(PageSize.A4.getWidth(), PageSize.A4.getHeight());
        pageSize.rotate();
        document.setPageSize(pageSize);
        PdfWriter pdfWriter = PdfWriter.getInstance(document,outputStream);
        int width = Math.round(PageSize.A4.getWidth());
        document.open();
        document.addCreationDate();
        XMLWorkerHelper worker = XMLWorkerHelper.getInstance();
        String mdContent = templateString;
        Charset charset =  Charset.forName("utf-8"); //Charset.forName("GBK");
        String htmlContent = "" + templateString + "";
        org.jsoup.nodes.Document htmlDoc = Jsoup.parse(htmlContent, "", Parser.xmlParser());

        org.jsoup.select.Elements centerEle = htmlDoc.select("center");

        Elements tblist = htmlDoc.select("table");
        if(tblist!=null){
            for(org.jsoup.nodes.Element element : tblist){
                element.attr("width","100%");
            }
        }

        //处理h1~h6问题
        Elements aList = htmlDoc.select("h1 a,h2 a,h3 a,h4 a,h5 a,h6 a");
        if(aList != null)
        {
            for (org.jsoup.nodes.Element a : aList) {
                String text = a.text();
                a.text("");
                a.appendElement("strong");
                a.child(0).text(text);
            }
        }
        Elements imglist = htmlDoc.select("img");
        if(imglist != null)
        {
            for (org.jsoup.nodes.Element a : imglist)
            {
                //处理图片
                Attributes as = a.attributes();
                String src = as.get("src");
                HttpServletRequest request = ServletUtils.getRequest();
                String ur = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort();
                String pictureUrl = "";
                if(src.contains("//")){
                    pictureUrl = src;
                }else{
                    pictureUrl = ur+src;
                }

                try
                {
                    Image img = Image.getInstance(pictureUrl);
                    if(img.getWidth()>width)
                    {
                        int imgwidth = Math.round(width*100/80);
                        int imgheight = Math.round(img.getHeight()*width/imgwidth);
                        img.scaleAbsolute(imgwidth,imgheight);
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }

            }
        }

        String bodyContent = htmlDoc.select("body").html();
        bodyContent = htmlToxhtml(bodyContent);
        worker.parseXHtml(pdfWriter, document, new ByteArrayInputStream(bodyContent.getBytes(charset))
                , new  ByteArrayInputStream(DEFAULT_ORDER_CSS.getBytes())
                ,charset
                , new AsianFontProvider("/Fonts/SimSun.ttf","/Fonts/simsunbd.ttf"));

        document.close();
        pdfWriter.close();
    }

}
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/1032019.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号