diff --git a/packages/react/src/components/Button/index.scss b/packages/react/src/components/Button/index.scss
index 268d9ea..5959124 100644
--- a/packages/react/src/components/Button/index.scss
+++ b/packages/react/src/components/Button/index.scss
@@ -1,10 +1,72 @@
.c__button {
- background-image: var(--c--theme--colors--primary-gradient);
- padding: 8px 30px;
- border-radius: var(--c--components--button--border-radius);
+ display: flex;
+ align-items: center;
border: none;
- box-shadow: var(--c--components--button--shadow);
- color: white;
- font-weight: bold;
cursor: pointer;
+ transition: background-color var(--c--theme--transitions--duration) var(--c--theme--transitions--ease-out);
+
+ padding: 0 var(--c--theme--spacings--s);
+
+ height: var(--c--components--button--height);
+ border-radius: var(--c--components--button--border-radius);
+ font-size: var(--c--components--button--font-size);
+ font-weight: var(--c--components--button--font-weight);
+
+ &--primary {
+ background-color: var(--c--theme--colors--primary-500);
+ color: var(--c--theme--colors--primary-text);
+
+ &:hover {
+ background-color: var(--c--theme--colors--primary-600);
+ }
+
+ &:active {
+ background-color: var(--c--theme--colors--primary-500);
+ }
+ }
+
+ &--secondary {
+ background-color: var(--c--theme--colors--secondary-500);
+ color: var(--c--theme--colors--secondary-text);
+
+ &:hover {
+ background-color: var(--c--theme--colors--secondary-600);
+ }
+
+ &:active {
+ background-color: var(--c--theme--colors--secondary-500);
+ }
+ }
+
+ &--tertiary {
+ background-color: transparent;
+ color: var(--c--theme--colors--greyscale-800);
+
+ &:hover {
+ color: var(--c--theme--colors--greyscale-900);
+ }
+
+ &:active {
+ color: var(--c--theme--colors--greyscale-800);
+ }
+ }
+
+ &--danger {
+ background-color: var(--c--theme--colors--danger-500);
+ color: var(--c--theme--colors--danger-text);
+
+ &:hover {
+ background-color: var(--c--theme--colors--danger-600);
+ }
+
+ &:active {
+ background-color: var(--c--theme--colors--danger-500);
+ }
+ }
+
+ &[disabled] {
+ cursor: not-allowed;
+ background-color: var(--c--theme--colors--greyscale-200);
+ color: var(--c--theme--colors--greyscale-400);
+ }
}
\ No newline at end of file
diff --git a/packages/react/src/components/Button/index.spec.tsx b/packages/react/src/components/Button/index.spec.tsx
index 00edb04..52f02a9 100644
--- a/packages/react/src/components/Button/index.spec.tsx
+++ b/packages/react/src/components/Button/index.spec.tsx
@@ -1,7 +1,8 @@
import { describe, expect, it } from "vitest";
-import { render, screen } from "@testing-library/react";
+import { act, render, screen, waitFor } from "@testing-library/react";
import React from "react";
import { buildTheme, loadTokens } from "tests/Theme";
+import userEvent from "@testing-library/user-event";
import { Button } from "./index";
describe("", () => {
@@ -11,10 +12,33 @@ describe("", () => {
expect(button.classList.contains("c__button")).toBe(true);
});
+ it("call onClick when click occurs", async () => {
+ const user = userEvent.setup();
+ const handleClick = vi.fn();
+ render();
+ const button = screen.getByRole("button", { name: "Test button" });
+ expect(handleClick).not.toBeCalled();
+ user.click(button);
+ await waitFor(() => expect(handleClick).toHaveBeenCalled());
+ });
+
+ it("does not call onClick when click occurs on a disabled button", async () => {
+ const user = userEvent.setup();
+ const handleClick = vi.fn();
+ render(
+
+ );
+ const button = screen.getByRole("button", { name: "Test button" });
+ expect(handleClick).not.toBeCalled();
+ await act(async () => user.click(button));
+ expect(handleClick).not.toHaveBeenCalled();
+ });
+
it("uses custom token", async () => {
await buildTheme();
const tokens = await loadTokens();
expect(tokens.components.button["border-radius"]).toBeDefined();
- expect(tokens.components.button.shadow).toBeDefined();
});
});
diff --git a/packages/react/src/components/Button/index.stories.tsx b/packages/react/src/components/Button/index.stories.tsx
index daed279..68b1b2c 100644
--- a/packages/react/src/components/Button/index.stories.tsx
+++ b/packages/react/src/components/Button/index.stories.tsx
@@ -9,7 +9,27 @@ export default {
const Template: ComponentStory = (args) => ;
-export const Default = Template.bind({});
-Default.args = {
- children: "Amazing button",
+export const Primary = Template.bind({});
+Primary.args = {
+ children: "Label",
+ color: "primary",
+};
+
+export const Secondary = Template.bind({});
+Secondary.args = {
+ children: "Label",
+ color: "secondary",
+};
+
+export const Tertiary = Template.bind({});
+Tertiary.args = {
+ children: "Label",
+ color: "tertiary",
+};
+
+export const Disabled = Template.bind({});
+Disabled.args = {
+ children: "Label",
+ color: "primary",
+ disabled: true,
};
diff --git a/packages/react/src/components/Button/index.tsx b/packages/react/src/components/Button/index.tsx
index 49b7c34..5a25770 100644
--- a/packages/react/src/components/Button/index.tsx
+++ b/packages/react/src/components/Button/index.tsx
@@ -1,7 +1,13 @@
-import React, { PropsWithChildren } from "react";
+import React, { ButtonHTMLAttributes } from "react";
-interface Props extends PropsWithChildren {}
+interface Props extends ButtonHTMLAttributes {
+ color?: "primary" | "secondary" | "tertiary";
+}
-export const Button = ({ children }: Props) => {
- return ;
+export const Button = ({ children, color = "primary", ...props }: Props) => {
+ return (
+
+ );
};
diff --git a/packages/react/src/components/Button/tokens.ts b/packages/react/src/components/Button/tokens.ts
index 32cb2e5..cc1eadb 100644
--- a/packages/react/src/components/Button/tokens.ts
+++ b/packages/react/src/components/Button/tokens.ts
@@ -2,7 +2,9 @@ import { DefaultTokens } from "@openfun/cunningham-tokens";
export const tokens = (defaults: DefaultTokens) => {
return {
- "border-radius": "5px",
- shadow: "0px 0px 10px 1px " + defaults.theme.colors.primary + ";",
+ "border-radius": "2px",
+ height: "48px",
+ "font-size": defaults.theme.typo.l,
+ "font-weight": defaults.theme.typo.medium,
};
};
diff --git a/packages/react/src/index.scss b/packages/react/src/index.scss
index 6bb0a23..d6dbb10 100644
--- a/packages/react/src/index.scss
+++ b/packages/react/src/index.scss
@@ -1,8 +1,13 @@
@import "@fontsource/roboto/100";
@import "@fontsource/roboto/300";
@import "@fontsource/roboto/400";
+@import "@fontsource/roboto/500";
@import "@fontsource/roboto/700";
@import "@fontsource/roboto/900";
@import "cunningham-tokens";
@import '@openfun/cunningham-tokens/default-tokens';
-@import './components/Button';
\ No newline at end of file
+@import './components/Button';
+
+* {
+ font-family: var(--c--theme--typo--font-base);
+}
\ No newline at end of file