diff --git a/ajax_comments.module b/ajax_comments.module index ef0b67b..ed7382a 100644 --- a/ajax_comments.module +++ b/ajax_comments.module @@ -29,6 +29,53 @@ use Drupal\Core\Render\Element; use Drupal\Core\Routing\RouteMatch; use Symfony\Component\HttpFoundation\Request; +/** + * Implements hook_entity_view_mode_alter(). + */ +function ajax_comments_entity_view_mode_alter(&$view_mode, Drupal\Core\Entity\EntityInterface $entity, $context) { + if (!\Drupal::currentUser()->hasPermission('post comments')) { + return; + } + + /** @var \Drupal\ajax_comments\FieldSettingsHelper $field_settings_helper */ + $field_settings_helper = \Drupal::service('ajax_comments.field_settings_helper'); + + // We lookup through the node fields + // and check out that the attached file was provided. + $nodeFields = \Drupal::service('entity_field.manager')->getFieldDefinitions($entity->getEntityTypeId(), $entity->bundle()); + foreach ($nodeFields as $nodeField) { + if ($nodeField->getType() == 'comment') { + // Load the configuration entity for the entity's view display settings. + /** @var \Drupal\Core\Entity\Display\EntityDisplayInterface $view_display */ + $view_display = \Drupal::service('entity_type.manager') + ->getStorage('entity_view_display') + ->load($entity->getEntityTypeId() . '.' . $entity->bundle() . '.' . $view_mode); + + // if the view display is empty fall back to the default mode. + $acting_view_mode = $view_mode; + if (empty($view_display)) { + $acting_view_mode = 'default'; + $view_display = \Drupal::service('entity_type.manager') + ->getStorage('entity_view_display') + ->load($entity->getEntityTypeId() . '.' . $entity->bundle() . '.' . $acting_view_mode); + } + if (empty($view_display)) { + continue; + } + $comment_formatter = $field_settings_helper->getFieldFormatter($view_display, $nodeField->getName(), $nodeField, $acting_view_mode); + + if (!empty($comment_formatter) && $field_settings_helper->isEnabled($comment_formatter)) { + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + + $tempStore->setViewMode($entity->getEntityType()->getLabel()->getUntranslatedString(), $acting_view_mode); + } + } + } + +} + + /** * Implements hook_comment_links_alter(). * @@ -36,10 +83,13 @@ use Symfony\Component\HttpFoundation\Request; * classes to allow ajax behaviors to be attached. */ function ajax_comments_comment_links_alter(array &$links, CommentInterface &$entity, array &$context) { - $request = \Drupal::request(); + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($entity->getCommentedEntity()->getEntityType()->getLabel()->getUntranslatedString()); + /** @var \Drupal\ajax_comments\FieldSettingsHelper $field_settings_helper */ $field_settings_helper = \Drupal::service('ajax_comments.field_settings_helper'); - $comment_formatter = $field_settings_helper->getFieldFormatterFromComment($entity, $context['view_mode']); + $comment_formatter = $field_settings_helper->getFieldFormatterFromComment($entity, $view_mode); if (!empty($comment_formatter) && $field_settings_helper->isEnabled($comment_formatter)) { // A little HACK for do not mark as NEW own comments. @@ -196,6 +246,10 @@ function ajax_comments_entity_view_alter(array &$build, ContentEntityInterface $ $field_formatter = $field_settings_helper->getFieldFormatter($display, $machine_name, $field_config, $display->getMode()); if (!empty($field_formatter) && $field_settings_helper->isEnabled($field_formatter)) { $build['#attached']['library'][] = 'ajax_comments/commands'; + if (isset($build[$machine_name]['0']['comments'])) { + $elements = &$build[$machine_name]['0']['comments']; + Utility::addCommentClasses($elements); + } $commands_added = TRUE; break; @@ -228,9 +282,13 @@ function ajax_comments_form_comment_form_alter(&$form, \Drupal\Core\Form\FormSta $commented_entity = $comment->getCommentedEntity(); $field_name = $comment->getFieldName(); + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($commented_entity->getEntityType()->getLabel()->getUntranslatedString()); + // Check to see if this node type uses ajax comments. - $comment_formatter = $field_settings_helper->getFieldFormatterFromComment($comment, 'full'); - if (empty($comment_formatter) || !$field_settings_helper->isEnabled($comment_formatter)) { + $comment_formatter = $field_settings_helper->getFieldFormatterFromComment($comment, $view_mode); + if (!empty($comment_formatter) && !$field_settings_helper->isEnabled($comment_formatter)) { return; } @@ -303,29 +361,32 @@ function ajax_comments_preprocess_pager(&$variables) { // the pager. // Unfortunately there is no way to remove this parameter before it is rendered to text, // so this preprocess function removes the parameter with string replacement. + $items = []; // Remove ajax wrapper format from first, previous. if (isset($variables['items']['first'])) { - $variables['items']['first']['href'] = str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['first']['href']); + $items['first'] = ['href' => str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['first']['href'])]; } if (isset($variables['items']['previous'])) { - $variables['items']['previous']['href'] = str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['previous']['href']); + $items['previous'] = ['href' => str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['previous']['href'])]; } // Remove ajax wrapper format from specific page links. if (isset($variables['items']['pages'])) { foreach($variables['items']['pages'] as $key => $value) { - $variables['items']['pages'][$key]['href'] = str_replace('_wrapper_format=drupal_ajax&', '', $value['href']); + $items['pages'][$key] = ['href' => str_replace('_wrapper_format=drupal_ajax&', '', $value['href'])]; } } // Remove ajax wrapper format from next, last. if (isset($variables['items']['next'])) { - $variables['items']['next']['href'] = str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['next']['href']); + $items['next'] = ['href' => str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['next']['href'])]; } if (isset($variables['items']['last'])) { - $variables['items']['last']['href'] = str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['last']['href']); + $items['last'] = ['href' => str_replace('_wrapper_format=drupal_ajax&', '', $variables['items']['last']['href'])]; } + + $variables['items'] = $items; } /** diff --git a/src/Controller/AjaxCommentsController.php b/src/Controller/AjaxCommentsController.php index 9d2d855..c87cd6f 100644 --- a/src/Controller/AjaxCommentsController.php +++ b/src/Controller/AjaxCommentsController.php @@ -137,12 +137,19 @@ class AjaxCommentsController extends ControllerBase { // Load the display settings to ensure that the field formatter // configuration is properly applied to the rendered field when it is // returned in the ajax response. + + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($entity->getEntityType()->getLabel()->getUntranslatedString()); $display_options = $this->entityTypeManager ->getStorage('entity_view_display') - ->load($entity->getEntityTypeId() . '.' . $entity->bundle() . '.default') + ->load($entity->getEntityTypeId() . '.' . $entity->bundle() . '.' . $view_mode) ->getComponent($field_name); $comment_display = $comment_field->view($display_options); + // Add default classes to comments elements. + Utility::addCommentClasses($comment_display[0]['comments']); + // To avoid infinite nesting of #theme_wrappers elements on subsequent // ajax responses, unset them here. unset($comment_display['#theme_wrappers']); @@ -153,25 +160,28 @@ class AjaxCommentsController extends ControllerBase { unset($comment_display[0]['comments']['pager']['#route_parameters']['field_name']); unset($comment_display[0]['comments']['pager']['#route_parameters']['pid']); - $entity_type = $entity->getEntityType(); - - // For replies, the passed $entity is the parent comment. - // However, for the pager we want the parent entity. - if ($entity_type->id() === 'comment') { - $entity = $entity->getCommentedEntity(); - $entity_type = $entity->getEntityType(); - } - - $handler = $this->entityTypeManager()->getRouteProviders($entity_type->id())['html']; - $route_collection = $handler->getRoutes($entity_type); - $name = 'entity.' . $entity_type->get('id') . '.canonical'; - $route = $route_collection->get($name); - // Override the ajax route object with the actual entity route. - $entity_url = $entity->toURL(); - if ($route) { - $comment_display[0]['comments']['pager']['#route_name'] = $route; - $comment_display[0]['comments']['pager']['#route_parameters'] = $entity_url->getRouteParameters(); - } + /** + + $entity_type = $entity->getEntityType(); + + // For replies, the passed $entity is the parent comment. + // However, for the pager we want the parent entity. + if ($entity_type->id() === 'comment') { + $entity = $entity->getCommentedEntity(); + $entity_type = $entity->getEntityType(); + } + + $handler = $this->entityTypeManager()->getRouteProviders($entity_type->id())['html']; + $route_collection = $handler->getRoutes($entity_type); + $name = 'entity.' . $entity_type->get('id') . '.canonical'; + $route = $route_collection->get($name); + // Override the ajax route object with the actual entity route. + $entity_url = $entity->toURL(); + if ($route) { + $comment_display[0]['comments']['pager']['#route_name'] = $route; + $comment_display[0]['comments']['pager']['#route_parameters'] = $entity_url->getRouteParameters(); + } + */ return $comment_display; } diff --git a/src/Form/AjaxCommentsForm.php b/src/Form/AjaxCommentsForm.php index c893f02..71d211b 100644 --- a/src/Form/AjaxCommentsForm.php +++ b/src/Form/AjaxCommentsForm.php @@ -131,9 +131,14 @@ class AjaxCommentsForm extends CommentForm { /** @var \Drupal\comment\CommentInterface $comment */ $comment = $form_state->getFormObject()->getEntity(); + + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($comment->getCommentedEntity()->getEntityType()->getLabel()->getUntranslatedString()); + // Check to see if this comment field uses ajax comments. - $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, 'full'); - if (empty($comment_formatter) || !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { + $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, $view_mode); + if (!empty($comment_formatter) && !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { // If not using Ajax Comments, return the unmodified form. return $form; } @@ -210,8 +215,12 @@ class AjaxCommentsForm extends CommentForm { // Populate the comment-specific variables. /** @var \Drupal\comment\CommentInterface $comment */ $comment = $form_state->getFormObject()->getEntity(); - $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, 'full'); - if (empty($comment_formatter) || !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($comment->getCommentedEntity()->getEntityType()->getLabel()->getUntranslatedString()); + + $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, $view_mode); + if (!empty($comment_formatter) && !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { // If not using Ajax Comments, return the unmodified element. return $element; } @@ -402,8 +411,12 @@ class AjaxCommentsForm extends CommentForm { parent::save($form, $form_state); /** @var \Drupal\comment\CommentInterface $comment */ $comment = $form_state->getFormObject()->getEntity(); - $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, 'full'); - if (empty($comment_formatter) || !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($comment->getCommentedEntity()->getEntityType()->getLabel()->getUntranslatedString()); + + $comment_formatter = $this->fieldSettingsHelper->getFieldFormatterFromComment($comment, $view_mode); + if (!empty($comment_formatter) && !$this->fieldSettingsHelper->isEnabled($comment_formatter)) { // If not using Ajax Comments, do not change the redirect. return; } diff --git a/src/TempStore.php b/src/TempStore.php index a83125f..f725d90 100644 --- a/src/TempStore.php +++ b/src/TempStore.php @@ -55,6 +55,14 @@ class TempStore { return $this->privateTempStore->get('cid'); } + public function setViewMode($entity_type, $viewmode) { + $this->privateTempStore->set('view_mode_entity_type_' . $entity_type, $viewmode); + } + + public function getViewMode($entity_type) { + return $this->privateTempStore->get('view_mode_entity_type_' . $entity_type); + } + /** * Get a single selector value, without the '#' prefix. * diff --git a/src/Utility.php b/src/Utility.php index 10c7ac9..a7f0872 100644 --- a/src/Utility.php +++ b/src/Utility.php @@ -2,11 +2,13 @@ namespace Drupal\ajax_comments; +use Drupal\ajax_comments\Controller\AjaxCommentsController; use Drupal\Component\Utility\Html; use Drupal\Core\Cache\Cache; use Drupal\Core\Entity\ContentEntityInterface; use Drupal\Core\EventSubscriber\AjaxResponseSubscriber; use Drupal\Core\EventSubscriber\MainContentViewSubscriber; +use Drupal\Core\Render\Element; use Drupal\Core\Render\Markup; use Symfony\Component\HttpFoundation\Request; @@ -94,10 +96,15 @@ class Utility { * The value of the id attribute of the comment field wrapper element. */ public static function getWrapperIdFromEntity(ContentEntityInterface $commented_entity, $field_name) { + + /** @var \Drupal\ajax_comments\TempStore $tempStore */ + $tempStore = \Drupal::service('ajax_comments.temp_store'); + $view_mode = $tempStore->getViewMode($commented_entity->getEntityType()->getLabel()->getUntranslatedString()); + // Load the early-stage render array for the commented entity. $build = \Drupal::entityTypeManager() ->getViewBuilder($commented_entity->getEntityTypeId()) - ->view($commented_entity, 'full'); + ->view($commented_entity, $view_mode); // First, attempt to retrieve the cached markup for the commented entity // and use a regular expression to get the id attribute value of the @@ -155,7 +162,7 @@ class Utility { // retrieve the render array from the static variable on this class // or from the cache set by this class (both approaches are tried // in the method static::getEntityRenderArray()). - $render_array = static::getEntityRenderArray($commented_entity, 'full'); + $render_array = static::getEntityRenderArray($commented_entity, $view_mode); if (isset($render_array[$field_name])) { $wrapper_html_id = $render_array[$field_name]['#attributes']['id']; } @@ -166,6 +173,8 @@ class Utility { $wrapper_html_id = $render_array['#attributes']['id']; } } + // Make sure users can alter the wrapper if necessary. + \Drupal::moduleHandler()->alter('ajax_comments_wrapper_id', $wrapper_html_id, $commented_entity, $field_name); return $wrapper_html_id; } @@ -209,4 +218,19 @@ class Utility { ->get(MainContentViewSubscriber::WRAPPER_FORMAT) === 'drupal_modal'; } + /** + * Helper function to add wrapper classes to comments render arrays. + * + * @param array $elements + * The comment field render array. + */ + public static function addCommentClasses(array &$elements) { + foreach (Element::children($elements) as $key) { + if (!isset($elements[$key]['#comment'])) { + continue; + } + $elements[$key]['#attributes']['class'][] = AjaxCommentsController::$commentClassPrefix . $elements[$key]['#comment']->id(); + } + } + }