Add a tiled watermark to PDF pages

PDF Watermark Drawing Text

This sample shows how to add a semi-transparent, rotated text watermark to every page of an existing PDF file. It demonstrates copying each source page's content into a new PDF with PdfReader, PdfWriter, and GraphicsContainer, then using TilingBrush to repeat rotated PlainText across the page as a watermark pattern.

Сode Snippet

const float dpi = 72;

using (var reader = new PdfReader("GraphicsContainer.pdf", dpi, dpi))
using (var writer = new PdfWriter("GraphicsContainerWithWatermark.pdf"))
using (var graphics = writer.GetGraphics())
{
    foreach (var frame in reader.Frames.OfType<PdfFrame>())
    {
        using (var pageContent = frame.GetContent())
        {
            // Recreate the page with the same size and resolution as the source content.
            writer.AddPage(pageContent.Width, pageContent.Height, pageContent.DpiX, pageContent.DpiY);

            // Copy the original page content before drawing the watermark on top of it.
            graphics.DrawContainer(pageContent, 0, 0);

            var text = new PlainText("watermark text", graphics.CreateFont("Arial", 30))
            {
                Brush = new SolidBrush(RgbColor.Violet.ScaleAlpha(0.25f)),
            };

            // Measure the text so the tile can be sized to fit it exactly.
            var bbox = text.GetBlackBox(graphics.FontRegistry, dpi, dpi);

            var tilingBrush = new TilingBrush(bbox.Width, bbox.Height, dpi, dpi);
            tilingBrush.Graphics.FontRegistry = graphics.FontRegistry;

            // Shift the text so its bounding box starts at the tile's origin, keeping it fully inside the tile.
            tilingBrush.Graphics.Transform.Translate(-bbox.Left, -bbox.Top);
            tilingBrush.Graphics.DrawText(text);

            // Rotate the tile pattern so the repeated watermark text reads diagonally across the page.
            tilingBrush.Transform.Rotate(30);

            // Fill the whole page with the rotated, tiled watermark text.
            graphics.FillRectangle(tilingBrush, 0, 0, graphics.Width, graphics.Height);
        }
    }
}

Input

GraphicsContainer.png

GraphicsContainer.pdf

Download

Output

GraphicsContainerWithWatermark.png

GraphicsContainerWithWatermark.pdf

Download

For AI-assisted development: Download Graphics Mill Code Samples XML Catalog