// 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.

#include "core/fxcrt/fx_basic.h"
#include "testing/fx_string_testhelpers.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "xfa/fxbarcode/pdf417/BC_PDF417HighLevelEncoder.h"

TEST(PDF417HighLevelEncoder, EncodeHighLevel) {
  // TODO(tsepez): implement test cases.
}

TEST(PDF417HighLevelEncoder, EncodeText) {
  // TODO(tsepez): implement test cases.
}

TEST(PDF417HighLevelEncoder, EncodeBinary) {
  struct EncodeBinaryCase {
    const char* input;
    int offset;
    int count;
    int startmode;
    const wchar_t* expected;
    int expected_length;
  } encode_binary_cases[] = {
      // Empty string encodes as empty string.
      {"", 0, 0, CBC_PDF417HighLevelEncoder::TEXT_COMPACTION, L"", 0},

      // Fewer than 6 characters encodes as prefix without compaction.
      {"xxxxx", 0, 5, CBC_PDF417HighLevelEncoder::TEXT_COMPACTION,
       L"\x0385xxxxx", 6},

      // 6 charcters triggerst text encoding compaction.
      {"xxxxxx", 0, 6, CBC_PDF417HighLevelEncoder::TEXT_COMPACTION,
       L"\u039c\u00c9\u031f\u012a\u00d2\u02d0", 6},

      // Same result if initially in numeric compaction mode.
      {"xxxxxx", 0, 6, CBC_PDF417HighLevelEncoder::NUMERIC_COMPACTION,
       L"\u039c\u00c9\u031f\u012a\u00d2\u02d0", 6},
  };

  CBC_PDF417HighLevelEncoder::Initialize();
  for (size_t i = 0; i < FX_ArraySize(encode_binary_cases); ++i) {
    EncodeBinaryCase* ptr = &encode_binary_cases[i];
    CFX_ByteArray input_array;
    size_t input_length = strlen(ptr->input);
    input_array.SetSize(input_length);
    for (size_t j = 0; j < input_length; ++j) {
      input_array.SetAt(j, ptr->input[j]);
    }
    CFX_WideString expected(ptr->expected, ptr->expected_length);
    CFX_WideString result;
    CBC_PDF417HighLevelEncoder::encodeBinary(
        &input_array, ptr->offset, ptr->count, ptr->startmode, result);
    EXPECT_EQ(expected, result) << " for case number " << i;
  }
  CBC_PDF417HighLevelEncoder::Finalize();
}

TEST(PDF417HighLevelEncoder, EncodeNumeric) {
  struct EncodeNumericCase {
    const wchar_t* input;
    int offset;
    int count;
    const wchar_t* expected;
    int expected_length;
  } encode_numeric_cases[] = {
      // Empty string encodes as empty string.
      {L"", 0, 0, L"", 0},

      // Single 0 should encode as 10 base-900 == a.
      {L"0", 0, 1, L"\x000a", 1},

      // 800 should encode as 1800 base-900 == 2,0.
      {L"800", 0, 3, L"\x0002\x0000", 2},

      // Test longer strings and sub-strings.
      {L"123456", 0, 6, L"\x0001\x015c\x0100", 3},
      {L"123456", 0, 5, L"\x007c\x02e9", 2},
      {L"123456", 1, 5, L"\x0089\x009c", 2},
      {L"123456", 2, 2, L"\x0086", 1},

      // Up to 44 characters encodes as 15 base-900 words.
      {L"00000000000000000000000000000000000000000000", 0, 44,
       L"\x01b5\x006f\x02cc\x0084\x01bc\x0076\x00b3\x005c\x01f0\x034f\x01e6"
       L"\x0090\x020b\x019b\x0064",
       15},

      // 45 characters should encode as same 15 words followed by one additional
      // word.
      {L"000000000000000000000000000000000000000000000", 0, 45,
       L"\x01b5\x006f\x02cc\x0084\x01bc\x0076\x00b3\x005c\x01f0\x034f\x01e6"
       L"\x0090\x020b\x019b\x0064\x000a",
       16},

      // 44 characters followed by 800 should encode as 15 words followed by
      // 1800 base-900 == 2,0.
      {L"00000000000000000000000000000000000000000000800", 0, 47,
       L"\x01b5\x006f\x02cc\x0084\x01bc\x0076\x00b3\x005c\x01f0\x034f\x01e6"
       L"\x0090\x020b\x019b\x0064\x0002\x0000",
       17},

      // Even longer input.
      {L"10000000000000000000000000000000000000000000000000", 0, 50,
       L"\x01e0\x02f0\x036d\x02ad\x029c\x01ea\x0011\x000b\x02d6\x023c\x0108"
       L"\x02bb\x0023\x02d2\x00c8\x0001\x00d3\x0064",
       18},
  };

  CBC_PDF417HighLevelEncoder::Initialize();
  for (size_t i = 0; i < FX_ArraySize(encode_numeric_cases); ++i) {
    EncodeNumericCase* ptr = &encode_numeric_cases[i];
    CFX_WideString input(ptr->input);
    CFX_WideString expected(ptr->expected, ptr->expected_length);
    CFX_WideString result;
    CBC_PDF417HighLevelEncoder::encodeNumeric(input, ptr->offset, ptr->count,
                                              result);
    EXPECT_EQ(expected, result) << " for case number " << i;
  }
  CBC_PDF417HighLevelEncoder::Finalize();
}

