// 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 2008 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 "../barcode.h"
#include "../common/BC_CommonByteMatrix.h"
#include "BC_QRCoderErrorCorrectionLevel.h"
#include "BC_QRCoder.h"
#include "BC_QRCoderMaskUtil.h"
CBC_QRCoderMaskUtil::CBC_QRCoderMaskUtil() {}
CBC_QRCoderMaskUtil::~CBC_QRCoderMaskUtil() {}
int32_t CBC_QRCoderMaskUtil::ApplyMaskPenaltyRule1(
    CBC_CommonByteMatrix* matrix) {
  return ApplyMaskPenaltyRule1Internal(matrix, TRUE) +
         ApplyMaskPenaltyRule1Internal(matrix, FALSE);
}
int32_t CBC_QRCoderMaskUtil::ApplyMaskPenaltyRule2(
    CBC_CommonByteMatrix* matrix) {
  int32_t penalty = 0;
  uint8_t* array = matrix->GetArray();
  int32_t width = matrix->GetWidth();
  int32_t height = matrix->GetHeight();
  for (int32_t y = 0; y < height - 1; y++) {
    for (int32_t x = 0; x < width - 1; x++) {
      int32_t value = array[y * width + x];
      if (value == array[y * width + x + 1] &&
          value == array[(y + 1) * width + x] &&
          value == array[(y + 1) * width + x + 1]) {
        penalty++;
      }
    }
  }
  return 3 * penalty;
}
int32_t CBC_QRCoderMaskUtil::ApplyMaskPenaltyRule3(
    CBC_CommonByteMatrix* matrix) {
  int32_t penalty = 0;
  uint8_t* array = matrix->GetArray();
  int32_t width = matrix->GetWidth();
  int32_t height = matrix->GetHeight();
  for (int32_t y = 0; y < height; ++y) {
    for (int32_t x = 0; x < width; ++x) {
      if (x == 0 &&
          ((y >= 0 && y <= 6) || (y >= height - 7 && y <= height - 1))) {
        continue;
      }
      if (x == width - 7 && (y >= 0 && y <= 6)) {
        continue;
      }
      if (y == 0 &&
          ((x >= 0 && x <= 6) || (x >= width - 7 && x <= width - 1))) {
        continue;
      }
      if (y == height - 7 && (x >= 0 && x <= 6)) {
        continue;
      }
      if (x + 6 < width && array[y * width + x] == 1 &&
          array[y * width + x + 1] == 0 && array[y * width + x + 2] == 1 &&
          array[y * width + x + 3] == 1 && array[y * width + x + 4] == 1 &&
          array[y * width + x + 5] == 0 && array[y * width + x + 6] == 1 &&
          ((x + 10 < width && array[y * width + x + 7] == 0 &&
            array[y * width + x + 8] == 0 && array[y * width + x + 9] == 0 &&
            array[y * width + x + 10] == 0) ||
           (x - 4 >= 0 && array[y * width + x - 1] == 0 &&
            array[y * width + x - 2] == 0 && array[y * width + x - 3] == 0 &&
            array[y * width + x - 4] == 0))) {
        penalty += 40;
      }
      if (y + 6 < height && array[y * width + x] == 1 &&
          array[(y + 1) * width + x] == 0 && array[(y + 2) * width + x] == 1 &&
          array[(y + 3) * width + x] == 1 && array[(y + 4) * width + x] == 1 &&
          array[(y + 5) * width + x] == 0 && array[(y + 6) * width + x] == 1 &&
          ((y + 10 < height && array[(y + 7) * width + x] == 0 &&
            array[(y + 8) * width + x] == 0 &&
            array[(y + 9) * width + x] == 0 &&
            array[(y + 10) * width + x] == 0) ||
           (y - 4 >= 0 && array[(y - 1) * width + x] == 0 &&
            array[(y - 2) * width + x] == 0 &&
            array[(y - 3) * width + x] == 0 &&
            array[(y - 4) * width + x] == 0))) {
        penalty += 40;
      }
    }
  }
  return penalty;
}
int32_t CBC_QRCoderMaskUtil::ApplyMaskPenaltyRule4(
    CBC_CommonByteMatrix* matrix) {
  int32_t numDarkCells = 0;
  uint8_t* array = matrix->GetArray();
  int32_t width = matrix->GetWidth();
  int32_t height = matrix->GetHeight();
  for (int32_t y = 0; y < height; ++y) {
    for (int32_t x = 0; x < width; ++x) {
      if (array[y * width + x] == 1) {
        numDarkCells += 1;
      }
    }
  }
  int32_t numTotalCells = matrix->GetHeight() * matrix->GetWidth();
  double darkRatio = (double)numDarkCells / numTotalCells;
  return abs((int32_t)(darkRatio * 100 - 50) / 5) * 5 * 10;
}
FX_BOOL CBC_QRCoderMaskUtil::GetDataMaskBit(int32_t maskPattern,
                                            int32_t x,
                                            int32_t y,
                                            int32_t& e) {
  if (!CBC_QRCoder::IsValidMaskPattern(maskPattern)) {
    e = (BCExceptionInvalidateMaskPattern);
    BC_EXCEPTION_CHECK_ReturnValue(e, FALSE);
  }
  int32_t intermediate = 0, temp = 0;
  switch (maskPattern) {
    case 0:
      intermediate = (y + x) & 0x1;
      break;
    case 1:
      intermediate = y & 0x1;
      break;
    case 2:
      intermediate = x % 3;
      break;
    case 3:
      intermediate = (y + x) % 3;
      break;
    case 4:
      intermediate = ((y >> 1) + (x / 3)) & 0x1;
      break;
    case 5:
      temp = y * x;
      intermediate = (temp & 0x1) + (temp % 3);
      break;
    case 6:
      temp = y * x;
      intermediate = (((temp & 0x1) + (temp % 3)) & 0x1);
      break;
    case 7:
      temp = y * x;
      intermediate = (((temp % 3) + ((y + x) & 0x1)) & 0x1);
      break;
    default: {
      e = BCExceptionInvalidateMaskPattern;
      BC_EXCEPTION_CHECK_ReturnValue(e, FALSE);
    }
  }
  return intermediate == 0;
}
int32_t CBC_QRCoderMaskUtil::ApplyMaskPenaltyRule1Internal(
    CBC_CommonByteMatrix* matrix,
    FX_BOOL isHorizontal) {
  int32_t penalty = 0;
  int32_t numSameBitCells = 0;
  int32_t prevBit = -1;
  int32_t width = matrix->GetWidth();
  int32_t height = matrix->GetHeight();
  int32_t iLimit = isHorizontal ? height : width;
  int32_t jLimit = isHorizontal ? width : height;
  uint8_t* array = matrix->GetArray();
  for (int32_t i = 0; i < iLimit; ++i) {
    for (int32_t j = 0; j < jLimit; ++j) {
      int32_t bit = isHorizontal ? array[i * width + j] : array[j * width + i];
      if (bit == prevBit) {
        numSameBitCells += 1;
        if (numSameBitCells == 5) {
          penalty += 3;
        } else if (numSameBitCells > 5) {
          penalty += 1;
        }
      } else {
        numSameBitCells = 1;
        prevBit = bit;
      }
    }
    numSameBitCells = 0;
  }
  return penalty;
}
