generated from gitea_admin/default
296 lines
7.8 KiB
Vue
296 lines
7.8 KiB
Vue
<template>
|
|
<div>
|
|
<!-- ================== -->
|
|
<!-- Fond noir -->
|
|
<!-- ================== -->
|
|
<PageSection tone="dark" content-size="default" class="theme_bandeau--grid">
|
|
<SectionContent pad="xs" class="theme_bandeau--grid--left">
|
|
<SectionTitle tone="invert" pad="">
|
|
LES MUSICIENS
|
|
</SectionTitle>
|
|
<DsHeading as="h3" tone="invert">
|
|
|
|
</DsHeading>
|
|
</SectionContent>
|
|
|
|
|
|
<SectionContent pad="xs" class="theme_bandeau--grid--right">
|
|
<DsText tone="invert" size="lg" class="theme_bandeau--grid--right--text" >
|
|
Les 95 musiciennes et musiciens proposent chaque saison plus de 120 concerts dans des salles et théâtres, des lieux culturels et des espaces atypiques de la région francilienne.
|
|
</DsText>
|
|
</SectionContent>
|
|
</PageSection>
|
|
|
|
<!-- ================== -->
|
|
<!-- Listes des musiciens -->
|
|
<!-- ================== -->
|
|
|
|
<PageSection padded_size="md" content-size="default" class="musiciens_list_section remonter_artistes_list">
|
|
<section v-if="pending" aria-busy="true" aria-live="polite">
|
|
<DsText as="p" tone="default">Chargement des artistes...</DsText>
|
|
</section>
|
|
|
|
<section v-else-if="error">
|
|
<DsText as="p" tone="default">Impossible de charger les artistes.</DsText>
|
|
</section>
|
|
|
|
<section v-else-if="artistesDirection.length" class="musiciens_list">
|
|
<article v-for="a in artistesDirection" :key="a.id" class="musicien_card">
|
|
<DsMedia
|
|
v-if="a.image?.url"
|
|
:src="a.image.url"
|
|
:alt="a.image.alternativeText || a.nom_artiste_ondif || ''"
|
|
ratio="square"
|
|
/>
|
|
<div v-else class="musicien_card_media-placeholder" aria-hidden="true" />
|
|
|
|
<DsHeading as="h4" tone="default" class="musicien_card_nom">
|
|
<NuxtLink :to="`/orchestre/artiste-${a.slug_artiste_ondif}?from=musiciens`">
|
|
{{ a.nom_artiste_ondif }}
|
|
</NuxtLink>
|
|
</DsHeading>
|
|
|
|
<DsText
|
|
v-if="a.postesLabel"
|
|
as="p"
|
|
tone="default"
|
|
size="md"
|
|
class="musicien_card_postes"
|
|
>
|
|
{{ a.postesLabel }}
|
|
</DsText>
|
|
</article>
|
|
|
|
<!-- ICI ON MET À LA SUITE LES MUSICIENS DE L'ORCHESTRE -->
|
|
<article v-for="a in artistesAutres" :key="a.id" class="musicien_card">
|
|
<DsMedia
|
|
v-if="a.image?.url"
|
|
:src="a.image.url"
|
|
:alt="a.image.alternativeText || a.nom_artiste_ondif || ''"
|
|
ratio="square"
|
|
/>
|
|
<div v-else class="musicien_card_media-placeholder" aria-hidden="true" />
|
|
|
|
<DsHeading as="h4" tone="default" class="musicien_card_nom">
|
|
<NuxtLink :to="`/orchestre/artiste-${a.slug_artiste_ondif}?from=musiciens`">
|
|
{{ a.nom_artiste_ondif }}
|
|
</NuxtLink>
|
|
</DsHeading>
|
|
|
|
<DsText
|
|
v-if="a.postesLabel"
|
|
as="p"
|
|
tone="default"
|
|
size="md"
|
|
class="musicien_card_postes"
|
|
>
|
|
{{ a.postesLabel }}
|
|
</DsText>
|
|
</article>
|
|
</section>
|
|
|
|
<section v-else>
|
|
<DsText as="p" tone="default">Aucun artiste pour la direction.</DsText>
|
|
</section>
|
|
</PageSection>
|
|
|
|
|
|
|
|
|
|
</div>
|
|
</template>
|
|
|
|
<script setup>
|
|
import DsHeading from '@root/design-system/primitives/DsHeading.vue'
|
|
import DsText from '@root/design-system/primitives/DsText.vue'
|
|
import DsMedia from '@root/design-system/primitives/DsMedia.vue'
|
|
const runtimeConfig = useRuntimeConfig()
|
|
const saisonFiltre = computed(() => String(runtimeConfig.public.saison || '').trim())
|
|
// Filtre non utilisé
|
|
const artistesFilters = computed(() => {
|
|
if (!saisonFiltre.value) return null
|
|
return {
|
|
saisons_artiste_ondif: {
|
|
nom_saison: {
|
|
$eq: saisonFiltre.value,
|
|
},
|
|
},
|
|
}
|
|
})
|
|
|
|
//--------------------
|
|
// DONNÉES POUR LES ARTISTES
|
|
//--------------------
|
|
const { items: artistes, pending, error } = useStrapi(
|
|
"/api/__strapi__/artistes",
|
|
{
|
|
locale: "fr-FR",
|
|
sort: "ordre_artiste_ondif:asc",
|
|
pageSize: 200,
|
|
populate: {
|
|
image_illustration_artiste_ondif: true,
|
|
postes_artiste_ondif: true,
|
|
},
|
|
}
|
|
)
|
|
|
|
const artistesDisplay = computed(() => {
|
|
return (artistes.value || []).map((artiste) => ({
|
|
...artiste,
|
|
image: getArtisteImage(artiste),
|
|
postesLabel: getPostesLabel(artiste),
|
|
}))
|
|
})
|
|
|
|
const postesDirection = [
|
|
"direction",
|
|
"cheffe assistante",
|
|
"chef assistante",
|
|
]
|
|
|
|
const artistesDirection = computed(() =>
|
|
artistesDisplay.value.filter((a) => isDirectionArtist(a))
|
|
)
|
|
|
|
const artistesAutres = computed(() =>
|
|
artistesDisplay.value.filter((a) => !isDirectionArtist(a))
|
|
)
|
|
|
|
function getArtisteImage(artiste) {
|
|
const media = artiste?.image_illustration_artiste_ondif
|
|
const rows = extractStrapiList(media)
|
|
if (rows.length) return rows[0]
|
|
if (media && typeof media === "object" && media.url) return media
|
|
return null
|
|
}
|
|
|
|
function getPostesLabel(artiste) {
|
|
const postes = extractStrapiList(artiste?.postes_artiste_ondif)
|
|
return postes
|
|
.map((p) => p?.nom_poste)
|
|
.filter(Boolean)
|
|
.join(", ")
|
|
}
|
|
|
|
function isDirectionArtist(artiste) {
|
|
const postes = extractStrapiList(artiste?.postes_artiste_ondif)
|
|
.map((p) => String(p?.nom_poste || "").trim().toLowerCase())
|
|
.filter(Boolean)
|
|
|
|
return postes.some((poste) => postesDirection.includes(poste))
|
|
}
|
|
|
|
function extractStrapiList(value) {
|
|
if (!value) return []
|
|
if (Array.isArray(value)) return value.map(normalizeStrapiItem).filter(Boolean)
|
|
if (value?.data) {
|
|
const rows = Array.isArray(value.data) ? value.data : [value.data]
|
|
return rows.map(normalizeStrapiItem).filter(Boolean)
|
|
}
|
|
if (typeof value === "object") return [normalizeStrapiItem(value)].filter(Boolean)
|
|
return []
|
|
}
|
|
|
|
function normalizeStrapiItem(item) {
|
|
if (!item || typeof item !== "object") return null
|
|
if (item.attributes && typeof item.attributes === "object") {
|
|
return { id: item.id, ...item.attributes }
|
|
}
|
|
return item
|
|
}
|
|
|
|
|
|
</script>
|
|
|
|
<style lang="scss">
|
|
|
|
|
|
.remonter_artistes_list {
|
|
transform: translateY(-90px);
|
|
}
|
|
|
|
.theme_bandeau--grid {
|
|
> .page-section--inner {
|
|
padding-top: 70px;
|
|
padding-bottom: 90px;
|
|
display: flex;
|
|
flex-wrap: wrap;
|
|
column-gap: 120px;
|
|
row-gap: 0px;
|
|
}
|
|
&--left {
|
|
max-width: 40%;
|
|
h1 {
|
|
padding-bottom: 0px;
|
|
}
|
|
}
|
|
&--right {
|
|
max-width: 60%;
|
|
&--text {
|
|
max-width: 500px;
|
|
}
|
|
}
|
|
}
|
|
|
|
.musiciens_list_wp {
|
|
// parce que le bloc du dessus à un transform: translateY(-170px); alors cela laisse un espace vide que l'on comble avec ce margin-top négatif
|
|
margin-top: -120px;
|
|
}
|
|
.musiciens_list {
|
|
display: grid;
|
|
grid-template-columns: repeat(3, minmax(0, 1fr));
|
|
gap: 28px;
|
|
}
|
|
|
|
.musicien_card {
|
|
display: flex;
|
|
flex-direction: column;
|
|
gap: 10px;
|
|
}
|
|
|
|
.musicien_card_media-placeholder {
|
|
width: 100%;
|
|
aspect-ratio: 1 / 1;
|
|
background: rgba(0, 0, 0, 0.04);
|
|
}
|
|
|
|
.musicien_card_nom {
|
|
margin-top: 8px;
|
|
margin-left: 5px;
|
|
&:hover {
|
|
color: var(--c-brand_rouge);
|
|
}
|
|
}
|
|
.musicien_card_postes {
|
|
margin-left: 5px;
|
|
text-transform: lowercase;
|
|
&::first-letter {
|
|
text-transform: uppercase;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
@media (max-width: 980px) {
|
|
.musiciens_list {
|
|
grid-template-columns: repeat(2, minmax(0, 1fr));
|
|
}
|
|
}
|
|
|
|
@media (max-width: 400px) {
|
|
.musiciens_list {
|
|
grid-template-columns: 1fr;
|
|
padding-left: 5px;
|
|
padding-right: 5px;
|
|
}
|
|
}
|
|
|
|
@media (max-width: 600px) {
|
|
.musiciens_list {
|
|
padding-left: 5px;
|
|
padding-right: 5px;
|
|
}
|
|
}
|
|
|
|
</style>
|