// 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 2009 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_UtilRSS.h"

#include <memory>

#include "core/include/fxcrt/fx_basic.h"
#include "xfa/src/fxbarcode/utils.h"

CBC_UtilRSS::CBC_UtilRSS() {}
CBC_UtilRSS::~CBC_UtilRSS() {}
CFX_Int32Array* CBC_UtilRSS::GetRssWidths(int32_t val,
                                          int32_t n,
                                          int32_t elements,
                                          int32_t maxWidth,
                                          FX_BOOL noNarrow) {
  std::unique_ptr<CFX_Int32Array> widths(new CFX_Int32Array);
  widths->SetSize(elements);
  int32_t bar;
  int32_t narrowMask = 0;
  for (bar = 0; bar < elements - 1; bar++) {
    narrowMask |= (1 << bar);
    int32_t elmWidth = 1;
    int32_t subVal;
    while (TRUE) {
      subVal = Combins(n - elmWidth - 1, elements - bar - 2);
      if (noNarrow && (narrowMask == 0) &&
          (n - elmWidth - (elements - bar - 1) >= elements - bar - 1)) {
        subVal -= Combins(n - elmWidth - (elements - bar), elements - bar - 2);
      }
      if (elements - bar - 1 > 1) {
        int32_t lessVal = 0;
        for (int32_t mxwElement = n - elmWidth - (elements - bar - 2);
             mxwElement > maxWidth; mxwElement--) {
          lessVal += Combins(n - elmWidth - mxwElement - 1, elements - bar - 3);
        }
        subVal -= lessVal * (elements - 1 - bar);
      } else if (n - elmWidth > maxWidth) {
        subVal--;
      }
      val -= subVal;
      if (val < 0) {
        break;
      }
      elmWidth++;
      narrowMask &= ~(1 << bar);
    }
    val += subVal;
    n -= elmWidth;
    (*widths)[bar] = elmWidth;
  }
  (*widths)[bar] = n;
  return widths.release();
}
int32_t CBC_UtilRSS::GetRSSvalue(CFX_Int32Array& widths,
                                 int32_t maxWidth,
                                 FX_BOOL noNarrow) {
  int32_t elements = widths.GetSize();
  int32_t n = 0;
  for (int32_t i = 0; i < elements; i++) {
    n += widths[i];
  }
  int32_t val = 0;
  int32_t narrowMask = 0;
  for (int32_t bar = 0; bar < elements - 1; bar++) {
    int32_t elmWidth;
    for (elmWidth = 1, narrowMask |= (1 << bar); elmWidth < widths[bar];
         elmWidth++, narrowMask &= ~(1 << bar)) {
      int32_t subVal = Combins(n - elmWidth - 1, elements - bar - 2);
      if (noNarrow && (narrowMask == 0) &&
          (n - elmWidth - (elements - bar - 1) >= elements - bar - 1)) {
        subVal -= Combins(n - elmWidth - (elements - bar), elements - bar - 2);
      }
      if (elements - bar - 1 > 1) {
        int32_t lessVal = 0;
        for (int32_t mxwElement = n - elmWidth - (elements - bar - 2);
             mxwElement > maxWidth; mxwElement--) {
          lessVal += Combins(n - elmWidth - mxwElement - 1, elements - bar - 3);
        }
        subVal -= lessVal * (elements - 1 - bar);
      } else if (n - elmWidth > maxWidth) {
        subVal--;
      }
      val += subVal;
    }
    n -= elmWidth;
  }
  return val;
}
int32_t CBC_UtilRSS::Combins(int32_t n, int32_t r) {
  int32_t maxDenom;
  int32_t minDenom;
  if (n - r > r) {
    minDenom = r;
    maxDenom = n - r;
  } else {
    minDenom = n - r;
    maxDenom = r;
  }
  int32_t val = 1;
  int32_t j = 1;
  for (int32_t i = n; i > maxDenom; i--) {
    val *= i;
    if (j <= minDenom) {
      val /= j;
      j++;
    }
  }
  while (j <= minDenom) {
    val /= j;
    j++;
  }
  return val;
}
CFX_Int32Array* CBC_UtilRSS::Elements(CFX_Int32Array& eDist,
                                      int32_t N,
                                      int32_t K) {
  CFX_Int32Array* widths = new CFX_Int32Array;
  widths->SetSize(eDist.GetSize() + 2);
  int32_t twoK = K << 1;
  (*widths)[0] = 1;
  int32_t i;
  int32_t minEven = 10;
  int32_t barSum = 1;
  for (i = 1; i < twoK - 2; i += 2) {
    (*widths)[i] = eDist[i - 1] - (*widths)[i - 1];
    (*widths)[i + 1] = eDist[i] - (*widths)[i];
    barSum += (*widths)[i] + (*widths)[i + 1];
    if ((*widths)[i] < minEven) {
      minEven = (*widths)[i];
    }
  }
  (*widths)[twoK - 1] = N - barSum;
  if ((*widths)[twoK - 1] < minEven) {
    minEven = (*widths)[twoK - 1];
  }
  if (minEven > 1) {
    for (i = 0; i < twoK; i += 2) {
      (*widths)[i] += minEven - 1;
      (*widths)[i + 1] -= minEven - 1;
    }
  }
  return widths;
}
