Applied part of #10034: wxImage::ConvertToDisabled()

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@62099 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Julian Smart
2009-09-24 20:05:33 +00:00
parent cc3d673a84
commit 198c264dbc
10 changed files with 288 additions and 61 deletions

View File

@@ -175,6 +175,9 @@ public:
virtual wxBitmap GetSubBitmap(const wxRect& rect) const = 0;
// Convert to disabled (dimmed) bitmap.
wxBitmap ConvertToDisabled(unsigned char brightness = 255);
virtual bool SaveFile(const wxString &name, wxBitmapType type,
const wxPalette *palette = NULL) const = 0;
virtual bool LoadFile(const wxString &name, wxBitmapType type) = 0;

View File

@@ -15,7 +15,6 @@
#include "wx/defs.h"
#include "wx/gdiobj.h"
class WXDLLIMPEXP_FWD_CORE wxColour;
// A macro to define the standard wxColour constructors:
@@ -148,6 +147,22 @@ public:
bool Ok() const { return IsOk(); }
#endif
// manipulation
// ------------
// These methods are static because they are mostly used
// within tight loops (where we don't want to instantiate wxColour's)
static void MakeMono (unsigned char* r, unsigned char* g, unsigned char* b, bool on);
static void MakeDisabled(unsigned char* r, unsigned char* g, unsigned char* b, unsigned char brightness = 255);
static void MakeGrey (unsigned char* r, unsigned char* g, unsigned char* b); // integer version
static void MakeGrey (unsigned char* r, unsigned char* g, unsigned char* b,
double weight_r, double weight_g, double weight_b); // floating point version
static unsigned char AlphaBlend (unsigned char fg, unsigned char bg, double alpha);
static void ChangeLightness(unsigned char* r, unsigned char* g, unsigned char* b, int ialpha);
wxColour ChangeLightness(int ialpha) const;
// old, deprecated
// ---------------

View File

@@ -354,13 +354,17 @@ public:
unsigned char r2, unsigned char g2, unsigned char b2 );
// Convert to greyscale image. Uses the luminance component (Y) of the image.
// The luma value (YUV) is calculated using (R * lr) + (G * lg) + (B * lb), defaults to ITU-T BT.601
wxImage ConvertToGreyscale( double lr = 0.299, double lg = 0.587, double lb = 0.114 ) const;
// The luma value (YUV) is calculated using (R * weight_r) + (G * weight_g) + (B * weight_b), defaults to ITU-T BT.601
wxImage ConvertToGreyscale(double weight_r, double weight_g, double weight_b) const;
wxImage ConvertToGreyscale(void) const;
// convert to monochrome image (<r,g,b> will be replaced by white,
// everything else by black)
wxImage ConvertToMono( unsigned char r, unsigned char g, unsigned char b ) const;
// Convert to disabled (dimmed) image.
wxImage ConvertToDisabled(unsigned char brightness = 255) const;
// these routines are slow but safe
void SetRGB( int x, int y, unsigned char r, unsigned char g, unsigned char b );
void SetRGB( const wxRect& rect, unsigned char r, unsigned char g, unsigned char b );

View File

@@ -498,6 +498,12 @@ public:
*/
wxSize GetSize() const;
/**
Returns disabled (dimmed) version of the bitmap.
@since 2.9.0
*/
wxBitmap ConvertToDisabled(unsigned char brightness = 255) const;
/**
Gets the width of the bitmap in pixels.

View File

@@ -213,6 +213,54 @@ public:
colours and alpha values.
*/
bool operator ==(const wxColour& colour) const;
/**
Assign 0 or 255 to rgb out parameters.
@since 2.9.0
*/
static void MakeMono(unsigned char* r, unsigned char* g, unsigned char* b, bool on);
/**
Create a disabled (dimmed) colour from (in/out) rgb parameters.
@since 2.9.0
*/
static void MakeDisabled(unsigned char* r, unsigned char* g, unsigned char* b, unsigned char brightness = 255);
/**
Create a grey colour from (in/out) rgb parameters using integer arithmetic.
@since 2.9.0
*/
static void MakeGrey(unsigned char* r, unsigned char* g, unsigned char* b);
/**
Create a grey colour from (in/out) rgb parameters using floating point arithmetic.
Defaults to using the standard ITU-T BT.601 when converting to YUV, where every pixel equals
(R * @a weight_r) + (G * @a weight_g) + (B * @a weight_b).
@since 2.9.0
*/
static void MakeGrey(unsigned char* r, unsigned char* g, unsigned char* b,
double weight_r, double weight_g, double weight_b);
/**
Blend colour, taking alpha into account.
@since 2.9.0
*/
static unsigned char AlphaBlend(unsigned char fg, unsigned char bg, double alpha);
/**
ChangeLightness() is a utility function that simply darkens
or lightens a color, based on the specified percentage
ialpha of 0 would be completely black, 200 completely white
an ialpha of 100 returns the same colour
@since 2.9.0
*/
static void ChangeLightness(unsigned char* r, unsigned char* g, unsigned char* b, int ialpha);
/**
wxColour wrapper for ChangeLightness(r,g,b,ialpha).
@since 2.9.0
*/
wxColour ChangeLightness(int ialpha) const;
};

