]>
git.saurik.com Git - wxWidgets.git/blob - src/msw/pen.cpp
12dd825ec721432409e90562b81f387709c2a7c8
1 /////////////////////////////////////////////////////////////////////////////
4 // Author: Julian Smart
8 // Copyright: (c) Julian Smart and Markus Holzem
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
13 #pragma implementation "pen.h"
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
32 #include "wx/msw/private.h"
35 #if !USE_SHARED_LIBRARIES
36 IMPLEMENT_DYNAMIC_CLASS(wxPen
, wxGDIObject
)
39 wxPenRefData::wxPenRefData(void)
44 m_join
= wxJOIN_ROUND
;
51 wxPenRefData::~wxPenRefData(void)
54 ::DeleteObject((HPEN
) m_hPen
);
62 wxThePenList
->AddPen(this);
68 wxThePenList
->RemovePen(this);
71 // Should implement Create
72 wxPen::wxPen(const wxColour
& col
, const int Width
, const int Style
)
74 m_refData
= new wxPenRefData
;
76 M_PENDATA
->m_colour
= col
;
77 // M_PENDATA->m_stipple = NULL;
78 M_PENDATA
->m_width
= Width
;
79 M_PENDATA
->m_style
= Style
;
80 M_PENDATA
->m_join
= wxJOIN_ROUND
;
81 M_PENDATA
->m_cap
= wxCAP_ROUND
;
82 M_PENDATA
->m_nbDash
= 0 ;
83 M_PENDATA
->m_dash
= 0 ;
84 M_PENDATA
->m_hPen
= 0 ;
87 // In Windows, only a pen of width = 1 can be dotted or dashed!
88 if ((Style
== wxDOT
) || (Style
== wxLONG_DASH
) ||
89 (Style
== wxSHORT_DASH
) || (Style
== wxDOT_DASH
) ||
90 (Style
== wxUSER_DASH
))
91 M_PENDATA
->m_width
= 1;
94 DWORD vers = GetVersion() ;
95 WORD high = HIWORD(vers) ; // high bit=0 for NT, 1 for Win32s
96 // Win32s doesn't support wide dashed pens
100 if (wxGetOsVersion()==wxWIN32S
)
102 // In Windows, only a pen of width = 1 can be dotted or dashed!
103 if ((Style
== wxDOT
) || (Style
== wxLONG_DASH
) ||
104 (Style
== wxSHORT_DASH
) || (Style
== wxDOT_DASH
) ||
105 (Style
== wxUSER_DASH
))
106 M_PENDATA
->m_width
= 1;
112 wxThePenList
->AddPen(this);
115 wxPen::wxPen(const wxBitmap
& stipple
, const int Width
)
117 m_refData
= new wxPenRefData
;
119 // M_PENDATA->m_colour = col;
120 M_PENDATA
->m_stipple
= stipple
;
121 M_PENDATA
->m_width
= Width
;
122 M_PENDATA
->m_style
= wxSTIPPLE
;
123 M_PENDATA
->m_join
= wxJOIN_ROUND
;
124 M_PENDATA
->m_cap
= wxCAP_ROUND
;
125 M_PENDATA
->m_nbDash
= 0 ;
126 M_PENDATA
->m_dash
= 0 ;
127 M_PENDATA
->m_hPen
= 0 ;
132 wxThePenList
->AddPen(this);
135 wxPen::wxPen(const wxString
& col
, const int Width
, const int Style
)
137 m_refData
= new wxPenRefData
;
139 M_PENDATA
->m_colour
= col
;
140 // M_PENDATA->m_stipple = NULL ;
141 M_PENDATA
->m_width
= Width
;
142 M_PENDATA
->m_style
= Style
;
143 M_PENDATA
->m_join
= wxJOIN_ROUND
;
144 M_PENDATA
->m_cap
= wxCAP_ROUND
;
145 M_PENDATA
->m_nbDash
= 0 ;
146 M_PENDATA
->m_dash
= 0 ;
147 M_PENDATA
->m_hPen
= 0 ;
149 // In Windows, only a pen of width = 1 can be dotted or dashed!
150 if ((Style
== wxDOT
) || (Style
== wxLONG_DASH
) || (Style
== wxSHORT_DASH
) || (Style
== wxDOT_DASH
))
151 M_PENDATA
->m_width
= 1;
156 wxThePenList
->AddPen(this);
159 bool wxPen::RealizeResource(void)
161 if (M_PENDATA
&& (M_PENDATA
->m_hPen
== 0))
163 if (M_PENDATA
->m_style
==wxTRANSPARENT
)
165 M_PENDATA
->m_hPen
= (WXHPEN
) ::GetStockObject(NULL_PEN
);
169 COLORREF ms_colour
= 0 ;
170 ms_colour
= M_PENDATA
->m_colour
.GetPixel() ;
172 // Join style, Cap style, Pen Stippling only on Win32.
173 // Currently no time to find equivalent on Win3.1, sorry
174 // [if such equiv exist!!]
176 if (M_PENDATA
->m_join
==wxJOIN_ROUND
&&
177 M_PENDATA
->m_cap
==wxCAP_ROUND
&&
178 M_PENDATA
->m_style
!=wxUSER_DASH
&&
179 M_PENDATA
->m_style
!=wxSTIPPLE
181 M_PENDATA
->m_hPen
= (WXHPEN
) CreatePen(wx2msPenStyle(M_PENDATA
->m_style
), M_PENDATA
->m_width
, ms_colour
);
184 DWORD ms_style
= PS_GEOMETRIC
|wx2msPenStyle(M_PENDATA
->m_style
) ;
188 switch(M_PENDATA
->m_join
)
190 case wxJOIN_BEVEL
: ms_style
|= PS_JOIN_BEVEL
; break ;
191 case wxJOIN_MITER
: ms_style
|= PS_JOIN_MITER
; break ;
193 case wxJOIN_ROUND
: ms_style
|= PS_JOIN_ROUND
; break ;
196 switch(M_PENDATA
->m_cap
)
198 case wxCAP_PROJECTING
: ms_style
|= PS_ENDCAP_SQUARE
; break ;
199 case wxCAP_BUTT
: ms_style
|= PS_ENDCAP_FLAT
; break ;
201 case wxCAP_ROUND
: ms_style
|= PS_ENDCAP_ROUND
; break ;
204 switch(M_PENDATA
->m_style
)
207 logb
.lbStyle
= BS_PATTERN
;
208 if (M_PENDATA
->m_stipple
.Ok())
209 logb
.lbHatch
= (LONG
)M_PENDATA
->m_stipple
.GetHBITMAP() ;
211 logb
.lbHatch
= (LONG
)0 ;
213 case wxBDIAGONAL_HATCH
:
214 logb
.lbStyle
= BS_HATCHED
;
215 logb
.lbHatch
= HS_BDIAGONAL
;
217 case wxCROSSDIAG_HATCH
:
218 logb
.lbStyle
= BS_HATCHED
;
219 logb
.lbHatch
= HS_DIAGCROSS
;
221 case wxFDIAGONAL_HATCH
:
222 logb
.lbStyle
= BS_HATCHED
;
223 logb
.lbHatch
= HS_FDIAGONAL
;
226 logb
.lbStyle
= BS_HATCHED
;
227 logb
.lbHatch
= HS_CROSS
;
229 case wxHORIZONTAL_HATCH
:
230 logb
.lbStyle
= BS_HATCHED
;
231 logb
.lbHatch
= HS_HORIZONTAL
;
233 case wxVERTICAL_HATCH
:
234 logb
.lbStyle
= BS_HATCHED
;
235 logb
.lbHatch
= HS_VERTICAL
;
238 logb
.lbStyle
= BS_SOLID
;
241 logb
.lbColor
= ms_colour
;
243 if (M_PENDATA
->m_style
==wxUSER_DASH
&& M_PENDATA
->m_nbDash
&& M_PENDATA
->m_dash
)
245 real_dash
= new wxDash
[M_PENDATA
->m_nbDash
] ;
247 for (i
=0;i
<M_PENDATA
->m_nbDash
;i
++)
248 real_dash
[i
] = M_PENDATA
->m_dash
[i
] * M_PENDATA
->m_width
;
253 // Win32s doesn't have ExtCreatePen function...
254 if (wxGetOsVersion()==wxWINDOWS_NT
|| wxGetOsVersion()==wxWIN95
)
255 M_PENDATA
->m_hPen
= (WXHPEN
) ExtCreatePen(ms_style
,M_PENDATA
->m_width
,&logb
,
256 M_PENDATA
->m_style
==wxUSER_DASH
? M_PENDATA
->m_nbDash
:0, (const DWORD
*)real_dash
);
258 M_PENDATA
->m_hPen
= (WXHPEN
) CreatePen(wx2msPenStyle(M_PENDATA
->m_style
), M_PENDATA
->m_width
, ms_colour
);
261 delete [] real_dash
;
264 M_PENDATA
->m_hPen
= (WXHPEN
) CreatePen(wx2msPenStyle(M_PENDATA
->m_style
), M_PENDATA
->m_width
, ms_colour
);
267 if (M_PENDATA
->m_hPen
==0)
268 wxError("Cannot create pen","Internal error") ;
275 WXHANDLE
wxPen::GetResourceHandle(void)
280 return (WXHANDLE
)M_PENDATA
->m_hPen
;
283 bool wxPen::FreeResource(bool force
)
285 if (M_PENDATA
&& (M_PENDATA
->m_hPen
!= 0))
287 DeleteObject((HPEN
) M_PENDATA
->m_hPen
);
288 M_PENDATA
->m_hPen
= 0;
295 bool wxPen::UseResource(void)
297 IncrementResourceUsage();
301 bool wxPen::ReleaseResource(void)
303 DecrementResourceUsage();
308 bool wxPen::IsFree(void)
310 return (M_PENDATA
&& M_PENDATA
->m_hPen
== 0);
313 void wxPen::SetColour(const wxColour
& col
)
316 m_refData
= new wxPenRefData
;
318 M_PENDATA
->m_colour
= col
;
324 void wxPen::SetColour(const wxString
& col
)
327 m_refData
= new wxPenRefData
;
329 M_PENDATA
->m_colour
= col
;
335 void wxPen::SetColour(const unsigned char r
, const unsigned char g
, const unsigned char b
)
338 m_refData
= new wxPenRefData
;
340 M_PENDATA
->m_colour
.Set(r
, g
, b
);
346 void wxPen::SetWidth(const int Width
)
349 m_refData
= new wxPenRefData
;
351 M_PENDATA
->m_width
= Width
;
357 void wxPen::SetStyle(const int Style
)
360 m_refData
= new wxPenRefData
;
362 M_PENDATA
->m_style
= Style
;
368 void wxPen::SetStipple(const wxBitmap
& Stipple
)
371 m_refData
= new wxPenRefData
;
373 M_PENDATA
->m_stipple
= Stipple
;
374 M_PENDATA
->m_style
= wxSTIPPLE
;
380 void wxPen::SetDashes(const int nb_dashes
, const wxDash
*Dash
)
383 m_refData
= new wxPenRefData
;
385 M_PENDATA
->m_nbDash
= nb_dashes
;
386 M_PENDATA
->m_dash
= (wxDash
*)Dash
;
392 void wxPen::SetJoin(const int Join
)
395 m_refData
= new wxPenRefData
;
397 M_PENDATA
->m_join
= Join
;
403 void wxPen::SetCap(const int Cap
)
406 m_refData
= new wxPenRefData
;
408 M_PENDATA
->m_cap
= Cap
;
414 int wx2msPenStyle(int wx_style
)
419 DWORD vers = GetVersion() ;
420 WORD high = HIWORD(vers) ; // high bit=0 for NT, 1 for Win32s
436 // User dash style not supported on Win3.1, sorry...
438 // Win32s doesn't have PS_USERSTYLE
440 if ((high&0x8000)==0)
442 if (wxGetOsVersion()==wxWINDOWS_NT
)
443 cstyle
= PS_USERSTYLE
;
445 cstyle
= PS_DOT
; // We must make a choice... This is mine!