• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.

Archived

This topic is now archived and is closed to further replies.

Ake

16 bit color

10 posts in this topic

Everybody new to DirectX seems to have this problem, here is what I use to extract or create the rgb values. Basicly, just add it at the top of your code and your good to go.

#define RED(p) ( p >> pRed ) // Extracts Red Component
#define GREEN(p) ((p & mGreen) >> pGreen) // Extracts Green Component
#define BLUE(p) ( p & mBlue ) // Extracts Blue Component
#define RGB16(r, g, b) ((r << pRed ) | (g << pGreen) | b) // create RGB value

0

Share this post


Link to post
Share on other sites
Thanks, but do you have any nice values for
masks and shift, or do you get them from DX?

0

Share this post


Link to post
Share on other sites
A good way to do it is to save your DDPIXELFORMAT masks dwRBitMask,
dwGBitMask, dwBBitMask (from GetPixelFormat) in variables, so you
can buildup a macro that will work great with everything.

But what GetPixelFormat does not explicitly return is the number of
bits you need to shift each RGB component to make your 16-bit value.

Well, the DD docs has a neat function that does this for you:

code:

WORD
GetNumberOfBits(DWORD dwMask) {

WORD wBits = 0;

while(dwMask) {
dwMask = dwMask & (dwMask - 1);
wBits++;
}
return wBits;
}


What this does is count the number of '1' bits in a mask. So,
a blue mask of 0x001F will return a value of 5 (only 5 bits are set)

Save these mask bit counts in variables too. These are needed to
finally determine how many bits you need to shift each RGB component.

It'll look something like this:
------
DDPIXELFORMAT ddpf;
ZeroMemory( &ddpf, sizeof(DDPIXELFORMAT) );
ddpf.dwSize = sizeof(DDPIXELFORMAT);

surface->GetPixelFormat(&ddpf);

red_mask = ddpf.dwRBitMask;
green_mask = ddpf.dwGBitMask;
blue_mask = ddpf.dwBBitMask;

red_bits = GetNumberOfBits(red_mask);
green_bits = GetNumberOfBits(green_mask);
blue_bits = GetNumberOfBits(blue_mask);

blue_shift = 0;
green_shift = blue_bits;
red_shift = blue_bits + green_bits;

------

That's all you need to do! Now you can reference these variables in
a 16bit macro or function and you are good to go. So use the masks
to extract RGB components, and use the shifts to make a 16-bit color
value.

Don't use constant values directly, it will only make your code less
compatible.

Reaver

[This message has been edited by Reaver (edited November 01, 1999).]

0

Share this post


Link to post
Share on other sites
To answer your second quesion, Ake, you need to scale R, G and B to get them in the 0-255 range. The simplest thing is to do another shift:

B = (col & 0x1F) << 3;
G = ((col >> 5) & 0x3F) << 2;
R = ((col >> 11) & 0x1F) << 3;

This doesn't quite work though! It results in these ranges.

R = 0-248
G = 0-252
B = 0-248

Close enough!

0

Share this post


Link to post
Share on other sites
OK, I'm not really happy yet. I'll give you the code first:
USHORT GetColor16()
{
return (USHORT) (( m_iR << m_wRShift ) | ( m_iG << m_wGShift ) | m_iB );
}

void GetRGB()
{
m_iB = ( col & m_dwBMask ) << 3;
m_iG = ( (col & m_dwGMask ) >> m_wGShift ) << 2;
m_iR = ( (col & m_dwRMask ) >> m_wRShift ) << 3;
}

void SetPixelFormat( LPDIRECTSURFACE4 bla )
{
m_dwRMask = ddpixel.dwRBitMask;
m_dwGMask = ddpixel.dwGBitMask;
m_dwBMask = ddpixel.dwBBitMask;

WORD wRBits = GetNumberOfBits( m_dwRMask );
WORD wGBits = GetNumberOfBits( m_dwGMask );
WORD wBBits = GetNumberOfBits( m_dwBMask );

m_wRShift = wBBits + wGBits;
m_wGShift = wBBits;
m_wBShift = 0;
}

