Get jpeg encoded in base64 string into Mat in Java.
I am trying to do a simple face detection example in Java, similar to what was done in the Introduction to Java Development article. When I load a jpeg image using Highgui.imread(path), everything works fine. But the images I am using come from an API that returns base64 encoded jpegs. My code for handling the base64 strings looks like this:
CascadeClassifier classifier = new CascadeClassifier(getClass().getResource("/lbpcascade_frontalface.xml").getPath());
// img is a String
byte[] bytes = parseBase64Binary(img); // This function is found in javax.xml.bind.DatatypeConverter
Mat image = new Mat;
image.put(0, 0, bytes);
MatOfRect faceDetections = new MatOfRect();
classifier.detectMultiScale(image, faceDetections);
This does not work. I tested it by encoding an image in which a face was successfully detected when loaded directly:
DataBufferByte byteBuffer = (DataBufferByte) ImageIO.read(new File(path_to_file_that_worked_before)).getRaster.getDataBuffer();
String img = printBase64Binary(byteBuffer.getData);
No faces are detected. Any idea what I am doing wrong?
parseBase64Binary probably does not return pixels, but a whole image. headers, compression and all.
you'll have to imdecode the bytes[] to make a Mat
http://docs.opencv.org/java/org/opencv/highgui/Highgui.html#imdecode(org.opencv.core.Mat,%20int)
@berak Can you elaborate? I had seen that function before, but it takes a Mat as input.
Mat ocvImg = Highgui.imdecode(new MatOfByte(bytes), Highgui.IMREAD_UNCHANGED);
@berak The results didn't change. However, I noticed that when I tried writing out the image using
Highgui.imwrite, the image is empty. This might explain why no faces are detected. Any thoughts on why the image turns up empty? The byte array that I am using to create the Mat is not empty.yes you're right. empty image -- no faces detected.
i'm a bit out of ideas. but it was a jpg, no ?
if the byte array does not start with ff d8 and end with ff d9, then it's corrupted.
you'er sure, parseBase64Binary is doing the right thing there ? (is it the right func to use even ?)