| Index: chrome/browser/ui/views/sidebar/sidebar_tab.cc
|
| ===================================================================
|
| --- chrome/browser/ui/views/sidebar/sidebar_tab.cc (revision 0)
|
| +++ chrome/browser/ui/views/sidebar/sidebar_tab.cc (revision 0)
|
| @@ -0,0 +1,247 @@
|
| +// Copyright (c) 2010 The Chromium Authors. All rights reserved.
|
| +// Use of this source code is governed by a BSD-style license that can be
|
| +// found in the LICENSE file.
|
| +
|
| +#include "chrome/browser/ui/views/sidebar/sidebar_tab.h"
|
| +
|
| +#include <limits>
|
| +
|
| +#include "chrome/browser/defaults.h"
|
| +#include "chrome/browser/themes/browser_theme_provider.h"
|
| +#include "chrome/common/extensions/extension.h"
|
| +#include "gfx/canvas_skia.h"
|
| +#include "gfx/path.h"
|
| +#include "gfx/skbitmap_operations.h"
|
| +#include "grit/app_resources.h"
|
| +#include "grit/generated_resources.h"
|
| +#include "grit/theme_resources.h"
|
| +#include "ui/base/animation/slide_animation.h"
|
| +#include "ui/base/animation/throb_animation.h"
|
| +#include "ui/base/resource/resource_bundle.h"
|
| +#include "views/widget/tooltip_manager.h"
|
| +
|
| +namespace {
|
| +
|
| +// Hit mask constants.
|
| +const SkScalar kTabCapCurveWidth = 3;
|
| +
|
| +// Icon transparency constants.
|
| +const int kOpaque = 255;
|
| +const int kCollapsedOpacityPercents = 80;
|
| +const int kExpandedActiveOpacityPercents = 100;
|
| +const int kExpandedInactiveOpacityPercents = 60;
|
| +
|
| +// SidebarTab's background image cache helper.
|
| +struct CachedImage {
|
| + CachedImage()
|
| + : image(NULL),
|
| + width(0),
|
| + height(0) {
|
| + }
|
| + // Loads an image with |resource_id| from resources.
|
| + void Load(int resource_id);
|
| +
|
| + SkBitmap* image;
|
| + int width;
|
| + int height;
|
| +};
|
| +
|
| +void CachedImage::Load(int resource_id) {
|
| + image = ResourceBundle::GetSharedInstance().GetBitmapNamed(resource_id);
|
| + width = image->width();
|
| + height = image->height();
|
| +}
|
| +
|
| +} // namespace
|
| +
|
| +// static
|
| +const char SidebarTab::kViewClassName[] = "browser/ui/views/sidebar/SidebarTab";
|
| +
|
| +// SidebarTab, background images cache:
|
| +
|
| +// Caches tab's background image for the particular tab state (active/inactive).
|
| +struct SidebarTab::TabImage {
|
| + CachedImage tab;
|
| +};
|
| +
|
| +// Caches all background images.
|
| +struct SidebarTab::TabImages {
|
| + TabImages();
|
| + // Loads all images from resources.
|
| + void Load();
|
| +
|
| + TabImage active;
|
| + TabImage inactive;
|
| +};
|
| +
|
| +SidebarTab::TabImages::TabImages() {
|
| + Load();
|
| +}
|
| +
|
| +void SidebarTab::TabImages::Load() {
|
| + active.tab.Load(IDR_SIDEBAR_TAB_ACTIVE);
|
| + inactive.tab.Load(IDR_SIDEBAR_TAB_INACTIVE);
|
| +}
|
| +
|
| +// SidebarTab, public:
|
| +
|
| +SidebarTab::SidebarTab(SidebarTabController* controller)
|
| + : SidebarBaseTab(controller) {
|
| +}
|
| +
|
| +SidebarTab::~SidebarTab() {
|
| +}
|
| +
|
| +void SidebarTab::GetShape(gfx::Path* shape) const {
|
| + SkScalar h = SkIntToScalar(height());
|
| + SkScalar w = SkIntToScalar(width());
|
| +
|
| + // When there's not enough space for properly formed caps, use the simpler
|
| + // tab shape (it happens during first frames of the insert tab animation).
|
| + if (h <= kTabCapCurveWidth * 2) {
|
| + shape->moveTo(w, 0);
|
| + shape->lineTo(w, h);
|
| + shape->lineTo(0, h);
|
| + shape->close();
|
| + return;
|
| + }
|
| +
|
| + // Foot of the tab.
|
| + shape->moveTo(w, 0);
|
| + shape->lineTo(w, h);
|
| + // Bottom cap.
|
| + shape->lineTo(kTabCapCurveWidth + 1, h);
|
| + shape->lineTo(0, h - kTabCapCurveWidth - 1);
|
| + // Connect to the top cap.
|
| + shape->lineTo(0, kTabCapCurveWidth);
|
| + // Top cap.
|
| + shape->lineTo(kTabCapCurveWidth, 0);
|
| +
|
| + shape->close();
|
| +}
|
| +
|
| +// static
|
| +gfx::Size SidebarTab::GetMinimumUnselectedSize() {
|
| + gfx::Size minimum_size;
|
| + // Since we use bitmap images, the real minimum width of the image is
|
| + // defined most accurately by the width of the end cap images.
|
| + return gfx::Size(tab_images().active.tab.width,
|
| + tab_images().active.tab.height);
|
| +}
|
| +
|
| +// static
|
| +gfx::Size SidebarTab::GetMinimumSelectedSize() {
|
| + gfx::Size minimum_size = GetMinimumUnselectedSize();
|
| + minimum_size.set_height(minimum_size.height());
|
| + return minimum_size;
|
| +}
|
| +
|
| +// static
|
| +gfx::Size SidebarTab::GetStandardSize() {
|
| + return GetMinimumSelectedSize();
|
| +}
|
| +
|
| +// SidebarTab, SidebarBaseTab overrides, protected:
|
| +
|
| +void SidebarTab::DataChanged(const SidebarTabRendererData& old) {
|
| + Layout();
|
| +}
|
| +
|
| +// SidebarTab, views::View overrides:
|
| +
|
| +void SidebarTab::Paint(gfx::Canvas* canvas) {
|
| + PaintTabBackground(canvas);
|
| +
|
| + PaintIcon(canvas);
|
| +
|
| + PaintBadge(canvas);
|
| +}
|
| +
|
| +void SidebarTab::Layout() {
|
| + gfx::Rect local_bounds = GetLocalBounds();
|
| + if (local_bounds.IsEmpty())
|
| + return;
|
| +
|
| + // Position the icon.
|
| + gfx::Size icon_size(!data().icon.empty() ?
|
| + gfx::Size(data().icon.width(), data().icon.height()) :
|
| + gfx::Size(Extension::kSidebarIconMaxSize,
|
| + Extension::kSidebarIconMaxSize));
|
| +
|
| + gfx::Point icon_origin(
|
| + local_bounds.x() + (local_bounds.width() - icon_size.width()) / 2,
|
| + local_bounds.y() + (local_bounds.height() - icon_size.height()) / 2);
|
| +
|
| + icon_bounds_ = gfx::Rect(icon_origin, icon_size);
|
| +}
|
| +
|
| +void SidebarTab::OnThemeChanged() {
|
| + tab_images().Load();
|
| +}
|
| +
|
| +bool SidebarTab::HasHitTestMask() const {
|
| + return true;
|
| +}
|
| +
|
| +void SidebarTab::GetHitTestMask(gfx::Path* path) const {
|
| + GetShape(path);
|
| +}
|
| +
|
| +bool SidebarTab::GetTooltipTextOrigin(const gfx::Point& p, gfx::Point* origin) {
|
| + origin->set_x(width() + views::TooltipManager::GetTooltipHeight());
|
| + origin->set_y(-views::TooltipManager::GetTooltipHeight());
|
| + return true;
|
| +}
|
| +
|
| +// SidebarTab, private
|
| +
|
| +// static
|
| +SidebarTab::TabImages& SidebarTab::tab_images() {
|
| + static TabImages images;
|
| + return images;
|
| +}
|
| +
|
| +void SidebarTab::PaintTabBackground(gfx::Canvas* canvas) {
|
| + if (IsSelected()) {
|
| + PaintTabBackgroundImage(canvas, true);
|
| + } else {
|
| + PaintTabBackgroundImage(canvas, false);
|
| +
|
| + double throb_value = GetThrobValue();
|
| + if (throb_value > 0) {
|
| + canvas->SaveLayerAlpha(static_cast<int>(throb_value * 0xff),
|
| + gfx::Rect(width(), height()));
|
| + canvas->AsCanvasSkia()->drawARGB(0, 255, 255, 255,
|
| + SkXfermode::kClear_Mode);
|
| + PaintTabBackgroundImage(canvas, true);
|
| + canvas->Restore();
|
| + }
|
| + }
|
| +}
|
| +
|
| +void SidebarTab::PaintTabBackgroundImage(gfx::Canvas* canvas,
|
| + bool as_active) {
|
| + TabImage* tab_image =
|
| + as_active ? &tab_images().active : &tab_images().inactive;
|
| +
|
| + canvas->DrawBitmapInt(*tab_image->tab.image, 0, 0);
|
| +}
|
| +
|
| +void SidebarTab::PaintIcon(gfx::Canvas* canvas) {
|
| + int alpha_percents = 100;
|
| + if (!IsExpanded()) {
|
| + alpha_percents = kCollapsedOpacityPercents;
|
| + } else {
|
| + if (IsSelected())
|
| + alpha_percents = kExpandedActiveOpacityPercents;
|
| + else
|
| + alpha_percents = kExpandedInactiveOpacityPercents;
|
| + }
|
| + SidebarBaseTab::PaintIcon(canvas, icon_bounds_.x(), icon_bounds_.y(),
|
| + kOpaque * alpha_percents / 100);
|
| +}
|
| +
|
| +void SidebarTab::PaintBadge(gfx::Canvas* canvas) {
|
| + // TODO(alekseys): paint badge text.
|
| +}
|
| +
|
|
|
| Property changes on: chrome\browser\ui\views\sidebar\sidebar_tab.cc
|
| ___________________________________________________________________
|
| Added: svn:eol-style
|
| + LF
|
|
|
|
|