![]() |
CXTPImageManager::ResampleAlphaLayer Correction |
Post Reply ![]() |
Author | |
tomay3000 ![]() Groupie ![]() ![]() Joined: 08 December 2010 Location: Algeria Status: Offline Points: 56 |
![]() ![]() ![]() ![]() ![]() Posted: 12 August 2011 at 9:29pm |
Inside .h file
//HBITMAP ResampleAlphaLayer(HBITMAP bmpAlpha, COLORREF clrMask = RGB(255, 255, 255)); Inside .cpp file /*HBITMAP ResampleAlphaLayer(HBITMAP bmpAlpha, COLORREF clrMask) { CDC dcSrc; dcSrc.CreateCompatibleDC(NULL); LPBYTE pBits = NULL; LPBITMAPINFO pBitmapInfo = NULL; UINT nSize; if (!CXTPImageManagerIcon::GetBitmapBits(dcSrc, bmpAlpha, pBitmapInfo, (LPVOID&)pBits, nSize)) return NULL; LPBYTE pTarget = NULL; LPBYTE pSource = pBits; pBitmapInfo->bmiHeader.biBitCount = 24; pBitmapInfo->bmiHeader.biSizeImage = 0; pBitmapInfo->bmiHeader.biCompression = BI_RGB; HBITMAP hBitmapResult = CreateDIBSection(dcSrc, pBitmapInfo, DIB_RGB_COLORS, (LPVOID*)&pTarget, NULL, 0); if (pTarget && pSource && hBitmapResult) { for (int i = 0; i < pBitmapInfo->bmiHeader.biHeight; i ++) { for (int j = 0; j < pBitmapInfo->bmiHeader.biWidth; j ++) { BYTE bytAlpha = pSource[3]; if (bytAlpha == 0) // Transparent { pTarget[0] = GetBValue(clrMask); pTarget[1] = GetGValue(clrMask); pTarget[2] = GetRValue(clrMask); } else if (bytAlpha == 255) // Opaque { pTarget[0] = pSource[0]; pTarget[1] = pSource[1]; pTarget[2] = pSource[2]; } else // Semitransparent { pTarget[0] = (BYTE)(abs(GetBValue(clrMask) - pSource[0]) * (255 - bytAlpha) / 255); pTarget[1] = (BYTE)(abs(GetGValue(clrMask) - pSource[1]) * (255 - bytAlpha) / 255); pTarget[2] = (BYTE)(abs(GetRValue(clrMask) - pSource[2]) * (255 - bytAlpha) / 255); } pTarget += 3; pSource += 4; } if (pBitmapInfo->bmiHeader.biWidth % 2) pTarget ++; } } FREE(pBits); FREE(pBitmapInfo); return hBitmapResult; }*/ ![]() |
|
Product: Codejock ToolkitPro MFC v16.2.0
Platform: Microsoft Windows 8 Pro (64-bit) Language: Microsoft Visual C++ v6.0 (MFC) |
|
![]() |
|
Oleg ![]() Admin Group ![]() Joined: 21 May 2003 Location: United States Status: Offline Points: 11234 |
![]() ![]() ![]() ![]() ![]() |
Thanks, actually Resample is obsolete function now - was added when ImageManager didn't support alpha images in Win9x. Now you can draw alpha bitmap in all OS, so you don't need call Resample.
|
|
Oleg, Support Team
CODEJOCK SOFTWARE SOLUTIONS |
|
![]() |
|
tomay3000 ![]() Groupie ![]() ![]() Joined: 08 December 2010 Location: Algeria Status: Offline Points: 56 |
![]() ![]() ![]() ![]() ![]() |
I think you are wrong about this. The problem depends on the printer capability. Because some printer devices doesn't support alpha-blending, so the use of CXTPImageManager::ResampleAlphaLayeris still needed. I have faced this problem when printing on an A4 paper.![]() |
|
Product: Codejock ToolkitPro MFC v16.2.0
Platform: Microsoft Windows 8 Pro (64-bit) Language: Microsoft Visual C++ v6.0 (MFC) |
|
![]() |
|
Oleg ![]() Admin Group ![]() Joined: 21 May 2003 Location: United States Status: Offline Points: 11234 |
![]() ![]() ![]() ![]() ![]() |
Hi,
Thanks, I see. Will review this code.
|
|
Oleg, Support Team
CODEJOCK SOFTWARE SOLUTIONS |
|
![]() |
|
tomay3000 ![]() Groupie ![]() ![]() Joined: 08 December 2010 Location: Algeria Status: Offline Points: 56 |
![]() ![]() ![]() ![]() ![]() |
welcome |
|
Product: Codejock ToolkitPro MFC v16.2.0
Platform: Microsoft Windows 8 Pro (64-bit) Language: Microsoft Visual C++ v6.0 (MFC) |
|
![]() |
|
tomay3000 ![]() Groupie ![]() ![]() Joined: 08 December 2010 Location: Algeria Status: Offline Points: 56 |
![]() ![]() ![]() ![]() ![]() |
I have seen your code in CXTPImageManager::ResampleAlphaLayer function of the Codejock ToolkitPro MFC v15.1.3.0908 & this is what I would like to say: First: This is the true, global & final math formula used in re-sampling 32bit alpha bitmaps to 24bit bitmaps. I have been working last night to find it. ![]() Second: In your code you used this: pTarget[0] = (BYTE)((pSource[0] * (255 - iAlpha) + pSource[0] * iAlpha) >> 8); pTarget[1] = (BYTE)((pSource[1] * (255 - iAlpha) + pSource[1] * iAlpha) >> 8); pTarget[2] = (BYTE)((pSource[2] * (255 - iAlpha) + pSource[2] * iAlpha) >> 8); And as known: (x * y) + (x * z) = x * (y + z) So, your code is the same as the below: pTarget[0] = (BYTE)((pSource[0] * 255) >> 8); pTarget[1] = (BYTE)((pSource[1] * 255) >> 8); pTarget[2] = (BYTE)((pSource[2] * 255) >> 8); Third: R G B & A values of a bitmap are stored in like this: BGRA BGRA BGRA BGRA BGRA ... and not RGBA as you did. (You confused Red with Blue). Fourth: This is the last CXTPImageManager::ResampleAlphaLayer function that should be: HBITMAP CXTPImageManager::ResampleAlphaLayer(HBITMAP hBitmapAlpha, COLORREF clrMask) { LPBYTE lpbytBits = NULL; LPBITMAPINFO lpBitmapInfo = NULL; UINT uiSize; if (!CXTPImageManagerIcon::GetBitmapBits(*CDC::FromHandle(::CreateCompatibleDC(NULL)), hBitmapAlpha, lpBitmapInfo, (LPVOID&)lpbytBits, uiSize)) return NULL; LPBYTE lpbytTarget = NULL; LPBYTE lpbytSource = lpbytBits; lpBitmapInfo->bmiHeader.biBitCount = 24; lpBitmapInfo->bmiHeader.biCompression = BI_RGB; lpBitmapInfo->bmiHeader.biSizeImage = 0; HBITMAP hBitmapResult = ::CreateDIBSection(::CreateCompatibleDC(NULL), lpBitmapInfo, DIB_RGB_COLORS, (LPVOID *)&lpbytTarget, NULL, 0); if (lpbytTarget && lpbytSource && hBitmapResult) { for (int i = 0; i < lpBitmapInfo->bmiHeader.biHeight; i ++) { for (int j = 0; j < lpBitmapInfo->bmiHeader.biWidth; j ++) { lpbytTarget[0] = (BYTE)(GetBValue(clrMask) + lpbytSource[3] * (lpbytSource[0] - GetBValue(clrMask)) / 255); lpbytTarget[1] = (BYTE)(GetGValue(clrMask) + lpbytSource[3] * (lpbytSource[1] - GetGValue(clrMask)) / 255); lpbytTarget[2] = (BYTE)(GetRValue(clrMask) + lpbytSource[3] * (lpbytSource[2] - GetRValue(clrMask)) / 255); lpbytTarget += 3; lpbytSource += 4; } lpbytTarget += -(lpBitmapInfo->bmiHeader.biWidth * 3) & 3; } } FREE(lpbytBits); FREE(lpBitmapInfo); return hBitmapResult; } Fifth: This is a result of the comparison of an image and some variable masks.Original Image: ![]() Mask = RGB(255, 255, 255) ![]() ![]() Mask = RGB(255, 0, 0) ![]() ![]() Mask = RGB(0, 255, 0) ![]() ![]() Mask = RGB(0, 0, 255) ![]() ![]() & Finally: Thank you for your understand & PLEASE do this fix in the next hotfix ![]() |
|
Product: Codejock ToolkitPro MFC v16.2.0
Platform: Microsoft Windows 8 Pro (64-bit) Language: Microsoft Visual C++ v6.0 (MFC) |
|
![]() |
Post Reply ![]() |
|
Tweet
|
Forum Jump | Forum Permissions ![]() You cannot post new topics in this forum You cannot reply to topics in this forum You cannot delete your posts in this forum You cannot edit your posts in this forum You cannot create polls in this forum You cannot vote in polls in this forum |