npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@robot-admin/directives

v1.0.0

Published

Vue3 自定义指令集合 - 复制、防抖、节流、拖拽、长按、权限、水印

Readme

@robot-admin/directives

🎯 开箱即用的 Vue3 自定义指令集合

npm version license

✨ 特性

  • 🚀 开箱即用 - 一行代码全局注册 7 个常用指令
  • 🎯 按需引入 - 支持单指令导入,Tree-shaking 友好
  • 💪 TypeScript - 完整类型定义和智能提示
  • 🔌 零依赖 - 仅依赖 Vue 3.3+
  • 📦 体积小巧 - 打包后 ~30KB (gzip < 10KB)
  • 🎨 灵活配置 - 简单/高级两种用法

📦 快速开始

安装

npm install @robot-admin/directives
# or
bun add @robot-admin/directives

全局注册(推荐)

// main.ts
import { createApp } from "vue";
import { setupDirectives } from "@robot-admin/directives";

const app = createApp(App);
setupDirectives(app);
app.mount("#app");

按需引入

<script setup>
import { vCopy, vDebounce } from "@robot-admin/directives";
</script>

<template>
  <button v-copy="'复制内容'">复制</button>
  <button v-debounce="300" @click="handleClick">防抖按钮</button>
</template>

快速体验

<script setup lang="ts">
import { ref } from "vue";

const searchText = ref("");
const handleSearch = (text: string) => {
  console.log("搜索:", text);
};
</script>

<template>
  <div class="demo-container">
    <!-- 复制指令 -->
    <button v-copy="'订单号: 202602150001'">复制订单号</button>

    <!-- 防抖搜索 -->
    <input
      v-model="searchText"
      v-debounce="500"
      @input="handleSearch(searchText)"
      placeholder="防抖搜索"
    />

    <!-- 权限按钮 -->
    <button v-permission="'admin'">管理员功能</button>

    <!-- 水印内容 -->
    <div v-watermark="'机密文件'" style="height: 300px">敏感内容区域</div>
  </div>
</template>

📚 指令列表

| 指令 | 功能 | 使用场景 | | ---------------- | ---------------- | -------------------------------- | | v-copy | 复制文本到剪贴板 | 一键复制订单号、邀请码、分享链接 | | v-debounce | 防抖处理 | 搜索输入框、表单提交按钮 | | v-throttle | 节流处理 | 滚动加载、频繁点击的按钮 | | v-drag | 元素拖拽 | 模态框拖动、看板卡片排序 | | v-longpress | 长按触发 | 删除操作二次确认、长按复制 | | v-permission | 权限控制 | 按钮/功能的权限显隐 | | v-watermark | 水印添加 | 敏感内容防截图、版权保护 |


📖 详细文档

v-copy - 复制指令

快速复制文本到剪贴板,支持自定义提示和回调。

基础用法

<!-- 复制字符串 -->
<button v-copy="'Hello World'">复制</button>

<!-- 复制元素文本内容 -->
<div v-copy>点击复制这段文本</div>

高级配置

<button
  v-copy="{
    text: '要复制的内容',
    successMessage: '复制成功!',
    errorMessage: '复制失败',
    onSuccess: (text) => console.log('已复制:', text),
    onError: (err) => console.error(err),
    messageInstance: message, // naive-ui 的 message 实例
  }"
>
  复制
</button>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ----------------- | ------------------------ | ------------ | ---------------------- | | text | string | 元素文本 | 要复制的文本内容 | | successMessage | string | '复制成功' | 成功提示信息 | | errorMessage | string | '复制失败' | 失败提示信息 | | onSuccess | (text: string) => void | - | 复制成功回调 | | onError | (error: Error) => void | - | 复制失败回调 | | messageInstance | any | - | UI 组件的 message 实例 |


v-debounce - 防抖指令

防止短时间内重复触发事件,适用于搜索输入、表单提交等场景。

基础用法

<!-- 默认 300ms 防抖 -->
<button v-debounce @click="handleSubmit">提交</button>

<!-- 自定义延迟时间 -->
<button v-debounce="500" @click="handleSubmit">提交</button>

高级配置

<button
  v-debounce="{
    delay: 500,
    immediate: true, // 首次立即执行
  }"
  @click="handleSubmit"
>
  立即提交
</button>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ----------- | --------- | ------- | -------------------- | | delay | number | 300 | 防抖延迟时间(毫秒) | | immediate | boolean | false | 是否首次立即执行 |


v-throttle - 节流指令

