bookfarm-frontend/src/pages/BookDetails.vue

193 lines
4.5 KiB
Vue

<script setup lang="ts">
import {onMounted, ref, watch} from "vue";
import {useRouter} from "vue-router";
import Suggestion from "@/components/Suggestion.vue";
import {useBookStore} from "@/services/stores/bookStore";
import {storeToRefs} from "pinia";
const router = useRouter();
watch(() => router.currentRoute, () => {
console.log("watch", router.currentRoute.value.params.id)
bookStore.loadBook(router.currentRoute.value.params.id as string)
},)
const bookStore = useBookStore();
const {book, isLoading} = storeToRefs(bookStore)
onMounted(() => {
bookStore.loadBook(router.currentRoute.value.params.id as string);
})
const shouldShowReco = ref(false);
</script>
<template>
<v-fab
icon="mdi-arrow-left"
location="top left"
size="small"
class="back-button"
position="absolute"
:to="{name: 'search'}"
/>
<div class="book-details mt-4 mb-10 d-flex flex-column align-center">
<template v-if="isLoading">
<div
class="v-skeleton-loader"
>
<div
class="rounded-lg v-skeleton-loader__bone v-skeleton-loader__image"
style="height: 300px; width: 300px"
/>
</div>
<v-skeleton-loader
type="sentences"
width="100"
class="bg-transparent"
/>
<v-skeleton-loader
type="paragraph"
width="300"
class="bg-transparent"
/>
</template>
<template v-else>
<v-avatar
rounded="lg"
size="300"
>
<v-img
:src="book?.image_url ?? `https://cdn.vuetifyjs.com/images/cards/sunshine.jpg`"
/>
</v-avatar>
<div class="book-author-title d-flex flex-column align-center">
<p
v-if="book?.product_title"
class="text-primary font-weight-bold"
>
{{ book.product_title }}
</p>
<p
v-if="book?.author"
class="text-secondary font-weight-medium text-capitalize"
>
{{ book.author.split("_").join(" ") }}
</p>
</div>
<section
v-if="book?.resume"
class="ma-1"
>
<span class="text-decoration-underline text-primary font-weight-medium">Résumé</span>
<span class="book-summary">{{ book.resume }}</span>
</section>
<section class="ma-1 book-characteristics">
<span class="text-decoration-underline text-primary font-weight-medium">Caractéristiques</span>
<div>
<span class="charac">
<p class="font-weight-medium">Date de parution</p>
<p>{{ book?.date_de_parution }}</p>
</span>
<span class="charac">
<p class="font-weight-medium">Éditeur</p>
<p>{{ book?.editeur }}</p>
</span>
</div>
<div>
<span class="charac">
<p class="font-weight-medium">Collection</p>
<p>{{ book?.collection?.split("_").join(" ") }}</p>
</span>
<span class="charac">
<p class="font-weight-medium">Nombre de pages</p>
<p>{{ book?.nb_de_pages }}</p>
</span>
</div>
</section>
</template>
</div>
<v-card
class="recommandations"
:disabled="isLoading"
>
<v-slide-y-reverse-transition v-if="!isLoading">
<v-card v-show="shouldShowReco">
<Suggestion :book="book!"/>
</v-card>
</v-slide-y-reverse-transition>
<v-btn
width="100%"
@click="shouldShowReco = !shouldShowReco"
>
<div class="d-flex align-center">
<p>
{{ shouldShowReco ? "Cacher" : "Voir" }} les recommandations
</p>
<v-btn
size="x-small"
flat
:icon="shouldShowReco ? 'mdi-chevron-down' : 'mdi-chevron-up'"
/>
</div>
</v-btn>
</v-card>
</template>
<style scoped>
.book-details {
width: 300px;
margin-left: calc((100% - 300px) / 2);
}
.recommandations {
position: fixed;
bottom: 0;
width: 100%;
left: 0
}
section {
width: 100%;
display: flex;
flex-direction: column;
}
.book-summary {
width: 100%;
line-height: 1.2em;
max-height: 7em;
overflow: hidden;
display: -webkit-box;
-webkit-line-clamp: 7;
-webkit-box-orient: vertical;
}
.book-characteristics {
& .charac {
width: 100%;
height: 100%;
display: flex;
gap: 8px;
line-height: 1.2em;
margin-top: 4px;
& > p:first-child {
background-color: #DDE5B6;
}
}
}
.back-button {
height: fit-content !important;
width: 64px;
z-index: 1;
position: fixed;
margin-top: 8px;
}
</style>