logo

Extra Block Types (EBT) - New Layout Builder experience❗

Extra Block Types (EBT) - styled, customizable block types: Slideshows, Tabs, Cards, Accordions and many others. Built-in settings for background, DOM Box, javascript plugins. Experience the future of layout building today.

Demo EBT modules Download EBT modules

❗Extra Paragraph Types (EPT) - New Paragraphs experience

Extra Paragraph Types (EPT) - analogical paragraph based set of modules.

Demo EPT modules Download EPT modules

Scroll

Extending EPT Settings form

13/06/2025, by Ivan

Create new EPT Settings form class

I heard from many programmers worries about number of settings for EPT modules: DOM Box, background, borders, classes, etc. These programmers implied that content editors will be confused or in another way will be encouraged to do drastically different paragraphs, margins, backgrounds. Some projects needs flexibility and more settings for content editors, but some projects have pretty strict story books with components. For this case we need to change our EPT Settings field widget. 

Also if you create a new EPT module and attached javascript plugin with options, you will need to use own EPT settings widget with setting fields for these options.

EPT Core module has EptSettingsDefaultWidget class for EPT Settings field widget. It contains DOM Box, background and all other settings. Let's start to create a new class EptSettingsSimpleWidget (I will put it in EPT Core module). It will contain only three settings Width, Spacing (for margin below paragraph).

Create a new file:
/src/Plugin/Field/FieldWidget/EptSettingsSimpleWidget.php

<?php

namespace Drupal\ept_core\Plugin\Field\FieldWidget;

use Drupal\Core\Field\FieldItemListInterface;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Component\Utility\Color;
use Drupal\Core\StringTranslation\TranslatableMarkup;
use Drupal\ept_core\Plugin\Field\FieldWidget\EptSettingsDefaultWidget;

/**
 * Plugin implementation of the 'ept_settings_simple' widget.
 *
 * @FieldWidget(
 *   id = "ept_settings_simple",
 *   label = @Translation("EPT simple paragraph settings"),
 *   field_types = {
 *     "ept_settings"
 *   }
 * )
 */
class EptSettingsSimpleWidget extends EptSettingsDefaultWidget  {

  /**
   * {@inheritdoc}
   */
  public function formElement(FieldItemListInterface $items, $delta, array $element, array &$form, FormStateInterface $form_state) {
    $element = parent::formElement($items, $delta, $element, $form, $form_state);


    return $element;
  }

  /**
   * {@inheritdoc}
   */
  public function massageFormValues(array $values, array $form, FormStateInterface $form_state) {
    foreach ($values as &$value) {
      $value += ['ept_settings' => []];
    }
    return $values;
  }

}

We will extend our basic settings class EptSettingsDefaultWidget. In annotation comment @FieldWidget we will name our widget id = "ept_settings_simple" and label = @Translation("EPT Simple settings")

/**
 * Plugin implementation of the 'ept_settings_simple' widget.
 *
 * @FieldWidget(
 *   id = "ept_settings_simple",
 *   label = @Translation("EPT simple paragraph settings"),
 *   field_types = {
 *     "ept_settings"
 *   }
 * )
 */

We also have two method formElement(), massageFormValues(). You can leave massageFormValues() as it is. Drupal will automatically serialize all settings in one field field_ept_settings. So it doesn't matter how many settings you have, they will store as serialized array and you need only specify settings fields with Form API:

https://www.drupal.org/docs/drupal-apis/form-api

In formElement(), we will define setting fields. Let's hide DOM Box and border settings:

  /**
   * {@inheritdoc}
   */
  public function formElement(FieldItemListInterface $items, $delta, array $element, array &$form, FormStateInterface $form_state) {
    $element = parent::formElement($items, $delta, $element, $form, $form_state);
    unset($element['ept_settings']['design_options']['box1']);
    unset($element['ept_settings']['design_options']['other_settings']['border_color']);
    unset($element['ept_settings']['design_options']['other_settings']['border_style']);
    unset($element['ept_settings']['design_options']['other_settings']['border_radius']);

    return $element;
  }

If you apply new field widget for one of your EPT paragraph types:

Simple EPT widget
Simple EPT widget

You will see smaller settings form:

EPT settings form
EPT settings form

Now we will remove background settings too. If you need background settings and don't need all other settings, you can extend EptSettingsDefaultWidget class and create own field widget. Here is example how to make EPT Settings small as possible.

...
    unset($element['ept_settings']['design_options']['other_settings']['background_color']);
    unset($element['ept_settings']['design_options']['other_settings']['background_media']);
    unset($element['ept_settings']['design_options']['other_settings']['background_image_style']);
...

Our form is already have only two settings:

Only two fields
Only two fields

It's remaining only to add Spacing field for adding margin to the bottom. We will use additional classes and CSS to organize spacings:

spacing-none
spacing-sm
spacing-md
spacing-lg
spacing-xl
spacing-xxl 

Maybe you will need for larger list of spacing, feel free to extend EptSettingsSimpleWidget class and create own field widget class from it as we did with EptSettingsDefaultWidget class.

$element['ept_settings']['design_options']['other_settings']['spacing'] = [
      '#type' => 'select',
      '#title' => $this->t('Background Image Style'),
      '#options' => [
        'spacing-none' => $this->t('None'),
        'spacing-sm' => $this->t('Small'),
        'spacing-md' => $this->t('Medium'),
        'spacing-lg' => $this->t('Large'),
        'spacing-xl' => $this->t('Extra Large'),
        'spacing-xxl' => $this->t('Double Extra Large'),
      ],
      '#default_value' => $items[$delta]->ept_settings['design_options']['other_settings']['spacing'] ?? 'spacing-none',
    ];

Now I see three ways to add styles for our block:

1. Override block template and set spacing there as block class.

2. Generate styles on fly and include them as custom CSS styles for each paragraph.

3. Add class with javascript by generating custom javascript for each EPT paragraph.

4. Override list of classes in template_preprocess_block() function.

All of this approaches will work, but I think it will be easier to use template_process_paragraph() function. At least we already have ept_core_preprocess_block() function in ebt_core.module file. Let's use it:

...
  if (!empty($ept_settings[0]['ept_settings']['design_options']['other_settings']['spacing'])) {
    $variables['attributes']['class'][] = $ept_settings[0]['ept_settings']['design_options']['other_settings']['spacing'];
  }
...
Medium spacing
Medium spacing
Spacing class
Spacing class

Now we pass Spacing field keys as class names and we will use CSS to define value for margins based on these classes:

/ebt_core/scss/ept_core.scss

.spacing-sm {
  margin-bottom: 10px;
}

.spacing-md {
  margin-bottom: 20px;
}

.spacing-lg {
  margin-bottom: 30px;
}

.spacing-xl {
  margin-bottom: 40px;
}

.spacing-xxl {
  margin-bottom: 50px;
}

You can override values in your custom CSS file, for example using any class from content or body tag:

body .spacing-sm {
  margin-bottom: 15px;
}

And you can override list of spacings in your custom class for EBT settings field widget.

That's it, now you can choose between DOM Box and plain select box for setting margins for your EBT blocks.

Feel free to ask about EBT modules on Drupal.org or contact form:

Contact

Create an issue on Drupal.org

Keep in touch on LinkedIn