export function money(cents: number) { return `¥${(cents / 100).toFixed(2)}`; } export function dateText(ms: number, timezone = "Asia/Shanghai") { return new Intl.DateTimeFormat("zh-CN", { dateStyle: "medium", timeStyle: "short", timeZone: timezone }).format(new Date(ms)); } export function monthNow(timezone = "Asia/Shanghai") { const p = Object.fromEntries(new Intl.DateTimeFormat("en-CA", { timeZone: timezone, year: "numeric", month: "2-digit" }).formatToParts(new Date()).map(x => [x.type, x.value])); return `${p.year}-${p.month}`; } export function dateInputValue(date: Date, timezone = "Asia/Shanghai") { const p = Object.fromEntries(new Intl.DateTimeFormat("en-CA", { timeZone: timezone, year: "numeric", month: "2-digit", day: "2-digit", hour: "2-digit", minute: "2-digit", hourCycle: "h23" }).formatToParts(date).map(x => [x.type, x.value])); return `${p.year}-${p.month}-${p.day} ${p.hour}:${p.minute}`; } export function dateFromInput(value: string, timezone = "Asia/Shanghai") { const m = /^(\d{4})-(\d{2})-(\d{2})[ T](\d{2}):(\d{2})$/.exec(value.trim()); if (!m) throw new Error("请选择有效的支付日期和时间"); const year = Number(m[1]); const month = Number(m[2]); const day = Number(m[3]); const hour = Number(m[4]); const minute = Number(m[5]); const probe = new Date(0); probe.setUTCFullYear(year, month - 1, day); probe.setUTCHours(0, 0, 0, 0); if (probe.getUTCFullYear() !== year || probe.getUTCMonth() !== month - 1 || probe.getUTCDate() !== day || hour > 23 || minute > 59) throw new Error("支付时间无效"); const wall = Date.UTC(year, month - 1, day, hour, minute); const observed = Object.fromEntries(new Intl.DateTimeFormat("en-CA", { timeZone: timezone, year: "numeric", month: "2-digit", day: "2-digit", hour: "2-digit", minute: "2-digit", hourCycle: "h23" }).formatToParts(new Date(wall)).map(x => [x.type, x.value])); const observedUtc = Date.UTC(Number(observed.year), Number(observed.month) - 1, Number(observed.day), Number(observed.hour), Number(observed.minute)); return new Date(wall + wall - observedUtc).toISOString(); } export function formatBytes(bytes: number) { return bytes < 1024 * 1024 ? `${Math.max(1, Math.round(bytes / 1024))} KB` : `${(bytes / 1024 / 1024).toFixed(1)} MB`; }