| // Copyright (c) 2011 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. |
| |
| #ifndef CHROME_BROWSER_EXTENSIONS_IMAGE_LOADING_TRACKER_H_ |
| #define CHROME_BROWSER_EXTENSIONS_IMAGE_LOADING_TRACKER_H_ |
| #pragma once |
| |
| #include <map> |
| |
| #include "base/memory/ref_counted.h" |
| #include "content/common/notification_observer.h" |
| #include "content/common/notification_registrar.h" |
| |
| class Extension; |
| class ExtensionResource; |
| class SkBitmap; |
| |
| namespace gfx { |
| class Size; |
| } |
| |
| // The views need to load their icons asynchronously but might be deleted before |
| // the images have loaded. This class encapsulates a loader class that stays |
| // alive while the request is in progress (manages its own lifetime) and keeps |
| // track of whether the view still cares about the icon loading. |
| // |
| // To use this class, have your class derive from ImageLoadingTracker::Observer, |
| // and add a member variable ImageLoadingTracker tracker_. Then override |
| // Observer::OnImageLoaded and call: |
| // tracker_.LoadImage(extension, resource, max_size, false); |
| // ... and wait for OnImageLoaded to be called back on you with a pointer to the |
| // SkBitmap loaded. |
| // NOTE: if the image is available already (or the resource is not valid), the |
| // Observer is notified immediately from the call to LoadImage. In other words, |
| // by the time LoadImage returns the observer has been notified. |
| // |
| class ImageLoadingTracker : public NotificationObserver { |
| public: |
| enum CacheParam { |
| CACHE, |
| DONT_CACHE |
| }; |
| |
| class Observer { |
| public: |
| virtual ~Observer(); |
| |
| // Will be called when the image with the given index has loaded. |
| // The |image| is owned by the tracker, so the observer should make a copy |
| // if they need to access it after this call. |image| can be null if valid |
| // image was not found or it failed to decode. |resource| is the |
| // ExtensionResource where the |image| came from and the |index| represents |
| // the index of the image just loaded (starts at 0 and increments every |
| // time LoadImage is called). |
| virtual void OnImageLoaded(SkBitmap* image, |
| const ExtensionResource& resource, |
| int index) = 0; |
| }; |
| |
| explicit ImageLoadingTracker(Observer* observer); |
| ~ImageLoadingTracker(); |
| |
| // Specify image resource to load. If the loaded image is larger than |
| // |max_size| it will be resized to those dimensions. IMPORTANT NOTE: this |
| // function may call back your observer synchronously (ie before it returns) |
| // if the image was found in the cache. |
| void LoadImage(const Extension* extension, |
| const ExtensionResource& resource, |
| const gfx::Size& max_size, |
| CacheParam cache); |
| |
| private: |
| typedef std::map<int, const Extension*> LoadMap; |
| |
| class ImageLoader; |
| |
| // When an image has finished loaded and been resized on the file thread, it |
| // is posted back to this method on the original thread. This method then |
| // calls the observer's OnImageLoaded and deletes the ImageLoadingTracker if |
| // it was the last image in the list. The |original_size| should be the size |
| // of the image before any resizing was done. |
| // |image| may be null if the file failed to decode. |
| void OnImageLoaded(SkBitmap* image, const ExtensionResource& resource, |
| const gfx::Size& original_size, int id); |
| |
| // NotificationObserver method. If an extension is uninstalled while we're |
| // waiting for the image we remove the entry from load_map_. |
| virtual void Observe(NotificationType type, |
| const NotificationSource& source, |
| const NotificationDetails& details); |
| |
| // The view that is waiting for the image to load. |
| Observer* observer_; |
| |
| // ID to use for next image requested. This is an ever increasing integer. |
| int next_id_; |
| |
| // The object responsible for loading the image on the File thread. |
| scoped_refptr<ImageLoader> loader_; |
| |
| // If LoadImage is told to cache the result an entry is added here. The |
| // integer identifies the id assigned to the request. If the extension is |
| // deleted while fetching the image the entry is removed from the map. |
| LoadMap load_map_; |
| |
| NotificationRegistrar registrar_; |
| |
| DISALLOW_COPY_AND_ASSIGN(ImageLoadingTracker); |
| }; |
| |
| #endif // CHROME_BROWSER_EXTENSIONS_IMAGE_LOADING_TRACKER_H_ |