1.5.3 • Published 7 months ago

@qisexin/utils-tool v1.5.3

Weekly downloads
-
License
MIT
Repository
github
Last release
7 months ago

🛠️ @qisexin/utils-tool

npm version npm downloads license TypeScript Build Status codecov

🚀 个人前端工具库,将工作中常用的方法封装成小函数,持续丰富中

English | 简体中文


📖 目录

🚀 安装

# npm
npm install @qisexin/utils-tool

# yarn
yarn add @qisexin/utils-tool

# pnpm
pnpm add @qisexin/utils-tool

📦 快速开始

// ES6 模块导入
import { toThousands, getQueryString } from '@qisexin/utils-tool';

// 使用示例
const formattedNumber = toThousands(1234567.89); // "1,234,567.89"
const urlParam = getQueryString('id'); // 获取URL参数
// CommonJS 导入
const { toThousands, getQueryString } = require('@qisexin/utils-tool');

// 按需导入(推荐)
import { toThousands } from '@qisexin/utils-tool/formatNumber';
import { getQueryString } from '@qisexin/utils-tool/other';

// Antd 工具导入
import { CopyToClipboard, downloadExcel } from '@qisexin/utils-tool/antd-utils';

// Hooks 导入
import { useLocalStorageState } from '@qisexin/utils-tool/hooks';

✨ 项目特点

📚 API 文档

🔤 字符串处理

encodeValue(val: string): string

编码字符串中的特殊字符,将特殊字符转换为 URL 编码格式

参数:

  • val (string): 需要编码的字符串

返回值: string - 编码后的字符串

encodeValue('test?name=value') // => 'test%3Fname%3Dvalue'
encodeValue('hello world') // => 'hello%20world'

decodeValue(val: string): string

解码字符串中的特殊字符,将 URL 编码格式转换为原始字符

参数:

  • val (string): 需要解码的字符串

返回值: string - 解码后的字符串

decodeValue('test%3Fname%3Dvalue') // => 'test?name=value'
decodeValue('hello%20world') // => 'hello world'

getActualWidthOfChars(text: string, options?: { font?: string }): number

通过 Canvas 获取字符串的实际像素宽度,支持自定义字体

参数:

  • text (string): 需要测量的文本
  • options (object, 可选): 配置选项
    • font (string, 可选): 字体样式,默认为 '12px Arial'

返回值: number - 文本的像素宽度

getActualWidthOfChars('Hello World') // => 66
getActualWidthOfChars('性能数据', { font: '14px Microsoft YaHei' }) // => 56

generateRandomColor(): string[]

生成随机颜色数组,返回 10 个随机的 RGB 颜色值

返回值: string[] - 包含 10 个 RGB 颜色字符串的数组

generateRandomColor()
// => ['rgb(48, 62, 6)', 'rgb(123, 45, 67)', 'rgb(200, 100, 150)', ...]

getRandomKey(): string

生成随机的唯一标识符,基于时间戳和随机数

返回值: string - 随机生成的唯一标识符

getRandomKey() // => '1701234567890_abc123'
getRandomKey() // => '1701234567891_def456'

🔢 数字处理

toThousands(x: number, digits?: number): string

将数字转换为千位分隔符格式,支持指定小数位数

参数:

  • x (number): 需要格式化的数字
  • digits (number, 可选): 小数位数,默认保持原有精度

返回值: string - 格式化后的字符串

toThousands(1234567.89) // => "1,234,567.89"
toThousands(1234567.123, 2) // => "1,234,567.12"
toThousands(1000) // => "1,000"

convertSpecialNumbers(num: number): number

处理特殊数字值,将 NaN 和 Infinity 转换为 0

参数:

  • num (number): 需要处理的数字

返回值: number - 处理后的数字

convertSpecialNumbers(NaN) // => 0
convertSpecialNumbers(Infinity) // => 0
convertSpecialNumbers(-Infinity) // => 0
convertSpecialNumbers(123) // => 123

convertEmptyNumber(num: any): string | number

