AI-Sphere-Butler之如何將豆包桌面版對接到AI全能管家~新玩法(一)

環境:

AI-Sphere-Butler

VBCABLE2.1.58

Win10專業版

豆包桌面版1.47.4

ubuntu22.04

英偉達4070ti 12G

python3.10

問題描述:

AI-Sphere-Butler之如何將豆包桌面版對接到AI全能管家~新玩法(一)

在這里插入圖片描述
在這里插入圖片描述

聊天視頻:

AI真人版豆包來了,AI全能管家新玩法。

解決方案:

1.先安裝VBCABLE2.1.58工具,采集豆包音頻

“VBCABLE_Driver_Pack45win10” 指的是適用于 Windows 10 系統的 VBCABLE 驅動程序包,版本號可能是 45 。“VBCABLE” 可能是該驅動相關的產品或技術名稱,“Driver_Pack” 明確是驅動程序包,而 “win10” 表明其適用的操作系統為 Windows 10 。例如,可能是一種虛擬音頻電纜相關的驅動包,用于在 Windows 10 系統上實現特定音頻功能。

下載完軟件安裝x64版

在這里插入圖片描述
繼續安裝
在這里插入圖片描述
2.打開電腦聲音設置找到應用音量和設備首選項
在這里插入圖片描述
3.將豆包程序的輸出設備選擇CABLEInput

在這里插入圖片描述

4.自行安裝python和安裝依賴:

pip install flask flask-sockets gevent gevent-websocket

5.編寫采集豆包聲音客戶端

Collection.py文件內容:

import asyncio
import sounddevice as sd
import websockets
import numpy as np
import signal
import threading
import time
from collections import dequeINPUT_RATE = 16000
CHANNELS = 1
FRAME_SIZE = 640  
WS_URL = "ws://192.168.1.4:8020"#websockets服務地址
SILENCE_THRESHOLD = 1000stop_event = threading.Event()
signal.signal(signal.SIGINT, lambda s, f: stop_event.set())class AudioBuffer:def __init__(self, max_frames=20):self.buffer = deque(maxlen=max_frames)self.lock = threading.Lock()def put(self, frame_bytes):with self.lock:if len(self.buffer) == self.buffer.maxlen:self.buffer.popleft()print("[BUF] Buffer full, dropping oldest frame")self.buffer.append(frame_bytes)def get_all(self):with self.lock:frames = list(self.buffer)self.buffer.clear()return framesdef size(self):with self.lock:return len(self.buffer)def is_voice(data_np):energy = np.mean(data_np.astype(np.float32) ** 2)return energy > SILENCE_THRESHOLDdef audio_callback(indata, frames, time_info, status, audio_buffer):if status:print(f"[CAP] Warning: {status}")audio_np = indata[:, 0]ts = time.time()if is_voice(audio_np):frame = audio_np.tobytes()#print(f"[CAP] Voice frame captured at {ts:.3f}s, energy sufficient")else:frame = (np.zeros_like(audio_np)).tobytes()#print(f"[CAP] Silence frame at {ts:.3f}s")audio_buffer.put(frame)async def sender(ws, audio_buffer):while not stop_event.is_set():frames = audio_buffer.get_all()if not frames:await asyncio.sleep(0.005)continuefor frame in frames:try:await ws.send(frame)#print(f"[SND] Sent frame size={len(frame)} at {time.time():.3f}s, buffer size={audio_buffer.size()}")except Exception as e:print(f"[SND] Send error: {e}")stop_event.set()returnasync def capture_and_send(ws):audio_buffer = AudioBuffer(20)device_index = Nonedevices = sd.query_devices()for i, d in enumerate(devices):if "CABLE" in d['name'] and d['max_input_channels'] >= CHANNELS:device_index = ibreakif device_index is None:device_index = sd.default.device[0]print(f"[SYS] Using device #{device_index}: {devices[device_index]['name']}")send_task = asyncio.create_task(sender(ws, audio_buffer))with sd.InputStream(samplerate=INPUT_RATE,device=device_index,channels=CHANNELS,dtype='int16',blocksize=FRAME_SIZE,callback=lambda indata, frames, time_info, status:audio_callback(indata, frames, time_info, status, audio_buffer)):print("[SYS] Recording started.")while not stop_event.is_set():await asyncio.sleep(0.1)send_task.cancel()try:await send_taskexcept asyncio.CancelledError:passprint("[SYS] Recording stopped.")async def main():print(f"[SYS] Connecting to {WS_URL}")try:async with websockets.connect(WS_URL) as ws:print("[SYS] Connected.")await capture_and_send(ws)except Exception as e:print(f"[ERR] Connection error: {e}")if __name__ == '__main__':asyncio.run(main())

