Просмотр исходного кода

add: 增加录音到文件,流式录音的扩展功能,以及相应的demo

梁健 6 месяцев назад
Родитель
Сommit
05fe4f5bd7

+ 46 - 15
module/Air8000/demo/audio/exaudio.lua

@@ -17,13 +17,16 @@ local i2s_channel_bits = 16     -- 声道的BCLK数量
 local multimedia_id = 0         -- 音频通道 0
 local voice_vol = 55
 local mic_vol = 80
+local pcm_buff0 = nil
+local pcm_buff1 = nil
 local power_on_level = 1
 local MSG_PD = "playDone"   -- 播放完成所有数据
 -- ES8311 的 I2C 地址和芯片 ID 寄存器
 local ES8311_ADDR = 0x18  -- 7位地址,根据实际情况调整
 local CHIP_ID_REG = 0x00  -- 芯片 ID 寄存器地址,需查阅数据手册确认
 exaudio.PLAY_DONE = 1
-exaudio.AMR = 0
+exaudio.RECODE_DONE = 1
+exaudio.AMR_NB = 0
 exaudio.AMR_WB = 1
 exaudio.PCM_8000 = 2
 exaudio.PCM_16000 = 3 
@@ -73,18 +76,30 @@ local audio_record_param ={
     time = 5,               -- 录制时间,单位(秒)
     path = nil,             -- 如果填入的是字符串,则表示是文件路径,录音会传输到这个路径里
                             -- 如果填入的是函数,则表示是流式录音,录音的数据会传输到此函数内
+    cbFnc = nil,            -- 录音完毕回调函数 
 }
 
-local function audio_callback(id, event)
+local function audio_callback(id, event,point)
     log.info("audio_callback,event:",event,audio.MORE_DATA,audio.DONE,audio.RECORD_DATA,audio.RECORD_DONE)
     if event  == audio.MORE_DATA then
         audio_play_param.content()
-    elseif audio.DONE  then
-        if audio_play_param.cbFnc ~= nil  then
+    elseif event  ==  audio.DONE  then
+        if audio_play_param.cbFnc ~= nil and  type(audio_play_param.cbFnc) == "function" then
             audio_play_param.cbFnc(exaudio.PLAY_DONE)
         end
         sys.publish(MSG_PD)
-        log.error("audio_callback 1111")
+    elseif event  ==  audio.RECORD_DATA then
+        if audio_record_param.path ~= nil and  type(audio_record_param.path) == "function" then
+            if point == 0 then
+                audio_record_param.path(pcm_buff0,pcm_buff0:used())
+            else
+                audio_record_param.path(pcm_buff1,pcm_buff1:used())
+            end
+        end
+    elseif event  ==  audio.RECORD_DONE then
+        if audio_record_param.cbFnc ~= nil and  type(audio_record_param.cbFnc) == "function" then
+            audio_record_param.cbFnc(exaudio.RECODE_DONE)
+        end
     end
 end
 local function read_es8311_id()
@@ -291,7 +306,7 @@ end
 function exaudio.record_start(recodConfigs)
     local record_type ,amr_quailty,recod_format
     if recodConfigs.format == nil and type(recodConfigs.format) ~= "number" and recodConfigs.format > 5  then   -- 录音格式必须填写
-        log.error("必须填写录制的音频格式(format),格式内容有exaudio.AMR,exaudio.AMR_WB,exaudio.PCM_8000,exaudio.PCM_16000,exaudio.PCM_24000,exaudio.PCM_32000")
+        log.error("必须填写录制的音频格式(format),格式内容有exaudio.AMR_NB,exaudio.AMR_WB,exaudio.PCM_8000,exaudio.PCM_16000,exaudio.PCM_24000,exaudio.PCM_32000")
         audio_record_param.format = recodConfigs.format
         return false      
     end
@@ -311,24 +326,40 @@ function exaudio.record_start(recodConfigs)
         log.error("必须填入路径,或者用于流式录音的回调函数")
         return  false
     end
