增加颜色代码复制功能。

This commit is contained in:
徐涛
2025-01-02 09:08:59 +08:00
parent b252b2eb20
commit 1772d6e047
2 changed files with 30 additions and 5 deletions

View File

@@ -1,6 +1,8 @@
import cx from 'clsx';
import { constant, flatten, isEqual, take, times } from 'lodash-es';
import { useMemo } from 'react';
import { constant, flatten, isEqual, isNil, take, times } from 'lodash-es';
import { useEffect, useMemo } from 'react';
import { useCopyToClipboard } from 'react-use';
import { NotificationType, useNotification } from '../../components/Notifications';
import { HarmonyColor } from '../../models';
import styles from './HarmonyPreview.module.css';
@@ -9,6 +11,8 @@ type HarmonyPreviewProps = {
};
export function HarmonyPreview({ colors = [] }: HarmonyPreviewProps) {
const [cpState, copyToClipboard] = useCopyToClipboard();
const { showToast } = useNotification();
const extendedColors = useMemo(() => {
const sortedColors = colors.sort((a, b) => -(a.ratio - b.ratio));
if (sortedColors.length >= 4) {
@@ -20,6 +24,19 @@ export function HarmonyPreview({ colors = [] }: HarmonyPreviewProps) {
]);
}, [colors]);
useEffect(() => {
if (!isNil(cpState.error)) {
showToast(NotificationType.ERROR, 'Failed to copy to clipboard', 'tabler:alert-circle', 3000);
} else if (!isNil(cpState.value)) {
showToast(
NotificationType.SUCCESS,
`${cpState.value} has been copied to clipboard.`,
'tabler:circle-check',
3000,
);
}
}, [cpState]);
return (
<div className={styles.preview}>
<h5>Harmony Preview</h5>
@@ -27,11 +44,13 @@ export function HarmonyPreview({ colors = [] }: HarmonyPreviewProps) {
{extendedColors.map(({ color, ratio }, index) => (
<div
key={index}
className={cx(styles.color_block, isEqual(ratio, 0) && styles.zero_width)}
className={cx(styles.color_block, isEqual(ratio, 0) && styles.hide)}
style={{ flexGrow: ratio }}>
<div className={styles.color_ratio}>{ratio > 0 && `Ratio: ${ratio}`}</div>
<div className={styles.color_square} style={{ backgroundColor: `#${color}` }}></div>
<div className={styles.color_code}>{ratio > 0 && `#${color}`}</div>
<div className={styles.color_code}>
{ratio > 0 && <span onClick={() => copyToClipboard(`#${color}`)}>#{color}</span>}
</div>
</div>
))}
</div>