处理空值数字显示,0 显示为 0,null/undefined 显示为 '--'

参数:

  • num (any): 需要处理的值

返回值: string | number - 处理后的显示值

convertEmptyNumber(null) // => '--'
convertEmptyNumber(undefined) // => '--'
convertEmptyNumber(0) // => 0
convertEmptyNumber(123) // => 123

bytesConverter(bytes: number, unit: string): string

字节单位转换,将字节数转换为指定单位

参数:

  • bytes (number): 字节数
  • unit (string): 目标单位 ('B', 'KB', 'MB', 'GB', 'TB')

返回值: string - 转换后的字符串(包含单位)

bytesConverter(1024, 'KB') // => '1KB'
bytesConverter(4 * 1024 * 1024, 'MB') // => '4MB'
bytesConverter(1073741824, 'GB') // => '1GB'

📦 对象处理

encodeObject(obj: Record<string, any>): Record<string, any>

递归编码对象中所有字符串值的特殊字符

参数:

  • obj (Record<string, any>): 需要编码的对象

返回值: Record<string, any> - 编码后的新对象

encodeObject({ name: 'hello world', desc: 'test?value' })
// => { name: 'hello%20world', desc: 'test%3Fvalue' }

decodeObject(obj: Record<string, any>): Record<string, any>

递归解码对象中所有字符串值的特殊字符

参数:

  • obj (Record<string, any>): 需要解码的对象

返回值: Record<string, any> - 解码后的新对象

decodeObject({ name: 'hello%20world', desc: 'test%3Fvalue' })
// => { name: 'hello world', desc: 'test?value' }

escapeRegExpObject(obj: Record<string, any>): Record<string, any>

转义对象中所有字符串值的正则表达式特殊字符

参数:

  • obj (Record<string, any>): 需要转义的对象

返回值: Record<string, any> - 转义后的新对象

escapeRegExpObject({ pattern: '[test]', regex: '(.*?)' })
// => { pattern: '\\[test\\]', regex: '\\(\\.\\*\\?\\)' }

replaceKeys<T>(obj: T, keysMap: Record<string, string>): T

根据映射表替换对象或数组中的键名

参数:

  • obj (T): 需要处理的对象或数组
  • keysMap (Record<string, string>): 键名映射表

返回值: T - 替换键名后的新对象或数组

replaceKeys({ oldKey: 'value' }, { oldKey: 'newKey' })
// => { newKey: 'value' }

replaceKeys([{ a: 1 }, { a: 2 }], { a: 'b' })
// => [{ b: 1 }, { b: 2 }]

⏰ 日期时间

checkAndCompleteDate(dateString: string): string

检查日期字符串格式,如果没有时分秒则自动补充 23:59:59

参数:

  • dateString (string): 日期字符串

返回值: string - 完整的日期时间字符串

checkAndCompleteDate('2023-12-01') // => '2023-12-01 23:59:59'
checkAndCompleteDate('2023-12-01 10:30:00') // => '2023-12-01 10:30:00'

showDuration(options: { startTime: string; endTime: string; language?: 'zh' | 'en' }): string

计算并格式化两个时间点之间的时长

参数:

  • options (object): 配置选项
    • startTime (string): 开始时间
    • endTime (string): 结束时间
    • language ('zh' | 'en', 可选): 语言,默认为 'zh'

返回值: string - 格式化的时长字符串

showDuration({
  startTime: '2023-12-01 10:00:00',
  endTime: '2023-12-01 13:30:45'
}) // => '3小时30分钟45秒'

showDuration({
  startTime: '2023-12-01 10:00:00',
  endTime: '2023-12-01 13:30:45',
  language: 'en'
}) // => '3h30m45s'

formatUUID(uuidStr: string): string

将 32 位 UUID 字符串转换为标准的带连字符格式

参数:

  • uuidStr (string): 32 位 UUID 字符串

返回值: string - 标准格式的 UUID 字符串

formatUUID('550e8400e29b41d4a716446655440000')
// => '550e8400-e29b-41d4-a716-446655440000'

