色彩优化
This commit is contained in:
136
src/App.jsx
136
src/App.jsx
@@ -1,144 +1,10 @@
|
||||
import React from "react";
|
||||
import { BrowserRouter } from "react-router-dom";
|
||||
import { ConfigProvider, theme } from "antd";
|
||||
import { ThemeProvider } from "./contexts/ThemeContext";
|
||||
import { AuthProvider } from "./contexts/AuthContext";
|
||||
import AppRoutes from "./routes/AppRoutes";
|
||||
import { useTheme } from "./contexts/ThemeContext";
|
||||
import { RootStoreProvider } from "./contexts/RootStore";
|
||||
|
||||
const ThemedApp = () => {
|
||||
const { isDarkMode } = useTheme();
|
||||
|
||||
return (
|
||||
<ConfigProvider
|
||||
theme={{
|
||||
algorithm: isDarkMode ? theme.darkAlgorithm : theme.defaultAlgorithm,
|
||||
token: {
|
||||
// 颜色
|
||||
colorPrimary: '#006494',
|
||||
colorSuccess: '#16A34A',
|
||||
colorWarning: '#FBBF24',
|
||||
colorError: '#DC2626',
|
||||
colorInfo: '#006494',
|
||||
|
||||
// 中性色
|
||||
colorText: isDarkMode ? 'rgba(255, 255, 255, 0.87)' : 'rgba(0, 0, 0, 0.87)',
|
||||
colorTextSecondary: isDarkMode ? 'rgba(255, 255, 255, 0.60)' : 'rgba(0, 0, 0, 0.60)',
|
||||
colorTextTertiary: isDarkMode ? 'rgba(255, 255, 255, 0.38)' : 'rgba(0, 0, 0, 0.38)',
|
||||
colorBgContainer: isDarkMode ? '#121212' : '#ffffff',
|
||||
colorBgElevated: isDarkMode ? '#242424' : '#ffffff',
|
||||
colorBorder: isDarkMode ? 'rgba(255, 255, 255, 0.12)' : 'rgba(0, 0, 0, 0.12)',
|
||||
|
||||
// 字体
|
||||
fontFamily: '"Roboto", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif',
|
||||
fontSize: 16,
|
||||
|
||||
// 圆角
|
||||
borderRadius: 8,
|
||||
borderRadiusLG: 12,
|
||||
borderRadiusSM: 4,
|
||||
borderRadiusXS: 2,
|
||||
|
||||
// 线框
|
||||
lineWidth: 1,
|
||||
lineType: 'solid',
|
||||
|
||||
// 动画
|
||||
motionDurationMid: '0.2s',
|
||||
motionEaseInOut: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
||||
motionEaseOut: 'cubic-bezier(0.0, 0, 0.2, 1)',
|
||||
motionEaseIn: 'cubic-bezier(0.4, 0, 1, 1)',
|
||||
|
||||
// 阴影
|
||||
boxShadow: isDarkMode
|
||||
? '0 1px 3px 0 rgba(0, 0, 0, 0.3), 0 4px 8px 3px rgba(0, 0, 0, 0.15)'
|
||||
: '0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 4px 8px 3px rgba(0, 0, 0, 0.08)',
|
||||
boxShadowSecondary: isDarkMode
|
||||
? '0 4px 12px 6px rgba(0, 0, 0, 0.4)'
|
||||
: '0 4px 12px 6px rgba(0, 0, 0, 0.12)',
|
||||
},
|
||||
components: {
|
||||
// 按钮样式
|
||||
Button: {
|
||||
borderRadius: 8,
|
||||
controlHeight: 40,
|
||||
paddingContentHorizontal: 24,
|
||||
primaryShadow: 'none',
|
||||
},
|
||||
// 输入框样式
|
||||
Input: {
|
||||
controlHeight: 48,
|
||||
borderRadius: 8,
|
||||
paddingContentHorizontal: 16,
|
||||
variant: 'filled',
|
||||
},
|
||||
// 选择器样式
|
||||
Select: {
|
||||
controlHeight: 48,
|
||||
borderRadius: 8,
|
||||
variant: 'filled',
|
||||
},
|
||||
// 表单样式
|
||||
Form: {
|
||||
labelFontSize: 14,
|
||||
margin: 24,
|
||||
itemMarginBottom: 24,
|
||||
variant: 'filled',
|
||||
},
|
||||
// 卡片样式
|
||||
Card: {
|
||||
borderRadius: 12,
|
||||
padding: 24,
|
||||
},
|
||||
// 模态框样式
|
||||
Modal: {
|
||||
borderRadius: 12,
|
||||
paddingContentHorizontal: 24,
|
||||
paddingContentVertical: 24,
|
||||
},
|
||||
// 下拉菜单样式
|
||||
Dropdown: {
|
||||
borderRadius: 8,
|
||||
controlHeight: 40,
|
||||
},
|
||||
// 标签页样式
|
||||
Tabs: {
|
||||
inkBarColor: '#006494',
|
||||
cardGutter: 8,
|
||||
},
|
||||
// 表格样式
|
||||
Table: {
|
||||
borderRadius: 8,
|
||||
padding: 16,
|
||||
cellPaddingBlock: 16,
|
||||
cellPaddingInline: 16,
|
||||
},
|
||||
// 其他组件的 filled 变体设置
|
||||
DatePicker: {
|
||||
variant: 'filled',
|
||||
},
|
||||
TimePicker: {
|
||||
variant: 'filled',
|
||||
},
|
||||
Cascader: {
|
||||
variant: 'filled',
|
||||
},
|
||||
TreeSelect: {
|
||||
variant: 'filled',
|
||||
},
|
||||
AutoComplete: {
|
||||
variant: 'filled',
|
||||
},
|
||||
},
|
||||
}}
|
||||
>
|
||||
<div className={isDarkMode ? "dark" : ""}>
|
||||
<AppRoutes />
|
||||
</div>
|
||||
</ConfigProvider>
|
||||
);
|
||||
};
|
||||
|
||||
const App = () => {
|
||||
return (
|
||||
@@ -146,7 +12,7 @@ const App = () => {
|
||||
<AuthProvider>
|
||||
<RootStoreProvider>
|
||||
<ThemeProvider>
|
||||
<ThemedApp />
|
||||
<AppRoutes />
|
||||
</ThemeProvider>
|
||||
</RootStoreProvider>
|
||||
</AuthProvider>
|
||||
|
||||
@@ -20,46 +20,119 @@ export const ThemeProvider = ({ children }) => {
|
||||
return (
|
||||
<ThemeContext.Provider value={{ isDarkMode, toggleTheme }}>
|
||||
<ConfigProvider
|
||||
componentSize="small"
|
||||
theme={{
|
||||
algorithm: isDarkMode ? theme.darkAlgorithm : theme.defaultAlgorithm,
|
||||
token: {
|
||||
colorPrimary: "#1677ff",
|
||||
borderRadius: 4,
|
||||
colorBgContainer: isDarkMode ? "#141414" : "#ffffff",
|
||||
colorBgElevated: isDarkMode ? "#1f1f1f" : "#ffffff",
|
||||
colorText: isDarkMode
|
||||
? "rgba(255, 255, 255, 0.85)"
|
||||
: "rgba(0, 0, 0, 0.85)",
|
||||
colorTextSecondary: isDarkMode
|
||||
? "rgba(255, 255, 255, 0.45)"
|
||||
: "rgba(0, 0, 0, 0.45)",
|
||||
// 主色调 - Google Blue
|
||||
colorPrimary: '#1a73e8',
|
||||
colorPrimaryHover: '#1557b0',
|
||||
colorPrimaryActive: '#174ea6',
|
||||
|
||||
// 成功色 - Google Green
|
||||
colorSuccess: '#1e8e3e',
|
||||
colorSuccessHover: '#188130',
|
||||
colorSuccessActive: '#137333',
|
||||
|
||||
// 警告色 - Google Yellow
|
||||
colorWarning: '#f9ab00',
|
||||
colorWarningHover: '#f29900',
|
||||
colorWarningActive: '#ea8600',
|
||||
|
||||
// 错误色 - Google Red
|
||||
colorError: '#d93025',
|
||||
colorErrorHover: '#c5221f',
|
||||
colorErrorActive: '#a50e0e',
|
||||
|
||||
// 文字颜色
|
||||
colorText: isDarkMode ? 'rgba(255, 255, 255, 0.87)' : 'rgba(0, 0, 0, 0.87)',
|
||||
colorTextSecondary: isDarkMode ? 'rgba(255, 255, 255, 0.60)' : 'rgba(0, 0, 0, 0.60)',
|
||||
colorTextTertiary: isDarkMode ? 'rgba(255, 255, 255, 0.38)' : 'rgba(0, 0, 0, 0.38)',
|
||||
|
||||
// 背景色
|
||||
colorBgContainer: isDarkMode ? '#1f1f1f' : '#ffffff',
|
||||
colorBgElevated: isDarkMode ? '#2d2d2d' : '#ffffff',
|
||||
colorBgLayout: isDarkMode ? '#121212' : '#f8f9fa',
|
||||
|
||||
// 边框
|
||||
borderRadius: 8,
|
||||
borderRadiusLG: 12,
|
||||
borderRadiusSM: 4,
|
||||
colorBorder: isDarkMode ? 'rgba(255, 255, 255, 0.12)' : 'rgba(0, 0, 0, 0.12)',
|
||||
|
||||
// 阴影
|
||||
boxShadow: '0 1px 3px 0 rgba(60,64,67,0.3), 0 4px 8px 3px rgba(60,64,67,0.15)',
|
||||
boxShadowSecondary: '0 1px 2px 0 rgba(60,64,67,0.3), 0 1px 3px 1px rgba(60,64,67,0.15)',
|
||||
|
||||
// 字体
|
||||
fontFamily: 'Google Sans, Roboto, Arial, sans-serif',
|
||||
fontSize: 14,
|
||||
|
||||
// 控件尺寸
|
||||
controlHeight: 36,
|
||||
controlHeightSM: 32,
|
||||
controlHeightLG: 44,
|
||||
},
|
||||
components: {
|
||||
// 为所有支持 variant 的组件设置 filled 模式
|
||||
Form: {
|
||||
variant: 'filled',
|
||||
Button: {
|
||||
algorithm: true,
|
||||
borderRadius: 20, // Google 风格的圆角按钮
|
||||
controlHeight: 36,
|
||||
controlHeightSM: 32,
|
||||
controlHeightLG: 44,
|
||||
paddingContentHorizontal: 24,
|
||||
},
|
||||
Input: {
|
||||
variant: 'filled',
|
||||
algorithm: true,
|
||||
controlHeight: 36,
|
||||
controlHeightSM: 32,
|
||||
controlHeightLG: 44,
|
||||
paddingContentHorizontal: 16,
|
||||
borderRadius: 4,
|
||||
controlOutline: 'none',
|
||||
controlOutlineWidth: 0,
|
||||
controlPaddingHorizontal: 16,
|
||||
controlPaddingHorizontalSM: 12,
|
||||
addonBg: 'transparent',
|
||||
},
|
||||
Select: {
|
||||
variant: 'filled',
|
||||
algorithm: true,
|
||||
controlHeight: 36,
|
||||
controlHeightSM: 32,
|
||||
controlHeightLG: 44,
|
||||
borderRadius: 4,
|
||||
controlOutline: 'none',
|
||||
controlOutlineWidth: 0,
|
||||
selectorBg: 'transparent',
|
||||
},
|
||||
TreeSelect: {
|
||||
variant: 'filled',
|
||||
Card: {
|
||||
algorithm: true,
|
||||
borderRadiusLG: 8,
|
||||
boxShadow: '0 1px 2px 0 rgba(60,64,67,0.3), 0 1px 3px 1px rgba(60,64,67,0.15)',
|
||||
},
|
||||
DatePicker: {
|
||||
variant: 'filled',
|
||||
Menu: {
|
||||
algorithm: true,
|
||||
itemBorderRadius: 20, // Google 风格的圆角菜单项
|
||||
itemHeight: 36,
|
||||
itemHeightSM: 32,
|
||||
},
|
||||
TimePicker: {
|
||||
variant: 'filled',
|
||||
Tabs: {
|
||||
algorithm: true,
|
||||
inkBarColor: '#1a73e8',
|
||||
itemSelectedColor: '#1a73e8',
|
||||
itemHoverColor: '#174ea6',
|
||||
},
|
||||
Cascader: {
|
||||
variant: 'filled',
|
||||
},
|
||||
AutoComplete: {
|
||||
variant: 'filled',
|
||||
Table: {
|
||||
algorithm: true,
|
||||
borderRadius: 8,
|
||||
headerBg: isDarkMode ? '#2d2d2d' : '#f8f9fa',
|
||||
},
|
||||
Modal: {
|
||||
algorithm: true,
|
||||
borderRadius: 28, // Google 风格的大圆角对话框
|
||||
paddingContentHorizontal: 24,
|
||||
paddingContentVertical: 24,
|
||||
}
|
||||
}
|
||||
}}
|
||||
>
|
||||
|
||||
@@ -83,7 +83,7 @@ const CustomerForm = () => {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-6">
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-2">
|
||||
<Card
|
||||
className="shadow-lg rounded-lg border-0"
|
||||
title={
|
||||
|
||||
@@ -629,7 +629,7 @@ const QuotationForm = () => {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-6">
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-2">
|
||||
<Card
|
||||
className="shadow-lg rounded-lg border-0"
|
||||
title={
|
||||
|
||||
@@ -12,7 +12,7 @@ import {
|
||||
import {
|
||||
ArrowLeftOutlined,
|
||||
} from "@ant-design/icons";
|
||||
import { useNavigate, useParams, useLocation } from "react-router-dom";
|
||||
import { useNavigate, useParams,useSearchParams, useLocation } from "react-router-dom";
|
||||
import { supabase } from "@/config/supabase";
|
||||
import SectionList from '@/components/SectionList';
|
||||
|
||||
@@ -21,7 +21,9 @@ const { Title } = Typography;
|
||||
const ServiceForm = () => {
|
||||
const [form] = Form.useForm();
|
||||
const navigate = useNavigate();
|
||||
const { id } = useParams();
|
||||
const { id} = useParams();
|
||||
const [searchParams] = useSearchParams();
|
||||
const isView = searchParams.get("isView") === "true";
|
||||
const [loading, setLoading] = useState(false);
|
||||
const location = useLocation();
|
||||
const isEdit = location.search.includes("edit=true");
|
||||
@@ -136,7 +138,7 @@ const ServiceForm = () => {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-6">
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-2">
|
||||
<Card
|
||||
className="shadow-lg rounded-lg border-0"
|
||||
title={
|
||||
@@ -160,13 +162,13 @@ const ServiceForm = () => {
|
||||
>
|
||||
返回
|
||||
</Button>
|
||||
<Button
|
||||
{!isView&& <Button
|
||||
type="primary"
|
||||
onClick={() => form.submit()}
|
||||
loading={loading}
|
||||
>
|
||||
保存
|
||||
</Button>
|
||||
</Button>}
|
||||
</Space>
|
||||
</div>
|
||||
}
|
||||
@@ -176,8 +178,9 @@ const ServiceForm = () => {
|
||||
onFinish={onFinish}
|
||||
onValuesChange={handleValuesChange}
|
||||
layout="vertical"
|
||||
variant="filled"
|
||||
disabled={isView}
|
||||
>
|
||||
{/* 基本信息 */}
|
||||
<Card
|
||||
className="shadow-sm rounded-lg mb-6"
|
||||
type="inner"
|
||||
@@ -221,7 +224,6 @@ const ServiceForm = () => {
|
||||
</div>
|
||||
</Card>
|
||||
|
||||
{/* 服务明细 */}
|
||||
<Card
|
||||
className="shadow-sm rounded-lg"
|
||||
type="inner"
|
||||
|
||||
@@ -311,21 +311,21 @@ const ServicePage = () => {
|
||||
</Paragraph>
|
||||
),
|
||||
},
|
||||
{
|
||||
title: "总金额",
|
||||
dataIndex: ["attributes", "totalAmount"],
|
||||
key: "totalAmount",
|
||||
className: "min-w-[150px] text-right",
|
||||
render: (amount) => (
|
||||
<span style={{ color: "#f50", fontWeight: "bold" }}>
|
||||
¥
|
||||
{amount?.toLocaleString("zh-CN", {
|
||||
minimumFractionDigits: 2,
|
||||
maximumFractionDigits: 2,
|
||||
}) || "0.00"}
|
||||
</span>
|
||||
),
|
||||
},
|
||||
// {
|
||||
// title: "总金额",
|
||||
// dataIndex: ["attributes", "totalAmount"],
|
||||
// key: "totalAmount",
|
||||
// className: "min-w-[150px] text-right",
|
||||
// render: (amount) => (
|
||||
// <span style={{ color: "#f50", fontWeight: "bold" }}>
|
||||
// ¥
|
||||
// {amount?.toLocaleString("zh-CN", {
|
||||
// minimumFractionDigits: 2,
|
||||
// maximumFractionDigits: 2,
|
||||
// }) || "0.00"}
|
||||
// </span>
|
||||
// ),
|
||||
// },
|
||||
{
|
||||
title: "操作",
|
||||
key: "action",
|
||||
|
||||
@@ -83,7 +83,7 @@ const SupplierForm = () => {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-6">
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-2">
|
||||
<Card
|
||||
className="shadow-lg rounded-lg border-0"
|
||||
title={
|
||||
|
||||
@@ -172,7 +172,7 @@ const ResourceTaskForm = () => {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-6">
|
||||
<div className="bg-gradient-to-b from-gray-50 to-white min-h-screen p-2">
|
||||
<Card
|
||||
className="shadow-lg rounded-lg border-0"
|
||||
title={
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
@tailwind base;
|
||||
@tailwind components;
|
||||
@tailwind utilities;
|
||||
|
||||
@import url('https://fonts.googleapis.com/css2?family=Google+Sans:wght@400;500;700&display=swap');
|
||||
:root {
|
||||
--primary-color: #1677ff;
|
||||
--primary-gradient: linear-gradient(45deg, #1677ff, #36cff0);
|
||||
|
||||
Reference in New Issue
Block a user