]> git.saurik.com Git - wxWidgets.git/blame - src/gtk1/colour.cpp
Start/EndDrawingOnTop are still used under Motif, don't deprecate them
[wxWidgets.git] / src / gtk1 / colour.cpp
CommitLineData
c801d85f 1/////////////////////////////////////////////////////////////////////////////
edc536d3 2// Name: src/gtk/colour.cpp
c801d85f
KB
3// Purpose:
4// Author: Robert Roebling
dbf858b5
RR
5// Id: $Id$
6// Copyright: (c) 1998 Robert Roebling
65571936 7// Licence: wxWindows licence
c801d85f
KB
8/////////////////////////////////////////////////////////////////////////////
9
14f355c2
VS
10// For compilers that support precompilation, includes "wx.h".
11#include "wx/wxprec.h"
12
ed39ff57 13#include "wx/colour.h"
e1bf3ad3 14#include "wx/gdicmn.h"
2b5f62a0 15#include "wx/gtk/private.h"
c801d85f 16
071a2d78 17#include <gdk/gdk.h>
307fc8d5 18#include <gdk/gdkx.h>
071a2d78 19#include <gdk/gdkprivate.h>
c801d85f
KB
20
21//-----------------------------------------------------------------------------
22// wxColour
23//-----------------------------------------------------------------------------
24
25class wxColourRefData: public wxObjectRefData
26{
47c93b63 27public:
c89f5c02
RR
28 wxColourRefData()
29 {
30 m_color.red = 0;
31 m_color.green = 0;
32 m_color.blue = 0;
33 m_color.pixel = 0;
34 m_colormap = (GdkColormap *) NULL;
aad6765c 35 m_hasPixel = false;
c89f5c02 36 }
4e6b8309 37
dbb846c6 38 wxColourRefData(const wxColourRefData& data)
d84afea9 39 : wxObjectRefData()
dbb846c6
VZ
40 {
41 m_color = data.m_color;
42 m_colormap = data.m_colormap;
43 m_hasPixel = data.m_hasPixel;
44 }
45
c89f5c02
RR
46 ~wxColourRefData()
47 {
48 FreeColour();
49 }
15248e43 50
c89f5c02
RR
51 bool operator == (const wxColourRefData& data) const
52 {
53 return (m_colormap == data.m_colormap &&
54 m_hasPixel == data.m_hasPixel &&
55 m_color.red == data.m_color.red &&
56 m_color.green == data.m_color.green &&
57 m_color.blue == data.m_color.blue &&
58 m_color.pixel == data.m_color.pixel);
59 }
4e6b8309 60
68dda785 61 void FreeColour();
d13fd3e4 62 void AllocColour( GdkColormap* cmap );
8bbe427f 63
c801d85f
KB
64 GdkColor m_color;
65 GdkColormap *m_colormap;
66 bool m_hasPixel;
8bbe427f 67
f6bcfd97 68 friend class wxColour;
d13fd3e4
VZ
69
70 // reference counter for systems with <= 8-Bit display
71 static gushort colMapAllocCounter[ 256 ];
72};
73
4e6b8309
VZ
74gushort wxColourRefData::colMapAllocCounter[ 256 ] =
75{
d13fd3e4
VZ
76 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
77 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
78 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
79 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
80 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
81 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
82 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
83 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
84 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
85 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
86 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
87 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
88 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
c801d85f
KB
89};
90
68dda785 91void wxColourRefData::FreeColour()
c801d85f 92{
47c93b63
RR
93 if (m_colormap)
94 {
95#ifdef __WXGTK20__
96 if ((m_colormap->visual->type == GDK_VISUAL_GRAYSCALE) ||
97 (m_colormap->visual->type == GDK_VISUAL_PSEUDO_COLOR))
98#else
99 GdkColormapPrivate *private_colormap = (GdkColormapPrivate*) m_colormap;
100 if ((private_colormap->visual->type == GDK_VISUAL_GRAYSCALE) ||
101 (private_colormap->visual->type == GDK_VISUAL_PSEUDO_COLOR))
102#endif
103 {
d13fd3e4
VZ
104 int idx = m_color.pixel;
105 colMapAllocCounter[ idx ] = colMapAllocCounter[ idx ] - 1;
4e6b8309 106
d13fd3e4 107 if (colMapAllocCounter[ idx ] == 0)
0a164d4c 108 gdk_colormap_free_colors( m_colormap, &m_color, 1 );
47c93b63
RR
109 }
110 }
ff7b1510 111}
c801d85f 112
d13fd3e4
VZ
113void wxColourRefData::AllocColour( GdkColormap *cmap )
114{
115 if (m_hasPixel && (m_colormap == cmap))
116 return;
117
118 FreeColour();
4e6b8309 119
d13fd3e4 120#ifdef __WXGTK20__
31c8af3a 121 if ( (cmap->visual->type == GDK_VISUAL_GRAYSCALE) ||
0a164d4c 122 (cmap->visual->type == GDK_VISUAL_PSEUDO_COLOR) )
d13fd3e4
VZ
123#else
124 GdkColormapPrivate *private_colormap = (GdkColormapPrivate*) cmap;
125 if ((private_colormap->visual->type == GDK_VISUAL_GRAYSCALE) ||
126 (private_colormap->visual->type == GDK_VISUAL_PSEUDO_COLOR))
127#endif
128 {
129 m_hasPixel = gdk_colormap_alloc_color( cmap, &m_color, FALSE, TRUE );
130 int idx = m_color.pixel;
131 colMapAllocCounter[ idx ] = colMapAllocCounter[ idx ] + 1;
132 }
133 else
134 {
135 m_hasPixel = gdk_color_alloc( cmap, &m_color );
136 }
137 m_colormap = cmap;
138}
139
c801d85f
KB
140//-----------------------------------------------------------------------------
141
142#define M_COLDATA ((wxColourRefData *)m_refData)
143
3b9faf4c
VS
144// GDK's values are in 0..65535 range, our are in 0..255
145#define SHIFT 8
c801d85f
KB
146
147IMPLEMENT_DYNAMIC_CLASS(wxColour,wxGDIObject)
148
4b5f3fe6 149wxColour::wxColour( unsigned char red, unsigned char green, unsigned char blue )
c801d85f 150{
1ecc4d80
RR
151 m_refData = new wxColourRefData();
152 M_COLDATA->m_color.red = ((unsigned short)red) << SHIFT;
153 M_COLDATA->m_color.green = ((unsigned short)green) << SHIFT;
154 M_COLDATA->m_color.blue = ((unsigned short)blue) << SHIFT;
155 M_COLDATA->m_color.pixel = 0;
ff7b1510 156}
8bbe427f 157
4e6b8309
VZ
158/* static */
159wxColour wxColour::CreateByName(const wxString& name)
160{
161 wxColour col;
162
163 GdkColor colGDK;
164 if ( gdk_color_parse( wxGTK_CONV( name ), &colGDK ) )
165 {
166 wxColourRefData *refData = new wxColourRefData;
167 refData->m_color = colGDK;
168 col.m_refData = refData;
169 }
170
171 return col;
172}
222ed1d6
MB
173
174
68dda785 175void wxColour::InitFromName( const wxString &colourName )
c801d85f 176{
4e6b8309
VZ
177 // check the cache first
178 wxColour col;
179 if ( wxTheColourDatabase )
c801d85f 180 {
4e6b8309 181 col = wxTheColourDatabase->Find(colourName);
1ecc4d80 182 }
15248e43 183
4e6b8309
VZ
184 if ( !col.Ok() )
185 {
186 col = CreateByName(colourName);
187 }
15248e43 188
4e6b8309
VZ
189 if ( col.Ok() )
190 {
191 *this = col;
192 }
193 else
194 {
195 wxFAIL_MSG( wxT("wxColour: couldn't find colour") );
ff7b1510 196 }
ff7b1510 197}
c801d85f 198
68dda785 199wxColour::~wxColour()
c801d85f 200{
ff7b1510 201}
c801d85f 202
33b64e6f 203bool wxColour::operator == ( const wxColour& col ) const
8bbe427f 204{
4e6b8309 205 if (m_refData == col.m_refData)
aad6765c 206 return true;
15248e43 207
4e6b8309 208 if (!m_refData || !col.m_refData)
aad6765c 209 return false;
15248e43 210
2b62ab35
RR
211 GdkColor *own = &(((wxColourRefData*)m_refData)->m_color);
212 GdkColor *other = &(((wxColourRefData*)col.m_refData)->m_color);
4e6b8309
VZ
213 return own->red == other->red &&
214 own->blue == other->blue &&
215 own->green == other->green;
ff7b1510 216}
c801d85f 217
c89f5c02
RR
218wxObjectRefData *wxColour::CreateRefData() const
219{
220 return new wxColourRefData;
221}
222
223wxObjectRefData *wxColour::CloneRefData(const wxObjectRefData *data) const
8bbe427f 224{
c89f5c02 225 return new wxColourRefData(*(wxColourRefData *)data);
ff7b1510 226}
c801d85f 227
4b5f3fe6 228void wxColour::Set( unsigned char red, unsigned char green, unsigned char blue )
c801d85f 229{
c89f5c02 230 AllocExclusive();
4e6b8309 231
1ecc4d80
RR
232 M_COLDATA->m_color.red = ((unsigned short)red) << SHIFT;
233 M_COLDATA->m_color.green = ((unsigned short)green) << SHIFT;
234 M_COLDATA->m_color.blue = ((unsigned short)blue) << SHIFT;
235 M_COLDATA->m_color.pixel = 0;
4e6b8309 236
2b5f62a0 237 M_COLDATA->m_colormap = (GdkColormap*) NULL;
aad6765c 238 M_COLDATA->m_hasPixel = false;
ff7b1510 239}
c801d85f 240
68dda785 241unsigned char wxColour::Red() const
c801d85f 242{
223d09f6 243 wxCHECK_MSG( Ok(), 0, wxT("invalid colour") );
8bbe427f 244
1ecc4d80 245 return (unsigned char)(M_COLDATA->m_color.red >> SHIFT);
ff7b1510 246}
c801d85f 247
68dda785 248unsigned char wxColour::Green() const
c801d85f 249{
223d09f6 250 wxCHECK_MSG( Ok(), 0, wxT("invalid colour") );
8bbe427f 251
1ecc4d80 252 return (unsigned char)(M_COLDATA->m_color.green >> SHIFT);
ff7b1510 253}
c801d85f 254
68dda785 255unsigned char wxColour::Blue() const
c801d85f 256{
223d09f6 257 wxCHECK_MSG( Ok(), 0, wxT("invalid colour") );
8bbe427f 258
1ecc4d80 259 return (unsigned char)(M_COLDATA->m_color.blue >> SHIFT);
ff7b1510 260}
c801d85f 261
c801d85f
KB
262void wxColour::CalcPixel( GdkColormap *cmap )
263{
1ecc4d80 264 if (!Ok()) return;
8bbe427f 265
d13fd3e4 266 M_COLDATA->AllocColour( cmap );
ff7b1510 267}
c801d85f 268
68dda785 269int wxColour::GetPixel() const
c801d85f 270{
223d09f6 271 wxCHECK_MSG( Ok(), 0, wxT("invalid colour") );
8bbe427f 272
1ecc4d80 273 return M_COLDATA->m_color.pixel;
ff7b1510 274}
c801d85f 275
68dda785 276GdkColor *wxColour::GetColor() const
c801d85f 277{
223d09f6 278 wxCHECK_MSG( Ok(), (GdkColor *) NULL, wxT("invalid colour") );
8bbe427f 279
1ecc4d80 280 return &M_COLDATA->m_color;
ff7b1510 281}