#encoding = utf8 import logging import time from queue import Queue, Empty from threading import Event, Thread import numpy as np from audio_render import AudioRender from base_render import BaseRender logger = logging.getLogger(__name__) class AudioRenderImpl(BaseRender): def __init__(self, start): super().__init__(start) self._queue = Queue() self._exit_event = Event() self._thread = Thread(target=self._on_run) self._exit_event.set() self._thread.start() self._audio_render = AudioRender() self._current_time = 0 self._display_time = 0 def _on_run(self): logging.info('Audio render run') while self._exit_event.is_set(): self._run_step() time.sleep(0.02) logging.info('Audio render exit') def _run_step(self): try: audio_frames, ps = self._queue.get(block=True, timeout=0.01) except Empty: return self._display_time = time.time() self._current_time = ps for audio_frame in audio_frames: frame, type_ = audio_frame frame = (frame * 32767).astype(np.int16) if self._audio_render is not None: try: self._audio_render.write(frame.tobytes(), int(frame.shape[0] * 2)) except Exception as e: logging.error(f'Error writing audio frame: {e}') def put(self, frame): ps = time.time() - self._start self._queue.put_nowait((frame, ps)) def stop(self): self._exit_event.clear() self._thread.join() def play_time(self): elapsed = time.time() - self._display_time return self._current_time + elapsed