猿问

如何使用pdfbox在pdf最后一页的左下角位置应用数字签名图像?

标题说明了一切,我能够使用 pdfbox 版本 2.0.8 对 pdf 进行可视化签名。目前我必须在代码中对图像的起始协调进行硬编码。但随着 PDF 的变化,图像的位置总是需要相应地改变。我想在 pdf 末尾的左角应用签名图像。我如何在代码中获得该位置?这是我的代码,使用 _x 和 _y 进行硬编码坐标。在代码中,'signing'是可见的签名对象,'page'是pdf的最后一页,'args[2]'是要签名的pdf文件:


int _x = 30;

int _y = 420;

signing.setVisibleSignDesigner(args[2], _x, _y, -50, imageStream, page);

imageStream.close();

signing.setExternalSigning(externalSig);

signing.signPDF(documentFile, signedDocumentFile, tsaClient);

removeFile(imageResult);

我想要的签名示例:

编辑:添加图像以澄清我希望签名字段位于文档的末尾,而不是最后一页的末尾。文档可以在最后一页的顶部完成,因此字段也应该位于文本后面而不是页面的末尾。抱歉,我之前的问题不清楚。



动漫人物
浏览 219回答 1
1回答

森林海

根据问题评论中的说明,您尝试将签名放置在最后一个文档页面现有内容的边界框下方。但正如您在对此评论的回应中发现的那样,您不能简单地使用其结果作为输入,因为CreateVisibleSignature.setVisibleSignDesigner假定了不同的坐标系:使用相关页面的 PDF 默认用户空间坐标:它们由相关页面的MediaBoxBoundingBoxFinder给出,并且y坐标向上增加。通常原点位于页面的左下角。CreateVisibleSignature另一方面,使用单位长度相同但原点位于页面左上角且 y坐标向下增加的坐标系。因此,必须转换坐标,例如:File documentFile = new File(SOURCE);File signedDocumentFile = new File(RESULT);Rectangle2D boundingBox;PDRectangle mediaBox;try (   PDDocument document = PDDocument.load(documentFile) ) {    PDPage pdPage = document.getPage(0);    BoundingBoxFinder boundingBoxFinder = new BoundingBoxFinder(pdPage);    boundingBoxFinder.processPage(pdPage);    boundingBox = boundingBoxFinder.getBoundingBox();    mediaBox = pdPage.getMediaBox();}CreateVisibleSignature signing = new CreateVisibleSignature(ks, PASSWORD.clone());try (   InputStream imageStream = IMAGE_STREAM) {    signing.setVisibleSignDesigner(documentFile.getPath(), (int)boundingBox.getX(), (int)(mediaBox.getUpperRightY() - boundingBox.getY()), -50, imageStream, 1);}signing.setVisibleSignatureProperties("name", "location", "Security", 0, 1, true);signing.setExternalSigning(false);signing.signPDF(documentFile, signedDocumentFile, null);评论将上面的代码应用到该文件,人们会发现最后可见的文本行和图像之间有一个小间隙。此间隙是由“请访问我们的网站”行下方的一行中的一些空格字符引起的。它BoundingBoxFinder不会检查绘图指令最终是否会产生可见的结果,它总是将有问题的区域添加到边界框。一般来说,您可能需要从上面代码计算出的y坐标中减去一点点,以在以前的页面内容和新的签名小部件之间创建视觉间隙。查看源代码CreateVisibleSignature会发现,实际上y坐标是通过从MediaBox 的高度中减去它们来转换的,而不是从其上边框值中减去它们。最终这些坐标被复制到目标文档中。因此,可能需要在上面的代码中使用而不是。mediaBox.getHeight()mediaBox.getUpperRightY()查看源代码后CreateVisibleSignature2发现,实际上使用了CropBox而不是MediaBox。如果您的代码源自该示例,您可能必须在上面的代码中替换pdPage.getMediaBox()为。pdPage.getCropBox()一般来说,任意使用不同的坐标系是使用 PDFBox 时相当少的令人烦恼的来源之一。
随时随地看视频慕课网APP

相关分类

Java
我要回答