diff --git a/package.json b/package.json
index b146ded..882a5df 100644
--- a/package.json
+++ b/package.json
@@ -21,7 +21,10 @@
},
"devDependencies": {
"@chromatic-com/storybook": "1",
- "@eslint/js": "^9.16.0",
+ "@emotion/babel-plugin": "^11.13.5",
+ "@emotion/react": "^11.14.0",
+ "@emotion/styled": "^11.14.0",
+ "@eslint/js": "^9.17.0",
"@floating-ui/react": "^0.26.28",
"@ianvs/prettier-plugin-sort-imports": "^4.4.0",
"@material/material-color-utilities": "^0.3.0",
@@ -33,22 +36,21 @@
"@storybook/blocks": "^8.4.7",
"@storybook/react": "^8.4.7",
"@storybook/react-vite": "^8.4.7",
- "@types/react": "^18.3.14",
- "@types/react-dom": "^18.3.2",
+ "@types/react": "^18.3.16",
+ "@types/react-dom": "^18.3.5",
"@vitejs/plugin-react": "^4.3.4",
- "chromatic": "^11.20.0",
+ "chromatic": "^11.20.2",
"clsx": "^2.1.1",
- "eslint": "^9.16.0",
+ "eslint": "^9.17.0",
"eslint-plugin-react-hooks": "^5.1.0",
"eslint-plugin-react-refresh": "^0.4.16",
"glob": "^10.4.5",
"globals": "^15.13.0",
"prettier": "^3.4.2",
- "sass": "^1.82.0",
+ "sass": "^1.83.0",
"storybook": "^8.4.7",
- "styled-jsx": "^5.1.6",
"typescript": "^5.7.2",
- "typescript-eslint": "^8.17.0",
+ "typescript-eslint": "^8.18.0",
"vite": "^5.4.11",
"vite-plugin-dts": "^4.3.0"
},
diff --git a/src/components/date-picker/MenuButton.tsx b/src/components/date-picker/MenuButton.tsx
index 88522f4..53ab154 100644
--- a/src/components/date-picker/MenuButton.tsx
+++ b/src/components/date-picker/MenuButton.tsx
@@ -1,3 +1,4 @@
+import { css } from '@emotion/react'
import { mdiChevronLeft, mdiChevronRight, mdiMenuDown } from '@mdi/js'
import Icon from '@mdi/react'
import { Ripple } from '@/ripple/Ripple'
@@ -15,41 +16,44 @@ export function MenuButton({
onClick?(): void
}) {
return (
-
+
{children && (
-
+
{children}
)}
-
)
}
diff --git a/src/components/date-picker/SelectDay.tsx b/src/components/date-picker/SelectDay.tsx
index 66b7c95..540835f 100644
--- a/src/components/date-picker/SelectDay.tsx
+++ b/src/components/date-picker/SelectDay.tsx
@@ -1,7 +1,79 @@
-import clsx from 'clsx'
+import { css } from '@emotion/react'
+import styled from '@emotion/styled'
import { ripple } from '@/ripple/ripple-effect'
import { getFormatCalendar, isSameDay } from './calendar'
+const Day = styled.time<{
+ isToday: boolean
+ selected: boolean
+ disabled: boolean
+}>`
+ display: inline-flex;
+ align-items: center;
+ justify-content: center;
+ box-sizing: border-box;
+ width: 40px;
+ height: 40px;
+ border-radius: 50%;
+ overflow: hidden;
+ transition: all 200ms;
+ margin: 2px 0;
+
+ &:active {
+ background: rgba(0 0 0 / 0.08);
+ }
+
+ ${(props) =>
+ props.isToday &&
+ css`
+ border: solid 1px;
+ overflow: hidden;
+ `}
+
+ ${(props) =>
+ props.disabled
+ ? css`
+ background: none;
+ filter: grayscale(1) opacity(0.6);
+ `
+ : css`
+ cursor: pointer;
+ revert: true;
+ `}
+
+
+
+ ${(props) =>
+ props.selected &&
+ css`
+ background: var(--md-sys-color-primary);
+ color: var(--md-sys-color-on-primary);
+ `}
+
+
+ ${(props) =>
+ !props.disabled &&
+ !props.selected &&
+ css`
+ @media (any-hover: hover) {
+ &:hover {
+ background: rgba(0 0 0 / 0.04);
+ }
+ }
+ `}
+`
+
+const SelectDayRow = styled.div`
+ display: flex;
+ align-items: center;
+ justify-content: space-around;
+`
+
+const SelectDayHeader = styled(SelectDayRow)`
+ margin-block-start: 30px;
+ margin-block-end: 16px;
+`.withComponent('header')
+
export function SelectDay({
year,
month,
@@ -15,8 +87,14 @@ export function SelectDay({
}) {
const calendar = getFormatCalendar(year, month)
return (
-
-
+
+
{['Mon', 'Tue', 'Wen', 'Thu', 'Fri', 'Sat', 'Sun'].map(
(day) => (
@@ -24,21 +102,21 @@ export function SelectDay({
),
)}
-
-
+
+
{calendar.map((row, i) => (
-
+
{row.map((col, j) => (
-
+
))}
-
+
))}
-
-
)
}
diff --git a/src/components/date-picker/SelectYear.tsx b/src/components/date-picker/SelectYear.tsx
index 0d3aa7d..cd67594 100644
--- a/src/components/date-picker/SelectYear.tsx
+++ b/src/components/date-picker/SelectYear.tsx
@@ -1,6 +1,58 @@
-import clsx from 'clsx'
+import { css } from '@emotion/react'
+import styled from '@emotion/styled'
import { ripple } from '@/ripple/ripple-effect'
+const Ul = styled.ul`
+ all: unset;
+ display: grid;
+ grid-template-columns: repeat(3, 1fr);
+ align-items: center;
+ justify-items: center;
+ -webkit-tap-highlight-color: transparent; // remove webkit blue tap effect
+`
+
+const Cell = styled.div`
+ display: inline-block;
+ width: 76px;
+ height: 36px;
+ line-height: 36px;
+ text-align: center;
+ border-radius: 2rem;
+ color: var(--md-sys-color-on-surface-variant);
+ overflow: hidden;
+ transition: all 200ms;
+ user-select: none;
+`
+
+const Li = styled.li<{ active: boolean }>`
+ all: unset;
+ display: grid;
+ width: 100%;
+ place-items: center;
+ padding: 6px 0;
+ cursor: pointer;
+ overflow: hidden;
+
+ @media (any-hover: hover) {
+ &:hover {
+ background: rgba(0 0 0 / 0.04);
+ }
+ }
+
+ &:active {
+ background: rgba(0 0 0 / 0.08);
+ }
+
+ ${(props) =>
+ props.active &&
+ css`
+ & > ${Cell} {
+ background: var(--md-sys-color-primary);
+ color: var(--md-sys-color-on-primary);
+ }
+ `}
+`
+
export function SelectYear({
current,
onChange,
@@ -9,67 +61,24 @@ export function SelectYear({
onChange?: (year: number) => void
}) {
return (
-
+
{getClosest15Years(current).map((year) => (
- - onChange?.(year)}
key={year}
ref={(el) => el && ripple(el)}
>
-
+
{
new Intl.DateTimeFormat(undefined, {
year: 'numeric',
}).formatToParts(new Date(year, 1, 1))[0].value
}
- |
-
+
+
))}
-
-
+
)
}
diff --git a/src/composition/PopoverHolder/PopoverHolder.tsx b/src/composition/PopoverHolder/PopoverHolder.tsx
index 3776161..6fcc604 100644
--- a/src/composition/PopoverHolder/PopoverHolder.tsx
+++ b/src/composition/PopoverHolder/PopoverHolder.tsx
@@ -1,4 +1,5 @@
import { forwardRef, useImperativeHandle, useState } from 'react'
+import { css } from '@emotion/react'
import {
autoUpdate,
flip,
@@ -72,9 +73,14 @@ export const PopoverHolder = forwardRef<
}))
return (
-
+
)
})
diff --git a/src/composition/TooltipHolder/TooltipHolder.tsx b/src/composition/TooltipHolder/TooltipHolder.tsx
index ea36d6f..577e88d 100644
--- a/src/composition/TooltipHolder/TooltipHolder.tsx
+++ b/src/composition/TooltipHolder/TooltipHolder.tsx
@@ -1,4 +1,5 @@
import { forwardRef, useImperativeHandle, useState } from 'react'
+import { css } from '@emotion/react'
import {
autoUpdate,
flip,
@@ -94,9 +95,14 @@ export const TooltipHolder = forwardRef(function TooltipHolder(
}))
return (
-
+
)
})
diff --git a/src/vite-env.d.ts b/src/vite-env.d.ts
index 11f02fe..683cbd2 100644
--- a/src/vite-env.d.ts
+++ b/src/vite-env.d.ts
@@ -1 +1,2 @@
///
+///
diff --git a/tsconfig.json b/tsconfig.json
index 7f49dc3..30828ab 100644
--- a/tsconfig.json
+++ b/tsconfig.json
@@ -12,6 +12,7 @@
"resolveJsonModule": true,
"isolatedModules": true,
"jsx": "react-jsx",
+ "jsxImportSource": "@emotion/react",
/* Linting */
"strict": true,
diff --git a/vite.config.ts b/vite.config.ts
index 852a4e9..edc2c6a 100644
--- a/vite.config.ts
+++ b/vite.config.ts
@@ -54,8 +54,9 @@ export default defineConfig({
},
plugins: [
react({
+ jsxImportSource: '@emotion/react',
babel: {
- plugins: [['styled-jsx/babel', { optimizeForSpeed: true }]],
+ plugins: ['@emotion/babel-plugin'],
},
}),
dts({