<?php

namespace Drupal\component_builder;

use Drupal\Component\Plugin\ConfigurableInterface;
use Drupal\Component\Plugin\PluginBase;
use Drupal\Component\Utility\NestedArray;

/**
 * Provides a base class for navigation component plugins.
 */
class ComponentBuilderBase extends PluginBase implements ComponentBuilderPluginInterface, ConfigurableInterface {

  /**
   * The module list service.
   *
   * @var \Drupal\Core\Extension\ModuleExtensionList
   */
  protected $moduleList;

  /**
   * Gets the module list service.
   *
   * @return \Drupal\Core\Extension\ModuleExtensionList
   *   The module extension list service.
   */
  protected function getModuleList() {
    if (!$this->moduleList) {
      $this->moduleList = \Drupal::service('extension.list.module');
    }
    return $this->moduleList;
  }

  /**
   * Gets the Drupal-root relative installation directory of a module.
   *
   * @param string $module_name
   *   The machine name of the module.
   *
   * @return string
   *   The module installation directory.
   *
   * @throws \InvalidArgumentException
   *   If there is no extension with the supplied machine name.
   *
   * @see \Drupal\Core\Extension\ExtensionList::getPath()
   */
  protected function getModulePath(string $module_name) {
    return $this->getModuleList()->getPath($module_name);
  }

  /**
   * The field definition.
   *
   * @var \Drupal\Core\Field\FieldDefinitionInterface
   */
  protected $fieldDefinition;

  /**
   * The formatter settings.
   *
   * @var array
   */
  protected $settings;

  /**
   * The label display setting.
   *
   * @var string
   */
  protected $label;

  /**
   * {@inheritdoc}
   */
  public function __construct(array $configuration, $pluginId, $pluginDefinition) {
    parent::__construct($configuration, $pluginId, $pluginDefinition);
    $this->setConfiguration($configuration);
    $this->moduleList = \Drupal::service('extension.list.module');
  }

  /**
   * {@inheritdoc}
   */
  public function getConfiguration() {
    return $this->configuration;
  }

  /**
   * {@inheritdoc}
   */
  public function setConfiguration(array $configuration) {
    $this->configuration = NestedArray::mergeDeep(
      $this->defaultConfiguration(),
      $configuration
    );
  }

  /**
   * {@inheritdoc}
   */
  public function defaultConfiguration() {
    return [];
  }

  /**
   * {@inheritdoc}
   */
  public function calculateDependencies() {
    return [];
  }

  /**
   * {@inheritdoc}
   */
  public function label() {
    $definition = $this->getPluginDefinition();
    return (string) $definition['label'];
  }

  /**
   * {@inheritdoc}
   */
  public function getTemplateName() {
    $definition = $this->getPluginDefinition();
    return (string) $definition['template'];
  }

  /**
   * {@inheritdoc}
   */
  public function prepareVariables(array &$variables) {
  }

  /**
   * {@inheritdoc}
   */
  public function getLibraries() {
    return [];
  }

  /**
   * {@inheritdoc}
   */
  public function getModule() {
    return $this->pluginDefinition['module'] ?? '';
  }

  /**
   * {@inheritdoc}
   */
  public function getComponentPath() {
    return $this->getModulePath('component_builder') . '/components/component_' . $this->getPluginId();
  }

  /**
   * {@inheritdoc}
   */
  public function isAlterWrapper() {
    return isset($this->pluginDefinition['alter_wrapper']) && $this->pluginDefinition['alter_wrapper'];
  }

  /**
   * {@inheritdoc}
   */
  public function getTemplatePath() {
    return '';
  }

  /**
   * {@inheritdoc}
   */
  public function getDefinePath() {
    $component_name = 'component_' . $this->getPluginId();
    return $this->getComponentPath() . '/' . $component_name . '.yml';
  }

  /**
   * {@inheritdoc}
   */
  public function getIcon() {
    $path = $this->getComponentPath() . '/assets/images/default.png';
    if (file_exists($path)) {
      return $path;
    }
    return '';
  }

  /**
   * {@inheritdoc}
   */
  public function isSingeValue(): bool {
    $definition = $this->getPluginDefinition();
    return $definition['single_value'] ?? FALSE;
  }

}
