Multi monitor XP, different color depths lead to greyscale variation

We have written a display driver for an 8 bit greyscale device.
In a multimon system for XP, our display is used along with a display adapter that has 24 bit color. When an icon is dragged over the greyscale monitor, the background color(greyscale) changes. This new color is always a number of the form (n%8) = 4, nearest to the original color/greyscale.

How can we handle the translation of olors from 24 bit depth to 8 bit in the display driver?
rajatkAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

KurtVonCommented:
Ugh, ugly problem I faced a while back.  The short answer is you can't directly.

It sounds like the same problem I had when I tried to draw in the screen DC.  The problem is that the screen DC is always the color depth of the primary monitor, and all other monitors are drawn using a very inneficient (I'd call it buggy) built in system method before being re-drawn to the proper graphics driver.

The solution I came up with was to decouple the drawing routine from the draw message. When it is a different function that takes a DC as a parameter it makes this easy (so the separation is the hard part).  Then you write another function like this:

BOOL CALLBACK MyDrawingEnumProc (HMONITOR hMonitor, HDC hDC,
                              LPRECT lpRect, LPARAM dwData)
{
   ENUM_CONTEXT     *pContext = (ENUM_CONTEXT *)dwData;
   HWND             hWnd = pContext->hWnd;

   // Make sure a zero width clip rect is never used.
   if ((lpRect->left == 0) && (lpRect->right == 0))
      return TRUE;

   // Call the original paint proc, alter the parameters which were passed in the struct
   // to match whatever parameters your paint function needed.
   MyPaintProc(hWnd, hDC, lpRect, FALSE, pContext->param1, pContext->param2, ...);

   // Before we return, see if the window was invalidated
   // in the middle of the paint, and if so remind Windows
   // to redraw the area that it caused us to miss.
   RECT rcClip;
   GetClipBox (hDC, &rcClip);
   if ((rcClip.left == 0) && (rcClip.right == 0))
   {
      InvalidateRect (hWnd, lpRect, FALSE);
   }

   return (TRUE);
}
 
Now you can call the montior enumerations from your normal paint handler like this:

   // You probably want to compute this bool only once and make it static (or global)
   bool bHasMultimonitorSupport;
   OSVERSIONINFO version;
   version.dwOSVersionInfoSize = sizeof(version);
   GetVersionEx (&version);
   if ((version.dwMajorVersion < 4) ||
       ((version.dwMajorVersion == 4) && (version.dwMinorVersion == 0)))
       bHasMultimonitorSupport = false;
   else
      bHasMultimonitorSupport = true;
   if (bHasMultimonitorSupport)
      EnumDisplayMonitors (hDC, rcPaint, MyDrawingEnumProc, (long)&EnumContext);
   else
       MyDrawingEnumProc((HMONITOR)1, hDC, rcPaint, (LPARAM)&EnumContext);

By calling the drawing routine only for the DC specific to the monitor you are drawing to, Windows doesn't do the "double translation" that causes the drawing inaccuracies.

Hope this helps.
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
KurtVonCommented:
I assume rajatk will correct me if I'm wrong, but the lack of a response suggests either this was a solution or a decision was made that the process was too difficult to be worth it.
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Programming

From novice to tech pro — start learning today.