Files
SaaS2/docs/antd-copy-message-guide.md
RUI d098d58018
Some checks failed
Next.js CI/CD 流水线 / deploy (push) Failing after 41s
0606.14
2025-06-06 21:02:14 +08:00

372 lines
8.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Ant Design 复制和 Message 功能使用指南
> **作者:阿瑞**
> **版本1.0.0**
> **适用范围Ant Design 5.x + Next.js 15 + React 19**
## 📖 概述
本文档详细介绍如何在 Ant Design 5.x 中正确使用复制功能和 message 组件,避免常见的警告和错误,提供最佳实践方案。
## 🚨 常见警告及解决方案
### 1. Message 静态方法警告
**警告信息:**
```
Warning: [antd: message] Static function can not consume context like dynamic theme. Please use 'App' component instead.
```
**产生原因:**
- Ant Design 5.x 中的静态方法(如 `message.success()`)无法获取动态主题上下文
- 静态方法不在 React 组件树中,无法访问 `ConfigProvider``App` 组件提供的上下文
## 💡 正确使用方法
### 1. App 组件配置
首先确保在 `_app.tsx` 中正确配置 `App` 组件:
```tsx
// src/pages/_app.tsx
import { ConfigProvider, App } from "antd";
import zhCN from "antd/locale/zh_CN";
function AppConfigProvider({ children }: { children: React.ReactNode }) {
return (
<ConfigProvider
theme={yourTheme}
locale={zhCN}
>
<App>
<div className="app-container">
{children}
</div>
</App>
</ConfigProvider>
);
}
export default function MyApp({ Component, pageProps }: AppProps) {
return (
<AppConfigProvider>
<Component {...pageProps} />
</AppConfigProvider>
);
}
```
### 2. 在组件中使用 useApp Hook
**正确方式:**
```tsx
import React from 'react';
import { App, Button } from 'antd';
const { useApp } = App;
const MyComponent = () => {
// ✅ 使用 useApp hook 获取 message 实例
const { message } = useApp();
const handleClick = () => {
message.success('操作成功!');
message.error('操作失败!');
message.warning('警告信息!');
message.info('提示信息!');
};
return (
<Button onClick={handleClick}>
Message
</Button>
);
};
export default MyComponent;
```
**错误方式:**
```tsx
import { message } from 'antd'; // ❌ 不推荐:静态导入
const MyComponent = () => {
const handleClick = () => {
message.success('操作成功!'); // ❌ 会产生警告
};
return <Button onClick={handleClick}></Button>;
};
```
## 📋 复制功能使用指南
### 1. 简单文本复制
使用 `Typography.Paragraph``copyable` 属性:
```tsx
import { Typography } from 'antd';
import { App } from 'antd';
const { Paragraph } = Typography;
const { useApp } = App;
const SimpleTextCopy = () => {
const { message } = useApp();
const textToCopy = "这是要复制的文本内容";
return (
<Paragraph
copyable={{
text: textToCopy,
onCopy: () => message.success('复制成功!'),
tooltips: ['点击复制', '复制成功']
}}
>
{textToCopy}
</Paragraph>
);
};
```
### 2. 自定义复制按钮
```tsx
import { Typography, Button } from 'antd';
import { CopyOutlined } from '@ant-design/icons';
const CustomCopyButton = () => {
const { message } = useApp();
const copyText = "自定义复制内容";
return (
<Paragraph
copyable={{
text: copyText,
icon: <CopyOutlined />, // 自定义图标
onCopy: () => message.success('内容已复制到剪贴板'),
tooltips: ['复制内容', '复制成功']
}}
style={{ margin: 0 }}
>
{/* 空内容,只显示复制按钮 */}
</Paragraph>
);
};
```
### 3. 复杂复制逻辑(图片 + 文本)
对于需要复制图片和文本的复杂场景:
```tsx
import { Button, Tooltip } from 'antd';
import { CopyOutlined } from '@ant-design/icons';
const ComplexCopyFunction = () => {
const { message } = useApp();
const handleComplexCopy = async () => {
try {
const textContent = "文本内容";
// 尝试复制图片 + 文本
if (hasImage) {
try {
const imageBlob = await fetchImageAsBlob();
const clipboardItems = {
"text/plain": new Blob([textContent], { type: "text/plain" }),
[imageBlob.type]: imageBlob
};
const clipboardItem = new ClipboardItem(clipboardItems);
await navigator.clipboard.write([clipboardItem]);
message.success('文本和图片已复制');
} catch (imageError) {
// 降级到仅文本复制
await navigator.clipboard.writeText(textContent);
message.success('文本已复制(图片复制失败)');
}
} else {
// 仅文本复制
await navigator.clipboard.writeText(textContent);
message.success('文本已复制');
}
} catch (error) {
console.error('复制失败:', error);
message.error('复制失败');
}
};
return (
<Tooltip title="复制内容">
<Button
icon={<CopyOutlined />}
onClick={handleComplexCopy}
>
</Button>
</Tooltip>
);
};
```
## 🎯 最佳实践
### 1. Message 使用建议
```tsx
const BestPracticeExample = () => {
const { message } = useApp();
// ✅ 推荐:使用 useApp hook
const showSuccess = () => {
message.success({
content: '操作成功!',
duration: 3, // 显示时长
key: 'unique-key', // 唯一键,避免重复显示
});
};
// ✅ 推荐:加载状态处理
const showLoading = () => {
message.loading({
content: '正在处理...',
key: 'loading-key',
duration: 0 // 0 表示不自动关闭
});
// 模拟异步操作
setTimeout(() => {
message.success({
content: '处理完成!',
key: 'loading-key' // 同样的 key 会替换之前的 message
});
}, 2000);
};
return (
<div>
<Button onClick={showSuccess}></Button>
<Button onClick={showLoading}></Button>
</div>
);
};
```
### 2. 复制功能建议
```tsx
const CopyBestPractice = () => {
const { message } = useApp();
// ✅ 推荐:简单文本使用 Paragraph copyable
const simpleCopy = (
<Paragraph
copyable={{
text: "简单文本",
onCopy: () => message.success('复制成功'),
}}
>
</Paragraph>
);
// ✅ 推荐:复杂逻辑使用自定义函数 + Tooltip
const complexCopy = (
<Tooltip title="复制详细信息">
<Button onClick={handleComplexCopyLogic}>
</Button>
</Tooltip>
);
return (
<div>
{simpleCopy}
{complexCopy}
</div>
);
};
```
## ⚠️ 常见错误
### 1. 避免事件冲突
```tsx
// ❌ 错误:在 Paragraph copyable 中嵌套按钮会导致事件冲突
<Paragraph copyable={{ text: "内容" }}>
<Button></Button> {/* 会导致点击事件冲突 */}
</Paragraph>
// ✅ 正确:分别处理
<div style={{ display: 'flex', gap: 8 }}>
<Paragraph copyable={{ text: "内容" }}></Paragraph>
<Button></Button>
</div>
```
### 2. 避免样式冲突
```tsx
// ❌ 错误fontSize: 0 可能影响可点击区域
<Paragraph
copyable={{ text: "内容" }}
style={{ fontSize: 0 }} // 可能导致无法点击
>
</Paragraph>
// ✅ 正确:使用合适的样式
<Paragraph
copyable={{ text: "内容" }}
style={{ margin: 0, lineHeight: 1 }}
>
</Paragraph>
```
## 🔧 调试技巧
### 1. 检查 App 组件配置
确保组件在 `App` 组件内部:
```tsx
// 在浏览器控制台检查
console.log('App context:', React.useContext(AppContext));
```
### 2. 验证复制功能
```tsx
const testCopy = async () => {
try {
await navigator.clipboard.writeText('测试');
console.log('复制功能正常');
} catch (error) {
console.error('复制功能异常:', error);
}
};
```
## 📚 参考资料
- [Ant Design App 组件文档](https://ant.design/components/app-cn)
- [Ant Design Typography 组件文档](https://ant.design/components/typography-cn)
- [Ant Design Message 组件文档](https://ant.design/components/message-cn)
- [Web Clipboard API](https://developer.mozilla.org/zh-CN/docs/Web/API/Clipboard)
## 📝 更新日志
- **v1.0.0** (2024-12-XX): 初始版本,包含基础使用方法和最佳实践
---
> 💡 **提示**:遵循本文档的最佳实践,可以避免常见的警告和错误,提供更好的用户体验。