1 /*
2 * Copyright (C) 2006, 2007 Apple Inc.
3 * Copyright (C) 2009 Kenneth Rohde Christiansen
4 *
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Library General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
9 *
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Library General Public License for more details.
14 *
15 * You should have received a copy of the GNU Library General Public License
16 * along with this library; see the file COPYING.LIB. If not, write to
17 * the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
19 *
20 */
21
22 #include "config.h"
23 #include "RenderThemeWin.h"
24
25 #include "CSSValueKeywords.h"
26 #include "Element.h"
27 #include "Frame.h"
28 #include "GraphicsContext.h"
29 #include "LocalWindowsContext.h"
30 #include "PaintInfo.h"
31 #include "RenderSlider.h"
32 #include "Settings.h"
33 #include "SoftLinking.h"
34 #include "SystemInfo.h"
35 #include "UserAgentStyleSheets.h"
36
37 #if ENABLE(VIDEO)
38 #include "RenderMediaControls.h"
39 #endif
40
41 #include <tchar.h>
42
43 /*
44 * The following constants are used to determine how a widget is drawn using
45 * Windows' Theme API. For more information on theme parts and states see
46 * http://msdn.microsoft.com/library/default.asp?url=/library/en-us/shellcc/platform/commctls/userex/topics/partsandstates.asp
47 */
48
49 // Generic state constants
50 #define TS_NORMAL 1
51 #define TS_HOVER 2
52 #define TS_ACTIVE 3
53 #define TS_DISABLED 4
54 #define TS_FOCUSED 5
55
56 // Button constants
57 #define BP_BUTTON 1
58 #define BP_RADIO 2
59 #define BP_CHECKBOX 3
60
61 // Textfield constants
62 #define TFP_TEXTFIELD 1
63 #define EP_EDITBORDER_NOSCROLL 6
64 #define TFS_READONLY 6
65
66 // ComboBox constants (from vsstyle.h)
67 #define CP_DROPDOWNBUTTON 1
68 #define CP_BORDER 4
69 #define CP_READONLY 5
70 #define CP_DROPDOWNBUTTONRIGHT 6
71
72 // TrackBar (slider) parts
73 #define TKP_TRACK 1
74 #define TKP_TRACKVERT 2
75
76 // TrackBar (slider) thumb parts
77 #define TKP_THUMBBOTTOM 4
78 #define TKP_THUMBTOP 5
79 #define TKP_THUMBLEFT 7
80 #define TKP_THUMBRIGHT 8
81
82 // Trackbar (slider) thumb states
83 #define TUS_NORMAL 1
84 #define TUS_HOT 2
85 #define TUS_PRESSED 3
86 #define TUS_FOCUSED 4
87 #define TUS_DISABLED 5
88
89 // button states
90 #define PBS_NORMAL 1
91 #define PBS_HOT 2
92 #define PBS_PRESSED 3
93 #define PBS_DISABLED 4
94 #define PBS_DEFAULTED 5
95
96 // Spin button parts
97 #define SPNP_UP 1
98 #define SPNP_DOWN 2
99
100 // Spin button states
101 #define DNS_NORMAL 1
102 #define DNS_HOT 2
103 #define DNS_PRESSED 3
104 #define DNS_DISABLED 4
105 #define UPS_NORMAL 1
106 #define UPS_HOT 2
107 #define UPS_PRESSED 3
108 #define UPS_DISABLED 4
109
110
111 SOFT_LINK_LIBRARY(uxtheme)
112 SOFT_LINK(uxtheme, OpenThemeData, HANDLE, WINAPI, (HWND hwnd, LPCWSTR pszClassList), (hwnd, pszClassList))
113 SOFT_LINK(uxtheme, CloseThemeData, HRESULT, WINAPI, (HANDLE hTheme), (hTheme))
114 SOFT_LINK(uxtheme, DrawThemeBackground, HRESULT, WINAPI, (HANDLE hTheme, HDC hdc, int iPartId, int iStateId, const RECT* pRect, const RECT* pClipRect), (hTheme, hdc, iPartId, iStateId, pRect, pClipRect))
115 SOFT_LINK(uxtheme, IsThemeActive, BOOL, WINAPI, (), ())
116 SOFT_LINK(uxtheme, IsThemeBackgroundPartiallyTransparent, BOOL, WINAPI, (HANDLE hTheme, int iPartId, int iStateId), (hTheme, iPartId, iStateId))
117
118 static bool haveTheme;
119
120 static const unsigned vistaMenuListButtonOutset = 1;
121
122 using namespace std;
123
124 namespace WebCore {
125
126 // This is the fixed width IE and Firefox use for buttons on dropdown menus
127 static const int dropDownButtonWidth = 17;
128
129 static const int shell32MagnifierIconIndex = 22;
130
131 // Default font size to match Firefox.
132 static const float defaultControlFontPixelSize = 13;
133
134 static const float defaultCancelButtonSize = 9;
135 static const float minCancelButtonSize = 5;
136 static const float maxCancelButtonSize = 21;
137 static const float defaultSearchFieldResultsDecorationSize = 13;
138 static const float minSearchFieldResultsDecorationSize = 9;
139 static const float maxSearchFieldResultsDecorationSize = 30;
140 static const float defaultSearchFieldResultsButtonWidth = 18;
141
142 static bool gWebKitIsBeingUnloaded;
143
documentIsInApplicationChromeMode(const Document * document)144 static bool documentIsInApplicationChromeMode(const Document* document)
145 {
146 Settings* settings = document->settings();
147 return settings && settings->inApplicationChromeMode();
148 }
149
setWebKitIsBeingUnloaded()150 void RenderThemeWin::setWebKitIsBeingUnloaded()
151 {
152 gWebKitIsBeingUnloaded = true;
153 }
154
create()155 PassRefPtr<RenderTheme> RenderThemeWin::create()
156 {
157 return adoptRef(new RenderThemeWin);
158 }
159
160 #if !USE(SAFARI_THEME)
themeForPage(Page * page)161 PassRefPtr<RenderTheme> RenderTheme::themeForPage(Page* page)
162 {
163 static RenderTheme* winTheme = RenderThemeWin::create().releaseRef();
164 return winTheme;
165 }
166 #endif
167
RenderThemeWin()168 RenderThemeWin::RenderThemeWin()
169 : m_buttonTheme(0)
170 , m_textFieldTheme(0)
171 , m_menuListTheme(0)
172 , m_sliderTheme(0)
173 , m_spinButtonTheme(0)
174 {
175 haveTheme = uxthemeLibrary() && IsThemeActive();
176 }
177
~RenderThemeWin()178 RenderThemeWin::~RenderThemeWin()
179 {
180 // If WebKit is being unloaded, then uxtheme.dll is no longer available.
181 if (gWebKitIsBeingUnloaded || !uxthemeLibrary())
182 return;
183 close();
184 }
185
buttonTheme() const186 HANDLE RenderThemeWin::buttonTheme() const
187 {
188 if (haveTheme && !m_buttonTheme)
189 m_buttonTheme = OpenThemeData(0, L"Button");
190 return m_buttonTheme;
191 }
192
textFieldTheme() const193 HANDLE RenderThemeWin::textFieldTheme() const
194 {
195 if (haveTheme && !m_textFieldTheme)
196 m_textFieldTheme = OpenThemeData(0, L"Edit");
197 return m_textFieldTheme;
198 }
199
menuListTheme() const200 HANDLE RenderThemeWin::menuListTheme() const
201 {
202 if (haveTheme && !m_menuListTheme)
203 m_menuListTheme = OpenThemeData(0, L"ComboBox");
204 return m_menuListTheme;
205 }
206
sliderTheme() const207 HANDLE RenderThemeWin::sliderTheme() const
208 {
209 if (haveTheme && !m_sliderTheme)
210 m_sliderTheme = OpenThemeData(0, L"TrackBar");
211 return m_sliderTheme;
212 }
213
spinButtonTheme() const214 HANDLE RenderThemeWin::spinButtonTheme() const
215 {
216 if (haveTheme && !m_spinButtonTheme)
217 m_spinButtonTheme = OpenThemeData(0, L"Spin");
218 return m_spinButtonTheme;
219 }
220
close()221 void RenderThemeWin::close()
222 {
223 // This method will need to be called when the OS theme changes to flush our cached themes.
224 if (m_buttonTheme)
225 CloseThemeData(m_buttonTheme);
226 if (m_textFieldTheme)
227 CloseThemeData(m_textFieldTheme);
228 if (m_menuListTheme)
229 CloseThemeData(m_menuListTheme);
230 if (m_sliderTheme)
231 CloseThemeData(m_sliderTheme);
232 if (m_spinButtonTheme)
233 CloseThemeData(m_spinButtonTheme);
234 m_buttonTheme = m_textFieldTheme = m_menuListTheme = m_sliderTheme = m_spinButtonTheme = 0;
235
236 haveTheme = uxthemeLibrary() && IsThemeActive();
237 }
238
themeChanged()239 void RenderThemeWin::themeChanged()
240 {
241 close();
242 }
243
extraDefaultStyleSheet()244 String RenderThemeWin::extraDefaultStyleSheet()
245 {
246 return String(themeWinUserAgentStyleSheet, sizeof(themeWinUserAgentStyleSheet));
247 }
248
extraQuirksStyleSheet()249 String RenderThemeWin::extraQuirksStyleSheet()
250 {
251 return String(themeWinQuirksUserAgentStyleSheet, sizeof(themeWinQuirksUserAgentStyleSheet));
252 }
253
supportsHover(const RenderStyle *) const254 bool RenderThemeWin::supportsHover(const RenderStyle*) const
255 {
256 // The Classic/2k look has no hover effects.
257 return haveTheme;
258 }
259
platformActiveSelectionBackgroundColor() const260 Color RenderThemeWin::platformActiveSelectionBackgroundColor() const
261 {
262 COLORREF color = GetSysColor(COLOR_HIGHLIGHT);
263 return Color(GetRValue(color), GetGValue(color), GetBValue(color));
264 }
265
platformInactiveSelectionBackgroundColor() const266 Color RenderThemeWin::platformInactiveSelectionBackgroundColor() const
267 {
268 // This color matches Firefox.
269 return Color(176, 176, 176);
270 }
271
platformActiveSelectionForegroundColor() const272 Color RenderThemeWin::platformActiveSelectionForegroundColor() const
273 {
274 COLORREF color = GetSysColor(COLOR_HIGHLIGHTTEXT);
275 return Color(GetRValue(color), GetGValue(color), GetBValue(color));
276 }
277
platformInactiveSelectionForegroundColor() const278 Color RenderThemeWin::platformInactiveSelectionForegroundColor() const
279 {
280 return platformActiveSelectionForegroundColor();
281 }
282
fillFontDescription(FontDescription & fontDescription,LOGFONT & logFont,float fontSize)283 static void fillFontDescription(FontDescription& fontDescription, LOGFONT& logFont, float fontSize)
284 {
285 fontDescription.setIsAbsoluteSize(true);
286 fontDescription.setGenericFamily(FontDescription::NoFamily);
287 fontDescription.firstFamily().setFamily(String(logFont.lfFaceName));
288 fontDescription.setSpecifiedSize(fontSize);
289 fontDescription.setWeight(logFont.lfWeight >= 700 ? FontWeightBold : FontWeightNormal); // FIXME: Use real weight.
290 fontDescription.setItalic(logFont.lfItalic);
291 }
292
fillFontDescription(FontDescription & fontDescription,LOGFONT & logFont)293 static void fillFontDescription(FontDescription& fontDescription, LOGFONT& logFont)
294 {
295 fillFontDescription(fontDescription, logFont, abs(logFont.lfHeight));
296 }
297
systemFont(int propId,FontDescription & fontDescription) const298 void RenderThemeWin::systemFont(int propId, FontDescription& fontDescription) const
299 {
300 static FontDescription captionFont;
301 static FontDescription controlFont;
302 static FontDescription smallCaptionFont;
303 static FontDescription menuFont;
304 static FontDescription iconFont;
305 static FontDescription messageBoxFont;
306 static FontDescription statusBarFont;
307 static FontDescription systemFont;
308
309 static bool initialized;
310 static NONCLIENTMETRICS ncm;
311
312 if (!initialized) {
313 initialized = true;
314 ncm.cbSize = sizeof(NONCLIENTMETRICS);
315 ::SystemParametersInfo(SPI_GETNONCLIENTMETRICS, sizeof(ncm), &ncm, 0);
316 }
317
318 switch (propId) {
319 case CSSValueIcon: {
320 if (!iconFont.isAbsoluteSize()) {
321 LOGFONT logFont;
322 ::SystemParametersInfo(SPI_GETICONTITLELOGFONT, sizeof(logFont), &logFont, 0);
323 fillFontDescription(iconFont, logFont);
324 }
325 fontDescription = iconFont;
326 break;
327 }
328 case CSSValueMenu:
329 if (!menuFont.isAbsoluteSize())
330 fillFontDescription(menuFont, ncm.lfMenuFont);
331 fontDescription = menuFont;
332 break;
333 case CSSValueMessageBox:
334 if (!messageBoxFont.isAbsoluteSize())
335 fillFontDescription(messageBoxFont, ncm.lfMessageFont);
336 fontDescription = messageBoxFont;
337 break;
338 case CSSValueStatusBar:
339 if (!statusBarFont.isAbsoluteSize())
340 fillFontDescription(statusBarFont, ncm.lfStatusFont);
341 fontDescription = statusBarFont;
342 break;
343 case CSSValueCaption:
344 if (!captionFont.isAbsoluteSize())
345 fillFontDescription(captionFont, ncm.lfCaptionFont);
346 fontDescription = captionFont;
347 break;
348 case CSSValueSmallCaption:
349 if (!smallCaptionFont.isAbsoluteSize())
350 fillFontDescription(smallCaptionFont, ncm.lfSmCaptionFont);
351 fontDescription = smallCaptionFont;
352 break;
353 case CSSValueWebkitSmallControl:
354 case CSSValueWebkitMiniControl: // Just map to small.
355 case CSSValueWebkitControl: // Just map to small.
356 if (!controlFont.isAbsoluteSize()) {
357 HGDIOBJ hGDI = ::GetStockObject(DEFAULT_GUI_FONT);
358 if (hGDI) {
359 LOGFONT logFont;
360 if (::GetObject(hGDI, sizeof(logFont), &logFont) > 0)
361 fillFontDescription(controlFont, logFont, defaultControlFontPixelSize);
362 }
363 }
364 fontDescription = controlFont;
365 break;
366 default: { // Everything else uses the stock GUI font.
367 if (!systemFont.isAbsoluteSize()) {
368 HGDIOBJ hGDI = ::GetStockObject(DEFAULT_GUI_FONT);
369 if (hGDI) {
370 LOGFONT logFont;
371 if (::GetObject(hGDI, sizeof(logFont), &logFont) > 0)
372 fillFontDescription(systemFont, logFont);
373 }
374 }
375 fontDescription = systemFont;
376 }
377 }
378 }
379
supportsFocus(ControlPart appearance) const380 bool RenderThemeWin::supportsFocus(ControlPart appearance) const
381 {
382 switch (appearance) {
383 case PushButtonPart:
384 case ButtonPart:
385 case DefaultButtonPart:
386 return true;
387 default:
388 return false;
389 }
390 }
391
supportsFocusRing(const RenderStyle * style) const392 bool RenderThemeWin::supportsFocusRing(const RenderStyle* style) const
393 {
394 return supportsFocus(style->appearance());
395 }
396
determineClassicState(RenderObject * o,ControlSubPart subPart)397 unsigned RenderThemeWin::determineClassicState(RenderObject* o, ControlSubPart subPart)
398 {
399 unsigned state = 0;
400 switch (o->style()->appearance()) {
401 case PushButtonPart:
402 case ButtonPart:
403 case DefaultButtonPart:
404 state = DFCS_BUTTONPUSH;
405 if (!isEnabled(o))
406 state |= DFCS_INACTIVE;
407 else if (isPressed(o))
408 state |= DFCS_PUSHED;
409 break;
410 case RadioPart:
411 case CheckboxPart:
412 state = (o->style()->appearance() == RadioPart) ? DFCS_BUTTONRADIO : DFCS_BUTTONCHECK;
413 if (isChecked(o))
414 state |= DFCS_CHECKED;
415 if (!isEnabled(o))
416 state |= DFCS_INACTIVE;
417 else if (isPressed(o))
418 state |= DFCS_PUSHED;
419 break;
420 case MenulistPart:
421 state = DFCS_SCROLLCOMBOBOX;
422 if (!isEnabled(o))
423 state |= DFCS_INACTIVE;
424 else if (isPressed(o))
425 state |= DFCS_PUSHED;
426 break;
427 case InnerSpinButtonPart: {
428 bool isUpButton = subPart == SpinButtonUp;
429 state = isUpButton ? DFCS_SCROLLUP : DFCS_SCROLLDOWN;
430 if (!isEnabled(o) || isReadOnlyControl(o))
431 state |= DFCS_INACTIVE;
432 else if (isPressed(o) && isUpButton == isSpinUpButtonPartPressed(o))
433 state |= DFCS_PUSHED;
434 else if (isHovered(o) && isUpButton == isSpinUpButtonPartHovered(o))
435 state |= DFCS_HOT;
436 break;
437 }
438 default:
439 break;
440 }
441 return state;
442 }
443
determineState(RenderObject * o)444 unsigned RenderThemeWin::determineState(RenderObject* o)
445 {
446 unsigned result = TS_NORMAL;
447 ControlPart appearance = o->style()->appearance();
448 if (!isEnabled(o))
449 result = TS_DISABLED;
450 else if (isReadOnlyControl(o) && (TextFieldPart == appearance || TextAreaPart == appearance || SearchFieldPart == appearance))
451 result = TFS_READONLY; // Readonly is supported on textfields.
452 else if (isPressed(o)) // Active overrides hover and focused.
453 result = TS_ACTIVE;
454 else if (supportsFocus(appearance) && isFocused(o))
455 result = TS_FOCUSED;
456 else if (isHovered(o))
457 result = TS_HOVER;
458 if (isChecked(o))
459 result += 4; // 4 unchecked states, 4 checked states.
460 return result;
461 }
462
determineSliderThumbState(RenderObject * o)463 unsigned RenderThemeWin::determineSliderThumbState(RenderObject* o)
464 {
465 unsigned result = TUS_NORMAL;
466 if (!isEnabled(o->parent()))
467 result = TUS_DISABLED;
468 else if (supportsFocus(o->style()->appearance()) && isFocused(o->parent()))
469 result = TUS_FOCUSED;
470 else if (toRenderSlider(o->parent())->inDragMode())
471 result = TUS_PRESSED;
472 else if (isHovered(o))
473 result = TUS_HOT;
474 return result;
475 }
476
determineButtonState(RenderObject * o)477 unsigned RenderThemeWin::determineButtonState(RenderObject* o)
478 {
479 unsigned result = PBS_NORMAL;
480 if (!isEnabled(o))
481 result = PBS_DISABLED;
482 else if (isPressed(o))
483 result = PBS_PRESSED;
484 else if (supportsFocus(o->style()->appearance()) && isFocused(o))
485 result = PBS_DEFAULTED;
486 else if (isHovered(o))
487 result = PBS_HOT;
488 else if (isDefault(o))
489 result = PBS_DEFAULTED;
490 return result;
491 }
492
determineSpinButtonState(RenderObject * o,ControlSubPart subPart)493 unsigned RenderThemeWin::determineSpinButtonState(RenderObject* o, ControlSubPart subPart)
494 {
495 bool isUpButton = subPart == SpinButtonUp;
496 unsigned result = isUpButton ? UPS_NORMAL : DNS_NORMAL;
497 if (!isEnabled(o) || isReadOnlyControl(o))
498 result = isUpButton ? UPS_DISABLED : DNS_DISABLED;
499 else if (isPressed(o) && isUpButton == isSpinUpButtonPartPressed(o))
500 result = isUpButton ? UPS_PRESSED : DNS_PRESSED;
501 else if (isHovered(o) && isUpButton == isSpinUpButtonPartHovered(o))
502 result = isUpButton ? UPS_HOT : DNS_HOT;
503 return result;
504 }
505
getClassicThemeData(RenderObject * o,ControlSubPart subPart)506 ThemeData RenderThemeWin::getClassicThemeData(RenderObject* o, ControlSubPart subPart)
507 {
508 ThemeData result;
509 switch (o->style()->appearance()) {
510 case PushButtonPart:
511 case ButtonPart:
512 case DefaultButtonPart:
513 case CheckboxPart:
514 case RadioPart:
515 result.m_part = DFC_BUTTON;
516 result.m_state = determineClassicState(o);
517 break;
518 case MenulistPart:
519 result.m_part = DFC_SCROLL;
520 result.m_state = determineClassicState(o);
521 break;
522 case SearchFieldPart:
523 case TextFieldPart:
524 case TextAreaPart:
525 result.m_part = TFP_TEXTFIELD;
526 result.m_state = determineState(o);
527 break;
528 case SliderHorizontalPart:
529 result.m_part = TKP_TRACK;
530 result.m_state = TS_NORMAL;
531 break;
532 case SliderVerticalPart:
533 result.m_part = TKP_TRACKVERT;
534 result.m_state = TS_NORMAL;
535 break;
536 case SliderThumbHorizontalPart:
537 result.m_part = TKP_THUMBBOTTOM;
538 result.m_state = determineSliderThumbState(o);
539 break;
540 case SliderThumbVerticalPart:
541 result.m_part = TKP_THUMBRIGHT;
542 result.m_state = determineSliderThumbState(o);
543 break;
544 case InnerSpinButtonPart:
545 result.m_part = DFC_SCROLL;
546 result.m_state = determineClassicState(o, subPart);
547 break;
548 default:
549 break;
550 }
551 return result;
552 }
553
getThemeData(RenderObject * o,ControlSubPart subPart)554 ThemeData RenderThemeWin::getThemeData(RenderObject* o, ControlSubPart subPart)
555 {
556 if (!haveTheme)
557 return getClassicThemeData(o, subPart);
558
559 ThemeData result;
560 switch (o->style()->appearance()) {
561 case PushButtonPart:
562 case ButtonPart:
563 case DefaultButtonPart:
564 result.m_part = BP_BUTTON;
565 result.m_state = determineButtonState(o);
566 break;
567 case CheckboxPart:
568 result.m_part = BP_CHECKBOX;
569 result.m_state = determineState(o);
570 break;
571 case MenulistPart:
572 case MenulistButtonPart: {
573 const bool isVistaOrLater = (windowsVersion() >= WindowsVista);
574 result.m_part = isVistaOrLater ? CP_DROPDOWNBUTTONRIGHT : CP_DROPDOWNBUTTON;
575 if (isVistaOrLater && documentIsInApplicationChromeMode(o->document())) {
576 // The "readonly" look we use in application chrome mode
577 // only uses a "normal" look for the drop down button.
578 result.m_state = TS_NORMAL;
579 } else
580 result.m_state = determineState(o);
581 break;
582 }
583 case RadioPart:
584 result.m_part = BP_RADIO;
585 result.m_state = determineState(o);
586 break;
587 case SearchFieldPart:
588 case TextFieldPart:
589 case TextAreaPart:
590 result.m_part = (windowsVersion() >= WindowsVista) ? EP_EDITBORDER_NOSCROLL : TFP_TEXTFIELD;
591 result.m_state = determineState(o);
592 break;
593 case SliderHorizontalPart:
594 result.m_part = TKP_TRACK;
595 result.m_state = TS_NORMAL;
596 break;
597 case SliderVerticalPart:
598 result.m_part = TKP_TRACKVERT;
599 result.m_state = TS_NORMAL;
600 break;
601 case SliderThumbHorizontalPart:
602 result.m_part = TKP_THUMBBOTTOM;
603 result.m_state = determineSliderThumbState(o);
604 break;
605 case SliderThumbVerticalPart:
606 result.m_part = TKP_THUMBRIGHT;
607 result.m_state = determineSliderThumbState(o);
608 break;
609 case InnerSpinButtonPart:
610 result.m_part = subPart == SpinButtonUp ? SPNP_UP : SPNP_DOWN;
611 result.m_state = determineSpinButtonState(o, subPart);
612 break;
613 }
614
615 return result;
616 }
617
drawControl(GraphicsContext * context,RenderObject * o,HANDLE theme,const ThemeData & themeData,const IntRect & r)618 static void drawControl(GraphicsContext* context, RenderObject* o, HANDLE theme, const ThemeData& themeData, const IntRect& r)
619 {
620 bool alphaBlend = false;
621 if (theme)
622 alphaBlend = IsThemeBackgroundPartiallyTransparent(theme, themeData.m_part, themeData.m_state);
623 LocalWindowsContext windowsContext(context, r, alphaBlend);
624 RECT widgetRect = r;
625 if (theme)
626 DrawThemeBackground(theme, windowsContext.hdc(), themeData.m_part, themeData.m_state, &widgetRect, 0);
627 else {
628 HDC hdc = windowsContext.hdc();
629 if (themeData.m_part == TFP_TEXTFIELD) {
630 ::DrawEdge(hdc, &widgetRect, EDGE_SUNKEN, BF_RECT | BF_ADJUST);
631 if (themeData.m_state == TS_DISABLED || themeData.m_state == TFS_READONLY)
632 ::FillRect(hdc, &widgetRect, (HBRUSH)(COLOR_BTNFACE+1));
633 else
634 ::FillRect(hdc, &widgetRect, (HBRUSH)(COLOR_WINDOW+1));
635 } else if (themeData.m_part == TKP_TRACK || themeData.m_part == TKP_TRACKVERT) {
636 ::DrawEdge(hdc, &widgetRect, EDGE_SUNKEN, BF_RECT | BF_ADJUST);
637 ::FillRect(hdc, &widgetRect, (HBRUSH)GetStockObject(GRAY_BRUSH));
638 } else if ((o->style()->appearance() == SliderThumbHorizontalPart ||
639 o->style()->appearance() == SliderThumbVerticalPart) &&
640 (themeData.m_part == TKP_THUMBBOTTOM || themeData.m_part == TKP_THUMBTOP ||
641 themeData.m_part == TKP_THUMBLEFT || themeData.m_part == TKP_THUMBRIGHT)) {
642 ::DrawEdge(hdc, &widgetRect, EDGE_RAISED, BF_RECT | BF_SOFT | BF_MIDDLE | BF_ADJUST);
643 if (themeData.m_state == TUS_DISABLED) {
644 static WORD patternBits[8] = {0xaa, 0x55, 0xaa, 0x55, 0xaa, 0x55, 0xaa, 0x55};
645 HBITMAP patternBmp = ::CreateBitmap(8, 8, 1, 1, patternBits);
646 if (patternBmp) {
647 HBRUSH brush = (HBRUSH) ::CreatePatternBrush(patternBmp);
648 COLORREF oldForeColor = ::SetTextColor(hdc, ::GetSysColor(COLOR_3DFACE));
649 COLORREF oldBackColor = ::SetBkColor(hdc, ::GetSysColor(COLOR_3DHILIGHT));
650 POINT p;
651 ::GetViewportOrgEx(hdc, &p);
652 ::SetBrushOrgEx(hdc, p.x + widgetRect.left, p.y + widgetRect.top, NULL);
653 HBRUSH oldBrush = (HBRUSH) ::SelectObject(hdc, brush);
654 ::FillRect(hdc, &widgetRect, brush);
655 ::SetTextColor(hdc, oldForeColor);
656 ::SetBkColor(hdc, oldBackColor);
657 ::SelectObject(hdc, oldBrush);
658 ::DeleteObject(brush);
659 } else
660 ::FillRect(hdc, &widgetRect, (HBRUSH)COLOR_3DHILIGHT);
661 ::DeleteObject(patternBmp);
662 }
663 } else {
664 // Push buttons, buttons, checkboxes and radios, and the dropdown arrow in menulists.
665 if (o->style()->appearance() == DefaultButtonPart) {
666 HBRUSH brush = ::GetSysColorBrush(COLOR_3DDKSHADOW);
667 ::FrameRect(hdc, &widgetRect, brush);
668 ::InflateRect(&widgetRect, -1, -1);
669 ::DrawEdge(hdc, &widgetRect, BDR_RAISEDOUTER, BF_RECT | BF_MIDDLE);
670 }
671 ::DrawFrameControl(hdc, &widgetRect, themeData.m_part, themeData.m_state);
672 }
673 }
674 }
675
paintButton(RenderObject * o,const PaintInfo & i,const IntRect & r)676 bool RenderThemeWin::paintButton(RenderObject* o, const PaintInfo& i, const IntRect& r)
677 {
678 drawControl(i.context, o, buttonTheme(), getThemeData(o), r);
679 return false;
680 }
681
adjustInnerSpinButtonStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const682 void RenderThemeWin::adjustInnerSpinButtonStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
683 {
684 int width = ::GetSystemMetrics(SM_CXVSCROLL);
685 if (width <= 0)
686 width = 17; // Vista's default.
687 style->setWidth(Length(width, Fixed));
688 style->setMinWidth(Length(width, Fixed));
689 }
690
paintInnerSpinButton(RenderObject * o,const PaintInfo & i,const IntRect & r)691 bool RenderThemeWin::paintInnerSpinButton(RenderObject* o, const PaintInfo& i, const IntRect& r)
692 {
693 // We split the specified rectangle into two vertically. We can't draw a
694 // spin button of which height is less than 2px.
695 if (r.height() < 2)
696 return false;
697 IntRect upRect(r);
698 upRect.setHeight(r.height() / 2);
699 IntRect downRect(r);
700 downRect.setY(upRect.maxY());
701 downRect.setHeight(r.height() - upRect.height());
702 drawControl(i.context, o, spinButtonTheme(), getThemeData(o, SpinButtonUp), upRect);
703 drawControl(i.context, o, spinButtonTheme(), getThemeData(o, SpinButtonDown), downRect);
704 return false;
705 }
706
setCheckboxSize(RenderStyle * style) const707 void RenderThemeWin::setCheckboxSize(RenderStyle* style) const
708 {
709 // If the width and height are both specified, then we have nothing to do.
710 if (!style->width().isIntrinsicOrAuto() && !style->height().isAuto())
711 return;
712
713 // FIXME: A hard-coded size of 13 is used. This is wrong but necessary for now. It matches Firefox.
714 // At different DPI settings on Windows, querying the theme gives you a larger size that accounts for
715 // the higher DPI. Until our entire engine honors a DPI setting other than 96, we can't rely on the theme's
716 // metrics.
717 if (style->width().isIntrinsicOrAuto())
718 style->setWidth(Length(13, Fixed));
719 if (style->height().isAuto())
720 style->setHeight(Length(13, Fixed));
721 }
722
paintTextField(RenderObject * o,const PaintInfo & i,const IntRect & r)723 bool RenderThemeWin::paintTextField(RenderObject* o, const PaintInfo& i, const IntRect& r)
724 {
725 drawControl(i.context, o, textFieldTheme(), getThemeData(o), r);
726 return false;
727 }
728
paintMenuList(RenderObject * o,const PaintInfo & i,const IntRect & r)729 bool RenderThemeWin::paintMenuList(RenderObject* o, const PaintInfo& i, const IntRect& r)
730 {
731 HANDLE theme;
732 int part;
733 if (haveTheme && (windowsVersion() >= WindowsVista)) {
734 theme = menuListTheme();
735 if (documentIsInApplicationChromeMode(o->document()))
736 part = CP_READONLY;
737 else
738 part = CP_BORDER;
739 } else {
740 theme = textFieldTheme();
741 part = TFP_TEXTFIELD;
742 }
743
744 drawControl(i.context, o, theme, ThemeData(part, determineState(o)), r);
745
746 return paintMenuListButton(o, i, r);
747 }
748
adjustMenuListStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const749 void RenderThemeWin::adjustMenuListStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
750 {
751 style->resetBorder();
752 adjustMenuListButtonStyle(selector, style, e);
753 }
754
adjustMenuListButtonStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const755 void RenderThemeWin::adjustMenuListButtonStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
756 {
757 // These are the paddings needed to place the text correctly in the <select> box
758 const int dropDownBoxPaddingTop = 2;
759 const int dropDownBoxPaddingRight = style->direction() == LTR ? 4 + dropDownButtonWidth : 4;
760 const int dropDownBoxPaddingBottom = 2;
761 const int dropDownBoxPaddingLeft = style->direction() == LTR ? 4 : 4 + dropDownButtonWidth;
762 // The <select> box must be at least 12px high for the button to render nicely on Windows
763 const int dropDownBoxMinHeight = 12;
764
765 // Position the text correctly within the select box and make the box wide enough to fit the dropdown button
766 style->setPaddingTop(Length(dropDownBoxPaddingTop, Fixed));
767 style->setPaddingRight(Length(dropDownBoxPaddingRight, Fixed));
768 style->setPaddingBottom(Length(dropDownBoxPaddingBottom, Fixed));
769 style->setPaddingLeft(Length(dropDownBoxPaddingLeft, Fixed));
770
771 // Height is locked to auto
772 style->setHeight(Length(Auto));
773
774 // Calculate our min-height
775 int minHeight = style->fontMetrics().height();
776 minHeight = max(minHeight, dropDownBoxMinHeight);
777
778 style->setMinHeight(Length(minHeight, Fixed));
779
780 // White-space is locked to pre
781 style->setWhiteSpace(PRE);
782 }
783
paintMenuListButton(RenderObject * o,const PaintInfo & i,const IntRect & r)784 bool RenderThemeWin::paintMenuListButton(RenderObject* o, const PaintInfo& i, const IntRect& r)
785 {
786 // FIXME: Don't make hardcoded assumptions about the thickness of the textfield border.
787 int borderThickness = haveTheme ? 1 : 2;
788
789 // Paint the dropdown button on the inner edge of the text field,
790 // leaving space for the text field's 1px border
791 IntRect buttonRect(r);
792 buttonRect.inflate(-borderThickness);
793 if (o->style()->direction() == LTR)
794 buttonRect.setX(buttonRect.maxX() - dropDownButtonWidth);
795 buttonRect.setWidth(dropDownButtonWidth);
796
797 if ((windowsVersion() >= WindowsVista)) {
798 // Outset the top, right, and bottom borders of the button so that they coincide with the <select>'s border.
799 buttonRect.setY(buttonRect.y() - vistaMenuListButtonOutset);
800 buttonRect.setHeight(buttonRect.height() + 2 * vistaMenuListButtonOutset);
801 buttonRect.setWidth(buttonRect.width() + vistaMenuListButtonOutset);
802 }
803
804 drawControl(i.context, o, menuListTheme(), getThemeData(o), buttonRect);
805
806 return false;
807 }
808
809 const int trackWidth = 4;
810
paintSliderTrack(RenderObject * o,const PaintInfo & i,const IntRect & r)811 bool RenderThemeWin::paintSliderTrack(RenderObject* o, const PaintInfo& i, const IntRect& r)
812 {
813 IntRect bounds = r;
814
815 if (o->style()->appearance() == SliderHorizontalPart) {
816 bounds.setHeight(trackWidth);
817 bounds.setY(r.y() + r.height() / 2 - trackWidth / 2);
818 } else if (o->style()->appearance() == SliderVerticalPart) {
819 bounds.setWidth(trackWidth);
820 bounds.setX(r.x() + r.width() / 2 - trackWidth / 2);
821 }
822
823 drawControl(i.context, o, sliderTheme(), getThemeData(o), bounds);
824 return false;
825 }
826
paintSliderThumb(RenderObject * o,const PaintInfo & i,const IntRect & r)827 bool RenderThemeWin::paintSliderThumb(RenderObject* o, const PaintInfo& i, const IntRect& r)
828 {
829 drawControl(i.context, o, sliderTheme(), getThemeData(o), r);
830 return false;
831 }
832
833 const int sliderThumbWidth = 7;
834 const int sliderThumbHeight = 15;
835
adjustSliderThumbSize(RenderObject * o) const836 void RenderThemeWin::adjustSliderThumbSize(RenderObject* o) const
837 {
838 ControlPart part = o->style()->appearance();
839 if (part == SliderThumbVerticalPart) {
840 o->style()->setWidth(Length(sliderThumbHeight, Fixed));
841 o->style()->setHeight(Length(sliderThumbWidth, Fixed));
842 } else if (part == SliderThumbHorizontalPart) {
843 o->style()->setWidth(Length(sliderThumbWidth, Fixed));
844 o->style()->setHeight(Length(sliderThumbHeight, Fixed));
845 }
846 #if ENABLE(VIDEO)
847 else if (part == MediaSliderThumbPart || part == MediaVolumeSliderThumbPart)
848 RenderMediaControls::adjustMediaSliderThumbSize(o);
849 #endif
850 }
851
paintSearchField(RenderObject * o,const PaintInfo & i,const IntRect & r)852 bool RenderThemeWin::paintSearchField(RenderObject* o, const PaintInfo& i, const IntRect& r)
853 {
854 return paintTextField(o, i, r);
855 }
856
adjustSearchFieldStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const857 void RenderThemeWin::adjustSearchFieldStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
858 {
859 // Override paddingSize to match AppKit text positioning.
860 const int padding = 1;
861 style->setPaddingLeft(Length(padding, Fixed));
862 style->setPaddingRight(Length(padding, Fixed));
863 style->setPaddingTop(Length(padding, Fixed));
864 style->setPaddingBottom(Length(padding, Fixed));
865 if (e && e->focused() && e->document()->frame()->selection()->isFocusedAndActive())
866 style->setOutlineOffset(-2);
867 }
868
paintSearchFieldCancelButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)869 bool RenderThemeWin::paintSearchFieldCancelButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
870 {
871 IntRect bounds = r;
872 ASSERT(o->parent());
873 if (!o->parent() || !o->parent()->isBox())
874 return false;
875
876 RenderBox* parentRenderBox = toRenderBox(o->parent());
877
878 IntRect parentBox = parentRenderBox->absoluteContentBox();
879
880 // Make sure the scaled button stays square and will fit in its parent's box
881 bounds.setHeight(min(parentBox.width(), min(parentBox.height(), bounds.height())));
882 bounds.setWidth(bounds.height());
883
884 // Center the button vertically. Round up though, so if it has to be one pixel off-center, it will
885 // be one pixel closer to the bottom of the field. This tends to look better with the text.
886 bounds.setY(parentBox.y() + (parentBox.height() - bounds.height() + 1) / 2);
887
888 static Image* cancelImage = Image::loadPlatformResource("searchCancel").releaseRef();
889 static Image* cancelPressedImage = Image::loadPlatformResource("searchCancelPressed").releaseRef();
890 paintInfo.context->drawImage(isPressed(o) ? cancelPressedImage : cancelImage, o->style()->colorSpace(), bounds);
891 return false;
892 }
893
adjustSearchFieldCancelButtonStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const894 void RenderThemeWin::adjustSearchFieldCancelButtonStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
895 {
896 // Scale the button size based on the font size
897 float fontScale = style->fontSize() / defaultControlFontPixelSize;
898 int cancelButtonSize = lroundf(min(max(minCancelButtonSize, defaultCancelButtonSize * fontScale), maxCancelButtonSize));
899 style->setWidth(Length(cancelButtonSize, Fixed));
900 style->setHeight(Length(cancelButtonSize, Fixed));
901 }
902
adjustSearchFieldDecorationStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const903 void RenderThemeWin::adjustSearchFieldDecorationStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
904 {
905 IntSize emptySize(1, 11);
906 style->setWidth(Length(emptySize.width(), Fixed));
907 style->setHeight(Length(emptySize.height(), Fixed));
908 }
909
adjustSearchFieldResultsDecorationStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const910 void RenderThemeWin::adjustSearchFieldResultsDecorationStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
911 {
912 // Scale the decoration size based on the font size
913 float fontScale = style->fontSize() / defaultControlFontPixelSize;
914 int magnifierSize = lroundf(min(max(minSearchFieldResultsDecorationSize, defaultSearchFieldResultsDecorationSize * fontScale),
915 maxSearchFieldResultsDecorationSize));
916 style->setWidth(Length(magnifierSize, Fixed));
917 style->setHeight(Length(magnifierSize, Fixed));
918 }
919
paintSearchFieldResultsDecoration(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)920 bool RenderThemeWin::paintSearchFieldResultsDecoration(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
921 {
922 IntRect bounds = r;
923 ASSERT(o->parent());
924 if (!o->parent() || !o->parent()->isBox())
925 return false;
926
927 RenderBox* parentRenderBox = toRenderBox(o->parent());
928 IntRect parentBox = parentRenderBox->absoluteContentBox();
929
930 // Make sure the scaled decoration stays square and will fit in its parent's box
931 bounds.setHeight(min(parentBox.width(), min(parentBox.height(), bounds.height())));
932 bounds.setWidth(bounds.height());
933
934 // Center the decoration vertically. Round up though, so if it has to be one pixel off-center, it will
935 // be one pixel closer to the bottom of the field. This tends to look better with the text.
936 bounds.setY(parentBox.y() + (parentBox.height() - bounds.height() + 1) / 2);
937
938 static Image* magnifierImage = Image::loadPlatformResource("searchMagnifier").releaseRef();
939 paintInfo.context->drawImage(magnifierImage, o->style()->colorSpace(), bounds);
940 return false;
941 }
942
adjustSearchFieldResultsButtonStyle(CSSStyleSelector * selector,RenderStyle * style,Element * e) const943 void RenderThemeWin::adjustSearchFieldResultsButtonStyle(CSSStyleSelector* selector, RenderStyle* style, Element* e) const
944 {
945 // Scale the button size based on the font size
946 float fontScale = style->fontSize() / defaultControlFontPixelSize;
947 int magnifierHeight = lroundf(min(max(minSearchFieldResultsDecorationSize, defaultSearchFieldResultsDecorationSize * fontScale),
948 maxSearchFieldResultsDecorationSize));
949 int magnifierWidth = lroundf(magnifierHeight * defaultSearchFieldResultsButtonWidth / defaultSearchFieldResultsDecorationSize);
950 style->setWidth(Length(magnifierWidth, Fixed));
951 style->setHeight(Length(magnifierHeight, Fixed));
952 }
953
paintSearchFieldResultsButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)954 bool RenderThemeWin::paintSearchFieldResultsButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
955 {
956 IntRect bounds = r;
957 ASSERT(o->parent());
958 if (!o->parent())
959 return false;
960 if (!o->parent() || !o->parent()->isBox())
961 return false;
962
963 RenderBox* parentRenderBox = toRenderBox(o->parent());
964 IntRect parentBox = parentRenderBox->absoluteContentBox();
965
966 // Make sure the scaled decoration will fit in its parent's box
967 bounds.setHeight(min(parentBox.height(), bounds.height()));
968 bounds.setWidth(min(parentBox.width(), static_cast<int>(bounds.height() * defaultSearchFieldResultsButtonWidth / defaultSearchFieldResultsDecorationSize)));
969
970 // Center the button vertically. Round up though, so if it has to be one pixel off-center, it will
971 // be one pixel closer to the bottom of the field. This tends to look better with the text.
972 bounds.setY(parentBox.y() + (parentBox.height() - bounds.height() + 1) / 2);
973
974 static Image* magnifierImage = Image::loadPlatformResource("searchMagnifierResults").releaseRef();
975 paintInfo.context->drawImage(magnifierImage, o->style()->colorSpace(), bounds);
976 return false;
977 }
978
979 // Map a CSSValue* system color to an index understood by GetSysColor
cssValueIdToSysColorIndex(int cssValueId)980 static int cssValueIdToSysColorIndex(int cssValueId)
981 {
982 switch (cssValueId) {
983 case CSSValueActiveborder: return COLOR_ACTIVEBORDER;
984 case CSSValueActivecaption: return COLOR_ACTIVECAPTION;
985 case CSSValueAppworkspace: return COLOR_APPWORKSPACE;
986 case CSSValueBackground: return COLOR_BACKGROUND;
987 case CSSValueButtonface: return COLOR_BTNFACE;
988 case CSSValueButtonhighlight: return COLOR_BTNHIGHLIGHT;
989 case CSSValueButtonshadow: return COLOR_BTNSHADOW;
990 case CSSValueButtontext: return COLOR_BTNTEXT;
991 case CSSValueCaptiontext: return COLOR_CAPTIONTEXT;
992 case CSSValueGraytext: return COLOR_GRAYTEXT;
993 case CSSValueHighlight: return COLOR_HIGHLIGHT;
994 case CSSValueHighlighttext: return COLOR_HIGHLIGHTTEXT;
995 case CSSValueInactiveborder: return COLOR_INACTIVEBORDER;
996 case CSSValueInactivecaption: return COLOR_INACTIVECAPTION;
997 case CSSValueInactivecaptiontext: return COLOR_INACTIVECAPTIONTEXT;
998 case CSSValueInfobackground: return COLOR_INFOBK;
999 case CSSValueInfotext: return COLOR_INFOTEXT;
1000 case CSSValueMenu: return COLOR_MENU;
1001 case CSSValueMenutext: return COLOR_MENUTEXT;
1002 case CSSValueScrollbar: return COLOR_SCROLLBAR;
1003 case CSSValueThreeddarkshadow: return COLOR_3DDKSHADOW;
1004 case CSSValueThreedface: return COLOR_3DFACE;
1005 case CSSValueThreedhighlight: return COLOR_3DHIGHLIGHT;
1006 case CSSValueThreedlightshadow: return COLOR_3DLIGHT;
1007 case CSSValueThreedshadow: return COLOR_3DSHADOW;
1008 case CSSValueWindow: return COLOR_WINDOW;
1009 case CSSValueWindowframe: return COLOR_WINDOWFRAME;
1010 case CSSValueWindowtext: return COLOR_WINDOWTEXT;
1011 default: return -1; // Unsupported CSSValue
1012 }
1013 }
1014
systemColor(int cssValueId) const1015 Color RenderThemeWin::systemColor(int cssValueId) const
1016 {
1017 int sysColorIndex = cssValueIdToSysColorIndex(cssValueId);
1018 if (sysColorIndex == -1)
1019 return RenderTheme::systemColor(cssValueId);
1020
1021 COLORREF color = GetSysColor(sysColorIndex);
1022 return Color(GetRValue(color), GetGValue(color), GetBValue(color));
1023 }
1024
1025 #if ENABLE(VIDEO)
1026
extraMediaControlsStyleSheet()1027 String RenderThemeWin::extraMediaControlsStyleSheet()
1028 {
1029 return String(mediaControlsQuickTimeUserAgentStyleSheet, sizeof(mediaControlsQuickTimeUserAgentStyleSheet));
1030 }
1031
supportsClosedCaptioning() const1032 bool RenderThemeWin::supportsClosedCaptioning() const
1033 {
1034 // We rely on QuickTime to render captions so only enable the button for a video element.
1035 #if SAFARI_THEME_VERSION >= 4
1036 return true;
1037 #else
1038 return false;
1039 #endif
1040 }
1041
paintMediaFullscreenButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1042 bool RenderThemeWin::paintMediaFullscreenButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1043 {
1044 return RenderMediaControls::paintMediaControlsPart(MediaFullscreenButton, o, paintInfo, r);
1045 }
1046
paintMediaMuteButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1047 bool RenderThemeWin::paintMediaMuteButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1048 {
1049 return RenderMediaControls::paintMediaControlsPart(MediaMuteButton, o, paintInfo, r);
1050 }
1051
paintMediaPlayButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1052 bool RenderThemeWin::paintMediaPlayButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1053 {
1054 return RenderMediaControls::paintMediaControlsPart(MediaPlayButton, o, paintInfo, r);
1055 }
1056
paintMediaRewindButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1057 bool RenderThemeWin::paintMediaRewindButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1058 {
1059 return RenderMediaControls::paintMediaControlsPart(MediaRewindButton, o, paintInfo, r);
1060 }
1061
paintMediaSeekBackButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1062 bool RenderThemeWin::paintMediaSeekBackButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1063 {
1064 return RenderMediaControls::paintMediaControlsPart(MediaSeekBackButton, o, paintInfo, r);
1065 }
1066
paintMediaSeekForwardButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1067 bool RenderThemeWin::paintMediaSeekForwardButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1068 {
1069 return RenderMediaControls::paintMediaControlsPart(MediaSeekForwardButton, o, paintInfo, r);
1070 }
1071
paintMediaSliderTrack(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1072 bool RenderThemeWin::paintMediaSliderTrack(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1073 {
1074 return RenderMediaControls::paintMediaControlsPart(MediaSlider, o, paintInfo, r);
1075 }
1076
paintMediaSliderThumb(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1077 bool RenderThemeWin::paintMediaSliderThumb(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1078 {
1079 return RenderMediaControls::paintMediaControlsPart(MediaSliderThumb, o, paintInfo, r);
1080 }
1081
paintMediaToggleClosedCaptionsButton(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1082 bool RenderThemeWin::paintMediaToggleClosedCaptionsButton(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1083 {
1084 return RenderMediaControls::paintMediaControlsPart(MediaShowClosedCaptionsButton, o, paintInfo, r);
1085 }
1086
paintMediaControlsBackground(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1087 bool RenderThemeWin::paintMediaControlsBackground(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1088 {
1089 return RenderMediaControls::paintMediaControlsPart(MediaTimelineContainer, o, paintInfo, r);
1090 }
1091
paintMediaVolumeSliderContainer(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1092 bool RenderThemeWin::paintMediaVolumeSliderContainer(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1093 {
1094 return RenderMediaControls::paintMediaControlsPart(MediaVolumeSliderContainer, o, paintInfo, r);
1095 }
1096
paintMediaVolumeSliderTrack(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1097 bool RenderThemeWin::paintMediaVolumeSliderTrack(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1098 {
1099 return RenderMediaControls::paintMediaControlsPart(MediaVolumeSlider, o, paintInfo, r);
1100 }
1101
paintMediaVolumeSliderThumb(RenderObject * o,const PaintInfo & paintInfo,const IntRect & r)1102 bool RenderThemeWin::paintMediaVolumeSliderThumb(RenderObject* o, const PaintInfo& paintInfo, const IntRect& r)
1103 {
1104 return RenderMediaControls::paintMediaControlsPart(MediaVolumeSliderThumb, o, paintInfo, r);
1105 }
1106
volumeSliderOffsetFromMuteButton(RenderBox * muteButtonBox,const IntSize & size) const1107 IntPoint RenderThemeWin::volumeSliderOffsetFromMuteButton(RenderBox* muteButtonBox, const IntSize& size) const
1108 {
1109 return RenderMediaControls::volumeSliderOffsetFromMuteButton(muteButtonBox, size);
1110 }
1111
1112
1113 #endif
1114
1115 }
1116