Compare commits
2 Commits
ae9a4799be
...
dd280d3e1e
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
dd280d3e1e | ||
|
|
d47bf2af8e |
@ -57,4 +57,11 @@ class CardController extends Controller
|
|||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function cartResult()
|
||||||
|
{
|
||||||
|
return Inertia::render('cards/resultat', [
|
||||||
|
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -8,6 +8,7 @@
|
|||||||
Pour une guidance plus approfondie, réservez une consultation personnalisée avec Kris Saint Ange.
|
Pour une guidance plus approfondie, réservez une consultation personnalisée avec Kris Saint Ange.
|
||||||
</p>
|
</p>
|
||||||
<button
|
<button
|
||||||
|
@click="goTobooking"
|
||||||
class="mt-8 inline-flex h-12 max-w-[480px] min-w-[120px] flex-shrink-0 cursor-pointer items-center justify-center rounded-full bg-[var(--subtle-gold)] px-8 text-base font-bold tracking-wide text-[var(--midnight-blue)] transition-all duration-300 hover:shadow-[var(--subtle-gold)]/30 hover:shadow-lg"
|
class="mt-8 inline-flex h-12 max-w-[480px] min-w-[120px] flex-shrink-0 cursor-pointer items-center justify-center rounded-full bg-[var(--subtle-gold)] px-8 text-base font-bold tracking-wide text-[var(--midnight-blue)] transition-all duration-300 hover:shadow-[var(--subtle-gold)]/30 hover:shadow-lg"
|
||||||
>
|
>
|
||||||
Réserver une Consultation
|
Réserver une Consultation
|
||||||
@ -15,3 +16,11 @@
|
|||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
<script lang="ts" setup>
|
||||||
|
import { router } from '@inertiajs/vue3';
|
||||||
|
|
||||||
|
const goTobooking = () => {
|
||||||
|
router.visit('/rendez-vous');
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|||||||
@ -7,6 +7,7 @@ import { ref, watchEffect } from 'vue';
|
|||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
drawCount?: number; // Optional prop for the shuffle animation
|
drawCount?: number; // Optional prop for the shuffle animation
|
||||||
drawnCards?: Card[]; // Optional prop to directly display cards
|
drawnCards?: Card[]; // Optional prop to directly display cards
|
||||||
|
clientSessionId?: string;
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
defineEmits(['drawCard']);
|
defineEmits(['drawCard']);
|
||||||
@ -53,6 +54,10 @@ const goToSelection = () => {
|
|||||||
router.visit('/tirage');
|
router.visit('/tirage');
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const goToResult = () => {
|
||||||
|
router.visit(`/resultat?client_session_id=${props.clientSessionId}`);
|
||||||
|
};
|
||||||
|
|
||||||
defineExpose({ setDrawnCards });
|
defineExpose({ setDrawnCards });
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@ -150,6 +155,12 @@ defineExpose({ setDrawnCards });
|
|||||||
>
|
>
|
||||||
<span class="truncate">Retourner à la sélection des cartes</span>
|
<span class="truncate">Retourner à la sélection des cartes</span>
|
||||||
</button>
|
</button>
|
||||||
|
<button
|
||||||
|
@click="goToResult"
|
||||||
|
class="mt-8 flex h-12 max-w-[480px] min-w-[200px] cursor-pointer items-center justify-center overflow-hidden rounded-full bg-[var(--midnight-blue)] px-8 text-base font-bold tracking-wide text-[var(--pure-white)] transition-all duration-300 hover:bg-[var(--spiritual-earth)] hover:shadow-[var(--spiritual-earth)]/30 hover:shadow-lg disabled:cursor-not-allowed disabled:bg-gray-400 disabled:hover:shadow-none"
|
||||||
|
>
|
||||||
|
<span class="truncate">Resultat du tirage</span>
|
||||||
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</transition>
|
</transition>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
29
resources/js/components/ui/card/CardResult.vue
Normal file
29
resources/js/components/ui/card/CardResult.vue
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
<template>
|
||||||
|
<div class="border-linen flex flex-col items-center gap-8 rounded-lg border bg-white p-8 shadow-sm md:flex-row">
|
||||||
|
<div
|
||||||
|
class="h-72 w-48 flex-shrink-0 rounded-md bg-cover bg-center bg-no-repeat"
|
||||||
|
:style="{
|
||||||
|
'background-image': `url('${imageUrl}')`,
|
||||||
|
'box-shadow': '0 0 15px 5px rgba(215, 186, 141, 0.3)'
|
||||||
|
}"
|
||||||
|
></div>
|
||||||
|
<div class="flex flex-col gap-2">
|
||||||
|
<p class="text-spiritual-earth text-sm tracking-widest uppercase">Carte {{ cardNumber }}</p>
|
||||||
|
<h3 class="text-midnight-blue text-2xl font-bold">{{ name }}</h3>
|
||||||
|
<p class="text-midnight-blue/80 leading-relaxed">{{ description }}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { defineProps } from 'vue';
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
cardNumber: number;
|
||||||
|
name: string;
|
||||||
|
imageUrl: string;
|
||||||
|
description: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
defineProps<Props>();
|
||||||
|
</script>
|
||||||
@ -45,7 +45,9 @@ const toggleMobileMenu = () => {
|
|||||||
<Link class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300" href="#"
|
<Link class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300" href="#"
|
||||||
>Témoignages</Link
|
>Témoignages</Link
|
||||||
>
|
>
|
||||||
<Link class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300" href="#">Contact</Link>
|
<Link class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300" href="/rendez-vous"
|
||||||
|
>Booking</Link
|
||||||
|
>
|
||||||
</nav>
|
</nav>
|
||||||
|
|
||||||
<div class="flex items-center gap-4">
|
<div class="flex items-center gap-4">
|
||||||
@ -91,9 +93,9 @@ const toggleMobileMenu = () => {
|
|||||||
>
|
>
|
||||||
<Link
|
<Link
|
||||||
class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300"
|
class="text-midnight-blue hover:text-subtle-gold text-sm font-medium transition-colors duration-300"
|
||||||
href="#"
|
href="/rendez-vous"
|
||||||
@click="toggleMobileMenu"
|
@click="toggleMobileMenu"
|
||||||
>Contact</Link
|
>Booking</Link
|
||||||
>
|
>
|
||||||
</nav>
|
</nav>
|
||||||
|
|
||||||
|
|||||||
@ -30,7 +30,6 @@ const redirectToStipeCheckout = async () => {
|
|||||||
selectedDate: selectedDate.value,
|
selectedDate: selectedDate.value,
|
||||||
});
|
});
|
||||||
const sessionId = res.data.sessionId;
|
const sessionId = res.data.sessionId;
|
||||||
console.log(sessionId);
|
|
||||||
const stripe = await loadStripe(import.meta.env.VITE_STRIPE_PUBLISHABLE_KEY!);
|
const stripe = await loadStripe(import.meta.env.VITE_STRIPE_PUBLISHABLE_KEY!);
|
||||||
if (stripe) {
|
if (stripe) {
|
||||||
const { error } = await stripe.redirectToCheckout({ sessionId });
|
const { error } = await stripe.redirectToCheckout({ sessionId });
|
||||||
|
|||||||
77
resources/js/pages/cards/resultat.vue
Normal file
77
resources/js/pages/cards/resultat.vue
Normal file
@ -0,0 +1,77 @@
|
|||||||
|
<script setup lang="ts">
|
||||||
|
import CardResult from '@/components/ui/card/CardResult.vue';
|
||||||
|
import LandingLayout from '@/layouts/app/LandingLayout.vue';
|
||||||
|
import { router } from '@inertiajs/vue3';
|
||||||
|
import axios from 'axios';
|
||||||
|
import { onMounted, ref } from 'vue';
|
||||||
|
|
||||||
|
const goTobooking = () => {
|
||||||
|
router.visit('/rendez-vous');
|
||||||
|
};
|
||||||
|
|
||||||
|
const cards = ref([]);
|
||||||
|
const error = ref<string | null>(null);
|
||||||
|
|
||||||
|
const params = new URLSearchParams(window.location.search);
|
||||||
|
const clientSessionId = params.get('client_session_id');
|
||||||
|
const loading = ref(false);
|
||||||
|
|
||||||
|
onMounted(async () => {
|
||||||
|
if (clientSessionId) {
|
||||||
|
try {
|
||||||
|
const response = await axios.get(`/api/get-cards?client_session_id=${clientSessionId}`);
|
||||||
|
if (response.data.success) {
|
||||||
|
cards.value = response.data.cards;
|
||||||
|
} else {
|
||||||
|
error.value = response.data.message || 'An error occurred while validating payment.';
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
console.error(err);
|
||||||
|
error.value = 'Failed to get cards from the server. Please contact support.';
|
||||||
|
} finally {
|
||||||
|
loading.value = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<LandingLayout>
|
||||||
|
<main class="flex flex-1 justify-center px-4 py-16 sm:px-6 lg:px-8">
|
||||||
|
<div class="layout-content-container flex w-full max-w-4xl flex-col">
|
||||||
|
<div class="mb-12 text-center">
|
||||||
|
<h1 class="text-midnight-blue text-5xl font-bold">Votre Lecture</h1>
|
||||||
|
<p class="text-spiritual-earth mt-2 text-lg">
|
||||||
|
Voici une analyse détaillée de votre lecture choisie. Veuillez vérifier avant de procéder au paiement.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="mb-12">
|
||||||
|
<div class="space-y-12">
|
||||||
|
<card-result
|
||||||
|
v-for="card in cards"
|
||||||
|
:key="card.id"
|
||||||
|
:card-number="1"
|
||||||
|
:name="card.name"
|
||||||
|
:image-url="card.image_url"
|
||||||
|
:orientation="card.orientation"
|
||||||
|
:description="card.description"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="border-linen rounded-lg border bg-white p-8 text-center shadow-sm md:p-12">
|
||||||
|
<div class="bg-subtle-gold mx-auto mb-6 h-px w-20"></div>
|
||||||
|
<p class="text-midnight-blue/80 mx-auto mb-8 max-w-2xl text-lg leading-relaxed">
|
||||||
|
Pour une guidance plus approfondie, réservez une consultation personnalisée avec Kris Saint Ange.
|
||||||
|
</p>
|
||||||
|
<button
|
||||||
|
@click="goTobooking"
|
||||||
|
class="mt-8 inline-flex h-12 max-w-[480px] min-w-[120px] flex-shrink-0 cursor-pointer items-center justify-center rounded-full bg-[var(--subtle-gold)] px-8 text-base font-bold tracking-wide text-[var(--midnight-blue)] transition-all duration-300 hover:shadow-[var(--subtle-gold)]/30 hover:shadow-lg"
|
||||||
|
>
|
||||||
|
Réserver une Consultation
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
</LandingLayout>
|
||||||
|
</template>
|
||||||
@ -36,7 +36,6 @@ onMounted(async () => {
|
|||||||
if (cardComponent.value) {
|
if (cardComponent.value) {
|
||||||
cardComponent.value.setDrawnCards(cards.value);
|
cardComponent.value.setDrawnCards(cards.value);
|
||||||
}
|
}
|
||||||
console.log(cards.value);
|
|
||||||
} else {
|
} else {
|
||||||
error.value = response.data.message || 'An error occurred while validating payment.';
|
error.value = response.data.message || 'An error occurred while validating payment.';
|
||||||
}
|
}
|
||||||
@ -112,6 +111,6 @@ const handleSelection = async (count: number) => {
|
|||||||
<template>
|
<template>
|
||||||
<LandingLayout>
|
<LandingLayout>
|
||||||
<card-selection @selectDraw="handleSelection" v-if="isSelectionScreen && !clientSessionId" />
|
<card-selection @selectDraw="handleSelection" v-if="isSelectionScreen && !clientSessionId" />
|
||||||
<ShuffleCardPresentation v-else ref="cardComponent" :drawn-cards="cards" />
|
<ShuffleCardPresentation v-else ref="cardComponent" :drawn-cards="cards" :client-session-id="clientSessionId" />
|
||||||
</LandingLayout>
|
</LandingLayout>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
@ -50,7 +50,6 @@ const params = new URLSearchParams(window.location.search);
|
|||||||
const clientSessionId = params.get('client_session_id');
|
const clientSessionId = params.get('client_session_id');
|
||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
console.log(clientSessionId);
|
|
||||||
if (clientSessionId) {
|
if (clientSessionId) {
|
||||||
try {
|
try {
|
||||||
const response = await axios.get(`/api/validate-payment?client_session_id=${clientSessionId}`);
|
const response = await axios.get(`/api/validate-payment?client_session_id=${clientSessionId}`);
|
||||||
|
|||||||
@ -25,6 +25,8 @@ Route::post('/stripe/webhook', [App\Http\Controllers\WebhookController::class, '
|
|||||||
|
|
||||||
Route::get('/rendez-vous', [App\Http\Controllers\AppointmentController::class, 'index']);
|
Route::get('/rendez-vous', [App\Http\Controllers\AppointmentController::class, 'index']);
|
||||||
|
|
||||||
|
Route::get('/resultat', [App\Http\Controllers\CardController::class, 'cartResult']);
|
||||||
|
|
||||||
Route::get('/success', function (Request $request) {
|
Route::get('/success', function (Request $request) {
|
||||||
$clientSessionId = $request->query('client_session_id');
|
$clientSessionId = $request->query('client_session_id');
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user