2

I'm trying to display the file size of a file next to a media link button on a page.

I have two content types with a media entity reference field in each. Each field is restricted to only pull from a file media type. What I was trying to do was create a twig variable using a field preprocess and pop that variable inside each of my field templates. However, my preprocess below doesn't seem to be displaying the file size as I want. What am I doing wrong?

function theme_preprocess_field(&$variables, $hook) {

  $pdf_fields = [
    'field_1',
    'field_2'
  ];

  if (in_array($element['#field_name'], $pdf_fields) && $element['#entity_type'] == 'node') {

    if ($variables['items'][0]) {

      $field_name = $element['#field_name'];

      $node = $element['#object'];
      // Get first referenced media id.
      $media_id = $node->$field_name->target_id;
      // Get file object.
      $file = \Drupal\file\Entity\File::load($media_id);
      if ($file) {
        // Get file size.
        $file_size = format_size($file->getSize());
        // Set file size variable.
        $variables['file_size'] = $file_size;
      }
    }
  }
}

Twig field template

{% for item in items %}
  <a href="{{ item.content['#url'] }}" class="button">Download Paper</a><span>(PDF | {{ file_size }})</span>
{% endfor %}
5
  • you need to get the file field id off the media object too, right now you are doing File::load on the media entity which will return null or the wrong file. Load the media entity and grab the file field just like you are doing for the Node media field. Check theme_preprocess_file_link for some more hints. If you render the media field as default and setup that media type to display as Generic File (core), won't this problem solve itself?
    – Kevin
    Feb 15, 2020 at 5:04
  • 2
    This should be done with a field formatter and not with templating.
    – leymannx
    Feb 15, 2020 at 6:15
  • Yes, hence the Generic File formatter. If you just want to get the class on the link and add the "PDF" string, you can override theme_preprocess_file_link pretty easily.
    – Kevin
    Feb 15, 2020 at 13:22
  • Thanks guys I'll try and change field formatter to generic and see if that does the trick. I know the code above works if I apply to a single field. When I tried to add a second field that's when I ran into issues.
    – Paul H
    Feb 15, 2020 at 18:13
  • Came across this post from leymannx about using field formatter too - medium.com/@leymannx/…. Very helpful
    – Paul H
    Feb 17, 2020 at 14:52

1 Answer 1

1
function HOOK_preprocess_file_link(&$variables) {
  if (isset($variables['file'])) {
    $variables['fileLinkDisplay'] = [
      'fileSize' => $variables['file']
        ->getSize(),
      'fileSizeFormatted' => format_size($variables['file']
        ->getSize()),
    ];
  }
}

{{ fileLinkDisplay.fileSize }}and {{ fileLinkDisplay.fileSizeFormatted }} will be available in your template.

PS: if it works then you can more filter to restrict to the content type and field you want applied for.

Additionally, there is a module that show the size https://www.drupal.org/project/field_formatter_file_size

Field Formatter File Size is a field formatter to display the file size.

2
  • Thanks Yusef! Saw that module too, I may give that a shot too.
    – Paul H
    Feb 17, 2020 at 14:51
  • @PaulH have you tried the HOOK_preprocess_file_link, let me know about the result.
    – Yuseferi
    Feb 17, 2020 at 18:43

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

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