Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(194)

Side by Side Diff: chrome/browser/extensions/extension_icon_image.cc

Issue 10825012: chromeos: Fix pixelated icons in app list and launcher (part 2) (by xiyuan) (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: minor cleanup Created 8 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
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.
4
5 #include "chrome/browser/extensions/extension_icon_image.h"
6
7 #include <vector>
8
9 #include "chrome/common/chrome_notification_types.h"
10 #include "chrome/common/extensions/extension.h"
11 #include "content/public/browser/notification_service.h"
12 #include "ui/gfx/image/image.h"
13 #include "ui/gfx/image/image_skia_source.h"
14 #include "ui/gfx/size.h"
15
16 namespace {
17
18 ExtensionResource GetExtensionIconResource(
19 const extensions::Extension* extension,
20 const ExtensionIconSet& icons,
21 int size,
22 ExtensionIconSet::MatchType match_type) {
23 std::string path = icons.Get(size, match_type);
24 if (path.empty())
25 return ExtensionResource();
26
27 return extension->GetResource(path);
28 }
29
30 } // namespace
31
32 namespace extensions {
33
34 ////////////////////////////////////////////////////////////////////////////////
35 // ExtensionIconImage::Source
36
37 class IconImage::Source : public gfx::ImageSkiaSource {
38 public:
39 explicit Source(IconImage* host);
40 virtual ~Source();
41
42 void ResetHost();
43
44 private:
45 // gfx::ImageSkiaSource overrides:
46 virtual gfx::ImageSkiaRep GetImageForScale(
47 ui::ScaleFactor scale_factor) OVERRIDE;
48
49 IconImage* host_;
50
51 DISALLOW_COPY_AND_ASSIGN(Source);
52 };
53
54 IconImage::Source::Source(IconImage* host) : host_(host) {
55 }
56
57 IconImage::Source::~Source() {
58 }
59
60 void IconImage::Source::ResetHost() {
61 host_ = NULL;
62 }
63
64 gfx::ImageSkiaRep IconImage::Source::GetImageForScale(
65 ui::ScaleFactor scale_factor) {
66 if (host_)
67 host_->LoadImageForScaleFactor(scale_factor, false);
68 return gfx::ImageSkiaRep();
69 }
70
71 ////////////////////////////////////////////////////////////////////////////////
72 // ExtensionIconImage
73
74 IconImage::IconImage(
75 const Extension* extension,
76 const ExtensionIconSet& icon_set,
77 int resource_size_in_dip,
78 Observer* observer)
79 : extension_(extension),
80 icon_set_(icon_set),
81 resource_size_in_dip_(resource_size_in_dip),
82 desired_size_in_dip_(resource_size_in_dip, resource_size_in_dip),
83 observer_(observer),
84 source_(NULL),
85 ALLOW_THIS_IN_INITIALIZER_LIST(tracker_(this)) {
86 source_ = new Source(this);
87 image_skia_ = gfx::ImageSkia(source_, desired_size_in_dip_);
88
89 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED,
90 content::NotificationService::AllSources());
91 }
92
93 IconImage::~IconImage() {
94 // |source_| could be NULL if resource does not exist.
95 if (source_)
96 source_->ResetHost();
97 }
98
99 void IconImage::LoadImageForScaleFactor(ui::ScaleFactor scale_factor,
100 bool is_retry) {
101 // Do nothing if extension is unloaded.
102 if (!extension_)
103 return;
104
105 const float scale = ui::GetScaleFactorScale(scale_factor);
106 const int resource_size_in_pixel =
107 static_cast<int>(resource_size_in_dip_ * scale);
108
109 ExtensionResource resource;
110 // We try loading bigger image only if resource size is >= 32 and we haven't
111 // already tried it.
112 if (!is_retry && resource_size_in_pixel >= 32) {
Aaron Boodman 2012/08/15 04:30:40 We can assume that if an icon is specified in Exte
tbarzic 2012/08/15 15:01:36 Done.
113 resource = GetExtensionIconResource(extension_, icon_set_,
114 resource_size_in_pixel, ExtensionIconSet::MATCH_BIGGER);
115 }
116
117 if (is_retry) {
118 // If this is second attempt, we will try loading resource using
119 // MATCH_SMALLER matcher.
120 resource = GetExtensionIconResource(extension_, icon_set_,
121 resource_size_in_pixel, ExtensionIconSet::MATCH_SMALLER);
122 }
123
124 // Resource for this try is empty, there's no point in trying to load it.
125 if (resource.empty()) {
126 if (is_retry) {
127 // If this is the second attempt, we have failed. Let observer know.
128 if (observer_)
129 observer_->OnIconImageLoadFailed(this, scale_factor);
130 } else {
131 // Try again; this time using MATCH_SMALLER.
132 LoadImageForScaleFactor(scale_factor, true);
133 }
134 return;
135 }
136
137 int id = tracker_.next_id();
138 load_map_[id].scale_factor = scale_factor;
139 load_map_[id].is_retry = is_retry;
140
141 std::vector<ImageLoadingTracker::ImageRepresentation> info_list;
142 info_list.push_back(ImageLoadingTracker::ImageRepresentation(
143 resource,
144 ImageLoadingTracker::ImageRepresentation::RESIZE_WHEN_LARGER,
145 desired_size_in_dip_.Scale(scale),
146 scale_factor));
147 tracker_.LoadImages(extension_, info_list, ImageLoadingTracker::DONT_CACHE);
148 }
149
150 void IconImage::OnImageLoaded(const gfx::Image& image,
151 const std::string& extension_id,
152 int index) {
153 LoadMap::iterator load_map_it = load_map_.find(index);
154 DCHECK(load_map_it != load_map_.end());
155
156 ui::ScaleFactor scale_factor = load_map_it->second.scale_factor;
157 bool is_retry = load_map_it->second.is_retry;
158
159 load_map_.erase(load_map_it);
160
161 if (image.IsEmpty()) {
162 if (is_retry) {
163 // We have failed for the second time. Give up and notify observer.
164 if (observer_)
165 observer_->OnIconImageLoadFailed(this, scale_factor);
166 } else {
167 // We failed loading bigger image, let's give a smaller image a chance.
168 LoadImageForScaleFactor(scale_factor, true);
169 }
170 return;
171 }
172
173 DCHECK(image.ToImageSkia()->HasRepresentation(scale_factor));
174 gfx::ImageSkiaRep rep = image.ToImageSkia()->GetRepresentation(scale_factor);
175 DCHECK(!rep.is_null());
176 image_skia_.AddRepresentation(rep);
177
178 if (observer_)
179 observer_->OnExtensionIconImageChanged(this);
180 }
181
182 void IconImage::Observe(int type,
183 const content::NotificationSource& source,
184 const content::NotificationDetails& details) {
185 DCHECK_EQ(type, chrome::NOTIFICATION_EXTENSION_UNLOADED);
186
187 const Extension* extension =
188 content::Details<extensions::UnloadedExtensionInfo>(details)->extension;
189
190 if (extension_ == extension)
191 extension_ = NULL;
192 }
193
194 } // namespace extensions
OLDNEW
« no previous file with comments | « chrome/browser/extensions/extension_icon_image.h ('k') | chrome/browser/extensions/extension_icon_image_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698