dcsimg
CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 5 of 5

Thread: [GDI] - owner draw: how draw it on gray scale?

  1. #1
    Join Date
    Apr 2009
    Posts
    1,272

    [GDI] - owner draw: how draw it on gray scale?

    these code owner draw a 98/2000 OS style button:
    Code:
    case WM_DRAWITEM:
                {
                    DRAWITEMSTRUCT *test=(DRAWITEMSTRUCT*) lParam;
    
                    //fill the background with button face color
                    FillRect(test->hDC, &test->rcItem,(HBRUSH) GetSysColor(COLOR_BTNFACE));
                    if ( test->itemState & ODS_SELECTED) // If it is pressed
                    {
                        DrawEdge(test->hDC,&test->rcItem,EDGE_SUNKEN,BF_RECT); // Draw a sunken face
                    }
                    else
                    {
                        DrawEdge(test->hDC, &test->rcItem,EDGE_RAISED,BF_RECT); // Draw a raised face
                    }
                    //add the transparent image to the button
                    TransparentBlt(test->hDC,0,0,inst->imgtest.width(),inst->imgtest.height(),inst->imgtest,0,0,inst->imgtest.width(),inst->imgtest.height(),GetPixel(inst->imgtest,0,0));
    
    
                    //draw the caption
                    SetTextColor(test->hDC,inst->clrTextColor);
                    SetBkMode(test->hDC,TRANSPARENT);//text background transparent
                    DrawText(test->hDC,inst->strCaption.c_str(),-1,&test->rcItem,DT_CENTER | DT_SINGLELINE | DT_VCENTER);
    
                    //draw the focus rectangle
                    HPEN pen = CreatePen(PS_DOT,1,RGB(0,0,0));//these is the must close to the rectangle focus style
                    SelectObject(test->hDC,pen);
                    SelectObject(test->hDC,GetStockObject(NULL_BRUSH));//the rectangle will be transparent
                    if ( (test->itemState & ODS_FOCUS )) // If the button is focused
                    {
                        int iChange = 3;
                        test->rcItem.top += iChange;
                        test->rcItem.left += iChange;
                        test->rcItem.right -= iChange;
                        test->rcItem.bottom -= iChange;
                        Rectangle(test->hDC, test->rcItem.left, test->rcItem.top, test->rcItem.right, test->rcItem.bottom);
                    }
                }
                break;
    but how can i show it in gray scale?(when is disable)
    (i did it pixel by pixel, but its very slow)

  2. #2
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,626

    Re: [GDI] - owner draw: how draw it on gray scale?

    if with 'pixel by pixel' you mean individually calling SetPixel or SetPixelV
    then YES, that is going to be slow. SetPixel is horribly slow and should be avoided for any and all purposes.

    Solution:
    Create a DIBsection of the desired size around ALL of the pixels you want to change.
    Blit the screen to the DIB (if needed, not necessary if you'll be changing all pixels inside it)
    set the actual bits/bytes in the DIB to the pixel colors you want
    Blt the entire DIB section to screen at once

  3. #3
    Join Date
    Apr 2009
    Posts
    1,272

    Re: [GDI] - owner draw: how draw it on gray scale?

    Quote Originally Posted by OReubens View Post
    if with 'pixel by pixel' you mean individually calling SetPixel or SetPixelV
    then YES, that is going to be slow. SetPixel is horribly slow and should be avoided for any and all purposes.

    Solution:
    Create a DIBsection of the desired size around ALL of the pixels you want to change.
    Blit the screen to the DIB (if needed, not necessary if you'll be changing all pixels inside it)
    set the actual bits/bytes in the DIB to the pixel colors you want
    Blt the entire DIB section to screen at once
    i'm so sorry, but can you please give me a sample of DIB's?

  4. #4
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    7,038

    Re: [GDI] - owner draw: how draw it on gray scale?

    Last edited by 2kaud; February 5th, 2015 at 10:58 AM.
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2019 (16.5.2)

  5. #5
    Join Date
    Apr 2009
    Posts
    1,272

    Re: [GDI] - owner draw: how draw it on gray scale?

    what i'm doing wrong with these code?
    Code:
    void RePaint(bool blackandwhite)
        {
            //clean the hdc
            Gdiplus::Graphics graphics(hdcimage);
            graphics.Clear(clrBackColor);
    
            //draw image to hdc
            graphics.DrawImage(img, 0, 0, img->GetWidth(), img->GetHeight());
    
            BITMAPINFO bitmap_info;
            BYTE ave_color;
            int bytes_per_scanLine;
            int pad_per_scanLine;
            int X;
            int Y;
    
            //add values to bitmap_info
            bitmap_info.bmiHeader.biSize = 40;
            bitmap_info.bmiHeader.biWidth = img->GetWidth();
            bitmap_info.bmiHeader.biHeight = -img->GetHeight();
            bitmap_info.bmiHeader.biPlanes = 1;
            bitmap_info.bmiHeader.biBitCount = 32;
            bitmap_info.bmiHeader.biCompression = BI_RGB;
            bytes_per_scanLine = ((((bitmap_info.bmiHeader.biWidth * bitmap_info.bmiHeader.biBitCount) + 31) / 32) * 4);
            pad_per_scanLine = bytes_per_scanLine - (((bitmap_info.bmiHeader.biWidth * bitmap_info.bmiHeader.biBitCount) + 7) / 8);
            bitmap_info.bmiHeader.biSizeImage = bytes_per_scanLine * abs(bitmap_info.bmiHeader.biHeight);
    
            //prepared for recive the pixels
            BYTE pixels[3][img->GetWidth()]  [img->GetHeight()];
            GetDIBits (hdcimage,btBitmap , 0, img->GetHeight(), &pixels, &bitmap_info, DIB_RGB_COLORS);
    
            //grayscale the pixels
            for (Y = 0; Y< img->GetHeight(); Y++)
            {
                for (X = 0; X< img->GetWidth(); X++)
                {
                    if(blackandwhite==true)
                    {
                        ave_color = pixels[0] [X] [Y] + pixels[1] [X] [Y] + pixels[2] [X] [Y] / 3;
                        pixels[0] [X] [Y] = ave_color;
                        pixels[1] [X] [Y] = ave_color;
                        pixels[2] [X] [Y] = ave_color;
                    }
                }
            }
            //save the new pixels on btBitmap
            SetDIBits(hdcimage,btBitmap , 0, img->GetHeight(), &pixels, &bitmap_info, DIB_RGB_COLORS);
        }
    i only see black and a memory leak

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  


Windows Mobile Development Center


Click Here to Expand Forum to Full Width




On-Demand Webinars (sponsored)