| OLD | NEW | 
|---|
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 "ui/gfx/paint_vector_icon.h" | 5 #include "ui/gfx/paint_vector_icon.h" | 
| 6 | 6 | 
| 7 #include <map> | 7 #include <map> | 
| 8 | 8 | 
| 9 #include "base/lazy_instance.h" | 9 #include "base/lazy_instance.h" | 
| 10 #include "base/strings/string_number_conversions.h" | 10 #include "base/strings/string_number_conversions.h" | 
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 61     else | 61     else | 
| 62       path.push_back(PathElement(CommandFromString(piece))); | 62       path.push_back(PathElement(CommandFromString(piece))); | 
| 63   } | 63   } | 
| 64   return path; | 64   return path; | 
| 65 } | 65 } | 
| 66 | 66 | 
| 67 void PaintPath(Canvas* canvas, | 67 void PaintPath(Canvas* canvas, | 
| 68                const PathElement* path_elements, | 68                const PathElement* path_elements, | 
| 69                size_t dip_size, | 69                size_t dip_size, | 
| 70                SkColor color) { | 70                SkColor color) { | 
|  | 71   canvas->Save(); | 
| 71   SkPath path; | 72   SkPath path; | 
| 72   path.setFillType(SkPath::kEvenOdd_FillType); | 73   path.setFillType(SkPath::kEvenOdd_FillType); | 
| 73 | 74 | 
| 74   size_t canvas_size = kReferenceSizeDip; | 75   size_t canvas_size = kReferenceSizeDip; | 
| 75   std::vector<SkPath> paths; | 76   std::vector<SkPath> paths; | 
| 76   std::vector<SkPaint> paints; | 77   std::vector<SkPaint> paints; | 
| 77   SkRect clip_rect = SkRect::MakeEmpty(); | 78   SkRect clip_rect = SkRect::MakeEmpty(); | 
| 78 | 79 | 
| 79   for (size_t i = 0; path_elements[i].type != END; i++) { | 80   for (size_t i = 0; path_elements[i].type != END; i++) { | 
| 80     if (paths.empty() || path_elements[i].type == NEW_PATH) { | 81     if (paths.empty() || path_elements[i].type == NEW_PATH) { | 
| (...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 231     SkScalar scale = SkIntToScalar(dip_size) / SkIntToScalar(canvas_size); | 232     SkScalar scale = SkIntToScalar(dip_size) / SkIntToScalar(canvas_size); | 
| 232     canvas->sk_canvas()->scale(scale, scale); | 233     canvas->sk_canvas()->scale(scale, scale); | 
| 233   } | 234   } | 
| 234 | 235 | 
| 235   if (!clip_rect.isEmpty()) | 236   if (!clip_rect.isEmpty()) | 
| 236     canvas->sk_canvas()->clipRect(clip_rect); | 237     canvas->sk_canvas()->clipRect(clip_rect); | 
| 237 | 238 | 
| 238   DCHECK_EQ(paints.size(), paths.size()); | 239   DCHECK_EQ(paints.size(), paths.size()); | 
| 239   for (size_t i = 0; i < paths.size(); ++i) | 240   for (size_t i = 0; i < paths.size(); ++i) | 
| 240     canvas->DrawPath(paths[i], paints[i]); | 241     canvas->DrawPath(paths[i], paints[i]); | 
|  | 242   canvas->Restore(); | 
| 241 } | 243 } | 
| 242 | 244 | 
| 243 class VectorIconSource : public CanvasImageSource { | 245 class VectorIconSource : public CanvasImageSource { | 
| 244  public: | 246  public: | 
| 245   VectorIconSource(VectorIconId id, size_t dip_size, SkColor color) | 247   VectorIconSource(VectorIconId id, | 
|  | 248                    size_t dip_size, | 
|  | 249                    SkColor color, | 
|  | 250                    VectorIconId badge_id) | 
| 246       : CanvasImageSource( | 251       : CanvasImageSource( | 
| 247             gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size)), | 252             gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size)), | 
| 248             false), | 253             false), | 
| 249         id_(id), | 254         id_(id), | 
| 250         color_(color) {} | 255         color_(color), | 
|  | 256         badge_id_(badge_id) {} | 
| 251 | 257 | 
| 252   VectorIconSource(const std::string& definition, | 258   VectorIconSource(const std::string& definition, | 
| 253                    size_t dip_size, | 259                    size_t dip_size, | 
| 254                    SkColor color) | 260                    SkColor color) | 
| 255       : CanvasImageSource( | 261       : CanvasImageSource( | 
| 256             gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size)), | 262             gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size)), | 
| 257             false), | 263             false), | 
| 258         id_(VectorIconId::VECTOR_ICON_NONE), | 264         id_(VectorIconId::VECTOR_ICON_NONE), | 
| 259         path_(PathFromSource(definition)), | 265         path_(PathFromSource(definition)), | 
| 260         color_(color) {} | 266         color_(color), | 
|  | 267         badge_id_(VectorIconId::VECTOR_ICON_NONE) {} | 
| 261 | 268 | 
| 262   ~VectorIconSource() override {} | 269   ~VectorIconSource() override {} | 
| 263 | 270 | 
| 264   // CanvasImageSource: | 271   // CanvasImageSource: | 
| 265   void Draw(gfx::Canvas* canvas) override { | 272   void Draw(gfx::Canvas* canvas) override { | 
| 266     if (path_.empty()) | 273     if (path_.empty()) { | 
| 267       PaintVectorIcon(canvas, id_, size_.width(), color_); | 274       PaintVectorIcon(canvas, id_, size_.width(), color_); | 
| 268     else | 275       if (badge_id_ != VectorIconId::VECTOR_ICON_NONE) | 
|  | 276         PaintVectorIcon(canvas, badge_id_, size_.width(), color_); | 
|  | 277     } else { | 
| 269       PaintPath(canvas, path_.data(), size_.width(), color_); | 278       PaintPath(canvas, path_.data(), size_.width(), color_); | 
|  | 279     } | 
| 270   } | 280   } | 
| 271 | 281 | 
| 272  private: | 282  private: | 
| 273   const VectorIconId id_; | 283   const VectorIconId id_; | 
| 274   const std::vector<PathElement> path_; | 284   const std::vector<PathElement> path_; | 
| 275   const SkColor color_; | 285   const SkColor color_; | 
|  | 286   const VectorIconId badge_id_; | 
| 276 | 287 | 
| 277   DISALLOW_COPY_AND_ASSIGN(VectorIconSource); | 288   DISALLOW_COPY_AND_ASSIGN(VectorIconSource); | 
| 278 }; | 289 }; | 
| 279 | 290 | 
| 280 // This class caches vector icons (as ImageSkia) so they don't have to be drawn | 291 // This class caches vector icons (as ImageSkia) so they don't have to be drawn | 
| 281 // more than once. This also guarantees the backing data for the images returned | 292 // more than once. This also guarantees the backing data for the images returned | 
| 282 // by CreateVectorIcon will persist in memory until program termination. | 293 // by CreateVectorIcon will persist in memory until program termination. | 
| 283 class VectorIconCache { | 294 class VectorIconCache { | 
| 284  public: | 295  public: | 
| 285   VectorIconCache() {} | 296   VectorIconCache() {} | 
| 286   ~VectorIconCache() {} | 297   ~VectorIconCache() {} | 
| 287 | 298 | 
| 288   ImageSkia GetOrCreateIcon(VectorIconId id, size_t dip_size, SkColor color) { | 299   ImageSkia GetOrCreateIcon(VectorIconId id, | 
| 289     IconDescription description(id, dip_size, color); | 300                             size_t dip_size, | 
|  | 301                             SkColor color, | 
|  | 302                             VectorIconId badge_id) { | 
|  | 303     IconDescription description(id, dip_size, color, badge_id); | 
| 290     auto iter = images_.find(description); | 304     auto iter = images_.find(description); | 
| 291     if (iter != images_.end()) | 305     if (iter != images_.end()) | 
| 292       return iter->second; | 306       return iter->second; | 
| 293 | 307 | 
| 294     ImageSkia icon( | 308     ImageSkia icon( | 
| 295         new VectorIconSource(id, dip_size, color), | 309         new VectorIconSource(id, dip_size, color, badge_id), | 
| 296         gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size))); | 310         gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size))); | 
| 297     images_.insert(std::make_pair(description, icon)); | 311     images_.insert(std::make_pair(description, icon)); | 
| 298     return icon; | 312     return icon; | 
| 299   } | 313   } | 
| 300 | 314 | 
| 301  private: | 315  private: | 
| 302   struct IconDescription { | 316   struct IconDescription { | 
| 303     IconDescription(VectorIconId id, size_t dip_size, SkColor color) | 317     IconDescription(VectorIconId id, | 
| 304         : id(id), dip_size(dip_size), color(color) {} | 318                     size_t dip_size, | 
|  | 319                     SkColor color, | 
|  | 320                     VectorIconId badge_id) | 
|  | 321         : id(id), dip_size(dip_size), color(color), badge_id(badge_id) {} | 
| 305 | 322 | 
| 306     bool operator<(const IconDescription& other) const { | 323     bool operator<(const IconDescription& other) const { | 
| 307       if (id != other.id) | 324       if (id != other.id) | 
| 308         return id < other.id; | 325         return id < other.id; | 
| 309       if (dip_size != other.dip_size) | 326       if (dip_size != other.dip_size) | 
| 310         return dip_size < other.dip_size; | 327         return dip_size < other.dip_size; | 
| 311       return color < other.color; | 328       if (color != other.color) | 
|  | 329         return color < other.color; | 
|  | 330       return badge_id < other.badge_id; | 
| 312     } | 331     } | 
| 313 | 332 | 
| 314     VectorIconId id; | 333     VectorIconId id; | 
| 315     size_t dip_size; | 334     size_t dip_size; | 
| 316     SkColor color; | 335     SkColor color; | 
|  | 336     VectorIconId badge_id; | 
| 317   }; | 337   }; | 
| 318 | 338 | 
| 319   std::map<IconDescription, ImageSkia> images_; | 339   std::map<IconDescription, ImageSkia> images_; | 
| 320 | 340 | 
| 321   DISALLOW_COPY_AND_ASSIGN(VectorIconCache); | 341   DISALLOW_COPY_AND_ASSIGN(VectorIconCache); | 
| 322 }; | 342 }; | 
| 323 | 343 | 
| 324 static base::LazyInstance<VectorIconCache> g_icon_cache = | 344 static base::LazyInstance<VectorIconCache> g_icon_cache = | 
| 325     LAZY_INSTANCE_INITIALIZER; | 345     LAZY_INSTANCE_INITIALIZER; | 
| 326 | 346 | 
| 327 }  // namespace | 347 }  // namespace | 
| 328 | 348 | 
| 329 void PaintVectorIcon(Canvas* canvas, | 349 void PaintVectorIcon(Canvas* canvas, | 
| 330                      VectorIconId id, | 350                      VectorIconId id, | 
| 331                      size_t dip_size, | 351                      size_t dip_size, | 
| 332                      SkColor color) { | 352                      SkColor color) { | 
| 333   DCHECK(VectorIconId::VECTOR_ICON_NONE != id); | 353   DCHECK(VectorIconId::VECTOR_ICON_NONE != id); | 
| 334   const PathElement* path = canvas->image_scale() == 1.f | 354   const PathElement* path = canvas->image_scale() == 1.f | 
| 335                                 ? GetPathForVectorIconAt1xScale(id) | 355                                 ? GetPathForVectorIconAt1xScale(id) | 
| 336                                 : GetPathForVectorIcon(id); | 356                                 : GetPathForVectorIcon(id); | 
| 337   PaintPath(canvas, path, dip_size, color); | 357   PaintPath(canvas, path, dip_size, color); | 
| 338 } | 358 } | 
| 339 | 359 | 
| 340 ImageSkia CreateVectorIcon(VectorIconId id, size_t dip_size, SkColor color) { | 360 ImageSkia CreateVectorIcon(VectorIconId id, size_t dip_size, SkColor color) { | 
| 341   return g_icon_cache.Get().GetOrCreateIcon(id, dip_size, color); | 361   return CreateVectorIconWithBadge(id, dip_size, color, | 
|  | 362                                    VectorIconId::VECTOR_ICON_NONE); | 
|  | 363 } | 
|  | 364 | 
|  | 365 ImageSkia CreateVectorIconWithBadge(VectorIconId id, | 
|  | 366                                     size_t dip_size, | 
|  | 367                                     SkColor color, | 
|  | 368                                     VectorIconId badge_id) { | 
|  | 369   return g_icon_cache.Get().GetOrCreateIcon(id, dip_size, color, badge_id); | 
| 342 } | 370 } | 
| 343 | 371 | 
| 344 ImageSkia CreateVectorIconFromSource(const std::string& source, | 372 ImageSkia CreateVectorIconFromSource(const std::string& source, | 
| 345                                      size_t dip_size, | 373                                      size_t dip_size, | 
| 346                                      SkColor color) { | 374                                      SkColor color) { | 
| 347   return ImageSkia( | 375   return ImageSkia( | 
| 348       new VectorIconSource(source, dip_size, color), | 376       new VectorIconSource(source, dip_size, color), | 
| 349       gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size))); | 377       gfx::Size(static_cast<int>(dip_size), static_cast<int>(dip_size))); | 
| 350 } | 378 } | 
| 351 | 379 | 
| 352 }  // namespace gfx | 380 }  // namespace gfx | 
| OLD | NEW | 
|---|