0

I'm trying to create a custom FieldType. I've found many example with a textfield. But I want a custom field with checkboxes. I'm having a hard time finding an example like that.

If anyone can help me out, it would be greatly appreciated.

I have the field made, correct options showing up. I'm currently stuck with the incorrect primitive type. I'm not sure how to set this up properly.

edit page

Here's my code for the FieldType, FieldWidget and config.

<?php

namespace Drupal\field_active_bundles\Plugin\Field\FieldType;

use Drupal\Core\Field\FieldItemBase;
use Drupal\Core\Field\FieldStorageDefinitionInterface;
use Drupal\Core\TypedData\DataDefinition;

/**
 * Plugin implementation of the 'field_active_bundles' field type.
 *
 * @FieldType(
 *   id = "field_active_bundles",
 *   label = @Translation("Active Bundles"),
 *   module = "field_active_bundles",
 *   category = "Custom",
 *   description = @Translation("Selects active bundles for component."),
 *   default_widget = "field_active_bundles_widget",
 *   default_formatter = "field_active_bundles_formatter"
 * )
 */
class ActiveBundles extends FieldItemBase {

  /**
   * {@inheritdoc}
   */
  public static function schema(FieldStorageDefinitionInterface $field_definition) {
    return [
      'columns' => [
        'value' => [
          'type' => 'text',
          'size' => 'tiny',
          'not null' => FALSE,
        ],
      ],
    ];
  }

  /**
   * {@inheritdoc}
   */
  public function isEmpty() {
    $value = $this->get('value')->getValue();
    return $value === NULL || $value === '';
  }

  /**
   * {@inheritdoc}
   */
  public static function propertyDefinitions(FieldStorageDefinitionInterface $field_definition) {
    $properties['value'] = DataDefinition::create('string')->setLabel(t('What ever'));
    return $properties;
  }

}
<?php

namespace Drupal\field_active_bundles\Plugin\Field\FieldWidget;

use Drupal\Core\Field\FieldItemListInterface;
use Drupal\Core\Field\WidgetBase;
use Drupal\Core\Form\FormStateInterface;

/**
 * Plugin implementation of the 'field_active_bundles' widget.
 *
 * @FieldWidget(
 *   id = "field_active_bundles_widget",
 *   module = "field_active_bundles",
 *   label = @Translation("Default checkboxes"),
 *   field_types = {
 *     "field_active_bundles"
 *   }
 * )
 */
class ActiveBundlesWidget extends WidgetBase {

  /**
   * {@inheritdoc}
   */
  public function formElement(FieldItemListInterface $items, $delta, array $element, array &$form, FormStateInterface $form_state) {
    $bundle_info = \Drupal::service('entity_type.bundle.info')->getBundleInfo('entity_product');

    foreach ($bundle_info as $key => $value) {
      $options[$key] = $value['label'];
    }

    $element['value'] = [
      '#type' => 'checkboxes',
      '#title' => 'Active Bundles',
      '#options' => $options,
      '#element_validate' => [
        [$this, 'validate'],
      ],
    ];

    if ($element['#required']) {
      $element[$key]['#required'] = TRUE;
    }

    return ['value' => $element];
  }

  /**
   * Validate the fields and convert them into a single value as text.
   */
  public function validate($element, FormStateInterface $form_state) {
    // TBD.
  }

}
# @see Configuration schema/metadata at https://drupal.org/node/1905070
field.field_active_bundles.value:
  type: sequence
  label: 'Default value'
  sequence:
    - type: mapping
      label: 'Default'
      mapping:
        value:
          type: string
          label: 'Value'

1 Answer 1

0

It seems the only custom requirement is providing dynamic checkboxes items. You could use the core field list type and provide the options in this callback:

mymodule.module

use Drupal\Core\Entity\ContentEntityInterface;
use Drupal\field\Entity\FieldStorageConfig;

function mymodule_allowed_values_function(FieldStorageConfig $definition, ContentEntityInterface $entity = NULL, $cacheable) {
  $options = [];
  $bundle_info = \Drupal::service('entity_type.bundle.info')->getBundleInfo('entity_product');
  foreach ($bundle_info as $key => $value) {
    $options[$key] = $value['label'];
  }
  return $options;
}

See How do I programmatically update the allowed values of a list field?

However, for this specific case there is a UI-only solution by adding a multi-value reference field for other entities and then specifying the config entity for the product bundles.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.