2013-09-02 2 views
11

У меня есть URL-адрес данных из файла изображения и должен передать его другой функции. По этому пути от URL-адреса данных к BufferedImage он должен быть байтом.Преобразование URL-адреса данных в BufferedImage

мой подход был следующим:

String dataUrl; 
byte[] imageData = dataUrl.getBytes(); 

// pass the byteArray along the path 

// create BufferedImage from byteArray 
BufferedImage inputImage = ImageIO.read(new ByteArrayInputStream(imageData)); 

// If the picture is null, then throw an unsupported image exception. 
if (inputImage == null) { 
    throw new UnknownImageFormatException(); 
} 

Проблема заключается в том, что всегда бросает UnknownImageFormatException Exception, что означает inputImage имеет нулевое значение, что означает, то ImageIO.read не признают IMAGETYPE.

Я использовал ImageIO.getReaderFormatNames(), чтобы получить поддерживаемые имена файлов и получил следующий список:

Supported Formats: 
jpg, BMP, bmp, JPG, jpeg, wbmp, png, JPEG, PNG, WBMP, GIF, gif 

The dataURLs я пытаюсь передать Походят: data:image/png;base64,... или data:image/jpg;base64,...

Насколько Я понимаю, что они находятся в поддерживаемом списке файлов и поэтому должны быть распознаны.

Что еще может привести к тому, что inputImage будет пустым в этом случае? И еще интереснее, как я могу его решить?

+3

Вам необходимо декодировать строку из base64 обратно в двоичный формат, который может считывать ImageIO, или, если у вас есть объект URL, возможно, передать его непосредственно в ImageIO – MadProgrammer

+2

. В дополнение к совету @MadProgrammer вы можете использовать [ DatatypeConverter'] (http://docs.oracle.com/javase/7/docs/api/javax/xml/bind/DatatypeConverter.html#method_summary), чтобы преобразовать базовую строку 64 в 'byte []'. –

ответ

16

Как уже отмечалось, данные изображения кодируются Base64. Чтобы получить двоичные данные, вам необходимо разбить заголовки типов/кодировок, а затем декодировать содержимое Base64 на двоичные данные.

String encodingPrefix = "base64,"; 
int contentStartIndex = dataUrl.indexOf(encodingPrefix) + encodingPrefix.length(); 
byte[] imageData = Base64.decodeBase64(dataUrl.substring(contentStartIndex)); 

Я использую org.apache.commons.codec.binary.Base64 от апачей общего кодека, другие Base64 декодеры должны работать так же хорошо.

+5

Начиная с Java 8, в базовом JDK есть кодировщик/декодер Base64: http://download.java.net/jdk8/docs/api/java/util/Base64.html – Jules

3

только одна проблема с RFC2397 строки является спецификация со всем, прежде чем данные, но data: и , опционально:

data:[<mediatype>][;base64],<data> 

Так чисто Java 8 решение приходится это было бы:

final int dataStartIndex = dataUrl.indexOf(",") + 1; 
final String data = dataUrl.substring(dataStartIndex); 
byte[] decoded = java.util.Base64.getDecoder().decode(data); 

Конечно dataStartIndex должен быть проверен.

Смежные вопросы