// Copyright (c) 2012 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 UI_GFX_IMAGE_IMAGE_SKIA_H_
#define UI_GFX_IMAGE_IMAGE_SKIA_H_

#include <vector>

#include "base/basictypes.h"
#include "base/gtest_prod_util.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "ui/gfx/gfx_export.h"
#include "ui/gfx/image/image_skia_rep.h"

namespace gfx {
class ImageSkiaSource;
class Size;

namespace internal {
class ImageSkiaStorage;
}  // namespace internal

namespace test {
class TestOnThread;
}

// Container for the same image at different densities, similar to NSImage.
// Image height and width are in DIP (Density Indepent Pixel) coordinates.
//
// ImageSkia should be used whenever possible instead of SkBitmap.
// Functions that mutate the image should operate on the gfx::ImageSkiaRep
// returned from ImageSkia::GetRepresentation, not on ImageSkia.
//
// ImageSkia is cheap to copy and intentionally supports copy semantics.
class GFX_EXPORT ImageSkia {
 public:
  typedef std::vector<ImageSkiaRep> ImageSkiaReps;

  // Creates an instance with no bitmaps.
  ImageSkia();

  // Creates an instance that will use the |source| to get the image
  // for scale factors. |size| specifes the size of the image in DIP.
  // ImageSkia owns |source|.
  ImageSkia(ImageSkiaSource* source, const gfx::Size& size);

  // Creates an instance that uses the |source|. The constructor loads the image
  // at |scale| and uses its dimensions to calculate the size in DIP. ImageSkia
  // owns |source|.
  ImageSkia(ImageSkiaSource* source, float scale);

  explicit ImageSkia(const gfx::ImageSkiaRep& image_rep);

  // Copies a reference to |other|'s storage.
  ImageSkia(const ImageSkia& other);

  // Copies a reference to |other|'s storage.
  ImageSkia& operator=(const ImageSkia& other);

  ~ImageSkia();

  // Changes the value of GetSupportedScales() to |scales|.
  static void SetSupportedScales(const std::vector<float>& scales);

  // Returns a vector with the scale factors which are supported by this
  // platform, in ascending order.
  static const std::vector<float>& GetSupportedScales();

  // Returns the maximum scale supported by this platform.
  static float GetMaxSupportedScale();

  // Creates an image from the passed in bitmap.
  // DIP width and height are based on scale factor of 1x.
  // Adds ref to passed in bitmap.
  // WARNING: The resulting image will be pixelated when painted on a high
  // density display.
  static ImageSkia CreateFrom1xBitmap(const SkBitmap& bitmap);

  // Returns true when ImageSkia looks up the resource pack with the closest
  // scale factor and rescale the fetched image.
  static bool IsDSFScalingInImageSkiaEnabled();

  // Returns a deep copy of this ImageSkia which has its own storage with
  // the ImageSkiaRep instances that this ImageSkia currently has.
  // This can be safely passed to and manipulated by another thread.
  // Note that this does NOT generate ImageSkiaReps from its source.
  // If you want to create a deep copy with ImageSkiaReps for supported
  // scale factors, you need to explicitly call
  // |EnsureRepsForSupportedScales()| first.
  scoped_ptr<ImageSkia> DeepCopy() const;

  // Returns true if this object is backed by the same ImageSkiaStorage as
  // |other|. Will also return true if both images are isNull().
  bool BackedBySameObjectAs(const gfx::ImageSkia& other) const;

  // Adds |image_rep| to the image reps contained by this object.
  void AddRepresentation(const gfx::ImageSkiaRep& image_rep);

  // Removes the image rep of |scale| if present.
  void RemoveRepresentation(float scale);

  // Returns true if the object owns an image rep whose density matches
  // |scale| exactly.
  bool HasRepresentation(float scale) const;

  // Returns the image rep whose density best matches |scale|.
  // Returns a null image rep if the object contains no image reps.
  const gfx::ImageSkiaRep& GetRepresentation(float scale) const;

  // Make the ImageSkia instance read-only. Note that this only prevent
  // modification from client code, and the storage may still be
  // modified by the source if any (thus, it's not thread safe).  This
  // detaches the storage from currently accessing thread, so its safe
  // to pass it to other thread as long as it is accessed only by that
  // thread. If this ImageSkia's storage will be accessed by multiple
  // threads, use |MakeThreadSafe()| method.
  void SetReadOnly();

  // Make the image thread safe by making the storage read only and remove
  // its source if any. All ImageSkia that shares the same storage will also
  // become thread safe. Note that in order to make it 100% thread safe,
  // this must be called before it's been passed to anther thread.
  void MakeThreadSafe();
  bool IsThreadSafe() const;

  // Returns true if this is a null object.
  bool isNull() const { return storage_.get() == NULL; }

  // Width and height of image in DIP coordinate system.
  int width() const;
  int height() const;
  gfx::Size size() const;

  // Returns pointer to 1x bitmap contained by this object. If there is no 1x
  // bitmap, the bitmap whose scale factor is closest to 1x is returned.
  // This function should only be used in unittests and on platforms which do
  // not support scale factors other than 1x.
  // TODO(pkotwicz): Return null SkBitmap when the object has no 1x bitmap.
  const SkBitmap* bitmap() const { return &GetBitmap(); }

  // Returns a vector with the image reps contained in this object.
  // There is no guarantee that this will return all images rep for
  // supported scale factors.
  std::vector<gfx::ImageSkiaRep> image_reps() const;

  // When the source is available, generates all ImageReps for
  // supported scale factors. This method is defined as const as
  // the state change in the storage is agnostic to the caller.
  void EnsureRepsForSupportedScales() const;

 private:
  friend class test::TestOnThread;
  FRIEND_TEST_ALL_PREFIXES(ImageSkiaTest, EmptyOnThreadTest);
  FRIEND_TEST_ALL_PREFIXES(ImageSkiaTest, StaticOnThreadTest);
  FRIEND_TEST_ALL_PREFIXES(ImageSkiaTest, SourceOnThreadTest);

  // Initialize ImageSkiaStorage with passed in parameters.
  // If the image rep's bitmap is empty, ImageStorage is set to NULL.
  void Init(const gfx::ImageSkiaRep& image_rep);

  SkBitmap& GetBitmap() const;

  // Checks if the current thread can read/modify the ImageSkia.
  bool CanRead() const;
  bool CanModify() const;

  // Detach the storage from the currently assinged thread
  // so that other thread can access the storage.
  void DetachStorageFromThread();

  // A refptr so that ImageRepSkia can be copied cheaply.
  scoped_refptr<internal::ImageSkiaStorage> storage_;
};

}  // namespace gfx

#endif  // UI_GFX_IMAGE_IMAGE_SKIA_H_
