• We’re currently investigating an issue related to the forum theme and styling that is impacting page layout and visual formatting. The problem has been identified, and we are actively working on a resolution. There is no impact to user data or functionality, this is strictly a front-end display issue. We’ll post an update once the fix has been deployed. Thanks for your patience while we get this sorted.

How to get color from bitmap? (C++)

h4ever

Member
Hi,
It is from MSDN example of locking bitmap, where this code is shown. They read pixels and detects the color or set it. However I dont understand why the color is only simple value like 0-255. I would expect RGB with three values : Red, Green, Blue. So it is not clear to me how can I get the value which I looks for. For example I would want to look for color in hex color="aaff08" ... So how should I convert it and which function to use to get the correct value in RGB. It contains no alpha channel. (I am beginner in C++)


http://paste.ofcode.org/ntpebmjHEBYWdvzeX4H25p
line 39-40

Code:
for ( int counter = 8; counter < rgbValues->Length; counter += 9 )
rgbValues[ counter ] = 255;
This is the code they use, and here the rgbValues with single integer is quite strange to me.
 
A single integer is four bytes, so it is large enough to hold the r, g, b, and alpha channels. As to why they are setting it to 255, I am not sure. It could be they want a single color, so writing one byte to an integer should result in... blue I think.
 
It is the datatype. They are copying the values into a byte array. Bytes store the values of 0->255 .

In the MS example (I'm guessing you are referring to this one) They shift by 3 bytes at a time, one byte for each color. In memory, the layout would look like this.

BGRBGRBGRBGRBGR (windows is backwards from the rest of the world).

So the index into this array would look something like this

Code:
 B   G   R   B   G   R ...
 ^   ^   ^   ^   ^   ^ ...
[0] [1] [2] [3] [4] [5]...
 
> // Set every ninth value to 255.
> for ( int counter = 8; counter < rgbValues->Length; counter += 9 )

They are leaving most bytes 0, so the color is ( 0, 0, 255) or b=0, g=0, r=ff

For a different color you would do something like this (C++)
Code:
int r, g, b;
r = 128; g = 128; b = 255;
for ( int counter = 0; counter < rgbValues->Length; counter += 3 ) // 3 NOT 9
 [ counter  +0 ] = b ;
 [ counter  +1 ] = g ;
 [ counter  +2 ] = r ;
 
It is the datatype. They are copying the values into a byte array. Bytes store the values of 0->255 .

In the MS example (I'm guessing you are referring to this one) They shift by 3 bytes at a time, one byte for each color. In memory, the layout would look like this.

Oh yes, you're right. I have changed the code a bit, so it produces different color than in the MSDN example. Thanks for your explanation. Should the upper limit for the loop be image_width*image_height*3 ? As I noticed, in the example there is rgbValues->Length equal to (pImage->Width*pImage->Height). That's also strange to me.

e8re4y.jpg


As a result in my image 800*600 the rgbValues lentgh is 1920000

Edit
Well - one more test I did. I set the width of locked area of bitmap to 5, however the stride is still 3200. So I thought that if I change the with to 5 the stride should be 5. MSDN says "The stride is the width of a single row of pixels (a scan line), rounded up to a four-byte boundary. " So the stride is 4 byte meaning is holds alpha, green, blue and red component, every one byte. However when the bitmap is locked to width 5 so why stride is not 5*4=20 ?
 
Last edited:
No, the total length for the entire row is rounded up to a total length that is a multiple of 4. Each pixel size is not rounded up from 3 to 4.

So 5 pixels = 5 * 3 (r,g,b) = 15, rounded up to a multiple of 4 = 16.

row length = x pixels * 3 ; // 24 bit image
while (row length % 4) != 0
row length ++ ;
 
Back
Top