View File

@@ -171,6 +171,12 @@ public:
*/
virtual ~wxIcon();
/**
Returns disabled (dimmed) version of the icon. MSW only.
@since 2.9.0
*/
wxIcon ConvertToDisabled(unsigned char brightness = 255) const;
/**
Copies @a bmp bitmap to this icon.
Under MS Windows the bitmap must have mask colour set.

View File

@@ -847,9 +847,15 @@ public:
The returned image uses the luminance component of the original to
calculate the greyscale. Defaults to using the standard ITU-T BT.601
when converting to YUV, where every pixel equals
(R * @a lr) + (G * @a lg) + (B * @a lb).
(R * @a weight_r) + (G * @a weight_g) + (B * @a weight_b).
*/
wxImage ConvertToGreyscale(double lr = 0.299, double lg = 0.587, double lb = 1.114) const;
wxImage ConvertToGreyscale(double weight_r, double weight_g, double weight_b) const;
/**
Returns a greyscale version of the image.
@since 2.9.0
*/
wxImage ConvertToGreyscale() const;
/**
Returns monochromatic version of the image.
@@ -859,6 +865,12 @@ public:
*/
wxImage ConvertToMono(unsigned char r, unsigned char g, unsigned char b) const;
/**
Returns disabled (dimmed) version of the image.
@since 2.9.0
*/
wxImage ConvertToDisabled(unsigned char brightness = 255) const;
//@}

View File

@@ -135,6 +135,16 @@ public:
void OnExit() { wxBitmap::CleanUpHandlers(); }
};
wxBitmap wxBitmapBase::ConvertToDisabled(unsigned char brightness) const
{
wxBitmap bmp;
#if wxUSE_IMAGE
wxImage image = ConvertToImage();
bmp = wxBitmap(image.ConvertToDisabled(brightness));
#endif
return bmp;
}
IMPLEMENT_DYNAMIC_CLASS(wxBitmapBaseModule, wxModule)
#endif // wxUSE_BITMAP_BASE

View File

@@ -149,6 +149,97 @@ wxString wxColourBase::GetAsString(long flags) const
return colName;
}
// static
void wxColourBase::MakeMono(unsigned char* r, unsigned char* g, unsigned char* b,
bool on)
{
*r = *g = *b = on ? 255 : 0;
}
// static
void wxColourBase::MakeGrey(unsigned char* r, unsigned char* g, unsigned char* b
/*, unsigned char brightness */
)
{
*r = *g = *b = (wxByte)(((*b)*117UL + (*g)*601UL + (*r)*306UL) >> 10);
}
// static
void wxColourBase::MakeGrey(unsigned char* r, unsigned char* g, unsigned char* b,
double weight_r, double weight_g, double weight_b)
{
double luma = (*r) * weight_r + (*g) * weight_g + (*b) * weight_b;
*r = *g = *b = (wxByte)wxRound(luma);
}
// static
void wxColourBase::MakeDisabled(unsigned char* r, unsigned char* g, unsigned char* b,
unsigned char brightness)
{
//MakeGrey(r, g, b, brightness); // grey no-blend version
*r = AlphaBlend(*r, brightness, 0.4);
*g = AlphaBlend(*g, brightness, 0.4);
*b = AlphaBlend(*b, brightness, 0.4);
}
// AlphaBlend is used by ChangeLightness and MakeDisabled
// static
unsigned char wxColourBase::AlphaBlend(unsigned char fg, unsigned char bg,
double alpha)
{
double result = bg + (alpha * (fg - bg));
result = wxMax(result, 0.0);
result = wxMin(result, 255.0);
return (unsigned char)result;
}
// ChangeLightness() is a utility function that simply darkens
// or lightens a color, based on the specified percentage
// ialpha of 0 would be completely black, 100 completely white
// an ialpha of 100 returns the same colour
// static
void wxColourBase::ChangeLightness(unsigned char* r, unsigned char* g, unsigned char* b,
int ialpha)
{
if (ialpha == 100) return;
// ialpha is 0..200 where 0 is completely black
// and 200 is completely white and 100 is the same
// convert that to normal alpha 0.0 - 1.0
ialpha = wxMax(ialpha, 0);
ialpha = wxMin(ialpha, 200);
double alpha = ((double)(ialpha - 100.0))/100.0;
unsigned char bg;
if (ialpha > 100)
{
// blend with white
bg = 255;
alpha = 1.0 - alpha; // 0 = transparent fg; 1 = opaque fg
}
else
{
// blend with black
bg = 0;
alpha = 1.0 + alpha; // 0 = transparent fg; 1 = opaque fg
}
*r = AlphaBlend(*r, bg, alpha);
*g = AlphaBlend(*g, bg, alpha);
*b = AlphaBlend(*b, bg, alpha);
}
wxColour wxColourBase::ChangeLightness(int ialpha) const
{
wxByte r = Red();
wxByte g = Green();
wxByte b = Blue();
ChangeLightness(&r, &g, &b, ialpha);
return wxColour(r,g,b);
}
#if WXWIN_COMPATIBILITY_2_6
// static

