From ba3e10c9f4546fc991957fed40360fe245dd6151 Mon Sep 17 00:00:00 2001 From: David Webster Date: Mon, 29 Apr 2002 04:00:57 +0000 Subject: [PATCH] Lots of image/bitmap processing updates. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@15301 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- src/os2/bitmap.cpp | 53 ++++++++-------- src/os2/dc.cpp | 148 +++++++++++++++++++++++++++++++++++++------ src/os2/dcclient.cpp | 3 +- src/os2/dcmemory.cpp | 111 +++++++++++++++++++++++++++----- 4 files changed, 250 insertions(+), 65 deletions(-) diff --git a/src/os2/bitmap.cpp b/src/os2/bitmap.cpp index 99264e0611..486cfed0af 100644 --- a/src/os2/bitmap.cpp +++ b/src/os2/bitmap.cpp @@ -227,6 +227,8 @@ wxBitmap::wxBitmap( pzData = (char *)zBits; // const_cast is harmless } + if (nDepth > 24) + nDepth = 24; // MAX supported in PM memset(&vHeader, '\0', 16); vHeader.cbFix = 16; vHeader.cx = (USHORT)nWidth; @@ -346,6 +348,9 @@ bool wxBitmap::Create( hDCScreen = ::GpiQueryDevice(hPSScreen); ::DevQueryCaps(hDCScreen, CAPS_COLOR_BITCOUNT, 1L, &lBitCount); + if (lBitCount > 24) + lBitCount = 24; + memset(&vHeader, '\0', 16); vHeader.cbFix = 16; vHeader.cx = nW; @@ -563,6 +568,8 @@ bool wxBitmap::CreateFromImage ( // BITMAPINFOHEADER2 vHeader; BITMAPINFO2 vInfo; + LONG alFormats[24]; // Max formats OS/2 PM supports + ULONG ulBitcount; // // Fill in the DIB header @@ -574,12 +581,6 @@ bool wxBitmap::CreateFromImage ( vHeader.cPlanes = 1L; vHeader.cBitCount = 24; - memset(&vInfo, '\0', 16); - vInfo.cbFix = 16; - vInfo.cx = (ULONG)nWidth; - vInfo.cy = (ULONG)nHeight; - vInfo.cPlanes = 1L; - vInfo.cBitCount = 24; // // Memory for DIB data // @@ -605,6 +606,17 @@ bool wxBitmap::CreateFromImage ( HBITMAP hBmp; HBITMAP hBmpOld; + ::GpiQueryDeviceBitmapFormats(hPS, 24, alFormats); + ulBitcount = alFormats[1]; // the best one for the device + if (ulBitcount > 24) + ulBitcount = 24; // MAX bits supported by PM + memset(&vInfo, '\0', 16); + vInfo.cbFix = 16; + vInfo.cx = (ULONG)nWidth; + vInfo.cy = (ULONG)nHeight; + vInfo.cPlanes = 1; + vInfo.cBitCount = ulBitcount; + hBmp = ::GpiCreateBitmap( hPS ,&vHeader ,0L @@ -661,7 +673,6 @@ bool wxBitmap::CreateFromImage ( // Have to do something similar to WIN32's StretchDIBits, use GpiBitBlt // in combination with setting the bits into the selected bitmap // - vInfo.cBitCount = 16; if ((lScans = ::GpiSetBitmapBits( hPS ,0 // Start at the bottom ,(LONG)nHeight // One line per scan @@ -676,25 +687,6 @@ bool wxBitmap::CreateFromImage ( sError = wxPMErrorToStr(vError); } - // - // for debugging---- - // -LONG alFormats[24]; -::GpiQueryDeviceBitmapFormats(hPS, 24, alFormats); -if ((lScans = ::GpiQueryBitmapBits( hPS - ,0L - ,(LONG)nHeight - ,(PBYTE)pucBits - ,&vInfo - )) == GPI_ALTERROR) -{ - ERRORID vError; - wxString sError; - - vError = ::WinGetLastError(vHabmain); - sError = wxPMErrorToStr(vError); -} - hPSScreen = ::GpiCreatePS( vHabmain ,hDCScreen ,&vSize @@ -827,6 +819,7 @@ if ((lScans = ::GpiQueryBitmapBits( hPS // ::GpiSetBitmap(hPS, NULLHANDLE); ::GpiDestroyPS(hPS); + ::DevCloseDC(hDCScreen); ::DevCloseDC(hDC); free(pucBits); return TRUE; @@ -862,7 +855,13 @@ wxImage wxBitmap::ConvertToImage() const DEVOPENSTRUC vDop = {0L, "DISPLAY", NULL, 0L, 0L, 0L, 0L, 0L, 0L}; SIZEL vSizlPage = {0,0}; HDC hDCMem; + LONG alFormats[24]; // 24 is MAX formats supported + ULONG ulBitcount; + ::GpiQueryDeviceBitmapFormats(hPS, 24, alFormats); + ulBitcount = alFormats[1]; // the best one + if (ulBitcount > 24) // PM supports a max of 24 + ulBitcount = 24; vImage.Create( nWidth ,nHeight ); @@ -895,7 +894,7 @@ wxImage wxBitmap::ConvertToImage() const vDIBInfo.cx = nWidth; vDIBInfo.cy = nHeight; vDIBInfo.cPlanes = 1; - vDIBInfo.cBitCount = 24; + vDIBInfo.cBitCount = ulBitcount; lpBits = (unsigned char *)malloc(nBytePerLine * nHeight); if (!lpBits) diff --git a/src/os2/dc.cpp b/src/os2/dc.cpp index 8bf6f5b520..87610e6d63 100644 --- a/src/os2/dc.cpp +++ b/src/os2/dc.cpp @@ -992,8 +992,8 @@ void wxDC::DoDrawRectangle( vPoint[0].x = vX; vPoint[0].y = vY; - vPoint[1].x = vX + vWidth; - vPoint[1].y = vY + vHeight; + vPoint[1].x = vX + vWidth - 1; + vPoint[1].y = vY + vHeight - 1; ::GpiMove(m_hPS, &vPoint[0]); lColor = m_brush.GetColour().GetPixel(); lBorderColor = m_pen.GetColour().GetPixel(); @@ -1031,8 +1031,8 @@ void wxDC::DoDrawRectangle( ); vPoint[0].x = vX + 1; vPoint[0].y = vY + 1; - vPoint[1].x = vX + vWidth - 1; - vPoint[1].y = vY + vHeight - 1; + vPoint[1].x = vX + vWidth - 2; + vPoint[1].y = vY + vHeight - 2; ::GpiMove(m_hPS, &vPoint[0]); ::GpiBox( m_hPS ,lControl @@ -1209,7 +1209,7 @@ void wxDC::DoDrawBitmap( , bool bUseMask ) { - if (!bUseMask && !IsKindOf(CLASSINFO(wxPrinterDC))) + if (!IsKindOf(CLASSINFO(wxPrinterDC))) { HBITMAP hBitmap = (HBITMAP)rBmp.GetHBITMAP(); wxBitmap vNewBitmap( rBmp.GetWidth() @@ -1220,6 +1220,17 @@ void wxDC::DoDrawBitmap( LONG lOldTextground = ::GpiQueryColor((HPS)GetHPS()); LONG lOldBackground = ::GpiQueryBackColor((HPS)GetHPS()); + vY = OS2Y(vY,rBmp.GetHeight()); + + // + // Flip the picture as OS/2 is upside-down + // + POINTL vPoint[4] = { vX, vY + rBmp.GetHeight() + ,vX + rBmp.GetWidth(), vY + ,0, 0 + ,rBmp.GetWidth(), rBmp.GetHeight() + }; + if (m_textForegroundColour.Ok()) { ::GpiSetColor( (HPS)GetHPS() @@ -1232,24 +1243,119 @@ void wxDC::DoDrawBitmap( ,m_textBackgroundColour.GetPixel() ); } + if (bUseMask) + { + wxMask* pMask = rBmp.GetMask(); + HPS hPS; + HDC hDC; - vY = OS2Y(vY,rBmp.GetHeight()); + if (!IsKindOf(CLASSINFO(wxMemoryDC))) + { + DEVOPENSTRUC vDop = {0L, "DISPLAY", NULL, 0L, 0L, 0L, 0L, 0L, 0L}; + SIZEL vSize = {0, 0}; - // - // Flip the picture as OS/2 is upside-down - // - POINTL vPoint[4] = { vX, vY + rBmp.GetHeight() - ,vX + rBmp.GetWidth(), vY - ,0, 0 - ,rBmp.GetWidth(), rBmp.GetHeight() - }; - ::GpiWCBitBlt( (HPS)GetHPS() - ,hBitmap - ,4 - ,vPoint - ,ROP_SRCCOPY - ,BBO_IGNORE - ); + hDC = ::DevOpenDC(vHabmain, OD_MEMORY, "*", 5L, (PDEVOPENDATA)&vDop, NULLHANDLE); + hPS = ::GpiCreatePS(vHabmain, hDC, &vSize, PU_PELS | GPIA_ASSOC); + } + else + hPS = m_hPS; + + if (pMask) + { + BITMAPINFOHEADER2 vHeader; + BITMAPINFO2 vInfo; + int nBytesPerLine = rBmp.GetWidth() * 3; + unsigned char* pucData; + LONG lScans = 0L; + LONG alFormats[24]; // Max formats OS/2 PM supports + ULONG ulBitcount; + HBITMAP hMask = (HBITMAP)pMask->GetMaskBitmap(); + POINTL vPointMask[4] = { 0, 0, rBmp.GetWidth(), rBmp.GetHeight() + ,0, 0, rBmp.GetWidth(), rBmp.GetHeight() + }; + + ::GpiSetBitmap(hPS, hMask); + + ::GpiQueryDeviceBitmapFormats(hPS, 24, alFormats); + ulBitcount = alFormats[1]; // the best one + if (ulBitcount > 24) // PM supports a max of 24 + ulBitcount = 24; + + vInfo.cbFix = 16; + vInfo.cx = rBmp.GetWidth(); + vInfo.cy = rBmp.GetHeight(); + vInfo.cPlanes = 1; + vInfo.cBitCount = ulBitcount; + pucData = (unsigned char*)malloc(nBytesPerLine * rBmp.GetHeight()); + if ((lScans = ::GpiQueryBitmapBits( hPS + ,0L + ,(LONG)rBmp.GetHeight() + ,(PBYTE)pucData + ,&vInfo + )) == GPI_ALTERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + if ((hBitmapOld = ::GpiSetBitmap(hPS, (HBITMAP)vNewBitmap.GetHBITMAP())) == HBM_ERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + if ((lScans = ::GpiSetBitmapBits( hPS + ,0 + ,(LONG)rBmp.GetHeight() + ,(PBYTE)pucData + ,&vInfo + )) == GPI_ALTERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + if ((hBitmapOld = ::GpiSetBitmap(hPS, NULLHANDLE)) == HBM_ERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + if ((hBitmapOld = ::GpiSetBitmap((HPS)GetHPS(), vNewBitmap.GetHBITMAP())) == HBM_ERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + ::GpiWCBitBlt( (HPS)GetHPS() + ,hBitmap + ,4 + ,vPoint + ,ROP_SRCAND + ,BBO_IGNORE + ); + } + } + else + { + ::GpiWCBitBlt( (HPS)GetHPS() + ,hBitmap + ,4 + ,vPoint + ,ROP_SRCCOPY + ,BBO_IGNORE + ); + } ::GpiSetBitmap((HPS)GetHPS(), hBitmapOld); ::GpiSetColor((HPS)GetHPS(), lOldTextground); ::GpiSetBackColor((HPS)GetHPS(), lOldBackground); diff --git a/src/os2/dcclient.cpp b/src/os2/dcclient.cpp index 4bb99210df..e1be6a1052 100644 --- a/src/os2/dcclient.cpp +++ b/src/os2/dcclient.cpp @@ -319,12 +319,14 @@ wxPaintDC::wxPaintDC( { HPS hPS; + m_hDC = (WXHDC)::WinOpenWindowDC(GetWinHwnd(m_pCanvas)); hPS = ::WinBeginPaint( GetWinHwnd(m_pCanvas) ,NULLHANDLE ,&g_paintStruct ); if(hPS) { + ::GpiAssociate(hPS, m_hDC); m_hOldPS = m_hPS; m_hPS = hPS; ::GpiCreateLogColorTable( m_hPS @@ -349,7 +351,6 @@ wxPaintDC::wxPaintDC( } m_bIsPaintTime = TRUE; - m_hDC = (WXHDC) -1; // to satisfy those anonizmous efforts ms_cache.Add(new wxPaintDCInfo(m_pCanvas, this)); } InitDC(); diff --git a/src/os2/dcmemory.cpp b/src/os2/dcmemory.cpp index 9217a80518..71f06468ae 100644 --- a/src/os2/dcmemory.cpp +++ b/src/os2/dcmemory.cpp @@ -208,12 +208,18 @@ void wxMemoryDC::DoDrawRectangle( LONG lScans = 0L; POINTL vPoint; LONG lColor; + LONG alFormats[24]; // Max formats OS/2 PM supports + ULONG ulBitcount; + ::GpiQueryDeviceBitmapFormats(m_hPS, 24, alFormats); + ulBitcount = alFormats[1]; // the best one for the device + if (ulBitcount > 24) + ulBitcount = 24; // MAX bits supported by PM vInfo.cbFix = 16; vInfo.cx = vHeader.cx; vInfo.cy = vHeader.cy; vInfo.cPlanes = vHeader.cPlanes; - vInfo.cBitCount = 24; + vInfo.cBitCount = ulBitcount; pucData = (unsigned char*)malloc(nBytesPerLine * m_vSelectedBitmap.GetHeight()); if ((lScans = ::GpiQueryBitmapBits( m_hPS ,0L @@ -233,21 +239,94 @@ void wxMemoryDC::DoDrawRectangle( { for (int j = 0; j < m_vSelectedBitmap.GetWidth(); j++) { - if (i >= vY && j >= vX && i < vHeight && j < vWidth) - { - if (i == vY || j == vX || - i == m_vSelectedBitmap.GetWidth() -1 || - j == m_vSelectedBitmap.GetHeight() - 1 - ) - lColor = m_pen.GetColour().GetPixel(); - else - lColor = m_brush.GetColour().GetPixel(); - *(pucBits++) = (unsigned char)lColor; - *(pucBits++) = (unsigned char)(lColor >> 8); - *(pucBits++) = (unsigned char)(lColor >> 16); - } - else - pucBits += 3; + vPoint.x = j; vPoint.y = i; + lColor = ::GpiQueryPel(m_hPS, &vPoint); + *(pucBits++) = (unsigned char)lColor; + *(pucBits++) = (unsigned char)(lColor >> 8); + *(pucBits++) = (unsigned char)(lColor >> 16); + } + } + if ((lScans = ::GpiSetBitmapBits( m_hPS + ,0 + ,(LONG)m_vSelectedBitmap.GetHeight() + ,(PBYTE)pucData + ,&vInfo + )) == GPI_ALTERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + free(pucData); + } + } +} // end of wxMemoryDC::DoDrawRectangle + +void wxMemoryDC::DoDrawRoundedRectangle( + wxCoord vX +, wxCoord vY +, wxCoord vWidth +, wxCoord vHeight +, double dRadius +) +{ + wxDC::DoDrawRoundedRectangle(vX, vY, vWidth, vHeight, dRadius); + + // + // Debug testing: + // + if (m_vSelectedBitmap.GetHBITMAP() != NULLHANDLE) + { + BITMAPINFOHEADER2 vHeader; + BITMAPINFO2 vInfo; + + vHeader.cbFix = 16L; + if (::GpiQueryBitmapInfoHeader(m_vSelectedBitmap.GetHBITMAP(), &vHeader)) + { + unsigned char* pucData = NULL; + unsigned char* pucBits; + int nBytesPerLine = m_vSelectedBitmap.GetWidth() * 3; + LONG lScans = 0L; + POINTL vPoint; + LONG lColor; + LONG alFormats[24]; // Max formats OS/2 PM supports + ULONG ulBitcount; + + ::GpiQueryDeviceBitmapFormats(m_hPS, 24, alFormats); + ulBitcount = alFormats[1]; // the best one for the device + if (ulBitcount > 24) + ulBitcount = 24; // MAX bits supported by PM + vInfo.cbFix = 16; + vInfo.cx = vHeader.cx; + vInfo.cy = vHeader.cy; + vInfo.cPlanes = vHeader.cPlanes; + vInfo.cBitCount = ulBitcount; + pucData = (unsigned char*)malloc(nBytesPerLine * m_vSelectedBitmap.GetHeight()); + if ((lScans = ::GpiQueryBitmapBits( m_hPS + ,0L + ,(LONG)m_vSelectedBitmap.GetHeight() + ,(PBYTE)pucData + ,&vInfo + )) == GPI_ALTERROR) + { + ERRORID vError; + wxString sError; + + vError = ::WinGetLastError(vHabmain); + sError = wxPMErrorToStr(vError); + } + pucBits = pucData; + for (int i = 0; i < m_vSelectedBitmap.GetHeight(); i++) + { + for (int j = 0; j < m_vSelectedBitmap.GetWidth(); j++) + { + vPoint.x = j; vPoint.y = i; + lColor = ::GpiQueryPel(m_hPS, &vPoint); + *(pucBits++) = (unsigned char)lColor; + *(pucBits++) = (unsigned char)(lColor >> 8); + *(pucBits++) = (unsigned char)(lColor >> 16); } } if ((lScans = ::GpiSetBitmapBits( m_hPS -- 2.45.2