OLD | NEW |
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/ui/views/tabs/tab.h" | 5 #include "chrome/browser/ui/views/tabs/tab.h" |
6 | 6 |
7 #include <limits> | 7 #include <limits> |
8 | 8 |
9 #include "app/multi_animation.h" | 9 #include "app/multi_animation.h" |
10 #include "app/resource_bundle.h" | 10 #include "app/resource_bundle.h" |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
46 // When a non-mini-tab becomes a mini-tab the width of the tab animates. If | 46 // When a non-mini-tab becomes a mini-tab the width of the tab animates. If |
47 // the width of a mini-tab is >= kMiniTabRendererAsNormalTabWidth then the tab | 47 // the width of a mini-tab is >= kMiniTabRendererAsNormalTabWidth then the tab |
48 // is rendered as a normal tab. This is done to avoid having the title | 48 // is rendered as a normal tab. This is done to avoid having the title |
49 // immediately disappear when transitioning a tab from normal to mini-tab. | 49 // immediately disappear when transitioning a tab from normal to mini-tab. |
50 static const int kMiniTabRendererAsNormalTabWidth = | 50 static const int kMiniTabRendererAsNormalTabWidth = |
51 browser_defaults::kMiniTabWidth + 30; | 51 browser_defaults::kMiniTabWidth + 30; |
52 | 52 |
53 // How opaque to make the hover state (out of 1). | 53 // How opaque to make the hover state (out of 1). |
54 static const double kHoverOpacity = 0.33; | 54 static const double kHoverOpacity = 0.33; |
55 | 55 |
56 Tab::TabImage Tab::tab_alpha = {0}; | 56 Tab::TabImage Tab::tab_alpha_ = {0}; |
57 Tab::TabImage Tab::tab_active = {0}; | 57 Tab::TabImage Tab::tab_active_ = {0}; |
58 Tab::TabImage Tab::tab_inactive = {0}; | 58 Tab::TabImage Tab::tab_inactive_ = {0}; |
59 | 59 |
60 // Durations for the various parts of the mini tab title animation. | 60 // Durations for the various parts of the mini tab title animation. |
61 static const int kMiniTitleChangeAnimationDuration1MS = 1600; | 61 static const int kMiniTitleChangeAnimationDuration1MS = 1600; |
62 static const int kMiniTitleChangeAnimationStart1MS = 0; | 62 static const int kMiniTitleChangeAnimationStart1MS = 0; |
63 static const int kMiniTitleChangeAnimationEnd1MS = 1900; | 63 static const int kMiniTitleChangeAnimationEnd1MS = 1900; |
64 static const int kMiniTitleChangeAnimationDuration2MS = 0; | 64 static const int kMiniTitleChangeAnimationDuration2MS = 0; |
65 static const int kMiniTitleChangeAnimationDuration3MS = 550; | 65 static const int kMiniTitleChangeAnimationDuration3MS = 550; |
66 static const int kMiniTitleChangeAnimationStart3MS = 150; | 66 static const int kMiniTitleChangeAnimationStart3MS = 150; |
67 static const int kMiniTitleChangeAnimationEnd3MS = 800; | 67 static const int kMiniTitleChangeAnimationEnd3MS = 800; |
68 | 68 |
69 // Offset from the right edge for the start of the mini title change animation. | 69 // Offset from the right edge for the start of the mini title change animation. |
70 static const int kMiniTitleChangeInitialXOffset = 6; | 70 static const int kMiniTitleChangeInitialXOffset = 6; |
71 | 71 |
72 // Radius of the radial gradient used for mini title change animation. | 72 // Radius of the radial gradient used for mini title change animation. |
73 static const int kMiniTitleChangeGradientRadius = 20; | 73 static const int kMiniTitleChangeGradientRadius = 20; |
74 | 74 |
75 // Colors of the gradient used during the mini title change animation. | 75 // Colors of the gradient used during the mini title change animation. |
76 static const SkColor kMiniTitleChangeGradientColor1 = SK_ColorWHITE; | 76 static const SkColor kMiniTitleChangeGradientColor1 = SK_ColorWHITE; |
77 static const SkColor kMiniTitleChangeGradientColor2 = | 77 static const SkColor kMiniTitleChangeGradientColor2 = |
78 SkColorSetARGB(0, 255, 255, 255); | 78 SkColorSetARGB(0, 255, 255, 255); |
79 | 79 |
80 // Hit mask constants. | 80 // Hit mask constants. |
81 static const SkScalar kTabCapWidth = 15; | 81 static const SkScalar kTabCapWidth = 15; |
82 static const SkScalar kTabTopCurveWidth = 4; | 82 static const SkScalar kTabTopCurveWidth = 4; |
83 static const SkScalar kTabBottomCurveWidth = 3; | 83 static const SkScalar kTabBottomCurveWidth = 3; |
84 | 84 |
85 namespace { | |
86 | |
87 void InitTabResources() { | |
88 static bool initialized = false; | |
89 if (initialized) | |
90 return; | |
91 | |
92 initialized = true; | |
93 Tab::LoadTabImages(); | |
94 } | |
95 | |
96 } // namespace | |
97 | |
98 // static | 85 // static |
99 const char Tab::kViewClassName[] = "browser/tabs/Tab"; | 86 const char Tab::kViewClassName[] = "browser/tabs/Tab"; |
100 | 87 |
101 //////////////////////////////////////////////////////////////////////////////// | 88 //////////////////////////////////////////////////////////////////////////////// |
102 // Tab, public: | 89 // Tab, public: |
103 | 90 |
104 Tab::Tab(TabController* controller) | 91 Tab::Tab(TabController* controller) |
105 : BaseTab(controller), | 92 : BaseTab(controller), |
106 showing_icon_(false), | 93 showing_icon_(false), |
107 showing_close_button_(false), | 94 showing_close_button_(false), |
(...skipping 22 matching lines...) Expand all Loading... |
130 mini_title_animation_->set_delegate(this); | 117 mini_title_animation_->set_delegate(this); |
131 } | 118 } |
132 mini_title_animation_->Start(); | 119 mini_title_animation_->Start(); |
133 } | 120 } |
134 | 121 |
135 void Tab::StopMiniTabTitleAnimation() { | 122 void Tab::StopMiniTabTitleAnimation() { |
136 if (mini_title_animation_.get()) | 123 if (mini_title_animation_.get()) |
137 mini_title_animation_->Stop(); | 124 mini_title_animation_->Stop(); |
138 } | 125 } |
139 | 126 |
140 void Tab::PaintIcon(gfx::Canvas* canvas) { | |
141 BaseTab::PaintIcon(canvas, favicon_bounds_.x(), favicon_bounds_.y()); | |
142 } | |
143 | |
144 // static | 127 // static |
145 gfx::Size Tab::GetMinimumUnselectedSize() { | 128 gfx::Size Tab::GetMinimumUnselectedSize() { |
146 InitTabResources(); | 129 InitTabResources(); |
147 | 130 |
148 gfx::Size minimum_size; | 131 gfx::Size minimum_size; |
149 minimum_size.set_width(kLeftPadding + kRightPadding); | 132 minimum_size.set_width(kLeftPadding + kRightPadding); |
150 // Since we use bitmap images, the real minimum height of the image is | 133 // Since we use bitmap images, the real minimum height of the image is |
151 // defined most accurately by the height of the end cap images. | 134 // defined most accurately by the height of the end cap images. |
152 minimum_size.set_height(tab_active.image_l->height()); | 135 minimum_size.set_height(tab_active_.image_l->height()); |
153 return minimum_size; | 136 return minimum_size; |
154 } | 137 } |
155 | 138 |
156 // static | 139 // static |
157 gfx::Size Tab::GetMinimumSelectedSize() { | 140 gfx::Size Tab::GetMinimumSelectedSize() { |
158 gfx::Size minimum_size = GetMinimumUnselectedSize(); | 141 gfx::Size minimum_size = GetMinimumUnselectedSize(); |
159 minimum_size.set_width(kLeftPadding + kFavIconSize + kRightPadding); | 142 minimum_size.set_width(kLeftPadding + kFavIconSize + kRightPadding); |
160 return minimum_size; | 143 return minimum_size; |
161 } | 144 } |
162 | 145 |
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
311 // as child Views (which is the preferred method). Instead, these UI elements | 294 // as child Views (which is the preferred method). Instead, these UI elements |
312 // are drawn directly on the canvas from within Tab::Paint(). The Tab's child | 295 // are drawn directly on the canvas from within Tab::Paint(). The Tab's child |
313 // Views (for example, the Tab's close button which is a views::Button | 296 // Views (for example, the Tab's close button which is a views::Button |
314 // instance) are automatically mirrored by the mirroring infrastructure in | 297 // instance) are automatically mirrored by the mirroring infrastructure in |
315 // views. The elements Tab draws directly on the canvas need to be manually | 298 // views. The elements Tab draws directly on the canvas need to be manually |
316 // mirrored if the View's layout is right-to-left. | 299 // mirrored if the View's layout is right-to-left. |
317 title_bounds_.set_x(MirroredLeftPointForRect(title_bounds_)); | 300 title_bounds_.set_x(MirroredLeftPointForRect(title_bounds_)); |
318 } | 301 } |
319 | 302 |
320 void Tab::OnThemeChanged() { | 303 void Tab::OnThemeChanged() { |
321 Tab::LoadTabImages(); | 304 LoadTabImages(); |
322 } | 305 } |
323 | 306 |
324 bool Tab::HasHitTestMask() const { | 307 bool Tab::HasHitTestMask() const { |
325 return true; | 308 return true; |
326 } | 309 } |
327 | 310 |
328 void Tab::GetHitTestMask(gfx::Path* path) const { | 311 void Tab::GetHitTestMask(gfx::Path* path) const { |
329 DCHECK(path); | 312 DCHECK(path); |
330 | 313 |
331 SkScalar h = SkIntToScalar(height()); | 314 SkScalar h = SkIntToScalar(height()); |
(...skipping 28 matching lines...) Expand all Loading... |
360 void Tab::OnMouseMoved(const views::MouseEvent& e) { | 343 void Tab::OnMouseMoved(const views::MouseEvent& e) { |
361 hover_point_ = e.location(); | 344 hover_point_ = e.location(); |
362 // We need to redraw here because otherwise the hover glow does not update | 345 // We need to redraw here because otherwise the hover glow does not update |
363 // and follow the new mouse position. | 346 // and follow the new mouse position. |
364 SchedulePaint(); | 347 SchedulePaint(); |
365 } | 348 } |
366 | 349 |
367 //////////////////////////////////////////////////////////////////////////////// | 350 //////////////////////////////////////////////////////////////////////////////// |
368 // Tab, private | 351 // Tab, private |
369 | 352 |
| 353 void Tab::PaintIcon(gfx::Canvas* canvas) { |
| 354 BaseTab::PaintIcon(canvas, favicon_bounds_.x(), favicon_bounds_.y()); |
| 355 } |
| 356 |
370 void Tab::PaintTabBackground(gfx::Canvas* canvas) { | 357 void Tab::PaintTabBackground(gfx::Canvas* canvas) { |
371 if (IsSelected()) { | 358 if (IsSelected()) { |
372 PaintActiveTabBackground(canvas); | 359 PaintActiveTabBackground(canvas); |
373 } else { | 360 } else { |
374 if (mini_title_animation_.get() && mini_title_animation_->is_animating()) | 361 if (mini_title_animation_.get() && mini_title_animation_->is_animating()) |
375 PaintInactiveTabBackgroundWithTitleChange(canvas); | 362 PaintInactiveTabBackgroundWithTitleChange(canvas); |
376 else | 363 else |
377 PaintInactiveTabBackground(canvas); | 364 PaintInactiveTabBackground(canvas); |
378 | 365 |
379 double throb_value = GetThrobValue(); | 366 double throb_value = GetThrobValue(); |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
455 if (GetWidget() && | 442 if (GetWidget() && |
456 GetWidget()->GetWindow()->GetNonClientView()->UseNativeFrame()) { | 443 GetWidget()->GetWindow()->GetNonClientView()->UseNativeFrame()) { |
457 tab_id = IDR_THEME_TAB_BACKGROUND_V; | 444 tab_id = IDR_THEME_TAB_BACKGROUND_V; |
458 } else { | 445 } else { |
459 tab_id = is_otr ? IDR_THEME_TAB_BACKGROUND_INCOGNITO : | 446 tab_id = is_otr ? IDR_THEME_TAB_BACKGROUND_INCOGNITO : |
460 IDR_THEME_TAB_BACKGROUND; | 447 IDR_THEME_TAB_BACKGROUND; |
461 } | 448 } |
462 | 449 |
463 SkBitmap* tab_bg = GetThemeProvider()->GetBitmapNamed(tab_id); | 450 SkBitmap* tab_bg = GetThemeProvider()->GetBitmapNamed(tab_id); |
464 | 451 |
465 TabImage* tab_image = &tab_active; | 452 TabImage* tab_image = &tab_active_; |
466 TabImage* tab_inactive_image = &tab_inactive; | 453 TabImage* tab_inactive_image = &tab_inactive_; |
467 TabImage* alpha = &tab_alpha; | 454 TabImage* alpha = &tab_alpha_; |
468 | 455 |
469 // If the theme is providing a custom background image, then its top edge | 456 // If the theme is providing a custom background image, then its top edge |
470 // should be at the top of the tab. Otherwise, we assume that the background | 457 // should be at the top of the tab. Otherwise, we assume that the background |
471 // image is a composited foreground + frame image. | 458 // image is a composited foreground + frame image. |
472 int bg_offset_y = GetThemeProvider()->HasCustomImage(tab_id) ? | 459 int bg_offset_y = GetThemeProvider()->HasCustomImage(tab_id) ? |
473 0 : background_offset_.y(); | 460 0 : background_offset_.y(); |
474 | 461 |
475 // We need a CanvasSkia object to be able to extract the bitmap from. | 462 // We need a CanvasSkia object to be able to extract the bitmap from. |
476 // We draw everything to this canvas and then output it to the canvas | 463 // We draw everything to this canvas and then output it to the canvas |
477 // parameter in addition to using it to mask the hover glow if needed. | 464 // parameter in addition to using it to mask the hover glow if needed. |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
529 tab_inactive_image->r_width, | 516 tab_inactive_image->r_width, |
530 height()); | 517 height()); |
531 canvas->DrawBitmapInt(*tab_inactive_image->image_r, | 518 canvas->DrawBitmapInt(*tab_inactive_image->image_r, |
532 width() - tab_inactive_image->r_width, 0); | 519 width() - tab_inactive_image->r_width, 0); |
533 } | 520 } |
534 | 521 |
535 void Tab::PaintActiveTabBackground(gfx::Canvas* canvas) { | 522 void Tab::PaintActiveTabBackground(gfx::Canvas* canvas) { |
536 int offset = GetX(views::View::APPLY_MIRRORING_TRANSFORMATION) + | 523 int offset = GetX(views::View::APPLY_MIRRORING_TRANSFORMATION) + |
537 background_offset_.x(); | 524 background_offset_.x(); |
538 ThemeProvider* tp = GetThemeProvider(); | 525 ThemeProvider* tp = GetThemeProvider(); |
539 if (!tp) | 526 DCHECK(tp) << "Unable to get theme provider"; |
540 NOTREACHED() << "Unable to get theme provider"; | |
541 | 527 |
542 SkBitmap* tab_bg = GetThemeProvider()->GetBitmapNamed(IDR_THEME_TOOLBAR); | 528 SkBitmap* tab_bg = GetThemeProvider()->GetBitmapNamed(IDR_THEME_TOOLBAR); |
543 | 529 |
544 TabImage* tab_image = &tab_active; | 530 TabImage* tab_image = &tab_active_; |
545 TabImage* alpha = &tab_alpha; | 531 TabImage* alpha = &tab_alpha_; |
546 | 532 |
547 // Draw left edge. | 533 // Draw left edge. |
548 SkBitmap tab_l = SkBitmapOperations::CreateTiledBitmap( | 534 SkBitmap tab_l = SkBitmapOperations::CreateTiledBitmap( |
549 *tab_bg, offset, 0, tab_image->l_width, height()); | 535 *tab_bg, offset, 0, tab_image->l_width, height()); |
550 SkBitmap theme_l = | 536 SkBitmap theme_l = |
551 SkBitmapOperations::CreateMaskedBitmap(tab_l, *alpha->image_l); | 537 SkBitmapOperations::CreateMaskedBitmap(tab_l, *alpha->image_l); |
552 canvas->DrawBitmapInt(theme_l, 0, 0); | 538 canvas->DrawBitmapInt(theme_l, 0, 0); |
553 | 539 |
554 // Draw right edge. | 540 // Draw right edge. |
555 SkBitmap tab_r = SkBitmapOperations::CreateTiledBitmap(*tab_bg, | 541 SkBitmap tab_r = SkBitmapOperations::CreateTiledBitmap(*tab_bg, |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
642 return pulse_animation()->GetCurrentValue() * kHoverOpacity; | 628 return pulse_animation()->GetCurrentValue() * kHoverOpacity; |
643 | 629 |
644 return hover_animation() ? | 630 return hover_animation() ? |
645 kHoverOpacity * hover_animation()->GetCurrentValue() : 0; | 631 kHoverOpacity * hover_animation()->GetCurrentValue() : 0; |
646 } | 632 } |
647 | 633 |
648 //////////////////////////////////////////////////////////////////////////////// | 634 //////////////////////////////////////////////////////////////////////////////// |
649 // Tab, private: | 635 // Tab, private: |
650 | 636 |
651 // static | 637 // static |
| 638 void Tab::InitTabResources() { |
| 639 static bool initialized = false; |
| 640 if (initialized) |
| 641 return; |
| 642 |
| 643 initialized = true; |
| 644 |
| 645 // Load the tab images once now, and maybe again later if the theme changes. |
| 646 LoadTabImages(); |
| 647 } |
| 648 |
| 649 // static |
652 void Tab::LoadTabImages() { | 650 void Tab::LoadTabImages() { |
653 // We're not letting people override tab images just yet. | 651 // We're not letting people override tab images just yet. |
654 ResourceBundle& rb = ResourceBundle::GetSharedInstance(); | 652 ResourceBundle& rb = ResourceBundle::GetSharedInstance(); |
655 | 653 |
656 tab_alpha.image_l = rb.GetBitmapNamed(IDR_TAB_ALPHA_LEFT); | 654 tab_alpha_.image_l = rb.GetBitmapNamed(IDR_TAB_ALPHA_LEFT); |
657 tab_alpha.image_r = rb.GetBitmapNamed(IDR_TAB_ALPHA_RIGHT); | 655 tab_alpha_.image_r = rb.GetBitmapNamed(IDR_TAB_ALPHA_RIGHT); |
658 | 656 |
659 tab_active.image_l = rb.GetBitmapNamed(IDR_TAB_ACTIVE_LEFT); | 657 tab_active_.image_l = rb.GetBitmapNamed(IDR_TAB_ACTIVE_LEFT); |
660 tab_active.image_c = rb.GetBitmapNamed(IDR_TAB_ACTIVE_CENTER); | 658 tab_active_.image_c = rb.GetBitmapNamed(IDR_TAB_ACTIVE_CENTER); |
661 tab_active.image_r = rb.GetBitmapNamed(IDR_TAB_ACTIVE_RIGHT); | 659 tab_active_.image_r = rb.GetBitmapNamed(IDR_TAB_ACTIVE_RIGHT); |
662 tab_active.l_width = tab_active.image_l->width(); | 660 tab_active_.l_width = tab_active_.image_l->width(); |
663 tab_active.r_width = tab_active.image_r->width(); | 661 tab_active_.r_width = tab_active_.image_r->width(); |
664 | 662 |
665 tab_inactive.image_l = rb.GetBitmapNamed(IDR_TAB_INACTIVE_LEFT); | 663 tab_inactive_.image_l = rb.GetBitmapNamed(IDR_TAB_INACTIVE_LEFT); |
666 tab_inactive.image_c = rb.GetBitmapNamed(IDR_TAB_INACTIVE_CENTER); | 664 tab_inactive_.image_c = rb.GetBitmapNamed(IDR_TAB_INACTIVE_CENTER); |
667 tab_inactive.image_r = rb.GetBitmapNamed(IDR_TAB_INACTIVE_RIGHT); | 665 tab_inactive_.image_r = rb.GetBitmapNamed(IDR_TAB_INACTIVE_RIGHT); |
668 tab_inactive.l_width = tab_inactive.image_l->width(); | 666 tab_inactive_.l_width = tab_inactive_.image_l->width(); |
669 tab_inactive.r_width = tab_inactive.image_r->width(); | 667 tab_inactive_.r_width = tab_inactive_.image_r->width(); |
670 } | 668 } |
OLD | NEW |