get('entity.manager'),
$container->get('entity_type.bundle.info'),
$container->get('datetime.time'),
$container->get('element_info'),
$container->get('logger.factory')->get('entityqueue')
);
}
/**
* Constructs a EntitySubqueueForm.
*
* @param \Drupal\Core\Entity\EntityManagerInterface $entity_manager
* The entity manager.
* @param \Drupal\Core\Entity\EntityTypeBundleInfoInterface $entity_type_bundle_info
* The entity type bundle service.
* @param \Drupal\Component\Datetime\TimeInterface $time
* The time service.
* @param \Drupal\Core\Render\ElementInfoManagerInterface $element_info
* The element info manager.
* @param \Psr\Log\LoggerInterface $logger
* A logger instance.
*/
public function __construct(EntityManagerInterface $entity_manager, EntityTypeBundleInfoInterface $entity_type_bundle_info, TimeInterface $time, ElementInfoManagerInterface $element_info, LoggerInterface $logger) {
parent::__construct($entity_manager, $entity_type_bundle_info, $time);
$this->elementInfo = $element_info;
$this->logger = $logger;
}
/**
* {@inheritdoc}
*/
public function form(array $form, FormStateInterface $form_state) {
// Reverse the items in the admin form if the queue uses the 'Reverse order
// in admin view' option.
if ($this->entity->getQueue()->getReverseInAdmin()) {
$subqueue_items = $this->entity->get('items');
$items_values = $subqueue_items->getValue();
$subqueue_items->setValue(array_reverse($items_values));
}
$form = parent::form($form, $form_state);
$form['#title'] = $this->t('Edit subqueue %label', ['%label' => $this->entity->label()]);
// Since the form has ajax buttons, the $wrapper_id will change each time
// one of those buttons is clicked. Therefore the whole form has to be
// replaced, otherwise the buttons will have the old $wrapper_id and will
// only work on the first click.
if ($form_state->has('subqueue_form_wrapper_id')) {
$wrapper_id = $form_state->get('subqueue_form_wrapper_id');
}
else {
$wrapper_id = Html::getUniqueId($this->getFormId() . '-wrapper');
}
$form_state->set('subqueue_form_wrapper_id', $wrapper_id);
$form['#prefix'] = '
';
$form['#suffix'] = '
';
// @todo Use the 'Machine name' field widget when
// https://www.drupal.org/node/2685749 is committed.
$element_info = $this->elementInfo->getInfo('machine_name');
$form['name'] = [
'#type' => 'machine_name',
'#default_value' => $this->entity->id(),
'#source_field' => 'title',
'#process' => array_merge([[get_class($this), 'processMachineNameSource']], $element_info['#process']),
'#machine_name' => [
'exists' => '\Drupal\entityqueue\Entity\EntitySubqueue::load',
],
'#disabled' => !$this->entity->isNew(),
'#weight' => -5,
'#access' => !$this->entity->getQueue()->getHandlerPlugin()->hasAutomatedSubqueues(),
];
return $form;
}
/**
* Form API callback: Sets the 'source' property of a machine_name element.
*
* This method is assigned as a #process callback in formElement() method.
*/
public static function processMachineNameSource($element, FormStateInterface $form_state, $form) {
$source_field_state = WidgetBase::getWidgetState($form['#parents'], $element['#source_field'], $form_state);
// Hide the field widget if the source field is not configured properly or
// if it doesn't exist in the form.
if (empty($element['#source_field']) || empty($source_field_state['array_parents'])) {
$element['#access'] = FALSE;
}
else {
$source_field_element = NestedArray::getValue($form_state->getCompleteForm(), $source_field_state['array_parents']);
$element['#machine_name']['source'] = $source_field_element[0]['value']['#array_parents'];
}
return $element;
}
/**
* {@inheritdoc}
*/
protected function actions(array $form, FormStateInterface $form_state) {
$actions = parent::actions($form, $form_state);
$actions['reverse'] = [
'#type' => 'submit',
'#value' => $this->t('Reverse'),
'#submit' => ['::submitAction'],
'#op' => 'reverse',
'#ajax' => [
'callback' => '::subqueueActionAjaxForm',
'wrapper' => $form_state->get('subqueue_form_wrapper_id'),
],
];
$actions['shuffle'] = [
'#type' => 'submit',
'#value' => $this->t('Shuffle'),
'#submit' => ['::submitAction'],
'#op' => 'shuffle',
'#ajax' => [
'callback' => '::subqueueActionAjaxForm',
'wrapper' => $form_state->get('subqueue_form_wrapper_id'),
],
];
$actions['clear'] = [
'#type' => 'submit',
'#value' => $this->t('Clear'),
'#submit' => ['::submitAction'],
'#op' => 'clear',
'#ajax' => [
'callback' => '::subqueueActionAjaxForm',
'wrapper' => $form_state->get('subqueue_form_wrapper_id'),
],
];
return $actions;
}
/**
* Submit callback for the 'reverse', 'shuffle' and 'clear' actions.
*/
public static function submitAction(array &$form, FormStateInterface $form_state) {
$trigger = $form_state->getTriggeringElement();
$op = $trigger['#op'];
// Check if we have a form element for the 'items' field.
$path = array_merge($form['#parents'], ['items']);
$key_exists = NULL;
NestedArray::getValue($form_state->getValues(), $path, $key_exists);
if ($key_exists) {
// Remove any user input for the 'items' element in order to allow the
// values set below to be applied.
$user_input = $form_state->getUserInput();
NestedArray::setValue($user_input, $path, NULL);
$form_state->setUserInput($user_input);
$entity = $form_state->getFormObject()->getEntity();
$items_widget = $form_state->getFormObject()->getFormDisplay($form_state)->getRenderer('items');
$subqueue_items = $entity->get('items');
$items_widget->extractFormValues($subqueue_items, $form, $form_state);
$items_values = $subqueue_items->getValue();
// Revert the effect of the 'Reverse order in admin view' option.
if ($entity->getQueue()->getReverseInAdmin()) {
$items_values = array_reverse($items_values);
}
switch ($op) {
case 'reverse':
$subqueue_items->setValue(array_reverse($items_values));
break;
case 'shuffle':
shuffle($items_values);
$subqueue_items->setValue($items_values);
break;
case 'clear':
$subqueue_items->setValue(NULL);
break;
}
// Handle 'inline_entity_form' widgets separately because they have a
// custom form state storage for the current state of the referenced
// entities.
if (\Drupal::moduleHandler()->moduleExists('inline_entity_form') && $items_widget instanceof InlineEntityFormBase) {
$items_form_element = NestedArray::getValue($form, $path);
$ief_id = $items_form_element['widget']['#ief_id'];
$entities = $form_state->get(['inline_entity_form', $ief_id, 'entities']);
if (isset($entities)) {
$form_state->set(['inline_entity_form', $ief_id, 'entities'], []);
switch ($op) {
case 'reverse':
$entities = array_reverse($entities);
break;
case 'shuffle':
shuffle($entities);
break;
case 'clear':
$entities = [];
break;
}
foreach ($entities as $delta => $item) {
$item['_weight'] = $delta;
$form_state->set(['inline_entity_form', $ief_id, 'entities', $delta], $item);
}
}
}
$form_state->getFormObject()->setEntity($entity);
$form_state->setRebuild();
}
}
/**
* AJAX callback; Returns the entire form element.
*/
public static function subqueueActionAjaxForm(array &$form, FormStateInterface $form_state) {
return $form;
}
/**
* {@inheritdoc}
*/
public function save(array $form, FormStateInterface $form_state) {
$subqueue = $this->entity;
// Revert the effect of the 'Reverse order in admin view' option.
if ($subqueue->getQueue()->getReverseInAdmin()) {
$subqueue_items = $subqueue->get('items');
$items_values = $subqueue_items->getValue();
$subqueue_items->setValue(array_reverse($items_values));
}
$status = $subqueue->save();
$edit_link = $subqueue->toLink($this->t('Edit'), 'edit-form')->toString();
if ($status == SAVED_UPDATED) {
drupal_set_message($this->t('The entity subqueue %label has been updated.', ['%label' => $subqueue->label()]));
$this->logger->notice('The entity subqueue %label has been updated.', ['%label' => $subqueue->label(), 'link' => $edit_link]);
}
else {
drupal_set_message($this->t('The entity subqueue %label has been added.', ['%label' => $subqueue->label()]));
$this->logger->notice('The entity subqueue %label has been added.', ['%label' => $subqueue->label(), 'link' => $edit_link]);
}
$queue = $subqueue->getQueue();
if ($queue->getHandlerPlugin()->supportsMultipleSubqueues()) {
$form_state->setRedirectUrl($queue->toUrl('subqueue-list'));
}
else {
$form_state->setRedirectUrl($queue->toUrl('collection'));
}
}
}