blob: bfb9feb1198efb62cba4ac5e39b5308570b7c92c [file] [log] [blame]
[email protected]e3c0bc22012-02-24 01:34:151// Copyright (c) 2012 The Chromium Authors. All rights reserved.
[email protected]502e39612011-03-26 01:36:282// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "chrome/browser/extensions/extension_uninstall_dialog.h"
6
7#include "base/logging.h"
8#include "base/message_loop.h"
[email protected]eed85492013-01-14 20:37:469#include "chrome/browser/extensions/image_loader.h"
10#include "chrome/browser/ui/browser.h"
[email protected]7f2d7d32012-06-25 21:47:3111#include "chrome/common/chrome_notification_types.h"
[email protected]502e39612011-03-26 01:36:2812#include "chrome/common/extensions/extension.h"
[email protected]faf87192012-08-17 00:07:5913#include "chrome/common/extensions/extension_constants.h"
[email protected]502e39612011-03-26 01:36:2814#include "chrome/common/extensions/extension_icon_set.h"
15#include "chrome/common/extensions/extension_resource.h"
[email protected]7f2d7d32012-06-25 21:47:3116#include "content/public/browser/notification_service.h"
17#include "content/public/browser/notification_source.h"
[email protected]502e39612011-03-26 01:36:2818#include "grit/generated_resources.h"
[email protected]2a2813352012-07-11 22:20:2319#include "grit/theme_resources.h"
[email protected]502e39612011-03-26 01:36:2820#include "ui/base/resource/resource_bundle.h"
[email protected]bdd6eec2012-03-03 19:58:0621#include "ui/gfx/image/image.h"
[email protected]502e39612011-03-26 01:36:2822
[email protected]dd46a4ce2012-09-15 10:50:5023namespace {
24
25// Returns pixel size under maximal scale factor for the icon whose device
26// independent size is |size_in_dip|
27int GetSizeForMaxScaleFactor(int size_in_dip) {
[email protected]059d76b2012-11-16 17:25:4228 ui::ScaleFactor max_scale_factor = ui::GetMaxScaleFactor();
[email protected]dd46a4ce2012-09-15 10:50:5029 float max_scale_factor_scale = ui::GetScaleFactorScale(max_scale_factor);
30
31 return static_cast<int>(size_in_dip * max_scale_factor_scale);
32}
33
34// Returns bitmap for the default icon with size equal to the default icon's
35// pixel size under maximal supported scale factor.
36SkBitmap GetDefaultIconBitmapForMaxScaleFactor(bool is_app) {
[email protected]dd46a4ce2012-09-15 10:50:5037 return extensions::Extension::GetDefaultIcon(is_app).
[email protected]059d76b2012-11-16 17:25:4238 GetRepresentation(ui::GetMaxScaleFactor()).sk_bitmap();
[email protected]dd46a4ce2012-09-15 10:50:5039}
40
41} // namespace
42
[email protected]502e39612011-03-26 01:36:2843// Size of extension icon in top left of dialog.
44static const int kIconSize = 69;
45
[email protected]6f03db062011-09-22 20:37:1446ExtensionUninstallDialog::ExtensionUninstallDialog(
[email protected]5f1ba412012-06-25 20:10:5247 Browser* browser,
[email protected]6f03db062011-09-22 20:37:1448 ExtensionUninstallDialog::Delegate* delegate)
[email protected]5f1ba412012-06-25 20:10:5249 : browser_(browser),
[email protected]6f03db062011-09-22 20:37:1450 delegate_(delegate),
[email protected]502e39612011-03-26 01:36:2851 extension_(NULL),
[email protected]eed85492013-01-14 20:37:4652 state_(kImageIsLoading),
[email protected]5f1ba412012-06-25 20:10:5253 ui_loop_(MessageLoop::current()) {
[email protected]7f2d7d32012-06-25 21:47:3154 if (browser) {
55 registrar_.Add(this,
56 chrome::NOTIFICATION_BROWSER_CLOSING,
57 content::Source<Browser>(browser));
58 }
[email protected]5f1ba412012-06-25 20:10:5259}
[email protected]502e39612011-03-26 01:36:2860
[email protected]5f1ba412012-06-25 20:10:5261ExtensionUninstallDialog::~ExtensionUninstallDialog() {
[email protected]5f1ba412012-06-25 20:10:5262}
[email protected]502e39612011-03-26 01:36:2863
[email protected]1c321ee52012-05-21 03:02:3464void ExtensionUninstallDialog::ConfirmUninstall(
65 const extensions::Extension* extension) {
[email protected]502e39612011-03-26 01:36:2866 DCHECK(ui_loop_ == MessageLoop::current());
[email protected]502e39612011-03-26 01:36:2867 extension_ = extension;
68
69 ExtensionResource image =
[email protected]faf87192012-08-17 00:07:5970 extension_->GetIconResource(extension_misc::EXTENSION_ICON_LARGE,
[email protected]e3c0bc22012-02-24 01:34:1571 ExtensionIconSet::MATCH_BIGGER);
[email protected]eed85492013-01-14 20:37:4672
[email protected]dd46a4ce2012-09-15 10:50:5073 // Load the icon whose pixel size is large enough to be displayed under
74 // maximal supported scale factor. UI code will scale the icon down if needed.
75 int pixel_size = GetSizeForMaxScaleFactor(kIconSize);
[email protected]eed85492013-01-14 20:37:4676
77 // Load the image asynchronously. The response will be sent to OnImageLoaded.
78 state_ = kImageIsLoading;
79 extensions::ImageLoader* loader =
80 extensions::ImageLoader::Get(browser_->profile());
81 loader->LoadImageAsync(extension_, image,
82 gfx::Size(pixel_size, pixel_size),
83 base::Bind(&ExtensionUninstallDialog::OnImageLoaded,
84 AsWeakPtr()));
[email protected]502e39612011-03-26 01:36:2885}
86
[email protected]bdd6eec2012-03-03 19:58:0687void ExtensionUninstallDialog::SetIcon(const gfx::Image& image) {
88 if (image.IsEmpty()) {
[email protected]dd46a4ce2012-09-15 10:50:5089 // Let's set default icon bitmap whose size is equal to the default icon's
90 // pixel size under maximal supported scale factor. If the bitmap is larger
91 // than the one we need, it will be scaled down by the ui code.
92 // TODO(tbarzic): We should use IconImage here and load the required bitmap
93 // lazily.
[email protected]1bc3ef02012-10-24 16:49:5994 icon_ = gfx::ImageSkia(
95 GetDefaultIconBitmapForMaxScaleFactor(extension_->is_app()));
[email protected]bdd6eec2012-03-03 19:58:0696 } else {
[email protected]6280b5882012-06-05 21:56:4197 icon_ = *image.ToImageSkia();
[email protected]502e39612011-03-26 01:36:2898 }
99}
100
[email protected]eed85492013-01-14 20:37:46101void ExtensionUninstallDialog::OnImageLoaded(const gfx::Image& image) {
[email protected]502e39612011-03-26 01:36:28102 SetIcon(image);
103
[email protected]eed85492013-01-14 20:37:46104 // Show the dialog unless the browser has been closed while we were waiting
105 // for the image.
106 DCHECK(state_ == kImageIsLoading || state_ == kBrowserIsClosing);
107 if (state_ == kImageIsLoading) {
108 state_ = kDialogIsShowing;
109 DCHECK(browser_ != NULL);
110 Show();
111 }
[email protected]502e39612011-03-26 01:36:28112}
[email protected]5f1ba412012-06-25 20:10:52113
[email protected]7f2d7d32012-06-25 21:47:31114void ExtensionUninstallDialog::Observe(
115 int type,
116 const content::NotificationSource& source,
117 const content::NotificationDetails& details) {
118 DCHECK(type == chrome::NOTIFICATION_BROWSER_CLOSING);
[email protected]5f1ba412012-06-25 20:10:52119
[email protected]eed85492013-01-14 20:37:46120 // If the browser is closed while waiting for the image, we need to send a
121 // "cancel" event here, because there will not be another opportunity to
122 // notify the delegate of the cancellation as we won't open the dialog.
123 if (state_ == kImageIsLoading) {
124 state_ = kBrowserIsClosing;
125 DCHECK(browser_ != NULL);
126 browser_ = NULL;
[email protected]5f1ba412012-06-25 20:10:52127 delegate_->ExtensionUninstallCanceled();
128 }
129}