// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "core/fxcodec/codec/ccodec_gifmodule.h"

#include "core/fxcodec/codec/codec_int.h"
#include "core/fxcodec/fx_codec.h"
#include "core/fxcodec/lgif/cgifcontext.h"
#include "core/fxcodec/lgif/fx_gif.h"
#include "core/fxge/fx_dib.h"
#include "third_party/base/ptr_util.h"

CCodec_GifModule::CCodec_GifModule() {
  memset(m_szLastError, 0, sizeof(m_szLastError));
}

CCodec_GifModule::~CCodec_GifModule() {}

std::unique_ptr<CGifContext> CCodec_GifModule::Start() {
  return pdfium::MakeUnique<CGifContext>(this, m_szLastError);
}

GifDecodeStatus CCodec_GifModule::ReadHeader(CGifContext* context,
                                             int* width,
                                             int* height,
                                             int* pal_num,
                                             void** pal_pp,
                                             int* bg_index,
                                             CFX_DIBAttribute* pAttribute) {
  if (setjmp(context->jmpbuf))
    return GifDecodeStatus::Error;

  GifDecodeStatus ret = gif_read_header(context);
  if (ret != GifDecodeStatus::Success)
    return ret;

  *width = context->width;
  *height = context->height;
  *pal_num = context->global_pal_num;
  *pal_pp = context->m_GlobalPalette.empty() ? nullptr
                                             : context->m_GlobalPalette.data();
  *bg_index = context->bc_index;
  return GifDecodeStatus::Success;
}

GifDecodeStatus CCodec_GifModule::LoadFrameInfo(CGifContext* context,
                                                int* frame_num) {
  if (setjmp(context->jmpbuf))
    return GifDecodeStatus::Error;

  GifDecodeStatus ret = gif_get_frame(context);
  if (ret != GifDecodeStatus::Success)
    return ret;

  *frame_num = gif_get_frame_num(context);
  return GifDecodeStatus::Success;
}

GifDecodeStatus CCodec_GifModule::LoadFrame(CGifContext* context,
                                            int frame_num,
                                            CFX_DIBAttribute* pAttribute) {
  if (setjmp(context->jmpbuf))
    return GifDecodeStatus::Error;

  GifDecodeStatus ret = gif_load_frame(context, frame_num);
  if (ret == GifDecodeStatus::Success) {
    if (pAttribute) {
      pAttribute->m_nGifLeft = context->m_Images[frame_num]->m_ImageInfo.left;
      pAttribute->m_nGifTop = context->m_Images[frame_num]->m_ImageInfo.top;
      pAttribute->m_fAspectRatio = context->pixel_aspect;
      const uint8_t* buf =
          reinterpret_cast<const uint8_t*>(context->cmt_data.GetBuffer(0));
      uint32_t len = context->cmt_data.GetLength();
      if (len > 21) {
        uint8_t size = *buf++;
        if (size != 0)
          pAttribute->m_strAuthor = CFX_ByteString(buf, size);
        else
          pAttribute->m_strAuthor.clear();
      }
    }
  }
  return ret;
}

uint32_t CCodec_GifModule::GetAvailInput(CGifContext* context,
                                         uint8_t** avail_buf_ptr) {
  return gif_get_avail_input(context, avail_buf_ptr);
}

void CCodec_GifModule::Input(CGifContext* context,
                             const uint8_t* src_buf,
                             uint32_t src_size) {
  gif_input_buffer(context, (uint8_t*)src_buf, src_size);
}
