web: show success on checkout completion

This commit is contained in:
Abdullah Atta
2023-05-01 12:53:24 +05:00
committed by Abdullah Atta
parent 6d3e985c9d
commit dd368a4170
3 changed files with 55 additions and 5 deletions

View File

@@ -55,6 +55,8 @@ export function BuyDialog(props: BuyDialogProps) {
const theme = useTheme() as Theme;
const onApplyCoupon = useCheckoutStore((store) => store.applyCoupon);
const isCheckoutCompleted = useCheckoutStore((store) => store.isCompleted);
useEffect(() => {
return () => {
useCheckoutStore.getState().reset();
@@ -118,7 +120,7 @@ export function BuyDialog(props: BuyDialogProps) {
boxShadow: "4px 5px 18px 2px #00000038",
borderRadius: "dialog",
flexDirection: ["column", "column", "row"],
width: ["95%", "80%", "60%"],
width: ["95%", "80%", isCheckoutCompleted ? "400px" : "60%"],
maxHeight: ["95%", "80%", "80%"],
alignSelf: "center",
overflowY: ["scroll", "scroll", "hidden"]
@@ -139,7 +141,7 @@ export function BuyDialog(props: BuyDialogProps) {
flexShrink: 0,
alignItems: "center",
justifyContent: "center",
width: ["100%", "100%", 350]
width: ["100%", "100%", isCheckoutCompleted ? "100%" : 350]
}}
p={4}
py={50}
@@ -165,6 +167,9 @@ function SideBar(props: SideBarProps) {
const user = useUserStore((store) => store.user);
const couponCode = useCheckoutStore((store) => store.couponCode);
const onApplyCoupon = useCheckoutStore((store) => store.applyCoupon);
const isCheckoutCompleted = useCheckoutStore((store) => store.isCompleted);
if (isCheckoutCompleted) return <CheckoutCompleted onClose={onClose} />;
if (user && selectedPlan)
return (
@@ -230,12 +235,16 @@ function Details() {
const user = useUserStore((store) => store.user);
const selectedPlan = useCheckoutStore((state) => state.selectedPlan);
const onPriceUpdated = useCheckoutStore((state) => state.updatePrice);
const completeCheckout = useCheckoutStore((state) => state.completeCheckout);
const isCheckoutCompleted = useCheckoutStore((store) => store.isCompleted);
const couponCode = useCheckoutStore((store) => store.couponCode);
const setIsApplyingCoupon = useCheckoutStore(
(store) => store.setIsApplyingCoupon
);
const theme = useThemeStore((store) => store.theme);
if (isCheckoutCompleted) return null;
if (selectedPlan && user)
return (
<PaddleCheckout
@@ -243,6 +252,7 @@ function Details() {
theme={theme}
user={user}
coupon={couponCode}
onCompleted={completeCheckout}
onCouponApplied={() => setIsApplyingCoupon(true)}
onPriceUpdated={(pricingInfo) => {
onPriceUpdated(pricingInfo);
@@ -396,6 +406,31 @@ function AlreadyPremium(props: AlreadyPremiumProps) {
);
}
function CheckoutCompleted(props: { onClose: () => void }) {
const { onClose } = props;
return (
<>
<Rocket width={200} />
<Text variant="heading" mt={4} sx={{ textAlign: "center" }}>
Thank you!
</Text>
<Text variant="body" mt={1} sx={{ textAlign: "center" }}>
You have successfully subscribed to Notesnook Pro.
</Text>
<Button
variant="primary"
mt={2}
sx={{ borderRadius: 100, px: 6 }}
onClick={onClose}
data-test-id="see-all-plans"
>
Continue
</Button>
</>
);
}
type SelectedPlanProps = {
plan: Plan;
pricingInfo: PricingInfo | undefined;

View File

@@ -39,7 +39,8 @@ const SUBSCRIBED_EVENTS: PaddleEvents[] = [
PaddleEvents["Checkout.Loaded"],
PaddleEvents["Checkout.Coupon.Applied"],
PaddleEvents["Checkout.Coupon.Remove"],
PaddleEvents["Checkout.Location.Submit"]
PaddleEvents["Checkout.Location.Submit"],
PaddleEvents["Checkout.Complete"]
];
type PaddleCheckoutProps = {
@@ -48,10 +49,11 @@ type PaddleCheckoutProps = {
plan: Plan;
onPriceUpdated?: (pricingInfo: PricingInfo) => void;
onCouponApplied?: () => void;
onCompleted?: () => void;
coupon?: string;
};
export function PaddleCheckout(props: PaddleCheckoutProps) {
const { plan, onPriceUpdated, coupon, onCouponApplied } = props;
const { plan, onPriceUpdated, coupon, onCouponApplied, onCompleted } = props;
const [sourceUrl, setSourceUrl] = useState<string>();
const [isLoading, setIsLoading] = useState(true);
const [checkoutId, setCheckoutId] = useState<string>();
@@ -96,6 +98,10 @@ export function PaddleCheckout(props: PaddleCheckoutProps) {
)
return;
if (event_name === PaddleEvents["Checkout.Complete"]) {
onCompleted && onCompleted();
return;
}
if (event_name === PaddleEvents["Checkout.Loaded"]) setIsLoading(false);
const pricingInfo = await updatePrice(checkout.id);
@@ -108,7 +114,7 @@ export function PaddleCheckout(props: PaddleCheckoutProps) {
return () => {
window.removeEventListener("message", onMessage);
};
}, [onPriceUpdated, updatePrice, plan]);
}, [onPriceUpdated, updatePrice, plan, onCompleted]);
useEffect(() => {
if (

View File

@@ -22,6 +22,8 @@ import create from "zustand";
import produce from "immer";
interface ICheckoutStore {
isCompleted: boolean;
completeCheckout: () => void;
selectedPlan?: Plan;
selectPlan: (plan?: Plan) => void;
pricingInfo?: PricingInfo;
@@ -33,10 +35,17 @@ interface ICheckoutStore {
reset: () => void;
}
export const useCheckoutStore = create<ICheckoutStore>((set) => ({
isCompleted: false,
selectedPlan: undefined,
pricingInfo: undefined,
couponCode: undefined,
isApplyingCoupon: false,
completeCheckout: () =>
set(
produce((state: ICheckoutStore) => {
state.isCompleted = true;
})
),
selectPlan: (plan) =>
set(
produce((state: ICheckoutStore) => {