wallet manage in checkout

This commit is contained in:
hamid zarghami
2025-12-29 10:11:52 +03:30
parent 3abf1c314a
commit 7a9dc0c891
@@ -6,6 +6,9 @@ import { useTranslation } from 'react-i18next';
import { RadioGroup, RadioGroupItem } from '@/components/ui/radio-group'; import { RadioGroup, RadioGroupItem } from '@/components/ui/radio-group';
import { useGetPaymentMethod } from '../../hooks/useOrderData'; import { useGetPaymentMethod } from '../../hooks/useOrderData';
import { useCheckoutStore } from '../../store/Store'; import { useCheckoutStore } from '../../store/Store';
import { useGetUserWallet } from '@/app/[name]/(Main)/transactions/hooks/useTransactionData';
import { useGetCartItems } from '@/app/[name]/(Dialogs)/cart/hooks/useCartData';
import { useGetProfile } from '@/app/[name]/(Profile)/profile/hooks/userProfileData';
type PaymentSectionProps = { type PaymentSectionProps = {
paymentType: string; paymentType: string;
@@ -23,12 +26,28 @@ const getIconByMethod = (method: "CardOnDelivery" | "Cash" | "Online", _gateway:
return Card; return Card;
}; };
const isWalletPayment = (method: string, gateway: string | null): boolean => {
return gateway?.toLowerCase() === 'wallet' || method.toLowerCase() === 'wallet';
};
export const PaymentSection = ({ paymentType, onPaymentTypeChange }: PaymentSectionProps) => { export const PaymentSection = ({ paymentType, onPaymentTypeChange }: PaymentSectionProps) => {
const { t: tOrderDetail } = useTranslation('parallels', { keyPrefix: 'OrderDetail' }); const { t: tOrderDetail } = useTranslation('parallels', { keyPrefix: 'OrderDetail' });
const { t: tOrders } = useTranslation('orders'); const { t: tOrders } = useTranslation('orders');
const { data: paymentMethod } = useGetPaymentMethod(); const { data: paymentMethod } = useGetPaymentMethod();
const { setIsSelectedPayment } = useCheckoutStore(); const { setIsSelectedPayment } = useCheckoutStore();
const { data: userWallet } = useGetUserWallet();
const { isSuccess } = useGetProfile();
const { data: cartData } = useGetCartItems(isSuccess);
const walletAmount = userWallet?.data?.wallet ?? 0;
const totalAmount = cartData?.data?.total ?? 0;
const isWalletInsufficient = walletAmount < totalAmount;
const formatPrice = useCallback(
(value: number) => value.toLocaleString('fa-IR'),
[]
);
const getPaymentMethodTranslation = useCallback((method: string, fallbackTitle: string) => { const getPaymentMethodTranslation = useCallback((method: string, fallbackTitle: string) => {
const translationKey = `paymentMethod.${method}`; const translationKey = `paymentMethod.${method}`;
@@ -46,6 +65,9 @@ export const PaymentSection = ({ paymentType, onPaymentTypeChange }: PaymentSect
id: item.id, id: item.id,
label: getPaymentMethodTranslation(item.method, item.title), label: getPaymentMethodTranslation(item.method, item.title),
icon: getIconByMethod(item.method, item.gateway), icon: getIconByMethod(item.method, item.gateway),
method: item.method,
gateway: item.gateway,
isWallet: isWalletPayment(item.method, item.gateway),
})); }));
}, [paymentMethod, getPaymentMethodTranslation]); }, [paymentMethod, getPaymentMethodTranslation]);
@@ -62,11 +84,30 @@ export const PaymentSection = ({ paymentType, onPaymentTypeChange }: PaymentSect
}} }}
className='flex flex-col gap-6 mt-6' className='flex flex-col gap-6 mt-6'
> >
{paymentOptions.map(({ id, label, icon: Icon }) => ( {paymentOptions.map(({ id, label, icon: Icon, isWallet }) => {
const isDisabled = isWallet && isWalletInsufficient;
const walletOption = paymentOptions.find(opt => opt.id === id && opt.isWallet);
return (
<div key={id} className='flex items-center justify-between'> <div key={id} className='flex items-center justify-between'>
<RadioGroupItem value={id} id={`paymentMethod${id}`} /> <RadioGroupItem
<label className='flex items-center gap-2 cursor-pointer' htmlFor={`paymentMethod${id}`}> value={id}
id={`paymentMethod${id}`}
disabled={isDisabled}
/>
<label
className={`flex items-center gap-2 ${isDisabled ? 'cursor-not-allowed opacity-50' : 'cursor-pointer'}`}
htmlFor={`paymentMethod${id}`}
>
<div className='flex gap-1'>
{walletOption && (
<span className='text-xs text-gray-500 dark:text-gray-400 mt-1'>
({formatPrice(walletAmount)} T)
</span>
)}
<span className='text-xs mt-0.5'>{label}</span> <span className='text-xs mt-0.5'>{label}</span>
</div>
<Icon <Icon
size={16} size={16}
color='currentColor' color='currentColor'
@@ -74,7 +115,8 @@ export const PaymentSection = ({ paymentType, onPaymentTypeChange }: PaymentSect
/> />
</label> </label>
</div> </div>
))} );
})}
</RadioGroup> </RadioGroup>
</div> </div>
</section> </section>