You are here

public function PanelizerEntityDefault::hook_entity_update in Panelizer 7.3

Same name and namespace in other branches
  1. 7.2 plugins/entity/PanelizerEntityDefault.class.php \PanelizerEntityDefault::hook_entity_update()

Overrides PanelizerEntityInterface::hook_entity_update

File

plugins/entity/PanelizerEntityDefault.class.php, line 1681
Base class for the Panelizer Entity plugin.

Class

PanelizerEntityDefault
Base class for the Panelizer Entity plugin.

Code

public function hook_entity_update($entity) {
  list($entity_id, $revision_id, $bundle) = entity_extract_ids($this->entity_type, $entity);
  if (!$this
    ->is_panelized($bundle)) {
    return;
  }

  // If there's no panelizer information on the entity then there is nothing
  // to do.
  if (empty($entity->panelizer)) {
    return;
  }

  // Allow exports or older data to be deployed successfully.
  if (is_object($entity->panelizer)) {
    $entity->panelizer = array(
      'page_manager' => $entity->panelizer,
    );
  }

  // When updating many/most objects, make sure the previous revision's
  // configuration is loaded too, as they won't be automatically loaded.
  // @todo There may be another way of handling this.
  if (isset($entity->original, $entity->original->panelizer)) {
    foreach ($entity->original->panelizer as $view_mode => $panelizer) {
      if (!isset($entity->panelizer[$view_mode])) {
        $entity->panelizer[$view_mode] = clone $panelizer;
      }
    }
  }

  // Update each panelizer configuration.
  foreach ($entity->panelizer as $view_mode => $panelizer) {

    // Don't write out empty records.
    if (empty($panelizer)) {
      continue;
    }

    // In some cases $panelizer is array, convert it to an object.
    if (is_array($panelizer)) {
      $panelizer = (object) $panelizer;
    }

    // Just a safety check to make sure we can't have a missing view mode.
    if (empty($view_mode)) {
      $view_mode = 'page_manager';
    }

    // In certain circumstances $panelizer will be the default's name rather
    // than a full object.
    if (!is_object($panelizer) && is_array($panelizer) && !empty($panelizer['name'])) {
      $panelizer = $this
        ->get_default_panelizer_object($bundle . '.' . $view_mode, $panelizer['name']);
      $panelizer->did = NULL;

      // Ensure original values are maintained.
      $panelizer->entity_id = $entity_id;
      $panelizer->revision_id = $revision_id;
    }

    // If this is a default display, and a change wasn't made, skip saving it.
    $default_display = $this
      ->get_default_display_default_name($bundle, $view_mode);
    if (empty($panelizer->display_is_modified) && !empty($panelizer->name) && $panelizer->name == $default_display) {

      // Delete the existing record for this revision/entity if one existed
      // before and a new revision was not being saved.
      if (empty($entity->revision)) {

        // Only delete the display for this specific revision.
        $this
          ->delete_entity_panelizer($entity, $view_mode, TRUE);
      }
      continue;
    }

    // Determine whether an existing Panelizer record needs to be updated or
    // a new one created.
    $update = array();

    // This entity supports revisions.
    if ($this->supports_revisions) {

      // If no revision value is assigned, indicating that no record was
      // previously saved for this entity/view_mode combination, or a new
      // revision is being created, create a new {panelizer_entity} record.
      if (empty($panelizer->revision_id) || $panelizer->revision_id != $revision_id) {
        $panelizer->revision_id = $revision_id;

        // If this has a custom display, flag the system that the display
        // needs to be saved as a new record.
        if (!empty($panelizer->did)) {
          $panelizer->display_is_modified = TRUE;
        }
      }
      else {
        $update = array(
          'entity_type',
          'entity_id',
          'revision_id',
          'view_mode',
        );
      }
    }
    else {

      // There is no entity_id set yet, the record was never saved before.
      if (empty($panelizer->entity_id)) {

        // Nothing to do.
      }
      else {
        $update = array(
          'entity_type',
          'entity_id',
          'view_mode',
        );
      }
    }

    // The editor will set this flag if the display is modified. This lets
    // us know if we need to clone a new display or not.
    // NOTE: This means that when exporting or deploying, we need to be sure
    // to set the display_is_modified flag to ensure this gets written.
    if (!empty($panelizer->display_is_modified)) {

      // Check if this display is shared and avoid changing other revisions
      // displays.
      $has_shared_display_args = array(
        ':entity_type' => $this->entity_type,
        ':entity_id' => $entity_id,
        ':revision_id' => $revision_id,
        ':did' => $panelizer->did,
      );
      $has_shared_display = db_query('SELECT COUNT(did) FROM {panelizer_entity} WHERE entity_type = :entity_type AND entity_id = :entity_id AND revision_id <> :revision_id AND did = :did', $has_shared_display_args)
        ->fetchField();

      // If this is a new entry or the entry is using a display from a
      // default, or revision is enabled and this is a shared display, clone
      // the display.
      if (!$update || empty($panelizer->did) || !empty($has_shared_display)) {
        $entity->panelizer[$view_mode] = $panelizer = $this
          ->clone_panelizer($panelizer, $entity);

        // Update the cache key since we are adding a new display
        $panelizer->display->cache_key = implode(':', array_filter(array(
          'panelizer',
          $panelizer->entity_type,
          $panelizer->entity_id,
          $view_mode,
          $revision_id,
        )));
      }

      // Ensure that Panels storage is set correctly.
      $panelizer->display->storage_type = 'panelizer_entity';
      $panelizer->display->storage_id = implode(':', array(
        $this->entity_type,
        $entity_id,
        $view_mode,
      ));

      // First write the display.
      panels_save_display($panelizer->display);

      // Make sure we have the did.
      $panelizer->did = $panelizer->display->did;

      // Ensure that we always write this as NULL when we have our own panel:
      $panelizer->name = NULL;
    }
    else {
      $panelizer->entity_type = $this->entity_type;
      $panelizer->entity_id = $entity_id;

      // The (int) ensures that entities that do not support revisions work
      // since the revision_id cannot be NULL.
      $panelizer->revision_id = (int) $revision_id;

      // Make sure we keep the same did as the original if the layout wasn't
      // changed.
      if (empty($panelizer->name) && empty($panelizer->did) && !empty($entity->original->panelizer[$view_mode]->did)) {
        $panelizer->did = $entity->original->panelizer[$view_mode]->did;
        $update = array(
          'entity_type',
          'entity_id',
          'revision_id',
          'view_mode',
        );
      }
    }

    // Make sure there is a view mode.
    if (empty($panelizer->view_mode)) {
      $panelizer->view_mode = $view_mode;
    }

    // Make sure there is a 'did' value. This can happen when the value is
    // passed via inline_entity_form.
    if (!isset($panelizer->did)) {
      $panelizer->did = 0;
    }

    // Save the record.
    drupal_write_record('panelizer_entity', $panelizer, $update);

    // If there was a CSS value saved before, update the exported file. This
    // is done after the entity is updated to ensure that the next page load
    // gets the new file.
    ctools_include('css');
    $cache_key = implode(':', array_filter(array(
      'panelizer',
      $this->entity_type,
      $entity_id,
      $view_mode,
      $revision_id,
    )));
    $filename = ctools_css_retrieve($cache_key);
    if ($filename) {
      ctools_css_clear($cache_key);
    }
    if (!empty($panelizer->css)) {
      ctools_css_store($cache_key, $panelizer->css);
    }
  }
}