我知道之前也曾问过类似的问题,但是它们已经过时了(有些可以追溯到2006年)。
我有一个.net 3.5应用程序(带有iTextSharp 5),我正在转换为.net核心(iText 7),该内核从FedEx跟踪文档中提取签名,并通过SOAP服务以byte []数组的形式发送。多年来,此代码在进行较小的更新后一直运行良好。从Fedex返回的PDF文档中有几张图像,但签名块不是110x46图像(这是pdf文件中的fedex徽标,因此为什么我跳过它。)
PdfReader pdf = new PdfReader(FedexData);
for(Int32 iPage = 1; iPage <= pdfReader.NumberOfPages; iPage++)
{
PdfDictionary pg = pdf.GetPageN(iPage);
PdfDictionary res = (PdfDictionary)PdfReader.GetPdfObject(pg.Get(PdfName.RESOURCES));
PdfDictionary xobj = (PdfDictionary)PdfReader.GetPdfObject(res.Get(PdfName.XOBJECT));
foreach(PdfName name in xobj.Keys)
{
PdfObject obj = xobj.Get(name);
if(obj.IsIndirect())
{
PdfDictionary tg = (PdfDictionary)PdfReader.GetPdfObject(obj);
String width = tg.Get(PdfName.WIDTH).ToString();
String height = tg.Get(PdfName.HEIGHT).ToString();
String decode = tg.Contains(PdfName.DECODEPARMS) ? tg.Get(PdfName.DECODEPARMS).ToString() : "";
String bitspercomponent = tg.Contains(PdfName.BITSPERCOMPONENT) ? tg.Get(PdfName.BITSPERCOMPONENT).ToString() : "";
String colorspace = tg.Contains(PdfName.COLORSPACE) ? tg.Get(PdfName.COLORSPACE).ToString() : "";
if(width != "110" && height != "46" && bitspercomponent != "1")
{
ImageRenderInfo imgRI = ImageRenderInfo.CreateForXObject(new GraphicsState(), (PRIndirectReference)obj, tg);
PdfImageObject image = imgRI.GetImage();
Image dotnetImg = image.GetDrawingImage();
if(dotnetImg != null)
{
// process image and update database
足以说明此代码不适用于iText7。我试图移植其中的一些,但似乎没有得到图像....所以我显然做错了一些事情,但我自己对iText7函数的无知,似乎并不能与旧版库向下兼容
有人可以给我指出iText7教程,该教程涉及提取存储在PDF文件中的图像吗?我找到了有关如何将PDF提取为图像(不是我想要的),如何将图像存储在PDF文档中(与我想要的相反)的教程,并且类似的问题答案都基于不再起作用的较早的库
谢谢, Vin
答案 0 :(得分:0)
这是IEventListener
的Java实现,可用于访问特定页面上的所有图像:
public class MyImageRenderListener implements IEventListener {
protected String path;
protected String extension;
public MyImageRenderListener(String path) {
this.path = path;
}
public void eventOccurred(IEventData data, EventType type) {
switch (type) {
case RENDER_IMAGE:
try {
String filename;
FileOutputStream os;
ImageRenderInfo renderInfo = (ImageRenderInfo) data;
PdfImageXObject image = renderInfo.getImage();
if (image == null) {
return;
}
// You can access various value from dictionary here:
PdfString decodeParamsPdfStr = image.getPdfObject().getAsString(PdfName.DecodeParms);
String decodeParams = decodeParamsPdfStr != null ? decodeParamsPdfStr.toUnicodeString() : null;
byte[] imageByte = image.getImageBytes(true);
extension = image.identifyImageFileExtension();
// You can use raw image bytes directly, or write image to disk
filename = String.format(path, image.getPdfObject().getIndirectReference().getObjNumber(), extension);
os = new FileOutputStream(filename);
os.write(imageByte);
os.flush();
os.close();
} catch (com.itextpdf.io.IOException | IOException e) {
System.out.println(e.getMessage());
}
break;
default:
break;
}
}
public Set<EventType> getSupportedEvents() {
return null;
}
}
我已经评论了一些您可能感兴趣的部分。
这是实际上为所有页面或感兴趣的任何页面调用处理器的代码:
PdfDocument pdfDoc = new PdfDocument(new PdfReader(src));
IEventListener listener = new MyImageRenderListener(outPath);
PdfCanvasProcessor parser = new PdfCanvasProcessor(listener);
for (int i = 1; i <= pdfDoc.getNumberOfPages(); i++) {
parser.processPageContent(pdfDoc.getPage(i));
}
pdfDoc.close();