iTextSharp水印未出现在扫描的PDF中

时间:2018-07-27 09:48:09

标签: c# itext pdf-generation

我有一些代码用于使用iTextSharp给PDF加水印。该代码对大多数PDF都适用,但是有一个测试用例,其中水印在扫描文档的PDF上不可见。 (不过,我还有其他扫描的文档出现在其中)。

我正在使用GetOverContent()方法。

这是我添加水印的代码;

using (PdfReader reader = new PdfReader(this.inputFilename))
{
    // Set transparent  - 1
    PdfGState gstate = new PdfGState();
    gstate.FillOpacity = 0.4f;
    gstate.StrokeOpacity = 0.5f;
    // 2
    BaseFont baseFont = BaseFont.CreateFont(BaseFont.HELVETICA_BOLD, Encoding.ASCII.EncodingName, false);

    using (var stream = new MemoryStream())
    {
        var pdfStamper = new PdfStamper(reader, stream);

        // Must start at 1 because 0 is not an actual page.
        for (int i = 1; i <= reader.NumberOfPages; i++)
        {
            Rectangle pageSize = reader.GetPageSizeWithRotation(i);

            // Gets the content ABOVE the PDF, Another option is GetUnderContent(...)  
            // which will place the text below the PDF content. 
            PdfContentByte pdfPageContents = pdfStamper.GetOverContent(i);
            pdfPageContents.BeginText(); // Start working with text.

            // 1 
            pdfPageContents.SaveState();
            pdfPageContents.SetGState(gstate);

            float hypotenuse = (float)Math.Sqrt(Math.Pow(pageSize.Width, 2) + Math.Pow(pageSize.Height, 2));
            float glyphWidth = baseFont.GetWidth("My watermark text");
            float fontSize = 1000 * (hypotenuse * 0.8f) / glyphWidth;
            float angle = (float)(Math.Atan(pageSize.Height / pageSize.Width) * (180 / Math.PI));

            // Create a font to work with 
            pdfPageContents.SetFontAndSize(baseFont, fontSize);
            pdfPageContents.SetRGBColorFill(128, 128, 128); // Sets the color of the font, GRAY in this instance

            // Note: The x,y of the Pdf Matrix is from bottom left corner. 
            // This command tells iTextSharp to write the text at a certain location with a certain angle.
            // Again, this will angle the text from bottom left corner to top right corner and it will 
            // place the text in the middle of the page. 
            pdfPageContents.ShowTextAligned(PdfContentByte.ALIGN_CENTER, "My watermark text", pageSize.Width / 2, pageSize.Height / 2, angle);
            pdfPageContents.EndText(); // Done working with text
            pdfPageContents.RestoreState();
        }

        pdfStamper.FormFlattening = true; // enable this if you want the PDF flattened. 
        pdfStamper.FreeTextFlattening = true; // enable this if you want the PDF flattened. 
        pdfStamper.Close(); // Always close the stamper or you'll have a 0 byte stream. 

        return stream.ToArray();
    }
}

有人对水印为什么不出现以及我可以如何解决这个问题有任何想法吗?

亲切的问候。

1 个答案:

答案 0 :(得分:1)

该代码基于一个假设,甚至可以将其记录为事实:

// Note: The x,y of the Pdf Matrix is from bottom left corner. 
// This command tells iTextSharp to write the text at a certain location with a certain angle.
// Again, this will angle the text from bottom left corner to top right corner and it will 
// place the text in the middle of the page. 
pdfPageContents.ShowTextAligned(PdfContentByte.ALIGN_CENTER, "My watermark text", pageSize.Width / 2, pageSize.Height / 2, angle);

不幸的是,假设 Pdf矩阵的x,y来自左下角是错误的:尽管在很多情况下,PDF坐标系的原点确实是这样(默认用户更精确地说,是空间坐标系)位于页面的左下角,这不是必需的,原点实际上可以在任何地方(在合理范围内)。

因此,也必须考虑Rectangle pageSize的左下角坐标。

同时OP已确认:

  

我假设页面的左下角的坐标为(0,0),但是对于本文档,坐标为(0,7022)。