0

I am creating a computed field price_range from a price field on a content type.

I have used the following code.

/**
 * Implements hook_entity_base_field_info().
 *
 * Adds price range computed field to the node entity type.
 */
function paddle_core_entity_base_field_info(EntityTypeInterface $entity_type) {
  if ($entity_type->id() === 'node') {
    $fields = [];

    $fields['price_range'] = BaseFieldDefinition::create('price_range_list')
      ->setName('price_range')
      ->setLabel(t('Price range'))
      ->setComputed(TRUE)
      ->setClass('\Drupal\mymodule\PriceRangeList')
      ->setDisplayConfigurable('view', TRUE)
      ->setDisplayOptions('view', [
        'label' => 'hidden',
        'weight' => -5,
      ]);

    return $fields;
  }
}

and then a class in mymodule\src\PriceRangeList

namespace Drupal\mymodule;

use Drupal\Core\Field\FieldItemList;
use Drupal\Core\TypedData\ComputedItemListTrait;

/**
 * Class PriceRangeList.
 *
 * Displays the price range computed field.
 */
class PriceRangeList extends FieldItemList {

  use ComputedItemListTrait;

  /**
   * {@inheritdoc}
   */
  protected function computeValue() {
    if (!isset($this->list[0])) {
      $this->list[0] = $this->createItem(0);
    }
  }

}

and then there is a 2nd class in mymodule\src\Plugin\Field\FieldType\PriceRangeListItem

namespace Drupal\mymodule\Plugin\Field\FieldType;

use Drupal\Core\Field\FieldItemList;
use Drupal\options\Plugin\Field\FieldType\ListStringItem;
use Drupal\link\Plugin\Field\FieldType\LinkItem;

/**
 * Variant of the 'link' field that links to the current company.
 *
 * @FieldType(
 *   id = "price_range_list",
 *   label = @Translation("Price range"),
 *   description = @Translation("Price range list that is associated with the entity."),
 *   default_widget = "options_select",
 *   default_formatter = "list_default",
 * )
 */
class PriceRangeListItem extends ListStringItem {

  /**
   * Whether or not the value has been calculated.
   *
   * @var bool
   */
  protected $isCalculated = FALSE;

  /**
   * {@inheritdoc}
   */
  public function __get($name) {
    $this->ensureCalculated();
    return parent::__get($name);
  }

  /**
   * {@inheritdoc}
   */
  public function isEmpty() {
    $this->ensureCalculated();
    return parent::isEmpty();
  }

  /**
   * {@inheritdoc}
   */
  public function getValue() {
    $this->ensureCalculated();
    return parent::getValue();
  }

  /**
   * Calculates the value of the field and sets it.
   */
  protected function ensureCalculated() {
    if (!$this->isCalculated) {
      $entity = $this->getEntity();

      if (!$entity->isNew() && !$entity->get('price')->isEmpty()) {
        // Some custom code that retrieves the current company.
        $price = $entity->get('price')->getString();
        $price_range = $this->getPriceRangeValue($price);

        if (!empty($price_range)) {
          $value = [
            $price_range['key'] => $price_range['value'],
          ];
          $this->setValue($value);
        }
      }
      $this->isCalculated = TRUE;
    }
  }

  protected function getPriceRangeValue($price) {
    $price_ranges = [
      '0_20' => $this->t('0 - 20 euro'),
      '20_50' => $this->t('20 - 50 euro'),
      '50_100' => $this->t('50 - 100 euro'),
      '100_500' => $this->t('100 - 500 euro'),
      '500' => $this->t('> 500 euro'),
    ];

    $price_range = [];

    foreach ($price_ranges as $range => $value) {
      $explode = explode('_', $range);

      if (!empty($explode)) {
        if (empty($explode[1]) && $price > $explode[0]) {
          $price_range = ['key' => $range, 'value' => $value];
          break;
        }

        if ($price > $explode[0] && $price <= $explode[1]) {
          $price_range = ['key' => $range, 'value' => $value];
          break;
        }
      }
    }

    return $price_range;
  }

}

But my field is not calculated. I can confirm this part is executed.

if (!empty($price_range)) {
              $value = [
                $price_range['key'] => $price_range['value'],
              ];
              $this->setValue($value);
            }

But the value is not setting for the price range field.

I am following this documentation.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.