/*
 * Copyright (c) 2021, Alliance for Open Media. All rights reserved
 *
 * This source code is subject to the terms of the BSD 2 Clause License and
 * the Alliance for Open Media Patent License 1.0. If the BSD 2 Clause License
 * was not distributed with this source code in the LICENSE file, you can
 * obtain it at www.aomedia.org/license/software. If the Alliance for Open
 * Media Patent License 1.0 was not distributed with this source code in the
 * PATENTS file, you can obtain it at www.aomedia.org/license/patent.
 */

#include <assert.h>
#include <jxl/butteraugli.h>

#include "aom_dsp/butteraugli.h"
#include "aom_mem/aom_mem.h"
#include "third_party/libyuv/include/libyuv/convert_argb.h"

int aom_calc_butteraugli(const YV12_BUFFER_CONFIG *source,
                         const YV12_BUFFER_CONFIG *distorted, int bit_depth,
                         float *dist_map) {
  (void)bit_depth;
  assert(bit_depth == 8);
  const int width = source->y_crop_width;
  const int height = source->y_crop_height;
  const int ss_x = source->subsampling_x;
  const int ss_y = source->subsampling_y;

  const size_t stride_argb = width * 4;
  const size_t buffer_size = height * stride_argb;
  uint8_t *src_argb = (uint8_t *)aom_malloc(buffer_size);
  uint8_t *distorted_argb = (uint8_t *)aom_malloc(buffer_size);
  if (!src_argb || !distorted_argb) {
    aom_free(src_argb);
    aom_free(distorted_argb);
    return 0;
  }

  if (ss_x == 1 && ss_y == 1) {
    I420ToARGBMatrix(source->y_buffer, source->y_stride, source->u_buffer,
                     source->uv_stride, source->v_buffer, source->uv_stride,
                     src_argb, stride_argb, &kYuvH709Constants, width, height);
    I420ToARGBMatrix(distorted->y_buffer, distorted->y_stride,
                     distorted->u_buffer, distorted->uv_stride,
                     distorted->v_buffer, distorted->uv_stride, distorted_argb,
                     stride_argb, &kYuvH709Constants, width, height);
  } else if (ss_x == 1 && ss_y == 0) {
    I422ToARGBMatrix(source->y_buffer, source->y_stride, source->u_buffer,
                     source->uv_stride, source->v_buffer, source->uv_stride,
                     src_argb, stride_argb, &kYuvH709Constants, width, height);
    I422ToARGBMatrix(distorted->y_buffer, distorted->y_stride,
                     distorted->u_buffer, distorted->uv_stride,
                     distorted->v_buffer, distorted->uv_stride, distorted_argb,
                     stride_argb, &kYuvH709Constants, width, height);
  } else if (ss_x == 0 && ss_y == 0) {
    I444ToARGBMatrix(source->y_buffer, source->y_stride, source->u_buffer,
                     source->uv_stride, source->v_buffer, source->uv_stride,
                     src_argb, stride_argb, &kYuvH709Constants, width, height);
    I444ToARGBMatrix(distorted->y_buffer, distorted->y_stride,
                     distorted->u_buffer, distorted->uv_stride,
                     distorted->v_buffer, distorted->uv_stride, distorted_argb,
                     stride_argb, &kYuvH709Constants, width, height);
  } else {
    aom_free(src_argb);
    aom_free(distorted_argb);
    return 0;
  }

  JxlPixelFormat pixel_format = { 4, JXL_TYPE_UINT8, JXL_NATIVE_ENDIAN, 0 };
  JxlButteraugliApi *api = JxlButteraugliApiCreate(NULL);
  JxlButteraugliApiSetHFAsymmetry(api, 0.8f);

  JxlButteraugliResult *result = JxlButteraugliCompute(
      api, width, height, &pixel_format, src_argb, buffer_size, &pixel_format,
      distorted_argb, buffer_size);

  const float *distmap = NULL;
  uint32_t row_stride;
  JxlButteraugliResultGetDistmap(result, &distmap, &row_stride);
  if (distmap == NULL) {
    JxlButteraugliApiDestroy(api);
    JxlButteraugliResultDestroy(result);
    aom_free(src_argb);
    aom_free(distorted_argb);
    return 0;
  }

  for (int j = 0; j < height; ++j) {
    for (int i = 0; i < width; ++i) {
      dist_map[j * width + i] = distmap[j * row_stride + i];
    }
  }

  JxlButteraugliApiDestroy(api);
  JxlButteraugliResultDestroy(result);
  aom_free(src_argb);
  aom_free(distorted_argb);
  return 1;
}
