Ubuntu 下播放语音提示
目录
一、安装语音库
二、生成音频文件
三、语音播放代码
一、安装语音库
sudo apt update
apt-get install libasound2-dev
二、生成音频文件
# 文字生成 MP3网地:https://www.text-to-speech.cn/# MP3 转 WAV网址:https://www.aconvert.com/cn/audio/mp3-to-wav/
三、语音播放代码
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <alsa/asoundlib.h>#pragma pack(1)
struct tagWavHeader
{char riff[4]; // RIFF标志int chunk_size; // 文件大小char type[4]; // 格式类型(wave)char fmt[4]; // "fmt"int subchunk_size; // sizeof(wave format matex)short audio_format; // 音频格式short channel_nums; // 声道数int sample_rate; // 采样率int byte_rate; // 比特率short block_align; // 块对齐short bits_per_sample; // 每个采样点的位数char data[4]; // ”data“int data_size; // 音频数据的大小
};
#pragma pack()void play_volume_set(long volume) {snd_mixer_t* handle;snd_mixer_open(&handle, 0);snd_mixer_attach(handle, "default");snd_mixer_selem_register(handle, NULL, NULL);snd_mixer_load(handle);snd_mixer_selem_id_t* sid;snd_mixer_selem_id_alloca(&sid);snd_mixer_selem_id_set_index(sid, 0);snd_mixer_selem_id_set_name(sid, "Master");long min = 0, max = 0;snd_mixer_elem_t* elem = snd_mixer_find_selem(handle, sid);snd_mixer_selem_get_playback_volume_range(elem, &min, &max);snd_mixer_selem_set_playback_volume_all(elem, volume * max / 100);snd_mixer_close(handle);
}int play_wav_file(const char* wav_file_path) {if (access(wav_file_path, F_OK) != 0) {printf("audio file (%s) not exist.", wav_path);return -1001;}FILE* fp = fopen(wav_file_path, "r+b");if (fp == NULL) {perror("\n fopen() failed: ");return -1002;}struct tagWavHeader wav_header;memset(&wav_header, 0, sizeof(wav_header));int rc = fread(&wav_header, 1, sizeof(wav_header), fp);printf("\n wav_header_size = %d", rc);if (rc == 0) {fclose(fp);return -1003;}snd_pcm_t* dev_handle;print_audio_info(wav_header);rc = snd_pcm_open(&dev_handle, "default", SND_PCM_STREAM_PLAYBACK, 0);if (rc < 0) {perror("\n snd_pcm_open() failed: ");fclose(fp);return -1004;}// 初始化结构体snd_pcm_hw_params_t* dev_params;snd_pcm_hw_params_alloca(&dev_params);rc = snd_pcm_hw_params_any(dev_handle, dev_params);if (rc < 0) {perror("\n snd_pcm_hw_params_any() failed: ");snd_pcm_close(dev_handle);fclose(fp);return -1005;}// 初始化参数权限rc = snd_pcm_hw_params_set_access(dev_handle, dev_params, SND_PCM_ACCESS_RW_INTERLEAVED);if (rc < 0) {perror("\n snd_pcm_hw_params_set_access() failed: ");snd_pcm_close(dev_handle);fclose(fp);return -1006;}// 设置采样的位数int bit = wav_header.bits_per_sample;switch (bit / 8) {case 1:snd_pcm_hw_params_set_format(dev_handle, dev_params, SND_PCM_FORMAT_U8);break;case 2:snd_pcm_hw_params_set_format(dev_handle, dev_params, SND_PCM_FORMAT_S16_LE);break;case 3:snd_pcm_hw_params_set_format(dev_handle, dev_params, SND_PCM_FORMAT_S24_LE);break;}// 设置声道播放(1表示单声>道,2表示立体声)int channel = wav_header.channel_nums;rc = snd_pcm_hw_params_set_channels(dev_handle, dev_params, channel);if (rc < 0) {perror("\n snd_pcm_hw_params_set_channels() failed: ");snd_pcm_close(dev_handle);fclose(fp);return -1007;}// 设置语音的播放频率int frequency = wav_header.sample_rate;int dir = 0; unsigned int freq = frequency;rc = snd_pcm_hw_params_set_rate_near(dev_handle, dev_params, &freq, &dir);if (rc < 0) {perror("\n snd_pcm_hw_params_set_rate_near() failied: ");snd_pcm_close(dev_handle);fclose(fp);return -1008;}// 更新播放参数到设备rc = snd_pcm_hw_params(dev_handle, dev_params);if (rc < 0) {perror("\n snd_pcm_hw_params() failed: ");snd_pcm_close(dev_handle);fclose(fp);return -1009;}// 获取播放周期长度snd_pcm_uframes_t frames = 0;rc = snd_pcm_hw_params_get_period_size(dev_params, &frames, &dir);if (rc < 0) {perror("\n snd_pcm_hw_params_get_period_size() failed: ");snd_pcm_close(dev_handle);fclose(fp);return -1010;}// 定位到音频的数据区fseek(fp, 58, SEEK_SET);snd_pcm_sframes_t frame_num = 0;int size = frames * wav_header.block_align;char* buffer = (char*)malloc(size);while (true) {memset(buffer, 0, size);int rv = fread(buffer, 1, size, fp);if (rv == 0) {printf("\n end of wav audio file");break;}// 下面开始写音频数据到 PCM 设备上进行播放while ((frame_num = snd_pcm_writei(dev_handle, buffer, frames)) < 0) {usleep(2000);if (frame_num == -EPIPE) {// EPIPE means underrunfprintf(stderr, "underrun occurred \n");// 完成参数设置,准备好设备snd_pcm_prepare(dev_handle);} else if (frame_num < 0) {fprintf(stderr, "snd_pcm_writei() failed: %s\n", snd_strerror(frame_num));}}}snd_pcm_drain(dev_handle);snd_pcm_close(dev_handle);free(buffer);fclose(fp);return 0;
}
相关文章:
Ubuntu 下播放语音提示
目录 一、安装语音库 二、生成音频文件 三、语音播放代码 一、安装语音库 sudo apt update apt-get install libasound2-dev二、生成音频文件 # 文字生成 MP3网地:https://www.text-to-speech.cn/# MP3 转 WAV网址:https://www.aconvert.com/cn/aud…...
ubuntu 用户管理
ubuntu 用户管理 用户组管理用户管理VNC 远程桌面参考 用户组管理 # 查看所有组信息 cat /etc/group # 查看当前用户所在组 groups # 添加用户组 sudo groupadd uav# 添加ostest用户到 uav 用户组 需要注销并重新登录 sudo gpasswd -a ostest uav sudo usermod -aG uav ostes…...
轻舟已过万重山,鸿蒙4.0程序员危机
现在是2023年末。自从华为推出的鸿蒙系统到现在已经有4年多。之前的鸿蒙系统只是基于Android套壳,因为这也也被无数人瞧不起,自从华为秋季发布会后,宣布鸿蒙4.0问世。不再兼容Android,华为做独立的系统终于打了翻身仗。 鸿蒙系统…...
【Pytorch】学习记录分享6——PyTorch经典网络 ResNet与手写体识别
【Pytorch】学习记录分享5——PyTorch经典网络 ResNet 1. ResNet (残差网络)基础知识2. 感受野3. 手写体数字识别3. 0 数据集(训练与测试集)3. 1 数据加载3. 2 函数实现:3. 3 训练及其测试: 1. ResNet &…...
Flink1.17实战教程(第三篇:时间和窗口)
系列文章目录 Flink1.17实战教程(第一篇:概念、部署、架构) Flink1.17实战教程(第二篇:DataStream API) Flink1.17实战教程(第三篇:时间和窗口) Flink1.17实战教程&…...
CSS 纵向扩展动画
上干货 <template><!-- mouseenter"startAnimation" 表示在鼠标进入元素时触发 startAnimation 方法。mouseleave"stopAnimation" 表示在鼠标离开元素时触发 stopAnimation 方法。 --><!-- 容器元素 --><div class"container&q…...
Android 12 Token 机制
一、前言 在 android framework 框架中 activity 和 window 是相互关联的,而他们的管理者 AMS 和 WMS 是怎么来实现这种关联关系的,答案就是通过 token。 首先大家需要了解一下 LayoutParams,当然属性很多,简单了解即可…...
TCP与UDP是流式传输协议吗?
TCP(传输控制协议)和UDP(用户数据报协议)是两种主要的传输层协议,它们用于在网络中传输数据。它们不是流式传输协议,而是提供了不同的数据传输特性: 1. TCP(传输控制协议࿰…...
61 贪心算法解救生艇问题
问题描述:第i个人的体重为peaple[i],每个船可以承载的最大重量为limit。每艘船最多可以同时载两人,但条件是这些人的重量之和最多为limit,返回载到每一个人多虚的最小船数,(保证每个人被船载)。 贪心算法求解:先将数组…...
C#高级 01.Net多线程
一.基本概念 1.什么是线程? 线程是操作系统中能独立运行的最小单位,也是程序中能并发执行的一段指令序列线程是进程的一部分,一个进程可以包含多个线程,这些线程共享进程资源进程有线程入口,也可以创建更多的线程 2.…...
Java---泛型讲解
文章目录 1. 泛型类2. 泛型方法3. 泛型接口4. 类型通配符5. 可变参数6. 可变参数的使用 1. 泛型类 1. 格式:修饰符 class 类名 <类型>{ }。例如:public class Generic <T>{ }。 2. 代码块举例: public class Generic <T>{…...
【论文阅读笔记】SegVol: Universal and Interactive Volumetric Medical Image Segmentation
Du Y, Bai F, Huang T, et al. SegVol: Universal and Interactive Volumetric Medical Image Segmentation[J]. arXiv preprint arXiv:2311.13385, 2023.[代码开源] 【论文概述】 本文思路借鉴于自然图像分割领域的SAM,介绍了一种名为SegVol的先进医学图像分割模型…...
Unix/Linux操作系统介绍
1、Unix/Linux操作系统介绍 1.1、操作系统的作用 1)操作系统的目标 方便:使计算机系统易于使用有效:以更有效的方式使用计算机系统资源扩展:方便用户有效开发、测试、引进新功能 2)操作系统的地位 操作系统在计算…...
什么是https证书?
HTTPS证书,也称为SSL(Secure Sockets Layer)证书或TLS(Transport Layer Security)证书,是一种数字证书,用于在网络上建立安全的加密连接。它的主要目的是确保在互联网上进行的数据传输的安全性和…...
C++ DAY2作业
1.课堂struct练习,用class; #include <iostream>using namespace std;class Stu { private:int age;char sex;int high; public:double score;void set_values(int a,char b,int c,double d);int get_age();char get_sex();int get_high(); }; vo…...
RabbitMQ核心概念记录
本文来记录下RabbitMQ核心概念 文章目录 什么叫消息队列为何用消息队列RabbitMQ简介RabbitMQ基本概念RabbitMQ 特点具体特点包括 Rabbitmq的工作过程RabbitMQ集群RabbitMQ 的集群节点包括Rabbit 模式大概分为以下三种单一模式普通模式镜像模式 本文小结 什么叫消息队列 消息&am…...
算法时间空间复杂度计算—空间复杂度
算法时间空间复杂度计算—空间复杂度 空间复杂度定义影响空间复杂度的因素算法在运行过程中临时占用的存储空间讲解 计算方法例子1、空间算法的常数阶2、空间算法的线性阶(递归算法)3、二分查找分析方法一(迭代法)方法二ÿ…...
计算机专业校招常见面试题目总结
博主面试岗位包括:java开发、软件测试、测试开发等岗位,基于之前经历的面试总结出的一些常见题目。仅供参考,互相学习!! 八股:java开发、测试、测开岗位 Java技术栈:Java基础、JVM、数据结构、…...
网络编程『简易TCP网络程序』
🔭个人主页: 北 海 🛜所属专栏: Linux学习之旅、神奇的网络世界 💻操作环境: CentOS 7.6 阿里云远程服务器 文章目录 🌤️前言🌦️正文TCP网络程序1.字符串回响1.1.核心功能1.2.程序…...
java itext5 生成PDF并填充数据导出
java itext5 生成PDF并填充数据导出 依赖**文本勾选框****页眉**,**页脚****图片**实际图 主要功能有文本勾选框,页眉,页脚,图片等功能。肯定没有专业软件画的好看,只是一点儿方法。仅供参考。 依赖 <!--pdf-->&…...
【大模型RAG】拍照搜题技术架构速览:三层管道、两级检索、兜底大模型
摘要 拍照搜题系统采用“三层管道(多模态 OCR → 语义检索 → 答案渲染)、两级检索(倒排 BM25 向量 HNSW)并以大语言模型兜底”的整体框架: 多模态 OCR 层 将题目图片经过超分、去噪、倾斜校正后,分别用…...
【Linux】shell脚本忽略错误继续执行
在 shell 脚本中,可以使用 set -e 命令来设置脚本在遇到错误时退出执行。如果你希望脚本忽略错误并继续执行,可以在脚本开头添加 set e 命令来取消该设置。 举例1 #!/bin/bash# 取消 set -e 的设置 set e# 执行命令,并忽略错误 rm somefile…...
label-studio的使用教程(导入本地路径)
文章目录 1. 准备环境2. 脚本启动2.1 Windows2.2 Linux 3. 安装label-studio机器学习后端3.1 pip安装(推荐)3.2 GitHub仓库安装 4. 后端配置4.1 yolo环境4.2 引入后端模型4.3 修改脚本4.4 启动后端 5. 标注工程5.1 创建工程5.2 配置图片路径5.3 配置工程类型标签5.4 配置模型5.…...
线程同步:确保多线程程序的安全与高效!
全文目录: 开篇语前序前言第一部分:线程同步的概念与问题1.1 线程同步的概念1.2 线程同步的问题1.3 线程同步的解决方案 第二部分:synchronized关键字的使用2.1 使用 synchronized修饰方法2.2 使用 synchronized修饰代码块 第三部分ÿ…...
关于iview组件中使用 table , 绑定序号分页后序号从1开始的解决方案
问题描述:iview使用table 中type: "index",分页之后 ,索引还是从1开始,试过绑定后台返回数据的id, 这种方法可行,就是后台返回数据的每个页面id都不完全是按照从1开始的升序,因此百度了下,找到了…...
将对透视变换后的图像使用Otsu进行阈值化,来分离黑色和白色像素。这句话中的Otsu是什么意思?
Otsu 是一种自动阈值化方法,用于将图像分割为前景和背景。它通过最小化图像的类内方差或等价地最大化类间方差来选择最佳阈值。这种方法特别适用于图像的二值化处理,能够自动确定一个阈值,将图像中的像素分为黑色和白色两类。 Otsu 方法的原…...
DBAPI如何优雅的获取单条数据
API如何优雅的获取单条数据 案例一 对于查询类API,查询的是单条数据,比如根据主键ID查询用户信息,sql如下: select id, name, age from user where id #{id}API默认返回的数据格式是多条的,如下: {&qu…...
【C++从零实现Json-Rpc框架】第六弹 —— 服务端模块划分
一、项目背景回顾 前五弹完成了Json-Rpc协议解析、请求处理、客户端调用等基础模块搭建。 本弹重点聚焦于服务端的模块划分与架构设计,提升代码结构的可维护性与扩展性。 二、服务端模块设计目标 高内聚低耦合:各模块职责清晰,便于独立开发…...
vue3+vite项目中使用.env文件环境变量方法
vue3vite项目中使用.env文件环境变量方法 .env文件作用命名规则常用的配置项示例使用方法注意事项在vite.config.js文件中读取环境变量方法 .env文件作用 .env 文件用于定义环境变量,这些变量可以在项目中通过 import.meta.env 进行访问。Vite 会自动加载这些环境变…...
OPenCV CUDA模块图像处理-----对图像执行 均值漂移滤波(Mean Shift Filtering)函数meanShiftFiltering()
操作系统:ubuntu22.04 OpenCV版本:OpenCV4.9 IDE:Visual Studio Code 编程语言:C11 算法描述 在 GPU 上对图像执行 均值漂移滤波(Mean Shift Filtering),用于图像分割或平滑处理。 该函数将输入图像中的…...
