refactor: simplify DesignerPreview component by removing unused props and events
This commit is contained in:
@@ -1,138 +1,36 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
previewUrl: string | null;
|
|
||||||
templateLabel: string;
|
|
||||||
productionPixels: number;
|
|
||||||
isExporting: boolean;
|
|
||||||
isCheckoutPending: boolean;
|
isCheckoutPending: boolean;
|
||||||
checkoutPrice: number;
|
checkoutPrice: number;
|
||||||
checkoutError: string | null;
|
checkoutError: string | null;
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
const emit = defineEmits<{
|
const emit = defineEmits<{
|
||||||
(e: "download-preview"): void;
|
|
||||||
(e: "download-production"): void;
|
|
||||||
(e: "export"): void;
|
|
||||||
(e: "checkout"): void;
|
(e: "checkout"): void;
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
const viewMode = ref<"flat" | "turntable">("flat");
|
|
||||||
|
|
||||||
const isFlat = computed(() => viewMode.value === "flat");
|
|
||||||
|
|
||||||
const handleSelectView = (mode: "flat" | "turntable") => {
|
|
||||||
viewMode.value = mode;
|
|
||||||
};
|
|
||||||
|
|
||||||
const handleExport = () => emit("export");
|
|
||||||
const handleDownloadPreview = () => emit("download-preview");
|
|
||||||
const handleDownloadProduction = () => emit("download-production");
|
|
||||||
const handleCheckout = () => emit("checkout");
|
const handleCheckout = () => emit("checkout");
|
||||||
|
|
||||||
const priceLabel = computed(() => props.checkoutPrice.toFixed(2));
|
const priceLabel = computed(() => props.checkoutPrice.toFixed(2));
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<section class="rounded-2xl border border-slate-800/60 bg-slate-900/80 p-4 shadow-lg shadow-slate-950/40">
|
<section class="rounded-2xl border border-slate-800/60 bg-slate-900/80 p-6 shadow-lg shadow-slate-950/40">
|
||||||
<header class="flex items-center justify-between">
|
<div class="space-y-4">
|
||||||
<div>
|
|
||||||
<h3 class="text-sm font-semibold uppercase tracking-wide text-slate-400">
|
|
||||||
Output Preview
|
|
||||||
</h3>
|
|
||||||
<p class="mt-1 text-sm text-slate-300">
|
|
||||||
{{ templateLabel }} • {{ productionPixels }}×{{ productionPixels }} px
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
class="rounded-lg border border-sky-500/60 px-3 py-1 text-xs font-semibold uppercase tracking-wide text-sky-100 transition hover:bg-sky-500/10 disabled:cursor-not-allowed disabled:border-slate-600 disabled:text-slate-500"
|
class="w-full rounded-xl bg-emerald-500 px-6 py-4 text-base font-semibold text-emerald-950 transition hover:bg-emerald-400 disabled:cursor-not-allowed disabled:bg-emerald-500/60 disabled:text-emerald-900/60"
|
||||||
:disabled="props.isExporting"
|
:disabled="props.isCheckoutPending"
|
||||||
@click="handleExport"
|
|
||||||
>
|
|
||||||
{{ props.isExporting ? "Exporting…" : "Generate Files" }}
|
|
||||||
</button>
|
|
||||||
</header>
|
|
||||||
<div class="mt-4 flex gap-2">
|
|
||||||
<button
|
|
||||||
type="button"
|
|
||||||
class="flex-1 rounded-xl border px-3 py-2 text-xs font-semibold uppercase tracking-wide transition"
|
|
||||||
:class="isFlat ? 'border-sky-500 bg-sky-500/10 text-sky-200' : 'border-slate-800 bg-slate-900 text-slate-400 hover:border-slate-700/80 hover:text-slate-200'"
|
|
||||||
@click="handleSelectView('flat')"
|
|
||||||
>
|
|
||||||
Flat View
|
|
||||||
</button>
|
|
||||||
<button
|
|
||||||
type="button"
|
|
||||||
class="flex-1 rounded-xl border px-3 py-2 text-xs font-semibold uppercase tracking-wide transition"
|
|
||||||
:class="!isFlat ? 'border-sky-500 bg-sky-500/10 text-sky-200' : 'border-slate-800 bg-slate-900 text-slate-400 hover:border-slate-700/80 hover:text-slate-200'"
|
|
||||||
@click="handleSelectView('turntable')"
|
|
||||||
>
|
|
||||||
Turntable View
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
<div class="mt-4 aspect-square overflow-hidden rounded-2xl border border-slate-800 bg-slate-950">
|
|
||||||
<template v-if="props.previewUrl">
|
|
||||||
<div v-if="isFlat" class="h-full w-full">
|
|
||||||
<img
|
|
||||||
:src="props.previewUrl"
|
|
||||||
alt="Slipmat preview flat"
|
|
||||||
class="h-full w-full object-cover"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div v-else class="relative h-full w-full bg-linear-to-br from-slate-900 via-slate-950 to-black">
|
|
||||||
<img
|
|
||||||
src="/turntable-mockup.svg"
|
|
||||||
alt="Turntable illustration"
|
|
||||||
class="pointer-events-none h-full w-full object-contain"
|
|
||||||
/>
|
|
||||||
<div class="absolute left-[16%] top-[18%] h-[64%] w-[48%] -rotate-2 overflow-hidden rounded-full shadow-xl shadow-black/40">
|
|
||||||
<div class="absolute inset-0 bg-slate-900/40" />
|
|
||||||
<img
|
|
||||||
:src="props.previewUrl"
|
|
||||||
alt="Slipmat preview turntable"
|
|
||||||
class="h-full w-full object-cover opacity-95 mix-blend-screen"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
<div
|
|
||||||
v-else
|
|
||||||
class="flex h-full items-center justify-center text-sm text-slate-500"
|
|
||||||
>
|
|
||||||
No preview yet—start designing!
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="mt-4 flex flex-wrap gap-3">
|
|
||||||
<button
|
|
||||||
type="button"
|
|
||||||
class="flex-1 rounded-xl bg-slate-800 px-4 py-3 text-sm font-medium text-slate-100 transition hover:bg-slate-700 disabled:cursor-not-allowed disabled:bg-slate-800/70 disabled:text-slate-500"
|
|
||||||
:disabled="!props.previewUrl"
|
|
||||||
@click="handleDownloadPreview"
|
|
||||||
>
|
|
||||||
Download Web Preview
|
|
||||||
</button>
|
|
||||||
<button
|
|
||||||
type="button"
|
|
||||||
class="flex-1 rounded-xl bg-sky-600 px-4 py-3 text-sm font-medium text-white transition hover:bg-sky-500 disabled:cursor-not-allowed disabled:bg-slate-600/70"
|
|
||||||
:disabled="props.isExporting"
|
|
||||||
@click="handleDownloadProduction"
|
|
||||||
>
|
|
||||||
Download Print-Ready PNG
|
|
||||||
</button>
|
|
||||||
<button
|
|
||||||
type="button"
|
|
||||||
class="flex-1 rounded-xl bg-emerald-500 px-4 py-3 text-sm font-semibold text-emerald-950 transition hover:bg-emerald-400 disabled:cursor-not-allowed disabled:bg-emerald-500/60 disabled:text-emerald-900/60"
|
|
||||||
:disabled="props.isCheckoutPending || props.isExporting"
|
|
||||||
@click="handleCheckout"
|
@click="handleCheckout"
|
||||||
>
|
>
|
||||||
{{ props.isCheckoutPending ? "Redirecting…" : `Buy This Design ($${priceLabel})` }}
|
{{ props.isCheckoutPending ? "Redirecting…" : `Buy This Design ($${priceLabel})` }}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
|
||||||
<div
|
<div
|
||||||
v-if="props.checkoutError"
|
v-if="props.checkoutError"
|
||||||
class="mt-3 rounded-xl border border-rose-500/60 bg-rose-500/10 px-4 py-3 text-sm text-rose-200"
|
class="rounded-xl border border-rose-500/60 bg-rose-500/10 px-4 py-3 text-sm text-rose-200"
|
||||||
>
|
>
|
||||||
{{ props.checkoutError }}
|
{{ props.checkoutError }}
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
</section>
|
</section>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
@@ -381,16 +381,9 @@ const handleCheckout = async () => {
|
|||||||
/>
|
/>
|
||||||
|
|
||||||
<DesignerPreview
|
<DesignerPreview
|
||||||
:preview-url="previewUrl"
|
|
||||||
:template-label="templateLabel"
|
|
||||||
:production-pixels="productionPixelSize"
|
|
||||||
:is-exporting="isExporting || isDesignLoading"
|
|
||||||
:is-checkout-pending="isCheckoutPending"
|
:is-checkout-pending="isCheckoutPending"
|
||||||
:checkout-price="DESIGN_PRICE_USD"
|
:checkout-price="DESIGN_PRICE_USD"
|
||||||
:checkout-error="checkoutError"
|
:checkout-error="checkoutError"
|
||||||
@export="handleExport"
|
|
||||||
@download-preview="downloadPreview"
|
|
||||||
@download-production="downloadProduction"
|
|
||||||
@checkout="handleCheckout"
|
@checkout="handleCheckout"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -322,8 +322,6 @@ export const useSlipmatDesigner = () => {
|
|||||||
instance.on(eventName, handleMutation);
|
instance.on(eventName, handleMutation);
|
||||||
});
|
});
|
||||||
|
|
||||||
instance.on("after:render", () => schedulePreviewRefresh());
|
|
||||||
|
|
||||||
const selectionEvents = [
|
const selectionEvents = [
|
||||||
"selection:created",
|
"selection:created",
|
||||||
"selection:updated",
|
"selection:updated",
|
||||||
|
|||||||
Reference in New Issue
Block a user