/*
 * (C) 1999-2003 Lars Knoll (knoll@kde.org)
 * Copyright (C) 2004, 2005, 2006, 2008 Apple Inc. All rights reserved.
 * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public License
 * along with this library; see the file COPYING.LIB.  If not, write to
 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */

#ifndef THIRD_PARTY_BLINK_RENDERER_CORE_CSS_CSS_PRIMITIVE_VALUE_H_
#define THIRD_PARTY_BLINK_RENDERER_CORE_CSS_CSS_PRIMITIVE_VALUE_H_

#include "third_party/blink/renderer/core/core_export.h"
#include "third_party/blink/renderer/core/css/css_property_names.h"
#include "third_party/blink/renderer/core/css/css_value.h"
#include "third_party/blink/renderer/core/css_value_keywords.h"
#include "third_party/blink/renderer/platform/wtf/bit_vector.h"
#include "third_party/blink/renderer/platform/wtf/forward.h"
#include "third_party/blink/renderer/platform/wtf/math_extras.h"
#include "third_party/blink/renderer/platform/wtf/text/string_hash.h"
#include "third_party/blink/renderer/platform/wtf/text/string_view.h"

namespace blink {

class CSSCalcValue;
class CSSToLengthConversionData;
class Length;

// Dimension calculations are imprecise, often resulting in values of e.g.
// 44.99998. We need to go ahead and round if we're really close to the next
// integer value.
template <typename T>
inline T RoundForImpreciseConversion(double value) {
  value += (value < 0) ? -0.01 : +0.01;
  return ((value > std::numeric_limits<T>::max()) ||
          (value < std::numeric_limits<T>::min()))
             ? 0
             : static_cast<T>(value);
}

template <>
inline float RoundForImpreciseConversion(double value) {
  double ceiled_value = ceil(value);
  double proximity_to_next_int = ceiled_value - value;
  if (proximity_to_next_int <= 0.01 && value > 0)
    return static_cast<float>(ceiled_value);
  if (proximity_to_next_int >= 0.99 && value < 0)
    return static_cast<float>(floor(value));
  return static_cast<float>(value);
}

// CSSPrimitiveValue stores numeric data types (e.g. 1, 10px, 4%) and calc()
// values (e.g. calc(3px + 2em)).
class CORE_EXPORT CSSPrimitiveValue : public CSSValue {
 public:
  // These units are iterated through, so be careful when adding or changing the
  // order.
  enum class UnitType {
    kUnknown,
    kNumber,
    kPercentage,
    // Length units
    kEms,
    kExs,
    kPixels,
    kCentimeters,
    kMillimeters,
    kInches,
    kPoints,
    kPicas,
    kQuarterMillimeters,
    kViewportWidth,
    kViewportHeight,
    kViewportMin,
    kViewportMax,
    kRems,
    kChs,
    kUserUnits,  // The SVG term for unitless lengths
    // Angle units
    kDegrees,
    kRadians,
    kGradians,
    kTurns,
    // Time units
    kMilliseconds,
    kSeconds,
    kHertz,
    kKilohertz,
    // Resolution
    kDotsPerPixel,
    kDotsPerInch,
    kDotsPerCentimeter,
    // Other units
    kFraction,
    kInteger,
    kCalc,
    kCalcPercentageWithNumber,
    kCalcPercentageWithLength,
    kCalcLengthWithNumber,
    kCalcPercentageWithLengthAndNumber,

    // This value is used to handle quirky margins in reflow roots (body, td,
    // and th) like WinIE. The basic idea is that a stylesheet can use the value
    // __qem (for quirky em) instead of em. When the quirky value is used, if
    // you're in quirks mode, the margin will collapse away inside a table cell.
    // This quirk is specified in the HTML spec but our impl is different.
    // TODO: Remove this. crbug.com/443952
    kQuirkyEms,
  };

  enum LengthUnitType {
    kUnitTypePixels = 0,
    kUnitTypePercentage,
    kUnitTypeFontSize,
    kUnitTypeFontXSize,
    kUnitTypeRootFontSize,
    kUnitTypeZeroCharacterWidth,
    kUnitTypeViewportWidth,
    kUnitTypeViewportHeight,
    kUnitTypeViewportMin,
    kUnitTypeViewportMax,

