feat(all): 新增工具

This commit is contained in:
2026-05-28 11:30:35 +08:00
parent 5dbedcaf0f
commit 3a55edfafc
85 changed files with 2902 additions and 2591 deletions
+7
View File
@@ -0,0 +1,7 @@
# @r-utils/uview-plus
## 1.3.0
### Minor Changes
- 添加工具
+56 -79
View File
@@ -1,6 +1,16 @@
# @r-utils/uview-plus
基于 [uview-plus](https://uview-plus.jiangruyi.com/) 的 Vue3 组合式 API 工具 Hooks,适用于 uni-app 项目
在项目已使用 [uview-plus](https://uview-plus.jiangruyi.com/) 的前提下,提供适用于 uview-plus 组件的组合式 API Hooks。
## 适用范围
- 适用于已接入 `uview-plus` 的项目。
- 典型场景是 uni-app + Vue3 + uview-plus。
## 不适用范围
- 未使用 `uview-plus` 的项目不建议使用。
- 不适用于 Vue2 项目。
## 安装
@@ -8,102 +18,69 @@
pnpm add @r-utils/uview-plus
```
## 使用
## 导入方式
### 推荐:根入口导入
大多数场景推荐从根入口导入,路径简单,使用心智负担更低。
```ts
import { usePickerSingle, usePicker, useCalendar } from '@r-utils/uview-plus'
import {
usePickerSingle,
usePicker,
useDateTimePicker,
useCalendar,
} from "@r-utils/uview-plus";
```
## API
### 兼容:子路径导入
### `usePickerSingle(options)`
单列 Picker 封装。
| 参数 | 类型 | 默认值 | 说明 |
| --- | --- | --- | --- |
| `value` | `unknown \| Ref<unknown>` | `null` | 选中的值 |
| `show` | `boolean \| Ref<boolean>` | `false` | 是否显示 |
| `indexes` | `Array<number \| null> \| Ref<...>` | `[null]` | 选中的索引 |
| `list` | `PickerColumns[0] \| Ref<...>` | `[]` | 列数据 |
| `textName` | `string` | `'text'` | 显示字段名 |
| `valueName` | `string` | `'value'` | 值字段名 |
| `placeholder` | `string` | `'请选择'` | 占位文本 |
**返回值:**
如果你希望模块边界更清晰,也可以使用子路径导入。两种方式都支持。
```ts
{
value, show, indexes, columns, text, defaultIndex,
showPicker, hidePicker, handleConfirm, handleClose
}
import { usePickerSingle } from "@r-utils/uview-plus/picker-single";
import { usePicker } from "@r-utils/uview-plus/picker";
import { useDateTimePicker } from "@r-utils/uview-plus/datetime-picker";
import { useCalendar } from "@r-utils/uview-plus/calendar";
```
---
## 导出模块
### `usePicker(options)`
| 子路径 | 说明 |
| --- | --- |
| `@r-utils/uview-plus/picker-single` | 单列 picker Hook |
| `@r-utils/uview-plus/picker` | 多列 picker Hook |
| `@r-utils/uview-plus/datetime-picker` | 时间选择器 Hook |
| `@r-utils/uview-plus/calendar` | 日历选择器 Hook |
多列 Picker 封装。
## 使用示例
| 参数 | 类型 | 默认值 | 说明 |
| --- | --- | --- | --- |
| `value` | `unknown[] \| Ref<unknown[]>` | `[]` | 选中的值数组 |
| `show` | `boolean \| Ref<boolean>` | `false` | 是否显示 |
| `indexes` | `Array<number \| null> \| Ref<...>` | `[]` | 选中的索引数组 |
| `columns` | `PickerColumns \| Ref<PickerColumns>` | `[]` | 列数据 |
| `textName` | `string` | `'text'` | 显示字段名 |
| `valueName` | `string` | `'value'` | 值字段名 |
| `placeholder` | `string` | `'请选择'` | 占位文本 |
| `separator` | `string` | `' '` | 多列值拼接分隔符 |
**返回值:**
### 单列选择器
```ts
{
value, show, indexes, columns, text, defaultIndex,
showPicker, hidePicker, handleConfirm, handleClose
}
import { usePickerSingle } from "@r-utils/uview-plus";
const picker = usePickerSingle({
list: [
{ text: "启用", value: 1 },
{ text: "禁用", value: 0 },
],
});
picker.showPicker();
```
---
### `useCalendar(options)`
日历选择封装。
| 参数 | 类型 | 默认值 | 说明 |
| --- | --- | --- | --- |
| `value` | `string \| string[] \| Ref<...>` | `null` | 选中的日期 |
| `show` | `boolean \| Ref<boolean>` | `false` | 是否显示 |
| `mode` | `'single' \| 'multiple' \| 'range' \| Ref<...>` | `'single'` | 日历模式 |
| `placeholder` | `string` | `'请选择'` | 占位文本 |
**返回值:**
### 子路径导入
```ts
{
value, show, text,
showCalendar, hideCalendar, handleConfirm, handleClose
}
import { usePicker } from "@r-utils/uview-plus/picker";
const picker = usePicker({
columns: [[{ text: "浙江", value: "zhejiang" }]],
});
```
## 类型声明
## 注意事项
包内置了 `UViewPlus` namespace 类型声明,无需额外引入。
```ts
declare namespace UViewPlus {
type PickerColumns = any[][];
type PickerValue<T extends PickerColumns = PickerColumns> = T[number][number][];
type PickerConfirmEvent<T extends PickerColumns = PickerColumns> = {
indexs: number[];
value: PickerValue<T>;
values: T;
};
type CalendarConfirmEvent = string[];
}
```
## 许可证
ISC
- 推荐优先使用根入口导入;如果需要更精确的模块边界,也可以使用子路径导入。
- 本包依赖 Vue3 和 uview-plus,请确保业务项目已安装并正确配置。
+29 -4
View File
@@ -1,6 +1,6 @@
{
"name": "@r-utils/uview-plus",
"version": "1.2.1",
"version": "1.3.0",
"private": false,
"description": "uview-plus 组合式 API Hooks",
"type": "module",
@@ -8,13 +8,35 @@
"module": "dist/index.mjs",
"types": "dist/index.d.ts",
"sideEffects": false,
"files": [
"dist"
],
"exports": {
".": {
"types": "./dist/index.d.ts",
"import": "./dist/index.mjs",
"require": "./dist/index.cjs"
},
"./*": "./*"
"./calendar": {
"types": "./dist/calendar/index.d.ts",
"import": "./dist/calendar/index.mjs",
"require": "./dist/calendar/index.cjs"
},
"./datetime-picker": {
"types": "./dist/datetime-picker/index.d.ts",
"import": "./dist/datetime-picker/index.mjs",
"require": "./dist/datetime-picker/index.cjs"
},
"./picker-single": {
"types": "./dist/picker-single/index.d.ts",
"import": "./dist/picker-single/index.mjs",
"require": "./dist/picker-single/index.cjs"
},
"./picker": {
"types": "./dist/picker/index.d.ts",
"import": "./dist/picker/index.mjs",
"require": "./dist/picker/index.cjs"
}
},
"keywords": [
"vue3",
@@ -46,11 +68,12 @@
"scripts": {
"build": "vite build",
"watch": "vite build --watch",
"typecheck": "tsc -p tsconfig.json --noEmit",
"lint": "eslint --ext .js,ts --fix src",
"release": "standard-version",
"format": "prettier --write src",
"commit": "cz",
"lint-staged": "lint-staged",
"test": "jest"
"test": "vitest run"
},
"peerDependencies": {
"uview-plus": ">=3.0.0",
@@ -62,9 +85,11 @@
}
},
"dependencies": {
"@jonny1994/qqmap-wx-jssdk": "^1.4.0",
"lodash-es": "catalog:"
},
"devDependencies": {
"@dcloudio/types": "^3.4.14",
"@types/lodash-es": "catalog:",
"vite": "catalog:",
"vite-plugin-dts": "catalog:",
+4 -1
View File
@@ -17,7 +17,10 @@ describe("useCalendar", () => {
test("单选模式:text 显示 value,无值时显示 placeholder", () => {
const scope = effectScope();
scope.run(() => {
const { value, text } = useCalendar({ mode: "single", placeholder: "请选日期" });
const { value, text } = useCalendar({
mode: "single",
placeholder: "请选日期",
});
expect(text.value).toBe("请选日期");
value.value = "2024-01-15";
expect(text.value).toBe("2024-01-15");
@@ -50,7 +50,9 @@ describe("useDateTimePicker", () => {
test("handleConfirm 关闭弹窗(不更新 value", () => {
const scope = effectScope();
scope.run(() => {
const { value, show, handleConfirm } = useDateTimePicker({ value: "2024-01-01" });
const { value, show, handleConfirm } = useDateTimePicker({
value: "2024-01-01",
});
show.value = true;
const event = { indexs: [], value: [], values: [] } as any;
handleConfirm(event);
+10 -2
View File
@@ -60,7 +60,11 @@ describe("usePicker", () => {
test("indexes 含 null 时 text 显示 placeholder", async () => {
const scope = effectScope();
await scope.run(async () => {
const { text } = usePicker({ indexes: [null, 1], columns, placeholder: "请选择地区" });
const { text } = usePicker({
indexes: [null, 1],
columns,
placeholder: "请选择地区",
});
await nextTick();
expect(text.value).toBe("请选择地区");
});
@@ -71,7 +75,11 @@ describe("usePicker", () => {
const scope = effectScope();
await scope.run(async () => {
const { indexes, value, handleConfirm } = usePicker({ columns });
handleConfirm({ indexs: [1, 0], value: ["pb", "ca"], values: columns } as any);
handleConfirm({
indexs: [1, 0],
value: ["pb", "ca"],
values: columns,
} as any);
expect(indexes.value).toEqual([1, 0]);
await nextTick();
expect(value.value).toEqual(["pb", "ca"]);
+1 -1
View File
@@ -6,6 +6,6 @@
"baseUrl": "./",
"paths": {
"@/*": ["src/*"]
},
}
}
}
+50
View File
@@ -0,0 +1,50 @@
import * as QQMapWX from "@jonny1994/qqmap-wx-jssdk";
export * from "@jonny1994/qqmap-wx-jssdk";
/**
* 行政区划列表
* @example
* cidx: [103, 118]
* fullname: "张家口市"
* id: "130700"
* location: {lat: 40.82444, lng: 114.88755}
* name: "张家口"
* pinyin: ["zhang", "jia", "kou"]
*/
export interface GetCityListSuccessResultResult {
/**
* 行政区划唯一标识
* @example "110000"
*/
id: number;
/**
* 简称,如“内蒙古”
*/
name?: string;
/**
* 全称,如“内蒙古自治区”
* @example "北京市"
*/
fullname: string;
/**
* 中心点坐标
* @example {lat: 39.90469, lng: 116.40717}
*/
location: QQMapWX.ResultLocation;
/**
* 行政区划拼音,每一下标为一个字的全拼,如:[“nei”,“meng”,“gu”]
*/
pinyin: string[];
/**
* 子级行政区划在下级数组中的下标位置
* @example [0, 15]
*/
cidx?: number[];
}
export interface GetCityListSuccessResult extends QQMapWX.CommonResult {
/**
* 结果数组,第0项,代表一级行政区划,第1项代表二级行政区划,以此类推;使用getchildren接口时,仅为指定父级行政区划的子级
*/
result: GetCityListSuccessResultResult[];
}
+2 -3
View File
@@ -1,10 +1,9 @@
/// <reference types="uview-plus/types" />
declare namespace UViewPlus {
type PickerColumns = never[][];
type PickerValue<T extends PickerColumns = PickerColumns> = T[number][number][];
type PickerValue<T extends PickerColumns = PickerColumns> =
T[number][number][];
type PickerConfirmEvent<T extends PickerColumns = PickerColumns> = {
indexs: number[];
+29 -12
View File
@@ -1,31 +1,48 @@
import { defineConfig } from 'vite';
import dts from 'vite-plugin-dts';
import { resolve } from 'node:path';
import { fileURLToPath } from 'node:url';
import { defineConfig } from "vite";
import dts from "vite-plugin-dts";
import { resolve } from "node:path";
import { fileURLToPath } from "node:url";
const __dirname = fileURLToPath(new URL('.', import.meta.url));
const __dirname = fileURLToPath(new URL(".", import.meta.url));
export default defineConfig({
build: {
lib: {
entry: resolve(__dirname, 'src/index.ts'),
formats: ['es', 'cjs'],
fileName: (format) => `index.${format === 'es' ? 'mjs' : 'cjs'}`,
entry: {
index: resolve(__dirname, "src/index.ts"),
"calendar/index": resolve(__dirname, "src/calendar/index.ts"),
"datetime-picker/index": resolve(
__dirname,
"src/datetime-picker/index.ts",
),
"picker-single/index": resolve(
__dirname,
"src/picker-single/index.ts",
),
"picker/index": resolve(__dirname, "src/picker/index.ts"),
},
formats: ["es", "cjs"],
fileName: (format, entryName) =>
`${entryName}.${format === "es" ? "mjs" : "cjs"}`,
},
rollupOptions: {
external: ['vue', 'lodash-es'],
external: ["vue", "lodash-es"],
output: {
chunkFileNames: "chunks/[name]-[hash].js",
assetFileNames: "assets/[name]-[hash][extname]",
},
},
sourcemap: true,
},
resolve: {
alias: {
'@': resolve(__dirname, 'src'),
"@": resolve(__dirname, "src"),
},
},
plugins: [
dts({
include: ['src', 'types'],
outDir: 'dist',
include: ["src", "types"],
outDir: "dist",
}),
],
});