web-dev-qa-db-fra.com

Chargement de l'image par défaut à partir d'un champ de nœud dans page.html.twig

Je veux imprimer l'image par défaut d'un champ de nœud dans le fichier modèle page.html.twig en Drupal 8. En faisant mes recherches, l'approche la plus simple que j'ai pu trouver était

{% if node.field_image.entity %} <img src="{{ file_url(node.field_image.entity.uri.value) }}" alt="{{ node.field_image.alt }}" {% if node.field_image.title %} title="{{ node.field_image.title }}" {% endif %} /> {% endif %}

Cela fonctionne si je charge une image dans le champ mais pas autrement avec l'image par défaut du champ d'image. Je souhaite utiliser le code ci-dessus pour imprimer l'image par défaut que je choisis pour ce champ d'image. Actuellement, la méthode ci-dessus donne <img src="http://example.com/" alt=""> pour l'image par défaut

Comment puis-je accéder à la valeur uri de l'image par défaut dans le src de la balise d'image ci-dessus. Existe-t-il un autre moyen d'imprimer l'image par défaut d'un nœud dans le fichier page.htm.twig, de préférence à partir de la couche modèle, car je n'ai aucune expérience des fonctions de prétraitement, etc.? Mon objectif est d'avoir une image statique qui soit la même dans tout le type de contenu.

5
adhavanjo

Voici une approche, en utilisant une méthode d'assistance. Il suppose que vous avez accès à l'entité de nœud chargée ($ entity) et que vous souhaitez obtenir l'ensemble ou l'image par défaut pour un champ d'image donné. J'ai également laissé des commentaires et des liens qui expliquent pourquoi Drupal :: service ('entity.repository') est utilisé et comment j'ai découvert la façon dont le module Image charge les paramètres d'image par défaut.

    /**
 * Get the set or default image uri for a file image field (if either
 * exist).
 * @param $entity
 * @param $fieldName
 * @return null|string
 */
function get_image_uri($entity, $fieldName) {
  $image_uri = NULL;
  if( $entity->hasField($fieldName) ) {
    try {
      $field = $entity->{$fieldName}; //Try loading from field values first.
      if ($field && $field->target_id) {
        $file = File::load($field->target_id);
        if ($file) {
          $image_uri = $file->getFileUri();
        }
      }
    } catch (\Exception $e) {
      \Drupal::logger('get_image_uri')->notice($e->getMessage(), []);
    }

    // If a set value above wasn't found, try the default image.
    if (is_null($image_uri)) {
      try {
        $field = $entity->get($fieldName); // Loading from field definition
        if ($field) {
          // From the image module /core/modules/image/ImageFormatterBase.php
          // $default_image = $test->fieldDefinition->getFieldStorageDefinition()->getSetting('default_image');
          $default_image = $field->getSetting('default_image');
          if ($default_image && $default_image['uuid']) {
            // $defaultImageFile = \Drupal::entityManager()->loadEntityByUuid('file', $default_image['uuid']));
            // See https://www.drupal.org/node/2549139  entityManager is deprecated.
            // Use entity.repository instead.
            $entityrepository = Drupal::service('entity.repository');
            $defaultImageFile = $entityrepository->loadEntityByUuid('file', $default_image['uuid']);
            if($defaultImageFile) {
              $image_uri = $defaultImageFile->getFileUri();
            }
          }
        }
      } catch (\Exception $e) {
        \Drupal::logger('get_image_uri')->notice($e->getMessage(), []);
      }
    }
  }

  return $image_uri;
}
9
Blue Waters

Merci @Blue Waters pour l'extrait de code. Je l'ai utilisé dans une fonction de prétraitement pour intégrer le thème. Partager mon code ici, donc cela aide quelqu'un d'autre à gagner du temps.

J'ai un nom de champ field_images, que je rend dans le modèle page.html.twig. Les propriétés d'image par défaut uui, height & width sont facilement disponibles dans les paramètres de champ, donc j'ai pensé que l'ajout des fileuri serait l'approche la plus simple.

Ma fonction dans mytheme.theme

function theme_preprocess_page(&$variables) {
  if (array_key_exists('node', $variables)) {
    $node = $variables['node'];

    if (isset($node) && !is_string($node)) {
      if ($node->hasField('field_images')) {
        $images = $node->get('field_images');

        if (sizeof($images) === 0) {
          $image = $images->getFieldDefinition();
          $defaultImage = $image->getSetting('default_image');

          $entityrepository = Drupal::service('entity.repository');
          $defaultImageFile = $entityrepository->loadEntityByUuid('file', $defaultImage['uuid']);

          if($defaultImageFile) {
            $defaultImageUri = $defaultImageFile->getFileUri();
            $defaultImage['fileuri'] = $defaultImageUri;
            $image->setSetting('default_image', $defaultImage);
          }
        }
      }
    }
  }
}

Ensuite, dans page.html.twig, j'ai les éléments suivants:

{% if node.field_images is not empty %}
  {% for image in node.field_images %}
    <img src="{{ file_url(image.entity.fileuri) }}" width="{{ image.width }}" height="{{ image.height }}" alt="{{ image.alt }}">
  {% endfor %}
{% else %}
  {% set image = node.field_images.setting('default_image') %}
  <img src="{{ file_url(image.fileuri) }}" width="{{ image.width }}" height="{{ image.height }}" alt="{{ image.alt }}">
{% endif %}
2
makbeta

Contourné en utilisant des images statiques au lieu d'images par défaut avec le code {{ base_path ~ directory }} pour obtenir le chemin vers l'image (src) sans aucun prétraitement.

0
adhavanjo