connected to new url param
This commit is contained in:
@@ -2,62 +2,44 @@
|
|||||||
// imports
|
// imports
|
||||||
|
|
||||||
import useGetResellersCategories from "~/composables/api/resellers/useGetResellersCategories";
|
import useGetResellersCategories from "~/composables/api/resellers/useGetResellersCategories";
|
||||||
import useGetResellersProducts, {
|
import useGetResellersProducts from "~/composables/api/resellers/useGetResellersProducts";
|
||||||
type GetResellersProductsFilters,
|
import { useAppParams } from "~/composables/global/useAppParams";
|
||||||
} from "~/composables/api/resellers/useGetResellersProducts";
|
import { PRODUCT_RANGE, PRODUCTS_SORTS } from "~/constants";
|
||||||
import { PRODUCT_RANGE } from "~/constants";
|
|
||||||
|
|
||||||
// state
|
// state
|
||||||
|
|
||||||
const route = useRoute();
|
const route = useRoute();
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
|
|
||||||
const params = inject("params") as GetResellersProductsFilters;
|
const { sort, in_stock, has_discount, price_gte, price_lte, search, page, slug } = useAppParams();
|
||||||
|
|
||||||
|
const isSideShow = useState("side-modal-resellers-product-filters");
|
||||||
|
|
||||||
const currentCategory = computed({
|
const currentCategory = computed({
|
||||||
get: () => {
|
get: () => {
|
||||||
return Array.isArray(route.params.slug) ? route.params.slug[1] ?? undefined : undefined;
|
return Array.isArray(slug.value) ? slug.value[1] ?? undefined : undefined;
|
||||||
},
|
},
|
||||||
set: (newValue) => {
|
set: (newValue) => {
|
||||||
router.push({ path: `/resellers/category/${newValue}`, query: { ...route.query } });
|
isSideShow.value = false;
|
||||||
|
router.push({
|
||||||
|
name: "resellers-slug",
|
||||||
|
params: { slug: ["category", `${newValue}`] },
|
||||||
|
query: { ...route.query },
|
||||||
|
});
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
const sort_filter = ref([
|
const sliderValue = ref([price_gte.value ?? PRODUCT_RANGE.min, price_lte.value ?? PRODUCT_RANGE.max]);
|
||||||
{ title: "جدیدترین ها", value: "newest" },
|
|
||||||
{ title: "گران ترین ها", value: "price" },
|
|
||||||
{ title: "ارزان ترین ها", value: "-price" },
|
|
||||||
]);
|
|
||||||
|
|
||||||
const sliderValue = ref([params.price_gte ?? PRODUCT_RANGE.min, params.price_lte ?? PRODUCT_RANGE.max]);
|
|
||||||
|
|
||||||
const has_discount = ref(Boolean(params.has_discount) ?? false);
|
|
||||||
const in_stock = ref(Boolean(params.in_stock) ?? false);
|
|
||||||
|
|
||||||
const sliderValueDebounced = refDebounced(sliderValue, 1000);
|
const sliderValueDebounced = refDebounced(sliderValue, 1000);
|
||||||
|
|
||||||
const filtersSuccessMessage = ref<{ title: string; status: string } | null>(null);
|
|
||||||
|
|
||||||
// queries
|
// queries
|
||||||
|
|
||||||
const filters = computed(() => {
|
|
||||||
return {
|
|
||||||
sort: params.sort ?? "newest",
|
|
||||||
search: params.search ?? "",
|
|
||||||
price_gte: params.price_gte ?? PRODUCT_RANGE.min,
|
|
||||||
price_lte: params.price_lte ?? PRODUCT_RANGE.max,
|
|
||||||
in_stock: params.in_stock ?? false,
|
|
||||||
has_discount: params.has_discount ?? false,
|
|
||||||
category: currentCategory.value,
|
|
||||||
page: params.page ?? 1,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
const { data: categories, suspense } = useGetResellersCategories();
|
const { data: categories, suspense } = useGetResellersCategories();
|
||||||
|
|
||||||
await suspense();
|
await suspense();
|
||||||
|
|
||||||
const { isPending: productsIsPending, status: productsStatus } = useGetResellersProducts(filters);
|
const { isPending: productsIsPending } = useGetResellersProducts();
|
||||||
|
|
||||||
// computed
|
// computed
|
||||||
|
|
||||||
@@ -70,48 +52,23 @@ const allCategories = computed(() => {
|
|||||||
// methods
|
// methods
|
||||||
|
|
||||||
const resetFilters = () => {
|
const resetFilters = () => {
|
||||||
params.search = "";
|
search.value = "";
|
||||||
params.sort = "";
|
sort.value = "";
|
||||||
sliderValue.value = [PRODUCT_RANGE.min, PRODUCT_RANGE.max];
|
sliderValue.value = [PRODUCT_RANGE.min, PRODUCT_RANGE.max];
|
||||||
has_discount.value = false;
|
has_discount.value = "false";
|
||||||
in_stock.value = false;
|
in_stock.value = "false";
|
||||||
|
page.value = 1;
|
||||||
|
|
||||||
router.push({ path: `/resellers/`, query: { ...route.query } });
|
isSideShow.value = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// watch
|
||||||
|
|
||||||
watch(
|
watch(
|
||||||
() => sliderValueDebounced.value,
|
() => sliderValueDebounced.value,
|
||||||
(newValue) => {
|
(newValue) => {
|
||||||
params.price_gte = newValue[0];
|
price_gte.value = newValue[0];
|
||||||
params.price_lte = newValue[1];
|
price_lte.value = newValue[1];
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
watch(
|
|
||||||
() => [has_discount.value, in_stock.value],
|
|
||||||
([newHasDiscount, newInStock]) => {
|
|
||||||
params.has_discount = newHasDiscount;
|
|
||||||
params.in_stock = newInStock;
|
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
watch(
|
|
||||||
() => productsStatus.value,
|
|
||||||
(nv) => {
|
|
||||||
if (nv == "success") {
|
|
||||||
filtersSuccessMessage.value = {
|
|
||||||
title: "فیلتر اعمال شد",
|
|
||||||
status: nv,
|
|
||||||
};
|
|
||||||
} else if (nv == "error") {
|
|
||||||
filtersSuccessMessage.value = {
|
|
||||||
title: "خطایی در اعمال فیلتر رخ داد",
|
|
||||||
status: nv,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
setTimeout(() => {
|
|
||||||
filtersSuccessMessage.value = null;
|
|
||||||
}, 4000);
|
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
</script>
|
</script>
|
||||||
@@ -129,13 +86,13 @@ watch(
|
|||||||
</div>
|
</div>
|
||||||
<div class="w-full flex items-center gap-2">
|
<div class="w-full flex items-center gap-2">
|
||||||
<button
|
<button
|
||||||
v-for="(sort, index) in sort_filter"
|
v-for="(sort_filter, index) in PRODUCTS_SORTS"
|
||||||
:key="index"
|
:key="index"
|
||||||
@click="params.sort = sort.value"
|
@click="sort = sort_filter.value"
|
||||||
:class="params.sort == sort.value ? 'bg-black text-white' : 'bg-slate-100'"
|
:class="sort == sort_filter.value ? 'bg-black text-white' : 'bg-slate-100'"
|
||||||
class="py-1 px-3 cursor-pointer text-nowrap transition-all rounded-md text-xs lg:text-sm"
|
class="py-1 px-3 cursor-pointer text-nowrap transition-all rounded-md text-xs lg:text-sm"
|
||||||
>
|
>
|
||||||
{{ sort.title }}
|
{{ sort_filter.title }}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -209,32 +166,31 @@ watch(
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="w-full flex flex-col items-center gap-5">
|
<div class="flex items-center gap-4 w-full">
|
||||||
|
<Button
|
||||||
|
:disabled="productsIsPending"
|
||||||
|
variant="primary"
|
||||||
|
@click="isSideShow = false"
|
||||||
|
class="w-full rounded-xl py-3 !cursor-pointer disabled:pointer-events-none z-[3]"
|
||||||
|
>
|
||||||
<Transition
|
<Transition
|
||||||
enter-active-class="animate__animated animate__fadeInUp animate__faster"
|
name="fade"
|
||||||
leave-active-class="animate__animated animate__fadeOutDown animate__faster"
|
mode="out-in"
|
||||||
>
|
>
|
||||||
<div
|
<span class="flex-center gap-3 text-sm">
|
||||||
v-if="!!filtersSuccessMessage"
|
اعمال فیلتر
|
||||||
class="w-max rounded-full py-1.5 px-3 text-xs border flex-center gap-0.5 z-[2]"
|
|
||||||
:class="
|
|
||||||
filtersSuccessMessage.status == 'success'
|
|
||||||
? 'text-success-600 bg-success-100 border-success-600'
|
|
||||||
: ' text-danger-600 bg-danger-100 border-danger-600'
|
|
||||||
"
|
|
||||||
>
|
|
||||||
<span class="text-sm">{{ filtersSuccessMessage.title }}</span>
|
|
||||||
<Icon
|
<Icon
|
||||||
:name="filtersSuccessMessage.status == 'success' ? 'bi:check' : 'bi:x'"
|
name="ci:plus"
|
||||||
size="20"
|
size="20"
|
||||||
/>
|
/>
|
||||||
</div>
|
</span>
|
||||||
</Transition>
|
</Transition>
|
||||||
|
</Button>
|
||||||
<Button
|
<Button
|
||||||
:disabled="productsIsPending"
|
:disabled="productsIsPending"
|
||||||
variant="solid"
|
variant="solid"
|
||||||
@click="resetFilters"
|
@click="resetFilters"
|
||||||
class="w-full rounded-full py-4 !cursor-pointer disabled:pointer-events-none z-[3]"
|
class="w-full rounded-xl py-3 !cursor-pointer disabled:pointer-events-none z-[3]"
|
||||||
>
|
>
|
||||||
<Transition
|
<Transition
|
||||||
name="fade"
|
name="fade"
|
||||||
@@ -242,7 +198,7 @@ watch(
|
|||||||
>
|
>
|
||||||
<span
|
<span
|
||||||
v-if="productsIsPending"
|
v-if="productsIsPending"
|
||||||
class="flex-center gap-3"
|
class="flex-center gap-3 text-sm"
|
||||||
>
|
>
|
||||||
در حال دریافت اطلاعات
|
در حال دریافت اطلاعات
|
||||||
<Icon
|
<Icon
|
||||||
@@ -252,7 +208,7 @@ watch(
|
|||||||
</span>
|
</span>
|
||||||
<span
|
<span
|
||||||
v-else
|
v-else
|
||||||
class="flex-center gap-3"
|
class="flex-center gap-3 text-sm"
|
||||||
>
|
>
|
||||||
بازنشانی به پیش فرض
|
بازنشانی به پیش فرض
|
||||||
<Icon
|
<Icon
|
||||||
|
|||||||
Reference in New Issue
Block a user