    // This value must come after the last length unit type to enable iteration
    // over the length unit types.
    kLengthUnitTypeCount,
  };

  struct CSSLengthArray {
    CSSLengthArray() : values(kLengthUnitTypeCount) {
      type_flags.Resize(kLengthUnitTypeCount);
    }

    Vector<double, CSSPrimitiveValue::kLengthUnitTypeCount> values;
    BitVector type_flags;
  };

  void AccumulateLengthArray(CSSLengthArray&, double multiplier = 1) const;

  enum UnitCategory {
    kUNumber,
    kUPercent,
    kULength,
    kUAngle,
    kUTime,
    kUFrequency,
    kUResolution,
    kUOther
  };
  static UnitCategory UnitTypeToUnitCategory(UnitType);
  static float ClampToCSSLengthRange(double);

  static bool IsAngle(UnitType unit) {
    return unit == UnitType::kDegrees || unit == UnitType::kRadians ||
           unit == UnitType::kGradians || unit == UnitType::kTurns;
  }
  bool IsAngle() const { return IsAngle(TypeWithCalcResolved()); }
  bool IsFontRelativeLength() const {
    return GetType() == UnitType::kQuirkyEms || GetType() == UnitType::kEms ||
           GetType() == UnitType::kExs || GetType() == UnitType::kRems ||
           GetType() == UnitType::kChs;
  }
  bool IsQuirkyEms() const { return GetType() == UnitType::kQuirkyEms; }
  bool IsViewportPercentageLength() const {
    return IsViewportPercentageLength(GetType());
  }
  static bool IsViewportPercentageLength(UnitType type) {
    return type >= UnitType::kViewportWidth && type <= UnitType::kViewportMax;
  }
  static bool IsLength(UnitType type) {
    return (type >= UnitType::kEms && type <= UnitType::kUserUnits) ||
           type == UnitType::kQuirkyEms;
  }
  static inline bool IsRelativeUnit(UnitType type) {
    return type == UnitType::kPercentage || type == UnitType::kEms ||
           type == UnitType::kExs || type == UnitType::kRems ||
           type == UnitType::kChs || IsViewportPercentageLength(type);
  }
  bool IsLength() const { return IsLength(TypeWithCalcResolved()); }
  bool IsNumber() const {
    return TypeWithCalcResolved() == UnitType::kNumber ||
           TypeWithCalcResolved() == UnitType::kInteger;
  }
  bool IsPercentage() const {
    return TypeWithCalcResolved() == UnitType::kPercentage;
  }
  bool IsPx() const { return TypeWithCalcResolved() == UnitType::kPixels; }
  static bool IsTime(UnitType unit) {
    return unit == UnitType::kSeconds || unit == UnitType::kMilliseconds;
  }
  bool IsTime() const { return IsTime(TypeWithCalcResolved()); }
  static bool IsFrequency(UnitType unit) {
    return unit == UnitType::kHertz || unit == UnitType::kKilohertz;
  }
  bool IsCalculated() const { return GetType() == UnitType::kCalc; }
  bool IsCalculatedPercentageWithNumber() const {
    return TypeWithCalcResolved() == UnitType::kCalcPercentageWithNumber;
  }
  bool IsCalculatedPercentageWithLength() const {
    return TypeWithCalcResolved() == UnitType::kCalcPercentageWithLength;
  }
  static bool IsResolution(UnitType type) {
    return type >= UnitType::kDotsPerPixel &&
           type <= UnitType::kDotsPerCentimeter;
  }
  bool IsResolution() const { return IsResolution(GetType()); }
  static bool IsFlex(UnitType unit) { return unit == UnitType::kFraction; }
  bool IsFlex() const { return IsFlex(GetType()); }

  static CSSPrimitiveValue* Create(double value, UnitType);
  static CSSPrimitiveValue* Create(const Length& value, float zoom) {
    return MakeGarbageCollected<CSSPrimitiveValue>(value, zoom);
  }

