feat(storefront): enhance category and product templates with HTML rendering

Updated catalog and product pages to render descriptions using HTML (`v-html`), allowing richer content presentation. Improved characteristics section for products, reintroducing previously commented-out functionality with refined structure and styling.

- Enabled `v-html` in `categorySlug.vue` and `slug.vue` for proper HTML display in descriptions.
- Restored and revamped characteristics section with better styling and layout.
- Adjusted SCSS for consistent typography and spacing in characteristics.

No breaking changes introduced—enhancements improve presentation and maintain code quality.
This commit is contained in:
Alexandr SaVBaD Waltz 2026-03-01 22:13:24 +03:00
parent e8e0675d7d
commit d4b2839502
2 changed files with 48 additions and 45 deletions

View file

@ -2,7 +2,7 @@
<div class="category"> <div class="category">
<ui-title> <ui-title>
<h1>{{ category?.name }}</h1> <h1>{{ category?.name }}</h1>
<p>{{ category?.description }}</p> <div v-html="category?.description" />
</ui-title> </ui-title>
<div class="category__main"> <div class="category__main">
<div class="container"> <div class="container">

View file

@ -38,7 +38,7 @@
/> />
<p class="product__main-price">{{ product?.price }} $</p> <p class="product__main-price">{{ product?.price }} $</p>
<p class="product__main-stock">{{ t('cards.product.stock') }} {{ product?.quantity }}</p> <p class="product__main-stock">{{ t('cards.product.stock') }} {{ product?.quantity }}</p>
<p class="product__main-description">{{ product?.description }}</p> <div class="product__main-description" v-html="product?.description" />
<div class="tools" v-if="isProductInCart"> <div class="tools" v-if="isProductInCart">
<button <button
class="tools__item tools__item-button" class="tools__item tools__item-button"
@ -100,30 +100,28 @@
</div> </div>
</div> </div>
</div> </div>
<!-- <client-only>--> <client-only>
<!-- <div class="characteristics" id="characteristics" v-if="attributes.length">--> <div class="characteristics" id="characteristics" v-if="attributes.length">
<!-- <div class="characteristics__wrapper">--> <h6 class="characteristics__title">{{ t('product.characteristics') }}</h6>
<!-- <h6 class="characteristics__title">{{ t('product.characteristics') }}</h6>--> <div class="characteristics__list">
<!-- <div class="characteristics__list">--> <div
<!-- <div--> class="characteristics__column"
<!-- class="characteristics__column"--> v-for="group in attributes"
<!-- v-for="group in attributes"--> :key="group.uuid"
<!-- :key="group.uuid"--> >
<!-- >--> <h6 class="characteristics__column-title">{{ group.name }}</h6>
<!-- <h6 class="characteristics__column-title">{{ group.name }}</h6>--> <p
<!-- <p--> class="characteristics__item"
<!-- class="characteristics__item"--> v-for="item in group.items"
<!-- v-for="item in group.items"--> :key="item.uuid"
<!-- :key="item.uuid"--> >
<!-- >--> <span class="characteristics__item-label"><span>{{ item.name }}</span></span>
<!-- <span class="characteristics__item-label"><span>{{ item.name }}</span></span>--> <span class="characteristics__item-value">{{ item.valuesStr }}</span>
<!-- <span class="characteristics__item-value">{{ item.valuesStr }}</span>--> </p>
<!-- </p>--> </div>
<!-- </div>--> </div>
<!-- </div>--> </div>
<!-- </div>--> </client-only>
<!-- </div>-->
<!-- </client-only>-->
<div class="similar"> <div class="similar">
<h6 class="similar__title">{{ t('product.similar') }}</h6> <h6 class="similar__title">{{ t('product.similar') }}</h6>
<div class="similar__inner"> <div class="similar__inner">
@ -569,27 +567,26 @@ watch(
} }
.characteristics { .characteristics {
padding-top: 100px; margin-top: 100px;
display: flex;
&__wrapper { flex-direction: column;
background-color: $main; gap: 25px;
border-radius: $less_border_radius; padding: 45px 25px;
box-shadow: 0 0 20px 2px rgba(0, 0, 0, 0.2); border-radius: $default_border_radius;
padding: 20px; border: 1px solid $border;
}
&__title { &__title {
padding-bottom: 10px; font-family: "Playfair Display", sans-serif;
border-bottom: 2px solid $primary_dark;
color: $primary_dark; color: $primary_dark;
font-size: 24px; font-size: 30px;
font-weight: 700; font-weight: 600;
letter-spacing: -0.5px;
} }
&__list { &__list {
margin-top: 20px; margin-top: 20px;
display: grid; display: grid;
grid-template-columns: repeat(auto-fit,minmax(100px, 30%)); grid-template-columns: repeat(auto-fit,minmax(30%, 30%));
gap: 40px; gap: 40px;
} }
@ -622,6 +619,11 @@ watch(
z-index: 1; z-index: 1;
background-color: $main; background-color: $main;
padding-bottom: 1px; padding-bottom: 1px;
color: $text;
font-size: 16px;
font-weight: 400;
letter-spacing: -0.5px;
} }
&::after { &::after {
@ -635,6 +637,11 @@ watch(
} }
&-value { &-value {
color: $primary_dark;
font-size: 16px;
font-weight: 500;
letter-spacing: -0.5px;
& span { & span {
&:first-child { &:first-child {
& span { & span {
@ -687,14 +694,10 @@ watch(
padding-inline: 10px; padding-inline: 10px;
aspect-ratio: 1; aspect-ratio: 1;
border-radius: 50%; border-radius: 50%;
background-color: $main; background-color: transparent;
@include hover { @include hover {
background-color: $main_hover; background-color: $link_secondary;
& span {
color: $main;
}
} }
& span { & span {