Skip to content

Commit

Permalink
OPHJOD-258: Expander
Browse files Browse the repository at this point in the history
  • Loading branch information
ketsappi committed Apr 8, 2024
1 parent f44a3f9 commit e66e9c6
Show file tree
Hide file tree
Showing 5 changed files with 167 additions and 0 deletions.
31 changes: 31 additions & 0 deletions lib/components/Expander/Expander.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import type { Meta, StoryObj } from '@storybook/react';

import { Expander } from './Expander';

const meta = {
title: 'Primitives/Expander',
component: Expander,
tags: ['autodocs'],
} satisfies Meta<typeof Expander>;

export default meta;

type Story = StoryObj<typeof meta>;

const parameters = {
design: {
type: 'figma',
url: 'https://www.figma.com/file/6M2LrpSCcB0thlFDaQAI2J/cx_jod_client?node-id=542%3A7857',
},
};

export const Default: Story = {
parameters: {
...parameters,
},
args: {
label: 'Label',
description: 'Description',
children: <div>Children here</div>,
},
};
51 changes: 51 additions & 0 deletions lib/components/Expander/Expander.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
import { render, screen, cleanup } from '@testing-library/react';
import { afterEach, describe, expect, test } from 'vitest';
import '@testing-library/jest-dom/vitest';
import userEvent from '@testing-library/user-event';

import { Expander } from './Expander';

afterEach(() => {
cleanup();
});

describe('Snapshot testing', () => {
test('Base button', () => {
const { container } = render(
<Expander label="Label" description="Description">
content
</Expander>,
);
expect(container.firstChild).toMatchSnapshot();
});
});

describe('Expander', () => {
test('renders label and description correctly', () => {
const label = 'Test Label';
const description = 'Test Description';
render(<Expander label={label} description={description} />);

const labelElement = screen.getByText(label);
const descriptionElement = screen.getByText(description);

expect(labelElement).toBeInTheDocument();
expect(descriptionElement).toBeInTheDocument();
});

test('expands and collapses on button click', async () => {
const user = userEvent.setup();
const label = 'Test Label';
const description = 'Test Description';
render(<Expander label={label} description={description} />);

const button = screen.getByRole('button');
expect(screen.queryByRole('region')).toBeNull();

await user.click(button);
expect(screen.getByRole('region')).not.toBeNull();
await user.click(button);

expect(screen.queryByRole('region')).toBeNull();
});
});
39 changes: 39 additions & 0 deletions lib/components/Expander/Expander.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
import { useId } from 'react';
import { Disclosure } from '@headlessui/react';

export interface ExpanderProps {
label: string;
description: string;
children?: React.ReactNode;
}

export const Expander = ({ label, description, children }: ExpanderProps) => {
const labelId = useId();

return (
<Disclosure as="div" className="rounded-[20px] border-[3px] border-[#767676] p-4">
{({ open }) => (
<>
<Disclosure.Button className="flex w-full flex-col">
<div className="mb-3 flex w-full flex-row justify-between">
<span id={labelId} className="text-[20px] font-bold text-[#333333]">
{label}
</span>
<CaretDownIcon className={open ? 'rotate-180' : undefined} />
</div>
<span className="mb-4 text-start text-[12px] font-bold text-[#767676]">{description}</span>
</Disclosure.Button>
<Disclosure.Panel role="region" aria-labelledby={labelId}>
{children}
</Disclosure.Panel>
</>
)}
</Disclosure>
);
};

const CaretDownIcon = ({ className }: { className?: string }) => (
<svg width="17" height="11" viewBox="0 0 17 11" fill="none" xmlns="http://www.w3.org/2000/svg" className={className}>
<path d="M1.08521 1.56995L8.19521 8.56995L15.3052 1.56995" stroke="#767676" strokeWidth="3" />
</svg>
);
45 changes: 45 additions & 0 deletions lib/components/Expander/__snapshots__/Expander.test.tsx.snap
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html

exports[`Snapshot testing > Base button 1`] = `
<div
class="rounded-[20px] border-[3px] border-[#767676] p-4"
data-headlessui-state=""
>
<button
aria-expanded="false"
class="flex w-full flex-col"
data-headlessui-state=""
id="headlessui-disclosure-button-:r1:"
type="button"
>
<div
class="mb-3 flex w-full flex-row justify-between"
>
<span
class="text-[20px] font-bold text-[#333333]"
id=":r0:"
>
Label
</span>
<svg
fill="none"
height="11"
viewBox="0 0 17 11"
width="17"
xmlns="http://www.w3.org/2000/svg"
>
<path
d="M1.08521 1.56995L8.19521 8.56995L15.3052 1.56995"
stroke="#767676"
stroke-width="3"
/>
</svg>
</div>
<span
class="mb-4 text-start text-[12px] font-bold text-[#767676]"
>
Description
</span>
</button>
</div>
`;
1 change: 1 addition & 0 deletions lib/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import './index.css';
export { Button } from './components/Button/Button';
export { HeroCard } from './components/HeroCard/HeroCard';
export { DropdownMenu } from './components/DropdownMenu/DropdownMenu';
export { Expander } from './components/Expander/Expander';
export { NavigationBar } from './components/NavigationBar/NavigationBar';
export { RadioButton } from './components/RadioButton/RadioButton';
export { RadioButtonGroup } from './components/RadioButton/RadioButtonGroup';
Expand Down

0 comments on commit e66e9c6

Please sign in to comment.