View File

@@ -26,6 +26,7 @@
#include "wx/module.h"
#include "wx/palette.h"
#include "wx/intl.h"
#include "wx/colour.h"
#endif
#include "wx/filefn.h"
@@ -1436,7 +1437,12 @@ void wxImage::Replace( unsigned char r1, unsigned char g1, unsigned char b1,
}
}
wxImage wxImage::ConvertToGreyscale( double lr, double lg, double lb ) const
wxImage wxImage::ConvertToGreyscale(void) const
{
return ConvertToGreyscale(0.299, 0.587, 0.114);
}
wxImage wxImage::ConvertToGreyscale(double weight_r, double weight_g, double weight_b) const
{
wxImage image;
@@ -1460,16 +1466,14 @@ wxImage wxImage::ConvertToGreyscale( double lr, double lg, double lb ) const
const long size = M_IMGDATA->m_width * M_IMGDATA->m_height;
for ( long i = 0; i < size; i++, src += 3, dest += 3 )
{
memcpy(dest, src, 3);
// don't modify the mask
if ( hasMask && src[0] == maskRed && src[1] == maskGreen && src[2] == maskBlue )
{
memcpy(dest, src, 3);
}
else
{
// calculate the luma
double luma = (src[0] * lr + src[1] * lg + src[2] * lb) + 0.5;
dest[0] = dest[1] = dest[2] = static_cast<unsigned char>(luma);
wxColour::MakeGrey(dest + 0, dest + 1, dest + 2, weight_r, weight_g, weight_b);
}
}
@@ -1514,15 +1518,43 @@ wxImage wxImage::ConvertToMono( unsigned char r, unsigned char g, unsigned char
for ( long i = 0; i < size; i++, srcd += 3, tard += 3 )
{
if (srcd[0] == r && srcd[1] == g && srcd[2] == b)
tard[0] = tard[1] = tard[2] = 255;
else
tard[0] = tard[1] = tard[2] = 0;
bool on = (srcd[0] == r) && (srcd[1] == g) && (srcd[2] == b);
wxColourBase::MakeMono(tard + 0, tard + 1, tard + 2, on);
}
return image;
}
wxImage wxImage::ConvertToDisabled(unsigned char brightness) const
{
wxImage image = *this;
unsigned char mr = image.GetMaskRed();
unsigned char mg = image.GetMaskGreen();
unsigned char mb = image.GetMaskBlue();
int width = image.GetWidth();
int height = image.GetHeight();
bool has_mask = image.HasMask();
for (int y = height-1; y >= 0; --y)
{
for (int x = width-1; x >= 0; --x)
{
unsigned char* data = image.GetData() + (y*(width*3))+(x*3);
unsigned char* r = data;
unsigned char* g = data+1;
unsigned char* b = data+2;
if (has_mask && (*r == mr) && (*g == mg) && (*b == mb))
continue;
wxColour::MakeDisabled(r, g, b, brightness);
}
}
return image;
}
int wxImage::GetWidth() const
{
wxCHECK_MSG( Ok(), 0, wxT("invalid image") );