Problem/Motivation

The default file type icons are 16⨉16-pixel, low-resolution, PNG files that look poor on a retina display.

Drupal previously shipped these file type icons inside the file module, but they're now distributed (duplicated) into the Demo Umami, Claro, and Starterkit themes in Drupal 11 across the following three core folder locations:

Proposed resolution

  • Create new high-resolution Scalable Vector Graphics files to replace the existing low-resolution PNG files.
  • Update stylesheet references to file icons in Demo Umami, Claro, and Starterkit theme css/component/file.css stylesheets.
  • SVG files should be crafted carefully to match, optimized well, and safe for inline-embedding in the future. This implies:
    • Maintain existing image size (dimensions) and colors from the originals, to minimize bikesheding and scope creep.
    • Path precision rounded to two decimal places, when necessary. Prefer whole integers when possible.
    • Use root element attributes (aria-hidden, focusable, height, width, viewBox) that facilitate the files being embedded in HTML and used inline.
    • Avoid SVG features requiring ID refs (e.g., filters, masks, gradients) to prevent duplicate ID issues when embedding the same or similar SVGs multiple times in one HTML doc.
  • Add the new high-resolution SVGs files alongside existing low-resolution PNGs in all themes shipped with Drupal core. Do not remove old PNG files from the codebase. Add cleanup task #3452493: Remove images that have been replaced with svg files.

Before/after comparison between PNG and SVGs, manually recreated in Figma:

Note: server limitations on uploading SVGs and/or rendering images from git.drupalcode.org prevent us from displaying the proposed SVGs inline here.

before/after comparison of file type icons in Drupal core with PNG stacked on left, SVGs to the right

Remaining tasks

  1. Craft the SVGs.
  2. Prepare the MR.
  3. Review the code changes.
  4. (Optional) Add instructions on how to manually test in Drupal.
  5. (Optional) Upload before/after screenshots from manual tests.

User interface changes

Users on devices with high resolution screens will see a crisp image with no diffusion artifacts or blur inherent from legacy image formats.

Users on devices with low resolution may or may not notice much of a visual difference.

API changes

In as much as image files shipped with core can be considered an "API", the old PNG files will be left in place to avoid breaking themes that may be referencing them directly. The old files may be deleted in the next major version of Drupal.

Issue fork drupal-3521857

Command icon Show commands

Start within a Git clone of the project using the version control instructions.

Or, if you do not have SSH keys set up on git.drupalcode.org:

  • 11.x Comparecompare
  • 1 hidden branch
  • 3521857-file-icons Comparechanges, plain diff MR !11983

Comments

jwilson3 created an issue. See original summary.

jwilson3’s picture

Issue summary: View changes
jwilson3’s picture

Issue summary: View changes
jwilson3’s picture

Title: Update Drupal's default file type icons » Update Drupal's default file type icons to use SVG
Issue tags: +CSS, +frontend, +HiDPI, +svg
Parent issue: » #2433761: [meta] svg guidelines / requirements
Related issues: +#1974928: Update Drupal's default throbber icons, +#2575253: Update loading icon and use SVG

jwilson3’s picture

Hrm. The test fail seems unrelated.

Drupal\Tests\node\Functional\NodeRevisionsAll
The string "page=1" was not found anywhere in the HTML response of the current page.
jwilson3’s picture

Status: Active » Needs review

I don't think issues like this that swap out image file references in CSS can even really be verified with automated tests anyway. Sending to NR.

jwilson3’s picture

Add the new high-resolution SVGs files alongside existing low-resolution PNGs in all themes shipped with Drupal core. Do not remove old PNG files from the codebase. Add cleanup task #3452493: [12.x] Remove images that have been replaced in core.

I'm having second thoughts about this in the context of the StarterKit theme. Certainly for Umami and Claro themes, we shouldnt remove the PNGs. However the StarterKit theme, when used as intended (if I understand correctly), is supposed to be a kind of "line in the sand" or fork of the codebase and a snapshot in time. This implies to me that we could easily remove the old PNG files and then any new themes created from the Starterkit would have a clean slate and no duplicitous files. Tech debt free!

jwilson3’s picture

Issue summary: View changes
kim.pepper’s picture

Component: file.module » theme system

I think this might get more attention if it were under theme system.

smustgrave’s picture

