| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144 |
- <template>
- <article class="event-card">
- <button
- type="button"
- class="event-header"
- :aria-expanded="isOpen"
- @click="isOpen = !isOpen"
- >
- <div class="min-w-0 flex-1 text-left">
- <span class="event-badge">
- <i :class="`mdi ${typeIcon}`" style="font-size: 0.875rem;"/>
- {{ eventTypeLabel(event.type) }}
- </span>
- <h3 class="text-subtitle-1 font-semibold text-text mt-2 mb-1 truncate">
- {{ event.title }}
- </h3>
- <p v-if="dateTimeLabel" class="text-body-2 text-text-2">
- {{ dateTimeLabel }}
- </p>
- </div>
- <span
- class="material-icons text-violet-normal shrink-0 transition-transform duration-300"
- :class="{ 'rotate-180': isOpen }"
- >
- expand_more
- </span>
- </button>
- <div class="event-body" :class="isOpen ? 'grid-rows-[1fr]' : 'grid-rows-[0fr]'">
- <div class="overflow-hidden">
- <div class="px-6 pb-6 pt-1">
- <img
- v-if="event.cover_url"
- :src="event.cover_url"
- :alt="event.title"
- class="event-cover"
- :class="{ 'mb-5': paragraphs.length }"
- loading="lazy"
- >
- <p
- v-for="(paragraph, index) in paragraphs"
- :key="index"
- lang="pt-BR"
- class="text-body-2 text-text-2 text-justify hyphens-auto event-text"
- :class="{ 'mt-3': index > 0 }"
- >
- {{ paragraph }}
- </p>
- <EventCarousel
- v-if="photos.length"
- :photos="photos"
- class="mt-4"
- />
- </div>
- </div>
- </div>
- </article>
- </template>
- <script setup lang="ts">
- import type { CompanyEvent } from '~/composables/useEvents'
- const { event } = defineProps<{ event: CompanyEvent }>()
- const isOpen = ref(true)
- const typeIcon = computed(() => (event.type === 'esporte' ? 'mdi-soccer' : 'mdi-palette-outline'))
- const dateTimeLabel = computed(() => formatEventDateTime(event))
- const photos = computed(() => (event.media ?? []).filter((photo) => !!photo.url))
- const paragraphs = computed(() =>
- (event.description ?? '')
- .split(/\r?\n/)
- .map((line) => line.trim())
- .filter(Boolean)
- )
- </script>
- <style scoped>
- .event-card {
- background-color: #ffffff;
- border-radius: 1rem;
- box-shadow: 0 4px 24px rgba(102, 29, 117, 0.14);
- transition: box-shadow 0.2s;
- overflow: hidden;
- height: 100%;
- }
- .event-card:hover {
- box-shadow: 0 8px 36px rgba(102, 29, 117, 0.22);
- }
- .event-header {
- display: flex;
- align-items: center;
- gap: 1rem;
- width: 100%;
- padding: 1.25rem 1.5rem;
- cursor: pointer;
- text-align: left;
- }
- .event-badge {
- display: inline-flex;
- align-items: center;
- gap: 0.25rem;
- background-color: #f0e8f1;
- color: #661d75;
- font-family: "Nunito", sans-serif;
- font-size: 0.6875rem;
- font-weight: 600;
- letter-spacing: 0.5px;
- text-transform: uppercase;
- padding: 0.125rem 0.5rem;
- border-radius: 9999px;
- }
- .event-body {
- display: grid;
- transition: grid-template-rows 0.35s ease;
- }
- .event-text {
- line-height: 1.7;
- }
- .event-cover {
- width: 100%;
- height: 240px;
- object-fit: cover;
- border-radius: 0.75rem;
- display: block;
- }
- @media (min-width: 1024px) {
- .event-cover {
- height: 280px;
- }
- }
- </style>
|