X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/dabeb02181178d15b6914992a34eb223a98aaa0a..56bd6aaca9d758663e202816e1861ee8674526e7:/src/msw/icon.cpp diff --git a/src/msw/icon.cpp b/src/msw/icon.cpp index 93293f2814..fa2c11ffaf 100644 --- a/src/msw/icon.cpp +++ b/src/msw/icon.cpp @@ -1,187 +1,181 @@ ///////////////////////////////////////////////////////////////////////////// -// Name: icon.cpp +// Name: msw/icon.cpp // Purpose: wxIcon class // Author: Julian Smart -// Modified by: +// Modified by: 20.11.99 (VZ): don't derive from wxBitmap any more // Created: 04/01/98 // RCS-ID: $Id$ // Copyright: (c) Julian Smart and Markus Holzem -// Licence: wxWindows license +// Licence: wxWindows license ///////////////////////////////////////////////////////////////////////////// +// ============================================================================ +// declarations +// ============================================================================ + +// ---------------------------------------------------------------------------- +// headers +// ---------------------------------------------------------------------------- + #ifdef __GNUG__ -#pragma implementation "icon.h" + #pragma implementation "icon.h" #endif // For compilers that support precompilation, includes "wx.h". #include "wx/wxprec.h" #ifdef __BORLANDC__ -#pragma hdrstop + #pragma hdrstop #endif #ifndef WX_PRECOMP -#include -#include "wx/setup.h" -#include "wx/list.h" -#include "wx/utils.h" -#include "wx/app.h" -#include "wx/icon.h" + #include "wx/defs.h" + #include "wx/list.h" + #include "wx/utils.h" + #include "wx/app.h" + #include "wx/icon.h" + #include "wx/bitmap.h" + #include "wx/log.h" #endif #include "wx/msw/private.h" -#include "assert.h" -#if USE_XPM_IN_MSW -#define FOR_MSW 1 -#include "..\..\contrib\wxxpm\libxpm.34b\lib\xpm34.h" +#if wxUSE_RESOURCE_LOADING_IN_MSW + #include "wx/msw/curico.h" + #include "wx/msw/curicop.h" #endif -#if USE_RESOURCE_LOADING_IN_MSW -#include "wx/msw/curico.h" -#include "wx/msw/curicop.h" -#endif +// ---------------------------------------------------------------------------- +// wxWin macros +// ---------------------------------------------------------------------------- -#if !USE_SHARED_LIBRARIES -IMPLEMENT_DYNAMIC_CLASS(wxIcon, wxBitmap) -IMPLEMENT_DYNAMIC_CLASS(wxICOFileHandler, wxBitmapHandler) -IMPLEMENT_DYNAMIC_CLASS(wxICOResourceHandler, wxBitmapHandler) -#endif +IMPLEMENT_DYNAMIC_CLASS(wxIcon, wxIconBase) -/* - * Icons - */ +// ============================================================================ +// implementation +// ============================================================================ +// ---------------------------------------------------------------------------- +// wxIconRefData +// ---------------------------------------------------------------------------- -wxIconRefData::wxIconRefData(void) +void wxIconRefData::Free() { - m_hIcon = (WXHICON) NULL ; -} + if ( m_hIcon ) + { + ::DestroyIcon((HICON) m_hIcon); -wxIconRefData::~wxIconRefData(void) -{ - if ( m_hIcon ) - ::DestroyIcon((HICON) m_hIcon); + m_hIcon = 0; + } } -wxIcon::wxIcon(void) -{ -} +// ---------------------------------------------------------------------------- +// wxIcon +// ---------------------------------------------------------------------------- -wxIcon::wxIcon(const char WXUNUSED(bits)[], const int WXUNUSED(width), const int WXUNUSED(height)) +wxIcon::wxIcon(const char bits[], int width, int height) { + wxBitmap bmp(bits, width, height); + CopyFromBitmap(bmp); } -wxIcon::wxIcon(const wxString& icon_file, const long flags, - int desiredWidth, int desiredHeight) +wxIcon::wxIcon(const wxString& iconfile, + long flags, + int desiredWidth, + int desiredHeight) { - LoadFile(icon_file, flags, desiredWidth, desiredHeight); + LoadFile(iconfile, flags, desiredWidth, desiredHeight); } -wxIcon::~wxIcon(void) +wxIcon::~wxIcon() { } -bool wxIcon::FreeResource(bool force) +void wxIcon::CopyFromBitmap(const wxBitmap& bmp) { - if (M_ICONDATA && M_ICONDATA->m_hIcon) - { - DestroyIcon((HICON) M_ICONDATA->m_hIcon); - M_ICONDATA->m_hIcon = (WXHICON) NULL; - } - return TRUE; -} - -bool wxIcon::LoadFile(const wxString& filename, const long type, - int desiredWidth, int desiredHeight) -{ - UnRef(); +#ifdef __WIN32__ + wxMask *mask = bmp.GetMask(); + if ( !mask ) + { + // we must have a mask for an icon, so even if it's probably incorrect, + // do create it (grey is the "standard" transparent colour) + mask = new wxMask(bmp, *wxLIGHT_GREY); + } - m_refData = new wxIconRefData; + ICONINFO iconInfo; + iconInfo.fIcon = TRUE; // we want an icon, not a cursor + iconInfo.hbmMask = wxInvertMask((HBITMAP)mask->GetMaskBitmap()); + iconInfo.hbmColor = GetHbitmapOf(bmp); + + /* GRG: black out the transparent area to preserve background + * colour, because Windows blits the original bitmap using + * SRCINVERT (XOR) after applying the mask to the dest rect. + */ + HDC dcSrc = ::CreateCompatibleDC(NULL); + HDC dcDst = ::CreateCompatibleDC(NULL); + SelectObject(dcSrc, (HBITMAP)mask->GetMaskBitmap()); + SelectObject(dcDst, iconInfo.hbmColor); + + BitBlt(dcDst, 0, 0, bmp.GetWidth(), bmp.GetHeight(), dcSrc, 0, 0, SRCAND); + + SelectObject(dcDst, NULL); + SelectObject(dcSrc, NULL); + DeleteDC(dcDst); + DeleteDC(dcSrc); + + HICON hicon = ::CreateIconIndirect(&iconInfo); + if ( !hicon ) + { + wxLogLastError(wxT("CreateIconIndirect")); + } + else + { + SetHICON((WXHICON)hicon); + SetSize(bmp.GetWidth(), bmp.GetHeight()); + } - wxBitmapHandler *handler = FindHandler(type); + if ( !bmp.GetMask() ) + { + // we created the mask, now delete it + delete mask; + } +#else // Win16 + // there are some functions in curico.cpp which probably could be used + // here... + // This probably doesn't work. + HBITMAP hBitmap = (HBITMAP) bmp.GetHBITMAP(); + HICON hIcon = MakeIconFromBitmap((HINSTANCE) wxGetInstance(), hBitmap); + if (hIcon) + { + SetHICON((WXHICON)hIcon); + SetSize(bmp.GetWidth(), bmp.GetHeight()); + } - if ( handler ) - return handler->LoadFile(this, filename, type, desiredWidth, desiredHeight); - else - return FALSE; +// wxFAIL_MSG("Bitmap to icon conversion (including use of XPMs for icons) not implemented"); +#endif // Win32/16 } -void wxIcon::SetHICON(WXHICON ico) +void wxIcon::CreateIconFromXpm(const char **data) { - if ( !M_ICONDATA ) - m_refData = new wxIconRefData; - - M_ICONDATA->m_hIcon = ico; + wxBitmap bmp(data); + CopyFromBitmap(bmp); } -bool wxICOFileHandler::LoadFile(wxBitmap *bitmap, const wxString& name, const long flags, - int desiredWidth, int desiredHeight) +bool wxIcon::LoadFile(const wxString& filename, + long type, + int desiredWidth, int desiredHeight) { -#if USE_RESOURCE_LOADING_IN_MSW - if ( bitmap->IsKindOf(CLASSINFO(wxIcon)) ) - { - wxIcon *icon = (wxIcon *)bitmap; - int width, height; - WXHICON hIcon = (WXHICON) ReadIconFile((char *)(const char *)name, wxGetInstance(), &width, &height); - - ((wxIconRefData *)icon->GetRefData())->m_hIcon = hIcon; - ((wxIconRefData *)icon->GetRefData())->m_ok = (((wxIconRefData *)icon->GetRefData())->m_hIcon != 0); - return ((wxIconRefData *)icon->GetRefData())->m_ok; - } - else - return FALSE; -#else - return FALSE; -#endif -} + UnRef(); -bool wxICOResourceHandler::LoadFile(wxBitmap *bitmap, const wxString& name, const long flags, - int desiredWidth, int desiredHeight) -{ - if ( bitmap->IsKindOf(CLASSINFO(wxIcon)) ) - { -#if defined(__WIN32__) - if (desiredWidth > -1 && desiredHeight > -1) - { - M_ICONHANDLERDATA->m_hIcon = (WXHICON) ::LoadImage(wxGetInstance(), name, IMAGE_ICON, desiredWidth, desiredHeight, LR_DEFAULTCOLOR); - } - else -#endif + wxGDIImageHandler *handler = FindHandler(type); + + if ( !handler ) { - M_ICONHANDLERDATA->m_hIcon = (WXHICON) ::LoadIcon(wxGetInstance(), name); + // say something? + return FALSE; } -#ifdef __WIN32__ - // Win32s doesn't have GetIconInfo function... - if (M_ICONHANDLERDATA->m_hIcon && wxGetOsVersion()!=wxWIN32S) - { - ICONINFO info ; - if (::GetIconInfo((HICON) M_ICONHANDLERDATA->m_hIcon, &info)) - { - HBITMAP ms_bitmap = info.hbmMask ; - if (ms_bitmap) - { - BITMAP bm; - ::GetObject(ms_bitmap, sizeof(BITMAP), (LPSTR) &bm); - M_ICONHANDLERDATA->m_width = bm.bmWidth; - M_ICONHANDLERDATA->m_height = bm.bmHeight; - } - if (info.hbmMask) - ::DeleteObject(info.hbmMask) ; - if (info.hbmColor) - ::DeleteObject(info.hbmColor) ; - } - } -#else - M_ICONHANDLERDATA->m_width = 32; - M_ICONHANDLERDATA->m_height = 32; -#endif - M_ICONHANDLERDATA->m_ok = (M_ICONHANDLERDATA->m_hIcon != 0); - return M_ICONHANDLERDATA->m_ok; - } - else - return FALSE; + return handler->Load(this, filename, type, desiredWidth, desiredHeight); }