我用过StrecthDIBits,不错啊,而且好像一般放大缩小都用这个int DrawDIB(HDC hDC, CRect DCRect, HANDLE hDIB, CRect DIBRect, CPalette* pPal)
{
LPSTR lpDIBHdr;
LPSTR lpDIBBits;
int bSuccess = 0;
HPALETTE hPal = NULL;
HPALETTE hOldPal = NULL;
if(hDIB == NULL)
return 0;
lpDIBHdr = (LPSTR)::GlobalLock((HGLOBAL) hDIB);
lpDIBBits = (LPSTR)(lpDIBHdr + *(LPDWORD)lpDIBHdr + PaletteSize(lpDIBHdr));
if(pPal != NULL)
{
hPal = (HPALETTE) pPal->m_hObject;
hOldPal = ::SelectPalette(hDC, hPal, TRUE);
} ::SetStretchBltMode(hDC, COLORONCOLOR);
bSuccess = ::StretchDIBits(hDC, DCRect.left, DCRect.top,
DCRect.Width(), DCRect.Height(),
DIBRect.left, DIBRect.top,
DIBRect.Width(), DIBRect.Height(),
lpDIBBits, (LPBITMAPINFO)lpDIBHdr, DIB_RGB_COLORS, SRCCOPY); ::GlobalUnlock((HGLOBAL)hDIB);
if (hOldPal != NULL)
{
::SelectPalette(hDC, hOldPal, TRUE);
}
return bSuccess;
}
{
LPSTR lpDIBHdr;
LPSTR lpDIBBits;
int bSuccess = 0;
HPALETTE hPal = NULL;
HPALETTE hOldPal = NULL;
if(hDIB == NULL)
return 0;
lpDIBHdr = (LPSTR)::GlobalLock((HGLOBAL) hDIB);
lpDIBBits = (LPSTR)(lpDIBHdr + *(LPDWORD)lpDIBHdr + PaletteSize(lpDIBHdr));
if(pPal != NULL)
{
hPal = (HPALETTE) pPal->m_hObject;
hOldPal = ::SelectPalette(hDC, hPal, TRUE);
} ::SetStretchBltMode(hDC, COLORONCOLOR);
bSuccess = ::StretchDIBits(hDC, DCRect.left, DCRect.top,
DCRect.Width(), DCRect.Height(),
DIBRect.left, DIBRect.top,
DIBRect.Width(), DIBRect.Height(),
lpDIBBits, (LPBITMAPINFO)lpDIBHdr, DIB_RGB_COLORS, SRCCOPY); ::GlobalUnlock((HGLOBAL)hDIB);
if (hOldPal != NULL)
{
::SelectPalette(hDC, hOldPal, TRUE);
}
return bSuccess;
}
可以把CreateDIBSection的返回值选进HDC
StretchBlt硬件支持,比StretchDIBits要快。
缩放的效果不太好,你可以用高通滤波。
BOOL FCDibEffect::Stretch (DWORD dwWidth, DWORD dwHeight, int iType)
{
FCDib Old ;
Old = *this ;
this->Unload () ;
BITMAPV4HEADER Bmif ;
Old.GetDibInfo (&Bmif) ; if (iType)
if (dwWidth > dwHeight)
dwWidth = Old.Width() * dwHeight / Old.Height() ;
else
dwHeight = Old.Height() * dwWidth / Old.Width() ; HDC hdcDesc = CreateCompatibleDC (NULL),
hdcSrc = CreateCompatibleDC (NULL) ;
if ((!this->Create (dwWidth, dwHeight, Bmif.bV4BitCount, Bmif.bV4V4Compression, &Bmif.bV4RedMask)) || (hdcDesc == NULL) || (hdcSrc == NULL))
return FALSE ; int iTe = ::SetStretchBltMode (hdcDesc, COLORONCOLOR) ;
HBITMAP hTa = (HBITMAP)SelectObject (hdcDesc, this->GetHandle ()) ;
HBITMAP hTb = (HBITMAP)SelectObject (hdcSrc, Old.GetHandle ()) ;
BOOL res = ::StretchBlt (hdcDesc, 0, 0, dwWidth, dwHeight,
hdcSrc, 0, 0, Old.Width(), Old.Height(), SRCCOPY) ;
SelectObject (hdcDesc, hTa) ;
SelectObject (hdcSrc, hTb) ;
::SetStretchBltMode (hdcDesc, iTe) ;
DeleteDC (hdcDesc) ;
DeleteDC (hdcSrc) ;
return res ;
}滤波用的卷积函数.
void FCDibEffect::ConvoluteDIB_3x3 (CONVOLUTEKERNEL_3x3 kernel)
{
FCDib Old ;
Old = *this ; this->Unload () ;
if (!this->Create (Old.Width(), Old.Height(), 32))
return ; RGBQUAD * pCurLineSrc, * pCurLineSrc_UP, * pCurLineSrc_DOWN, * pCurLineDest ;
int iBlue, iGreen, iRed ;
int iCou1, x, y, ixMax = (int)Old.Width() - 2 ; for (y = Old.Height() - 2 ; y >=1 ; y--) // 行
{
pCurLineDest = (RGBQUAD *) this->GetBits (y) ;
pCurLineSrc = (RGBQUAD *) Old.GetBits (y) ;
pCurLineSrc_UP = (RGBQUAD *) Old.GetBits (y - 1) ;
pCurLineSrc_DOWN = (RGBQUAD *) Old.GetBits (y + 1) ;
for (x = 1 ; x < ixMax ; x++) // 列
{
iBlue = iRed = iGreen = 0 ;
for (iCou1 = 0 ; iCou1 < 3 ; iCou1++)
{
iBlue += pCurLineSrc_UP[iCou1].rgbBlue * kernel.iElement[iCou1] + pCurLineSrc[iCou1].rgbBlue * kernel.iElement[iCou1 + 3] + pCurLineSrc_DOWN[iCou1].rgbBlue * kernel.iElement[iCou1 + 6] ;
iGreen += pCurLineSrc_UP[iCou1].rgbGreen * kernel.iElement[iCou1] + pCurLineSrc[iCou1].rgbGreen * kernel.iElement[iCou1 + 3] + pCurLineSrc_DOWN[iCou1].rgbGreen * kernel.iElement[iCou1 + 6] ;
iRed += pCurLineSrc_UP[iCou1].rgbRed * kernel.iElement[iCou1] + pCurLineSrc[iCou1].rgbRed * kernel.iElement[iCou1 + 3] + pCurLineSrc_DOWN[iCou1].rgbRed * kernel.iElement[iCou1 + 6] ;
}
pCurLineDest[x].rgbBlue = ::fooBound (iBlue / kernel.iDivisor, 0, 0xFF) ;
pCurLineDest[x].rgbGreen = ::fooBound (iGreen / kernel.iDivisor, 0, 0xFF) ;
pCurLineDest[x].rgbRed = ::fooBound (iRed / kernel.iDivisor, 0, 0xFF) ;
pCurLineSrc_UP++ ; pCurLineSrc++ ; pCurLineSrc_DOWN++ ;
}
}
return ;
} case EFFECT_SMOOTH_1 :
this->InitKernel (&kernel, 1, 1, 1 , 1, 1, 1 , 1, 1, 1 , 9 ) ;
this->ConvoluteDIB_3x3 (kernel) ; break ;