How can I convert the image binary code from an API call to a data URI in Javascript?

The Google API that I use only transmits images as binary data.

I absolutely don't know how to put this in a data URI to display it, thanks for any help!

The call I'm talking about is this API call .

As you can see, it says:

The server returns bytes of the photo.

To call (this is an extension) I use chrome_ex_oauth methods. Maybe I need to add something to the header in order to get real binary data, and not a string, as it happens right now ...

What I need to do is convert the resulting binary to a data URI so that I can display it.


Ok i get this from xhr request

enter image description here

Now I am not very versed in binary materials. Is it somehow encoded binary data that I assume? I tried putting this in btoa and other base64 encoders, everything causes an error. I tried to redefine MimeType with different things, and the “response” changed in some strange way, but it doesn’t accept data.

So now I have this code:

var nxhr = new XMLHttpRequest(); nxhr.onreadystatechange = function (data) { if (nxhr.readyState == 4) { console.log(nxhr); } }; nxhr.open(method, url, true); nxhr.setRequestHeader('GData-Version', '3.0'); nxhr.setRequestHeader('Authorization', oauth.getAuthorizationHeader(url, method, params)); nxhr.send('Data to send'); 

Does anyone else have an idea how to get this obscure answer for me in uri data ???

Thanks for any help

+7
source share
4 answers

Ok, I found a solution ...

First of all, the request should override the returend type as x-user

 xhr.overrideMimeType('text\/plain; charset=x-user-defined'); 

After that, the data is not touched by the browser.

Use the following Base64 encoder

 Base64 = { // private property _keyStr: "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=", encodeBinary: function (input) { var output = ""; var bytebuffer; var encodedCharIndexes = new Array(4); var inx = 0; var paddingBytes = 0; while (inx < input.length) { // Fill byte buffer array bytebuffer = new Array(3); for (jnx = 0; jnx < bytebuffer.length; jnx++) if (inx < input.length) bytebuffer[jnx] = input.charCodeAt(inx++) & 0xff; // throw away high-order byte, as documented at: https://developer.mozilla.org/En/Using_XMLHttpRequest#Handling_binary_data else bytebuffer[jnx] = 0; // Get each encoded character, 6 bits at a time // index 1: first 6 bits encodedCharIndexes[0] = bytebuffer[0] >> 2; // index 2: second 6 bits (2 least significant bits from input byte 1 + 4 most significant bits from byte 2) encodedCharIndexes[1] = ((bytebuffer[0] & 0x3) << 4) | (bytebuffer[1] >> 4); // index 3: third 6 bits (4 least significant bits from input byte 2 + 2 most significant bits from byte 3) encodedCharIndexes[2] = ((bytebuffer[1] & 0x0f) << 2) | (bytebuffer[2] >> 6); // index 3: forth 6 bits (6 least significant bits from input byte 3) encodedCharIndexes[3] = bytebuffer[2] & 0x3f; // Determine whether padding happened, and adjust accordingly paddingBytes = inx - (input.length - 1); switch (paddingBytes) { case 2: // Set last 2 characters to padding char encodedCharIndexes[3] = 64; encodedCharIndexes[2] = 64; break; case 1: // Set last character to padding char encodedCharIndexes[3] = 64; break; default: break; // No padding - proceed } // Now we will grab each appropriate character out of our keystring // based on our index array and append it to the output string for (jnx = 0; jnx < encodedCharIndexes.length; jnx++) output += this._keyStr.charAt(encodedCharIndexes[jnx]); } return output; } }; 

There is magical stuff posted by mozilla that didn't let me encode the stuff correctly.

 bytebuffer[jnx] = input.charCodeAt(inx++) & 0xff 

The last code would look like this ...

 oauth.authorize(function () { var method = "GET", params = {}, url = photo.href; var nxhr = new XMLHttpRequest(); nxhr.onreadystatechange = function (data) { if (nxhr.readyState == 4) { console.log("<img src='data:image/*;base64," + Base64.encodeBinary(nxhr.response) + "' />"); } }; nxhr.open(method, url, true); nxhr.setRequestHeader('GData-Version', '3.0'); nxhr.setRequestHeader('Authorization', oauth.getAuthorizationHeader(url, method, params)); nxhr.overrideMimeType('text\/plain; charset=x-user-defined'); }); 

PS If you put "data: image / *" in the browser window directly, it will download the file and will not be able to open it. But if you put it directly in img src, it works great!

+5
source

After doing some tests, here is my answer:

To simply display an image using the <img> , you must first encode the binary result with Base64. You can do this in two ways:

  • Using Javascript: Use a Base64 encoder function such as this . After encoding the binary data of the result, you can display the image using the <img> as follows: <img src="data:image/*;base64,[BASE64 ENCODED BINARY]" /> . You must replace [BASE64 ENCODED BINARY] with the actual encoded binary image. I assume that you already know how to change the attributes of an HTML element using Javascript, it's pretty easy to put a coded binary in the src attribute of the <img> .

  • Using PHP (my personal preferences) . After sending the GET API request, it will return you a binary file. Just use the PHP function base64_encode() .

    <img src="data:image/*;base64,<?php echo base64_encode($result); ?>" />

Where the $result variable is what you get from the API call. You can use the PHP cURL library.

Hope this helps.

+16
source

If you are using the URI data: I suppose you do not need older browsers. In this case, use btoa() as suggested in How can you encode a Base64 string in JavaScript? and return to the alternative mentioned in the second answer . Then the URI data: is simple:

 data:image/*;base64,<the btoa output> 
+2
source

All other solutions are out of date. No Base64. Check my answer for getting BLOB data from an XHR request .

+1
source

All Articles