前端调用浏览器录音功能且生成文件(vue)
如果可以实现记得点赞分享,谢谢老铁~
首先在页面中给两个按钮,分别是“开始录音”,“结束录音”。以及录音成功后生成一个下载语音的链接。
1. 先看页面展示
<template><div><button @click="startRecording" :disabled="isRecording">Start Recording</button><button @click="stopRecording" :disabled="!isRecording">Stop Recording</button><a v-if="downloadLink" :href="downloadLink" download="recording.pcm">Download Recording</a></div>
</template>
2. 看vue3.0的代码实现
<script setup>
import { ref, onBeforeUnmount } from 'vue';const isRecording = ref(false);
const downloadLink = ref('');
let audioContext = null;
let processor = null;
let socket = null;
let mediaStream = null;
let audioChunks = [];
let silenceTimeout = null;
const silenceDelay = 2000; // 停止录音的延迟时间(毫秒)
const desiredSampleRate = 16000; // 期望的采样率为16kHzconst startRecording = async () => {try {mediaStream = await navigator.mediaDevices.getUserMedia({ audio: {sampleRate: desiredSampleRate,sampleSize: 16,channelCount: 1,} });audioContext = new (window.AudioContext || window.webkitAudioContext)({sampleRate: desiredSampleRate});const source = audioContext.createMediaStreamSource(mediaStream);processor = audioContext.createScriptProcessor(4096, 1, 1);source.connect(processor);processor.connect(audioContext.destination);socket = new WebSocket('ws://yourserver.com');socket.binaryType = 'arraybuffer';// 接收 WebSocket 消息socket.onmessage = (event) => {const receivedData = event.data;console.log('Received data from server:', receivedData);// 这里可以处理接收到的数据,例如显示在 UI 上};processor.onaudioprocess = processAudio;isRecording.value = true;audioChunks = []; // 清空之前的音频数据} catch (error) {console.error('Error accessing media devices.', error);}
};const stopRecording = async () => {if (processor) {processor.disconnect();}if (mediaStream) {mediaStream.getTracks().forEach(track => track.stop());}if (audioContext && audioContext.state !== 'closed') {await audioContext.close();audioContext = null}if (socket) {socket.close();}isRecording.value = false;createDownloadLink();
};const processAudio = (event) => {const inputBuffer = event.inputBuffer;const outputBuffer = new Float32Array(inputBuffer.length);inputBuffer.copyFromChannel(outputBuffer, 0);const pcmData = convertFloat32ToPCM(outputBuffer);// 检查音量是否为静音const isSilent = outputBuffer.every(sample => Math.abs(sample) < 0.01);if (!isSilent) {clearTimeout(silenceTimeout);silenceTimeout = setTimeout(() => stopRecording(), silenceDelay);}if (socket && socket.readyState === WebSocket.OPEN) {socket.send(pcmData);}audioChunks.push(pcmData);
};const convertFloat32ToPCM = (input) => {const buffer = new ArrayBuffer(input.length * 2);const output = new DataView(buffer);for (let i = 0; i < input.length; i++) {const s = Math.max(-1, Math.min(1, input[i]));output.setInt16(i * 2, s < 0 ? s * 0x8000 : s * 0x7FFF, true);}return buffer;
};const createDownloadLink = () => {const blob = new Blob(audioChunks, { type: 'application/octet-stream' });downloadLink.value = URL.createObjectURL(blob);
};onBeforeUnmount(() => {stopRecording();
});
</script>
解释
audioChunks 数组:
存储录音过程中的 PCM 数据块。
processAudio 方法:
将 PCM 数据块添加到 audioChunks 数组中。
stopRecording 方法:
停止录音,并调用 createDownloadLink 方法生成下载链接。
createDownloadLink 方法:
将存储的音频数据块创建为一个 Blob 对象,并生成一个下载链接。
downloadLink 变量:
存储生成的下载链接,供用户下载录音文件。
注意事项
确保WebSocket服务器可以处理PCM数据。
处理音频数据时,注意性能问题,避免阻塞主线程。
Web Audio API和WebSocket在不同浏览器上的实现可能会有所不同,确保在目标浏览器上测试。
OK,收工!如果可以实现记得点赞分享,谢谢老铁~
相关文章:
前端调用浏览器录音功能且生成文件(vue)
如果可以实现记得点赞分享,谢谢老铁~ 首先在页面中给两个按钮,分别是“开始录音”,“结束录音”。以及录音成功后生成一个下载语音的链接。 1. 先看页面展示 <template><div><button click"startRecording…...
「大数据」Kappa架构
Kappa架构是一种处理大数据的架构,它作为Lambda架构的替代方案出现。Kappa架构的核心思想是简化数据处理流程,通过使用单一的流处理层来同时处理实时和批量数据,从而避免了Lambda架构中需要维护两套系统(批处理层和速度层…...

详细分析Element Plus中的ElMessageBox弹窗用法(附Demo及模版)
目录 前言1. 基本知识2. Demo3. 实战4. 模版 前言 由于需要在登录时,附上一些用户说明书的弹窗 对于ElMessageBox的基本知识详细了解 可通过官网了解基本的语法知识ElMessageBox官网基本知识 1. 基本知识 Element Plus 是一个基于 Vue 3 的组件库,其中…...

Python自动化工具(桌面自动化、Web自动化、游戏辅助)
工具介绍 连点工具是一款可以模拟键鼠后台操作的连点器工具。支持鼠标连点、键鼠脚本录制,支持辅助您实现办公自动化以及辅助游戏操作。功能简洁易用,非常方便操作。连点工具让您在在玩游戏、网购抢购的时候全自动点击鼠标!主要功能有&#…...

opencv进阶 ——(五)图像处理之马赛克
一、遍历图像并对每个马赛克区域进行像素化处理 for (int y 0; y < image.rows; y blockSize) {for (int x 0; x < image.cols; x blockSize) {cv::Rect rect cv::Rect(x, y, std::min(blockSize, image.cols - x), std::min(blockSize, image.rows - y));cv::Scal…...

电机控制系列模块解析(22)—— 零矢量刹车
一、零矢量刹车 基本概念 逆变器通常采用三相桥式结构,包含六个功率开关元件(如IGBT或MOSFET),分为上桥臂和下桥臂。每个桥臂由两个反并联的开关元件组成,上桥臂和下桥臂对应于电机三相绕组的正负端。正常工作时&…...

自定义一个SpringBoot场景启动器
前言 一个刚刚看完SpringBoot自动装配原理的萌新依据自己的理解写下的文章,如有大神发现错误,敬请斧正,不胜感激。 分析SpringBoot自动配置原理 SpringBoot的启动从被SpringBootApplication修饰的启动类开始,SpringBootApplicaiotn注解中最…...

UDP的报文结构和注意事项
UDP协议是在传输层的协议。 UDP无连接,不可靠传输,面向数据报,全双工。 UDP的报文结构 学习网络协议,最主要的就是报文格式。 对于UDP来说,应用层的数据到达,UDP之后,就会给应用层的数据报前面…...
rust语言一些规则学习
目录 rust中迭代器的使用(iter().map()与for循环的区别)map()与for的描述区别总结 最后更新时间2024-05-24 rust中迭代器的使用(iter().map()与for循环的区别) map()与for的描述 rust源码中关于iter().map()函数的解释ÿ…...
QML基本语法介绍
为什么使用QML 开发者效率 将前后端分离,QML和JavaScript语言主要用于前度UI的方法,后端有C++来完成绘制。将JavaScript和C++分开能够快速迭代开发; 跨平台移植性 基于Qt平台的统一抽象概念,现在可以更加容易和快速和将Qt移植到更多的平台上。 开发的开放 Qt是由Qt-Proje…...
学习和分享关于 Vue.js 的路由(vue-router)
学习和分享关于 Vue.js 的路由(vue-router)是一个非常有价值的主题,因为路由是构建单页应用程序(SPA)的核心部分。本文将介绍 Vue.js 路由的基本概念和实现,并展示一个典型的项目目录结构。 目录 Vue.js 路…...

小猪APP分发:一站式免费应用推广解决方案
在竞争激烈的移动应用市场中,寻找一个高效且成本友好的方式来推广自己的应用程序,成为了众多开发者面临的共同挑战。幸运的是,像"小猪APP分发www.appzhu.cn"这样的平台应运而生,为开发者提供了一个全面、免费的应用分发…...

新抖:抖音的数据分析平台,敢用深色系,别的真不敢!
举报 评论 0...

独享IP是原生IP吗?二者有何区别?
原生IP: 原生IP是指由Internet服务提供商(ISP)直接分配给用户的IP地址,这些IP地址通常反映了用户的实际地理位置和网络连接。原生IP是用户在其所在地区或国家使用的真实IP地址,与用户的物理位置直接相关。在跨境电商中…...

AI大模型探索之路-实战篇7:Function Calling技术实战:自动生成函数
系列篇章💥 AI大模型探索之路-实战篇4:深入DB-GPT数据应用开发框架调研 AI大模型探索之路-实战篇5:探索Open Interpreter开放代码解释器调研 AI大模型探索之路-实战篇6:掌握Function Calling的详细流程 目录 系列篇章Ὂ…...

Android14 - 绘制系统 - 概览
从Android 12开始,Android的绘制系统有结构性变化, 在绘制的生产消费者模式中,新增BLASTBufferQueue,客户端进程自行进行queue的生产和消费,随后通过Transation提交到SurfaceFlinger,如此可以使得各进程将缓…...

Add object from object library 从对象库中添加内置器件
Add object from object library 从对象库中添加内置器件 正文正文 对于 Lumerical,有些时候我们在使用中,可能需要从 Object library 中添加器件,通常我们的做法是手动添加。如下图所示,我们添加一个 Directional Coupler 到我们的工程文件中: 但是这种操作方式不够智能…...

天诚公租房/人才公寓WiFi人脸识别物联网智能门锁解决方案
人才是引领城市高质量发展的重要因素,城市要想吸纳人才的保障便是人才公寓。近年来,全国各地一二三线城市都在大力建设人才公寓,集聚菁英人才,倾力打造人才高地。 一、人才公寓如火如荼建设 2023年底,山东德州提出三年…...
JAVA学习-练习试用Java实现“子集”
问题: 给定一个整数数组 nums,数组中的元素互不相同。返回该数组所有可能的子集(幂集)。解集不能包含重复的子集。可以按任意顺序返回解集。 示例 1: 输入:nums [1,2,3] 输出:[[],[1],[2],[…...

揭秘《庆余年算法番外篇》:范闲如何使用维吉尼亚密码解密二皇子密信
❤️❤️❤️ 欢迎来到我的博客。希望您能在这里找到既有价值又有趣的内容,和我一起探索、学习和成长。欢迎评论区畅所欲言、享受知识的乐趣! 推荐:数据分析螺丝钉的首页 格物致知 终身学习 期待您的关注 导航: LeetCode解锁100…...
浅谈 React Hooks
React Hooks 是 React 16.8 引入的一组 API,用于在函数组件中使用 state 和其他 React 特性(例如生命周期方法、context 等)。Hooks 通过简洁的函数接口,解决了状态与 UI 的高度解耦,通过函数式编程范式实现更灵活 Rea…...

TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...

基于距离变化能量开销动态调整的WSN低功耗拓扑控制开销算法matlab仿真
目录 1.程序功能描述 2.测试软件版本以及运行结果展示 3.核心程序 4.算法仿真参数 5.算法理论概述 6.参考文献 7.完整程序 1.程序功能描述 通过动态调整节点通信的能量开销,平衡网络负载,延长WSN生命周期。具体通过建立基于距离的能量消耗模型&am…...
在HarmonyOS ArkTS ArkUI-X 5.0及以上版本中,手势开发全攻略:
在 HarmonyOS 应用开发中,手势交互是连接用户与设备的核心纽带。ArkTS 框架提供了丰富的手势处理能力,既支持点击、长按、拖拽等基础单一手势的精细控制,也能通过多种绑定策略解决父子组件的手势竞争问题。本文将结合官方开发文档,…...

Swift 协议扩展精进之路:解决 CoreData 托管实体子类的类型不匹配问题(下)
概述 在 Swift 开发语言中,各位秃头小码农们可以充分利用语法本身所带来的便利去劈荆斩棘。我们还可以恣意利用泛型、协议关联类型和协议扩展来进一步简化和优化我们复杂的代码需求。 不过,在涉及到多个子类派生于基类进行多态模拟的场景下,…...
Go 语言接口详解
Go 语言接口详解 核心概念 接口定义 在 Go 语言中,接口是一种抽象类型,它定义了一组方法的集合: // 定义接口 type Shape interface {Area() float64Perimeter() float64 } 接口实现 Go 接口的实现是隐式的: // 矩形结构体…...

高等数学(下)题型笔记(八)空间解析几何与向量代数
目录 0 前言 1 向量的点乘 1.1 基本公式 1.2 例题 2 向量的叉乘 2.1 基础知识 2.2 例题 3 空间平面方程 3.1 基础知识 3.2 例题 4 空间直线方程 4.1 基础知识 4.2 例题 5 旋转曲面及其方程 5.1 基础知识 5.2 例题 6 空间曲面的法线与切平面 6.1 基础知识 6.2…...
【Go】3、Go语言进阶与依赖管理
前言 本系列文章参考自稀土掘金上的 【字节内部课】公开课,做自我学习总结整理。 Go语言并发编程 Go语言原生支持并发编程,它的核心机制是 Goroutine 协程、Channel 通道,并基于CSP(Communicating Sequential Processes࿰…...
Java 加密常用的各种算法及其选择
在数字化时代,数据安全至关重要,Java 作为广泛应用的编程语言,提供了丰富的加密算法来保障数据的保密性、完整性和真实性。了解这些常用加密算法及其适用场景,有助于开发者在不同的业务需求中做出正确的选择。 一、对称加密算法…...

《基于Apache Flink的流处理》笔记
思维导图 1-3 章 4-7章 8-11 章 参考资料 源码: https://github.com/streaming-with-flink 博客 https://flink.apache.org/bloghttps://www.ververica.com/blog 聚会及会议 https://flink-forward.orghttps://www.meetup.com/topics/apache-flink https://n…...