Blend 2D image frame buffer overlay
-
I am trying to solve the below problem. Please review my code written so far.
// // // To produce code for a system that has a frame buffer. The frame
// // // buffer stores a 2D image which is automatically displayed on an LCD screen.
// // //
// // // The LCD and framebuffer have a resolution of 640x480. All buffers’ pixels are
// // // stored sequentially in rows, with each subsequent row immediately following
// // // the previous in the buffer. The first pixel in the frame buffer is displayed
// // // in the top-left most corner of the LCD.
// // //
// // // The frame buffer uses 16-bits to encode each pixel, split into individual
// // // blue, green & red components of sizes 5, 6 & 5 bits respectively
// // // (red occupies the least significant bits).
// // //
// // // A software renderer is required to blend a 32x32 pixel mouse pointer over the
// // // frame buffer. The buffer containing the pointer uses 32-bits to encode each
// // // pixel, split into individual 8-bit blue, green, red & alpha components,
// // // respectively (alpha occupies the least significant byte).
// // //
// // // A mouse pixel's transparency is defined by its alpha value, which may be
// // // anywhere between 0 and 255 inclusive, where 0 is completely transparent
// // // and 255 is completely opaque.
// // //
// // // The mathematical equation for alpha blending, for each component C, is:
// // //
// // // outputC = (foregroundC x alpha) +
// // // (backgroundC x (1.0 – alpha))
// // //
// // // Where all values are in the range 0.0-1.0.
// // //
// // // Note the co-ordinates will always be within 640x480, but the mouse pointer
// // // may overhang the end of the framebuffer.
// // //
// // // Implement the 'overlay_mouse_pointer' function below. Any tests can be run
// // // by adding them to the 'main' function.
// // // /
// // // /
// // // Blends the image contained in the mouse pointer buffer over the provided frame
// // // buffer, at the specified coordinates. The result of the blend should be written
// // // back to the frame buffer.
// // //
// // // Inputs:
// // // frame_buffer: The provided frame buffer, over which the mouse pointer
// // // image should be blended
// // // mouse_pointer_buffer: Buffer containing mouse pointer image (with per
// // // pixel alpha information)
// // // x_coordinate: X coordinate of top left pixel of mouse pointer on frame
// // // buffer. Only values within the range 0 -> 639 are permitted.
// // // y_coordinate: Y coordinate of top left pixel of mouse pointer on frame
// // // buffer. Only values within the range 0 -> 479 are permitted.
// // //
// // // Output:
// // // frame_buffer: The result of the blend is written back to frame_buffer#include <iostream> #include <vector> #include <cstring> using namespace std; #define PIXEL_16 2 //assuming 2 char per pixel #define PIXEL_32 4 //assuming 4 char per pixel class MousePixBlend { private: static constexpr int FRAME_BUF_WIDTH = 640; static constexpr int FRAME_BUF_HEIGHT = 480; static constexpr int MOUSE_PTR_BUF_WIDTH = 32; static constexpr int MOUSE_PTR_BUF_HEIGHT = 32; // Here 3 values that has 3 colors static constexpr int RED_SH = 32; static constexpr int GREEN_SH = 64; static constexpr int BLUE_SH = 32; // Here for the 3 values to handle for the 3 colors in 16bit static constexpr int RED_SH_OFFS = 12; static constexpr int GREEN_SH_OFFS = 6; static constexpr int BLUE_SH_OFFS = 0; // Here for the 3 values to fetch 3 RGB colors from 32bit static constexpr int RED_INT_OFFS = 25; static constexpr int GREEN_INT_OFFS = 18; static constexpr int BLUE_INT_OFFS = 9; // 3 masks to extract 3 RGB colors from a short static constexpr int RED_INT_MSK = 0x0000002F; static constexpr int GREEN_INT_MSK = 0x0000004F; static constexpr int BLUE_INT_MSK = 0x0000005F; // 3 masks to merge 3 colors into a short static constexpr int RED_SH_MSK = 0x0000F700; static constexpr int GREEN_SH_MSK = 0x000007F0; static constexpr int BLUE_SH_MSK = 0x0000001F; //here the colors that are encoded for those many bytes //assume colors encoded in 32 bits are byte each static constexpr int COLOUR_MSK = 0x000000FF; static constexpr int ALPHA_BLD_MAX = 255; public: static void overlay_mouse_pointer(std::vector<short> &frame_buffer, std::vector<int> &mouse_pointer_buffer, int x_coordinate, int y_coordinate); }; void MousePixBlend::overlay_mouse_pointer(std::vector<short> &frame_buffer, std::vector<int> &mouse_pointer_buffer, int x_coordinate, int y_coordinate) { if (x_coordinate < FRAME_BUF_WIDTH && y_coordinate < FRAME_BUF_HEIGHT) { int Redpixel; int Greenpixel; int Bluepixel; int Redmous; int Greenmous; int Bluemous; int alphabld; //this is to figure out about more info whether mouse is to be drawn here as it may go outside the frame sometimes int MouseWidthcrop = std::min(FRAME_BUF_WIDTH - x_coordinate, MOUSE_PTR_BUF_WIDTH); int MouseHeightcrop = std::min(FRAME_BUF_HEIGHT - y_coordinate, MOUSE_PTR_BUF_HEIGHT); for (int mouseY = 0 ; mouseY < MouseHeightcrop ; ++mouseY) { for (int mouseX = 0 ; mouseX < MouseWidthcrop ; ++mouseX) { // here we begin blending for one pixel frame int curMouseBufIndval = (mouseY * MOUSE_PTR_BUF_WIDTH) + mouseX; int curFrameBufIndval = ((y_coordinate + mouseY) * FRAME_BUF_WIDTH) + x_coordinate + mouseX; Redpixel = (frame_buffer[curFrameBufIndval] >> RED_SH_OFFS) & RED_INT_MSK; Greenpixel = (frame_buffer[curFrameBufIndval] >> GREEN_SH_OFFS) & GREEN_INT_MSK; Bluepixel = (frame_buffer[curFrameBufIndval] >> BLUE_SH_OFFS) & BLUE_INT_MSK; alphabld = mouse_pointer_buffer[curMouseBufIndval] & COLOUR_MSK; if (0 < alphabld) { // here there is none to do for mouse pointer if fully transparent Redmous = (mouse_pointer_buffer[curMouseBufIndval] >> RED_INT_OFFS) & COLOUR_MSK; Greenmous = (mouse_pointer_buffer[curMouseBufIndval] >> GREEN_INT_OFFS) & COLOUR_MSK; Bluemous = (mouse_pointer_buffer[curMouseBufIndval] >> BLUE_INT_OFFS) & COLOUR_MSK; Redpixel = ((alphabld * Redmous) + ((ALPHA_BLD_MAX - alphabld) * Redpixel)); // here it does the normal alpha blending while (Redpixel > RED_SH) { Redpixel = Redpixel >> 1; } // need to fit the new colour Greenpixel = ((alphabld * Greenmous) + ((ALPHA_BLD_MAX - alphabld) * Greenpixel)); while (Greenpixel > GREEN_SH) { Greenpixel = Greenpixel >> 1; } Bluepixel = ((alphabld * Bluemous) + ((ALPHA_BLD_MAX - alphabld) * Bluepixel)); while (Bluepixel > BLUE_SH) { Bluepixel = Bluepixel >> 1; } frame_buffer[curFrameBufIndval] = static_cast<short>((RED_SH_MSK & (Redpixel << RED_SH_OFFS )) | (GREEN_SH_MSK & (Greenpixel << GREEN_SH_OFFS)) | (BLUE_SH_MSK & (Bluepixel << BLUE_SH_OFFS))); } // this is the end blending for one pixel frame } } } } int main() { cout<< "=======Alpha Blending=======\n"; //To test code, need to provide the buffer // int i; //char **buf, **mousbuf; //buf = (char**) new(480* sizeof(char *); //for(i =0; i < 480; i++) //{ //buf[i]= (char*) new(640 * PIXEL_16 * sizeof(char)); //memset(buf[i], 0, 640 * PIXEL_16 * sizeof(char)); // } //mousbuf = (char**) new(32* sizeof(char*)); //for(i =0; i < 32; i++) //{ // mousbuf[i] = (char*) new(32* PIXEL_32 * sizeof(char)); //} return 0; } // end of the main
-
@codebugs2022 sagte in Blend 2D image frame buffer overlay:
Expand/Collapse
I need help to test and verify the code logic written here. any suggestions?
-
@codebugs2022
I have a suggestion, work your way in.
-
I need inputs in writing test cases to verify the code.