Version: 11.1.x-dev » 11.x-dev
Status: Needs review » Needs work

MR needs to be updated for 11.x please.

jwilson3’s picture

Status: Needs work » Needs review

My apologies for starting from the wrong branch. I recreated the same existing MR branch name locally, cherry-picked the existing commits, and force-pushed to the existing MR. Back to NR.

needs-review-queue-bot’s picture

Status: Needs review » Needs work
StatusFileSize
new91 bytes

The Needs Review Queue Bot tested this issue. It no longer applies to Drupal core. Therefore, this issue status is now "Needs work".

This does not mean that the patch necessarily needs to be re-rolled or the MR rebased. Read the Issue Summary, the issue tags and the latest discussion here to determine what needs to be done.

Consult the Drupal Contributor Guide to find step-by-step guides for working with issues.

jwilson3’s picture

Status: Needs work » Needs review

MR has been updated to 11.x.

jwilson3’s picture

I've rebased the MR on the latest 11.x in an attempt to clear unrelated CI failures...

mgifford’s picture

Can we spend some time optimizing them before bringing them into Core?

https://www.svgviewer.dev/
https://optimize.svgomg.net/

For instance, 948 bytes:

<svg aria-hidden="true" focusable="false" width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
  <path d="M11 0L14 3V16H2V0H11Z" fill="#fff"/>
  <path d="M11 0L14 3V16H2V0H11ZM3 15H13V4H10V1H3V15ZM11 3H12.5L11 1.5V3Z" fill="#7f7f7f"/>
  <path d="M4 2H9V3H4V2Z" fill="#dadada"/>
  <path d="M4 3H9V4H4V3Z" fill="#e0e0e0"/>
  <path d="M4 4H9V5H4V4Z" fill="#ebebeb"/>
  <path d="M4 5H12V6H4V5Z" fill="#eee"/>
  <path d="M4 6H12V7H4V6Z" fill="#f5f5f5"/>
  <path d="M4 7H12V8H4V7Z" fill="#f8f8f8"/>
  <path d="M4 8H12V9H4V8Z" fill="#fcfcfc"/>
  <path d="M4 3H9V4H4V3Z" fill="#9e9e9e"/>
  <path d="M6 8H4V7H6V8ZM12 8H7V7H12V8Z" fill="#9e9e9e" fill-opacity="0.65"/>
  <path d="M8 6H4V5H8V6ZM12 6H9V5H12V6Z" fill="#9e9e9e" fill-opacity="0.8"/>
  <path d="M8 10H4V9H8V10ZM12 10H9V9H12V10Z" fill="#9e9e9e" fill-opacity="0.45"/>
  <path d="M6 12H4V11H6V12ZM10 12H7V11H10V12ZM12 12H11V11H12V12Z" fill="#9e9e9e" fill-opacity="0.3"/>
</svg>

Than 803 bytes:
<svg xmlns="http://www.w3.org/2000/svg" fill="none" aria-hidden="true" viewBox="0 0 16 16"><path fill="#fff" d="m11 0 3 3v13H2V0z"/><path fill="#7f7f7f" d="m11 0 3 3v13H2V0zM3 15h10V4h-3V1H3zm8-12h1.5L11 1.5z"/><path fill="#dadada" d="M4 2h5v1H4z"/><path fill="#e0e0e0" d="M4 3h5v1H4z"/><path fill="#ebebeb" d="M4 4h5v1H4z"/><path fill="#eee" d="M4 5h8v1H4z"/><path fill="#f5f5f5" d="M4 6h8v1H4z"/><path fill="#f8f8f8" d="M4 7h8v1H4z"/><path fill="#fcfcfc" d="M4 8h8v1H4z"/><path fill="#9e9e9e" d="M4 3h5v1H4z"/><path fill="#9e9e9e" fill-opacity=".7" d="M6 8H4V7h2zm6 0H7V7h5z"/><path fill="#9e9e9e" fill-opacity=".8" d="M8 6H4V5h4zm4 0H9V5h3z"/><path fill="#9e9e9e" fill-opacity=".5" d="M8 10H4V9h4zm4 0H9V9h3z"/><path fill="#9e9e9e" fill-opacity=".3" d="M6 12H4v-1h2zm4 0H7v-1h3zm2 0h-1v-1h1z"/></svg>

These are little, but they add up, with every page load.

