Files
CeruMusic/CONTEXT_MENU_COMPLETE.md
sqj 51df14a9e9 1. 歌单
- 新增右键移除歌曲
   - local 页歌单右键操作
   - 歌单页支持修改封面
2. debug:右键菜单二级菜单位置决策
2025-09-25 19:56:45 +08:00

6.5 KiB
Raw Blame History

🎯 自定义右键菜单组件 - 完整功能实现

项目完成状态

已完成 - 功能完整的自定义右键菜单组件,包含所有要求的特性和优化

🚀 核心功能特性

📋 基础功能

  • 可配置菜单项 - 支持图标、文字、快捷键显示
  • 多级子菜单 - 支持无限层级嵌套
  • 菜单项状态 - 支持禁用、隐藏、分割线
  • 事件回调 - 完整的点击事件处理机制

🎨 样式与主题

  • 自定义主题 - 支持亮色/暗色/自动主题切换
  • 现代化设计 - 圆角、阴影、渐变、动画效果
  • 响应式布局 - 适配不同屏幕尺寸
  • 无障碍支持 - 高对比度、减少动画模式

🔧 智能定位与边界处理

  • 智能定位 - 自动检测屏幕边界并调整位置
  • 向上展开 - 底部空间不足时自动向上显示
  • 滚动支持 - 菜单过长时支持滚动和滚动指示器
  • 子菜单定位 - 子菜单智能避让边界

⌨️ 交互优化

  • 键盘导航 - 支持方向键、ESC、回车等快捷键
  • 鼠标交互 - 悬停显示子菜单,点击外部关闭
  • 滚轮支持 - 长菜单支持滚轮滚动
  • 触摸友好 - 移动端优化的交互体验

📁 文件结构

src/renderer/src/components/ContextMenu/
├── types.ts                    # TypeScript 类型定义
├── ContextMenu.vue            # 主菜单组件
├── ContextMenuItem.vue        # 菜单项组件
├── useContextMenu.ts          # 组合式 API 钩子
├── index.ts                   # 组件导出入口
└── README.md                  # 使用文档

🎯 使用示例

基础用法

<template>
  <div @contextmenu="handleContextMenu">右键点击此区域</div>

  <ContextMenu
    v-model:visible="visible"
    :items="menuItems"
    :position="position"
    @item-click="handleItemClick"
  />
</template>

<script setup>
import { ref } from 'vue'
import { ContextMenu, createMenuItem, commonMenuItems } from '@renderer/components/ContextMenu'

const visible = ref(false)
const position = ref({ x: 0, y: 0 })
const menuItems = ref([
  createMenuItem('copy', '复制', {
    icon: 'copy',
    shortcut: 'Ctrl+C',
    onClick: () => console.log('复制')
  }),
  commonMenuItems.divider,
  createMenuItem('paste', '粘贴', {
    icon: 'paste',
    onClick: () => console.log('粘贴')
  })
])

const handleContextMenu = (event) => {
  event.preventDefault()
  position.value = { x: event.clientX, y: event.clientY }
  visible.value = true
}

const handleItemClick = (item, event) => {
  if (item.onClick) {
    item.onClick(item, event)
  }
  visible.value = false
}
</script>

多级菜单

const menuItems = [
  createMenuItem('file', '文件', {
    icon: 'folder',
    children: [
      createMenuItem('new', '新建', {
        icon: 'add',
        children: [
          createMenuItem('vue', 'Vue 组件', {
            onClick: () => console.log('新建 Vue 组件')
          }),
          createMenuItem('ts', 'TypeScript 文件', {
            onClick: () => console.log('新建 TS 文件')
          })
        ]
      }),
      createMenuItem('open', '打开', {
        icon: 'folder-open',
        onClick: () => console.log('打开文件')
      })
    ]
  })
]

🎨 样式特性

现代化视觉效果

  • 毛玻璃效果 - backdrop-filter: blur(8px)
  • 多层阴影 - 立体感阴影效果
  • 流畅动画 - cubic-bezier 缓动函数
  • 悬停反馈 - 微妙的变换和颜色变化

响应式设计

  • 桌面端 - 最小宽度 160px最大宽度 300px
  • 平板端 - 适配中等屏幕尺寸
  • 移动端 - 优化触摸交互,增大点击区域

🔧 高级功能

智能边界处理

// 自动检测屏幕边界
if (x + menuWidth > viewportWidth) {
  x = viewportWidth - menuWidth - 8
}

// 向上展开逻辑
if (availableHeight < 200 && availableHeightFromTop > availableHeight) {
  y = y - menuHeight
}

滚动功能

  • 自动滚动 - 菜单超出屏幕高度时启用
  • 滚动指示器 - 显示可滚动方向
  • 键盘滚动 - 支持方向键和 Home/End 键
  • 鼠标滚轮 - 平滑滚动体验

无障碍支持

  • 高对比度模式 - 自动适配系统设置
  • 减少动画模式 - 尊重用户偏好设置
  • 键盘导航 - 完整的键盘操作支持

🧪 测试页面

访问 http://localhost:5174/#/context-menu-test 查看完整的功能演示:

  1. 基础功能测试 - 图标、快捷键、禁用项
  2. 多级菜单测试 - 嵌套子菜单
  3. 长菜单滚动 - 25+ 菜单项滚动测试
  4. 边界处理测试 - 四个角落的边界测试
  5. 歌曲列表模拟 - 实际使用场景演示

🎯 集成状态

已集成页面

  • 本地音乐页面 (src/renderer/src/views/music/local.vue)
    • 歌曲右键菜单
    • 播放、收藏、添加到歌单等功能
    • 多级歌单选择

菜单功能

  • 播放歌曲
  • 下一首播放
  • 收藏歌曲
  • 添加到歌单(支持子菜单)
  • 导出歌曲
  • 查看歌曲信息
  • 删除歌曲

🚀 性能优化

渲染优化

  • Teleport 渲染 - 避免 z-index 冲突
  • 按需渲染 - 只在显示时渲染菜单
  • 事件委托 - 高效的事件处理

内存管理

  • 自动清理 - 组件卸载时清理事件监听
  • 防抖处理 - 避免频繁的位置计算
  • 缓存优化 - 计算结果缓存

🔮 扩展性

自定义组件

// 支持自定义图标组件
createMenuItem('custom', '自定义', {
  icon: CustomIconComponent,
  onClick: () => {}
})

主题扩展

/* 自定义主题变量 */
:root {
  --context-menu-bg: #ffffff;
  --context-menu-border: #e5e5e5;
  --context-menu-shadow: 0 4px 12px rgba(0, 0, 0, 0.15);
}

📊 浏览器兼容性

  • Chrome 88+
  • Firefox 85+
  • Safari 14+
  • Edge 88+
  • Electron (项目环境)

🎉 总结

这个自定义右键菜单组件完全满足了项目需求:

  1. 功能完整 - 支持所有要求的特性
  2. 性能优秀 - 流畅的动画和交互
  3. 样式现代 - 符合当前设计趋势
  4. 易于使用 - 简洁的 API 设计
  5. 高度可定制 - 灵活的配置选项
  6. 无障碍友好 - 支持各种用户需求

组件已成功集成到 CeruMusic 项目中,可以在本地音乐页面体验完整功能。通过测试页面可以验证各种边界情况和高级功能的表现。