TEST(PDF417HighLevelEncoder, ConsecutiveDigitCount) {
  struct ConsecutiveDigitCase {
    const wchar_t* input;
    int offset;
    int expected_count;
  } consecutive_digit_cases[] = {
      // Empty string contains 0 consecuitve digits.
      {L"", 0, 0},

      // Single non-digit character contains 0 consecutive digits.
      {L"X", 0, 0},

      // Leading non-digit followed by digits contains 0 consecutive.
      {L"X123", 0, 0},

      // Single digit contains 1 consecutive digit.
      {L"1", 0, 1},

      // Single digit followe by non-digit contains 1 consecutive digit.
      {L"1Z", 0, 1},

      // Test longer strings.
      {L"123FOO45678", 0, 3},

      // Test subtring starting in digits field.
      {L"123FOO45678", 3, 0},

      // Test subtring starting in non-digits field.
      {L"123FOO45678", 3, 0},

      // Test substring starting in digits field following non-digit field.
      {L"123FOO45678", 6, 5},
  };

  CBC_PDF417HighLevelEncoder::Initialize();
  for (size_t i = 0; i < FX_ArraySize(consecutive_digit_cases); ++i) {
    ConsecutiveDigitCase* ptr = &consecutive_digit_cases[i];
    CFX_WideString input(ptr->input);
    int actual_count =
        CBC_PDF417HighLevelEncoder::determineConsecutiveDigitCount(input,
                                                                   ptr->offset);
    EXPECT_EQ(ptr->expected_count, actual_count) << " for case number " << i;
  }
  CBC_PDF417HighLevelEncoder::Finalize();
}

TEST(PDF417HighLevelEncoder, ConsecutiveTextCount) {
  struct ConsecutiveTextCase {
    const wchar_t* input;
    int offset;
    int expected_count;
  } consecutive_text_cases[] = {
      // Empty string contains 0 consecutive text characters.
      {L"", 0, 0},

      // Single text character is 1 consecutive text characters.
      {L"X", 0, 1},

      // Trailing numbers count as text characters.
      {L"X123", 0, 4},

      // Leading numbers count as text characters.
      {L"123X", 0, 4},

      // Embedded lo-value binary characters terminate text runs.
      {L"ABC\x0001XXXX", 0, 3},

      // Embedded hi-value binary characters terminate text runs.
      {L"ABC\x0100XXXX", 0, 3},

      // Text run still found after indexing past lo-value character.
      {L"ABC\x0001XXXX", 4, 4},

      // Text run still found after indexing past hi-value character.
      {L"ABC\x0100XXXX", 4, 4},

      // Leading hi-value character results in 0 consecutive characters.
      {L"\x0100XXX", 0, 0},

      // Up to 12 numbers count as text.
      {L"123456789012", 0, 12},

      // 13 or more numbers are compresssed using numeric compression, not text.
      {L"1234567890123", 0, 0},

      // Leading Text character doesn't affect the 12 character case.
      {L"X123456789012", 0, 13},

      // Leading Text character doesn't affect the 13 character case.
      {L"X1234567890123", 0, 1},

      // Jumping between numbers and letters works properly.
      {L"XXX121XXX12345678901234", 0, 9},
  };

  CBC_PDF417HighLevelEncoder::Initialize();
  for (size_t i = 0; i < FX_ArraySize(consecutive_text_cases); ++i) {
    ConsecutiveTextCase* ptr = &consecutive_text_cases[i];
    CFX_WideString input(ptr->input);
    int actual_count =
        CBC_PDF417HighLevelEncoder::determineConsecutiveTextCount(input,
                                                                  ptr->offset);
    EXPECT_EQ(ptr->expected_count, actual_count) << " for case number " << i;
  }
  CBC_PDF417HighLevelEncoder::Finalize();
}

TEST(PDF417HighLevelEncoder, ConsecutiveBinaryCount) {}
