mercury_editor-2.0.x-dev/src/Controller/MercuryEditorController.php

src/Controller/MercuryEditorController.php
<?php

namespace Drupal\mercury_editor\Controller;

use Drupal\Core\Url;
use Drupal\Core\Ajax\AjaxResponse;
use Drupal\Core\Access\AccessResult;
use Drupal\Core\Ajax\ReplaceCommand;
use Drupal\Core\Ajax\AjaxHelperTrait;
use Drupal\mercury_editor\DialogService;
use Drupal\Core\Render\RendererInterface;
use Drupal\Core\Session\AccountInterface;
use Drupal\Core\Entity\RevisionableInterface;
use Drupal\Core\Messenger\MessengerInterface;
use Symfony\Component\HttpFoundation\Request;
use Drupal\Core\Entity\ContentEntityInterface;
use Drupal\Core\Entity\EntityRepositoryInterface;
use Drupal\mercury_editor\MercuryEditorTempstore;
use Drupal\Core\Entity\EntityFormBuilderInterface;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Core\Language\LanguageManagerInterface;
use Drupal\mercury_editor\MercuryEditorContextService;
use Drupal\mercury_editor\MercuryEditorPreviewService;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Drupal\Core\Entity\Controller\EntityViewController;
use Drupal\mercury_editor\Ajax\OpenMercuryDialogCommand;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Drupal\mercury_editor\Ajax\IFrameAjaxResponseWrapper;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Drupal\layout_paragraphs\LayoutParagraphsLayoutTempstoreRepository;

/**
 * Class EditTrayController.
 *
 * Refreshes the node being edited in the tray.
 */
class MercuryEditorController extends EntityViewController {

  use AjaxHelperTrait;
  use StringTranslationTrait;

  /**
   * The Mercury Editor Edit Tray tempstore service.
   *
   * @var \Drupal\mercury_editor\MercuryEditorTempstore
   */
  protected $tempstore;

  /**
   * The current user.
   *
   * @var \Drupal\Core\Session\AccountInterface
   */
  protected $currentUser;

  /**
   * The entity repository.
   *
   * @var \Drupal\Core\Entity\EntityRepositoryInterface
   */
  protected $entityRepository;

  /**
   * The mercury editor context service.
   *
   * @var \Drupal\mercury_editor\MercuryEditorContextService
   */
  protected $mercuryEditorContext;

  /**
   * The messenger service.
   *
   * @var \Drupal\Core\Messenger\MessengerInterface
   */
  protected $messenger;

  /**
   * Creates a NodeViewController object.
   *
   * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager
   *   The entity type manager.
   * @param \Drupal\Core\Render\RendererInterface $renderer
   *   The renderer service.
   * @param \Drupal\Core\Session\AccountInterface $current_user
   *   The current user.
   * @param \Drupal\Core\Entity\EntityRepositoryInterface $entity_repository
   *   The entity repository.
   * @param \Drupal\mercury_editor\MercuryEditorTempstore $tempstore
   *   The tempstore.
   * @param \Drupal\mercury_editor\MercuryEditorContextService $mercury_editor_context
   *   The mercury editor context service.
   * @param \Drupal\mercury_editor\MercuryEditorPreviewService $mercuryEditorPreviewService
   *   The mercury editor preview service.
   * @param \Drupal\mercury_editor\Ajax\IFrameAjaxResponseWrapper $iFrameAjaxResponseWrapper
   *   The IFrame ajax response wrapper.
   * @param \Drupal\layout_paragraphs\LayoutParagraphsLayoutTempstoreRepository $layoutParagraphsTempstore
   *   The layout paragraphs tempstore repository.
   * @param \Drupal\mercury_editor\DialogService $mercuryEditorDialog
   *   The mercury editor dialog service.
   * @param \Drupal\Core\Messenger\MessengerInterface $messenger
   *   The messenger service.
   * @param \Drupal\Core\Language\LanguageManagerInterface $languageManager
   *   The language manager service.
   * @param \Drupal\Core\Entity\EntityFormBuilderInterface $entityFormBuilder
   *   The entity form builder service.
   */
  public function __construct(
    EntityTypeManagerInterface $entity_type_manager,
    RendererInterface $renderer,
    AccountInterface $current_user,
    EntityRepositoryInterface $entity_repository,
    MercuryEditorTempstore $tempstore,
    MercuryEditorContextService $mercury_editor_context,
    protected MercuryEditorPreviewService $mercuryEditorPreviewService,
    protected IFrameAjaxResponseWrapper $iFrameAjaxResponseWrapper,
    protected LayoutParagraphsLayoutTempstoreRepository $layoutParagraphsTempstore,
    protected DialogService $mercuryEditorDialog,
    MessengerInterface $messenger,
    protected LanguageManagerInterface $languageManager,
    protected EntityFormBuilderInterface $entityFormBuilder,
  ) {
    parent::__construct($entity_type_manager, $renderer);
    $this->currentUser = $current_user;
    $this->entityRepository = $entity_repository;
    $this->tempstore = $tempstore;
    $this->mercuryEditorContext = $mercury_editor_context;
    $this->messenger = $messenger;
  }

