diff --git a/modules/entity_form/entity_browser_entity_form.module b/modules/entity_form/entity_browser_entity_form.module index 4243ade..7923680 100644 --- a/modules/entity_form/entity_browser_entity_form.module +++ b/modules/entity_form/entity_browser_entity_form.module @@ -12,6 +12,7 @@ use Drupal\Core\Field\FieldDefinitionInterface; use Drupal\Core\Field\WidgetInterface; use Drupal\Core\Url; use Drupal\Component\Utility\NestedArray; +use Drupal\entity_browser\Element\EntityBrowserElement; /** * Implements hook_inline_entity_form_reference_form_alter(). @@ -32,18 +33,15 @@ function entity_browser_entity_form_inline_entity_form_reference_form_alter(&$re $widget = $form_display->getRenderer($instance->getName()); - if (empty($widget->getThirdPartySetting('entity_browser_entity_form', 'entity_browser_id'))) { - return; - } - - if ($widget->getThirdPartySetting('entity_browser_entity_form', 'entity_browser_id') === '_none') { + $entity_browser_id = $widget->getThirdPartySetting('entity_browser_entity_form', 'entity_browser_id', '_none'); + if ($entity_browser_id === '_none') { return; } unset($reference_form['entity_id']); $reference_form['entity_browser'] = [ '#type' => 'entity_browser', - '#entity_browser' => $widget->getThirdPartySetting('entity_browser_entity_form', 'entity_browser_id'), + '#entity_browser' => $entity_browser_id, ]; $reference_form['#attached']['library'][] = 'entity_browser_entity_form/ief_autocomplete'; $reference_form['actions']['ief_reference_save']['#ajax']['event'] = 'entities-selected'; @@ -75,15 +73,7 @@ function entity_browser_entity_form_reference_form_validate(array &$reference_fo } $ief_id = $reference_form['#ief_id']; $labels = $reference_form['#ief_labels']; - $storage = \Drupal::entityTypeManager()->getStorage($reference_form['#entity_type']); - $attach_entities = $storage->loadMultiple( - array_map( - function ($item) { - return explode(':', $item)[1]; - }, - explode(' ', $form_values['entity_browser']['entity_ids']) - ) - ); + $attach_entities = EntityBrowserElement::processEntityIds($form_values['entity_browser']['entity_ids']); // Check if the entity is already referenced by the field. if (!empty($attach_entities)) { @@ -114,15 +104,7 @@ function entity_browser_entity_form_reference_form_validate(array &$reference_fo function entity_browser_entity_form_reference_form_submit($reference_form, FormStateInterface $form_state) { $ief_id = $reference_form['#ief_id']; $form_values = NestedArray::getValue($form_state->getValues(), $reference_form['#parents']); - $storage = \Drupal::entityTypeManager()->getStorage($reference_form['#entity_type']); - $attach_entities = $storage->loadMultiple( - array_map( - function ($item) { - return explode(':', $item)[1]; - }, - explode(' ', $form_values['entity_browser']['entity_ids']) - ) - ); + $attach_entities = EntityBrowserElement::processEntityIds($form_values['entity_browser']['entity_ids']); $entities =& $form_state->get(['inline_entity_form', $ief_id, 'entities']); // Determine the correct weight of the new element. diff --git a/src/DisplayBase.php b/src/DisplayBase.php index 3b4ebff..be44fc5 100644 --- a/src/DisplayBase.php +++ b/src/DisplayBase.php @@ -156,7 +156,7 @@ abstract class DisplayBase extends PluginBase implements DisplayInterface, Conta /** * {@inheritdoc} */ - public function displayEntityBrowser(FormStateInterface $form_state, array $element, array &$complete_form, array $persistent_data = []) { + public function displayEntityBrowser(array $element, FormStateInterface $form_state, array &$complete_form, array $persistent_data = []) { // Store persistent data so that after being rendered widgets can still // have access to contextual information. $this->selectionStorage->setWithExpire( diff --git a/src/DisplayInterface.php b/src/DisplayInterface.php index f3c0ca9..4d9fbf2 100644 --- a/src/DisplayInterface.php +++ b/src/DisplayInterface.php @@ -34,12 +34,12 @@ interface DisplayInterface extends PluginInspectionInterface, ConfigurablePlugin * with it. It will take care about displaying entity browser in one way or * another. * - * @param \Drupal\Core\Form\FormStateInterface $form_state - * The form state object. * @param array $element * A form element array containing basic properties for the entity browser * element: * - #eb_parents: The 'parents' space for the field in the form. + * @param \Drupal\Core\Form\FormStateInterface $form_state + * The form state object. * @param array $complete_form * The form structure where entity browser is being attached to. * @param array $persistent_data @@ -57,7 +57,7 @@ interface DisplayInterface extends PluginInspectionInterface, ConfigurablePlugin * @return array * An array suitable for drupal_render(). */ - public function displayEntityBrowser(FormStateInterface $form_state, array $element, array &$complete_form, array $persistent_data = []); + public function displayEntityBrowser(array $element, FormStateInterface $form_state, array &$complete_form, array $persistent_data = []); /** * Indicates completed selection. diff --git a/src/Element/EntityBrowserElement.php b/src/Element/EntityBrowserElement.php index d5dc662..5448e22 100644 --- a/src/Element/EntityBrowserElement.php +++ b/src/Element/EntityBrowserElement.php @@ -79,8 +79,8 @@ class EntityBrowserElement extends FormElement { '#eb_parents' => array_merge($element['#parents'], ['entity_browser']), ]; $element['entity_browser'] = $display->displayEntityBrowser( - $form_state, $element['entity_browser'], + $form_state, $complete_form, ['validators' => $validators, 'selected_entities' => $element['#default_value']] ); @@ -112,19 +112,52 @@ class EntityBrowserElement extends FormElement { return $element['#default_value'] ?: []; } + $entities = []; if ($input['entity_ids']) { - return [ - 'entities' => array_map( - function ($item) { - list($entity_type, $entity_id) = explode(':', $item); - return \Drupal::entityTypeManager()->getStorage($entity_type)->load($entity_id); - }, - explode(' ', $input['entity_ids']) - ), - ]; + $entities = static::processEntityIds($input['entity_ids']); + } + + return ['entities' => $entities]; + } + + /** + * Processes entity IDs and gets array of loaded entities. + * + * @param array|string $ids + * Processes entity IDs as they are returned from the entity browser. They + * are in [entity_type_id]:[entity_id] form. Array of IDs or a + * space-delimited string is supported. + * + * @return \Drupal\Core\Entity\EntityInterface[] + * Array of entity objects. + */ + public static function processEntityIds($ids) { + if (!is_array($ids)) { + $ids = array_filter(explode(' ', $ids)); } - return ['entities' => []]; + return array_map( + function ($item) { + list($entity_type, $entity_id) = explode(':', $item); + return \Drupal::entityTypeManager()->getStorage($entity_type)->load($entity_id); + }, + $ids + ); + } + + /** + * Processes entity IDs and gets array of loaded entities. + * + * @param string $id + * Processes entity ID as it is returned from the entity browser. ID should + * be in [entity_type_id]:[entity_id] form. + * + * @return \Drupal\Core\Entity\EntityInterface + * Entity object. + */ + public static function processEntityId($id) { + $return = static::processEntityIds([$id]); + return current($return); } } diff --git a/src/Plugin/EntityBrowser/Display/IFrame.php b/src/Plugin/EntityBrowser/Display/IFrame.php index c60ddb5..9acfec3 100644 --- a/src/Plugin/EntityBrowser/Display/IFrame.php +++ b/src/Plugin/EntityBrowser/Display/IFrame.php @@ -115,8 +115,8 @@ class IFrame extends DisplayBase implements DisplayRouterInterface { /** * {@inheritdoc} */ - public function displayEntityBrowser(FormStateInterface $form_state, array $element, array &$complete_form, array $persistent_data = []) { - parent::displayEntityBrowser($form_state, $element, $complete_form, $persistent_data); + public function displayEntityBrowser(array $element, FormStateInterface $form_state, array &$complete_form, array $persistent_data = []) { + parent::displayEntityBrowser($element, $form_state, $complete_form, $persistent_data); /** @var \Drupal\entity_browser\Events\RegisterJSCallbacks $event */ $js_event_object = new RegisterJSCallbacks($this->configuration['entity_browser_id'], $this->getUuid()); $js_event_object->registerCallback('Drupal.entityBrowser.selectionCompleted'); diff --git a/src/Plugin/EntityBrowser/Display/Modal.php b/src/Plugin/EntityBrowser/Display/Modal.php index 2705979..0ea6cb6 100644 --- a/src/Plugin/EntityBrowser/Display/Modal.php +++ b/src/Plugin/EntityBrowser/Display/Modal.php @@ -119,8 +119,8 @@ class Modal extends DisplayBase implements DisplayRouterInterface { /** * {@inheritdoc} */ - public function displayEntityBrowser(FormStateInterface $form_state, array $element, array &$complete_form, array $persistent_data = []) { - parent::displayEntityBrowser($form_state, $element, $complete_form, $persistent_data); + public function displayEntityBrowser(array $element, FormStateInterface $form_state, array &$complete_form, array $persistent_data = []) { + parent::displayEntityBrowser($element, $form_state, $complete_form, $persistent_data); $js_event_object = new RegisterJSCallbacks($this->configuration['entity_browser_id'], $this->getUuid()); $js_event_object->registerCallback('Drupal.entityBrowser.selectionCompleted'); $js_event = $this->eventDispatcher->dispatch(Events::REGISTER_JS_CALLBACKS, $js_event_object); diff --git a/src/Plugin/EntityBrowser/Display/Standalone.php b/src/Plugin/EntityBrowser/Display/Standalone.php index 60b03aa..4e4e474 100644 --- a/src/Plugin/EntityBrowser/Display/Standalone.php +++ b/src/Plugin/EntityBrowser/Display/Standalone.php @@ -45,8 +45,8 @@ class Standalone extends DisplayBase implements DisplayRouterInterface { /** * {@inheritdoc} */ - public function displayEntityBrowser(FormStateInterface $form_state, array $element, array &$complete_form, array $persistent_data = []) { - parent::displayEntityBrowser($form_state, $element, $complete_form, $persistent_data); + public function displayEntityBrowser(array $element, FormStateInterface $form_state, array &$complete_form, array $persistent_data = []) { + parent::displayEntityBrowser($element, $form_state, $complete_form, $persistent_data); // @TODO Implement it. } diff --git a/src/Plugin/Field/FieldWidget/EntityReferenceBrowserWidget.php b/src/Plugin/Field/FieldWidget/EntityReferenceBrowserWidget.php index 6cf1ebb..3c0a7ba 100644 --- a/src/Plugin/Field/FieldWidget/EntityReferenceBrowserWidget.php +++ b/src/Plugin/Field/FieldWidget/EntityReferenceBrowserWidget.php @@ -3,6 +3,7 @@ namespace Drupal\entity_browser\Plugin\Field\FieldWidget; use Drupal\Core\Entity\EntityInterface; +use Drupal\entity_browser\Element\EntityBrowserElement; use Symfony\Component\Validator\ConstraintViolationInterface; use Drupal\Component\Utility\Html; use Drupal\Component\Utility\NestedArray; @@ -319,9 +320,7 @@ class EntityReferenceBrowserWidget extends WidgetBase implements ContainerFactor } if (isset($parents) && $value = $form_state->getValue($parents)) { - $ids = explode(' ', $value); - $ids = array_map(function ($item) {return explode(':', $item)[1];}, $ids); - $entities = $entity_storage->loadMultiple($ids); + $entities = EntityBrowserElement::processEntityIds($value); } } // IDs from a previous request might be saved in the form state. @@ -568,7 +567,6 @@ class EntityReferenceBrowserWidget extends WidgetBase implements ContainerFactor return [ 'validators' => [ 'entity_type' => ['type' => $this->fieldDefinition->getFieldStorageDefinition()->getSetting('target_type')], - 'cardinality' => ['cardinality' => $this->fieldDefinition->getFieldStorageDefinition()->getCardinality()], ], ]; } diff --git a/src/Plugin/Field/FieldWidget/FileBrowserWidget.php b/src/Plugin/Field/FieldWidget/FileBrowserWidget.php index 33ea13a..209a4f8 100644 --- a/src/Plugin/Field/FieldWidget/FileBrowserWidget.php +++ b/src/Plugin/Field/FieldWidget/FileBrowserWidget.php @@ -304,7 +304,7 @@ class FileBrowserWidget extends EntityReferenceBrowserWidget { $current[$entity_id] = [ '#attributes' => [ 'class' => ['draggable'], - 'data-entity-id' => $entity_id, + 'data-entity-id' => $entity->getEntityTypeId() . ':' . $entity_id, ], 'display' => $display, 'filename' => ['#markup' => $entity->label()], @@ -363,7 +363,7 @@ class FileBrowserWidget extends EntityReferenceBrowserWidget { '#submit' => [[get_class($this), 'removeItemSubmit']], '#name' => $field_machine_name . '_remove_' . $entity_id, '#limit_validation_errors' => [], - '#attributes' => ['data-entity-id' => $entity_id], + '#attributes' => ['data-entity-id' => $entity->getEntityTypeId() . ':' . $entity_id], '#access' => (bool) $widget_settings['field_widget_remove'], ], '_weight' => [ diff --git a/tests/modules/entity_browser_test/src/Form/FormElementTest.php b/tests/modules/entity_browser_test/src/Form/FormElementTest.php index a316237..66f61c8 100644 --- a/tests/modules/entity_browser_test/src/Form/FormElementTest.php +++ b/tests/modules/entity_browser_test/src/Form/FormElementTest.php @@ -5,6 +5,7 @@ namespace Drupal\entity_browser_test\Form; use Drupal\Core\Entity\EntityInterface; use Drupal\Core\Form\FormBase; use Drupal\Core\Form\FormStateInterface; +use Drupal\entity_browser\Element\EntityBrowserElement; /** * Provides a user login form. @@ -30,9 +31,7 @@ class FormElementTest extends FormBase { ]; if ($default = \Drupal::request()->get('default_entity')) { - list($entity_type, $entity_id) = explode(':', $default); - $entity = \Drupal::entityTypeManager()->getStorage($entity_type)->load($entity_id); - $form['fancy_entity_browser']['#default_value'] = [$entity]; + $form['fancy_entity_browser']['#default_value'] = [EntityBrowserElement::processEntityId($default)]; } $form['main_submit'] = [