In this tuto, I'll show you how to add custom data on configuration menu entity using the ThirdPartySettingsInterface .
By default configuration menu entity fields is like this:
In this article we are going to look at how to use the ThirdPartySettingsInterface to add some extra fields to existing configuration menu entity. For example, if you ever need to store some config together with a node type or a taxonomy vocabulary, there is a great way to do so using this interface.
Today we are going to see an example of this and add an extra fields to the menu definition and store the value in this way.
There are a number of steps involved in this process. First, we need to alter the form with which the entity configuration data is added and saved. In the case of the menu entity there are two forms (one for adding and one for editing) so we need to alter them both.
I added a new #entity_builder
to the form which will be triggered when the form is submitted.
Create mymodule.module file:
<?php
use Drupal\Core\Form\FormStateInterface;
use Drupal\system\Entity\Menu;
/**
* override hook_form_alter().
*/
function mymodule_form_alter(&$form, FormStateInterface $form_state, $form_id)
{
if ($form_id === 'menu_add_form' || $form_id === 'menu_edit_form') {
// get menu configuration entity
$menu = $form_state->getFormObject()->getEntity();
// add custom field textfield
$form['my_custom_field'] = array(
'#type' => 'textfield',
'#title' => t('My Custom field'),
'#description' => t('This is custom extra field'),
'#default_value' => $menu->getThirdPartySetting('mymodule', 'my_custom_field'),
'#weight' => 1
);
// add custom field text_format
$form['my_custom_description'] = array(
'#type' => 'text_format',
'#title' => t('Description'),
'#default_value' => $menu->getThirdPartySetting('mymodule', 'my_custom_description'),
'#format' => 'full_html',
'#weight' => 2
);
// change links field weight to become after my fields
if (isset($form['links'])) {
$form['links']['#weight'] = 3;
}
// Entity builder for the menu configuration entity.
$form['#entity_builders'][] = '_mymodule_form_menu_add_form_builder';
}
}
/**
* @param $entity_type
* @param Menu $menu
* @param $form
* @param FormStateInterface $form_state
*/
function _mymodule_form_menu_add_form_builder($entity_type, Menu $menu, &$form, FormStateInterface $form_state)
{
if ($form_state->getValue('my_custom_field')) {
// save my_text_field value in Third Party Setting
$menu->setThirdPartySetting('mymodule', 'my_custom_field', $form_state->getValue('my_custom_field'));
} else {
// remove my_text_field value from Third Party Setting
$menu->unsetThirdPartySetting('mymodule', 'my_custom_field');
}
if ($form_state->getValue('my_custom_description')) {
// save my_custom_description value in Third Party Setting
$menu->setThirdPartySetting('mymodule', 'my_custom_description', $form_state->getValue('my_custom_description')['value']);
} else {
// remove my_custom_description value from Third Party Setting
$menu->unsetThirdPartySetting('mymodule', 'my_custom_description');
}
}
The getThirdPartySetting()
method on the entity object is provided by the ThirdPartySettingsInterface
which all configuration entities have by default if they extend from the ConfigEntityBase
class. with this method we simply retrieve a value that is stored as third party settings.
We need also to add our configuration schema so that it becomes translatable. Inside the /config/schema/mymodule.schema.yml
file of our module we need to add this:
config/schema/mymodule.schema.yml
system.menu.*.third_party.mymodule:
type: mapping
label: 'My custom fields'
mapping:
my_custom_field:
type: text
label: 'My Custom Field'
my_custom_description:
type: text_format
label: 'My Custom Description'
With this schema definition we are basically appending to the schema of the system.menu
config menu entity by specifying some metadata about the third party settings our module provides. For more information on config schemas be sure to check out the docs on Drupal.org.
After adding our custom fields to existing config menu entity the result is like this: