Java BufferedImage到PNG格式的Base64字符串

我试图将屏幕截图输出作为base64编码的字符串,但没有得到很远。 到目前为止我的代码使用的是Base64库( http://iharder.sourceforge.net/current/java/base64/ ):

Robot robot = new Robot(); Rectangle r = new Rectangle( Toolkit.getDefaultToolkit().getScreenSize() ); BufferedImage bi = robot.createScreenCapture(r); ByteArrayOutputStream os = new ByteArrayOutputStream(); OutputStream b64 = new Base64.OutputStream(os); ImageIO.write(bi, "png", os); ByteArrayOutputStream out = new ByteArrayOutputStream(); out.writeTo(b64); String result = out.toString("UTF-8"); 

每次我运行它,“结果”总是一个空字符串,但我不明白为什么。 有任何想法吗?

注意:我不想将png写入磁盘上的文件。

我遵循了xehpuk的回答,但是在某些浏览器中通过数据url(Chrome和Firefox,Safari似乎渲染它们很好)时,某些图像的最后几行像素丢失了。 我怀疑这是因为浏览器最好解释数据,但最后几个字节的数据丢失了,所以它显示了它的function。

输出流的包装似乎是导致此问题的原因。 Base64.wrap(OutputStream os)的文档解释了:

建议在使用后立即关闭返回的输出流,在此期间它会将所有可能的剩余字节刷新到底层输出流。

因此,根据数据的长度,最后几个字节可能不会从流中刷新,因为没有调用close() 。 我的解决方案是不打扰包装流并直接编码流:

 public static String imgToBase64String(final RenderedImage img, final String formatName) { final ByteArrayOutputStream os = new ByteArrayOutputStream(); try { ImageIO.write(img, formatName, os); return Base64.getEncoder().encodeToString(os.toByteArray()); } catch (final IOException ioe) { throw new UncheckedIOException(ioe); } } 

这解决了在浏览器中呈现时丢失的像素行的问题。

以下陈述的工作方向错误:

 out.writeTo(b64); 

它用out的空字节数组覆盖Base 64数据。

无论如何, out什么目的? 我认为你不需要它。

更新:

并且您将图像直接写入os而不是通过Base 64编码器写入。

以下代码应该工作:

 ... ByteArrayOutputStream os = new ByteArrayOutputStream(); OutputStream b64 = new Base64.OutputStream(os); ImageIO.write(bi, "png", b64); String result = os.toString("UTF-8"); 

使用Java 8对图像进行Base64编码和解码:

 public static String imgToBase64String(final RenderedImage img, final String formatName) { final ByteArrayOutputStream os = new ByteArrayOutputStream(); try { ImageIO.write(img, formatName, Base64.getEncoder().wrap(os)); return os.toString(StandardCharsets.ISO_8859_1.name()); } catch (final IOException ioe) { throw new UncheckedIOException(ioe); } } public static BufferedImage base64StringToImg(final String base64String) { try { return ImageIO.read(new ByteArrayInputStream(Base64.getDecoder().decode(base64String))); } catch (final IOException ioe) { throw new UncheckedIOException(ioe); } } 

像这样使用截图方案:

 final Robot robot = new Robot(); final Rectangle r = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize()); final BufferedImage bi = robot.createScreenCapture(r); final String base64String = imgToBase64String(bi, "png"); 

这对我有用:

将图像编码为Base64字符串

 public static String encodeToString(BufferedImage image, String type) { String imageString = null; ByteArrayOutputStream bos = new ByteArrayOutputStream(); try { ImageIO.write(image, type, bos); byte[] imageBytes = bos.toByteArray(); Base64.Encoder encoder = Base64.getEncoder(); imageString = encoder.encodeToString(imageBytes); bos.close(); } catch (IOException e) { e.printStackTrace(); } return imageString; } 

将Base64字符串解码为图像

 public static BufferedImage decodeToImage(String imageString) { BufferedImage image = null; byte[] imageByte; try { Base64.Decoder decoder = Base64.getDecoder(); imageByte = decoder.decode(imageString); ByteArrayInputStream bis = new ByteArrayInputStream(imageByte); image = ImageIO.read(bis); bis.close(); } catch (Exception e) { e.printStackTrace(); } return image; }