feat: mail receipt preview

This commit is contained in:
Ahmed Bouhuolia
2024-11-23 20:36:46 +02:00
parent d5b0546301
commit da47418f17
17 changed files with 388 additions and 77 deletions

View File

@@ -5,7 +5,7 @@ import {
SendMailReceiptProps,
} from '../SendMailViewDrawer/SendMailViewReceiptPreview';
interface EstimateSendMailReceiptProps extends SendMailReceiptProps {
export interface EstimateSendMailReceiptProps extends SendMailReceiptProps {
// # Company name.
companyLogoUri?: string;
companyName: string;

View File

@@ -1,39 +1,20 @@
import { css } from '@emotion/css';
import { EstimateSendMailReceipt } from './EstimateSendMailReceipt';
import { ComponentType, useMemo } from 'react';
import { EstimateSendMailReceipt, EstimateSendMailReceiptProps } from './EstimateSendMailReceipt';
import { EstimateSendMailPreviewHeader } from './EstimateSendMailPreviewHeader';
import { Stack } from '@/components';
import { useEstimateSendMailBoot } from './EstimateSendMailBoot';
import { useSendEstimateMailMessage } from './hooks';
import { defaultEstimateMailReceiptProps } from './_constants';
const defaultEstimateMailReceiptProps = {
companyName: 'Bigcapital Technology, Inc.',
companyLogoUri: ' ',
total: '$1,000.00',
subtotal: '$1,000.00',
estimateNumber: 'INV-0001',
expirationDate: '2 Oct 2024',
dueAmount: '$1,000.00',
items: [{ label: 'Web development', total: '$1000.00', quantity: 1 }],
message: `Hi Ahmed Bouhuolia,
Here's invoice # INV-00002 for $738.30
The amount outstanding of $737.30 is due on 01 Feb 2023.
From your online payment page you can print a PDF or view your outstanding bills.
If you have any questions, please let us know.
Thanks,
Bigcapital`,
};
export const EstimateSendMailReceiptPreview = () => {
return (
<Stack>
<EstimateSendMailPreviewHeader />
<Stack px={4} py={6}>
<EstimateSendMailReceipt
{...defaultEstimateMailReceiptProps}
<EstimateSendMailReceiptConnected
className={css`
margin: 0 auto;
border-radius: 5px !important;
@@ -46,3 +27,44 @@ export const EstimateSendMailReceiptPreview = () => {
</Stack>
);
};
/**
* Injects props from estimate mail state into the `EstimateSendMailReceipt` component.
*/
const withEstimateMailReceiptPreviewProps = <
P extends EstimateSendMailReceiptProps,
>(
WrappedComponent: ComponentType<P & EstimateSendMailReceiptProps>,
) => {
return function WithInvoiceMailReceiptPreviewProps(props: P) {
const { estimateMailState } = useEstimateSendMailBoot();
const message = useSendEstimateMailMessage();
const items = useMemo(
() =>
estimateMailState?.entries?.map((entry: any) => ({
quantity: entry.quantity,
total: entry.totalFormatted,
label: entry.name,
})),
[estimateMailState?.entries],
);
const mailReceiptPreviewProps = {
...defaultEstimateMailReceiptProps,
companyName: estimateMailState?.companyName,
companyLogoUri: estimateMailState?.companyLogoUri,
primaryColor: estimateMailState?.primaryColor,
total: estimateMailState?.totalFormatted,
expirationDate: estimateMailState?.expirationDateFormatted,
estimateNumber: estimateMailState?.estimateNumber,
estimateDate: estimateMailState?.estimateDateFormatted,
items,
message
};
return <WrappedComponent {...mailReceiptPreviewProps} {...props} />;
};
};
const EstimateSendMailReceiptConnected = withEstimateMailReceiptPreviewProps(
EstimateSendMailReceipt
);

View File

@@ -0,0 +1,23 @@
export const defaultEstimateMailReceiptProps = {
companyName: 'Bigcapital Technology, Inc.',
companyLogoUri: ' ',
total: '$1,000.00',
subtotal: '$1,000.00',
estimateNumber: 'INV-0001',
expirationDate: '2 Oct 2024',
dueAmount: '$1,000.00',
items: [{ label: 'Web development', total: '$1000.00', quantity: 1 }],
message: `Hi Ahmed Bouhuolia,
Here's invoice # INV-00002 for $738.30
The amount outstanding of $737.30 is due on 01 Feb 2023.
From your online payment page you can print a PDF or view your outstanding bills.
If you have any questions, please let us know.
Thanks,
Bigcapital`,
};

View File

@@ -1,23 +1,14 @@
import { css } from '@emotion/css';
import { PaymentReceivedMailReceipt } from './PaymentReceivedMailReceipt';
import { ComponentType, useMemo } from 'react';
import {
PaymentReceivedMailReceipt,
PaymentReceivedMailReceiptProps,
} from './PaymentReceivedMailReceipt';
import { PaymentReceivedMailPreviewHeader } from './PaymentReceivedMailPreviewHeader';
import { Stack } from '@/components';
const defaultPaymentReceiptMailProps = {
companyName: 'Company Name',
companyLogoUri: 'https://via.placeholder.com/150',
primaryColor: 'rgb(0, 82, 204)',
paymentDate: '2021-01-01',
paymentDateLabel: 'Payment Date',
total: '100.00',
totalLabel: 'Total',
paymentNumber: '123456',
paymentNumberLabel: 'Payment #',
message: 'Thank you for your payment!',
subtotal: '100.00',
subtotalLabel: 'Subtotal',
items: [{ label: 'Invoice 1', total: '100.00' }],
};
import { useSendPaymentReceivedtMailMessage } from './_hooks';
import { usePaymentReceivedSendMailBoot } from './PaymentReceivedMailBoot';
import { defaultPaymentReceiptMailProps } from './_constants';
export function PaymentReceivedMailPreviewReceipt() {
return (
@@ -25,8 +16,7 @@ export function PaymentReceivedMailPreviewReceipt() {
<PaymentReceivedMailPreviewHeader />
<Stack px={4} py={6}>
<PaymentReceivedMailReceipt
{...defaultPaymentReceiptMailProps}
<PaymentReceivedMailReceiptPreviewConnected
className={css`
margin: 0 auto;
border-radius: 5px !important;
@@ -39,3 +29,43 @@ export function PaymentReceivedMailPreviewReceipt() {
</Stack>
);
}
/**
* Injects props from invoice mail state into the InvoiceMailReceiptPreview component.
*/
const withPaymentReceivedMailReceiptPreviewProps = <
P extends PaymentReceivedMailReceiptProps,
>(
WrappedComponent: ComponentType<P & PaymentReceivedMailReceiptProps>,
) => {
return function WithInvoiceMailReceiptPreviewProps(props: P) {
const message = useSendPaymentReceivedtMailMessage();
const { paymentReceivedMailState } = usePaymentReceivedSendMailBoot();
const items = useMemo(
() =>
paymentReceivedMailState?.entries?.map((entry: any) => ({
quantity: entry.quantity,
total: entry.totalFormatted,
label: entry.name,
})),
[paymentReceivedMailState?.entries],
);
const mailPaymentReceivedPreviewProps = {
...defaultPaymentReceiptMailProps,
companyName: paymentReceivedMailState?.companyName,
companyLogoUri: paymentReceivedMailState?.companyLogoUri,
primaryColor: paymentReceivedMailState?.primaryColor,
total: paymentReceivedMailState?.totalFormatted,
subtotal: paymentReceivedMailState?.subtotalFormatted,
paymentNumber: paymentReceivedMailState?.paymentNumber,
items,
message,
};
return <WrappedComponent {...mailPaymentReceivedPreviewProps} {...props} />;
};
};
export const PaymentReceivedMailReceiptPreviewConnected =
withPaymentReceivedMailReceiptPreviewProps(PaymentReceivedMailReceipt);

View File

@@ -0,0 +1,15 @@
export const defaultPaymentReceiptMailProps = {
companyName: 'Company Name',
companyLogoUri: 'https://via.placeholder.com/150',
primaryColor: 'rgb(0, 82, 204)',
paymentDate: '2021-01-01',
paymentDateLabel: 'Payment Date',
total: '100.00',
totalLabel: 'Total',
paymentNumber: '123456',
paymentNumberLabel: 'Payment #',
message: 'Thank you for your payment!',
subtotal: '100.00',
subtotalLabel: 'Subtotal',
items: [{ label: 'Invoice 1', total: '100.00' }],
};

View File

@@ -1,22 +1,14 @@
import { ComponentType } from 'react';
import { css } from '@emotion/css';
import { Stack } from '@/components';
import { ReceiptSendMailPreviewHeader } from './ReceiptSendMailPreviewHeader';
import { ReceiptSendMailReceipt } from './ReceiptSendMailReceipt';
import { css } from '@emotion/css';
const defaultReceiptMailProps = {
companyLogoUri: 'https://via.placeholder.com/150',
companyName: 'Company Name',
receiptNumber: '1234',
total: '1000',
message: 'Thank you for your business!',
items: [
{ label: 'Item 1', quantity: 1, total: '500' },
{ label: 'Item 2', quantity: 2, total: '500' },
],
subtotal: '1000',
showViewReceiptButton: true,
viewReceiptButtonLabel: 'View Receipt',
};
import {
ReceiptSendMailReceipt,
ReceiptSendMailReceiptProps,
} from './ReceiptSendMailReceipt';
import { defaultReceiptMailProps } from './_constants';
import { useReceiptSendMailBoot } from './ReceiptSendMailBoot';
import { useSendReceiptMailMessage } from './_hooks';
export function ReceiptSendMailPreview() {
return (
@@ -24,8 +16,7 @@ export function ReceiptSendMailPreview() {
<ReceiptSendMailPreviewHeader />
<Stack px={4} py={6}>
<ReceiptSendMailReceipt
{...defaultReceiptMailProps}
<ReceiptMailPreviewConnected
className={css`
margin: 0 auto;
border-radius: 5px !important;
@@ -38,3 +29,45 @@ export function ReceiptSendMailPreview() {
</Stack>
);
}
/**
* Injects props from receipt mail state into the `ReceiptMailPreviewConnected` component.
*/
const withReceiptMailReceiptPreviewProps = <
P extends ReceiptSendMailReceiptProps,
>(
WrappedComponent: ComponentType<P & ReceiptSendMailReceiptProps>,
) => {
return function WithInvoiceMailReceiptPreviewProps(props: P) {
const message = useSendReceiptMailMessage();
const { receiptMailState } = useReceiptSendMailBoot();
// const items = useMemo(
// () =>
// invoiceMailState?.entries?.map((entry: any) => ({
// quantity: entry.quantity,
// total: entry.totalFormatted,
// label: entry.name,
// })),
// [invoiceMailState?.entries],
// );
const mailReceiptPreviewProps = {
...defaultReceiptMailProps,
// companyName: receiptMailState?.companyName,
// companyLogoUri: receiptMailState?.companyLogoUri,
// primaryColor: receiptMailState?.primaryColor,
// total: receiptMailState?.totalFormatted,
// dueDate: receiptMailState?.dueDateFormatted,
// dueAmount: invoiceMailState?.dueAmountFormatted,
// invoiceNumber: invoiceMailState?.invoiceNo,
// items,
message,
};
return <WrappedComponent {...mailReceiptPreviewProps} {...props} />;
};
};
export const ReceiptMailPreviewConnected = withReceiptMailReceiptPreviewProps(
ReceiptSendMailReceipt,
);

View File

@@ -1,8 +1,17 @@
import { Suspense } from 'react';
import { lazy, Suspense } from 'react';
import { Tab } from '@blueprintjs/core';
import { SendMailViewPreviewTabs } from '../../Estimates/SendMailViewDrawer/SendMailViewPreviewTabs';
import { ReceiptSendMailPreview } from './ReceiptSendMailPreview';
import { ReceiptSendMailPdfPreview } from './ReceiptSendMailPdfPreview';
const ReceiptSendMailPreview = lazy(() =>
import('./ReceiptSendMailPreview').then((module) => ({
default: module.ReceiptSendMailPreview,
})),
);
const ReceiptSendMailPdfPreview = lazy(() =>
import('./ReceiptSendMailPdfPreview').then((module) => ({
default: module.ReceiptSendMailPdfPreview,
})),
);
export function ReceiptSendMailPreviewTabs() {
return (

View File

@@ -5,7 +5,7 @@ import {
SendMailReceiptProps,
} from '../../Estimates/SendMailViewDrawer/SendMailViewReceiptPreview';
interface ReceiptSendMailReceiptProps extends SendMailReceiptProps {
export interface ReceiptSendMailReceiptProps extends SendMailReceiptProps {
// # Company name.
companyLogoUri?: string;
companyName: string;

View File

@@ -0,0 +1,14 @@
export const defaultReceiptMailProps = {
companyLogoUri: 'https://via.placeholder.com/150',
companyName: 'Company Name',
receiptNumber: '1234',
total: '1000',
message: 'Thank you for your business!',
items: [
{ label: 'Item 1', quantity: 1, total: '500' },
{ label: 'Item 2', quantity: 2, total: '500' },
],
subtotal: '1000',
showViewReceiptButton: true,
viewReceiptButtonLabel: 'View Receipt',
};