# universal_audio_player **Repository Path**: mbt_tlt/universal_audio_player ## Basic Information - **Project Name**: universal_audio_player - **Description**: 通用性音频播放器 - **Primary Language**: JavaScript - **License**: AGPL-3.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 1 - **Forks**: 0 - **Created**: 2022-07-15 - **Last Updated**: 2023-11-16 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # MBT_TLT 通用化音频播放器 # 项目简介 MBT_TLT 通用音频播放器是一款开源的通用性 Web 音频播放器,旨在提供一款功能强大,能够解析并播放大部分主流音频格式的通用性 Web 音频播放器组件,所支持的功能: - 简约清爽的用户界面及丝滑流畅的操作交互 - 比主流音频播放器更加丰富的播放模式选择,支持自定义歌单中各个歌曲随机权重的随机选取算法,支持自定义歌单歌曲推荐播放顺序 - 播放器全组件化设计,支持播放器组件自定义配置及拓展功能 - 功能强大的音频歌词展示,可独立浏览器进程的悬浮音频歌词展示拓展栏(开发中,仅支持 Electron) - 支持相比浏览器默认音频更加全面的主流音频格式解析及播放功能(开发中) # 项目技术栈 基于 `Vue3 + Vite2` 基础技术架构 # 项目初始化 ```shell npm i ``` # 开发日志 - v0.1.0 - 基础的可供单曲播放的音频播放器。 注:音频播放模式, 音频歌词模块, 收藏歌曲接口暂不可用 - v0.2.0 - 实现播放器播放模式相关功能 - 修复播放器在播放后切换音频再暂停后切换音频会出现异常播放播放音频的 BUG - 修复在随机模式时正在播放音频后手动切换音频与选取音频不一致下偶现的 BUG - 初步判断是由于播放过程中异常触发了音频结束机制导致了切换 - 确定是因为异常触发音频结束机制导致了切换, 原因为 duration 值异常置为 0 导致了异常触发音频结束策略 - 本质原因是由于定时器执行 Interval 延时逻辑时恰好切换的音频并未完成加载元数据的事件, duration 被校验机制由 NaN 修改为了 0 导致异常触发了播放结束机制 - v0.3.0 - 修复 音频播放器拓展区 定位绝对基准点异常的 BUG - 将音频播放定时器相关逻辑重构修改为 timeupdate 事件与 ended 事件处理器 - 将音频播放时间相关逻辑独立成 store 监控项 - 基础歌词展示组件(嵌入模式) - 以音频播放进度为基准的歌词展示 - 歌词对象切换缓动过渡效果 - 两种歌词展示组件模式:浏览歌词模式, 进入该模式时歌词基准对齐功能停止; 默认模式, 进入该模式时歌词展示自动与音频时间轴校准定位 - 点击歌词音频跳转定位功能 - 词间伴奏提示功能 - 多语言歌词字幕支持 - 修改切换歌曲相关逻辑, 若为重复选中正在播放的歌曲, 将其处理逻辑由原来的清空随机选取缓存池重新播放该歌曲改为忽略用户操作 - 修复歌曲切换时歌词列表不回滚置顶的 BUG - 对齐 Chrome 与 FireFox 浏览器的样式设计 - 由于 FireFox 浏览器存在中英文使用不同字体时设置 font-weight: bold 效果不一致的 BUG, 细调 歌词展示组件 歌词节点在高亮与默认情况下的 color 对比度, 取消高亮时 font-weight 样式变化 - 修复 歌词展示组件 在 FireFox 浏览器下 歌词节点行间距过大的 BUG - 修复 歌词展示组件 在 FireFox 浏览器下 滚动条样式 不生效的 BUG - v0.4.0 - 鼠标悬浮时滚动展示因内容过长被截断的内容 - 实现 自动隐藏内容容器 基础组件, 其可以自动截断隐藏溢出文本, 并且支持鼠标悬浮时滚动展示被截断的内容 - 完成 播放器元数据区组件 文本节点溢出内容的鼠标悬浮滚动展示功能对接 - 完成 歌单/歌曲列表组件 文本节点溢出内容的鼠标悬浮滚动展示功能对接 - 基础组件优化 - 实现 AutoHideContentBox 基础组件(自动隐藏内容容器)依据内容字符数量自动设置默认动画时间 - 实现 Timeline 基础组件(时间轴组件)冻结模式 - 基础组件的 slot 监听实现(利用 MutationObserver API) - Tooltip 基础组件(信息提示)的 slot 监听对接 - AutoHideContentBox 基础组件(自动隐藏内容容器)的 slot 监听对接 - 修复 拓展组件 点击事件不能触发其他拓展组件本应该触发的自动关闭的 BUG - 修复 播放器元数据 未加载状态下依赖播放器时间轴而导致的歌词展示组件加载异常的 BUG - 实现 音量调节拓展组件 一键静音/还原 功能 - 实现 播放器 整体在不小于组件最小宽度时响应式自适应包裹容器宽度 - 播放器最小宽度最小峰值区间为 544px(对应着元数据区显示"暂无数据"), 建议播放器包裹容器宽度至少为 700 px - v0.5.0 - 播放器播放模式功能完善 - 实现 推荐播放列表模式 功能, 存在推荐列表按照推荐列表顺序播放, 否则默认按照歌单的歌曲列表播放 - 完善 随机权重列表模式 功能, 当不存在给定随机权重列表时默认按照所有歌曲均等权重进行随机选取 - 实现需求项 - 播放器用户自定义工具项相关接口开发 - 播放器用户自定义拓展模块相关接口开发 - 播放器 工具栏-歌曲收藏 自定义远端接口配置开发 - 实现 播放器 对外暴露方法列表 externalMethodList, 其包含以下方法: - setPlaylistWarehouse 方法, 用于 设置播放器歌单列表 - addPlaylist 方法, 用于 播放器添加歌单 - removePlaylist 方法, 用于 播放器移除歌单 - setPlaylistValue 方法, 用于 设置指定歌单的歌曲列表 - addSong 方法, 用于 指定歌单添加歌曲 - removeSong 方法, 用于 指定歌单移除歌曲 - setRandomWeightedObjList 方法, 用于 设定指定歌单的随机权重列表 - setRecommendedOrderList 方法, 用于 设置指定歌单的推荐播放列表 - setEnableToolList 方法, 用于 设置播放器所启用的工具项列表 - createToolStateObj 方法, 用于 创建工具项状态列表, 配合 registerCustomToolItem 实现用户自定义工具项 - registerCustomToolItem 方法, 用于 注册用户自定义工具项 - changeExtendFunc 方法, 用于 更改工具项拓展方法, 不过不建议使用该方法去修改播放器所默认提供的工具项本身自带的 ExtendFunc - registerExtendModule 方法, 用于 注册用户自定义拓展模块, - 说明1: 若项将 自定义拓展模块 与 自定义工具项 绑定, 则两者 key 必须相同 - 说明2: 若想将自定义拓展模块与自定义工具项的某个状态绑定, 则拓展模块 key 必须为 `${ 工具项 key }_${ 工具项状态 key }` - addRemoteInterface 方法, 用于 注册远端接口对象 - removeRemoteInterface 方法, 用于 移除远端接口对象, 不建议使用该方法删除播放器所默认提供的远端接口对象 - updateRemoteInterface 方法, 用于 更新远端接口对象, 若不存在则新增该接口, 若存在则覆盖, 不建议使用该方法更改播放器所默认提供的远端接口对象 - setRemoteInterfaceList 方法, 用于 设置远端接口列表, 不会清空原有接口对象, 由 isOverwrite 参数决定是否覆盖同名接口配置 - setSongCollectionInterface 方法, 用于 设置播放器工具栏 歌曲收藏 工具远端接口配置 - 实现 播放器拓展模块基础模板组件 开发, 其需要基于自定义拓展模块才能够正常的被播放器所识别控制 - 1、拓展组件模板的 isShow 参数依据 props 所提供的 toolKey 与 stateKey 决定其默认值,当提供toolKey 与 stateKey 时,isShow 参数将由所注册的用户拓展模块的 isShow 参数 && 当前拓展组件所绑定的工具项的 stateKey 是否与拓展组件所绑定的 stateKey 一致;当只提供toolKey时,isShow 参数将仅由所注册的用户拓展模块对应 key 值对象的 isShow 参数决定 - 2、拓展组件模板提供自定义的 mouseDown 组件外部点击事件(`mouseDownOutComponent`)与 mouseDown 组件内部点击事件(`mouseDownInComponent`),可以通过注册对应的事件监听处理器来控制调控 全体拓展组件共存性检查、特定拓展组件展示状态变更、特定拓展组件对应的工具项状态变更 或者 一些自定义的额外处理 - 3、拓展组件模板提供针对 `` 内容(即用户自定义拓展组件内容)进行监听并在内容发生突变时通过一特定 emit 事件将突变暴露至外部, 该 emit 事件名为 `mutation`; 同时拓展组件模板提供了关于突变监听的自定义配置参数 observeConfig, 突变相关内容及配置可详见 [MDN > MutationObserver](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver) - BUG 修复 - 修复 播放器 在进行最小宽度检测时, 检测虚拟 DOM 节点为 null 时异常抛出错误的 BUG - 原理:Vue 框架内部针对虚拟 DOM 的 $el 重绘会导致其 ref 响应式数据暂时性置为 null - 修复项目无法正常打包的 BUG - 原理:错误的配置了 vite 的 rollupOption 参数, 导致无法正常获取到项目打包入口 - 修复 歌词展示组件 已播放的带有歌词的歌曲向未带有歌词歌曲切换时无法正常使用的 BUG - 原理:歌曲切换时未检查已播放歌曲是否存在对应的歌词对象, 导致错误的运行了歌词动态监听相关功能逻辑, 并且所抛出的异常未被捕获导致无法正常使用 - 优化 - 优化 播放器工具项 初始化逻辑, 使其无需依赖于其对应的实体组件渲染生命周期 - 优化原有播放器所内置的 音量调节、歌单/歌曲列表、歌词展示拓展组件的相关基础设计 - v0.6.0(开发中, 敬请期待 ( •̀ ω •́ )✧) - ... # 待办事务 通用性音频播放器一期开发需求(v0.1.0 ~ v1.0.0): - v0.6.0 播放器设置工具拓展模块【正常】 - v0.6.0 播放器更多工具拓展模块【正常】 - v0.6.0 制作控制音频播放速度的组件(0.1 ~ 2), 相关参数:`audio.playbackRate`【无关紧要】 - v0.7.0 针对已解析音频的缓存机制【正常】 - v0.7.0 将基础组件独立拆分为通用组件库, 作为外部依赖项【正常】 - v0.7.0 各基础组件 props 参数校验化【次要】 - v0.8.0 国际化【正常】 - 歌词国际化模式设置【正常】 - 默认模式下多语言歌词展示(现已实现, 仅需对接) - 智能选取模式下自动适配客户端语言进行歌词展示 - 组件文本内容国际化【次要】 - v0.8.0 完善各组件相关细节【次要】 - v0.8.0 对接 changeState-showToast 事件, 当工具栏列表变化时展示变化文本提示框 - v0.8.0 对接 AudioThumbnail 组件的 isDetailed 事件, 实现用户可自定义的 hook 钩子 - v0.9.0 优化需求项:当工具项不被启用(即不被包含在 enableToolList 中)时, 若其关联拓展模块, 则不再渲染该拓展模块【次要】 通用性音频播放器二期开发需求(v1.1.0 ~ v2.0.0): - v1.1.0 制作歌词展示组件(悬浮状态) - v1.2.0 自定义 / 自适应的播放器主题色设计 - v1.3.0 对接音频解析及操作库(外部依赖项) - v1.4.0 对接 自定义字幕文件(JSON)与 SRT, ASS 等字幕文件格式转换器(外部依赖项) - v1.5.0 音频可视化拓展组件实现 # 项目指令 - `preview`: `vite preview` 读取 **项目打包文件** 并开启 **生产环境** 服务 - `dev`: `vite` 读取 **项目文件** 并开启 **开发环境** 服务 - `build`: `vite build` 读取 **项目文件** 并打包出项目 **静态资源文件包** # `Git` 提交注释类型规范(`V1.1`) ## 1、提交类型 | 类型 | 说明 | 模板规范 | | :---------: | :----------------: | :----------------------------------------------------------: | | `feature` | 新增内容 | `feature: [需求], [涉及模块], [特殊说明(可选)]` | | `fix` | `BUG` 修复 | `fix: [缺陷类型], [错误说明], [涉及模块], [发现阶段(可选,现网缺陷必须注明)], [优先度(可选, 缺陷工单则必须说明)], [解决方案(可选)], [特殊说明(可选)]` | | `back` | 回退内容 | `back: [回退涉及范围], [回退原因说明]` | | `merge` | 合并更改 | `merge: [被合并分支及最后提交记录哈希号 -> 合并分支及最后提交哈希号], [合并请求链接(远端分支合并必须说明)], [特殊说明(可选)], [冲突文件列表(可选,本地合并则必须说明)]` | | `review` | 代码审查优化 | `review: [涉及范围], [review 原因说明]` | | `comment` | 注释或文档 | `comment: [文档类型], [涉及范围(可选)], [特殊说明(可选)]` | | `other` | 杂项提交 | `other: 提交内容说明` | | `minor` | 多项不重要内容提交 | `minor: 提交内容说明` | | `replenish` | 补充 | `replenish: 指定补充分支哈希号(可选)` | ## 2、推荐示例 ### 2.1、`feature` 当进行 **需求新增开发** 时,对应提交类型使用 `feature`,提交内容需注明为何种需求、涉及到的模块、以及相关特殊说明。 **`feature` 推荐提交规范模板:** `feature: [需求], [涉及模块], [特殊说明(可选)]` ```shell # 例如,本次提交为客户端高级美颜国际化开发,提交说明为: # feature: 客户端高级美颜国际化开发, 涉及高级美颜模块, ``` ### 2.2、`fix` 当进行 **`BUG`修复** 时,对应提交类型使用 `fix`,提交内容需注明 `BUG` 类型、发现阶段、紧急程度、涉及到的模块,以及相关特殊说明。 **`fix` 推荐提交规范模板:** `fix: [缺陷类型], [错误说明], [涉及模块], [发现阶段(可选,现网缺陷必须注明)], [优先度(可选, 缺陷工单则必须说明)], [解决方案(可选)], [特殊说明(可选)]` - **缺陷类型** - 样式缺陷 - 逻辑缺陷 - 文本缺陷 - 其他缺陷 - **发现阶段** - 自测 - 测评 - 提测 - 内灰 - 外灰 - 现网 - **优先度** - 无关紧要 - 低 - 中 - 高 - 紧急 ```shell # 例如,本次提交为修复高级美颜国际化开发带来的样式错误 BUG,提交说明为: # fix: 样式缺陷, 修复高级美颜国际化开发带来的样式错误 BUG, 涉及高级美颜模块, 阶段:自测, 优先度:中 ``` ### 2.3、`back` 当进行 **代码回滚(提交级别)** 时,对应提交类型使用 `back`,提交内容需注明回退代码涉及的影响范围、以及相关回退说明。 **`back` 推荐提交规范模板:** `back: [回退涉及范围], [回退原因说明]` ```shell # 例如,本次提交为回退客户端高级美颜的国际化,提交说明为: # back: 回退涉及范围:客户端高级美颜模块, 回退原因: 国际化文本出错 ``` ### 2.4、`merge` 当进行 **`git` 冲突合并或分支合并修改** 时,对应的提交类型使用 `merge`,提交内容需注明涉及的合并分支以及对应的 `GitLab` 合并请求链接。 **`merge` 推荐提交规范模板:** `merge: [被合并分支及最后提交记录哈希号 -> 合并分支及最后提交哈希号], [合并请求链接(远端分支合并必须说明)], [特殊说明(可选)], [冲突文件列表(可选,本地合并则必须说明)]` ```shell # 例如,本次合并修改为 dev/1.8.3 m18u3709 到 master d8u32901, 对应的请求链接为 https://xxx.com,提交说明为: # merge: dev/1.8.3 m18u3709 -> master d8u32901, 对应请求链接为: https://xxx.com, 冲突文件列表为: # - plugin/qtService.js ``` ### 2.5、`review` 当进行 **代码重构 或 涉及代码优化** 时,对应提交类型使用 `review`,提交内容需注明涉及范围,`review` 原因。 **`review` 推荐提交规范模板:** `review: [涉及范围], [review 原因说明]` ```shell # 例如,本次提交为针对高级美颜性能做的重构优化,提交说明为: # review: 高级美颜, 代码重构与性能优化 ``` ### 2.6、`comment` 当进行 **注释或文档类型操作** 时,对应的提交类型使用 `comment`,提交内容需注明文档类型,涉及范围。 **`comment` 推荐提交规范模板:** `comment: [文档类型], [涉及范围(可选)], [特殊说明(可选)]` - **文档类型** - 注释开发文档,特指 `可用于自动化开发文档生成的相关注释文档` - 说明文档,特指 `类似于 README 这类说明性文档` - 代码注释,特指 `嵌入至代码内的说明注释` ```shell # 例如,本次提交为修改 TIM 通信模块相关代码注释,提交说明为: # comment: 代码注释开发文档,TIM 通信模块相关逻辑代码 ``` ### 2.7、`other` 当 **提交内容分类无法明确的被现有其他提交类型字段囊括** 时,对应提交类型应使用 `other`,此时提交者需要利用尽可能清晰的针对提交内容的 **业务内容及作用范围** 进行说明。 **需要注意的是:`other` 并非为多项混合内容的统一性提交类型字段,对于多项混合内容的提交,应该根据其内容对功能的影响程度选择使用 `minor` 提交类型字段或将其拆分为单一提交类型字段的多次提交。** **`other 推荐提交规范模板`**:`other: 提交内容说明` ```shell # 例如,本次提交为针对项目新手引导引用的静态图片资源的替换,提交说明为: # other: 修改小鹅通助手直播新手引导所使用的静态文件 ``` ### 2.8、`minor` 当 **提交内容为多项且不重要的修改** 时,对应提交类型应使用 `minor`,此时提交者需要利用尽可能清晰的针对提交内容的 **业务内容及作用范围** 进行说明。 **需要注意的是:`minor` 字段所描述的内容仅指提交内容对原有内容逻辑无影响或者完全等价的情况,例如简化(而不是优化)判断条件、代码的空格换行、小幅度调整图标偏移量等情况。** **`minor` 推荐提交规范**:`minor: 提交内容说明` ```shell # 例如,本次提交为简单修改一个代码书写规范不当且存在很多硬编码的非重要性且多项情况,提交说明为: # minor: 整理了 xxx 文件的代码格式及排版,并且修改代码中多次出现的硬编码问题及样式小幅度偏移问题 ``` ### 2.9、`replenish` 当 **提交内容有部分文件遗漏** 时,可以使用 `replenish` 字段说明本次提交为上次提交或指定提交的补充提交。 **需要注意的是:该字段仅为提交时不小心遗漏部分提交内容时使用。** `replenish` 推荐提交规范:`replenish: 指定补充分支哈希号(可选)` ```shell # 例如,之前提交时不小心漏了一个文件,这个文件与之前提交文件提交类型完全一致,提交说明为: # replenish: (留空) ```