  // TODO(sashab): Remove this.
  template <typename T>
  static CSSPrimitiveValue* Create(T value) {
    return MakeGarbageCollected<CSSPrimitiveValue>(value);
  }

  CSSPrimitiveValue(const Length&, float zoom);
  CSSPrimitiveValue(double, UnitType);
  template <typename T>
  CSSPrimitiveValue(T);  // Defined in CSSPrimitiveValueMappings.h
  template <typename T>
  CSSPrimitiveValue(T* val) : CSSValue(kPrimitiveClass) {
    Init(val);
  }
  ~CSSPrimitiveValue();

  UnitType TypeWithCalcResolved() const;

  double ComputeDegrees() const;
  double ComputeSeconds() const;
  double ComputeDotsPerPixel() const;

  // Computes a length in pixels, resolving relative lengths
  template <typename T>
  T ComputeLength(const CSSToLengthConversionData&) const;

  // Converts to a Length (Fixed, Percent or Calculated)
  Length ConvertToLength(const CSSToLengthConversionData&) const;

  double GetDoubleValue() const;
  float GetFloatValue() const { return GetValue<float>(); }
  int GetIntValue() const { return GetValue<int>(); }
  template <typename T>
  inline T GetValue() const {
    return clampTo<T>(GetDoubleValue());
  }

  CSSCalcValue* CssCalcValue() const {
    DCHECK(IsCalculated());
    return value_.calc;
  }

  template <typename T>
  inline T ConvertTo() const;  // Defined in CSSPrimitiveValueMappings.h

  static const char* UnitTypeToString(UnitType);
  static UnitType StringToUnitType(StringView string) {
    if (string.Is8Bit())
      return StringToUnitType(string.Characters8(), string.length());
    return StringToUnitType(string.Characters16(), string.length());
  }

  String CustomCSSText() const;

  bool Equals(const CSSPrimitiveValue&) const;

  void TraceAfterDispatch(blink::Visitor*);

  static UnitType CanonicalUnitTypeForCategory(UnitCategory);
  static double ConversionToCanonicalUnitsScaleFactor(UnitType);

  // Returns true and populates lengthUnitType, if unitType is a length unit.
  // Otherwise, returns false.
  static bool UnitTypeToLengthUnitType(UnitType, LengthUnitType&);
  static UnitType LengthUnitTypeToUnitType(LengthUnitType);

 private:
  static void Create(int);       // compile-time guard
  static void Create(unsigned);  // compile-time guard
  template <typename T>
  operator T*();  // compile-time guard

  // Code generated by css_primitive_value_unit_trie.cc.tmpl
  static UnitType StringToUnitType(const LChar*, unsigned length);
  static UnitType StringToUnitType(const UChar*, unsigned length);

  void Init(UnitType);
  void Init(const Length&);
  void Init(CSSCalcValue*);

  double ComputeLengthDouble(const CSSToLengthConversionData&) const;

  inline UnitType GetType() const {
    return static_cast<UnitType>(primitive_unit_type_);
  }

  union {
    double num;
    // FIXME: oilpan: Should be a member, but no support for members in unions.
    // Just trace the raw ptr for now.
    CSSCalcValue* calc;
  } value_;
};

using CSSLengthArray = CSSPrimitiveValue::CSSLengthArray;

DEFINE_CSS_VALUE_TYPE_CASTS(CSSPrimitiveValue, IsPrimitiveValue());

template <>
int CSSPrimitiveValue::ComputeLength(const CSSToLengthConversionData&) const;

template <>
Length CSSPrimitiveValue::ComputeLength(const CSSToLengthConversionData&) const;

template <>
unsigned CSSPrimitiveValue::ComputeLength(
    const CSSToLengthConversionData&) const;

template <>
int16_t CSSPrimitiveValue::ComputeLength(
    const CSSToLengthConversionData&) const;

template <>
float CSSPrimitiveValue::ComputeLength(const CSSToLengthConversionData&) const;

template <>
double CSSPrimitiveValue::ComputeLength(const CSSToLengthConversionData&) const;
}  // namespace blink

#endif  // THIRD_PARTY_BLINK_RENDERER_CORE_CSS_CSS_PRIMITIVE_VALUE_H_
