<?php
/**
 * @copyright (c) Kufer Software GmbH, Loisachstrasse 4, D-84453 Mühldorf
 */

namespace Kufer\KuferTools\Utils\WssField;

abstract class WssFieldFreiWaehlbareEingabefelder extends WssField
{
  private $_htmlFreiWaehlbaresEingabefeld;

  abstract protected function getFeldnameOhneNummer();

  abstract protected function getDbwFreiWaehlbareEingabefelder();

  protected function getFieldBearbeitbar($datamodulWert, $isFormular, string $requestPrefix = '')
  {
    return $this->_getFeldInput($this->datamodulColumn, $this->datamodulColumn->accesslevel, $datamodulWert, $requestPrefix);
  }

  protected function getValue($datamodulWert, $isFormular = false)
  {
    return $this->_getFeldValue($this->datamodulColumn, $datamodulWert);
  }

  public function inPost(string $requestPrefix = ''): bool
  {
    if ($this->isCheckbox()) {
      
      return $this->datamodulColumn->canedit;
    }

    return parent::inPost($requestPrefix);
  }

  public function getValueFromPost(string $requestPrefix = '')
  {
    if ($this->isCheckbox()) {
      if (\PostOperations::isDefined(($requestPrefix === '' ? '' : $requestPrefix . '_') . $this->getDatamodulAndFieldName())) {
        return 'W';
      } else {
        return 'F';
      }
    }

    return parent::getValueFromPost($requestPrefix);
  }

  public function getHtmlEncodedValue($datamodulWert, bool $isFormular): string
  {
    if ($this->isCheckbox()) {
      $value = $this->getValue($datamodulWert, $isFormular);
      if ($value == 'W') {
        return 'Ja';
      } else {
        if ($this->showAlternativtext()) {
          return $this->getAlternativtext();
        } else {
          return 'Nein';
        }
      }
    }

    return parent::getHtmlEncodedValue($datamodulWert, $isFormular);
  }

  public function isValueEmpty($value): bool
  {
    return parent::isValueEmpty($value) || ($this->isCheckbox() && $value == 'Nein');
  }

  protected function isMandatoryValueEmpty($value)
  {
    if ($this->isCheckbox()) {
      return parent::isMandatoryValueEmpty($value) || in_array($value, array('F', 'N'));
    }

    return parent::isMandatoryValueEmpty($value);
  }

  private function getHTMLFreiWaehlbaresEingabefeld()
  {
    if (is_null($this->_htmlFreiWaehlbaresEingabefeld)) {
      
      $this->_htmlFreiWaehlbaresEingabefeld = new \HtmlFreiWaehlbaresEingabefeldResponsive();
    }

    return $this->_htmlFreiWaehlbaresEingabefeld;
  }

  private function _getFeldInput($pField, $pPrivileg, $pDataModulWert, string $requestPrefix = '')
  {
    $feldEinstellungenMitWert = $this->getEinstellungenMitWertZumAktuellenFeld($pField, $pDataModulWert);
    if ($feldEinstellungenMitWert === false) {
      return false;
    }
    $prefix = ($requestPrefix === '' ? '' : $requestPrefix . '_');

    $readonly = ($pField->canedit == false) || ($pPrivileg < 2);
    $name = $prefix . $this->_getFieldname($pField);
    $class = 'recht_' . $pField->privileg_key . ' ' . $this->getMandatoryClass($pField);
    $id = $prefix . $this->_getFieldname($pField);

    return $this->getHTMLFreiWaehlbaresEingabefeld()->getInputFeld($feldEinstellungenMitWert, $name, $id, $class, $readonly, null);
  }

  private function _getFeldValue($pField, $pDataModulWert)
  {
    $feldEinstellungenMitWert = $this->getEinstellungenMitWertZumAktuellenFeld($pField, $pDataModulWert);
    if ($feldEinstellungenMitWert === false) {
      return '';
    }

    return $feldEinstellungenMitWert->wert;
  }

  public function isValid($value, bool $checkPflichtfelder = true): bool
  {
    if ($this->isMandatoryValueEmpty($value)) {
      return !($checkPflichtfelder && $this->isMandatory());
    }

    $feldEinstellungen = $this->getEinstellungenZumAktuellenFeld();
    if ($feldEinstellungen === false) {
      return false;
    }

    $typ = $feldEinstellungen->typ;
    if (is_null($typ)) {
      return true;
    }

    switch ($typ[0] ?? 'T') {
      default: 
      case 'T':
        $maxLength = (int)\StringOperations::substr($typ, 1); 
        if ($maxLength > 0) {
          return \StringOperations::strlen($value) <= $maxLength;
        }

        return true;
      case 'C': 
        return true;
      case 'D': 
        return \DateTimeOperations::isValidDate($value);
      case 'Z': 
        if ($typ[1] === 'W') {
          return \CleanOperations::isFloatMitKomma($value);
        } else {
          return \CleanOperations::isInt($value);
        }
    }
  }

  protected function encodeValue($value)
  {
    return $this->dontEncode($value);
  }

  private function isCheckbox()
  {
    $feldEinstellungen = $this->getEinstellungenZumAktuellenFeld();
    if ($feldEinstellungen !== false && $feldEinstellungen->typ === 'C') {
      return true;
    } else {
      return false;
    }
  }

  
  private function getDbwFreiWaehlbareEingabefelderCached()
  {
    static $cache = array();
    if (!array_key_exists(static::class, $cache)) {
      $cache[static::class] = $this->getDbwFreiWaehlbareEingabefelder();
    }

    return $cache[static::class];
  }

  private function getFreifeldNummer()
  {
    $found = array();
    preg_match('/' . $this->getFeldnameOhneNummer() . '(\\d+)/', $this->getFieldName(), $found);

    return $found[1] ?? false;
  }

  private function getEinstellungenZumAktuellenFeld()
  {
    $dbwFreiWaehlbareEingabefelder = $this->getDbwFreiWaehlbareEingabefelderCached();
    $freiWaehlbareFelderEinstellungen = $dbwFreiWaehlbareEingabefelder->getFreiWaehlbareFelder();
    $freifeldNummer = $this->getFreifeldNummer();
    if ($freifeldNummer === false || !isset($freiWaehlbareFelderEinstellungen[$freifeldNummer - 1])) {
      return false;
    }

    return $freiWaehlbareFelderEinstellungen[$freifeldNummer - 1];
  }

  private function getEinstellungenMitWertZumAktuellenFeld($pField, $pDataModulWert)
  {
    $feldEinstellungen = $this->getEinstellungenZumAktuellenFeld();
    if ($feldEinstellungen !== false) {
      $dbwFreiWaehlbareEingabefelder = $this->getDbwFreiWaehlbareEingabefelderCached();

      
      $datamodul = $pDataModulWert->getDatamodulByName($pField->datamodul);

      return $dbwFreiWaehlbareEingabefelder->fillEingabefeldByDatamodul($feldEinstellungen, $datamodul);
    }

    return false;
  }
}