// Copyright 2012 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "ui/gfx/android/java_bitmap.h"

#include <android/bitmap.h>

#include "base/android/jni_string.h"
#include "base/bits.h"
#include "base/check_op.h"
#include "base/debug/crash_logging.h"
#include "base/notreached.h"
#include "base/numerics/safe_conversions.h"
#include "ui/gfx/geometry/size.h"
#include "ui/gfx/gfx_jni_headers/BitmapHelper_jni.h"

using base::android::AttachCurrentThread;
using base::android::ConvertUTF8ToJavaString;
using base::android::ScopedJavaLocalRef;
using base::android::JavaRef;

namespace gfx {
namespace {

int SkColorTypeToBitmapFormat(SkColorType color_type) {
  switch (color_type) {
    case kN32_SkColorType:
      return BITMAP_FORMAT_ARGB_8888;
    case kRGB_565_SkColorType:
      return BITMAP_FORMAT_RGB_565;
    default:
      // A bad format can cause out-of-bounds issues when copying pixels into or
      // out of the java bitmap's pixel buffer.
      CHECK_NE(color_type, color_type);
  }
  return BITMAP_FORMAT_NO_CONFIG;
}

SkColorType BitmapFormatToSkColorType(BitmapFormat bitmap_format) {
  switch (bitmap_format) {
    case BITMAP_FORMAT_ALPHA_8:
      return kAlpha_8_SkColorType;
    case BITMAP_FORMAT_ARGB_4444:
      return kARGB_4444_SkColorType;
    case BITMAP_FORMAT_ARGB_8888:
      return kN32_SkColorType;
    case BITMAP_FORMAT_RGB_565:
      return kRGB_565_SkColorType;
    case BITMAP_FORMAT_NO_CONFIG:
    default:
      SCOPED_CRASH_KEY_NUMBER("gfx", "bitmap_format",
                              static_cast<int>(bitmap_format));
      CHECK_NE(bitmap_format, bitmap_format);
      return kUnknown_SkColorType;
  }
}

// Wraps a Java bitmap as an SkPixmap. Since the pixmap references the
// underlying pixel data in the Java bitmap directly, it is only valid as long
// as |bitmap| is.
SkPixmap WrapJavaBitmapAsPixmap(const JavaBitmap& bitmap) {
  auto color_type = BitmapFormatToSkColorType(bitmap.format());
  auto image_info =
      SkImageInfo::Make(bitmap.size().width(), bitmap.size().height(),
                        color_type, kPremul_SkAlphaType);
  return SkPixmap(image_info, bitmap.pixels(), bitmap.bytes_per_row());
}

}  // namespace

#define ASSERT_ENUM_EQ(a, b) \
  static_assert(static_cast<int>(a) == static_cast<int>(b), "")

// BitmapFormat has the same values as AndroidBitmapFormat, for simplicitly, so
// that SkColorTypeToBitmapFormat() and the JavaBitmap::format() have the same
// values.
ASSERT_ENUM_EQ(BITMAP_FORMAT_NO_CONFIG, ANDROID_BITMAP_FORMAT_NONE);
ASSERT_ENUM_EQ(BITMAP_FORMAT_ALPHA_8, ANDROID_BITMAP_FORMAT_A_8);
ASSERT_ENUM_EQ(BITMAP_FORMAT_ARGB_4444, ANDROID_BITMAP_FORMAT_RGBA_4444);
ASSERT_ENUM_EQ(BITMAP_FORMAT_ARGB_8888, ANDROID_BITMAP_FORMAT_RGBA_8888);
ASSERT_ENUM_EQ(BITMAP_FORMAT_RGB_565, ANDROID_BITMAP_FORMAT_RGB_565);

JavaBitmap::JavaBitmap(const JavaRef<jobject>& bitmap)
    : bitmap_(bitmap), pixels_(NULL) {
  int err =
      AndroidBitmap_lockPixels(AttachCurrentThread(), bitmap_.obj(), &pixels_);
  DCHECK(!err);
  DCHECK(pixels_);

  AndroidBitmapInfo info;
  err = AndroidBitmap_getInfo(AttachCurrentThread(), bitmap_.obj(), &info);
  DCHECK(!err);
  size_ = gfx::Size(info.width, info.height);
  format_ = static_cast<BitmapFormat>(info.format);
  bytes_per_row_ = info.stride;
  byte_count_ = Java_BitmapHelper_getByteCount(AttachCurrentThread(), bitmap_);
}

JavaBitmap::~JavaBitmap() {
  int err = AndroidBitmap_unlockPixels(AttachCurrentThread(), bitmap_.obj());
  DCHECK(!err);
}

ScopedJavaLocalRef<jobject> ConvertToJavaBitmap(const SkBitmap& skbitmap,
                                                OomBehavior reaction) {
  DCHECK(!skbitmap.isNull());
  DCHECK_GT(skbitmap.width(), 0);
  DCHECK_GT(skbitmap.height(), 0);

  int java_bitmap_format = SkColorTypeToBitmapFormat(skbitmap.colorType());

  ScopedJavaLocalRef<jobject> jbitmap = Java_BitmapHelper_createBitmap(
      AttachCurrentThread(), skbitmap.width(), skbitmap.height(),
      java_bitmap_format, reaction == OomBehavior::kReturnNullOnOom);
  if (!jbitmap) {
    DCHECK_EQ(OomBehavior::kReturnNullOnOom, reaction);
    return jbitmap;
  }

  JavaBitmap dst_lock(jbitmap);
  SkPixmap dst = WrapJavaBitmapAsPixmap(dst_lock);
  skbitmap.readPixels(dst);
  return jbitmap;
}

SkBitmap CreateSkBitmapFromJavaBitmap(const JavaBitmap& jbitmap) {
  DCHECK(!jbitmap.size().IsEmpty());
  DCHECK_GT(jbitmap.bytes_per_row(), 0U);
  DCHECK(jbitmap.pixels());

  // Ensure 4 byte stride alignment since the texture upload code in the
  // compositor relies on this.
  SkPixmap src = WrapJavaBitmapAsPixmap(jbitmap);
  const size_t min_row_bytes = src.info().minRowBytes();
  const size_t row_bytes = base::bits::AlignUp(min_row_bytes, size_t{4});

  SkBitmap skbitmap;
  skbitmap.allocPixels(src.info(), row_bytes);
  skbitmap.writePixels(src);
  return skbitmap;
}

SkColorType ConvertToSkiaColorType(const JavaRef<jobject>& bitmap_config) {
  BitmapFormat jbitmap_format =
      static_cast<BitmapFormat>(Java_BitmapHelper_getBitmapFormatForConfig(
          AttachCurrentThread(), bitmap_config));
  return BitmapFormatToSkColorType(jbitmap_format);
}

}  //  namespace gfx
