132 lines
5 KiB
Vue
132 lines
5 KiB
Vue
<template>
|
|
<header class="flex">
|
|
<h2 id="tabslist" class="sr-only">Projets</h2>
|
|
<Tabs :tabs="tabs" @update:currentTab="changeTab" />
|
|
</header>
|
|
<section
|
|
v-if="currentTab === 'currentProjects'"
|
|
id="projets-en-cours"
|
|
role="tabpanel"
|
|
tabindex="0"
|
|
:aria-label="tabs[0].label"
|
|
class="flow"
|
|
:class="{ skeleton: isProjectsLoading }"
|
|
>
|
|
<Project
|
|
v-for="project in currentProjects"
|
|
:key="project.id"
|
|
:project="project"
|
|
/>
|
|
</section>
|
|
<section
|
|
v-else
|
|
id="projets-archives"
|
|
role="tabpanel"
|
|
tabindex="0"
|
|
:aria-label="tabs[1].label"
|
|
class="flow"
|
|
>
|
|
<Project
|
|
v-for="project in archivedProjects"
|
|
:key="project.id"
|
|
:project="project"
|
|
/>
|
|
</section>
|
|
</template>
|
|
<script setup>
|
|
import Tabs from './Tabs.vue';
|
|
import Project from './project/Project.vue';
|
|
import { useProjectsStore } from '../stores/projects';
|
|
import { ref, computed } from 'vue';
|
|
import { storeToRefs } from 'pinia';
|
|
|
|
const { projects, currentProjects, archivedProjects, isProjectsLoading } =
|
|
storeToRefs(useProjectsStore());
|
|
|
|
const currentTab = ref('currentProjects');
|
|
const tabs = computed(() => {
|
|
return [
|
|
{
|
|
label: 'Projets en cours',
|
|
id: 'currentProjects',
|
|
count: currentProjects.value.length,
|
|
isActive: currentTab.value === 'currentProjects',
|
|
},
|
|
{
|
|
label: 'Projets archivés',
|
|
id: 'archivedProjects',
|
|
count: archivedProjects.value.length,
|
|
isActive: currentTab.value === 'archivedProjects',
|
|
},
|
|
];
|
|
});
|
|
|
|
function changeTab(newValue) {
|
|
currentTab.value = newValue;
|
|
}
|
|
</script>
|
|
|
|
<style scoped>
|
|
section {
|
|
--flow-space: var(--space-16);
|
|
min-height: calc(100vh - 8.5rem);
|
|
}
|
|
section:empty::after,
|
|
section.loading::after {
|
|
content: 'Aucun projet pour le moment';
|
|
position: absolute;
|
|
inset: 0;
|
|
display: grid;
|
|
place-items: center;
|
|
text-align: center;
|
|
max-width: 24ch;
|
|
height: 8rem;
|
|
margin: auto;
|
|
font-size: var(--text-sm);
|
|
color: var(--color-grey-700);
|
|
background-image: var(--icon-document-thin);
|
|
background-position: top center;
|
|
background-repeat: no-repeat;
|
|
background-size: var(--space-40);
|
|
}
|
|
section.loading::after {
|
|
content: 'Chargement des projets…';
|
|
}
|
|
/* Skeleton */
|
|
section.skeleton::before,
|
|
section.skeleton::after {
|
|
content: '';
|
|
display: block;
|
|
width: 100%;
|
|
height: 100%;
|
|
max-width: 100%;
|
|
margin: 0;
|
|
background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 1080 260' xmlns='http://www.w3.org/2000/svg'%3E%3Crect fill='white' x='0' y='0' width='100%25' height='244' rx='20' ry='20' /%3E%3Crect fill='%23F2F2F2' x='32' y='34' width='72' height='72' rx='4' ry='4' /%3E%3Crect fill='%23F2F2F2' x='136' y='40' width='240' height='26' rx='4' ry='4' /%3E%3Crect fill='%23F2F2F2' x='136' y='80' width='160' height='18' rx='4' ry='4' /%3E%3C/svg%3E%0A");
|
|
background-repeat: repeat-y;
|
|
background-size: 1080px 260px;
|
|
background-position-x: left;
|
|
mask-image: linear-gradient(to bottom, rgba(0, 0, 0, 1) 50%, rgba(0, 0, 0, 0) 100%);
|
|
animation: skeleton 1s cubic-bezier(0.25, 1, 0.5, 1) infinite alternate;
|
|
}
|
|
section.skeleton::after {
|
|
background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 1080 260' xmlns='http://www.w3.org/2000/svg'%3E%3Cdefs%3E%3Cmask id='tr'%3E%3Crect width='100%25' height='100%25' fill='white'/%3E%3Ccircle r='20' cx='1060' cy='20' fill='black'/%3E%3C/mask%3E%3Cmask id='br'%3E%3Crect width='100%25' height='100%25' fill='white'/%3E%3Ccircle r='20' cx='1060' cy='224' fill='black'/%3E%3C/mask%3E%3C/defs%3E%3Crect fill='%23F2F2F2' x='1060' y='0' width='20' height='20' mask='url(%23tr)' /%3E%3Crect fill='%23F2F2F2' x='1060' y='224' width='20' height='20' mask='url(%23br)' /%3E%3C/svg%3E");
|
|
background-size: 1080px 260px;
|
|
background-position-x: right;
|
|
animation: none;
|
|
mask-image: none;
|
|
}
|
|
@media (min-width: 1530px) {
|
|
section.skeleton::before {
|
|
background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 3468 156' xmlns='http://www.w3.org/2000/svg'%3E%3Crect fill='white' x='0' y='0' width='100%25' height='140' rx='20' ry='20' /%3E%3Crect fill='%23F2F2F2' x='32' y='34' width='72' height='72' rx='4' ry='4' /%3E%3Crect fill='%23F2F2F2' x='136' y='40' width='240' height='26' rx='4' ry='4' /%3E%3Crect fill='%23F2F2F2' x='136' y='80' width='160' height='18' rx='4' ry='4' /%3E%3C/svg%3E%0A");
|
|
background-size: 3468px 156px;
|
|
}
|
|
section.skeleton::after {
|
|
background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 3468 156' xmlns='http://www.w3.org/2000/svg'%3E%3Cdefs%3E%3Cmask id='tr'%3E%3Crect width='100%25' height='100%25' fill='white'/%3E%3Ccircle r='20' cx='3448' cy='20' fill='black'/%3E%3C/mask%3E%3Cmask id='br'%3E%3Crect width='100%25' height='100%25' fill='white'/%3E%3Ccircle r='20' cx='3448' cy='120' fill='black'/%3E%3C/mask%3E%3C/defs%3E%3Crect fill='%23F2F2F2' x='3448' y='0' width='20' height='20' mask='url(%23tr)' /%3E%3Crect fill='%23F2F2F2' x='3448' y='120' width='20' height='20' mask='url(%23br)' /%3E%3C/svg%3E");
|
|
background-size: 3468px 156px;
|
|
}
|
|
}
|
|
@keyframes skeleton {
|
|
0% { opacity: .50 }
|
|
100% { opacity: 1.0 }
|
|
}
|
|
</style>
|