From: Vadim Zeitlin Date: Sat, 2 Apr 2005 21:30:22 +0000 (+0000) Subject: added wxImage::IsTransparent(x, y) X-Git-Url: https://git.saurik.com/wxWidgets.git/commitdiff_plain/21dc4be5d27fd73cda55795ab9d1e7e02b494c46?ds=inline added wxImage::IsTransparent(x, y) git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@33284 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- diff --git a/docs/changes.txt b/docs/changes.txt index d8226f0dab..6a6388c212 100644 --- a/docs/changes.txt +++ b/docs/changes.txt @@ -29,6 +29,7 @@ All (GUI): - Added wxTE_BESTWRAP (based on patch by Mart Raudsepp). - wxEVT_COMMAND_SPLITTER_SASH_POS_CHANGED is now only sent once at the end of splitter dragging and not after each CHANGING event (Jacobo Vilella Vilahur). +- Added wxImage::IsTransparent() Unix: diff --git a/docs/latex/wx/image.tex b/docs/latex/wx/image.tex index 9d95417a0c..9990550f56 100644 --- a/docs/latex/wx/image.tex +++ b/docs/latex/wx/image.tex @@ -270,7 +270,7 @@ Returns number of colours in the histogram. \membersection{wxImage::ConvertAlphaToMask}\label{wximageconvertalphatomask} -\func{bool}{ConvertAlphaToMask}{\param{unsigned char}{ threshold = 128}} +\func{bool}{ConvertAlphaToMask}{\param{unsigned char}{ threshold = $128$}} If the image has alpha channel, this method converts it to mask. All pixels with alpha value less than \arg{threshold} are replaced with mask colour @@ -708,6 +708,15 @@ of a given handler class in an application session.} \helpref{wxImageHandler}{wximagehandler} +\membersection{wxImage::IsTransparent}\label{wximageistransparent} + +\constfunc{IsTransparent}{\param{int }{x}, \param{int }{y}, \param{unsigned char threshold = $128$}} + +Returns \true if the given pixel is transparent, i.e. either has the mask +colour if this image has a mask or if this image has alpha channel and alpha +value of this pixel is strictly less than \arg{threshold}. + + \membersection{wxImage::LoadFile}\label{wximageloadfile} \func{bool}{LoadFile}{\param{const wxString\&}{ name}, \param{long}{ type = wxBITMAP\_TYPE\_ANY}, \param{int}{ index = -1}} diff --git a/include/wx/image.h b/include/wx/image.h index c4737d7273..36843a4122 100644 --- a/include/wx/image.h +++ b/include/wx/image.h @@ -46,6 +46,13 @@ enum wxIMAGE_RESOLUTION_CM = 2 }; +// alpha channel values: fully transparent, default threshold separating +// transparent pixels from opaque for a few functions dealing with alpha and +// fully opaque +const unsigned char wxIMAGE_ALPHA_TRANSPARENT = 0; +const unsigned char wxIMAGE_ALPHA_THRESHOLD = 0x80; +const unsigned char wxIMAGE_ALPHA_OPAQUE = 0xff; + //----------------------------------------------------------------------------- // classes //----------------------------------------------------------------------------- @@ -240,7 +247,7 @@ public: // converts image's alpha channel to mask, if it has any, does nothing // otherwise: - bool ConvertAlphaToMask(unsigned char threshold = 128); + bool ConvertAlphaToMask(unsigned char threshold = wxIMAGE_ALPHA_THRESHOLD); // This method converts an image where the original alpha // information is only available as a shades of a colour @@ -290,6 +297,11 @@ public: void SetAlpha(unsigned char *alpha = NULL, bool static_data=false); void InitAlpha(); + // return true if this pixel is masked or has alpha less than specified + // threshold + bool IsTransparent(int x, int y, + unsigned char threshold = wxIMAGE_ALPHA_THRESHOLD) const; + // Mask functions void SetMaskColour( unsigned char r, unsigned char g, unsigned char b ); // Get the current mask colour or find a suitable colour diff --git a/src/common/image.cpp b/src/common/image.cpp index 7767fedb90..3514fd761b 100644 --- a/src/common/image.cpp +++ b/src/common/image.cpp @@ -787,6 +787,20 @@ wxImage wxImage::ConvertToMono( unsigned char r, unsigned char g, unsigned char return image; } +int wxImage::GetWidth() const +{ + wxCHECK_MSG( Ok(), 0, wxT("invalid image") ); + + return M_IMGDATA->m_width; +} + +int wxImage::GetHeight() const +{ + wxCHECK_MSG( Ok(), 0, wxT("invalid image") ); + + return M_IMGDATA->m_height; +} + long wxImage::XYToIndex(int x, int y) const { if ( Ok() && @@ -1022,8 +1036,6 @@ void wxImage::InitAlpha() unsigned char *alpha = M_IMGDATA->m_alpha; const size_t lenAlpha = M_IMGDATA->m_width * M_IMGDATA->m_height; - static const unsigned char ALPHA_TRANSPARENT = 0; - static const unsigned char ALPHA_OPAQUE = 0xff; if ( HasMask() ) { // use the mask to initialize the alpha channel. @@ -1037,8 +1049,8 @@ void wxImage::InitAlpha() src += 3, alpha++ ) { *alpha = (src[0] == mr && src[1] == mg && src[2] == mb) - ? ALPHA_TRANSPARENT - : ALPHA_OPAQUE; + ? wxIMAGE_ALPHA_TRANSPARENT + : wxIMAGE_ALPHA_OPAQUE; } M_IMGDATA->m_hasMask = false; @@ -1046,7 +1058,7 @@ void wxImage::InitAlpha() else // no mask { // make the image fully opaque - memset(alpha, ALPHA_OPAQUE, lenAlpha); + memset(alpha, wxIMAGE_ALPHA_OPAQUE, lenAlpha); } } @@ -1117,18 +1129,35 @@ bool wxImage::HasMask() const return M_IMGDATA->m_hasMask; } -int wxImage::GetWidth() const +bool wxImage::IsTransparent(int x, int y, unsigned char threshold) const { - wxCHECK_MSG( Ok(), 0, wxT("invalid image") ); + long pos = XYToIndex(x, y); + wxCHECK_MSG( pos != -1, false, wxT("invalid image coordinates") ); - return M_IMGDATA->m_width; -} + // check mask + if ( M_IMGDATA->m_hasMask ) + { + const unsigned char *p = M_IMGDATA->m_data + 3*pos; + if ( p[0] == M_IMGDATA->m_maskRed && + p[1] == M_IMGDATA->m_maskGreen && + p[2] == M_IMGDATA->m_maskBlue ) + { + return true; + } + } -int wxImage::GetHeight() const -{ - wxCHECK_MSG( Ok(), 0, wxT("invalid image") ); + // then check alpha + if ( M_IMGDATA->m_alpha ) + { + if ( M_IMGDATA->m_alpha[pos] < threshold ) + { + // transparent enough + return true; + } + } - return M_IMGDATA->m_height; + // not transparent + return false; } bool wxImage::SetMaskFromImage(const wxImage& mask, @@ -1216,9 +1245,11 @@ bool wxImage::ConvertAlphaToMask(unsigned char threshold) return true; } -#if wxUSE_PALETTE - +// ---------------------------------------------------------------------------- // Palette functions +// ---------------------------------------------------------------------------- + +#if wxUSE_PALETTE bool wxImage::HasPalette() const { @@ -1244,7 +1275,10 @@ void wxImage::SetPalette(const wxPalette& palette) #endif // wxUSE_PALETTE +// ---------------------------------------------------------------------------- // Option functions (arbitrary name/value mapping) +// ---------------------------------------------------------------------------- + void wxImage::SetOption(const wxString& name, const wxString& value) { wxCHECK_RET( Ok(), wxT("invalid image") ); @@ -1292,6 +1326,10 @@ bool wxImage::HasOption(const wxString& name) const return (M_IMGDATA->m_optionNames.Index(name, false) != wxNOT_FOUND); } +// ---------------------------------------------------------------------------- +// image I/O +// ---------------------------------------------------------------------------- + bool wxImage::LoadFile( const wxString& filename, long type, int index ) { #if wxUSE_STREAMS @@ -1549,6 +1587,10 @@ bool wxImage::SaveFile( wxOutputStream& stream, const wxString& mimetype ) const } #endif // wxUSE_STREAMS +// ---------------------------------------------------------------------------- +// image I/O handlers +// ---------------------------------------------------------------------------- + void wxImage::AddHandler( wxImageHandler *handler ) { // Check for an existing handler of the type being added.