Skip to content

Create custom Form field

You can extend the Form Builder by adding new Form fields or modifying existing ones. Define new form fields in configuration.

Configure Form field

For example, to create a Country Form field in the "Custom form fields" category, provide the following configuration under the ibexa_form_builder.fields configuration key:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
ibexa_form_builder:
    fields:
        country:
            name: Country
            category: Custom form fields
            thumbnail: '/bundles/ibexaplatformicons/img/all-icons.svg#places'
            attributes:
                label:
                    name: Display label
                    type: string
                    validators:
                        not_blank:
                            message: You must provide a label for the field
                help:
                    name: Help text
                    type: string
            validators:
                required: ~

Available attribute types are:

Type Description
string String
text Text block
integer Integer number
url URL
multiple Multiple choice
select Dropdown
checkbox Checkbox
location Content location
radio Radio button
action Button
choices List of available options

Each type of Form field can have validators of the following types:

  • required
  • min_length
  • max_length
  • min_choices
  • max_choices
  • min_value
  • max_value
  • regex
  • upload_size
  • extensions

Create mapper

New types of fields require a mapper which implements the Ibexa\Contracts\FormBuilder\FieldType\Field\FieldMapperInterface interface.

To create a Country field type, implement the FieldMapperInterface interface in src/FormBuilder/Field/Mapper/CountryFieldMapper.php:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
<?php declare(strict_types=1);

namespace App\FormBuilder\Field\Mapper;

use Ibexa\Contracts\FormBuilder\FieldType\Model\Field;
use Ibexa\FormBuilder\FieldType\Field\Mapper\GenericFieldMapper;

class CountryFieldMapper extends GenericFieldMapper
{
    protected function mapFormOptions(Field $field, array $constraints): array
    {
        $options = parent::mapFormOptions($field, $constraints);
        $options['label'] = $field->getAttributeValue('label');
        $options['help'] = $field->getAttributeValue('help');

        return $options;
    }
}

Then, register the mapper as a service:

1
2
3
4
5
6
7
services:
    App\FormBuilder\Field\Mapper\CountryFieldMapper:
        arguments:
            $fieldIdentifier: country
            $formType: Symfony\Component\Form\Extension\Core\Type\CountryType
        tags:
            - { name: ibexa.form_builder.field.mapper }

Now you can go to back office and build a new form. You should be able to see the new section in the list of available fields:

Custom form fields

And a new Country Form field:

Country field

Modify existing Form fields

Field or field attribute definition can be modified by subscribing to one of the following events:

  • ibexa.form_builder.field.<FIELD_ID>
  • ibexa.form_builder.field.<FIELD_ID>.<ATTRIBUTE_ID>

The following example adds a custom string attribute to single_line field definition.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<?php declare(strict_types=1);

namespace App\EventSubscriber;

use Ibexa\FormBuilder\Definition\FieldAttributeDefinitionBuilder;
use Ibexa\FormBuilder\Event\FieldDefinitionEvent;
use Ibexa\FormBuilder\Event\FormEvents;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;

class FormFieldDefinitionSubscriber implements EventSubscriberInterface
{
    public static function getSubscribedEvents(): array
    {
        return [
            FormEvents::getFieldDefinitionEventName('single_line') => 'onSingleLineFieldDefinition',
        ];
    }

    public function onSingleLineFieldDefinition(FieldDefinitionEvent $event): void
    {
        $isReadOnlyAttribute = new FieldAttributeDefinitionBuilder();
        $isReadOnlyAttribute->setIdentifier('custom');
        $isReadOnlyAttribute->setName('Custom attribute');
        $isReadOnlyAttribute->setType('string');

        $definitionBuilder = $event->getDefinitionBuilder();
        $definitionBuilder->addAttribute($isReadOnlyAttribute->buildDefinition());
    }
}

Register this subscriber as a service:

1
2
3
4
5
services:
    App\EventSubscriber\FormFieldDefinitionSubscriber:
        public: true
        tags:
            - kernel.event_subscriber

Access Form field definitions

Field definitions are accessible through:

  • Ibexa\FormBuilder\Definition\FieldDefinitionFactory in the back end
  • global variable ibexa.formBuilder.config.fieldsConfig in the front end