限制事件触发频率,适用于滚动、窗口调整大小等高频事件。

基础用法

<!-- 默认 300ms 节流 -->
<button v-throttle @click="handleClick">点击</button>

<!-- 自定义间隔时间 -->
<div v-throttle="1000" @scroll="handleScroll">滚动区域</div>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ------- | -------- | ------ | -------------------- | | delay | number | 300 | 节流间隔时间(毫秒) |


v-drag - 拖拽指令

使元素可拖拽移动,支持边界限制。

基础用法

<!-- 自由拖拽 -->
<div v-drag>拖动我</div>

<!-- 仅标题栏可拖拽 -->
<div>
  <div v-drag="{ handle: '.header' }">
    <div class="header">拖拽此处</div>
    <div class="body">内容区域</div>
  </div>
</div>

高级配置

<div
  v-drag="{
    boundary: true, // 限制在父容器内
    handle: '.drag-handle', // 拖拽手柄选择器
  }"
>
  受限拖拽元素
</div>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ---------- | --------- | ------- | --------------------- | | boundary | boolean | false | 是否限制在父容器内 | | handle | string | - | 拖拽手柄的 CSS 选择器 |


v-longpress - 长按指令

长按触发回调,适用于删除确认、长按复制等场景。

基础用法

<script setup>
const handleLongPress = () => {
  console.log("长按触发");
};
</script>

<button v-longpress="handleLongPress">长按我</button>

高级配置

<button
  v-longpress="{
    duration: 1000, // 长按 1 秒触发
    callback: handleLongPress,
  }"
>
  长按 1 秒
</button>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ---------- | ------------ | ------ | -------------------- | | duration | number | 500 | 长按触发时间(毫秒) | | callback | () => void | - | 长按触发的回调函数 |


v-permission - 权限指令

根据用户权限控制元素的显示/隐藏/禁用。

基础用法

<!-- 单个权限 -->
<button v-permission="'admin'">管理员可见</button>

<!-- 多个权限(OR 模式) -->
<button v-permission="['admin', 'editor']">编辑权限可见</button>

高级配置

<button
  v-permission="{
    permissions: ['admin', 'super'],
    mode: 'AND', // 需要同时拥有多个权限
    fallback: 'disable', // 无权限时禁用而非隐藏
    authData: userPermissions, // 自定义权限数据源
  }"
>
  需要多权限
</button>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | ------------- | ------------------------- | -------- | ------------------ | | permissions | string \| string[] | - | 所需权限标识 | | mode | 'OR' \| 'AND' | 'OR' | 多权限判断模式 | | fallback | 'hide' \| 'disable' | 'hide' | 无权限时的处理方式 | | authData | Record<string, boolean> | - | 自定义权限数据 |


v-watermark - 水印指令

为元素添加防篡改水印,适用于敏感内容保护。

基础用法

<!-- 文本水印 -->
<div v-watermark="'机密文件'">内容区域</div>

<!-- 多行水印 -->
<div v-watermark="['机密文件', '请勿外传']">内容区域</div>

高级配置

<div
  v-watermark="{
    text: '内部资料',
    textColor: 'rgba(0, 0, 0, 0.15)',
    fontSize: 16,
    fontFamily: 'Microsoft YaHei',
    rotate: -30, // 旋转角度
    gap: [100, 100], // 水印间距
    zIndex: 9999,
    preventDelete: true, // 防止删除(MutationObserver)
  }"
>
  带水印的内容
</div>

参数说明

| 参数 | 类型 | 默认值 | 说明 | | --------------- | -------------------- | ----------------- | ------------------------- | | text | string \| string[] | - | 水印文本内容 | | textColor | string | rgba(0,0,0,.15) | 水印文字颜色 | | fontSize | number | 16 | 水印字体大小 | | fontFamily | string | sans-serif | 水印字体 | | rotate | number | -30 | 水印旋转角度 | | gap | [number, number] | [100, 100] | 水印间距 [x, y] | | zIndex | number | 9999 | 水印层级 | | preventDelete | boolean | false | 防止删除(监听 DOM 变化) |


� 最佳实践

1. 指令组合使用

<!-- 防抖 + 权限控制 + 复制 -->
<button
  v-permission="'admin'"
  v-debounce="500"
  v-copy="orderNumber"
  @click="handleSubmit"
>
  提交订单
</button>

2. 与 UI 组件库集成

