diff --git a/.changeset/fair-knives-protect.md b/.changeset/fair-knives-protect.md
new file mode 100644
index 000000000..353932cad
--- /dev/null
+++ b/.changeset/fair-knives-protect.md
@@ -0,0 +1,5 @@
+---
+"@4design/for-ui": minor
+---
+
+refactor(Button): MUI剥がし
diff --git a/package-lock.json b/package-lock.json
index 39c876e1f..1e68edcf4 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -19,7 +19,7 @@
"npm-run-all2": "6.1.2",
"prettier": "3.2.5",
"turbo": "1.11.2",
- "typescript": "5.1.6"
+ "typescript": "5.4.5"
},
"engines": {
"node": ">=14.0.0",
@@ -5771,11 +5771,14 @@
}
},
"node_modules/@storybook/builder-webpack4/node_modules/watchpack/chokidar2": {
- "version": "0.0.1",
+ "version": "2.0.0",
"dev": true,
"optional": true,
"dependencies": {
"chokidar": "^2.1.8"
+ },
+ "engines": {
+ "node": "<8.10.0"
}
},
"node_modules/@storybook/builder-webpack4/node_modules/webpack": {
@@ -28469,9 +28472,9 @@
}
},
"node_modules/typescript": {
- "version": "5.1.6",
- "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.1.6.tgz",
- "integrity": "sha512-zaWCozRZ6DLEWAWFrVDz1H6FVXzUSfTy5FUMWsQlU8Ym5JP9eO4xkTIROFCQvhQf61z6O/G6ugw3SgAnvvm+HA==",
+ "version": "5.4.5",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.4.5.tgz",
+ "integrity": "sha512-vcI4UpRgg81oIRUFwR0WSIHKt11nJ7SAVlYNIu+QpqeyXP+gpQJy/Z4+F0aGxSE4MqwjyXvW/TzgkLAx2AGHwQ==",
"bin": {
"tsc": "bin/tsc",
"tsserver": "bin/tsserver"
@@ -30636,7 +30639,7 @@
"react-hook-form": "7.45.4",
"react-icons": "4.10.1",
"tailwindcss": "3.4.3",
- "typescript": "5.1.6",
+ "typescript": "5.4.5",
"vite": "3.2.5",
"vitest": "0.33.0",
"webpack": "5.88.2",
@@ -33004,7 +33007,7 @@
"react-transition-group": "4.4.5",
"tailwind-merge": "1.14.0",
"tailwindcss": "3.4.3",
- "typescript": "5.1.6",
+ "typescript": "5.4.5",
"vite": "3.2.5",
"vitest": "0.33.0",
"webpack": "5.88.2",
@@ -53942,9 +53945,9 @@
}
},
"typescript": {
- "version": "5.1.6",
- "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.1.6.tgz",
- "integrity": "sha512-zaWCozRZ6DLEWAWFrVDz1H6FVXzUSfTy5FUMWsQlU8Ym5JP9eO4xkTIROFCQvhQf61z6O/G6ugw3SgAnvvm+HA=="
+ "version": "5.4.5",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.4.5.tgz",
+ "integrity": "sha512-vcI4UpRgg81oIRUFwR0WSIHKt11nJ7SAVlYNIu+QpqeyXP+gpQJy/Z4+F0aGxSE4MqwjyXvW/TzgkLAx2AGHwQ=="
},
"ufo": {
"version": "1.1.2",
diff --git a/package.json b/package.json
index 3a5315aca..8c84465db 100644
--- a/package.json
+++ b/package.json
@@ -41,7 +41,7 @@
"npm-run-all2": "6.1.2",
"prettier": "3.2.5",
"turbo": "1.11.2",
- "typescript": "5.1.6"
+ "typescript": "5.4.5"
},
"volta": {
"node": "16.20.2"
diff --git a/packages/for-ui/package.json b/packages/for-ui/package.json
index 4dec3b8df..160fbfad5 100644
--- a/packages/for-ui/package.json
+++ b/packages/for-ui/package.json
@@ -95,7 +95,7 @@
"react-hook-form": "7.45.4",
"react-icons": "4.10.1",
"tailwindcss": "3.4.3",
- "typescript": "5.1.6",
+ "typescript": "5.4.5",
"vite": "3.2.5",
"vitest": "0.33.0",
"webpack": "5.88.2",
diff --git a/packages/for-ui/src/button/Button.test.tsx b/packages/for-ui/src/button/Button.test.tsx
index e8b308d23..3d9e20d8f 100644
--- a/packages/for-ui/src/button/Button.test.tsx
+++ b/packages/for-ui/src/button/Button.test.tsx
@@ -1,3 +1,4 @@
+import { FC, ReactNode } from 'react';
import { MdOutlineCheck } from 'react-icons/md';
import { describe, expect, it } from 'vitest';
import { render, screen } from '@testing-library/react';
@@ -93,3 +94,16 @@ describe('Button', () => {
expect(element).toBeInTheDocument();
});
});
+
+describe('Type', () => {
+ it('is semantically correct for React component using as props', async () => {
+ const Link: FC<{ to: string; children?: ReactNode }> = ({ to, children }) => {children};
+ render(
+ ,
+ );
+ const element = await screen.findByRole('link', { name: 'test' });
+ expect(element).toBeInTheDocument();
+ });
+});
diff --git a/packages/for-ui/src/button/Button.tsx b/packages/for-ui/src/button/Button.tsx
index bd1f965eb..2b9e21155 100644
--- a/packages/for-ui/src/button/Button.tsx
+++ b/packages/for-ui/src/button/Button.tsx
@@ -1,6 +1,4 @@
-import { Children, ElementType, forwardRef, MouseEvent, MouseEventHandler, ReactNode, useMemo } from 'react';
-import MuiButton, { ButtonUnstyledProps as MuiButtonProps } from '@mui/base/ButtonUnstyled';
-import { LoadingButtonProps } from '@mui/lab/LoadingButton';
+import { Children, ElementType, forwardRef, ReactNode, useMemo } from 'react';
import { Loader } from '../loader';
import { ComponentPropsWithAs, Element, Ref } from '../system/componentType';
import { fsx } from '../system/fsx';
@@ -10,7 +8,7 @@ import { walkChildren } from '../system/walkChildren';
type Child = Exclude> | string;
export type ButtonProps = ComponentPropsWithAs<
- Omit, 'href' | 'children' | 'onClick'> & {
+ {
/**
* 種類を指定
*
@@ -57,48 +55,6 @@ export type ButtonProps = ComponentPropsWithA
disabled?: boolean;
- /**
- * 先頭に表示するアイコンを指定
- *
- * @deprecated childrenを使用してください
- * ```
- *
- * ```
- */
- startIcon?: ReactNode;
-
- /**
- * 末尾に表示するアイコンを指定
- *
- * @deprecated childrenを使用してください
- * ```
- *
- * ```
- */
- endIcon?: ReactNode;
-
- /**
- * 読み込み中のアイコンを表示する場所を指定
- *
- * @deprecated デザインの仕様変更に伴い表示位置は固定になりました
- */
- loadingPosition?: LoadingButtonProps['loadingPosition'];
-
- /**
- * colorを指定する場合に指定
- *
- * @deprecated intention propsを使ってください
- */
- color?: 'primary' | 'secondary' | 'default';
-
- onClick?: MouseEventHandler;
-
className?: string;
},
As
@@ -130,56 +86,41 @@ export const Button: ButtonComponent = forwardRef(
{
as,
variant = 'outlined',
- intention: passedIntention = 'subtle',
+ intention = 'subtle',
size = 'large',
loading = false,
- startIcon,
- endIcon,
- color,
children,
className,
+ disabled,
onClick,
...rest
}: ButtonProps,
ref?: Ref,
): Element => {
- const component = as || 'button';
+ const Component = as || 'button';
const childTexts = useMemo(() => Children.map(children, extractText) || [], [children]);
const structure: Structure = useMemo(() => {
- if ((childTexts.at(0) && !childTexts.at(-1)) || (endIcon && children)) {
+ if (childTexts.at(0) && !childTexts.at(-1)) {
return 'text-icon';
}
- if ((!childTexts.at(0) && childTexts.at(-1)) || (startIcon && children)) {
+ if (!childTexts.at(0) && childTexts.at(-1)) {
return 'icon-text';
}
- if (!childTexts.at(0) || (startIcon && !children)) {
+ if (!childTexts.at(0)) {
return 'icon';
}
return 'text';
- }, [startIcon, endIcon, children, childTexts]);
-
- // Legacy support for color props
- // If not needed, rename the passedIntention to intention.
-
- const intention = color
- ? (
- {
- primary: 'primary',
- secondary: 'secondary',
- default: 'primary',
- } as const
- )[color]
- : passedIntention;
+ }, [childTexts]);
return (
-
- component={component}
+ )}
- onClick={(e: MouseEvent) => {
+ {...rest}
+ onClick={(e) => {
if (loading) {
return;
}
onClick?.(e);
}}
>
- {startIcon}
{children}
- {endIcon}
{loading && (
)}
-
+
);
},
);
diff --git a/packages/for-ui/src/system/componentType.ts b/packages/for-ui/src/system/componentType.ts
index 906c7dda2..3fba3b656 100644
--- a/packages/for-ui/src/system/componentType.ts
+++ b/packages/for-ui/src/system/componentType.ts
@@ -15,7 +15,7 @@ export type AsProps = {
export type ComponentPropsWithAs = AsProps &
Props &
RefProps &
- PreservedOmit, keyof (Props & AsProps & RefProps)>;
+ NoInfer, keyof (Props & AsProps & RefProps)>>;
export type ElementTypeToHTMLElement = Element extends keyof HTMLElementTagNameMap
? HTMLElementTagNameMap[Element]