简体   繁体   English

用 iText 读取图像签名流/对象..是黑色背景和白色前景,如何反转

[英]With iText Reading an image signature stream/object..is black background and white foreground, how to reverse

I am trying to read image objects from a PDF document.我正在尝试从 PDF 文档中读取图像对象。 The image comes out as black background and white text.图像显示为黑色背景和白色文本。 How can I reverse that.我怎么能扭转它。 the image in the pdf, is white foreground and black background. pdf 中的图像是白色前景和黑色背景。

Here is the code, main piece for loading the image component这是代码,用于加载图像组件的主要部分

import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;

import javax.imageio.ImageIO;

import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Image;
import com.itextpdf.text.pdf.PRStream;
import com.itextpdf.text.pdf.PdfDictionary;
import com.itextpdf.text.pdf.PdfName;
import com.itextpdf.text.pdf.parser.ImageRenderInfo;
import com.itextpdf.text.pdf.parser.PdfImageObject;
import com.itextpdf.text.pdf.parser.RenderListener;
import com.itextpdf.text.pdf.parser.TextRenderInfo;

public class MyImageRenderListener implements RenderListener {

    /**
     * The new document to which we've added a border rectangle.
     */
    protected String path = "";

    /**
     * Creates a RenderListener that will look for images.
     */
    public MyImageRenderListener(String path) {
        this.path = path;
    }

    /**
     * @see com.itextpdf.text.pdf.parser.RenderListener#beginTextBlock()
     */
    public void beginTextBlock() {
    }

    /**
     * @see com.itextpdf.text.pdf.parser.RenderListener#endTextBlock()
     */
    public void endTextBlock() {
    }

    /**
     * @see com.itextpdf.text.pdf.parser.RenderListener#renderImage(
     *com.itextpdf.text.pdf.parser.ImageRenderInfo)
     */
    public void renderImage(final ImageRenderInfo renderInfo) {
        try {
            String filename;
            FileOutputStream os;
            PdfImageObject image = renderInfo.getImage();
            PdfImageObject tmp = null;
            PdfName filter = (PdfName) image.get(PdfName.FILTER);

            ///
            PdfDictionary imageDictionary = image.getDictionary();
            // Try SMASK, SMASKINDATA
            PRStream maskStream = (PRStream) imageDictionary.getAsStream(PdfName.SMASK);

            // todo - required - black white - fix
            PdfImageObject maskImage = new PdfImageObject(maskStream);
            image = maskImage;
            if (PdfName.DCTDECODE.equals(filter)) {
                filename = String.format(path, renderInfo.getRef().getNumber(), "jpg");
                os = new FileOutputStream(filename);
                os.write(image.getImageAsBytes());
                os.flush();
                os.close();
            } else if (PdfName.JPXDECODE.equals(filter)) {
                filename = String.format(path, renderInfo.getRef().getNumber(), "jp2");
                os = new FileOutputStream(filename);
                os.write(image.getImageAsBytes());
                os.flush();
                os.close();
            } else if (PdfName.JBIG2DECODE.equals(filter)) {
                // ignore: filter not supported.
            } else {
                BufferedImage awtimage = renderInfo.getImage().getBufferedImage();
                if (awtimage != null) {
                    filename = String.format(path, renderInfo.getRef().getNumber(), "png");
                    ImageIO.write(awtimage, "png", new FileOutputStream(filename));
                }
            }

            try {
                final String newfile = String.format(path, renderInfo.getRef().getNumber(), ".x.", "png");

                BufferedImage bi = image.getBufferedImage();
                BufferedImage newBi = new BufferedImage(bi.getWidth(), bi.getHeight(), BufferedImage.TYPE_USHORT_GRAY);
                newBi.getGraphics().drawImage(bi, 0, 0, null);
                ImageIO.write(newBi, "png", new FileOutputStream(newfile));
            } catch(final Exception e) {
                e.printStackTrace();;
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static Image makeBlackAndWhitePng(PdfImageObject image) throws IOException, DocumentException {
        BufferedImage bi = image.getBufferedImage();
        BufferedImage newBi = new BufferedImage(bi.getWidth(), bi.getHeight(), BufferedImage.TYPE_USHORT_GRAY);
        newBi.getGraphics().drawImage(bi, 0, 0, null);
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        ImageIO.write(newBi, "png", baos);
        return Image.getInstance(baos.toByteArray());
    }

    /**
     * @see com.itextpdf.text.pdf.parser.RenderListener#renderText(
     *com.itextpdf.text.pdf.parser.TextRenderInfo)
     */
    public void renderText(TextRenderInfo renderInfo) {
    }
}

And code around loading the pages以及加载页面的代码

 public static void readImages(final PdfReader reader, final File filex) throws IOException {
        for (int i = 0; i < reader.getXrefSize(); i++) {
            PdfObject pdfobj = reader.getPdfObject(i);
            if (pdfobj == null || !pdfobj.isStream()) {
                continue;
            }
            PdfStream stream = (PdfStream) pdfobj;
            PdfObject pdfsubtype = stream.get(PdfName.SUBTYPE);
            if (pdfsubtype != null && pdfsubtype.toString().equals(PdfName.IMAGE.toString())) {
                byte[] img = PdfReader.getStreamBytesRaw((PRStream) stream);
                FileOutputStream out = new FileOutputStream(new File(filex.getParentFile(), String.format("%1$05d", i) + ".jpg"));
                out.write(img);
                out.flush();
                out.close();
            }
        }
    }

To combine my comments:结合我的评论:

What you see, merely is the soft mask of the image which contains transparency information, white = opaque, black = transparent.你所看到的,仅仅是图像的软蒙版,其中包含透明度信息,白色 = 不透明,黑色 = 透明。 The base image actually is all black but only where the mask indicates opaque, that image black is drawn.基本图像实际上是全黑的,但只有在遮罩指示不透明的情况下,才会绘制黑色图像。 Thus it looks like reversed.因此它看起来像是颠倒的。

You can use image manipulation libraries to invert a bitmap.您可以使用图像处理库来反转 bitmap。 Simply googl'ing for "imageio invert image" returns this , this , and numerous other interesting matches.只需谷歌搜索“imageio invert image”即可返回thisthis和许多其他有趣的匹配项。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM