-1

How can I add a CSS class to an <img> tag by using a template file if output looks like this:

<!-- BEGIN OUTPUT from 'themes/contrib/bootstrap/templates/system/image.html.twig' -->
<img class="media__image media__element b-lazy b-responsive img-responsive b-loaded" src="/sites/default/files/styles/media_image/public/2018-03/Trainer-Norbert-Sauer-auf-der-Rennbahn-Wambel-Am-Donnerstag-249903.jpg?h=c913b3c6&amp;itok=sENPOWtc" alt="Trainer Norbert Sauer auf der Rennbahn Wambel">
<!-- END OUTPUT from 'themes/contrib/bootstrap/templates/system/image.html.twig' -->
0

3 Answers 3

3

You can use hook_preprocess_field to add classes to the attributes array without modifying twig:

/**
 * Implements hook_preprocess_field().
 */
function mytheme_preprocess_field(&$variables) {
  if ($variables['entity_type'] == 'media' && $variables['field_name'] == 'image') {
    foreach ($variables['items'] as $key => $item) {
      $variables['items'][$key]['content']['#item_attributes']['class'][] = 'myclass';
    }
  }
}

Note that I am checking by both entity type (media) here along with the field name (image).

If you want to do this by image style, you can also use hook_preprocess_image:

/**
 * Implements hook_preprocess_image().
 */
function mytheme_preprocess_image(&$variables) {
  if ($variables['style_name'] == 'content_embed') {
    $variables['attributes']['class'][] = 'myclass';
  }
}

In both cases you do not need to touch the Twig file because the image field will be rendered and as long as attributes is output on the img tag (coming from core, it will be), the class will be appended to any other existing classes.

2
  • Any other solution rather than preprocess? Like using merge in attribute? Feb 11, 2019 at 11:48
  • 1
    Like this {% set user_pic = author.picture.thumbnail %} {% set user_pic = user_pic|merge({"#attributes" : {'class' : 'rounded-circle'} }) %} {{ user_pic }} Feb 11, 2019 at 12:09
0

A less hacky option is to enable Display Suite field templates, which allows you to add classes to the immediately <div> wrapper of the <img> tag. This way, you can practically add different classes to different image fields.

2
  • 1
    Display Suite is a heavy dependency though if you aren't really using it for much else - and it will also change how preprocess hooks etc are invoked. If you already have a healthy .theme file going, it might break things unexpectedly.
    – Kevin
    Jul 6, 2018 at 15:04
  • I didn’t downvote it.
    – Kevin
    Jul 9, 2018 at 11:19
0

Copy image.html.twig from themes/contrib/bootstrap/templates/system/image.html.twig to your theme's template folder

and modify the image tag adding addClass("myClass")

<img{{ attributes.addClass(classes).addClass("myClass") }} /> 

Note: this will apply the class to all images fields in the site

4
  • 3
    Note that this will apply the class to all images uploaded to image fields in the site.
    – Kevin
    Mar 10, 2018 at 16:20
  • @Kevin yes I know, it seems this is what the poster actually wants ... unless I am wrong ;-)
    – GiorgosK
    Mar 10, 2018 at 16:44
  • The heading is misleading. Actually I like to add a class to the IMG tag of a given field called field--trainer--photo
    – Josh
    Mar 12, 2018 at 9:02
  • Misleading or not, it contributes to solve the initial question. I agree it's not the best answer, but it's a workaround.
    – JFC
    Mar 13, 2023 at 16:43

Not the answer you're looking for? Browse other questions tagged or ask your own question.