<?php

namespace Internetgalerie\IgDatapoolFe\ViewHelpers;

use TYPO3Fluid\Fluid\Core\ViewHelper\AbstractViewHelper;
use TYPO3\CMS\Extbase\DomainObject\AbstractDomainObject;
use TYPO3\CMS\Core\Utility\GeneralUtility;
use Internetgalerie\IgDatapoolFe\Utility\NeedfulThings;
use Internetgalerie\IgDatapoolFe\Services\LangService;
use TYPO3\CMS\Extbase\Reflection\ObjectAccess;
use TYPO3\CMS\Extbase\Persistence\ObjectStorage;
use TYPO3\CMS\Extbase\Domain\Model\FileReference;
use DateTime;

/**
 * Renders a field summary, i.e. a table of all modified propertys of an object
 *
 * @api
 * @author     Markus Baumgartner <mb@stylesheep.ch>, Internetgalerie AG
 * @package    IgDatapoolFE
 * @subpackage ViewHelpers
 */
class FieldSummaryViewHelper extends AbstractViewHelper
{
    use ViewHelperTrait;

    public function initializeArguments(): void
    {
        $this->registerArgument('object', AbstractDomainObject::class, 'The object', true);
        $this->registerArgument('changedValueColor', 'string', 'The bg-color of the changes values', false, '#FF9696');
        $this->registerArgument('dontPrefixWithModelName', 'boolean', 'Prefix', false, false);
        $this->registerArgument('hideEmptyValues', 'boolean', 'hide', false, false);
        $this->registerArgument('fieldList', 'string', 'Comma-separated list of fields to show', false, '*');
        $this->registerArgument('exclude', 'string', 'Comma-separated list of excluded fields', false, 'uid,pid');
        $this->registerArgument('noBorder', 'boolean', 'Remove Border', false, true);
    }

    /**
     * renders a summary (mail friendly)
     *
     * @param AbstractDomainObject $object
     * @return string
     */
    public function render() : string
    {
        $object = $this->arguments['object'];
        // resolve the fields
        $fields = [];
        if ($this->arguments['fieldList'] == '*') {
            $fields = array_keys($object->_getProperties());
        } else {
            $fields = GeneralUtility::trimExplode(',', $this->arguments['fieldList']);
        }
        $fields = array_diff($fields, GeneralUtility::trimExplode(',', $this->arguments['exclude']));

        //render
        $html = [];
        //get the tablename for label resolution
        $tablename = NeedfulThings::classToTable($object::class);
        if (!$this->arguments['dontPrefixWithModelName']) {
            $html[] = '<strong>' . LangService::ll($tablename) . '</strong>';
        }
        $borderWidth = intval($this->arguments['noBorder']);

        $html[] = '<table border="'.$borderWidth.'" cellspacing="0" style="border-collapse:collapse;width:100%">';

        foreach ($fields as $f) {
            $val = ObjectAccess::getPropertyPath($object, $f);

            $changed_txt = '';
            if ($object->_isDirty($f)) {
                $changed_txt = 'background-color:' . $this->arguments['changedValueColor'] . ';';
            }
            //convert types
            if ($val instanceof ObjectStorage) {
                $val->rewind();
                $current = $val->current();
                if ($current instanceof FileReference) {
                    $name = $current->getOriginalResource()->getName();
                    $val = '<a target="_blank" href="' . GeneralUtility::getIndpEnv('TYPO3_REQUEST_HOST') . '/' . $current->getOriginalResource()->getOriginalFile()->getPublicUrl() . '">' . basename($name) . '</a>';
                } else {
                    $val = implode('<br />', $val->toArray());
                }
            } elseif ($val instanceof DateTime) {
                $val = $val->format('d.m.Y');
            } elseif ($val instanceof FileReference) {
                $name = $val->getOriginalResource()->getName();
                $val = '<a href="' . GeneralUtility::getIndpEnv('TYPO3_REQUEST_HOST') . '/' . $val->getOriginalResource()->getOriginalFile()->getPublicUrl() . '">' . basename($name) . '</a>';
            }
            //handle empty  values
            if (!$val && $this->arguments['hideEmptyValues']) {
                continue;
            }

            if (!$val) {
                $val = '&nbsp;';
            }

            //resolve label
            $fieldname = NeedfulThings::propertyToField($f);
            $field_label = LangService::ll($tablename . '.' . $fieldname);

            //changed_txt, fieldlabel, val
            $html[] = '<tr><td style="padding:3px;' . $changed_txt . 'width:150px;font-size:12px;vertical-align:top">' . $field_label . '</td><td style="padding:3px; ' . $changed_txt . 'vertical-align:top;font-size:12px">' . $val . '</td></tr>';
        }
        $html[] = '</table><br />';

        return implode("\n", $html);
    }
}
