You are here

public static function FractionDecimal::validateDecimal in Fraction 8

Same name and namespace in other branches
  1. 2.x src/Element/FractionDecimal.php \Drupal\fraction\Element\FractionDecimal::validateDecimal()

Validates the fraction_decimal element.

Parameters

array $element: The form element.

\Drupal\Core\Form\FormStateInterface $form_state: The current state of the form.

array $complete_form: The complete form structure.

File

src/Element/FractionDecimal.php, line 66

Class

FractionDecimal
Provides a fraction decimal form element.

Namespace

Drupal\fraction\Element

Code

public static function validateDecimal(array $element, FormStateInterface $form_state, array &$complete_form) {
  $value = trim($element['#value']);

  // Only continue with validation if the value is not empty.
  if ($element['#value'] === '') {
    return;
  }

  // Do basic number validations.
  Number::validateNumber($element, $form_state, $complete_form);

  // Only continue with validation if value is a valid number.
  if (count($form_state
    ->getErrors()) !== 0) {
    return;
  }

  // Convert the value to a fraction.
  $fraction = Fraction::createFromDecimal($value);

  // Get the numerator and denominator.
  $numerator = $fraction
    ->getNumerator();
  $denominator = $fraction
    ->getDenominator();

  // Set the numerator and denominator values for the form.
  $values = [
    'decimal' => $value,
    'numerator' => $numerator,
    'denominator' => $denominator,
  ];
  $form_state
    ->setValueForElement($element, $values);

  // The maximum number of digits after the decimal place is 9.
  // Explicitly perform a string comparison to ensure precision.
  if ((string) $denominator > '1000000000') {
    $form_state
      ->setError($element, t('The maximum number of digits after the decimal place is 9.'));
  }

  // Ensure that the decimal value is within an acceptable value range.
  // Convert the fraction back to a decimal, because that is what will be
  // stored. Explicitly perform a string comparison to ensure precision.
  $decimal = (string) $fraction
    ->toDecimal(0, TRUE);
  $min_decimal_fraction = new Fraction('-9223372036854775808', $denominator);
  $min_decimal = (string) $min_decimal_fraction
    ->toDecimal(0, TRUE);
  $max_decimal_fraction = new Fraction('9223372036854775807', $denominator);
  $max_decimal = (string) $max_decimal_fraction
    ->toDecimal(0, TRUE);
  $scale = strlen($denominator) - 1;
  $in_bounds = static::checkInBounds($decimal, $min_decimal, $max_decimal, $scale);
  if (!$in_bounds) {
    $form_state
      ->setError($element, t('The number you entered is outside the range of acceptable values. This limitation is related to the decimal precision, so reducing the precision may solve the problem.'));
  }
}