问题:
我似乎无法将一种坐标格式与另一种格式配合使用。我想我只是没有使用正确的矩阵,但我对它们的了解还不够确定。我希望能得到一些帮助,弄清楚我是否在假设我的转变应该是什么
根据ISO标准,iText使用左下角作为原点,但pdfbox代码和为我提供从pdf中抓取坐标的程序都使用左上角作为原点。
我应该做什么变换来调整坐标,以便iText能够以有效的方式使用它们?
背景
我有一些代码使用pdfbox来操作pdf并剥离一些数据,现在我需要将修改后的数据重新注入页面。PDFBox的作者一直在破坏pdf,所以我们决定使用iText来进行注入。
诀窍是,我在pdfbox中使用的坐标(以及我们从生成pdf的系统中获得的坐标(似乎与iText不匹配。
到目前为止我做了什么
我检查了一下,iText页面和隔板似乎都是准确的:
PdfReader splitPDFDocumentReader = new PdfReader(splitPDFdocumentName);
com.lowagie.text.Rectangle theCropBox = splitPDFDocumentReader.getCropBox(1);
com.lowagie.text.Rectangle thePageSize = splitPDFDocumentReader.getPageSize(1);
consolePrintln("Cropbox: " + theCropBox.toString());
consolePrintln("tBottom " + theCropBox.getBottom());
consolePrintln("tLeft " + theCropBox.getLeft());
consolePrintln("tTop " + theCropBox.getTop());
consolePrintln("tRight " + theCropBox.getRight());
consolePrintln("PageSize: " + thePageSize.toString());
consolePrintln("tBottom " + thePageSize.getBottom());
consolePrintln("tLeft " + thePageSize.getLeft());
consolePrintln("tTop " + thePageSize.getTop());
consolePrintln("tRight " + thePageSize.getRight());
输出:
Cropbox: Rectangle: 612.0x792.0 (rot: 0 degrees)
Bottom 0.0
Left 0.0
Top 792.0
Right 612.0
PageSize: Rectangle: 612.0x792.0 (rot: 0 degrees)
Bottom 0.0
Left 0.0
Top 792.0
Right 612.0
这让我相信这只是翻转y坐标的问题,因为pdfbox的原点在左上角,而iText在左下角。
我遇到麻烦的地方
当我应用转换时:
// matrix data example:
// [m00, m01, m02,
// m10, m11, m12,
// 0 , 0 , 1 ] // this bit is implied as part of affineTransform docs
content.saveState();
int m00 = 1;
int m01 = 0;
int m02 = 0;
int m10 = 0;
int m11 = -1;
int m12 = 0;
content.concatCTM(m00, m10, m01, m11, m02, m12);
content.setColorStroke(Color.RED);
content.setColorFill(Color.white);
content.rectangle(x, y, x + height, y + width);
content.fillStroke();
content.restoreState();
它似乎没有达到我的预期。数据似乎完全在页面之外。
杂项注释
老实说,我对矩阵不是很在行,也许我需要做一些翻译工作,而不是像我试图做的那样只偷y?
concatTM函数似乎采用了与awt.geom.affinetransform相同的格式,我将通过这个例子和教程来使用转换。
我想明白了。当我在绘制y坐标时,我假设它会翻转到文档的中间,并将所有内容翻转过来。然而,它实际上在y=0这条线上翻转;
在它翻转到y=0之后,您需要将整个页面移回原来的位置。
我最终直接使用affineTransform来完成它,然后将生成的矩阵输入concatTM。
content.saveState();
AffineTransform transform = new AffineTransform();
transform.scale(1, -1); // flip along the line y=0
transform.translate(0, -pageHeight); // move the page conet back up
/* the version of iText used in Jasper iReport doesn't seem to use affineTransform directly */
double[] transformMatrix = new double[6];
transform.getMatrix(transformMatrix);
content.concatCTM((float) transformMatrix[0], (float) transformMatrix[1], (float) transformMatrix[2], (float) transformMatrix[3], (float) transformMatrix[4], (float) transformMatrix[5]);
// drawing and printing code here (stamping?)
content.restoreState();