pinafore/src/routes/_components/status/StatusCard.html
Vincent 852a8582fb fix: Add the non-truncated text in the title attribute (#1598)
The `.card-title` element carries `text-overflow: ellipsis`, (and
`white-space: nowrap`), resulting in the last part of long article
titles not being visible. By adding it to the `title` attribute,
one can see the full title on hovering without having to visit the
article first.

The main concern I had was that the text is now technically
duplicated in the source code, and for short titles, also in the
UI. The primary concern there, however, was screen reader users
getting duplicate announcements. However, I believe the title
attribute is not announced by screen readers, which this (old)
article seems to confirm:
https://developer.paciellogroup.com/blog/2010/11/using-the-html-title-attribute/

That leaves the following two disadvantages:
- This doesn't solve anything for mobile users, who will still
  have to follow the link to see the full title.
- Desktop users can however a (non-truncated) title to see the same
  title again.
2019-10-23 21:54:57 -07:00

116 lines
2.6 KiB
HTML

<a ref:cardlink href={url} class="status-card" target="_blank" rel="noopener noreferrer">
<strong class="card-title" title={unescapedTitle}>
{unescapedTitle}
</strong>
{#if description}
<div class="card-content">
{#if imageUrl}
<div class="status-card-image-container">
<LazyImage src={imageUrl} ariaHidden={true} />
</div>
{/if}
<span class="card-description">
{unescapedDescription}
</span>
</div>
{/if}
{#if enableShortcuts}
<Shortcut scope={shortcutScope} key="l" on:pressed="open(url)" />
{/if}
</a>
<style>
.status-card {
grid-area: card;
display: flex;
flex-direction: column;
padding: 15px;
text-decoration: none;
color: inherit;
overflow: hidden;
margin: 10px 10px 10px 5px;
border: 1px solid var(--settings-list-item-border);
background: var(--settings-list-item-bg-hover);
border-radius: 6px;
}
.status-card:hover {
background: transparent;
}
.status-card :first-child:not(span) {
flex-shrink: 0;
}
.card-content {
display: flex;
align-items: center;
margin-top: 5px;
opacity: 0.8;
}
.status-card-image-container {
position: relative;
width: 50px;
height: 50px;
}
:global(.status-card-image-container img) {
object-fit: cover;
}
.card-title {
font-weight: 600;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
width: 100%;
display: inline-block;
opacity: 0.8;
}
.card-description {
font-size: small;
line-height: 1.4;
max-height: 5.6em; /* 4 * line-height */
overflow: hidden;
}
.card-description:not(:first-child) {
margin-left: 15px;
}
</style>
<script>
import LazyImage from '../LazyImage.html'
import Shortcut from '../shortcut/Shortcut.html'
import { unescape } from '../../_thirdparty/unescape/unescape'
export default {
components: {
Shortcut,
LazyImage
},
computed: {
card: ({ originalStatus }) => originalStatus.card,
title: ({ card }) => card.title,
unescapedTitle: ({ title }) => title && unescape(title),
url: ({ card }) => card.url,
hostname: ({ url }) => window.URL ? new window.URL(url).hostname : '',
description: ({ card, hostname }) => card.description || card.provider_name || hostname,
unescapedDescription: ({ description }) => description && unescape(description),
imageUrl: ({ card }) => card.image
},
methods: {
open () {
if (this.refs.cardlink) {
this.refs.cardlink.click()
}
}
}
}
</script>