  /**
   * {@inheritdoc}
   */
  public static function create(ContainerInterface $container) {
    return new static(
      $container->get('entity_type.manager'),
      $container->get('renderer'),
      $container->get('current_user'),
      $container->get('entity.repository'),
      $container->get('mercury_editor.tempstore_repository'),
      $container->get('mercury_editor.context'),
      $container->get('mercury_editor.preview'),
      $container->get('mercury_editor.iframe_ajax_response_wrapper'),
      $container->get('layout_paragraphs.tempstore_repository'),
      $container->get('mercury_editor.dialog'),
      $container->get('messenger'),
      $container->get('language_manager'),
      $container->get('entity.form_builder'),
    );
  }

  /**
   * Edit an entity with the mercury editor edit tray.
   *
   * @param \Symfony\Component\HttpFoundation\Request $request
   *   The request.
   * @param \Drupal\Core\Entity\ContentEntityInterface $mercury_editor_entity
   *   The entity.
   *
   * @return array
   *   The edit form.
   */
  public function editor(Request $request, ContentEntityInterface $mercury_editor_entity) {
    $access = $this->access();
    if ($access->isForbidden()) {
      $message = $this->currentUser->isAnonymous()
        ? $this->t('You must be logged in to edit this entity.')
        : $this->t('You do not have permission to edit this entity.');
      $this->messenger->addError($message);
      if (method_exists($mercury_editor_entity, 'toUrl')) {
        $url = $mercury_editor_entity->toUrl();
      }
      else {
        $url = Url::fromRoute('<front>');
      }
      return new RedirectResponse($url->toString());
    }
    $form_state_additions = [];
    if ($request->get('translation_mode')) {
      $form_state_additions['langcode'] = $request->get('langcode');
      $form_state_additions['content_translation']['translation_form'] = $request->get('translation_form');
      if ($request->get('source')) {
        $form_state_additions['content_translation']['source'] = $this->languageManager->getLanguage($request->get('source'));
      }
      if ($request->get('target')) {
        $form_state_additions['content_translation']['target'] = $this->languageManager->getLanguage($request->get('target'));
      }
    }
    $form = $this->entityFormBuilder->getForm($mercury_editor_entity, 'mercury_editor', $form_state_additions);
    if ($this->isAjax()) {
      $response = $this->mercuryEditorPreviewService->ajaxUpdatePreview($mercury_editor_entity);
      $response->addCommand(new ReplaceCommand('.me-entity-form', $form));
      return $response;
    }
    else {
      return $form;
    }
  }

  /**
   * Undoes the last change to the entity being edited.
   *
   * @param \Drupal\Core\Entity\ContentEntityInterface $mercury_editor_entity
   *   The entity.
   */
  public function undo(ContentEntityInterface $mercury_editor_entity) {
    $this->tempstore->previousState($mercury_editor_entity);
    return $this->isAjax() ? new AjaxResponse() : [];
  }

  /**
   * Redoes the last undone change to the entity being edited.
   *
   * @param \Drupal\Core\Entity\ContentEntityInterface $mercury_editor_entity
   *   The entity.
   */
  public function redo(ContentEntityInterface $mercury_editor_entity) {
    $this->tempstore->nextState($mercury_editor_entity);
    return $this->isAjax() ? new AjaxResponse() : [];
  }

