Timo Willemsen
Timo Willemsen

Reputation: 8857

Javascript dealing with BinaryString

I'm currently using the HTML5 File Api to read some files.

var reader = new FileReader();
reader.onload = function(event){
 var result =  event.target.result;
}
reader.readAsBinaryString(...)

Now... the result is a large (50k+bytes) file. And I want to do some calculations with it. For example checking it's first few bytes, drawing the last 20k bytes as pixels on a canvas etc...

What would be the most efficient way to parse this string...

Upvotes: 0

Views: 992

Answers (1)

Delta
Delta

Reputation: 4328

Ok, let me walk you through the part of drawing the last 20K Bytes as pixels in canvas. (Though I am not sure about whether the browser can handle on this without slowing down or breaking script execution)

First of all, to get the start position of the lattest 20K bytes do the following:

var pixelsOffset = result.length - 20480

Since your binary data is in string format and each ASCII character takes just 1 byte, the length of the string is the same as the number of bytes, and 20KBytes is equal to 20,480 bytes.

So now that you know where your pixels information starts, you need to loop through the bytes until you reach the end of the string while drawing a pixel to the canvas.

var x = 0;
var y = 0;
var width = 300;

for(var I = pixelsOffset; I < result.length; I += 4)
{
    var R = result.charCodeAt(I);
    var G = result.charCodeAt(I + 1);
    var B = result.charCodeAt(I + 2);
    var A = result.charCodeAt(I + 3);

    var colorString = "rgba(" + R + ", " + G + ", " + B + ", " + A + ")";

    canvasContext.fillStyle = colorString;

    canvasContext.fillRect(x, y, 1, 1);

    x++;

    if(x == width)
    {
        x = 0;
        y++;
    }
}

What I did here was firstly to create variables where I can store the current pixel's position (x,y) and the width of the image.

Then a FOR loop where I jump 4 bytes each time, that is, of course, because each pixel takes one byte for it's Red value, one byte for it's Geen value, another byte for it's Blue value and one byte for it's Alpha value. Resulting in 4 bytes per pixel.

When you read a binary file, JavaScript transforms it into a string, but since RGBA values are integers (from 0 to 255) and not characters, we need to retrieve back the numeric value of the byte which was converted into a char. To do this we only need to get the charCode of the character so we have our original integer.

After we have our RGBA values we need to put it into a string in the format that is accepted by the canvas, set it as the current fillStyle and then draw a 1x1 rect. Once we get to the last pixel of the row, we increment y to get to the next row and set x to zero so we start from the beginning of the row.

Upvotes: 1

Related Questions