// main.ts - 与 Naive UI 集成
import { createApp } from "vue";
import { createDiscreteApi } from "naive-ui";
import { setupDirectives } from "@robot-admin/directives";

const app = createApp(App);
const { message } = createDiscreteApi(["message"]);

// 全局提供 message 实例供 v-copy 使用
app.provide("$message", message);

setupDirectives(app);
<!-- 在组件中使用 -->
<script setup>
import { inject } from "vue";
const message = inject("$message");
</script>

<template>
  <button v-copy="{ text: '内容', messageInstance: message }">
    复制(使用 Naive UI 提示)
  </button>
</template>

3. 动态权限控制

<script setup>
import { computed } from "vue";
import { useUserStore } from "@/stores/user";

const userStore = useUserStore();
const userPermissions = computed(() => userStore.permissions);
</script>

<template>
  <!-- 动态权限数据 -->
  <button
    v-permission="{
      permissions: ['delete:user'],
      authData: userPermissions,
      fallback: 'disable',
    }"
  >
    删除用户
  </button>
</template>

4. 响应式水印

<script setup>
import { computed } from "vue";
import { useUserStore } from "@/stores/user";

const userStore = useUserStore();
const watermarkText = computed(() => [
  userStore.username,
  new Date().toLocaleDateString(),
]);
</script>

<template>
  <!-- 水印会随用户信息自动更新 -->
  <div v-watermark="watermarkText">敏感内容</div>
</template>

5. 性能优化建议

  • 全局注册推荐:如果项目中多处使用,推荐全局注册
  • 按需引入优化:单页应用特定页面可按需引入
  • 防抖节流参数:根据实际网络延迟和用户体验调整延迟时间
  • 水印防删除preventDelete: true 会启用 MutationObserver,注意性能影响
  • ⚠️ 避免过度使用:不要在列表循环中使用复杂指令(如水印)

�🔧 TypeScript 支持

完整的类型定义和智能提示:

import type {
  CopyOptions,
  CopyBinding,
  DebounceOptions,
  ThrottleOptions,
  DragOptions,
  LongPressOptions,
  PermissionOptions,
  WatermarkOptions,
  WatermarkBinding,
} from "@robot-admin/directives";

// 示例:类型化配置
const copyConfig: CopyOptions = {
  text: "Hello World",
  successMessage: "复制成功",
  onSuccess: (text) => console.log(text),
};

🛠️ 开发与调试

本地开发

# 克隆 monorepo
git clone https://github.com/ChenyCHENYU/robot-admin-packages.git
cd robot-admin-packages/packages/directives

# 安装依赖
bun install

# 开发模式(监听文件变化)
bun run dev

# 构建生产包
bun run build

在主项目中调试

# 1. 在 directives 包目录建立链接
cd packages/directives
bun link

# 2. 在主项目中使用链接
cd /path/to/your-project
bun link @robot-admin/directives

# 3. 启动开发服务器(自动使用本地源码)
bun run dev:local

提示:主项目需配置 Vite alias 解析本地包源码,参考 viteLocalPackagesConfig.ts


🚀 扩展指南

添加新指令

  1. 创建指令文件 src/directives/your-directive.ts
import type { Directive, DirectiveBinding } from "vue";

// 定义配置类型
export interface YourDirectiveOptions {
  // 配置选项
}

// 定义指令值类型
export type YourDirectiveBinding = string | YourDirectiveOptions;

// 实现指令逻辑
const vYourDirective: Directive = {
  mounted(el: HTMLElement, binding: DirectiveBinding<YourDirectiveBinding>) {
    // 指令挂载时的逻辑
  },
  updated(el: HTMLElement, binding: DirectiveBinding<YourDirectiveBinding>) {
    // 指令更新时的逻辑
  },
  unmounted(el: HTMLElement) {
    // 指令卸载时的清理逻辑
  },
};

export default vYourDirective;
  1. 注册到导出 src/index.ts
// 导出指令
export { default as vYourDirective } from "./directives/your-directive";
// 导出类型
export type {
  YourDirectiveOptions,
  YourDirectiveBinding,
} from "./directives/your-directive";
  1. 添加到全局注册 src/install.ts
import vYourDirective from "./directives/your-directive";

const directivesMap = {
  // ...existing directives
  "your-directive": vYourDirective,
};
  1. 更新 README 文档 添加使用示例和说明

  2. 构建并测试

bun run build
# 在主项目中测试

贡献新指令

