Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .changeset/forty-peaches-stay.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
'@clerk/clerk-js': patch
'@clerk/types': patch
---

Refactor InvoicePage title and invoice ID UI.
2 changes: 1 addition & 1 deletion packages/clerk-js/bundlewatch.config.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"files": [
{ "path": "./dist/clerk.js", "maxSize": "592.5kB" },
{ "path": "./dist/clerk.js", "maxSize": "593kB" },
{ "path": "./dist/clerk.browser.js", "maxSize": "74KB" },
{ "path": "./dist/clerk.headless*.js", "maxSize": "55KB" },
{ "path": "./dist/ui-common*.js", "maxSize": "100KB" },
Expand Down
90 changes: 80 additions & 10 deletions packages/clerk-js/src/ui/components/Invoices/InvoicePage.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import { useInvoicesContext } from '../../contexts';
import { Badge, Box, Dd, descriptors, Dl, Dt, Heading, Spinner, Text } from '../../customizables';
import { Badge, Box, Button, Dd, descriptors, Dl, Dt, Heading, Icon, Span, Spinner, Text } from '../../customizables';
import { Header, LineItems } from '../../elements';
import { useClipboard } from '../../hooks';
import { Check, Copy } from '../../icons';
import { useRouter } from '../../router';
import { common } from '../../styledSystem';
import { colors } from '../../utils';
Expand Down Expand Up @@ -76,18 +78,43 @@ export const InvoicePage = () => {
})}
>
<Box
elementDescriptor={descriptors.invoiceHeaderTitleBadgeContainer}
sx={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
alignItems: 'start',
}}
>
<Heading
textVariant='h2'
elementDescriptor={descriptors.invoiceTitle}
>
{truncateWithEndVisible(invoice.id)}
</Heading>
<Span elementDescriptor={descriptors.invoiceTitleIdContainer}>
<Heading
textVariant='h2'
elementDescriptor={descriptors.invoiceTitle}
>
Invoice ID
</Heading>
<Span
elementDescriptor={descriptors.invoiceIdContainer}
sx={t => ({
display: 'flex',
alignItems: 'center',
gap: t.space.$0x25,
color: t.colors.$colorTextSecondary,
})}
>
<CopyButton
copyLabel='Copy invoice ID'
text={invoice.id}
/>
<Text
elementDescriptor={descriptors.invoiceId}
colorScheme='secondary'
variant='subtitle'
>
{truncateWithEndVisible(invoice.id)}
</Text>
</Span>
</Span>

<Badge
elementDescriptor={descriptors.invoiceBadge}
colorScheme={
Expand All @@ -109,14 +136,20 @@ export const InvoicePage = () => {
<Box elementDescriptor={descriptors.invoiceDetailsItem}>
<Dt elementDescriptor={descriptors.invoiceDetailsItemTitle}>
<Text
elementDescriptor={descriptors.invoiceDetailsItemTitleText}
colorScheme='secondary'
variant='body'
>
Created on
</Text>
</Dt>
<Dd elementDescriptor={descriptors.invoiceDetailsItemValue}>
<Text variant='subtitle'>{new Date(invoice.paymentDueOn).toLocaleDateString()}</Text>
<Text
elementDescriptor={descriptors.invoiceDetailsItemValueText}
variant='subtitle'
>
{new Date(invoice.paymentDueOn).toLocaleDateString()}
</Text>
</Dd>
</Box>
<Box
Expand All @@ -127,14 +160,20 @@ export const InvoicePage = () => {
>
<Dt elementDescriptor={descriptors.invoiceDetailsItemTitle}>
<Text
elementDescriptor={descriptors.invoiceDetailsItemTitleText}
colorScheme='secondary'
variant='body'
>
Due on
</Text>
</Dt>
<Dd elementDescriptor={descriptors.invoiceDetailsItemValue}>
<Text variant='subtitle'>{new Date(invoice.paymentDueOn).toLocaleDateString()}</Text>
<Text
elementDescriptor={descriptors.invoiceDetailsItemValueText}
variant='subtitle'
>
{new Date(invoice.paymentDueOn).toLocaleDateString()}
</Text>
</Dd>
</Box>
</Dl>
Expand Down Expand Up @@ -183,3 +222,34 @@ export const InvoicePage = () => {
</>
);
};

function CopyButton({ text, copyLabel = 'Copy' }: { text: string; copyLabel?: string }) {
const { onCopy, hasCopied } = useClipboard(text);

return (
<Button
elementDescriptor={descriptors.invoiceCopyButton}
variant='unstyled'
onClick={onCopy}
sx={t => ({
color: 'inherit',
width: t.sizes.$4,
height: t.sizes.$4,
padding: 0,
borderRadius: t.radii.$sm,
'&:focus-visible': {
outline: '2px solid',
outlineColor: t.colors.$neutralAlpha200,
},
})}
focusRing={false}
aria-label={hasCopied ? 'Copied' : copyLabel}
>
<Icon
size='sm'
icon={hasCopied ? Check : Copy}
aria-hidden
/>
</Button>
);
}
8 changes: 8 additions & 0 deletions packages/clerk-js/src/ui/customizables/elementDescriptors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -343,12 +343,20 @@ export const APPEARANCE_KEYS = containsAllElementsConfigKeys([
'invoiceRoot',
'invoiceCard',
'invoiceHeader',
'invoiceHeaderContent',
'invoiceTitle',
'invoiceHeaderTitleBadgeContainer',
'invoiceId',
'invoiceIdContainer',
'invoiceTitleIdContainer',
'invoiceBadge',
'invoiceDetails',
'invoiceDetailsItem',
'invoiceDetailsItemTitle',
'invoiceDetailsItemTitleText',
'invoiceDetailsItemValue',
'invoiceDetailsItemValueText',
'invoiceCopyButton',
'invoiceContent',

'menuButton',
Expand Down
8 changes: 8 additions & 0 deletions packages/types/src/appearance.ts
Original file line number Diff line number Diff line change
Expand Up @@ -467,12 +467,20 @@ export type ElementsConfig = {
invoiceRoot: WithOptions;
invoiceCard: WithOptions;
invoiceHeader: WithOptions;
invoiceHeaderContent: WithOptions;
invoiceTitle: WithOptions;
invoiceHeaderTitleBadgeContainer: WithOptions;
invoiceTitleIdContainer: WithOptions;
invoiceId: WithOptions;
invoiceIdContainer: WithOptions;
invoiceBadge: WithOptions;
invoiceDetails: WithOptions;
invoiceDetailsItem: WithOptions;
invoiceDetailsItemTitle: WithOptions;
invoiceDetailsItemTitleText: WithOptions;
invoiceDetailsItemValue: WithOptions;
invoiceDetailsItemValueText: WithOptions;
invoiceCopyButton: WithOptions;
invoiceContent: WithOptions;

menuButton: WithOptions<MenuId>;
Expand Down