]> git.saurik.com Git - wxWidgets.git/blob - src/common/rgncmn.cpp
[ 1492053 ] Add wxVListBox style callbacks to wxOwnerDrawnComboBox.
[wxWidgets.git] / src / common / rgncmn.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/common/rgncmn.cpp
3 // Purpose: Methods of wxRegion that have a generic implementation
4 // Author: Robin Dunn
5 // Modified by:
6 // Created: 27-Mar-2003
7 // RCS-ID: $Id$
8 // Copyright: (c) Robin Dunn
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 // For compilers that support precompilation, includes "wx.h".
13 #include "wx/wxprec.h"
14
15 #ifdef __BORLANDC__
16 #pragma hdrstop
17 #endif
18
19 #include "wx/region.h"
20
21 #ifndef WX_PRECOMP
22 #include "wx/dcmemory.h"
23 #include "wx/bitmap.h"
24 #endif //WX_PRECOMP
25
26 #if wxUSE_IMAGE
27 #include "wx/image.h"
28 #endif
29
30
31
32 wxBitmap wxRegion::ConvertToBitmap() const
33 {
34 wxRect box = GetBox();
35 wxBitmap bmp(box.GetRight(), box.GetBottom());
36 wxMemoryDC dc;
37 dc.SelectObject(bmp);
38 dc.SetBackground(*wxBLACK_BRUSH);
39 dc.Clear();
40 dc.SetClippingRegion(*this);
41 dc.SetBackground(*wxWHITE_BRUSH);
42 dc.Clear();
43 dc.SelectObject(wxNullBitmap);
44 return bmp;
45 }
46
47 //---------------------------------------------------------------------------
48
49 #if wxUSE_IMAGE
50 static bool DoRegionUnion(wxRegion& region,
51 const wxImage& image,
52 unsigned char loR,
53 unsigned char loG,
54 unsigned char loB,
55 int tolerance)
56 {
57 unsigned char hiR, hiG, hiB;
58
59 hiR = (unsigned char)wxMin(0xFF, loR + tolerance);
60 hiG = (unsigned char)wxMin(0xFF, loG + tolerance);
61 hiB = (unsigned char)wxMin(0xFF, loB + tolerance);
62
63 // Loop through the image row by row, pixel by pixel, building up
64 // rectangles to add to the region.
65 int width = image.GetWidth();
66 int height = image.GetHeight();
67 for (int y=0; y < height; y++)
68 {
69 wxRect rect;
70 rect.y = y;
71 rect.height = 1;
72
73 for (int x=0; x < width; x++)
74 {
75 // search for a continuous range of non-transparent pixels
76 int x0 = x;
77 while ( x < width)
78 {
79 unsigned char R = image.GetRed(x,y);
80 unsigned char G = image.GetGreen(x,y);
81 unsigned char B = image.GetBlue(x,y);
82 if (( R >= loR && R <= hiR) &&
83 ( G >= loG && G <= hiG) &&
84 ( B >= loB && B <= hiB)) // It's transparent
85 break;
86 x++;
87 }
88
89 // Add the run of non-transparent pixels (if any) to the region
90 if (x > x0) {
91 rect.x = x0;
92 rect.width = x - x0;
93 region.Union(rect);
94 }
95 }
96 }
97
98 return true;
99 }
100
101
102 bool wxRegion::Union(const wxBitmap& bmp)
103 {
104 #if (!defined(__WXMSW__) || wxUSE_WXDIB)
105 if (bmp.GetMask())
106 {
107 wxImage image = bmp.ConvertToImage();
108 wxASSERT_MSG( image.HasMask(), _T("wxBitmap::ConvertToImage doesn't preserve mask?") );
109 return DoRegionUnion(*this, image,
110 image.GetMaskRed(),
111 image.GetMaskGreen(),
112 image.GetMaskBlue(),
113 0);
114 }
115 else
116 #endif
117 {
118 return Union(0, 0, bmp.GetWidth(), bmp.GetHeight());
119 }
120 }
121
122 bool wxRegion::Union(const wxBitmap& bmp,
123 const wxColour& transColour,
124 int tolerance)
125 {
126 #if (!defined(__WXMSW__) || wxUSE_WXDIB)
127 wxImage image = bmp.ConvertToImage();
128 return DoRegionUnion(*this, image,
129 transColour.Red(),
130 transColour.Green(),
131 transColour.Blue(),
132 tolerance);
133 #else
134 return false;
135 #endif
136 }
137
138 #else
139
140 bool wxRegion::Union(const wxBitmap& WXUNUSED(bmp))
141 {
142 // No wxImage support
143 return false;
144 }
145
146 bool wxRegion::Union(const wxBitmap& WXUNUSED(bmp),
147 const wxColour& WXUNUSED(transColour),
148 int WXUNUSED(tolerance))
149 {
150 // No wxImage support
151 return false;
152 }
153
154 #endif