Chromium Code Reviews| Index: chrome/common/extensions/extension_action.cc |
| diff --git a/chrome/common/extensions/extension_action.cc b/chrome/common/extensions/extension_action.cc |
| index 9df8905772c436650aa306670ca0f61cf2110778..a489aaf0257f6115a27e4ebd3a22a32e0fe90819 100644 |
| --- a/chrome/common/extensions/extension_action.cc |
| +++ b/chrome/common/extensions/extension_action.cc |
| @@ -11,7 +11,11 @@ |
| #include "googleurl/src/gurl.h" |
| #include "grit/ui_resources.h" |
| #include "third_party/skia/include/core/SkBitmap.h" |
| +#include "third_party/skia/include/core/SkCanvas.h" |
| +#include "third_party/skia/include/core/SkDevice.h" |
| +#include "third_party/skia/include/core/SkPaint.h" |
| #include "third_party/skia/include/effects/SkGradientShader.h" |
| +#include "ui/base/animation/animation_delegate.h" |
| #include "ui/base/resource/resource_bundle.h" |
| #include "ui/gfx/canvas.h" |
| #include "ui/gfx/rect.h" |
| @@ -52,6 +56,47 @@ const int kCenterAlignThreshold = 20; |
| const int ExtensionAction::kDefaultTabId = -1; |
| +ExtensionAction::IconAnimation::IconAnimation( |
| + ui::AnimationDelegate* delegate) |
| + // 100ms animation at 50fps (so 5 animation frames in total). |
| + : ui::LinearAnimation(100, 50, delegate) {} |
| + |
| +ExtensionAction::IconAnimation::~IconAnimation() {} |
| + |
| +const SkBitmap& ExtensionAction::IconAnimation::Apply( |
| + const SkBitmap& icon) const { |
| + DCHECK_GT(icon.width(), 0); |
| + DCHECK_GT(icon.height(), 0); |
| + |
| + if (!device_.get() || |
| + (device_->width() != icon.width()) || |
| + (device_->height() != icon.height())) { |
| + device_.reset(new SkDevice( |
| + SkBitmap::kARGB_8888_Config, icon.width(), icon.height(), true)); |
| + } |
| + |
| + SkCanvas canvas(device_.get()); |
| + canvas.clear(SK_ColorWHITE); |
| + SkPaint paint; |
| + paint.setAlpha(CurrentValueBetween(0, 255)); |
| + canvas.drawBitmap(icon, 0, 0, &paint); |
| + return device_->accessBitmap(false); |
| +} |
| + |
| +void ExtensionAction::IconAnimation::AddObserver( |
| + ExtensionAction::IconAnimation::Observer* observer) { |
| + observers_.AddObserver(observer); |
| +} |
| + |
| +void ExtensionAction::IconAnimation::RemoveObserver( |
| + ExtensionAction::IconAnimation::Observer* observer) { |
| + observers_.RemoveObserver(observer); |
| +} |
| + |
| +void ExtensionAction::IconAnimation::AnimateToState(double state) { |
| + FOR_EACH_OBSERVER(Observer, observers_, OnIconChanged(*this)); |
| +} |
| + |
| ExtensionAction::ExtensionAction(const std::string& extension_id, |
| Type action_type) |
| : extension_id_(extension_id), |
| @@ -95,6 +140,7 @@ void ExtensionAction::SetIconIndex(int tab_id, int index) { |
| } |
| void ExtensionAction::ClearAllValuesForTab(int tab_id) { |
| + popup_url_.erase(tab_id); |
| title_.erase(tab_id); |
| icon_.erase(tab_id); |
| icon_index_.erase(tab_id); |
| @@ -102,7 +148,7 @@ void ExtensionAction::ClearAllValuesForTab(int tab_id) { |
| badge_text_color_.erase(tab_id); |
| badge_background_color_.erase(tab_id); |
| visible_.erase(tab_id); |
| - popup_url_.erase(tab_id); |
| + icon_animation_.erase(tab_id); |
| } |
| void ExtensionAction::PaintBadge(gfx::Canvas* canvas, |
| @@ -193,3 +239,53 @@ void ExtensionAction::PaintBadge(gfx::Canvas* canvas, |
| *text_paint); |
| canvas->Restore(); |
| } |
| + |
| +// Wraps an IconAnimation and implements its ui::AnimationDelegate to erase the |
| +// animation from a map when the animation ends or is cancelled, causing itself |
| +// and its owned IconAnimation to be deleted. |
| +class ExtensionAction::IconAnimationWrapper : public ui::AnimationDelegate { |
| + public: |
| + IconAnimationWrapper(ExtensionAction* owner, int tab_id) |
| + : owner_(owner), |
| + tab_id_(tab_id), |
| + ALLOW_THIS_IN_INITIALIZER_LIST(animation_(this)) {} |
| + |
| + virtual ~IconAnimationWrapper() {} |
| + |
| + IconAnimation* animation() { |
| + return &animation_; |
| + } |
| + |
| + private: |
| + virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE { |
| + Done(); |
| + } |
| + |
| + virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE { |
| + Done(); |
| + } |
| + |
| + void Done() { |
| + owner_->icon_animation_.erase(tab_id_); |
| + // this will now have been deleted. |
| + } |
| + |
| + ExtensionAction* owner_; |
| + int tab_id_; |
| + IconAnimation animation_; |
| +}; |
| + |
| +base::WeakPtr<ExtensionAction::IconAnimation> ExtensionAction::GetIconAnimation( |
|
Yoyo Zhou
2012/06/26 18:38:15
nit: Group ExtensionAnimation functions together i
not at google - send to devlin
2012/06/27 06:26:54
I don't understand what this means; they are group
Yoyo Zhou
2012/06/27 06:28:25
Between ExtensionAction::PaintBadge and ExtensionA
|
| + int tab_id) const { |
| + std::map<int, linked_ptr<IconAnimationWrapper> >::const_iterator it = |
| + icon_animation_.find(tab_id); |
| + return (it != icon_animation_.end()) ? it->second->animation()->AsWeakPtr() |
| + : base::WeakPtr<IconAnimation>(); |
| +} |
| + |
| +void ExtensionAction::RunIconAnimation(int tab_id) { |
| + IconAnimationWrapper* icon_animation = |
| + new IconAnimationWrapper(this, tab_id); |
| + icon_animation_[tab_id] = make_linked_ptr(icon_animation); |
| + icon_animation->animation()->Start(); |
| +} |