HDC() fix was wrong, may have been just a problem with mismatched parens.
[wxWidgets.git] / src / msw / renderer.cpp
1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: src/msw/renderer.cpp
3 // Purpose: implementation of wxRendererNative for Windows
4 // Author: Vadim Zeitlin
5 // Modified by:
6 // Created: 20.07.2003
7 // RCS-ID: $Id$
8 // Copyright: (c) 2003 Vadim Zeitlin <vadim@wxwindows.org>
9 // License: wxWindows licence
10 ///////////////////////////////////////////////////////////////////////////////
11
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 // for compilers that support precompilation, includes "wx.h".
21 #include "wx/wxprec.h"
22
23 #ifdef __BORLANDC__
24 #pragma hdrstop
25 #endif
26
27 #ifndef WX_PRECOMP
28 #include "wx/string.h"
29 #include "wx/window.h"
30 #include "wx/dc.h"
31 #include "wx/settings.h"
32 #endif //WX_PRECOMP
33
34 #include "wx/scopeguard.h"
35 #include "wx/splitter.h"
36 #include "wx/renderer.h"
37 #include "wx/msw/private.h"
38 #include "wx/msw/dc.h"
39 #include "wx/msw/uxtheme.h"
40
41 #if wxUSE_GRAPHICS_CONTEXT
42 // TODO remove this dependency (gdiplus needs the macros)
43 #ifndef max
44 #define max(a,b) (((a) > (b)) ? (a) : (b))
45 #endif
46
47 #ifndef min
48 #define min(a,b) (((a) < (b)) ? (a) : (b))
49 #endif
50
51 #include "gdiplus.h"
52 using namespace Gdiplus;
53 #endif
54
55 // tmschema.h is in Win32 Platform SDK and might not be available with earlier
56 // compilers
57 #ifndef CP_DROPDOWNBUTTON
58 #define BP_PUSHBUTTON 1
59 #define BP_RADIOBUTTON 2
60 #define BP_CHECKBOX 3
61 #define RBS_UNCHECKEDNORMAL 1
62 #define RBS_CHECKEDNORMAL (RBS_UNCHECKEDNORMAL + 4)
63 #define RBS_MIXEDNORMAL (RBS_CHECKEDNORMAL + 4)
64 #define CBS_UNCHECKEDNORMAL 1
65 #define CBS_CHECKEDNORMAL (CBS_UNCHECKEDNORMAL + 4)
66 #define CBS_MIXEDNORMAL (CBS_CHECKEDNORMAL + 4)
67
68 #define PBS_NORMAL 1
69 #define PBS_HOT 2
70 #define PBS_PRESSED 3
71 #define PBS_DISABLED 4
72 #define PBS_DEFAULTED 5
73
74 #define CP_DROPDOWNBUTTON 1
75
76 #define CBXS_NORMAL 1
77 #define CBXS_HOT 2
78 #define CBXS_PRESSED 3
79 #define CBXS_DISABLED 4
80
81 #define TVP_GLYPH 2
82
83 #define GLPS_CLOSED 1
84 #define GLPS_OPENED 2
85
86 #define HP_HEADERITEM 1
87
88 #define HIS_NORMAL 1
89 #define HIS_HOT 2
90 #define HIS_PRESSED 3
91
92 #define TMT_HEIGHT 2417
93
94 #define HP_HEADERSORTARROW 4
95 #define HSAS_SORTEDUP 1
96 #define HSAS_SORTEDDOWN 2
97
98 #define EP_EDITTEXT 1
99 #define ETS_NORMAL 1
100 #define ETS_HOT 2
101 #define ETS_SELECTED 3
102 #define ETS_DISABLED 4
103 #define ETS_FOCUSED 5
104 #define ETS_READONLY 6
105 #define ETS_ASSIST 7
106 #define TMT_FILLCOLOR 3802
107 #define TMT_TEXTCOLOR 3803
108 #define TMT_BORDERCOLOR 3801
109 #define TMT_EDGEFILLCOLOR 3808
110 #endif
111
112
113 // ----------------------------------------------------------------------------
114 // If the DC is a wxGCDC then pull out the HDC from the GraphicsContext when
115 // it is needed, and handle the Release when done.
116
117 class GraphicsHDC
118 {
119 public:
120 GraphicsHDC(wxDC* dc)
121 {
122 #if wxUSE_GRAPHICS_CONTEXT
123 m_graphics = NULL;
124 wxGCDC* gcdc = wxDynamicCast(dc, wxGCDC);
125 if (gcdc) {
126 m_graphics = (Graphics*)gcdc->GetGraphicsContext()->GetNativeContext();
127 m_hdc = m_graphics->GetHDC();
128 }
129 else
130 #endif
131 m_hdc = GetHdcOf(*dc);
132 }
133
134 ~GraphicsHDC()
135 {
136 #if wxUSE_GRAPHICS_CONTEXT
137 if (m_graphics)
138 m_graphics->ReleaseHDC(m_hdc);
139 #endif
140 }
141
142 operator HDC() const { return m_hdc; }
143
144 private:
145 HDC m_hdc;
146 #if wxUSE_GRAPHICS_CONTEXT
147 Graphics* m_graphics;
148 #endif
149 };
150
151 #if defined(__WXWINCE__)
152 #ifndef DFCS_FLAT
153 #define DFCS_FLAT 0
154 #endif
155 #ifndef DFCS_MONO
156 #define DFCS_MONO 0
157 #endif
158 #endif
159
160 #ifndef DFCS_HOT
161 #define DFCS_HOT 0x1000
162 #endif
163
164 // ----------------------------------------------------------------------------
165 // wxRendererMSW: wxRendererNative implementation for "old" Win32 systems
166 // ----------------------------------------------------------------------------
167
168 class WXDLLEXPORT wxRendererMSW : public wxDelegateRendererNative
169 {
170 public:
171 wxRendererMSW() { }
172
173 static wxRendererNative& Get();
174
175 virtual void DrawComboBoxDropButton(wxWindow *win,
176 wxDC& dc,
177 const wxRect& rect,
178 int flags = 0);
179
180 virtual void DrawCheckBox(wxWindow *win,
181 wxDC& dc,
182 const wxRect& rect,
183 int flags = 0);
184
185 virtual void DrawPushButton(wxWindow *win,
186 wxDC& dc,
187 const wxRect& rect,
188 int flags = 0);
189
190 virtual void DrawFocusRect(wxWindow* win,
191 wxDC& dc,
192 const wxRect& rect,
193 int flags = 0);
194
195 virtual void DrawChoice(wxWindow* win,
196 wxDC& dc,
197 const wxRect& rect,
198 int flags=0);
199
200 virtual void DrawComboBox(wxWindow* win,
201 wxDC& dc,
202 const wxRect& rect,
203 int flags=0);
204
205 virtual void DrawTextCtrl(wxWindow* win,
206 wxDC& dc,
207 const wxRect& rect,
208 int flags=0);
209
210 virtual void DrawRadioButton(wxWindow* win,
211 wxDC& dc,
212 const wxRect& rect,
213 int flags=0);
214
215 virtual wxSize GetCheckBoxSize(wxWindow *win);
216
217 virtual int GetHeaderButtonHeight(wxWindow *win);
218
219 private:
220 DECLARE_NO_COPY_CLASS(wxRendererMSW)
221 };
222
223 // ----------------------------------------------------------------------------
224 // wxRendererXP: wxRendererNative implementation for Windows XP and later
225 // ----------------------------------------------------------------------------
226
227 #if wxUSE_UXTHEME
228
229 class WXDLLEXPORT wxRendererXP : public wxDelegateRendererNative
230 {
231 public:
232 wxRendererXP() : wxDelegateRendererNative(wxRendererMSW::Get()) { }
233
234 static wxRendererNative& Get();
235
236 virtual int DrawHeaderButton(wxWindow *win,
237 wxDC& dc,
238 const wxRect& rect,
239 int flags = 0,
240 wxHeaderSortIconType sortArrow = wxHDR_SORT_ICON_NONE,
241 wxHeaderButtonParams* params = NULL);
242
243 virtual void DrawTreeItemButton(wxWindow *win,
244 wxDC& dc,
245 const wxRect& rect,
246 int flags = 0);
247 virtual void DrawSplitterBorder(wxWindow *win,
248 wxDC& dc,
249 const wxRect& rect,
250 int flags = 0);
251 virtual void DrawSplitterSash(wxWindow *win,
252 wxDC& dc,
253 const wxSize& size,
254 wxCoord position,
255 wxOrientation orient,
256 int flags = 0);
257 virtual void DrawComboBoxDropButton(wxWindow *win,
258 wxDC& dc,
259 const wxRect& rect,
260 int flags = 0);
261 virtual void DrawCheckBox(wxWindow *win,
262 wxDC& dc,
263 const wxRect& rect,
264 int flags = 0);
265
266 virtual void DrawPushButton(wxWindow *win,
267 wxDC& dc,
268 const wxRect& rect,
269 int flags = 0);
270
271 virtual void DrawItemSelectionRect(wxWindow *win,
272 wxDC& dc,
273 const wxRect& rect,
274 int flags = 0 );
275
276
277 virtual wxSplitterRenderParams GetSplitterParams(const wxWindow *win);
278 private:
279 DECLARE_NO_COPY_CLASS(wxRendererXP)
280 };
281
282 #endif // wxUSE_UXTHEME
283
284 // ============================================================================
285 // wxRendererNative and wxRendererMSW implementation
286 // ============================================================================
287
288 /* static */
289 wxRendererNative& wxRendererNative::GetDefault()
290 {
291 #if wxUSE_UXTHEME
292 wxUxThemeEngine *themeEngine = wxUxThemeEngine::Get();
293 if ( themeEngine && themeEngine->IsAppThemed() )
294 return wxRendererXP::Get();
295 #endif // wxUSE_UXTHEME
296
297 return wxRendererMSW::Get();
298 }
299
300 /* static */
301 wxRendererNative& wxRendererMSW::Get()
302 {
303 static wxRendererMSW s_rendererMSW;
304
305 return s_rendererMSW;
306 }
307
308 void
309 wxRendererMSW::DrawComboBoxDropButton(wxWindow * WXUNUSED(win),
310 wxDC& dc,
311 const wxRect& rect,
312 int flags)
313 {
314 RECT r;
315 wxCopyRectToRECT(rect, r);
316
317 int style = DFCS_SCROLLCOMBOBOX;
318 if ( flags & wxCONTROL_DISABLED )
319 style |= DFCS_INACTIVE;
320 if ( flags & wxCONTROL_PRESSED )
321 style |= DFCS_PUSHED | DFCS_FLAT;
322
323 ::DrawFrameControl(GraphicsHDC((wxMSWDCImpl*)dc.GetImpl()), &r, DFC_SCROLL, style);
324 }
325
326 void
327 wxRendererMSW::DrawCheckBox(wxWindow * WXUNUSED(win),
328 wxDC& dc,
329 const wxRect& rect,
330 int flags)
331 {
332 RECT r;
333 wxCopyRectToRECT(rect, r);
334
335 int style = DFCS_BUTTONCHECK;
336 if ( flags & wxCONTROL_CHECKED )
337 style |= DFCS_CHECKED;
338 if ( flags & wxCONTROL_DISABLED )
339 style |= DFCS_INACTIVE;
340 if ( flags & wxCONTROL_FLAT )
341 style |= DFCS_MONO;
342 if ( flags & wxCONTROL_PRESSED )
343 style |= DFCS_PUSHED;
344 if ( flags & wxCONTROL_CURRENT )
345 style |= DFCS_HOT;
346
347 ::DrawFrameControl(GraphicsHDC((wxMSWDCImpl*)dc.GetImpl()), &r, DFC_BUTTON, style);
348 }
349
350 void
351 wxRendererMSW::DrawPushButton(wxWindow * WXUNUSED(win),
352 wxDC& dc,
353 const wxRect& rectOrig,
354 int flags)
355 {
356 wxRect rect(rectOrig);
357
358 int style = DFCS_BUTTONPUSH;
359 if ( flags & wxCONTROL_DISABLED )
360 style |= DFCS_INACTIVE;
361 if ( flags & wxCONTROL_PRESSED )
362 style |= DFCS_PUSHED | DFCS_FLAT;
363 if ( flags & wxCONTROL_ISDEFAULT )
364 {
365 // DrawFrameControl() doesn't seem to support default buttons so we
366 // have to draw the border ourselves
367 wxDCPenChanger pen(dc, *wxBLACK_PEN);
368 wxDCBrushChanger brush(dc, *wxTRANSPARENT_BRUSH);
369 dc.DrawRectangle(rect);
370 rect.Deflate(1);
371 }
372
373 RECT rc;
374 wxCopyRectToRECT(rect, rc);
375
376 ::DrawFrameControl(GraphicsHDC((wxMSWDCImpl*)dc.GetImpl()), &rc, DFC_BUTTON, style);
377 }
378
379 void wxRendererMSW::DrawFocusRect(wxWindow * WXUNUSED(win),
380 wxDC& dc,
381 const wxRect& rect,
382 int WXUNUSED(flags))
383 {
384 RECT rc;
385 wxCopyRectToRECT(rect, rc);
386
387 ::DrawFocusRect(GraphicsHDC((wxMSWDCImpl*)dc.GetImpl()), &rc);
388 }
389
390 wxSize wxRendererMSW::GetCheckBoxSize(wxWindow * WXUNUSED(win))
391 {
392 return wxSize(::GetSystemMetrics(SM_CXMENUCHECK),
393 ::GetSystemMetrics(SM_CYMENUCHECK));
394 }
395
396 int wxRendererMSW::GetHeaderButtonHeight(wxWindow * WXUNUSED(win))
397 {
398 // some "reasonable" value returned in case of error, it doesn't really
399 // correspond to anything but it's better than returning 0
400 static const int DEFAULT_HEIGHT = 20;
401
402
403 // create a temporary header window just to get its geometry
404 HWND hwndHeader = ::CreateWindow(WC_HEADER, NULL, 0,
405 0, 0, 0, 0, NULL, NULL, NULL, NULL);
406 if ( !hwndHeader )
407 return DEFAULT_HEIGHT;
408
409 wxON_BLOCK_EXIT1( ::DestroyWindow, hwndHeader );
410
411 // initialize the struct filled with the values by Header_Layout()
412 RECT parentRect = { 0, 0, 100, 100 };
413 WINDOWPOS wp = { 0, 0, 0, 0, 0, 0, 0 };
414 HDLAYOUT hdl = { &parentRect, &wp };
415
416 return Header_Layout(hwndHeader, &hdl) ? wp.cy : DEFAULT_HEIGHT;
417 }
418
419 // Uses the theme to draw the border and fill for something like a wxTextCtrl
420 void wxRendererMSW::DrawTextCtrl(wxWindow* win, wxDC& dc, const wxRect& rect, int flags)
421 {
422 wxColour fill;
423 wxColour bdr;
424 COLORREF cref;
425
426 #if wxUSE_UXTHEME
427 wxUxThemeHandle hTheme(win, L"EDIT");
428 if (hTheme)
429 {
430 wxUxThemeEngine::Get()->GetThemeColor(hTheme, EP_EDITTEXT,
431 ETS_NORMAL, TMT_FILLCOLOR, &cref);
432 fill = wxRGBToColour(cref);
433
434 int etsState;
435 if ( flags & wxCONTROL_DISABLED )
436 etsState = ETS_DISABLED;
437 else
438 etsState = ETS_NORMAL;
439
440 wxUxThemeEngine::Get()->GetThemeColor(hTheme, EP_EDITTEXT,
441 etsState, TMT_BORDERCOLOR, &cref);
442 bdr = wxRGBToColour(cref);
443 }
444 else
445 #endif
446 {
447 fill = wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW);
448 bdr = *wxBLACK;
449 }
450
451 dc.SetPen( bdr );
452 dc.SetBrush( fill );
453 dc.DrawRectangle(rect);
454 }
455
456
457 // Draw the equivallent of a wxComboBox
458 void wxRendererMSW::DrawComboBox(wxWindow* win, wxDC& dc, const wxRect& rect, int flags)
459 {
460 // Draw the main part of the control same as TextCtrl
461 DrawTextCtrl(win, dc, rect, flags);
462
463 // Draw the button inside the border, on the right side
464 wxRect br(rect);
465 br.height -= 2;
466 br.x += br.width - br.height - 1;
467 br.width = br.height;
468 br.y += 1;
469
470 DrawComboBoxDropButton(win, dc, br, flags);
471 }
472
473
474 void wxRendererMSW::DrawChoice(wxWindow* win, wxDC& dc,
475 const wxRect& rect, int flags)
476 {
477 DrawComboBox(win, dc, rect, flags);
478 }
479
480
481 // Draw a themed radio button
482 void wxRendererMSW::DrawRadioButton(wxWindow* win, wxDC& dc, const wxRect& rect, int flags)
483 {
484 #if wxUSE_UXTHEME
485 wxUxThemeHandle hTheme(win, L"BUTTON");
486 if ( !hTheme )
487 #endif
488 {
489 // ??? m_rendererNative.DrawRadioButton(win, dc, rect, flags);
490 return;
491 }
492
493 #if wxUSE_UXTHEME
494 RECT r;
495 wxCopyRectToRECT(rect, r);
496
497 int state;
498 if ( flags & wxCONTROL_CHECKED )
499 state = RBS_CHECKEDNORMAL;
500 else if ( flags & wxCONTROL_UNDETERMINED )
501 state = RBS_MIXEDNORMAL;
502 else
503 state = RBS_UNCHECKEDNORMAL;
504
505 // RBS_XXX is followed by RBX_XXXGOT, then RBS_XXXPRESSED and DISABLED
506 if ( flags & wxCONTROL_CURRENT )
507 state += 1;
508 else if ( flags & wxCONTROL_PRESSED )
509 state += 2;
510 else if ( flags & wxCONTROL_DISABLED )
511 state += 3;
512
513 wxUxThemeEngine::Get()->DrawThemeBackground
514 (
515 hTheme,
516 GraphicsHDC(&dc),
517 BP_RADIOBUTTON,
518 state,
519 &r,
520 NULL
521 );
522 #endif
523 }
524
525 // ============================================================================
526 // wxRendererXP implementation
527 // ============================================================================
528
529 #if wxUSE_UXTHEME
530
531 /* static */
532 wxRendererNative& wxRendererXP::Get()
533 {
534 static wxRendererXP s_rendererXP;
535
536 return s_rendererXP;
537 }
538
539 // NOTE: There is no guarantee that the button drawn fills the entire rect (XP
540 // default theme, for example), so the caller should have cleared button's
541 // background before this call. This is quite likely a wxMSW-specific thing.
542 void
543 wxRendererXP::DrawComboBoxDropButton(wxWindow * win,
544 wxDC& dc,
545 const wxRect& rect,
546 int flags)
547 {
548 wxUxThemeHandle hTheme(win, L"COMBOBOX");
549 if ( !hTheme )
550 {
551 m_rendererNative.DrawComboBoxDropButton(win, dc, rect, flags);
552 return;
553 }
554
555 RECT r;
556 wxCopyRectToRECT(rect, r);
557
558 int state;
559 if ( flags & wxCONTROL_PRESSED )
560 state = CBXS_PRESSED;
561 else if ( flags & wxCONTROL_CURRENT )
562 state = CBXS_HOT;
563 else if ( flags & wxCONTROL_DISABLED )
564 state = CBXS_DISABLED;
565 else
566 state = CBXS_NORMAL;
567
568 wxUxThemeEngine::Get()->DrawThemeBackground
569 (
570 hTheme,
571 GetHdcOf(*((wxMSWDCImpl*)dc.GetImpl())),
572 CP_DROPDOWNBUTTON,
573 state,
574 &r,
575 NULL
576 );
577
578 }
579
580 int
581 wxRendererXP::DrawHeaderButton(wxWindow *win,
582 wxDC& dc,
583 const wxRect& rect,
584 int flags,
585 wxHeaderSortIconType sortArrow,
586 wxHeaderButtonParams* params)
587 {
588 wxUxThemeHandle hTheme(win, L"HEADER");
589 if ( !hTheme )
590 {
591 return m_rendererNative.DrawHeaderButton(win, dc, rect, flags, sortArrow, params);
592 }
593
594 RECT r;
595 wxCopyRectToRECT(rect, r);
596
597 int state;
598 if ( flags & wxCONTROL_PRESSED )
599 state = HIS_PRESSED;
600 else if ( flags & wxCONTROL_CURRENT )
601 state = HIS_HOT;
602 else
603 state = HIS_NORMAL;
604 wxUxThemeEngine::Get()->DrawThemeBackground
605 (
606 hTheme,
607 GetHdcOf(*((wxMSWDCImpl*)dc.GetImpl())),
608 HP_HEADERITEM,
609 state,
610 &r,
611 NULL
612 );
613
614 // NOTE: Using the theme to draw HP_HEADERSORTARROW doesn't do anything.
615 // Why? If this can be fixed then draw the sort arrows using the theme
616 // and then clear those flags before calling DrawHeaderButtonContents.
617
618 // Add any extras that are specified in flags and params
619 return DrawHeaderButtonContents(win, dc, rect, flags, sortArrow, params);
620 }
621
622
623 void
624 wxRendererXP::DrawTreeItemButton(wxWindow *win,
625 wxDC& dc,
626 const wxRect& rect,
627 int flags)
628 {
629 wxUxThemeHandle hTheme(win, L"TREEVIEW");
630 if ( !hTheme )
631 {
632 m_rendererNative.DrawTreeItemButton(win, dc, rect, flags);
633 return;
634 }
635
636 RECT r;
637 wxCopyRectToRECT(rect, r);
638
639 int state = flags & wxCONTROL_EXPANDED ? GLPS_OPENED : GLPS_CLOSED;
640 wxUxThemeEngine::Get()->DrawThemeBackground
641 (
642 hTheme,
643 GetHdcOf(*((wxMSWDCImpl*)dc.GetImpl())),
644 TVP_GLYPH,
645 state,
646 &r,
647 NULL
648 );
649 }
650
651
652
653 void
654 wxRendererXP::DrawCheckBox(wxWindow *win,
655 wxDC& dc,
656 const wxRect& rect,
657 int flags)
658 {
659 wxUxThemeHandle hTheme(win, L"BUTTON");
660 if ( !hTheme )
661 {
662 m_rendererNative.DrawCheckBox(win, dc, rect, flags);
663 return;
664 }
665
666 RECT r;
667 wxCopyRectToRECT(rect, r);
668
669 int state;
670 if ( flags & wxCONTROL_CHECKED )
671 state = CBS_CHECKEDNORMAL;
672 else if ( flags & wxCONTROL_UNDETERMINED )
673 state = CBS_MIXEDNORMAL;
674 else
675 state = CBS_UNCHECKEDNORMAL;
676
677 // CBS_XXX is followed by CBX_XXXHOT, then CBS_XXXPRESSED and DISABLED
678 enum
679 {
680 CBS_HOT_OFFSET = 1,
681 CBS_PRESSED_OFFSET = 2,
682 CBS_DISABLED_OFFSET = 3
683 };
684
685 if ( flags & wxCONTROL_DISABLED )
686 state += CBS_DISABLED_OFFSET;
687 else if ( flags & wxCONTROL_PRESSED )
688 state += CBS_PRESSED_OFFSET;
689 else if ( flags & wxCONTROL_CURRENT )
690 state += CBS_HOT_OFFSET;
691
692 wxUxThemeEngine::Get()->DrawThemeBackground
693 (
694 hTheme,
695 GetHdcOf(*((wxMSWDCImpl*)dc.GetImpl())),
696 BP_CHECKBOX,
697 state,
698 &r,
699 NULL
700 );
701 }
702
703 void
704 wxRendererXP::DrawPushButton(wxWindow * win,
705 wxDC& dc,
706 const wxRect& rect,
707 int flags)
708 {
709 wxUxThemeHandle hTheme(win, L"BUTTON");
710 if ( !hTheme )
711 {
712 m_rendererNative.DrawPushButton(win, dc, rect, flags);
713 return;
714 }
715
716 RECT r;
717 wxCopyRectToRECT(rect, r);
718
719 int state;
720 if ( flags & wxCONTROL_PRESSED )
721 state = PBS_PRESSED;
722 else if ( flags & wxCONTROL_CURRENT )
723 state = PBS_HOT;
724 else if ( flags & wxCONTROL_DISABLED )
725 state = PBS_DISABLED;
726 else if ( flags & wxCONTROL_ISDEFAULT )
727 state = PBS_DEFAULTED;
728 else
729 state = PBS_NORMAL;
730
731 wxUxThemeEngine::Get()->DrawThemeBackground
732 (
733 hTheme,
734 GetHdcOf(*((wxMSWDCImpl*)dc.GetImpl())),
735 BP_PUSHBUTTON,
736 state,
737 &r,
738 NULL
739 );
740 }
741
742 void
743 wxRendererXP::DrawItemSelectionRect(wxWindow *win,
744 wxDC& dc,
745 const wxRect& rect,
746 int flags)
747 {
748 wxBrush brush;
749 if ( flags & wxCONTROL_SELECTED )
750 {
751 if ( flags & wxCONTROL_FOCUSED )
752 {
753 brush = wxBrush(wxSystemSettings::GetColour(wxSYS_COLOUR_HIGHLIGHT));
754 }
755 else // !focused
756 {
757 brush = wxBrush(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE));
758 }
759 }
760 else // !selected
761 {
762 brush = *wxTRANSPARENT_BRUSH;
763 }
764
765 dc.SetBrush(brush);
766 dc.SetPen(*wxTRANSPARENT_PEN);
767 dc.DrawRectangle( rect );
768
769 if ((flags & wxCONTROL_FOCUSED) && (flags & wxCONTROL_CURRENT))
770 DrawFocusRect( win, dc, rect, flags );
771 }
772
773
774
775 // ----------------------------------------------------------------------------
776 // splitter drawing
777 // ----------------------------------------------------------------------------
778
779 // the width of the sash: this is the same as used by Explorer...
780 static const wxCoord SASH_WIDTH = 4;
781
782 wxSplitterRenderParams
783 wxRendererXP::GetSplitterParams(const wxWindow * win)
784 {
785 if ( win->HasFlag(wxSP_NO_XP_THEME) )
786 return m_rendererNative.GetSplitterParams(win);
787 else
788 return wxSplitterRenderParams(SASH_WIDTH, 0, false);
789 }
790
791 void
792 wxRendererXP::DrawSplitterBorder(wxWindow * win,
793 wxDC& dc,
794 const wxRect& rect,
795 int flags)
796 {
797 if ( win->HasFlag(wxSP_NO_XP_THEME) )
798 {
799 m_rendererNative.DrawSplitterBorder(win, dc, rect, flags);
800 }
801 }
802
803 void
804 wxRendererXP::DrawSplitterSash(wxWindow *win,
805 wxDC& dc,
806 const wxSize& size,
807 wxCoord position,
808 wxOrientation orient,
809 int flags)
810 {
811 if ( !win->HasFlag(wxSP_NO_XP_THEME) )
812 {
813 dc.SetPen(*wxTRANSPARENT_PEN);
814 dc.SetBrush(wxBrush(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE)));
815 if ( orient == wxVERTICAL )
816 {
817 dc.DrawRectangle(position, 0, SASH_WIDTH, size.y);
818 }
819 else // wxHORIZONTAL
820 {
821 dc.DrawRectangle(0, position, size.x, SASH_WIDTH);
822 }
823
824 return;
825 }
826
827 m_rendererNative.DrawSplitterSash(win, dc, size, position, orient, flags);
828 }
829
830 #endif // wxUSE_UXTHEME