+
+    
     
-    if audio_record_param.format  == exaudio.AMR  then
-        recod_format = exaudio.AMR
+    if recodConfigs.format  == exaudio.AMR_NB  then
+        recod_format = audio.AMR_NB
         amr_quailty = 7
-    elseif audio_record_param.format  == exaudio.AMR_WB then
-        recod_format = exaudio.AMR_WB
+    elseif recodConfigs.format  == exaudio.AMR_WB then
+        recod_format = audio.AMR_WB
         amr_quailty = 8
-    elseif audio_record_param.format  == exaudio.PCM_8000 then
+    elseif recodConfigs.format  == exaudio.PCM_8000 then
         recod_format = 8000
-    elseif audio_record_param.format  == exaudio.PCM_16000 then
+    elseif recodConfigs.format  == exaudio.PCM_16000 then
         recod_format = 16000
-    elseif audio_record_param.format  == exaudio.PCM_24000 then
+    elseif recodConfigs.format  == exaudio.PCM_24000 then
         recod_format = 24000
-    elseif audio_record_param.format  == exaudio.PCM_32000 then
+    elseif recodConfigs.format  == exaudio.PCM_32000 then
         recod_format = 32000
     end
 
-    return audio.record(multimedia_id, recod_format, audio_record_param.time, amr_quailty, record_type, 1)
+    if recodConfigs.cbFnc ~= nil and type(recodConfigs.cbFnc) == "function" then -- 如果填了回调函数,则保存回调韩函数,播放完毕调用回调函数
+        audio_record_param.cbFnc = recodConfigs.cbFnc
+    else
+        audio_record_param.cbFnc = nil
+    end
+
+    if record_type == "string" then
+        return audio.record(multimedia_id, recod_format, audio_record_param.time, amr_quailty, record_type)
+    else
+        if pcm_buff0 == nil  and pcm_buff1 == nil then
+            pcm_buff0 = zbuff.create(16000)
+            pcm_buff1 = zbuff.create(16000)
+        end
+        return audio.record(multimedia_id, recod_format, audio_record_param.time, amr_quailty, record_type, 3,pcm_buff0,pcm_buff1)
+    end
  
 end
 

+ 11 - 2
module/Air8000/demo/audio/record_file.lua

