From e9a6fa3dd837c1eb89b61f5d3610b60607c8334d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=9B=A8=E9=9C=96=E9=93=83?= Date: Wed, 20 May 2026 21:32:35 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=94=AF=E6=8C=81=E5=8F=B3=E9=94=AE?= =?UTF-8?q?=E8=8F=9C=E5=8D=95=E6=97=B6=E9=97=B4=E6=88=B3=E8=BD=AC=E6=8D=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 在 useTimestampConverter 中添加 useContextMenuData hook - 智能识别输入是时间戳还是日期时间字符串 - 自动切换到对应模式并执行转换 - 时间戳自动识别秒/毫秒单位 --- pages/Timestamp/useTimestampConverter.ts | 49 ++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/pages/Timestamp/useTimestampConverter.ts b/pages/Timestamp/useTimestampConverter.ts index c86ba18..b7fa2fb 100644 --- a/pages/Timestamp/useTimestampConverter.ts +++ b/pages/Timestamp/useTimestampConverter.ts @@ -3,6 +3,7 @@ import dayjs from '@/utils/dayjs'; import type { UnitType, ZoneType } from '@/config/pageTheme'; import { DATE_FORMAT } from '@/config/pageTheme'; import { useTranslation } from 'react-i18next'; +import { useContextMenuData } from '@/utils/useContextMenuData'; export interface UseTimestampConverterReturn { // State @@ -23,6 +24,15 @@ export interface UseTimestampConverterReturn { convert: () => void; } +/** + * 判断输入是否为时间戳(纯数字或长度 >= 10 的数字字符串) + */ +function isTimestampLike(input: string): boolean { + const trimmed = input.trim(); + if (!/^\d+$/.test(trimmed)) return false; + return trimmed.length >= 10; +} + export function useTimestampConverter(): UseTimestampConverterReturn { const { t } = useTranslation(['timestamp']); const [mode, setMode] = useState<'ts2dt' | 'dt2ts'>('ts2dt'); @@ -63,6 +73,45 @@ export function useTimestampConverter(): UseTimestampConverterReturn { } }, [mode, tsInput, dtInput, unit, zone, t]); + // 处理右键菜单传递的数据 + const handleContextMenuData = useCallback((payload: string) => { + const trimmed = payload.trim(); + if (isTimestampLike(trimmed)) { + // 看起来是时间戳,切换到 ts2dt 模式 + setMode('ts2dt'); + setTsInput(trimmed); + // 如果是 13 位毫秒级时间戳,自动选择 ms 单位 + const detectedUnit: UnitType = trimmed.length >= 13 ? 'ms' : 's'; + setUnit(detectedUnit); + // 直接执行转换 + const num = Number(trimmed); + if (!isNaN(num)) { + const d = detectedUnit === 'ms' ? dayjs(num) : dayjs.unix(num); + if (d.isValid()) { + setError(''); + setResult(d.tz('Asia/Shanghai').format(DATE_FORMAT)); + } + } + } else { + // 尝试作为日期时间解析 + const d = dayjs(trimmed); + if (d.isValid()) { + setMode('dt2ts'); + setDtInput(d.format(DATE_FORMAT)); + // 直接执行转换 + const ms = d.valueOf(); + setError(''); + setResult(String(ms)); + } else { + // 无法识别,作为时间戳处理 + setMode('ts2dt'); + setTsInput(trimmed); + } + } + }, []); + + useContextMenuData({ featureKey: 'timestamp', onData: handleContextMenuData }); + const handleUseNow = useCallback( (now: number) => { if (mode === 'ts2dt') {