6.主程序引入模塊文件websocket_service.py:

AI-Sphere-Butler\core\server\virtual_human\websocket_service.py

import asyncio
import uuid
import websockets
import multiprocessing
import queueMAX_QUEUE_SIZE = 10def enqueue_audio_data(audio_queue, data):try:audio_queue.put_nowait(data)except queue.Full:try:discarded = audio_queue.get_nowait()print("[WSrv] 丟棄過舊音頻包,防止積壓")except queue.Empty:passtry:audio_queue.put_nowait(data)except queue.Full:# print("[WSrv] 隊列滿,丟棄當前音頻包")passasync def audio_handler(websocket, audio_queue: multiprocessing.Queue):session_id = str(uuid.uuid4())# print(f"[WSrv] Session {session_id} connected")try:async for raw in websocket:if isinstance(raw, (bytes, bytearray)):enqueue_audio_data(audio_queue, (session_id, raw))# print(f"[WSrv] Queued {len(raw)} bytes from {session_id}")else:# print(f"[WSrv] Ignored non-binary message from {session_id}")passexcept websockets.exceptions.ConnectionClosed:passfinally:# print(f"[WSrv] Session {session_id} disconnected")passasync def run_server(audio_queue: multiprocessing.Queue, host='0.0.0.0', port=8020):async def handler(websocket):await audio_handler(websocket, audio_queue)server = await websockets.serve(handler, host, port)# print(f"[WSrv] Listening on ws://{host}:{port}")await asyncio.Future()  if __name__ == "__main__":q = multiprocessing.Queue(maxsize=MAX_QUEUE_SIZE)asyncio.run(run_server(q))

7.運行采集客戶端和AI-Sphere-Butler服務

在這里插入圖片描述

8.這樣就可以和豆包聊天,驅動AI全能管家數字人說話了

在這里插入圖片描述

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/88161.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/88161.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/88161.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【STM32】啟動流程

1、.s啟動文件解析 STM32的啟動文件(一般是.s匯編文件,如startup_stm32f407xx.s)是STM32上電后執行的第一段代碼,承擔著“系統初始化化引導員”的角色。 它的主要作用是設置初始化棧指針(SP)、程序計數器&…

【vim】通過vim編輯器打開、修改、退出配置文件

通過vim編輯器打開任一配置文件 vim /etc/profile 英文輸入下,按i鍵進入INSERT模式,修改配置文件 完成修改后,按esc鍵退出INSERT模式 英文輸入下,輸入":wq!",即可保存并退出 :q #不保存并退出 :q! …

Effective Modern C++ 條款6:當 auto 推導類型不符合預期時,使用顯式類型初始化慣用法

在C開發中,auto關鍵字以其簡潔性和高效性被廣泛使用。然而,“自動推導”并非萬能,尤其在某些特殊場景下,auto的推導結果可能與開發者預期不符,甚至導致未定義行為。今天,我們以《Effective Modern C》條款6…

學習Linux進程凍結技術

原文:蝸窩科技Linux進程凍結技術 功耗中經常需要用到,但是linux這塊了解甚少,看到這個文章還蠻適合我閱讀的 1 什么是進程凍結 進程凍結技術(freezing of tasks)是指在系統hibernate或者suspend的時候,將…

GitHub 趨勢日報 (2025年06月22日)

📊 由 TrendForge 系統生成 | 🌐 https://trendforge.devlive.org/ 🌐 本日報中的項目描述已自動翻譯為中文 📈 今日獲星趨勢圖 今日獲星趨勢圖 624 LLMs-from-scratch 523 ai-engineering-hub 501 n8n 320 data-engineer-handb…

kotlin中為什么新增擴展函數功能?

