Bit Plane Slicing and Compression

Bit Plane Slicing and Compression

·

3 min read

Bit plane is image compression algorithm, which I find pretty interesting. Let's see how it works.

We know that a image contains pixels. Each pixels contains rgb(or rgba) values. Each value is a unsigned int, with value from 0-255. If the image is a grayscale image, then its rgb values are the same, so this gray image can be seen as a 2d array of values. If the gray image's size is 3 * 2, then can be expressed in below.

17  28  125
44  9   211

Let's express this image in 8-bits.

00010001  00011100  01111101
00101100  00001001  11010011

Each value can be expressed in 8 bits. From left to right, the leftest bit is called most significant bit(MSB), then rightest bit is called the least significant bit(LSB). Take the first value (17) as an example.

 0      0      0      1      0      0      0      1
MSB   bit-7  bit-6  bit-5  bit-4  bit-3  bit-2   LSB

So why called MSB and LSB? Because, if we change the value of the most significant bit, then the whole value will be changed significantly. If we change the value of the least significant bit, then the whole value will be changed just a little(by 1). We will see this change later.

A bit plane a image with values which just take specific bit position of the original value. For example, if we take the least significant bit of each value, and use them as a new image, then this is a bit plane. Same logic, we can take bit-2 of each value and use them a new image too, then this is another bit plane. So because each value has 8 bit, we can create 8 bit plane. This process is called bit plane slicing.

Let's see the code how to do the bit plane slicing.

<!DOCTYPE html>
<html lang="en">

    <head>
        <meta charset="UTF-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>Document</title>
    </head>

    <body>
        <img src="./download.jpg" alt="" onload="start()" style="display: none;">

        <script>
            function createCanvas(width, height) {
                const c = document.createElement("canvas");
                c.width = width;
                c.height = height;
                document.body.appendChild(c);
                const ctx = c.getContext("2d");
                return ctx;
            }

            function createPlane(width, height, originalData, planeNum) {
                const ctx = createCanvas(width, height);
                const imgData = ctx.getImageData(0, 0, width, height);
                for (let i = 0; i < imgData.data.length; i++) {
                    if ((i + 1) % 4 === 0) {
                        imgData.data[i] = originalData.data[i];
                    } else {
                        imgData.data[i] = (originalData.data[i] & (1 << planeNum)) * 255;
                    }
                }
                ctx.putImageData(imgData, 0, 0);
            }

            function start() {
                const img = document.querySelector("img");
                const width = img.width;
                const height = img.height;

                const originalCtx = createCanvas(width, height);
                originalCtx.drawImage(img, 0, 0);
                const originalData = originalCtx.getImageData(0, 0, width, height);

                // gray
                for (let i = 0; i < originalData.data.length; i += 4) {
                    const v = (originalData.data[i] + originalData.data[i + 1] + originalData.data[i + 2]) / 3;
                    originalData.data[i] = v;
                    originalData.data[i + 1] = v;
                    originalData.data[i + 2] = v;
                }
                originalCtx.putImageData(originalData, 0, 0);

                createPlane(width, height, originalData, 0);
                createPlane(width, height, originalData, 1);
                createPlane(width, height, originalData, 2);
                createPlane(width, height, originalData, 3);
                createPlane(width, height, originalData, 4);
                createPlane(width, height, originalData, 5);
                createPlane(width, height, originalData, 6);
                createPlane(width, height, originalData, 7);
            }
        </script>
    </body>

</html>

If you run the code above, you should see an image like below. The first image is the original gray image. And later is the bit plane image from LSB to MSB.

Screen Shot 0004-07-09 at 15.56.39.png

As you can see from the image, the MSB bit plane contains the most information, and the LSB bit plane contains the least information.

Last thing, the bit plane compression is just store the information of the MSB of each pixels. When in compression, each MSB stored one by one in bits, and when in decompression, MSB will be restored back to pixels values.