🌐 DOM 操作

copyToClipboard(text: string): Promise<void>

复制文本到剪贴板,支持现代浏览器的 Clipboard API

参数:

  • text (string): 需要复制的文本

返回值: Promise<void> - 复制操作的 Promise

await copyToClipboard('Hello World')
copyToClipboard('https://example.com').then(() => {
  console.log('复制成功')
})

scrollToAnchor(anchorName: string): void

平滑滚动到指定的锚点元素

参数:

  • anchorName (string): 锚点元素的 ID

返回值: void

scrollToAnchor('section1') // 滚动到 id="section1" 的元素
scrollToAnchor('top') // 滚动到 id="top" 的元素

🔗 URL 处理

getQueryString(name: string): string | null

从当前页面 URL 中获取指定参数的值

参数:

  • name (string): 参数名

返回值: string | null - 参数值,不存在时返回 null

// 当前 URL: https://example.com?id=123&name=test
getQueryString('id') // => '123'
getQueryString('name') // => 'test'
getQueryString('notexist') // => null

urlParamsToObject(url: string): Record<string, string>

将 URL 中的查询参数转换为对象

参数:

  • url (string): 完整的 URL 字符串

返回值: Record<string, string> - 参数对象

urlParamsToObject('https://example.com?id=123&name=test&active=true')
// => { id: '123', name: 'test', active: 'true' }

objectToUrlParams(params: Record<string, any>): string

将对象转换为 URL 查询参数字符串

参数:

  • params (Record<string, any>): 参数对象

返回值: string - URL 参数字符串

objectToUrlParams({ id: 123, name: 'test', active: true })
// => 'id=123&name=test&active=true'

🛠️ 工具函数

mixedSort(a: any, b: any): number

中英文数字混合排序比较函数,排序优先级:数字 > 英文字母 > 中文拼音

参数:

  • a (any): 第一个比较值
  • b (any): 第二个比较值

返回值: number - 比较结果 (-1, 0, 1)

const arr = ['中文', '1', 'apple', '2', '测试', 'banana']
arr.sort(mixedSort)
// => ['1', '2', 'apple', 'banana', '测试', '中文']

📊 Echarts 工具

largeDataTooltipOptimization(params: any, labelField: string, rowsPerColumn: number, defaultColumnWidth: number): string

优化 Echarts 大数据量下的 Tooltip 显示,支持多列布局

参数:

  • params (any): Echarts tooltip 的 params 参数
  • labelField (string): 用作标签的字段名
  • rowsPerColumn (number): 每列显示的行数
  • defaultColumnWidth (number): 默认列宽(像素)

返回值: string - 格式化的 HTML 字符串

// 在 Echarts 配置中使用
const option = {
  tooltip: {
    formatter: (params) => largeDataTooltipOptimization(
      params,
      'deviceName',
      10,
      200
    )
  }
}

🎨 Antd 相关工具

⚠️ 注意: 使用 antd-utils 时,需要在项目中安装 reactreact-domantd,并从 @qisexin/utils-tool/antd-utils 内引入方法

CopyToClipboard 组件

复制到剪贴板的 React 组件,基于 Antd 的 Button 组件

Props:

  • copyText (string): 需要复制的文本内容
  • children (ReactNode): 按钮显示内容
  • 其他 Antd Button 组件支持的 props
import { CopyToClipboard } from '@qisexin/utils-tool/antd-utils';

// 基础用法
<CopyToClipboard copyText="需要复制的内容">
  点击复制
</CopyToClipboard>

// 自定义样式
<CopyToClipboard
  copyText="https://example.com"
  type="primary"
  size="small"
>
  复制链接
</CopyToClipboard>

downloadExcel

基础的 Excel 文件下载功能

函数签名:

downloadExcel(data: any[], filename?: string): void

参数:

  • data (any[]): 要导出的数据数组
  • filename (string, 可选): 文件名,默认为 'export.xlsx'
