You are here

public function CKEditor::buildConfigurationForm in Drupal 8

Same name and namespace in other branches
  1. 9 core/modules/ckeditor/src/Plugin/Editor/CKEditor.php \Drupal\ckeditor\Plugin\Editor\CKEditor::buildConfigurationForm()

Form constructor.

Plugin forms are embedded in other forms. In order to know where the plugin form is located in the parent form, #parents and #array_parents must be known, but these are not available during the initial build phase. In order to have these properties available when building the plugin form's elements, let this method return a form element that has a #process callback and build the rest of the form in the callback. By the time the callback is executed, the element's #parents and #array_parents properties will have been set by the form API. For more documentation on #parents and #array_parents, see \Drupal\Core\Render\Element\FormElement.

Parameters

array $form: An associative array containing the initial structure of the plugin form.

\Drupal\Core\Form\FormStateInterface $form_state: The current state of the form. Calling code should pass on a subform state created through \Drupal\Core\Form\SubformState::createForSubform().

Return value

array The form structure.

Overrides EditorBase::buildConfigurationForm

File

core/modules/ckeditor/src/Plugin/Editor/CKEditor.php, line 156

Class

CKEditor
Defines a CKEditor-based text editor for Drupal.

Namespace

Drupal\ckeditor\Plugin\Editor

Code

public function buildConfigurationForm(array $form, FormStateInterface $form_state) {
  $editor = $form_state
    ->get('editor');
  $settings = $editor
    ->getSettings();
  $ckeditor_settings_toolbar = [
    '#theme' => 'ckeditor_settings_toolbar',
    '#editor' => $editor,
    '#plugins' => $this->ckeditorPluginManager
      ->getButtons(),
  ];
  $form['toolbar'] = [
    '#type' => 'container',
    '#attached' => [
      'library' => [
        'ckeditor/drupal.ckeditor.admin',
      ],
      'drupalSettings' => [
        'ckeditor' => [
          'toolbarAdmin' => (string) $this->renderer
            ->renderPlain($ckeditor_settings_toolbar),
        ],
      ],
    ],
    '#attributes' => [
      'class' => [
        'ckeditor-toolbar-configuration',
      ],
    ],
  ];
  $form['toolbar']['button_groups'] = [
    '#type' => 'textarea',
    '#title' => $this
      ->t('Toolbar buttons'),
    '#default_value' => json_encode($settings['toolbar']['rows']),
    '#attributes' => [
      'class' => [
        'ckeditor-toolbar-textarea',
      ],
    ],
  ];

  // CKEditor plugin settings, if any.
  $form['plugin_settings'] = [
    '#type' => 'vertical_tabs',
    '#title' => $this
      ->t('CKEditor plugin settings'),
    '#attributes' => [
      'id' => 'ckeditor-plugin-settings',
    ],
  ];
  $this->ckeditorPluginManager
    ->injectPluginSettingsForm($form, $form_state, $editor);
  if (count(Element::children($form['plugins'])) === 0) {
    unset($form['plugins']);
    unset($form['plugin_settings']);
  }

  // Hidden CKEditor instance. We need a hidden CKEditor instance with all
  // plugins enabled, so we can retrieve CKEditor's per-feature metadata (on
  // which tags, attributes, styles and classes are enabled). This metadata is
  // necessary for certain filters' (for instance, the html_filter filter)
  // settings to be updated accordingly.
  // Get a list of all external plugins and their corresponding files.
  $plugins = array_keys($this->ckeditorPluginManager
    ->getDefinitions());
  $all_external_plugins = [];
  foreach ($plugins as $plugin_id) {
    $plugin = $this->ckeditorPluginManager
      ->createInstance($plugin_id);
    if (!$plugin
      ->isInternal()) {
      $all_external_plugins[$plugin_id] = $plugin
        ->getFile();
    }
  }

  // Get a list of all buttons that are provided by all plugins.
  $all_buttons = array_reduce($this->ckeditorPluginManager
    ->getButtons(), function ($result, $item) {
    return array_merge($result, array_keys($item));
  }, []);

  // Build a fake Editor object, which we'll use to generate JavaScript
  // settings for this fake Editor instance.
  $fake_editor = Editor::create([
    'format' => $editor
      ->id(),
    'editor' => 'ckeditor',
    'settings' => [
      // Single toolbar row, single button group, all existing buttons.
      'toolbar' => [
        'rows' => [
          0 => [
            0 => [
              'name' => 'All existing buttons',
              'items' => $all_buttons,
            ],
          ],
        ],
      ],
      'plugins' => $settings['plugins'],
    ],
  ]);
  $config = $this
    ->getJSSettings($fake_editor);

  // Remove the ACF configuration that is generated based on filter settings,
  // because otherwise we cannot retrieve per-feature metadata.
  unset($config['allowedContent']);
  $form['hidden_ckeditor'] = [
    '#markup' => '<div id="ckeditor-hidden" class="hidden"></div>',
    '#attached' => [
      'drupalSettings' => [
        'ckeditor' => [
          'hiddenCKEditorConfig' => $config,
        ],
      ],
    ],
  ];
  return $form;
}