FieldTypePluginManager.php 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. <?php
  2. namespace Drupal\Core\Field;
  3. use Drupal\Component\Plugin\Factory\DefaultFactory;
  4. use Drupal\Core\Cache\CacheBackendInterface;
  5. use Drupal\Core\Entity\FieldableEntityInterface;
  6. use Drupal\Core\Extension\ModuleHandlerInterface;
  7. use Drupal\Core\Plugin\CategorizingPluginManagerTrait;
  8. use Drupal\Core\Plugin\DefaultPluginManager;
  9. use Drupal\Core\TypedData\TypedDataManagerInterface;
  10. /**
  11. * Plugin manager for 'field type' plugins.
  12. *
  13. * @ingroup field_types
  14. */
  15. class FieldTypePluginManager extends DefaultPluginManager implements FieldTypePluginManagerInterface {
  16. use CategorizingPluginManagerTrait;
  17. /**
  18. * The typed data manager.
  19. *
  20. * @var \Drupal\Core\TypedData\TypedDataManagerInterface
  21. */
  22. protected $typedDataManager;
  23. /**
  24. * Constructs the FieldTypePluginManager object
  25. *
  26. * @param \Traversable $namespaces
  27. * An object that implements \Traversable which contains the root paths
  28. * keyed by the corresponding namespace to look for plugin implementations.
  29. * @param \Drupal\Core\Cache\CacheBackendInterface $cache_backend
  30. * Cache backend instance to use.
  31. * @param \Drupal\Core\Extension\ModuleHandlerInterface $module_handler
  32. * The module handler.
  33. * @param \Drupal\Core\TypedData\TypedDataManagerInterface $typed_data_manager
  34. * The typed data manager.
  35. */
  36. public function __construct(\Traversable $namespaces, CacheBackendInterface $cache_backend, ModuleHandlerInterface $module_handler, TypedDataManagerInterface $typed_data_manager) {
  37. parent::__construct('Plugin/Field/FieldType', $namespaces, $module_handler, 'Drupal\Core\Field\FieldItemInterface', 'Drupal\Core\Field\Annotation\FieldType');
  38. $this->alterInfo('field_info');
  39. $this->setCacheBackend($cache_backend, 'field_types_plugins');
  40. $this->typedDataManager = $typed_data_manager;
  41. }
  42. /**
  43. * {@inheritdoc}
  44. *
  45. * Creates a field item, which is not part of an entity or field item list.
  46. *
  47. * @param string $field_type
  48. * The field type, for which a field item should be created.
  49. * @param array $configuration
  50. * The plugin configuration array, i.e. an array with the following keys:
  51. * - field_definition: The field definition object, i.e. an instance of
  52. * Drupal\Core\Field\FieldDefinitionInterface.
  53. *
  54. * @return \Drupal\Core\Field\FieldItemInterface
  55. * The instantiated object.
  56. */
  57. public function createInstance($field_type, array $configuration = []) {
  58. $configuration['data_definition'] = $configuration['field_definition']->getItemDefinition();
  59. return $this->typedDataManager->createInstance("field_item:$field_type", $configuration);
  60. }
  61. /**
  62. * {@inheritdoc}
  63. */
  64. public function createFieldItemList(FieldableEntityInterface $entity, $field_name, $values = NULL) {
  65. // Leverage prototyping of the Typed Data API for fast instantiation.
  66. return $this->typedDataManager->getPropertyInstance($entity->getTypedData(), $field_name, $values);
  67. }
  68. /**
  69. * {@inheritdoc}
  70. */
  71. public function createFieldItem(FieldItemListInterface $items, $index, $values = NULL) {
  72. // Leverage prototyping of the Typed Data API for fast instantiation.
  73. return $this->typedDataManager->getPropertyInstance($items, $index, $values);
  74. }
  75. /**
  76. * {@inheritdoc}
  77. */
  78. public function processDefinition(&$definition, $plugin_id) {
  79. parent::processDefinition($definition, $plugin_id);
  80. if (!isset($definition['list_class'])) {
  81. $definition['list_class'] = '\Drupal\Core\Field\FieldItemList';
  82. }
  83. // Ensure that every field type has a category.
  84. if (empty($definition['category'])) {
  85. $definition['category'] = $this->t('General');
  86. }
  87. }
  88. /**
  89. * {@inheritdoc}
  90. */
  91. public function getDefaultStorageSettings($type) {
  92. $plugin_definition = $this->getDefinition($type, FALSE);
  93. if (!empty($plugin_definition['class'])) {
  94. $plugin_class = DefaultFactory::getPluginClass($type, $plugin_definition);
  95. return $plugin_class::defaultStorageSettings();
  96. }
  97. return [];
  98. }
  99. /**
  100. * {@inheritdoc}
  101. */
  102. public function getDefaultFieldSettings($type) {
  103. $plugin_definition = $this->getDefinition($type, FALSE);
  104. if (!empty($plugin_definition['class'])) {
  105. $plugin_class = DefaultFactory::getPluginClass($type, $plugin_definition);
  106. return $plugin_class::defaultFieldSettings();
  107. }
  108. return [];
  109. }
  110. /**
  111. * {@inheritdoc}
  112. */
  113. public function getUiDefinitions() {
  114. $definitions = $this->getDefinitions();
  115. // Filter out definitions that can not be configured in Field UI.
  116. $definitions = array_filter($definitions, function ($definition) {
  117. return empty($definition['no_ui']);
  118. });
  119. // Add preconfigured definitions.
  120. foreach ($definitions as $id => $definition) {
  121. if (is_subclass_of($definition['class'], '\Drupal\Core\Field\PreconfiguredFieldUiOptionsInterface')) {
  122. foreach ($this->getPreconfiguredOptions($definition['id']) as $key => $option) {
  123. $definitions['field_ui:' . $id . ':' . $key] = [
  124. 'label' => $option['label'],
  125. ] + $definition;
  126. if (isset($option['category'])) {
  127. $definitions['field_ui:' . $id . ':' . $key]['category'] = $option['category'];
  128. }
  129. }
  130. }
  131. }
  132. return $definitions;
  133. }
  134. /**
  135. * {@inheritdoc}
  136. */
  137. public function getPreconfiguredOptions($field_type) {
  138. $options = [];
  139. $class = $this->getPluginClass($field_type);
  140. if (is_subclass_of($class, '\Drupal\Core\Field\PreconfiguredFieldUiOptionsInterface')) {
  141. $options = $class::getPreconfiguredOptions();
  142. $this->moduleHandler->alter('field_ui_preconfigured_options', $options, $field_type);
  143. }
  144. return $options;
  145. }
  146. /**
  147. * {@inheritdoc}
  148. */
  149. public function getPluginClass($type) {
  150. $plugin_definition = $this->getDefinition($type, FALSE);
  151. return $plugin_definition['class'];
  152. }
  153. }