@@ -5,6 +5,7 @@ local audio_setup_param ={
     i2c_id = 0,          -- i2c_id,可填入0,1 并使用pins 工具配置对应的管脚
     pa_ctrl = 162,         -- 音频放大器电源控制管脚
     dac_ctrl = 164,        --  音频编解码芯片电源控制管脚
+    bits_per_sample = 16  -- 录音的位深,可选8,16,24 位,但是当选择音频格式为AMR_NB,自动调节为8位,当音频格式为AMR_WB,自动调节为16位
     -- dac_delay = 3,        -- 在DAC启动前插入的冗余时间,单位100ms,控制pop 音
     -- pa_delay = 100,      -- 在DAC启动后,延迟多长时间打开PA,单位1ms,控制pop 音
     -- dac_time_delay = 600,    -- 音频播放完毕时,PA与DAC关闭的时间间隔,单位1ms,控制pop 音
@@ -12,11 +13,19 @@ local audio_setup_param ={
 }
 local recordPath = "/record.amr"
 
+local function record_end(event)
+    if event == exaudio.RECODE_DONE then
+        log.info("录音完成")
+    end
+end 
+
+
 local audio_record_param ={
-    format= exaudio.AMR,    -- 录制格式,有exaudio.AMR,exaudio.AMR_WB,exaudio.PCM_8000,exaudio.PCM_16000,exaudio.PCM_24000,exaudio.PCM_32000
+    format= exaudio.AMR_NB,    -- 录制格式,有exaudio.AMR_NB,exaudio.AMR_WB,exaudio.PCM_8000,exaudio.PCM_16000,exaudio.PCM_24000,exaudio.PCM_32000
     time = 5,               -- 录制时间,单位(秒)
     path = recordPath,             -- 如果填入的是字符串,则表示是文件路径,录音会传输到这个路径里
-                            -- 如果填入的是函数,则表示是流式录音,录音的数据会传输到此函数内
+                                      -- 如果填入的是函数,则表示是流式录音,录音的数据会传输到此函数内,返回的是zbuf地址,以及数据长度
+    cbFnc = record_end,            -- 录音完毕回调函数
 }
 
 

+ 19 - 17
module/Air8000/demo/audio/record_steam.lua

@@ -5,36 +5,38 @@ local audio_setup_param ={
     i2c_id = 0,          -- i2c_id,可填入0,1 并使用pins 工具配置对应的管脚
     pa_ctrl = 162,         -- 音频放大器电源控制管脚
     dac_ctrl = 164,        --  音频编解码芯片电源控制管脚
+    bits_per_sample = 16  -- 录音的位深,可选8,16,24 位,但是当选择音频格式为AMR_NB,自动调节为8位,当音频格式为AMR_WB,自动调节为16位
     -- dac_delay = 3,        -- 在DAC启动前插入的冗余时间,单位100ms,控制pop 音
     -- pa_delay = 100,      -- 在DAC启动后,延迟多长时间打开PA,单位1ms,控制pop 音
     -- dac_time_delay = 600,    -- 音频播放完毕时,PA与DAC关闭的时间间隔,单位1ms,控制pop 音
     -- pa_on_level = 1,           -- PA打开电平 1 高电平 0 低电平        
 }
-local function play_end(event)
-    if event == exaudio.PLAY_DONE then
-        log.info("播放完成")
-        
+
+local function  recode_data_callback(addr,data_len)
+    log.info("收到音频流,地址为:",addr,"有效数据长度为:",data_len)
+end
+local function record_end(event)
+    if event == exaudio.RECODE_DONE then
+        log.info("录音完成")
     end
 end 
-local audio_play_param ={
-    type= 0,                -- 播放类型,有0,播放文件,1.播放tts 2. 流式播放
-                            -- 如果是播放文件,支持mp3,amr,wav格式
-                            -- 如果是tts,内容格式见:https://wiki.luatos.com/chips/air780e/tts.html?highlight=tts
-                            -- 流式播放,仅支持PCM 格式音频,如果是流式播放,则Sampling_Rate, Sampling_Depth,Signed_or_Unsigned 必填写
-    content = "/luadb/1.mp3",          -- 如果播放类型为0时,则填入string 是播放单个音频文件,如果是表则是播放多段音频文件。
-    cbFnc = play_end,            -- 播放完毕回调函数
+
+local audio_record_param ={
+    format= exaudio.AMR_NB,    -- 录制格式,有exaudio.AMR_NB,exaudio.AMR_WB,exaudio.PCM_8000,exaudio.PCM_16000,exaudio.PCM_24000,exaudio.PCM_32000
+    time = 5,               -- 录制时间,单位(秒)
+    path = recode_data_callback,             -- 如果填入的是字符串,则表示是文件路径,录音会传输到这个路径里
+                            -- 如果填入的是函数,则表示是流式录音,录音的数据会传输到此函数内,返回的是zbuf地址,以及数据长度
+    cbFnc = record_end,            -- 录音完毕回调函数
 }
 
 
 
 local taskName = "task_audio"
 local function audio_task()
-    log.info("开始播放音频文件")
-    exaudio.setup(audio_setup_param)
-    exaudio.play_start(audio_play_param)
-    sys.wait(2000)
-    --exaudio.play_start({type= 0,content = "/luadb/1.mp3",priority = 1})     -- 可对之前的播放进行打断
-    
+    log.info("开始流式录制音频到文件")
+    if exaudio.setup(audio_setup_param) then
+        exaudio.record_start(audio_record_param)
+    end
 end
 
 sysplus.taskInitEx(audio_task, taskName)