1

I'm using iTextSharp to populate the data to PDF Templates, which is created in OpenOffice. it populating fine, I'm getting proper PDF, Watermark is not displaying properly.

below is my code:

public void addWaterMark(PdfStamper stamper, int pageNumber, Watermark watermark)
    {
        List<WatermarkField> watermarkFields = watermark.getWatermarkFieldAsReference();
        for (WatermarkField watermarkField : watermarkFields) {
            // setting font and font size for the watermark text
            Font FONT = new Font(FontFamily.HELVETICA, watermarkField.getFontSize(), Font.BOLD, new GrayColor(0.75f));
            // setting alignment for the watermark
            ColumnText.showTextAligned(stamper.getUnderContent(pageNumber), Element.ALIGN_CENTER, new Phrase(watermarkField.getText(), FONT), watermarkField.getXDirection(), watermarkField.getYDirection(), watermarkField.getRotation());
        }

    } 

When i putting in background text-boxes are hiding the watermark.
When i putting in foreground watermark is hiding the text.
Both screen shorts are attaching below.

enter image description here

enter image description here

Please Suggest me the solution. Thanks.

Rajesh Narravula
  • 1,433
  • 3
  • 26
  • 54
  • What do you expect? Obviously something in the foreground covers while something in the background is covered. That been said you can reduce the amount the writing in the foreground covers by using outline writing or transparency. – mkl Jun 27 '14 at 06:34
  • 1
    [This answer](http://stackoverflow.com/questions/20351916/how-to-make-my-watermark-text-in-any-pdf-file-as-non-selectable/20361261#20361261) among other stuff contains code for using outline-only overcontent marks. It is using iText/Java but should be easy to translate for iTextSharp/C#. – mkl Jun 27 '14 at 06:54
  • mkl is correct `getUnderContent()` is the culprit. You need `getOverContent()` if you don't want the Watermark to be covered by existing content. Of course: if you don't want to cover the existing content with the watermark, you need to make it transparent as described in mkl's answer to http://stackoverflow.com/questions/20351916/how-to-make-my-watermark-text-in-any-pdf-file-as-non-selectable/ – Bruno Lowagie Jun 27 '14 at 07:10
  • @mkl here my problem is when i use `getOverContent()`, label text is covered(which is there in the Template). Strock is ok, but client is not accepting. – Rajesh Narravula Jun 27 '14 at 09:57
  • *client is not accepting* - what would he accept then? Transparency? – mkl Jun 27 '14 at 10:50
  • @mkl they want Transparency.. not Strocked one, they want filled one, like first screenshot, with Transparent. – Rajesh Narravula Jun 27 '14 at 11:21
  • You might want to try enclosing your operation on the OverContent in `overContent.saveState(); PdfGState state = new PdfGState(); state.setFillOpacity(0.5f); overContent.setGState(state);` and `overContent.restoreState();` – mkl Jun 27 '14 at 12:41

2 Answers2

2

In this answer there already are some ideas on how to add watermarks (in the under content, in the over content, both in the under content and in the over content before bitmaps.,,,).

The missing use case, a transparent mark in the over content, can be generated like this:

void addSimpleTransparentPatternToOverContent(File source, File target) throws IOException, DocumentException
{
    PdfReader reader = new PdfReader(source.getPath());
    OutputStream os = new FileOutputStream(target);
    PdfStamper stamper = new PdfStamper(reader, os);

    PdfPatternPainter painter = stamper.getOverContent(1).createPattern(200, 150);
    painter.setColorFill(BaseColor.GREEN);
    painter.beginText();
    painter.setTextMatrix(AffineTransform.getTranslateInstance(0, 50));
    painter.setFontAndSize(BaseFont.createFont(), 100);
    painter.showText("Test");
    painter.endText();

    PdfGState state = new PdfGState();
    state.setFillOpacity(0.5f);

    for (int i = reader.getNumberOfPages(); i > 0; i--)
    {
        PdfContentByte overContent = stamper.getOverContent(i);

        overContent.setGState(state);
        overContent.setColorFill(new PatternColor(painter));
        overContent.rectangle(200, 300, 200, 150);
        overContent.fill();
    }

    stamper.close();
    os.close();
}

In the spirit of that other answer the mark is generated using a pattern to prevent the watermark from appearing in copy&paste outputs.

You can change the transparency / opacity by selecting a different value in state.setFillOpacity(0.5f).

Community
  • 1
  • 1
mkl
  • 90,588
  • 15
  • 125
  • 265
0

This is the actual code.

public void addWaterMark(PdfStamper stamper, int pageNumber, Watermark watermark){
    List<WatermarkField> watermarkFields = watermark.getWatermarkFieldAsReference();
    PdfReader reader = stamper.getReader();
    Rectangle pageSize = reader.getPageSize(1);
    BaseFont font = BaseFont.createFont(BaseFont.HELVETICA_BOLD, BaseFont.WINANSI, BaseFont.NOT_EMBEDDED);

    PdfPatternPainter painter = stamper.getOverContent(1).createPattern(pageSize.getWidth(), pageSize.getHeight());
    painter.setColorStroke(new BaseColor(192, 192, 192));
    painter.setLineDash(0.4f, 0.4f, 0.2f);
    painter.beginText();
    painter.setTextMatrix(AffineTransform.getTranslateInstance(0, 50));
    for (WatermarkField watermarkField : watermarkFields) {
        painter.setFontAndSize(font, watermarkField.getFontSize());
        painter.showTextAlignedKerned(Element.ALIGN_MIDDLE, watermarkField.getText(), watermarkField.getXDirection(), watermarkField.getYDirection(),
        watermarkField.getRotation());
    }
    painter.endText();
    PdfGState state = new PdfGState();
    state.setFillOpacity(0.2f);
    PdfContentByte overContent = stamper.getOverContent(pageNumber);
    overContent.setGState(state);
    overContent.setColorFill(new PatternColor(painter));
    overContent.rectangle(pageSize.getLeft(), pageSize.getBottom(), pageSize.getWidth(), pageSize.getHeight());
    overContent.fill();
}
Rajesh Narravula
  • 1,433
  • 3
  • 26
  • 54