diff --git a/components/ui/dialog.tsx b/components/ui/dialog.tsx new file mode 100644 index 0000000..91163a6 --- /dev/null +++ b/components/ui/dialog.tsx @@ -0,0 +1,101 @@ +import * as React from 'react'; +import * as DialogPrimitive from '@radix-ui/react-dialog'; +import { X } from 'lucide-react'; +import { cn } from '@/lib/utils'; + +const Dialog = DialogPrimitive.Root; + +const DialogTrigger = DialogPrimitive.Trigger; + +const DialogPortal = DialogPrimitive.Portal; + +const DialogClose = DialogPrimitive.Close; + +const DialogOverlay = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +DialogOverlay.displayName = DialogPrimitive.Overlay.displayName; + +const DialogContent = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, children, ...props }, ref) => ( + + + + {children} + + + Close + + + +)); +DialogContent.displayName = DialogPrimitive.Content.displayName; + +const DialogHeader = ({ className, ...props }: React.HTMLAttributes) => ( +
+); +DialogHeader.displayName = 'DialogHeader'; + +const DialogFooter = ({ className, ...props }: React.HTMLAttributes) => ( +
+); +DialogFooter.displayName = 'DialogFooter'; + +const DialogTitle = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +DialogTitle.displayName = DialogPrimitive.Title.displayName; + +const DialogDescription = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +DialogDescription.displayName = DialogPrimitive.Description.displayName; + +export { + Dialog, + DialogPortal, + DialogOverlay, + DialogClose, + DialogTrigger, + DialogContent, + DialogHeader, + DialogFooter, + DialogTitle, + DialogDescription, +}; diff --git a/pages/StorageCleaner/AutoRefreshToggle.tsx b/pages/StorageCleaner/AutoRefreshToggle.tsx index a261cc3..949d31b 100644 --- a/pages/StorageCleaner/AutoRefreshToggle.tsx +++ b/pages/StorageCleaner/AutoRefreshToggle.tsx @@ -1,5 +1,3 @@ -import { Box, Switch, Typography } from '@mui/material'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; import { useLazyTranslation } from '@/utils/useLazyTranslation'; interface AutoRefreshToggleProps { @@ -10,17 +8,19 @@ interface AutoRefreshToggleProps { export default function AutoRefreshToggle({ autoRefresh, onChange }: AutoRefreshToggleProps) { const { t } = useLazyTranslation('storageCleaner'); return ( - - +
+ {t('storageCleaner:autoRefresh')} - - onChange(e.target.checked)} - color="warning" - sx={storageCleanerPageStyles.AUTO_REFRESH_SWITCH} - /> - + +
); } diff --git a/pages/StorageCleaner/ErrorDisplay.tsx b/pages/StorageCleaner/ErrorDisplay.tsx index 6398070..b72b2b7 100644 --- a/pages/StorageCleaner/ErrorDisplay.tsx +++ b/pages/StorageCleaner/ErrorDisplay.tsx @@ -1,6 +1,4 @@ -import { Box, Container, Typography } from '@mui/material'; -import WarningIcon from '@mui/icons-material/Warning'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; +import { AlertCircle } from 'lucide-react'; import { useLazyTranslation } from '@/utils/useLazyTranslation'; interface ErrorDisplayProps { @@ -10,35 +8,16 @@ interface ErrorDisplayProps { export default function ErrorDisplay({ error }: ErrorDisplayProps) { const { t } = useLazyTranslation('storageCleaner'); return ( - - - - - - {error} - - +
+
+
+ +

{error}

+

{t('storageCleaner:errorStandardOnly')} - - - - +

+
+
+
); } diff --git a/pages/StorageCleaner/OptionItem.tsx b/pages/StorageCleaner/OptionItem.tsx index f4f8bfb..29908fb 100644 --- a/pages/StorageCleaner/OptionItem.tsx +++ b/pages/StorageCleaner/OptionItem.tsx @@ -1,6 +1,4 @@ -import { Box, Checkbox, Typography } from '@mui/material'; import { formatSize } from '@/utils/storageCleaner'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; import { useLazyTranslation } from '@/utils/useLazyTranslation'; interface OptionItemProps { @@ -20,32 +18,37 @@ export default function OptionItem({ }: OptionItemProps) { const { t } = useLazyTranslation('storageCleaner'); return ( - - - +
+ {t(labelKey)} - + {size !== undefined && size > 0 ? ( - + {isCount ? `${size} ${t('storageCleaner:countUnit')}` : formatSize(size)} - + ) : ( - + {t('storageCleaner:noData')} - + )} - - + - +
); } diff --git a/pages/StorageCleaner/StorageCleanerConfirm.tsx b/pages/StorageCleaner/StorageCleanerConfirm.tsx index 0a7c3de..29c28ec 100644 --- a/pages/StorageCleaner/StorageCleanerConfirm.tsx +++ b/pages/StorageCleaner/StorageCleanerConfirm.tsx @@ -1,15 +1,13 @@ +import { Button } from '@/components/ui/button'; import { - Box, - Chip, Dialog, - DialogActions, DialogContent, + DialogDescription, + DialogFooter, + DialogHeader, DialogTitle, - Typography, -} from '@mui/material'; +} from '@/components/ui/dialog'; import type { StorageCleanerOptions } from '@/types/storage'; -import Button from '@/components/Button'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; import { useLazyTranslation } from '@/utils/useLazyTranslation'; export interface StorageCleanerConfirmProps { @@ -32,69 +30,53 @@ export function StorageCleanerConfirm({ .map(([key, _]) => t(`storageCleaner:options.${key as keyof StorageCleanerOptions}`)); return ( - - - {t('storageCleaner:confirmTitle')} - + !isOpen && onClose()}> + + + + {t('storageCleaner:confirmTitle')} + + - - - {t('storageCleaner:confirmDesc')} - +
+ + {t('storageCleaner:confirmDesc')} + - - {selectedOptions.map((label) => ( - - ))} - +
+ {selectedOptions.map((label) => ( + + {label} + + ))} +
- - - - ⚠️ - {' '} - {t('storageCleaner:irreversible')} - - +
+ + + ⚠️ + {' '} + {t('storageCleaner:irreversible')} + +
+
+ + + + +
- - - - -
); } diff --git a/pages/StorageCleaner/StorageOptionsGrid.tsx b/pages/StorageCleaner/StorageOptionsGrid.tsx index a631d61..c6cba96 100644 --- a/pages/StorageCleaner/StorageOptionsGrid.tsx +++ b/pages/StorageCleaner/StorageOptionsGrid.tsx @@ -1,7 +1,5 @@ -import { Box, Checkbox, Divider, Grid, Typography } from '@mui/material'; import type { StorageCleanerOptions } from '@/types/storage'; import OptionItem from './OptionItem'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; import { useLazyTranslation } from '@/utils/useLazyTranslation'; interface StorageOptionsGridProps { @@ -17,7 +15,7 @@ export default function StorageOptionsGrid({ options, sizes, allSelected, - someSelected, + someSelected: _someSelected, onOptionChange, onSelectAll, }: StorageOptionsGridProps) { @@ -33,11 +31,11 @@ export default function StorageOptionsGrid({ ]; return ( - - - +
+
+
{optionKeys.map(({ key, isCount }) => ( - +
onOptionChange(key)} /> - +
))} -
- - - - - {t('storageCleaner:selectAll')} - - +
+
+
+ {t('storageCleaner:selectAll')} + onSelectAll(e.target.checked)} - color="warning" - sx={storageCleanerPageStyles.OPTIONS_GRID_CHECKBOX} + className="h-4 w-4 rounded border-gray-300 text-amber-500 focus:ring-amber-500" /> - - +
+
); } diff --git a/pages/StorageCleaner/index.tsx b/pages/StorageCleaner/index.tsx index 22682a2..6790715 100644 --- a/pages/StorageCleaner/index.tsx +++ b/pages/StorageCleaner/index.tsx @@ -1,8 +1,6 @@ -import { Box, CircularProgress, Container } from '@mui/material'; -import Button from '@/components/Button'; +import { Button } from '@/components/ui/button'; import { useSnackbar } from '@/components/GlobalSnackbar'; import StorageCleanerConfirm from '@/pages/StorageCleaner/StorageCleanerConfirm'; -import { storageCleanerPageStyles } from '@/config/pageTheme'; import { useStorageCleaner } from './useStorageCleaner'; import DomainHeader from './DomainHeader'; import StorageOptionsGrid from './StorageOptionsGrid'; @@ -38,9 +36,9 @@ export default function Index() { if (isInitializing) { return ( - - - +
+
+
); } @@ -49,8 +47,8 @@ export default function Index() { } return ( - - +
+
- +
- +
); }