It could get smaller still if we simplifed how it looks.

jwilson3’s picture

Isn't this kind of micro-optimization mostly obviated by gzip or brotli? I'm happy to be wrong, but these savings seem negligible in practice—especially considering that Drupal core’s own HTML output doesn’t aggressively strip whitespace, newlines, or indentation either.

jwilson3’s picture

Also worth noting: running SVGs through optimizers like SVGO can make them harder to review and maintain. For example,

path="M11 0L14 3V16H2V0H11ZM3 15H13V4H10V1H3V15ZM11 3H12.5L11 1.5V3Z"

becomes

path="m11 0 3 3v13H2V0zM3 15h10V4h-3V1H3zm8-12h1.5L11 1.5z",

which is more compact but much less readable for quick diffs or manual review.

jwilson3’s picture

It would be nice if there was an automated solution to always minify SVGs in core in the same way, because different tools optimize in different ways, using different default options, often stripping out important attributes. Applications that generate SVGs also generate their own different ways of structuring the SVG, so every time you pull an "optimized" file into an SVG editor, and save it again, it may make unrelated changes on the roundtrip back to optimized SVG. Therefore, the SVGs require manual edits after optimization to restore settings. (In the example in #16 focusable="false" and the width and height attributes got removed, which will hinder future proofing the SVGs in core for inlining them server-side in the HTML).

I think what is missing here is:

1) clear agreement to treat SVGs as implementation assets as opposed to hand-curated visual code.
2) a single CLI tool to optimize assets and a well-defined list of options to ensure SVGs are optimized in the same way every time.
3) (ideally), CI testing tool to balk when required attributes are missing, or when forbidden attributes are used (eg id).

All this feels somewhat outside the scope of this issue, and implies a much larger conversation. For now, I opted for hand crafted SVG code that is structured in a way that optimizes for Brotli compression, while retaining readability and ensuring inlineability in the future. If optimization becomes a big deal it would be interesting to compare apples with apples and see what the actual Brotli / gzipped size difference would be both with and without a proper optimization that leaves the required attributes in place.

smustgrave’s picture

So late to the game here. But this is kinda a massive ticket in that we would need before/after screenshots of every icon in use to make sure no regression. Would it be worth trying to break out into 3-4 icons a ticket vs all at once.

jwilson3’s picture

There are before/after screenshots in the IS, from the raster PNG to the SVG. The approach taken on this issue is exactly the same approach taken on the loading and throbber icon issues, whereby we're not really introducing redesign, we're simply updating the format of the existing files rom raster to vector, so as not to have to spend time bikeshedding redesign, and getting this into core in the next immediate major release.

Splitting these apart into separate issues feels like it would open the door for more cat herding.

I propose keeping this on a single issue, and using the following steps to take before/after screenshots (untested):

  1. Install Drupal with the Standard profile.
  2. Add a multi-cardinality file field to the Article content type that allows upload of each of the file mime types.
  3. Configure field display to display the generic file widget.
  4. Create a node and upload a bunch of files with different file extensions. The files could be zero byte and just be the correct file extension.
  5. Take before/after screenshots of the rendered node with attached files.

There would be some amount of iteration, testing, and exploration to ensure we establish a definitive list of file extensions that map to each mime type.

smustgrave’s picture

Looking at the folder structure shouldn't svg go under the svg folder? Example in demo_umami

jwilson3’s picture

@Smusgrave: Thanks for bringing this up.

  • In D7 and D8 these files were located in core's /modules/file/icons/ folder.
  • In D9 the files moved to various folder locations, and ultimately ended up duplicated across a bunch of core themes but always maintaining a subfolder structure of `images/classy/icons` as a way to indicate that the "source of truth" for these files was from the classy theme which was being removed from core in D10. (See Umami images/classy/README.txt)
  • In the current MR for D11, I opted for keeping the touch points as light as possible so that themers can easily get their starterkit themes up-to-date on a new core version by effectively downloading a zip folder of SVGs, swapping ".png" for ".svg" in their theme CSS and done.
  • If we're talking about restructuring the folders, maybe that frustratingly turns this into a D12 issue, since we're not supposed to be removing the old images, since they're kind of unofficially an "api" of sorts.

