Home | History | Annotate | Download | only in native_theme
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "ui/native_theme/common_theme.h"
      6 
      7 #include "base/logging.h"
      8 #include "grit/ui_resources.h"
      9 #include "third_party/skia/include/core/SkCanvas.h"
     10 #include "ui/base/resource/resource_bundle.h"
     11 #include "ui/gfx/canvas.h"
     12 #include "ui/gfx/color_utils.h"
     13 #include "ui/gfx/image/image_skia.h"
     14 #include "ui/gfx/rect.h"
     15 #include "ui/gfx/skia_util.h"
     16 #include "ui/gfx/sys_color_change_listener.h"
     17 
     18 namespace {
     19 
     20 // Theme colors returned by GetSystemColor().
     21 
     22 // MenuItem:
     23 const SkColor kMenuBackgroundColor = SK_ColorWHITE;
     24 const SkColor kMenuHighlightBackgroundColor = SkColorSetRGB(0x42, 0x81, 0xF4);
     25 const SkColor kMenuInvertedSchemeHighlightBackgroundColor =
     26     SkColorSetRGB(48, 48, 48);
     27 const SkColor kMenuBorderColor = SkColorSetRGB(0xBA, 0xBA, 0xBA);
     28 const SkColor kEnabledMenuButtonBorderColor = SkColorSetARGB(36, 0, 0, 0);
     29 const SkColor kFocusedMenuButtonBorderColor = SkColorSetARGB(72, 0, 0, 0);
     30 const SkColor kHoverMenuButtonBorderColor = SkColorSetARGB(72, 0, 0, 0);
     31 const SkColor kMenuSeparatorColor = SkColorSetRGB(0xE9, 0xE9, 0xE9);
     32 const SkColor kEnabledMenuItemForegroundColor = SK_ColorBLACK;
     33 const SkColor kDisabledMenuItemForegroundColor = SkColorSetRGB(161, 161, 146);
     34 const SkColor kHoverMenuItemBackgroundColor =
     35     SkColorSetARGB(204, 255, 255, 255);
     36 // Button:
     37 const SkColor kButtonHoverBackgroundColor = SkColorSetRGB(0xEA, 0xEA, 0xEA);
     38 const SkColor kBlueButtonEnabledColor = SK_ColorWHITE;
     39 const SkColor kBlueButtonDisabledColor = SK_ColorWHITE;
     40 const SkColor kBlueButtonHighlightColor = SK_ColorWHITE;
     41 const SkColor kBlueButtonHoverColor = SK_ColorWHITE;
     42 
     43 }  // namespace
     44 
     45 namespace ui {
     46 
     47 bool CommonThemeGetSystemColor(NativeTheme::ColorId color_id, SkColor* color) {
     48   switch (color_id) {
     49     // MenuItem
     50     case NativeTheme::kColorId_MenuBorderColor:
     51       *color = kMenuBorderColor;
     52       break;
     53     case NativeTheme::kColorId_EnabledMenuButtonBorderColor:
     54       *color = kEnabledMenuButtonBorderColor;
     55       break;
     56     case NativeTheme::kColorId_FocusedMenuButtonBorderColor:
     57       *color = kFocusedMenuButtonBorderColor;
     58       break;
     59     case NativeTheme::kColorId_HoverMenuButtonBorderColor:
     60       *color = kHoverMenuButtonBorderColor;
     61       break;
     62     case NativeTheme::kColorId_MenuSeparatorColor:
     63       *color = kMenuSeparatorColor;
     64       break;
     65     case NativeTheme::kColorId_MenuBackgroundColor:
     66       *color = kMenuBackgroundColor;
     67       break;
     68     case NativeTheme::kColorId_FocusedMenuItemBackgroundColor:
     69       *color = kMenuHighlightBackgroundColor;
     70       break;
     71     case NativeTheme::kColorId_HoverMenuItemBackgroundColor:
     72       *color = kHoverMenuItemBackgroundColor;
     73       break;
     74     case NativeTheme::kColorId_EnabledMenuItemForegroundColor:
     75       *color = kEnabledMenuItemForegroundColor;
     76       break;
     77     case NativeTheme::kColorId_DisabledMenuItemForegroundColor:
     78       *color = kDisabledMenuItemForegroundColor;
     79       break;
     80     case NativeTheme::kColorId_DisabledEmphasizedMenuItemForegroundColor:
     81       *color = SK_ColorBLACK;
     82       break;
     83     case NativeTheme::kColorId_SelectedMenuItemForegroundColor:
     84       *color = SK_ColorWHITE;
     85       break;
     86     case NativeTheme::kColorId_ButtonDisabledColor:
     87       *color = kDisabledMenuItemForegroundColor;
     88       break;
     89     // Button
     90     case NativeTheme::kColorId_ButtonHoverBackgroundColor:
     91       *color = kButtonHoverBackgroundColor;
     92       break;
     93     case NativeTheme::kColorId_BlueButtonEnabledColor:
     94       *color = kBlueButtonEnabledColor;
     95       break;
     96     case NativeTheme::kColorId_BlueButtonDisabledColor:
     97       *color = kBlueButtonDisabledColor;
     98       break;
     99     case NativeTheme::kColorId_BlueButtonHighlightColor:
    100       *color = kBlueButtonHighlightColor;
    101       break;
    102     case NativeTheme::kColorId_BlueButtonHoverColor:
    103       *color = kBlueButtonHoverColor;
    104       break;
    105     default:
    106       return false;
    107   }
    108 
    109   if (gfx::IsInvertedColorScheme()) {
    110     switch (color_id) {
    111       case NativeTheme::kColorId_FocusedMenuItemBackgroundColor:
    112         *color = kMenuInvertedSchemeHighlightBackgroundColor;
    113         break;
    114       default:
    115         *color = color_utils::InvertColor(*color);
    116     }
    117   }
    118   return true;
    119 }
    120 
    121 gfx::Size CommonThemeGetPartSize(NativeTheme::Part part,
    122                                  NativeTheme::State state,
    123                                  const NativeTheme::ExtraParams& extra) {
    124   gfx::Size size;
    125   switch (part) {
    126     case NativeTheme::kComboboxArrow:
    127       return ui::ResourceBundle::GetSharedInstance().GetImageNamed(
    128           IDR_MENU_DROPARROW).Size();
    129 
    130     case NativeTheme::kMenuCheck: {
    131       const gfx::ImageSkia* check =
    132           ui::ResourceBundle::GetSharedInstance().GetImageNamed(
    133               IDR_MENU_CHECK_CHECKED).ToImageSkia();
    134       size.SetSize(check->width(), check->height());
    135       break;
    136     }
    137     default:
    138       break;
    139   }
    140 
    141   return size;
    142 }
    143 
    144 void CommonThemePaintComboboxArrow(SkCanvas* canvas, const gfx::Rect& rect) {
    145   gfx::ImageSkia* arrow = ui::ResourceBundle::GetSharedInstance().
    146       GetImageSkiaNamed(IDR_MENU_DROPARROW);
    147   CommonThemeCreateCanvas(canvas)->DrawImageInt(*arrow, rect.x(), rect.y());
    148 }
    149 
    150 void CommonThemePaintMenuSeparator(
    151     SkCanvas* canvas,
    152     const gfx::Rect& rect,
    153     const NativeTheme::MenuSeparatorExtraParams& extra) {
    154   SkColor color;
    155   CommonThemeGetSystemColor(NativeTheme::kColorId_MenuSeparatorColor, &color);
    156   SkPaint paint;
    157   paint.setColor(kMenuSeparatorColor);
    158   int position_y = rect.y() + rect.height() / 2;
    159   canvas->drawLine(rect.x(), position_y, rect.right(), position_y, paint);
    160 }
    161 
    162 void CommonThemePaintMenuGutter(SkCanvas* canvas, const gfx::Rect& rect) {
    163   SkColor color;
    164   CommonThemeGetSystemColor(NativeTheme::kColorId_MenuSeparatorColor, &color);
    165   SkPaint paint;
    166   paint.setColor(kMenuSeparatorColor);
    167   int position_x = rect.x() + rect.width() / 2;
    168   canvas->drawLine(position_x, rect.y(), position_x, rect.bottom(), paint);
    169 }
    170 
    171 void CommonThemePaintMenuBackground(SkCanvas* canvas, const gfx::Rect& rect) {
    172   SkColor color;
    173   CommonThemeGetSystemColor(NativeTheme::kColorId_MenuBackgroundColor, &color);
    174   SkPaint paint;
    175   paint.setColor(color);
    176   canvas->drawRect(gfx::RectToSkRect(rect), paint);
    177 }
    178 
    179 void CommonThemePaintMenuItemBackground(SkCanvas* canvas,
    180                                         NativeTheme::State state,
    181                                         const gfx::Rect& rect) {
    182   SkColor color;
    183   SkPaint paint;
    184   switch (state) {
    185     case NativeTheme::kNormal:
    186     case NativeTheme::kDisabled:
    187       CommonThemeGetSystemColor(NativeTheme::kColorId_MenuBackgroundColor,
    188                                 &color);
    189       paint.setColor(color);
    190       break;
    191     case NativeTheme::kHovered:
    192       CommonThemeGetSystemColor(
    193           NativeTheme::kColorId_FocusedMenuItemBackgroundColor, &color);
    194       paint.setColor(color);
    195       break;
    196     default:
    197       NOTREACHED() << "Invalid state " << state;
    198       break;
    199   }
    200   canvas->drawRect(gfx::RectToSkRect(rect), paint);
    201 }
    202 
    203 // static
    204 scoped_ptr<gfx::Canvas> CommonThemeCreateCanvas(SkCanvas* sk_canvas) {
    205   // TODO(pkotwicz): Do something better and don't infer device
    206   // scale factor from canvas scale.
    207   SkMatrix m = sk_canvas->getTotalMatrix();
    208   float device_scale = static_cast<float>(SkScalarAbs(m.getScaleX()));
    209   return scoped_ptr<gfx::Canvas>(
    210       gfx::Canvas::CreateCanvasWithoutScaling(sk_canvas, device_scale));
    211 }
    212 
    213 }  // namespace ui
    214