  /**
   * Exits the editor.
   *
   * @param \Symfony\Component\HttpFoundation\Request $request
   *   The request.
   * @param \Drupal\Core\Entity\ContentEntityInterface $mercury_editor_entity
   *   The entity.
   *
   * @return \Symfony\Component\HttpFoundation\RedirectResponse
   *   A redirect response.
   */
  public function exit(Request $request, ContentEntityInterface $mercury_editor_entity) {
    $ids = $this->tempstore->getLayoutParagraphsFieldIds($mercury_editor_entity);
    foreach ($ids as $id) {
      $layout = $this->layoutParagraphsTempstore->getWithStorageKey($id);
      // Check we have a layout before attempting to delete it.
      if ($layout !== NULL) {
        $this->layoutParagraphsTempstore->delete($layout);
      }
    }
    $this->tempstore->clearStates($mercury_editor_entity);
    $this->tempstore->delete($mercury_editor_entity);

    $url = NULL;
    if ($request->get('destination')) {
      $url = $request->get('destination');
    }
    elseif (!$mercury_editor_entity->id()) {
      $url = Url::fromRoute('<front>')->toString();
    }
    elseif ($mercury_editor_entity instanceof RevisionableInterface) {
      /** @var \Drupal\Core\Entity\RevisionableStorageInterface $storage */
      $storage = $this->entityTypeManager
        ->getStorage($mercury_editor_entity->getEntityTypeId());
      /** @var \Drupal\Core\Entity\RevisionableInterface $revision */
      $revision = $storage->loadRevision($mercury_editor_entity->getRevisionId());
      if ($revision && !$revision->isDefaultRevision() && $mercury_editor_entity->hasLinkTemplate('latest-version')) {
        $url = $revision
          ->toUrl('latest-version', [
            'absolute' => TRUE,
            'language' => $mercury_editor_entity->language(),
          ])
          ->toString();
      }
    }
    if (empty($url)) {
      $url = $mercury_editor_entity
        ->toUrl('canonical', ['absolute' => TRUE])
        ->toString();
    }
    return new RedirectResponse($url);
  }

  /**
   * Renders an outline of components for a given Mercury Editor entity.
   *
   * @param \Symfony\Component\HttpFoundation\Request $request
   *   The request.
   * @param \Drupal\Core\Entity\ContentEntityInterface $mercury_editor_entity
   *   The entity.
   *
   * @return array|\Drupal\Core\Ajax\AjaxResponse
   *   The outline of components.
   */
  public function componentOutline(Request $request, ContentEntityInterface $mercury_editor_entity) {
    $outline = [
      '#type' => 'mercury_editor_component_outline',
      '#entity' => $mercury_editor_entity,
      // Wrapper for ajax replacement.
      '#prefix' => '<div id="me-component-outline-wrapper">',
      '#suffix' => '</div>',
    ];
    if ($this->isAjax()) {
      $response = new AjaxResponse();
      $command = $request->get('update')
        ? new ReplaceCommand('#me-component-outline-wrapper', $outline)
        : new OpenMercuryDialogCommand(
          '#mercury-editor-component-outline',
          $this->t('Component Outline'),
          $outline,
          [
            'width' => 'fit-content',
            'height' => 'fit-content',
            'drupalAutoButtons' => 'false',
            'resizable' => TRUE,
            'modal' => FALSE,
            'dock' => 'left',
            'classes' => [
              'lpb-dialog',
            ],
          ],
        );
      $response->addCommand($command);
      return $response;
    }
    else {
      return $outline;
    }
  }

  /**
   * Preview an entity being edited with the mercury editor edit tray.
   */
  public function preview() {
    $mercury_editor_entity = $this->mercuryEditorContext->getEntity();
    $this->tempstore->clearStates($mercury_editor_entity);
    $this->tempstore->saveState($mercury_editor_entity);
    $this->mercuryEditorContext->setPreview(TRUE);
    $preview = $this->view($mercury_editor_entity);
    $preview['#attached']['drupalSettings']['mercuryEditor']['id'] = $mercury_editor_entity->uuid();
    $preview['#cache']['max-age'] = 0;
    $preview['#attached']['drupalSettings']['mercuryEditorId'] = $mercury_editor_entity->uuid();
    return $preview;
  }

  /**
   * Access callback for using mercury editor.
   */
  public function access() {
    $mercury_editor_entity = $this->mercuryEditorContext->getEntity();

    if ($mercury_editor_entity instanceof ContentEntityInterface) {
      return $mercury_editor_entity->id()
        ? $mercury_editor_entity->access('update', NULL, TRUE)
        : $mercury_editor_entity->access('create', NULL, TRUE);
    }

    return AccessResult::forbidden();
  }

}

Главная | Обратная связь

drupal hosting | друпал хостинг | it patrol .inc