--[[
@module  play_stream
@summary 流式播放
@version 1.0
@date    2025.09.08
@author  梁健
@usage

本文件为流式播放应用功能模块，核心业务逻辑为：
1、创建一个播放流式音频task（task_audio）
2、创建一个模拟获取流式音频的task（audio_get_data）
3、此task通过流式传输不断向exaudio.play_stream_write填入播放的音频
4、播放task 不断播放传入流式音频
5、使用powerkey 按键进行音量减小，点击boot 按键进行音量增加
本文件没有对外接口，直接在main.lua中require "play_stream"就可以加载运行；
]]

exaudio = require("exaudio")


-- 音频初始化设置参数,exaudio.setup 传入参数
local audio_setup_param ={
    model= "es8311",          -- dac类型,可填入"es8311","es8211"
    i2c_id = 0,          -- i2c_id,可填入0，1 并使用pins 工具配置对应的管脚
    pa_ctrl = gpio.AUDIOPA_EN,         -- 音频放大器电源控制管脚
    dac_ctrl = 20,        --  音频编解码芯片电源控制管脚,780ehv 默认使用20
}

-- 播放完成回调
local function play_end(event)
    if event == exaudio.PLAY_DONE then
        log.info("播放完成",exaudio.is_end())

    end
end 

-- 流式播放音频播放的配置
local audio_play_param ={
    type= 2,                -- 播放类型，有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 必填写
    cbfnc = play_end,            -- 播放完毕回调函数
    sampling_rate = 16000,  -- 采样率,仅为流式播放起作用
    sampling_depth =  16,   -- 采样位位深,仅流式播放的时候才有作用
    signed_or_unsigned = true  -- PCM 的数据是否有符号，仅为流式播放起作用
}

---------------------------------
---通过BOOT 按键增大音量---
---------------------------------
local volume_number = 50 
local function add_volume()
    volume_number = volume_number + 20
    log.info("增大音量",volume_number)
    exaudio.vol(volume_number)
end

gpio.setup(0, add_volume, gpio.PULLDOWN, gpio.RISING)
gpio.debounce(0, 200, 1)

---------------------------------
---通过POWERKEY按键减小音量-------
---------------------------------

local function down_volume()
    volume_number = volume_number - 15
    log.info("减小音量",volume_number)
    exaudio.vol(volume_number)
end

gpio.setup(gpio.PWR_KEY, down_volume, gpio.PULLUP, gpio.FALLING)
gpio.debounce(gpio.PWR_KEY, 200, 1)   -- 防抖，防止频繁触发


---------------------------------
---------模拟获取音频task---------
---------------------------------
local function audio_get_data()
    log.info("开始流式获取音频数据")
    local file = io.open("/luadb/test.pcm", "rb")   -- 模拟流式播放音源，实际的音频数据来源也可以来自网络或者本地存储
    while true do
        local read_data = file:read(4096)  --  读取文件，模拟流式音频源,需要1024 的倍数
        if read_data  == nil then
            file:close()                -- 模拟音频获取完毕，关闭音频文件
            break
        end
        exaudio.play_stream_write(read_data)  -- 流式写入音频数据
        sys.wait(100)                   -- 写数据需要留出事件给其他task 运行代码
    end
end

sys.taskInitEx(audio_get_data, "audio_get_data")


---------------------------------
------------通过主task------------
---------------------------------
local taskName = "task_audio"
local function audio_task()
    log.info("开始流式播报")
    if exaudio.setup(audio_setup_param) then
        exaudio.play_start(audio_play_param)
        log.info("播放状态",exaudio.is_end())
    end
end

sys.taskInitEx(audio_task, taskName)
