You are here

protected function ParserConfigurationForm::buildRenderStrategy in Markdown 8.2

Builds the render strategy for a specific parser.

Parameters

\Drupal\markdown\Plugin\Markdown\ParserInterface $parser: The parser.

array $element: An element in a render array.

\Drupal\markdown\Form\SubformStateInterface $form_state: The form state.

bool $siteWide: Flag indicating whether the parser is the site-wide parser.

Return value

array The $element passed, modified to include the render strategy elements.

1 call to ParserConfigurationForm::buildRenderStrategy()
ParserConfigurationForm::buildParser in src/Form/ParserConfigurationForm.php
Builds the parser form elements.

File

src/Form/ParserConfigurationForm.php, line 465

Class

ParserConfigurationForm
Form for modifying parser configuration.

Namespace

Drupal\markdown\Form

Code

protected function buildRenderStrategy(ParserInterface $parser, array $element, SubformStateInterface $form_state, $siteWide = FALSE) {
  $element['render_strategy'] = [
    '#weight' => -10,
    '#type' => 'details',
    '#title' => $this
      ->t('Render Strategy'),
    '#group' => $form_state
      ->get('markdownGroup'),
  ];
  $renderStrategySubform =& $element['render_strategy'];
  $renderStrategySubformState = SubformState::createForSubform($renderStrategySubform, $element, $form_state);
  $renderStrategySubform['type'] = [
    '#weight' => -10,
    '#type' => 'select',
    '#description' => $this
      ->t('Determines the strategy to use when dealing with user provided HTML markup.'),
    '#default_value' => $renderStrategySubformState
      ->getValue('type', $parser
      ->getRenderStrategy()),
    '#attributes' => [
      'data-markdown-element' => 'render_strategy',
      'data-markdown-summary' => 'render_strategy',
    ],
    '#options' => [
      RenderStrategyInterface::FILTER_OUTPUT => $this
        ->t('Filter Output'),
      RenderStrategyInterface::ESCAPE_INPUT => $this
        ->t('Escape Input'),
      RenderStrategyInterface::STRIP_INPUT => $this
        ->t('Strip Input'),
      RenderStrategyInterface::NONE => $this
        ->t('None'),
    ],
  ];
  $renderStrategySubform['type']['#description'] = $this
    ->moreInfo($renderStrategySubform['type']['#description'], RenderStrategyInterface::DOCUMENTATION_URL . '#xss');

  // Build allowed HTML plugins.
  $renderStrategySubform['plugins'] = [
    '#weight' => -10,
    '#type' => 'item',
    '#input' => FALSE,
    '#title' => $this
      ->t('Allowed HTML'),
    '#description_display' => 'before',
    '#description' => $this
      ->t('The following are registered <code>@MarkdownAllowedHtml</code> plugins that allow HTML tags and attributes based on configuration. These are typically provided by the parser itself, any of its enabled extensions that convert additional HTML tag and potentially various Drupal filters, modules or themes (if supported).'),
  ];
  $renderStrategySubform['plugins']['#description'] = $this
    ->moreInfo($renderStrategySubform['plugins']['#description'], RenderStrategyInterface::DOCUMENTATION_URL);
  $renderStrategySubformState
    ->addElementState($renderStrategySubform['plugins'], 'visible', 'type', [
    'value' => RenderStrategyInterface::FILTER_OUTPUT,
  ]);
  $allowedHtmlManager = AllowedHtmlManager::create();
  foreach ($allowedHtmlManager
    ->appliesTo($parser) as $plugin_id => $allowedHtml) {
    $pluginDefinition = $allowedHtml
      ->getPluginDefinition();
    $label = isset($pluginDefinition['label']) ? $pluginDefinition['label'] : $plugin_id;
    $description = isset($pluginDefinition['description']) ? $pluginDefinition['description'] : '';
    $type = isset($pluginDefinition['type']) ? $pluginDefinition['type'] : 'other';
    if (!isset($renderStrategySubform['plugins'][$type])) {
      $renderStrategySubform['plugins'][$type] = [
        '#type' => 'details',
        '#open' => TRUE,
        '#title' => $this
          ->t(ucfirst($type) . 's'),
        //phpcs:ignore
        '#parents' => $renderStrategySubformState
          ->createParents([
          'plugins',
        ]),
      ];
      if ($type === 'module') {
        $renderStrategySubform['plugins'][$type]['#weight'] = -10;
      }
      if ($type === 'filter') {
        $renderStrategySubform['plugins'][$type]['#weight'] = -9;
        $renderStrategySubform['plugins'][$type]['#description'] = $this
          ->t('NOTE: these will only be applied when the filter it represents is actually enabled.');
        $renderStrategySubform['plugins'][$type]['#description_display'] = 'before';
      }
      if ($type === 'parser') {
        $renderStrategySubform['plugins'][$type]['#weight'] = -8;
      }
      if ($type === 'extension') {
        $renderStrategySubform['plugins'][$type]['#weight'] = -7;
        $renderStrategySubform['plugins'][$type]['#title'] = $this
          ->t('Extensions');
        $renderStrategySubform['plugins'][$type]['#description'] = $this
          ->t('NOTE: these will only be applied when the parser extension it represents is actually enabled.');
        $renderStrategySubform['plugins'][$type]['#description_display'] = 'before';
      }
      if ($type === 'theme') {
        $renderStrategySubform['plugins'][$type]['#weight'] = -6;
        $renderStrategySubform['plugins'][$type]['#description'] = $this
          ->t('NOTE: these will only be applied when the theme that provides the plugin is the active theme or is a descendant of the active theme.');
        $renderStrategySubform['plugins'][$type]['#description_display'] = 'before';
      }
    }
    $allowedHtmlTags = $allowedHtml
      ->allowedHtmlTags($parser);
    $allowedHtmlPlugins = $parser
      ->getAllowedHtmlPlugins();

    // Determine the default value.
    $defaultValue = NULL;
    if ($allowedHtmlTags) {

      // Setting value.
      if (!isset($defaultValue) && isset($allowedHtmlPlugins[$plugin_id])) {
        $defaultValue = $allowedHtmlPlugins[$plugin_id];
      }
      if (!isset($defaultValue)) {
        if ($type === 'filter' && ($filter = $this
          ->getFilter()) && $filter instanceof FilterFormatAwareInterface && ($format = $filter
          ->getFilterFormat())) {
          $definition = $allowedHtml
            ->getPluginDefinition();
          $filterId = isset($definition['requiresFilter']) ? $definition['requiresFilter'] : $plugin_id;
          $defaultValue = $format
            ->filters()
            ->has($filterId) ? !!$format
            ->filters($filterId)->status : FALSE;
        }
        elseif ($type === 'extension' && $parser instanceof ExtensibleParserInterface && $parser
          ->extensions()
          ->has($plugin_id)) {
          $defaultValue = $parser
            ->extension($plugin_id)
            ->isEnabled();
        }
        else {
          $defaultValue = TRUE;
        }
      }
    }
    $renderStrategySubform['plugins'][$type][$plugin_id] = [
      '#type' => 'checkbox',
      '#title' => $label,
      '#disabled' => !$allowedHtmlTags,
      '#description' => Markup::create(sprintf('%s<pre><code>%s</code></pre>', $description, $allowedHtmlTags ? htmlentities(FilterHtml::tagsToString($allowedHtmlTags)) : $this
        ->t('No HTML tags provided.'))),
      '#default_value' => $renderStrategySubformState
        ->getValue([
        'plugins',
        $plugin_id,
      ], $defaultValue),
      '#attributes' => [
        'data-markdown-default-value' => $renderStrategySubformState
          ->getValue([
          'plugins',
          $plugin_id,
        ], $defaultValue) ? 'true' : 'false',
      ],
    ];
    if ($plugin_id === 'markdown') {
      $renderStrategySubform['plugins'][$type][$plugin_id]['#weight'] = -10;
    }
    if (!$allowedHtmlTags) {
      continue;
    }

    // Filters should only show based on whether they're enabled.
    if ($type === 'extension') {

      // If using the site-wide parser, then allowed HTML plugins that
      // reference disabled extensions there cannot be enable here.
      if ($siteWide) {
        $extensionDisabled = $defaultValue !== TRUE;
        $renderStrategySubform['plugins'][$type][$plugin_id]['#disabled'] = $extensionDisabled;
        if ($extensionDisabled) {
          $renderStrategySubform['plugins'][$type][$plugin_id]['#title'] = new FormattableMarkup('@title @disabled', [
            '@title' => $renderStrategySubform['plugins'][$type][$plugin_id]['#title'],
            '@disabled' => $this
              ->t('(extension disabled)'),
          ]);
        }
      }
      else {
        $parents = array_merge(array_slice($renderStrategySubformState
          ->createParents(), 0, -1), [
          'extensions',
          $plugin_id,
          'enabled',
        ]);
        $selector = ':input[name="' . array_shift($parents) . '[' . implode('][', $parents) . ']"]';
        $renderStrategySubform['plugins'][$type][$plugin_id]['#title'] = new FormattableMarkup('@title @disabled', [
          '@title' => $renderStrategySubform['plugins'][$type][$plugin_id]['#title'],
          '@disabled' => $renderStrategySubformState
            ->conditionalElement([
            '#value' => $this
              ->t('(extension disabled)'),
          ], 'visible', $selector, [
            'checked' => FALSE,
          ]),
        ]);
        $renderStrategySubform['plugins'][$type][$plugin_id]['#states'] = [
          '!checked' => [
            $selector => [
              'checked' => FALSE,
            ],
          ],
          'disabled' => [
            $selector => [
              'checked' => FALSE,
            ],
          ],
        ];
      }
    }
    elseif ($type === 'filter') {
      $selector = ':input[name="filters[' . $plugin_id . '][status]"]';
      $renderStrategySubform['plugins'][$type][$plugin_id]['#title'] = new FormattableMarkup('@title @disabled', [
        '@title' => $renderStrategySubform['plugins'][$type][$plugin_id]['#title'],
        '@disabled' => $renderStrategySubformState
          ->conditionalElement([
          '#value' => $this
            ->t('(filter disabled)'),
        ], 'visible', $selector, [
          'checked' => FALSE,
        ]),
      ]);
      $renderStrategySubform['plugins'][$type][$plugin_id]['#states'] = [
        '!checked' => [
          $selector => [
            'checked' => FALSE,
          ],
        ],
        'disabled' => [
          $selector => [
            'checked' => FALSE,
          ],
        ],
      ];
    }
  }
  $renderStrategySubform['plugins']['#access'] = !!Element::getVisibleChildren($renderStrategySubform['plugins']);
  $renderStrategySubform['custom_allowed_html'] = [
    '#weight' => -10,
    '#type' => 'textarea',
    '#title' => $this
      ->t('Custom Allowed HTML'),
    '#description' => $this
      ->t('A list of additional custom allowed HTML tags that can be used. This follows the same rules as above; use cautiously and sparingly.'),
    '#default_value' => $renderStrategySubformState
      ->getValue('custom_allowed_html', $parser
      ->getCustomAllowedHtml()),
    '#attributes' => [
      'data-markdown-element' => 'custom_allowed_html',
    ],
  ];
  $renderStrategySubform['custom_allowed_html']['#description'] = $this
    ->moreInfo($renderStrategySubform['custom_allowed_html']['#description'], RenderStrategyInterface::DOCUMENTATION_URL);
  FormTrait::resetToDefault($renderStrategySubform['custom_allowed_html'], 'custom_allowed_html', '', $renderStrategySubformState);
  $renderStrategySubformState
    ->addElementState($renderStrategySubform['custom_allowed_html'], 'visible', 'type', [
    'value' => RenderStrategyInterface::FILTER_OUTPUT,
  ]);
  return $element;
}