CSS
.tng-asset-download wraps a <ul> of one or more downloadable assets, and each row carries .tng-asset-download-item. A row holds two children: the link that names the file, and the file size on a second line beneath it.
The link is a real Link: .is-neutral pins its rested colour, .is-md its type scale, and the underline, hover / active / visited colours and focus ring all come from the Link component. Wrap the filename in a <span> — that is the box .tng-overflow-ellipsis truncates. Only the file size stays outside the link, so it keeps its own colour and stays out of the link’s accessible name.
The trailing glyph goes inside the link, as the Link’s trailing icon. It needs no class of its own, and it takes the link’s colour and states for free. It is decorative — mark it aria-hidden="true".
Which glyph you draw follows what the row does, and every row draws one:
- Opens in a new tab —
target="_blank" rel="noopener noreferrer",icon-external-link, and a.sr-onlyspan so the new tab is announced. - Saves the file —
<a download>,icon-download, and nothing to announce.
In practice the file type picks between them: a PDF the browser can render opens in a new tab, everything else downloads. Both shapes sit in one list with no alignment work — the row hugs its content, so a shorter filename simply ends sooner.
<ul class="tng-asset-download" role="list"> <li class="tng-asset-download-item"> <a class="tng-link is-neutral is-md" href="#" target="_blank" rel="noopener noreferrer" > <span class="tng-overflow-ellipsis">Download brochure.pdf</span> <span class="sr-only">(opens in a new tab)</span> <i class="tng-icon icon-external-link" aria-hidden="true"></i> </a> <span class="tng-asset-download-meta">100 MB</span> </li> <li class="tng-asset-download-item"> <a class="tng-link is-neutral is-md" href="#" download> <span class="tng-overflow-ellipsis"> Download price list.jpg </span> <i class="tng-icon icon-download" aria-hidden="true"></i> </a> <span class="tng-asset-download-meta">12 MB</span> </li></ul>Everything clickable is in that one link, so a row is one tab stop.
The row is a native <a>, so the browser handles the outcome — keyboard activation, Open in New Tab and Save Link As all come for free. Don’t intercept the click with bespoke JavaScript download logic, and don’t script the new tab open with window.open; target="_blank" already does it and keeps the browser’s own controls working.
Elements
Section titled “Elements”Item without the list
Section titled “Item without the list”.tng-asset-download-item styles itself, so a row renders correctly outside .tng-asset-download. This exists for platforms that emit one asset per component instance and can’t wrap them in a shared list — it is not the supported shape, and Design and Accessibility document only the list.
What you give up is what the list owns: the dividers above and below each row, and the role="list" reset. Stacking these boxes doesn’t reassemble a list either — each container draws its own leading and trailing edge, so consecutive instances meet in a doubled seam you have to collapse in your own CSS. Use the <ul> whenever you can wrap the rows.
<div class="tng-asset-download-item"> <a class="tng-link is-neutral is-md" href="#" target="_blank" rel="noopener noreferrer" > <span class="tng-overflow-ellipsis">Download brochure.pdf</span> <span class="sr-only">(opens in a new tab)</span> <i class="tng-icon icon-external-link" aria-hidden="true"></i> </a> <span class="tng-asset-download-meta">100 MB</span></div>