From 1d99634957f85b1fc482bcee1f57f6e74ec405d1 Mon Sep 17 00:00:00 2001 From: HenryDu8133 <813367384@qq.com> Date: Sun, 16 Aug 2026 11:58:31 +0800 Subject: [PATCH] =?UTF-8?q?fix(audio):=20=E4=BF=AE=E5=A4=8D=E5=AF=BC?= =?UTF-8?q?=E8=87=B4=E5=AE=8C=E5=85=A8=E6=B2=A1=E6=9C=89=E5=A3=B0=E9=9F=B3?= =?UTF-8?q?=E7=9A=84=E5=9B=9E=E5=BD=92=E9=94=99=E8=AF=AF=EF=BC=8C=E6=B7=BB?= =?UTF-8?q?=E5=8A=A0=E8=B6=85=E6=97=B6=E9=98=B2=E6=AD=A2=E6=8C=82=E8=B5=B7?= =?UTF-8?q?=EF=BC=8C=E4=BF=AE=E5=A4=8D=E7=AD=89=E5=BE=85=E7=BC=93=E5=86=B2?= =?UTF-8?q?=E5=8C=BA=E6=B8=85=E7=A9=BA=E7=9A=84=E9=80=BB=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- station_broadcast-warning.lua | 5 +++++ station_broadcast.lua | 25 +++++++++++++++++++++---- 2 files changed, 26 insertions(+), 4 deletions(-) diff --git a/station_broadcast-warning.lua b/station_broadcast-warning.lua index de4f881..8944108 100644 --- a/station_broadcast-warning.lua +++ b/station_broadcast-warning.lua @@ -61,6 +61,7 @@ local function playDfpwmFile(path, volume) for _, sp in ipairs(speakers) do pending[peripheral.getName(sp)] = sp end + local maxAttempts = 20 while next(pending) do for name, sp in pairs(pending) do if sp.playAudio(samples, volume) then @@ -68,6 +69,10 @@ local function playDfpwmFile(path, volume) end end if next(pending) then + maxAttempts = maxAttempts - 1 + if maxAttempts <= 0 then + break + end local timerId = os.startTimer(0.05) while true do local ev = { os.pullEvent() } diff --git a/station_broadcast.lua b/station_broadcast.lua index 968ba68..372e1c6 100644 --- a/station_broadcast.lua +++ b/station_broadcast.lua @@ -1,6 +1,6 @@ -- 1. Configuration & Constants -local APP_VERSION_TEXT = "v1.0.66" +local APP_VERSION_TEXT = "v1.0.67" local CONFIG = { CLOUD_URL = "ws://stabadmin.fse-media.group", @@ -1216,12 +1216,17 @@ local function waitForNativeSpeakersEmpty(speakers, playSeq) if name then waiting[name] = true end end + local timerId = os.startTimer(2.0) -- Maximum 2 seconds wait for empty while next(waiting) do if shouldStop(playSeq) then return false end local ev = { os.pullEvent() } if ev[1] == "audio_interrupt" and tonumber(ev[2]) and tonumber(ev[2]) >= playSeq then return false end + if ev[1] == "timer" and ev[2] == timerId then + Utils.log("WARN", "Timeout waiting for native speakers to empty") + break + end if ev[1] == "speaker_audio_empty" and ev[2] and waiting[ev[2]] then waiting[ev[2]] = nil end @@ -1284,6 +1289,7 @@ local function playChunkOnSpeakers(samples, volume, playSeq, waitForDrain) end local usedNativePath = false + local maxAttempts = 20 while next(pending) do if shouldStop(playSeq) then return false end for name, sp in pairs(pending) do @@ -1299,6 +1305,11 @@ local function playChunkOnSpeakers(samples, volume, playSeq, waitForDrain) end end if next(pending) then + maxAttempts = maxAttempts - 1 + if maxAttempts <= 0 then + Utils.log("WARN", "Speaker buffer full or failed, skipping chunk") + break + end local timerId = os.startTimer(0.05) while true do local ev = { os.pullEvent() } @@ -1319,6 +1330,7 @@ local function playChunkOnSpeakers(samples, volume, playSeq, waitForDrain) local controller = Peripherals.speakers[1] if controller and type(controller.playAudioAll) == "function" then Utils.log("WARN", "Falling back to controller.playAudioAll for decoded samples") + local maxAttempts = 20 while true do if shouldStop(playSeq) then return false end local ok = false @@ -1326,6 +1338,11 @@ local function playChunkOnSpeakers(samples, volume, playSeq, waitForDrain) ok = controller.playAudioAll(samples, volume) end) if ok then break end + maxAttempts = maxAttempts - 1 + if maxAttempts <= 0 then + Utils.log("WARN", "Controller buffer full or failed, skipping chunk") + break + end local timerId = os.startTimer(0.05) while true do local ev = { os.pullEvent() } @@ -1765,7 +1782,7 @@ function Audio.playDfpwmItem(item) if chunk == nil then break end if type(chunk) == "string" and #chunk > 0 then local samples = decoder(chunk) - if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq) then + if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq, false) then break end end @@ -1826,7 +1843,7 @@ function Audio.playPcmItem(item) if chunk == nil then break end if type(chunk) == "string" and #chunk > 0 then local samples = decodePcmS8Chunk(chunk) - if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq) then + if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq, false) then Audio.stop("current") break end @@ -1888,7 +1905,7 @@ function Audio.playPcmS16LEItem(item) if chunk == nil then break end if type(chunk) == "string" and #chunk > 0 then local samples = decodePcmS16LEChunk(chunk) - if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq) then + if samples and not playChunkOnSpeakers(samples, CONFIG.AUDIO_VOLUME, playSeq, false) then Audio.stop("current") break end