Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / chrome / browser / ui / views / tab_icon_view.cc
blob1c0e8366824e9ec34a54fd12f7d4d22494b8cea6
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.
5 #include "chrome/browser/ui/views/tab_icon_view.h"
7 #if defined(OS_WIN)
8 #include <windows.h>
9 #include <shellapi.h>
10 #endif
12 #include "base/logging.h"
13 #include "base/memory/scoped_ptr.h"
14 #include "chrome/app/chrome_command_ids.h"
15 #include "chrome/browser/ui/views/tab_icon_view_model.h"
16 #include "grit/theme_resources.h"
17 #include "ui/base/resource/resource_bundle.h"
18 #include "ui/base/theme_provider.h"
19 #include "ui/gfx/canvas.h"
20 #include "ui/gfx/favicon_size.h"
21 #include "ui/gfx/paint_throbber.h"
22 #include "ui/native_theme/native_theme.h"
23 #include "ui/resources/grit/ui_resources.h"
25 #if defined(OS_WIN)
26 #include "chrome/browser/app_icon_win.h"
27 #include "ui/gfx/icon_util.h"
28 #endif
30 namespace {
32 bool g_initialized = false;
33 gfx::ImageSkia* g_default_favicon = nullptr;
35 } // namespace
37 // static
38 void TabIconView::InitializeIfNeeded() {
39 if (!g_initialized) {
40 g_initialized = true;
42 #if defined(OS_WIN)
43 // The default window icon is the application icon, not the default
44 // favicon.
45 HICON app_icon = GetAppIcon();
46 scoped_ptr<SkBitmap> bitmap(
47 IconUtil::CreateSkBitmapFromHICON(app_icon, gfx::Size(16, 16)));
48 g_default_favicon = new gfx::ImageSkia(gfx::ImageSkiaRep(*bitmap, 1.0f));
49 DestroyIcon(app_icon);
50 #else
51 ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance();
52 g_default_favicon = rb.GetImageSkiaNamed(IDR_PRODUCT_LOGO_16);
53 #endif
57 TabIconView::TabIconView(chrome::TabIconViewModel* model,
58 views::MenuButtonListener* listener)
59 : views::MenuButton(NULL, base::string16(), listener, false),
60 model_(model),
61 is_light_(false) {
62 InitializeIfNeeded();
65 TabIconView::~TabIconView() {
68 void TabIconView::Update() {
69 if (!model_->ShouldTabIconViewAnimate())
70 throbber_start_time_ = base::TimeTicks();
72 SchedulePaint();
75 void TabIconView::PaintThrobber(gfx::Canvas* canvas) {
76 if (throbber_start_time_ == base::TimeTicks())
77 throbber_start_time_ = base::TimeTicks::Now();
79 gfx::PaintThrobberSpinning(
80 canvas, GetLocalBounds(),
81 GetNativeTheme()->GetSystemColor(
82 is_light_ ? ui::NativeTheme::kColorId_ThrobberLightColor
83 : ui::NativeTheme::kColorId_ThrobberSpinningColor),
84 base::TimeTicks::Now() - throbber_start_time_);
87 void TabIconView::PaintFavicon(gfx::Canvas* canvas,
88 const gfx::ImageSkia& image) {
89 // For source images smaller than the favicon square, scale them as if they
90 // were padded to fit the favicon square, so we don't blow up tiny favicons
91 // into larger or nonproportional results.
92 float float_src_w = static_cast<float>(image.width());
93 float float_src_h = static_cast<float>(image.height());
94 float scalable_w, scalable_h;
95 if (image.width() <= gfx::kFaviconSize &&
96 image.height() <= gfx::kFaviconSize) {
97 scalable_w = scalable_h = gfx::kFaviconSize;
98 } else {
99 scalable_w = float_src_w;
100 scalable_h = float_src_h;
103 // Scale proportionately.
104 float scale = std::min(static_cast<float>(width()) / scalable_w,
105 static_cast<float>(height()) / scalable_h);
106 int dest_w = static_cast<int>(float_src_w * scale);
107 int dest_h = static_cast<int>(float_src_h * scale);
109 // Center the scaled image.
110 canvas->DrawImageInt(image, 0, 0, image.width(), image.height(),
111 (width() - dest_w) / 2, (height() - dest_h) / 2, dest_w,
112 dest_h, true);
115 gfx::Size TabIconView::GetPreferredSize() const {
116 return gfx::Size(gfx::kFaviconSize, gfx::kFaviconSize);
119 const char* TabIconView::GetClassName() const {
120 return "TabIconView";
123 void TabIconView::OnPaint(gfx::Canvas* canvas) {
124 bool rendered = false;
126 if (model_->ShouldTabIconViewAnimate()) {
127 rendered = true;
128 PaintThrobber(canvas);
129 } else {
130 gfx::ImageSkia favicon = model_->GetFaviconForTabIconView();
131 if (!favicon.isNull()) {
132 rendered = true;
133 PaintFavicon(canvas, favicon);
137 if (!rendered)
138 PaintFavicon(canvas, *g_default_favicon);