欢迎贡献常用的业务指令!提交前请确保:

  • ✅ 指令具有通用性,适用于多种业务场景
  • ✅ 完整的 TypeScript 类型定义
  • ✅ 清晰的代码注释和 JSDoc 文档
  • ✅ 测试验证跨浏览器兼容性
  • ✅ 更新 README 文档和使用示例

🗺️ 路线图

v1.x(当前版本)

  • ✅ 7 个核心指令(copy / debounce / throttle / drag / longpress / permission / watermark)
  • ✅ 完整 TypeScript 支持
  • ✅ 零依赖设计

v2.0(规划中)

  • [ ] v-lazy - 图片懒加载指令
  • [ ] v-infinite-scroll - 无限滚动指令
  • [ ] v-click-outside - 点击外部区域触发
  • [ ] v-tooltip - 轻量级 tooltip 指令
  • [ ] v-loading - 加载状态指令
  • [ ] 支持自定义指令配置(全局默认值)
  • [ ] 提供 Vue 模板类型增强(Volar 插件)

未来计划

  • [ ] 指令组合器(Compose API)
  • [ ] 单元测试覆盖
  • [ ] 在线 Playground 演示
  • [ ] 性能监控和优化

🎉 欢迎提交 IssuePR 参与建设!


❓ 常见问题

Q1: 如何解决 TypeScript 类型提示不生效?

A: 确保安装了 @vue/runtime-core 类型扩展。在项目根目录创建 global.d.ts

// global.d.ts
import "@robot-admin/directives";

declare module "@vue/runtime-core" {
  export interface GlobalDirectives {
    vCopy: (typeof import("@robot-admin/directives"))["vCopy"];
    vDebounce: (typeof import("@robot-admin/directives"))["vDebounce"];
    vThrottle: (typeof import("@robot-admin/directives"))["vThrottle"];
    vDrag: (typeof import("@robot-admin/directives"))["vDrag"];
    vLongpress: (typeof import("@robot-admin/directives"))["vLongpress"];
    vPermission: (typeof import("@robot-admin/directives"))["vPermission"];
    vWatermark: (typeof import("@robot-admin/directives"))["vWatermark"];
  }
}

Q2: v-permission 指令如何与 Pinia/Vuex 集成?

A: 通过 authData 参数传入响应式权限数据:

<script setup>
import { computed } from "vue";
import { useAuthStore } from "@/stores/auth";

const authStore = useAuthStore();
const permissions = computed(() => authStore.permissions);
</script>

<template>
  <button v-permission="{ permissions: 'admin', authData: permissions }">
    管理功能
  </button>
</template>

Q3: v-copy 复制失败怎么办?

A: 可能原因:

  1. HTTPS 要求:现代浏览器要求 HTTPS 才能使用剪贴板 API
  2. 权限问题:用户未授予剪贴板权限
  3. 降级方案:包已自动降级到 document.execCommand 方式

调试方法:

<button
  v-copy="{
    text: '内容',
    onError: (err) => console.error('复制失败:', err),
  }"
>
  复制
</button>

Q4: 水印被删除怎么办?

A: 启用 preventDelete 选项:

<div v-watermark="{ text: '水印', preventDelete: true }">内容</div>

注意:此功能使用 MutationObserver 监听 DOM 变化,会有轻微性能开销。

Q5: 如何在 Nuxt/Vite SSR 中使用?

A: 指令仅在客户端执行,需添加客户端判断:

// plugins/directives.client.ts (Nuxt)
import { setupDirectives } from "@robot-admin/directives";

export default defineNuxtPlugin((nuxtApp) => {
  setupDirectives(nuxtApp.vueApp);
});
// main.ts (Vite SSR)
import { setupDirectives } from "@robot-admin/directives";

if (typeof window !== "undefined") {
  setupDirectives(app);
}

Q6: 指令性能优化建议?

A:

  • ✅ 避免在 v-for 循环中大量使用复杂指令(如水印)
  • ✅ 防抖/节流延迟时间根据实际需求调整(不宜过小)
  • ✅ 拖拽指令在长列表中慎用,考虑虚拟滚动
  • ✅ 权限指令使用计算属性缓存权限判断结果

📄 许可证

MIT © 2026 ChenYu


🔗 相关链接

  • NPM: https://www.npmjs.com/package/@robot-admin/directives
  • GitHub: https://github.com/ChenyCHENYU/robot-admin-packages
  • 主项目: https://github.com/ChenyCHENYU/Robot_Admin
  • 问题反馈: https://github.com/ChenyCHENYU/robot-admin-packages/issues