<template> <ul class="clips nolist"> <li v-for="clip in clips" :key="`clip-${clip.id}`" class="clip" > <div class="clip-poster-container"> <a v-if="clip.poster" :href="`/media/${clip.poster.path}`" target="_blank" rel="noopener noreferrer" > <img :src="`/media/${clip.poster.thumbnail}`" class="clip-poster" > </a> <span v-if="clip.duration" class="clip-duration" >{{ formatDuration(clip.duration) }}</span> </div> <div class="clip-info"> <h3 v-if="clip.title" class="clip-row clip-title" :title="clip.title" >{{ clip.title }}</h3> <p class="clip-row clip-description">{{ clip.description }}</p> <Tags :tags="clip.tags" class="clip-row clip-tags" /> </div> </li> </ul> </template> <script> import Tags from './tags.vue'; export default { components: { Tags, }, props: { clips: { type: Array, default: () => [], }, }, }; </script> <style lang="scss" scoped> @import 'breakpoints'; .clips { display: grid; grid-template-columns: repeat(auto-fill, minmax(15rem, 1fr)); grid-gap: 1rem; } .clip { background: var(--background); box-shadow: 0 0 3px var(--shadow-weak); margin: 0 0 .5rem 0; } .clip-poster-container { position: relative; margin: 0 0 1rem 0; } .clip-poster { width: 100%; height: 10rem; object-fit: cover; object-position: center; } .clip-duration { background: var(--darken); color: var(--text-light); display: block; position: absolute; top: 0; right: 0; padding: .25rem .5rem; font-size: .9rem; font-weight: bold; text-shadow: 0 0 2px var(--darken-strong); } .clip-info { padding: 0 1rem; } .clip-row { margin: 0 0 .75rem 0; } .clip-title { padding: 0; font-size: 1rem; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; } .clip-description { line-height: 1.5; } @media(max-width: $breakpoint-micro) { .clips { grid-template-columns: repeat(auto-fill, minmax(12rem, 1fr)); } } </style>