Not this looks ok to everyone, then let's try it.
wSurf2[ y * 256 + x] = GetColor16( 255, 0, 255 );
GetRGB( wSurf2[ y * 256 + x] );
Now it should be, R = 248, G = 0, B = 248. But it's not.
It's R = 248, G = 28, B = 248. Hmmmm. I remove the << 2
and I found that G gets the value 7 when it should be 0.
Pretty much the same thing happened when I wrote (0,255,255)
it read (56,124,248). (124 can be fixed by shifting the G by
3 instead). Any ideas why this happens.

And Reaver, would the Mask and shift be correct in 24 or 32
bpp mode too, using the GetNumberOfBits thingie?

0

Share this post


Link to post
Share on other sites
If you are passing 24-bit values (0 to 255), You need to convert them to
16-bit values (0 to 31) before you combine them together. Try this for
your GetColor16() function:

code:

WORD
GetColor16(BYTE r, BYTE g, BYTE b) {
return (WORD)( (((r>>(8-wRBits))&31) << m_wRShift) | (((g>>(8-wGBits))&31) << m_wGShift) | ((b>>(8-wBBits))&31) );
}


I hope that came out right.

Hmmm, or try this:

code:

WORD
GetColor16(BYTE r, BYTE g, BYTE b) {
return (WORD)( ((r>>(8-wRBits)) << m_wRShift) | ((g>>(8-wGBits)) << m_wGShift) | (b>>(8-wBBits)) );
}

I don't know if that will do much visually, but I just remembered I put in
the &31 part because I want all color to clamp to 555, even though it might be 565.
Or you could try substituting &63 for the &31 part in the green component.
I never tried this, it might not work right.

If that doesn't work, make sure you have everything setup correctly, write
out your masks values, shift values, and bit count values. Make sure it is
all correct for 16-bit 565.

And, I think you don't need to use GetNumberOfBits or figure out
how bits to shift with 24-bit, because it usually only has one format.
At least I hope so. Always 888 for 24-bit. I think 32-bit can be
2-10-10-10 or 8-8-8-8. I never tested it with anything else than 16-bit,
but I would guess it would still give you the same results.

Reaver

[This message has been edited by Reaver (edited November 01, 1999).]

0

Share this post


Link to post
Share on other sites
The thing is though, if you want to make a 16bit engine you have to have RGB color ranges from 0-31. You can't have 0-255.

For 555 format
R = 32 shades
G = 32 shades
B = 32 shades
Total 32768 colors

For 565 format
R = 32 shades
G = 64 shades
B = 32 shades
Total 65536 colors

I dont think that our eyes can even notice all thoses shades.

#define RGB16(r, g, b) ((r << RedPos) | (g << GreenPos) | b)
When you call this macro with 255,255,255 it truncates them down to 31,31,31

So then when you plot lets say a pure red pixel with 255 and you call this macro to extract the red color
#define RED(p)(p >> RedPos)

The value you will get is 31.

So if you make a 16 bit engine you have to stick with 31 shades. Ifnot you will have to go up to 24bit mode or 32 bit mode but those are still to frigin slow.

0

Share this post


Link to post
Share on other sites
You'd be surprised what the eye can distinguish. It can reliably discern all the 16M colors of 24bit color modes, because all it really does it discern the 256 levels of each RGB. Even more impressive is that it can distinguish about 50M colors on a reflective surface such as paper!

Rock

0

Share this post


Link to post
Share on other sites
Hi everybody,

How do I extract each color components of a 16bit 565 color?
I tried this:
B = col & 0x1F;
G = (col >> 5) & 0x3F;
R = (col >> 11) & 0x1F;
But it didn't work very well, color values are just between 0-31, I want them 0-255.
There must be some way, please help.

TIA, Tobias

0

Share this post


Link to post
Share on other sites
Anyways, the point is if you are going 16bit you will always come back to 32 shades of each color no matter what you do even if you convert to 255. So if you really want more colors you have no choice but to go 24 or 32bit. But since both modes you need to work in DWORD alignement cause there is not 3 byte
alignement, might as well go full 32bit. But stick to 16 cause it's way faster then 24 and 32 and still looks good

[This message has been edited by voodoo (edited November 02, 1999).]

[This message has been edited by voodoo (edited November 03, 1999).]

0

Share this post


Link to post
Share on other sites