It does indeed look like the `classy` folder could be removed in D11, since referencing classy is no longer appropriate in core as of D10. I'm just not sure moving them into the umami/images/svg/ folder is entirely the right thing either. For one, the svg subfolder could also be thought of as a transitionary folder and with this issue getting merged the `svg` folder itself becomes obviated because all of the images will be SVGs. Secondly, it makes sense to keep the file icons grouped together in a separate subfolder, versus thrown in with the rest of the lot.

If only we'd had had the foresight to just move these back into /core/modules/file/icons/ in Drupal 10 since no one really wants to spend time overriding these images in a theme, and if you do, you know what you're doing and can edit your Twig templates, theme CSS, and SVG files accordingly to do what you please. Maybe there was a valid reason to copy the files so many times into various core themes (perhaps because each theme was overriding the template HTML classnames and needed different CSS styles but this seems like an anti-pattern). Maybe now is the time to clean this up and centralize it all again. Get the HTML **right**, get the classnames right, and get the CSS right in one centralized location, so no-one needs to override this any longer. IMO, getting the HTML right means skipping ahead to inlining the SVGs directly into the Twig templates.

All that being said, I still think it makes sense to keep the scope here eyed towards incremental improvements to expedite the chances of this getting in with minimal bc breaks, and then push the additional considerations, consolidations and cleanup to follow-ups, but am looking forward to your considered feedback given wider core subsystem maintainer experience.

smustgrave’s picture

Status: Needs review » Reviewed & tested by the community

Fair, icons when viewing locally do appear to be 1 to 1 so lets see. Maybe a 11.4 target.

  • longwave committed 25393706 on 11.x
    feat: #3521857 Update Drupal's default file type icons to use SVG
    
    By:...

  • longwave committed 794c6dee on main
    feat: #3521857 Update Drupal's default file type icons to use SVG
    
    By:...
longwave’s picture

Status: Reviewed & tested by the community » Fixed
Issue tags: +11.4.0 release highlights

Thanks, this is a nice improvement. Tagging as a highlight as I think this is perhaps worth mentioning in 11.4.0. Also thank you @jwilson3 for your thoughtful comments in this issue while keeping the scope tight. I agree that micro-optimising the SVGs isn't really worth the effort, it's better for them to be maintainable than save a few bytes here and there.

If only we'd had had the foresight to just move these back into /core/modules/file/icons/ in Drupal 10 since no one really wants to spend time overriding these images in a theme

I think this is a great idea, these icons are generic and there is no need to have them copied about between themes; they would be good to have as a default set in file.module itself. If you want to open a followup for that please do so!

Committed and pushed 794c6dee90e to main and 253937064d9 to 11.x. Thanks!

Now that this issue is closed, review the contribution record.

As a contributor, attribute any organization that helped you, or if you volunteered your own time.

Maintainers, credit people who helped resolve this issue.

longwave’s picture

Issue tags: +Needs followup

Also tagging for a followup to eventually remove the unused PNGs; it's possible that sites have hardcoded references to them so we shouldn't just delete them here.

jwilson3’s picture

Thanks @longwave for the thoughtful review, the merge, and your kind words in #27. Much appreciated — and thanks to you and the other core maintainers for the drum-beat triage of the never-ending stream of “grains of sand” contributions like this one. 🙂

Pending:

  1. Re: #30. no follow-up needed; the PNGs have already been added to #3452493: Remove images that have been replaced with svg files.
  2. Re: #27. create follow-up to consolidate the new SVG files from disparate core themes into a more appropriate core location (file module / misc / etc., per that discussion).
  3. (Optional) some small forward-looking 12.x-related CR opportunities:
    • a) “API deprecation”: PNGs removed from core themes for 12.x (tracked in #3452493: Remove images that have been replaced with svg files).
    • b) document the new SVG location in file module (requires follow-up being created in point 2), and
    • c) starterkit upgrade guide for themers with starterkit-based themes in D10/11 (based on point 3 in #23):

      the touch points [were kept] as light as possible so that themers can easily get their starterkit themes up-to-date on a new core version by effectively downloading a zip folder of SVGs, swapping ".png" for ".svg" in their theme CSS and done.

Point 3c feels like it could expand beyond just these images. Do we have a place where we’re tracking the various starterkit/theme update notes for an eventual CR? If not, I’m wondering if this becomes a D12 follow-up task — potentially driven by `git log` on the starterkit directory to collect the D11 lifecycle changes.

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.