+ -
当前位置:首页 → 问答吧 → PNG 异形对话框 图片位深度的疑问!!!

PNG 异形对话框 图片位深度的疑问!!!

时间:2011-12-07

来源:互联网

C/C++ code


void CPNGDlg::UpdateView(CString pngFileName, int width,int height)
{
    HBITMAP hBitmap;
    hBitmap=CreateCompatibleBitmap(this->GetDC()->m_hDC,width,height);
    hBitmap=ConverBmp(hBitmap);
    m_bmpDialog.DeleteObject();
    m_bmpDialog.Attach(hBitmap);

    DoUpdateDummyDialog(pngFileName, *this,m_bmpDialog,255);
}


void CPNGDlg::DoUpdateDummyDialog(CString pngFileName, CWnd &wnd, CBitmap &bmp, BYTE SourceConstantAlpha)
{
    CBitmap *pOldBitmap= dcMemory.SelectObject(&bmp);
    BITMAP bmpInfo;
    bmp.GetBitmap(&bmpInfo);
    CRect rectDlg;
    wnd.GetWindowRect(rectDlg);
    CPoint ptWindowScreenPosition(rectDlg.TopLeft());
    CSize szWindow(bmpInfo.bmWidth, bmpInfo.bmHeight);
    BLENDFUNCTION blendPixelFunction= { AC_SRC_OVER, 0, SourceConstantAlpha, 0x01};
    CPoint ptSrc(0,0);

    Graphics graphics(dcMemory.m_hDC);

    //////////////////////////////////////////////////////////////////////////

    Bitmap *m_bit=new Bitmap(pngFileName.AllocSysString());
    graphics.DrawImage(m_bit,0,0);
    delete m_bit;

    //////////////////////////////////////////////////////////////////////////

    graphics.ReleaseHDC(dcMemory.m_hDC);

    HINSTANCE hInst=::LoadLibrary("user32.dll");    
    if (hInst)    
    {    
        typedef BOOL (WINAPI *MYFUNC)(HWND,HDC,POINT*,SIZE*,HDC,POINT*,COLORREF,BLENDFUNCTION*,DWORD);    
        MYFUNC fun=NULL;   

        fun=(MYFUNC)GetProcAddress(hInst,"UpdateLayeredWindow");  
        if (fun)
            fun(wnd,m_screenDC->m_hDC, &ptWindowScreenPosition, &szWindow, dcMemory,&ptSrc, 0, &blendPixelFunction, 0x02);    

        FreeLibrary(hInst);    
    }

    dcMemory.SelectObject(pOldBitmap);
}


HBITMAP CPNGDlg::ConverBmp(HBITMAP hBitmap)
{
    HDC hDC;
    WORD wBitCount=32;
    DWORD dwPaletteSize=0, dwBmBitsSize=0, dwDIBSize=0, dwWritten=0;
    BITMAP Bitmap; 
    BITMAPINFOHEADER bi; 
    LPBITMAPINFOHEADER lpbi; 
    HANDLE hPal,hOldPal=NULL;
    HBITMAP hDib;

    GetObject(hBitmap, sizeof(Bitmap), (LPSTR)&Bitmap);
    bi.biSize = sizeof(BITMAPINFOHEADER);
    bi.biWidth = Bitmap.bmWidth;
    bi.biHeight = Bitmap.bmHeight;
    bi.biPlanes = 1;
    bi.biBitCount = wBitCount;
    bi.biCompression = BI_RGB;
    bi.biSizeImage = 0;
    bi.biXPelsPerMeter = 0;
    bi.biYPelsPerMeter = 0;
    bi.biClrImportant = 0;
    bi.biClrUsed = 0;

    dwBmBitsSize = ((Bitmap.bmWidth * wBitCount + 31) / 32) * 4 * Bitmap.bmHeight;

    hPal = GetStockObject(DEFAULT_PALETTE);
    if (hPal)
    {
        hDC = ::GetDC(NULL);
        hOldPal = ::SelectPalette(hDC, (HPALETTE)hPal, FALSE);
        RealizePalette(hDC);
    }

    hDib = CreateDIBSection(hDC,(BITMAPINFO*)&bi,DIB_RGB_COLORS, (LPVOID*)&lpbi, NULL, 0);
    GetDIBits(hDC, hBitmap, 0, (UINT) Bitmap.bmHeight, (LPSTR)lpbi+dwPaletteSize, (LPBITMAPINFO)&bi, DIB_RGB_COLORS);
    if (hOldPal)
    {
        ::SelectPalette(hDC, (HPALETTE)hOldPal, TRUE);
        RealizePalette(hDC);
        ::ReleaseDC(NULL, hDC);
    }

    CloseHandle(hPal);
    CloseHandle(hOldPal);
    DeleteObject(hBitmap);

    return hDib;
}

BOOL CPNGDlg::OnInitDialog()
{
    CDialog::OnInitDialog();

    // TODO:  在此添加额外的初始化
    m_screenDC=new CDC();
    m_screenDC->Attach(::GetDC(NULL));
    dcMemory.CreateCompatibleDC(m_screenDC);
    ModifyStyleEx(0,0x80000);



    CString m_AppPath;
    char szPathName[MAX_PATH];
    ::GetModuleFileName(NULL,szPathName,sizeof(szPathName));
    m_AppPath=CString(szPathName).Left(CString(szPathName).ReverseFind('//')+1);

    UpdateView(_T("res\\bg.png"),595,396);

    return TRUE;  // return TRUE unless you set the focus to a control
    // 异常: OCX 属性页应返回 FALSE
}



这段代码是支持24位PNG图片的异性窗口,但是当我加载32位PNG图片的时候,图片会变大,失真很多,请教大家如何将代码修改为支持32位PNG图片异性窗口!

感谢!!!

作者: x858078   发布时间: 2011-12-07

是分数太少了吗? 大家帮帮忙!!!

作者: x858078   发布时间: 2011-12-07