// 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
// Original code is licensed as follows:
/*
 * Copyright 2013 ZXing authors
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include "xfa/src/fxbarcode/BC_ResultPoint.h"
#include "xfa/src/fxbarcode/common/BC_CommonBitMatrix.h"
#include "xfa/src/fxbarcode/pdf417/BC_PDF417BoundingBox.h"
#include "xfa/src/fxbarcode/utils.h"

CBC_BoundingBox::CBC_BoundingBox(CBC_CommonBitMatrix* image,
                                 CBC_ResultPoint* topLeft,
                                 CBC_ResultPoint* bottomLeft,
                                 CBC_ResultPoint* topRight,
                                 CBC_ResultPoint* bottomRight,
                                 int32_t& e) {
  if ((topLeft == NULL && topRight == NULL) ||
      (bottomLeft == NULL && bottomRight == NULL) ||
      (topLeft && bottomLeft == NULL) || (topRight && bottomRight == NULL)) {
    e = BCExceptionNotFoundInstance;
  }
  init(image, topLeft, bottomLeft, topRight, bottomRight);
}
CBC_BoundingBox::CBC_BoundingBox(CBC_BoundingBox* boundingBox) {
  init(boundingBox->m_image, boundingBox->m_topLeft, boundingBox->m_bottomLeft,
       boundingBox->m_topRight, boundingBox->m_bottomRight);
}
CBC_BoundingBox::~CBC_BoundingBox() {
  if (m_topLeft) {
    delete m_topLeft;
  }
  if (m_bottomLeft) {
    delete m_bottomLeft;
  }
  if (m_topRight) {
    delete m_topRight;
  }
  if (m_bottomRight) {
    delete m_bottomRight;
  }
}
CBC_BoundingBox* CBC_BoundingBox::merge(CBC_BoundingBox* leftBox,
                                        CBC_BoundingBox* rightBox,
                                        int32_t& e) {
  CBC_BoundingBox* boundingBox = NULL;
  if (leftBox == NULL) {
    boundingBox = new CBC_BoundingBox(rightBox);
    return boundingBox;
  }
  if (rightBox == NULL) {
    boundingBox = new CBC_BoundingBox(leftBox);
    return boundingBox;
  }
  boundingBox = new CBC_BoundingBox(leftBox->m_image, leftBox->m_topLeft,
                                    leftBox->m_bottomLeft, rightBox->m_topRight,
                                    rightBox->m_bottomRight, e);
  BC_EXCEPTION_CHECK_ReturnValue(e, NULL);
  return boundingBox;
}
CBC_BoundingBox* CBC_BoundingBox::addMissingRows(int32_t missingStartRows,
                                                 int32_t missingEndRows,
                                                 FX_BOOL isLeft,
                                                 int32_t& e) {
  CBC_ResultPoint* newTopLeft = m_topLeft;
  CBC_ResultPoint* newBottomLeft = m_bottomLeft;
  CBC_ResultPoint* newTopRight = m_topRight;
  CBC_ResultPoint* newBottomRight = m_bottomRight;
  CBC_ResultPoint* newTop = NULL;
  CBC_ResultPoint* newBottom = NULL;
  if (missingStartRows > 0) {
    CBC_ResultPoint* top = isLeft ? m_topLeft : m_topRight;
    int32_t newMinY = (int32_t)top->GetY() - missingStartRows;
    if (newMinY < 0) {
      newMinY = 0;
    }
    newTop = new CBC_ResultPoint((FX_FLOAT)top->GetX(), (FX_FLOAT)newMinY);
    if (isLeft) {
      newTopLeft = newTop;
    } else {
      newTopRight = newTop;
    }
  }
  if (missingEndRows > 0) {
    CBC_ResultPoint* bottom = isLeft ? m_bottomLeft : m_bottomRight;
    int32_t newMaxY = (int32_t)bottom->GetY() + missingEndRows;
    if (newMaxY >= m_image->GetHeight()) {
      newMaxY = m_image->GetHeight() - 1;
    }
    newBottom =
        new CBC_ResultPoint((FX_FLOAT)bottom->GetX(), (FX_FLOAT)newMaxY);
    if (isLeft) {
      newBottomLeft = newBottom;
    } else {
      newBottomRight = newBottom;
    }
  }
  calculateMinMaxValues();
  CBC_BoundingBox* boundingBox = new CBC_BoundingBox(
      m_image, newTopLeft, newBottomLeft, newTopRight, newBottomRight, e);
  delete newTop;
  delete newBottom;
  BC_EXCEPTION_CHECK_ReturnValue(e, NULL);
  return boundingBox;
}
void CBC_BoundingBox::setTopRight(CBC_ResultPoint topRight) {
  if (m_topRight) {
    delete m_topRight;
  }
  m_topRight = new CBC_ResultPoint(topRight.GetX(), topRight.GetY());
  calculateMinMaxValues();
}
void CBC_BoundingBox::setBottomRight(CBC_ResultPoint bottomRight) {
  if (m_bottomRight) {
    delete m_bottomRight;
  }
  m_bottomRight = new CBC_ResultPoint(bottomRight.GetX(), bottomRight.GetY());
  calculateMinMaxValues();
}
int32_t CBC_BoundingBox::getMinX() {
  return m_minX;
}
int32_t CBC_BoundingBox::getMaxX() {
  return m_maxX;
}
int32_t CBC_BoundingBox::getMinY() {
  return m_minY;
}
int32_t CBC_BoundingBox::getMaxY() {
  return m_maxY;
}
CBC_ResultPoint* CBC_BoundingBox::getTopLeft() {
  return m_topLeft;
}
CBC_ResultPoint* CBC_BoundingBox::getTopRight() {
  return m_topRight;
}
CBC_ResultPoint* CBC_BoundingBox::getBottomLeft() {
  return m_bottomLeft;
}
CBC_ResultPoint* CBC_BoundingBox::getBottomRight() {
  return m_bottomRight;
}
void CBC_BoundingBox::init(CBC_CommonBitMatrix* image,
                           CBC_ResultPoint* topLeft,
                           CBC_ResultPoint* bottomLeft,
                           CBC_ResultPoint* topRight,
                           CBC_ResultPoint* bottomRight) {
  m_topLeft = NULL;
  m_bottomLeft = NULL;
  m_topRight = NULL;
  m_bottomRight = NULL;
  m_image = image;
  if (topLeft) {
    m_topLeft = new CBC_ResultPoint(topLeft->GetX(), topLeft->GetY());
  }
  if (bottomLeft) {
    m_bottomLeft = new CBC_ResultPoint(bottomLeft->GetX(), bottomLeft->GetY());
  }
  if (topRight) {
    m_topRight = new CBC_ResultPoint(topRight->GetX(), topRight->GetY());
  }
  if (bottomRight) {
    m_bottomRight =
        new CBC_ResultPoint(bottomRight->GetX(), bottomRight->GetY());
  }
  calculateMinMaxValues();
}
void CBC_BoundingBox::calculateMinMaxValues() {
  if (m_topLeft == NULL) {
    m_topLeft = new CBC_ResultPoint(0, m_topRight->GetY());
    m_bottomLeft = new CBC_ResultPoint(0, m_bottomRight->GetY());
  } else if (m_topRight == NULL) {
    m_topRight = new CBC_ResultPoint((FX_FLOAT)m_image->GetWidth() - 1,
                                     (FX_FLOAT)m_topLeft->GetY());
    m_bottomRight = new CBC_ResultPoint((FX_FLOAT)m_image->GetWidth() - 1,
                                        (FX_FLOAT)m_bottomLeft->GetY());
  }
  m_minX = (int32_t)(m_topLeft->GetX() < m_bottomLeft->GetX()
                         ? m_topLeft->GetX()
                         : m_bottomLeft->GetX());
  m_maxX = (int32_t)(m_topRight->GetX() > m_bottomRight->GetX()
                         ? m_topRight->GetX()
                         : m_bottomRight->GetX());
  m_minY =
      (int32_t)(m_topLeft->GetY() < m_topRight->GetY() ? m_topLeft->GetY()
                                                       : m_topRight->GetY());
  m_maxY = (int32_t)(m_bottomLeft->GetY() > m_bottomRight->GetY()
                         ? m_bottomLeft->GetY()
                         : m_bottomRight->GetY());
}