在 Kotlin 中,擴展函數的本質是「不修改原有類代碼,為其新增功能」,這源自編程中「開閉原則」(對擴展開放,對修改關閉)的第一性原理。 核心需求:當需要給第三方庫的類(如 Android 的…

excel 數據透視表介紹

Excel 數據透視表(PivotTable)就是你的數據分析神器!它能幫你快速匯總、分類、比較和分析 大量數據,從看似雜亂無章的表格中一鍵提取關鍵信息 ,生成交互式的匯總報告。無需復雜公式,只需拖拽幾下,就能讓數據“開口說話”&#xff…

半導體行業中的專用標準產品ASSP是什么?

半導體行業中的專用標準產品ASSP是什么? “專用標準產品”(ASSP - Application Specific Standard Product)是半導體集成電路中的一個重要分類。 你可以把它理解為介于通用標準產品和全定制ASIC之間的一種芯片。以下是它的核心定義和特點&a…

秋招Day14 - MySQL - 鎖

MySQL中有幾種類型的鎖? 鎖粒度來分,有表鎖、頁鎖和行鎖。 加鎖機制劃分,有樂觀鎖和悲觀鎖。 按兼容性劃分,有共享鎖和排他鎖。 按鎖模式劃分,有記錄鎖,間隙鎖,next-key鎖,意向鎖…

/var/lib/docker/overlay2目錄過大怎么辦

/var/lib/docker/overlay2 是 Docker 默認用于存儲 容器鏡像和容器運行時數據 的核心目錄,基于 overlay2 存儲驅動實現。以下是其具體作用和內容的詳細解析: 1. overlay2 目錄的作用 存儲鏡像分層結構: Docker 鏡像采用分層設計,o…

JimuReport:一款免費的數據可視化報表工具

JimuReport(積木報表)是一款免費的企業級數據可視化報表軟件,提供拖拽的方式像搭建積木一樣完成在線設計,功能涵蓋數據報表、打印設計、圖表報表、門戶設計、大屏設計等。 數據源 JimuReport 支持 30 多種數據源,包括…

Neo4j.5.X社區版創建數據庫和切換數據庫

在使用Neo4j數據庫(版本:neo4j-community-5.22.0)時,系統自帶的“neo4j”和“system”數據庫適用于日常的簡單學習和練習,但對于新的項目,將項目數據與練習數據混用會帶來諸多不便,例如查詢效率…

DAY33神經網絡

浙大疏錦行 定義了一個簡單的神經網絡,主要是掌握pytorch框架

拼團系統多層限流架構詳解

拼團系統多層限流架構詳解 一、整體架構設計理念 多層限流采用"層層設防"思想,通過網關層全局流量控制→服務層接口粒度限流→本地資源隔離→熱點參數精準防護的四級防御體系,實現從粗到細的流量治理,確保大促期間系統穩定性。 …

[ctfshow web入門] web92 `==`特性與intval特性

信息收集 和之前的題差不多,這次是使用了不嚴格相等的,詳情看這篇博客: 和 在 PHP 中有何區別?一共包含哪些部分? 首先,不能使$num 4476,然后需要使intval($num,0)4476 include("flag…

在Springboot項目部署時遇到,centos服務器上,curl請求目標地址不通 ,curl -x 可以請求通的解決辦法

在甲方服務器部署項目時,通常遇到需要開通外網權限的問題,有的是直接給開通服務器的白名單,就可以直接訪問白名單外網地址了。也有的是通過網絡轉發,將url前面的部分替換,可以進行網絡請求。有一次遇到一個罕見的&…

Python異步爬蟲編程技巧:從入門到高級實戰指南

Python異步爬蟲編程技巧:從入門到高級實戰指南 🚀 📚 目錄 前言:為什么要學異步爬蟲異步編程基礎概念異步爬蟲核心技術棧入門實戰:第一個異步爬蟲進階技巧:并發控制與資源管理高級實戰:分布式…

JMeter-SSE響應數據自動化3.0

背景 此次因為多了一些需要過濾排除的錯誤(數量很少),還需要修改下JMeter的jtl文件輸出數據(后續統計數據需要) 所以只涉及到JSR腳本的一些改動(此部分改動并不會影響到JMeter的HTML報告) 改動 主要通過設置JMeter中prev輸出數據變量threadN…

012 進程狀態和優先級

🦄 個人主頁: 小米里的大麥-CSDN博客 🎏 所屬專欄: Linux_小米里的大麥的博客-CSDN博客 🎁 GitHub主頁: 小米里的大麥的 GitHub ?? 操作環境: Visual Studio 2022 文章目錄 進程狀態和優先級一、進程狀態分類特殊狀態說明 二、如何查看進程…

React JSX原理

JSX本質 實質上是React.createElement()的語法糖