import { downloadExcel } from '@qisexin/utils-tool/antd-utils';

const data = [
  { name: '张三', age: 25, city: '北京' },
  { name: '李四', age: 30, city: '上海' }
];

downloadExcel(data, '用户列表.xlsx');

downloadXlsxPro

高级 Excel 文件下载功能,支持复杂样式定制、多工作表、合并单元格等

主要特性:

  • ✅ 支持多工作表
  • ✅ 支持单元格样式定制(字体、颜色、边框等)
  • ✅ 支持合并单元格
  • ✅ 支持列宽自适应
  • ✅ 支持数据类型转换
  • ✅ 支持自定义表头

详细使用方法请参考:downloadXlsxPro 文档

getColumnSearchProps

为 Antd Table 添加本地搜索功能的高阶函数

函数签名:

getColumnSearchProps(dataIndex: string, searchInput?: RefObject<InputRef>): ColumnType<any>

参数:

  • dataIndex (string): 要搜索的列字段名
  • searchInput (RefObject, 可选): 搜索输入框的 ref

返回值: ColumnType<any> - Antd Table 列配置对象

import { getColumnSearchProps } from '@qisexin/utils-tool/antd-utils';
import { useRef } from 'react';
import type { InputRef } from 'antd';

const MyTable = () => {
  const searchInput = useRef<InputRef>(null);
  
  const columns = [
    {
      title: '姓名',
      dataIndex: 'name',
      key: 'name',
      width: '30%',
      ...getColumnSearchProps('name', searchInput),
    },
    {
      title: '年龄',
      dataIndex: 'age',
      key: 'age',
      ...getColumnSearchProps('age'),
    }
  ];
  
  return <Table columns={columns} dataSource={data} />;
};

🪝 自定义 Hooks

useLocalStorageState

将状态存储在 localStorage 中的 Hook,支持跨标签页通信和 SSR

函数签名:

useLocalStorageState<T>(
  key: string,
  defaultValue?: T | (() => T),
  options?: {
    defaultValue?: T | (() => T);
    serializer?: Serializer<T>;
    onError?: (error: Error) => void;
  }
): [T, (value: T | ((prevState: T) => T)) => void]

参数:

  • key (string): localStorage 的键名
  • defaultValue (T | (() => T), 可选): 默认值或默认值工厂函数
  • options (object, 可选): 配置选项
    • defaultValue (T | (() => T), 可选): 默认值(优先级高于第二个参数)
    • serializer (Serializer, 可选): 自定义序列化器
    • onError ((error: Error) => void, 可选): 错误处理函数

返回值: [T, (value: T | ((prevState: T) => T)) => void] - 状态值和设置函数

import { useLocalStorageState } from '@qisexin/utils-tool/hooks';

// 基础用法
const [count, setCount] = useLocalStorageState('count', 0);

// 使用对象
const [user, setUser] = useLocalStorageState('user', {
  name: '',
  age: 0
});

// 自定义配置
const [theme, setTheme] = useLocalStorageState('theme', 'light', {
  onError: (error) => {
    console.error('localStorage error:', error);
  }
});

// 函数式更新
setCount(prev => prev + 1);

🤝 贡献指南

欢迎提交 Issue 和 Pull Request!

  1. Fork 本仓库
  2. 创建你的特性分支 (git checkout -b feature/AmazingFeature)
  3. 提交你的修改 (git commit -m 'Add some AmazingFeature')
  4. 推送到分支 (git push origin feature/AmazingFeature)
  5. 打开一个 Pull Request

📄 许可证

本项目基于 MIT 许可证开源。

🔗 相关链接


如果这个工具库对你有帮助,请给个 ⭐️ 支持一下!

1.5.3

7 months ago

1.5.2

7 months ago

1.5.1

7 months ago

1.4.1

3 years ago

1.4.0

3 years ago

1.3.1

3 years ago

1.3.0

3 years ago

1.2.1

3 years ago

1.2.0

3 years ago

1.1.0

3 years ago

1.0.0

3 years ago