Как добавить прозрачный текст водяного знака на каждую страницу, используя iText7 pdfHtml - PullRequest
0 голосов
/ 26 марта 2019

В настоящее время я пытаюсь добавить водяной знак, который появляется на заднем плане каждой страницы моего pdf, используя iText7 pdfHtml, но я не могу найти решение.Например, я хотел бы, чтобы текст «Конфиденциально» появлялся на заднем плане каждой страницы.Я попытался добавить его с помощью css, например

@page {
    size: Letter;
    margin: .5in .5in .5in .5in;

    @left-middle {
        content: "Confidential";
        /* z-index: 100; */
        font-size: 80pt;
        font-weight: bold;
        opacity: .2;
        text-align: center;
        text-transform: uppercase;
        transform: translateX(350px) rotate(-54.7deg);
        position: absolute;
        left: 0;
        top: 0;
        width: 100%;
        height: 100%;
        overflow: auto;
        z-index: 0;
    }
}

Это почти решает мою проблему, но текст не прозрачен и скрывает текст позади него.Он также не вращается, но это не является обязательным требованием.

Приветствуются решения, включающие некоторую комбинацию Java, CSS или Html.

Вот пример моего кода Java:

        FileInputStream htmlStream = null;
        FileOutputStream pdfStream = null;

        try {
            ConverterProperties converterProperties = new ConverterProperties().setBaseUri(path);
            converterProperties.setMediaDeviceDescription(new MediaDeviceDescription(MediaType.PRINT));
            htmlStream = new FileInputStream(inputPath);
            pdfStream = new FileOutputStream(outputPath);
            HtmlConverter.convertToPdf(htmlStream, pdfStream, converterProperties);

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } finally {
            if (htmlStream != null) {
                htmlStream.close();
            }
            if (pdfStream != null) {
                pdfStream.close();
            }
        }

Изменить

образец html для воспроизведения:

<!DOCTYPE html>
<html>
<link id="watermark_link" href="watermark.css" rel="stylesheet" type="text/css" />
</head>

<body>
    <h1>My First Heading</h1>
    <p>My first paragraph.</p>
</body>

</html>

Редактировать 2

Послев ответе @BenIngle здесь приведен мой Java-код для работы с pdfHtml:

    private static void generatePDFFromHTML(String inputPath, String outputPath, String baseUrl) throws IOException {
        FileInputStream htmlStream = null;
        FileOutputStream pdfStream = null;

        try {
            ConverterProperties converterProperties = new ConverterProperties().setBaseUri(baseUrl);
            converterProperties.setMediaDeviceDescription(new MediaDeviceDescription(MediaType.PRINT));
            htmlStream = new FileInputStream(inputPath);
            pdfStream = new FileOutputStream(outputPath);
            PdfWriter writer = new PdfWriter(pdfStream);
            PdfDocument pdfDocument = new PdfDocument(writer);
            Watermark watermark = new Watermark("Confidential");
            pdfDocument.addEventHandler(PdfDocumentEvent.END_PAGE,watermark);
            HtmlConverter.convertToPdf(htmlStream, pdfDocument, converterProperties);
            pdfDocument.close();

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } finally {
            if (htmlStream != null) {
                htmlStream.close();
            }
            if (pdfStream != null) {
                pdfStream.close();
            }
        }

    }

    protected static class Watermark implements IEventHandler {

        String watermarkText;

        public Watermark(String watermarkText) {
            this.watermarkText = watermarkText;
        }

        @Override
        public void handleEvent(Event event) {
            //Retrieve document and
            PdfDocumentEvent docEvent = (PdfDocumentEvent) event;
            PdfDocument pdf = docEvent.getDocument();
            PdfPage page = docEvent.getPage();
            Rectangle pageSize = page.getPageSize();
            PdfCanvas pdfCanvas = new PdfCanvas(page.getLastContentStream(), page.getResources(), pdf);
            Canvas canvas = new Canvas(pdfCanvas, pdf, pageSize);
            PdfExtGState gstate = new PdfExtGState();
            gstate.setFillOpacity(.2f);
            pdfCanvas.setExtGState(gstate);

            double rotationDeg = -54.7d;
            double rotationRad = Math.toRadians(rotationDeg);
            Paragraph watermarkParagraph = new Paragraph(watermarkText)
                    .setFontSize(80f)
                    .setTextAlignment(TextAlignment.CENTER)
                    .setVerticalAlignment(VerticalAlignment.MIDDLE)
                    .setRotationAngle(rotationRad)
                    .setFixedPosition(100, page.getPageSize().getHeight(), page.getPageSize().getWidth());
            canvas.add(watermarkParagraph);
            canvas.close();

        }

    }

Надеюсь, это поможет всем, кто пытается начать работу с iText pdfHtml!

1 Ответ

0 голосов
/ 28 марта 2019

Вот решение для добавления текста "в фоновом режиме каждой страницы". Это добавит текст позади существующего контента, чтобы он не закрывал его. Обратите внимание, что это не добавляет прозрачности. Прозрачность должна быть добавлена ​​с внешним графическим состоянием.

try (PdfDocument doc = new PdfDocument(new PdfReader(in.toFile()), new PdfWriter(out.toFile()))) {
    PdfFont helvetica = PdfFontFactory.createFont();
    for (int pageNum = 1; pageNum <= doc.getNumberOfPages(); pageNum++) {
        PdfPage page = doc.getPage(pageNum);
        // important - add a new content stream in the beginning, to render behind existing text
        PdfCanvas canvas = new PdfCanvas(page.newContentStreamBefore(), page.getResources(), doc);

        // option 1 - manual placement
        canvas.saveState();
        canvas.beginText();
        canvas.setFillColor(ColorConstants.GRAY);
        canvas.setFontAndSize(helvetica, 80f);
        canvas.moveText(0f, page.getPageSize().getHeight() - 80f);
        canvas.showText("Confidential1");
        canvas.endText();
        canvas.restoreState();

        // option 2 - let iText place it
        try (Canvas canvas1 = new Canvas(canvas, doc, page.getPageSize())) {
            Paragraph watermark = new Paragraph("Confidential2")
                    .setFontColor(ColorConstants.GRAY)
                    .setFont(helvetica)
                    .setFontSize(80f)
                    .setHorizontalAlignment(HorizontalAlignment.LEFT)
                    .setVerticalAlignment(VerticalAlignment.BOTTOM)
                    .setFixedPosition(0f, page.getPageSize().getHeight() - 100f, page.getPageSize().getWidth());
            canvas1.add(watermark);
        }

        // option 3 - set opacity and place on top of existing content, plus rotation
        PdfExtGState gstate = new PdfExtGState();
        gstate.setFillOpacity(.2f);
        canvas = new PdfCanvas(page);
        canvas.saveState();
        canvas.setExtGState(gstate);
        try (Canvas canvas2 = new Canvas(canvas, doc, page.getPageSize())) {
            double rotationDeg = -54.7d;
            double rotationRad = Math.toRadians(rotationDeg);
            Paragraph watermark = new Paragraph("Confidential3")
                    .setFont(helvetica)
                    .setFontSize(80f)
                    .setTextAlignment(TextAlignment.CENTER)
                    .setVerticalAlignment(VerticalAlignment.MIDDLE)
                    .setRotationAngle(rotationRad)
                    .setFixedPosition(100, page.getPageSize().getHeight(), page.getPageSize().getWidth());
            canvas2.add(watermark);
        }
        canvas.restoreState();
    }
}

Редактировать

Добавлен третий параметр, который применяет прозрачность и вращение.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...