According to a document from 2026-04-24,下面按"四博皮克斯苹果 AI 台灯 + AI 智能音箱一体化 S3 视觉机械臂版本 "来写方案:它不是单纯音箱,而是把 AI 音箱的语音交互能力 、AI 台灯的照明能力 、机械臂动作能力 、摄像头视觉能力 、大模型 / 多模态模型能力 合成一个可开源、可量产、可二次开发的平台。若客户只做纯 AI 智能音箱,可直接去掉机械臂、摄像头、灯光恒流驱动部分,保留 S3 + VB6824 + 屏幕 + 喇叭 + 联网 + MCP 即可。方案依据你上传的四博乐鑫系模组选型手册、AI 硬件选型表和《四博智联 AI 开发宝典》整理。
四博皮克斯苹果 AI 台灯 / AI 智能音箱 S3 视觉机械臂方案
1. 方案定位
本方案定位为 "AI 视觉台灯 + 智能音箱 + 机械臂执行器 + 屏幕交互终端",核心采用:
ESP32-S3R8 + 16M Flash + 8M PSRAM
VB6824 离线语音 / AEC / 唤醒前端
摄像头模组
机械臂 / 云台舵机
LED 台灯恒流驱动
单屏 / 双屏 / 异显屏幕
喇叭 + 功放
Wi-Fi / BLE / 4G / 蓝牙 PAN 可选
小智 / 豆包 / ChatGPT / Coze / 客户私有大模型
AT+MCP / WebSocket / HTTP / MQTT / UART 二次开发接口
四博资料中,ESP32-S3 系列被归类到 音视频 / AI 市场 ,ESPS3-32 / ESPS3-32E 兼容官方 S3 系列模组;ESP32-S3 也具备 LCD 支持,适合做带屏 AI 设备主控。 AI 硬件选型表中已经出现 ESP32-S3 + 7014 + 摄像头 + 4G 高端方案 ,并说明其特点是开发者生态好、可对接各家平台、可多模态、可当蓝牙音箱;同时 AI 智能相机方案采用 ESP32S3R8 + 16M Flash + VB6824,可选 4G、摄像头、屏幕、麦克风、喇叭、电池包等配件。
开发宝典中,AI-S3 标准开发板是"四博 AI-Speaker 开发板",带 240×240 分辨率 1.3 寸屏,全开源,支持"四博小助手"小程序、声音克隆、知识库、自建大模型和 MCP。 另外,DOIT_ESPS3_AI_EYE_Vision 多模态开发板基于 ESP32-S3,集摄像头、双目显示和触摸交互于一体,硬件与软件全开源,可直接用于二次开发或量产制造,这一点非常适合"皮克斯苹果 AI 台灯再升级"的视觉版本。
2. 整机系统架构
┌────────────────────────────────────────────────────────────┐
│ 四博皮克斯苹果 AI 台灯 / AI 智能音箱 S3 版 │
├────────────────────────────────────────────────────────────┤
│ │
│ ┌────────────────────┐ UART / I2C / GPIO │
│ │ VB6824 语音前端 │◄─────────────────────────────┐ │
│ │ - 离线唤醒 │ │ │
│ │ - 远场拾音 │ │ │
│ │ - AEC 回声消除 │ │ │
│ │ - 高噪降噪 │ │ │
│ │ - 唤醒词打断 │ │ │
│ │ - 自定义唤醒词 │ │ │
│ └─────────┬──────────┘ │ │
│ │ MIC / 回采音频 │ │
│ ▼ │
│ ┌──────────────────────────────────────────────────────┐ │
│ │ ESP32-S3R8 + 16M Flash + 8M PSRAM │ │
│ │ - Wi-Fi / BLE / BluFi │ │
│ │ - 4G PPP / ECM,可选 │ │
│ │ - 蓝牙 PAN / 蓝牙音箱,可选 7014 │ │
│ │ - WebSocket AI 对话 │ │
│ │ - 摄像头采集 / JPEG 编码 │ │
│ │ - 视觉大模型请求 / 场景理解 │ │
│ │ - 舵机 / 机械臂控制 │ │
│ │ - 灯光亮度 / 色温控制 │ │
│ │ - 单屏 / 双屏 / 异显 UI │ │
│ │ - MCP 工具扩展 / 客户系统接入 │ │
│ └───────┬───────────────┬───────────────┬─────────────┘ │
│ │ │ │ │
│ ┌──────▼──────┐ ┌──────▼──────┐ ┌──────▼──────┐ │
│ │ Camera │ │ Servo Arm │ │ LED Driver │ │
│ │ 视觉输入 │ │ 云台/机械臂 │ │ 冷暖光/亮度 │ │
│ └─────────────┘ └─────────────┘ └─────────────┘ │
│ │
│ ┌─────────────┐ ┌─────────────┐ ┌────────────────────┐ │
│ │ LCD Screen A │ │ LCD Screen B │ │ I2S AMP + Speaker │ │
│ │ 表情 / 主 UI │ │ 信息 / 异显 │ │ TTS / 音乐 / 提示音 │ │
│ └─────────────┘ └─────────────┘ └────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────┘
云端 / 私有化后端:
┌────────────────────────────────────────────────────────────┐
│ OTA │ WebSocket │ ASR │ LLM │ TTS │ VLM │ MCP │ 客户业务系统 │
└────────────────────────────────────────────────────────────┘
3. 产品核心功能
3.1 AI 音箱能力
1. 语音唤醒:
默认"你好小智"或客户定制唤醒词。
2. 远场拾音:
通过 VB6824 做语音前端,支持远距离拾音、降噪、唤醒识别。
3. 实时打断:
AI 播报、蓝牙音乐、提示音播放过程中,用户可唤醒打断。
4. 大模型对话:
接入小智、豆包、ChatGPT、Coze 或客户自有 LLM。
5. TTS 播放:
支持标准 TTS、声音克隆、角色音色。
6. MCP 工具:
可通过语音控制灯光、机械臂、摄像头、屏幕、客户系统。
开发宝典对 VB6824 的描述是:它采用语音识别算法和语音降噪算法,支持更远距离唤醒、更低误唤醒率、更强抗噪能力、更快响应识别时间和免联网离线识别。 自定义唤醒词升级完成后,可支持选定唤醒词,并能在 AI 说话过程中随时打断。
3.2 视觉台灯能力
1. 摄像头识别:
识别桌面、书本、人物、手势、物体位置。
2. 视觉问答:
用户问"桌上有什么""这道题怎么做""帮我看看书本在哪里",设备拍照并请求视觉大模型。
3. 自动补光:
根据摄像头亮度估计环境光,自动调节台灯亮度和色温。
4. 机械臂指向:
根据视觉目标位置,机械臂转向书本、用户、物体或展示区域。
5. 屏幕反馈:
屏幕显示识别结果、AI 表情、台灯状态、机械臂状态、网络状态。
开发宝典中的多模态方案已经覆盖 摄像头 + 双目显示 + 触摸交互 + 小智云端 / 本地服务,并强调硬件原理图、BOM、固件源码齐全,便于二次开发和量产制造。
3.3 机械臂能力
推荐机械结构:
基础版:
2 自由度云台
- pan:左右旋转
- tilt:上下俯仰
增强版:
3 自由度机械臂
- base:底座旋转
- shoulder:大臂俯仰
- head:灯头角度
高端版:
3 自由度机械臂 + 限位检测 + 电流保护 + 姿态回零
典型语音指令:
"小博,转过来看我"
"把灯光照向书本"
"台灯抬高一点"
"低一点,亮一点"
"看一下桌面上有什么"
"帮我拍一下这张纸"
"切换专注学习模式"
3.4 三种联网能力
1. Wi-Fi:
ESP32-S3 原生 Wi-Fi,用于家庭、办公室、展厅、OTA。
2. BLE / BluFi:
用于四博小助手小程序配网、绑定设备、参数配置。
3. 4G:
外接 4G 模组,用于户外、移动、展厅、无 Wi-Fi 环境。
4. 蓝牙 PAN,可选:
通过 7014 或蓝牙 PAN 模组使用手机网络,适合低成本户外联网。
AI 选型表中,7014 蓝牙 PAN 方案的特点是成本低、可脱离 APP、可通过手机网络通信解决户外网络问题;四博 AI-C5 开发板资料也显示其支持 2.4G / 5G Wi-Fi、4G 模组、喇叭、麦克风、电池和屏幕,可作为三网设计参考。
4. 推荐硬件方案
4.1 主控
主控:ESP32-S3R8
模组:ESPS3-32-N16R8 / ESPS3-32E-N16R8
Flash:16MB
PSRAM:8MB
无线:2.4GHz Wi-Fi + BLE
显示:SPI / RGB / I8080 LCD
摄像头:DVP Camera,具体传感器按 BOM 选型
四博乐鑫系手册中,ESPS3-32 提供 N4、N8、N8R2、N16R2、N16R8 等子型号,芯片覆盖 ESP32-S3 / S3R2 / S3R8,ESPS3-32E 则兼容 ESP32-S3-WROOM-1U 系列模组。
4.2 语音与音频
语音前端:VB6824
麦克风:单麦 / 双麦,根据结构选型
功放:I2S 数字功放或模拟功放
喇叭:3W / 4Ω 或 5W / 4Ω
回采:功放输出或 I2S 回采给 AEC
4.3 摄像头
接口:ESP32-S3 DVP Camera
格式:JPEG / RGB565 / YUV
用途:
- 拍照上传给视觉模型
- 桌面物体识别
- 手势 / 人脸方向检测
- 机械臂目标定位
4.4 机械臂
执行器:
- PWM 舵机:成本低、控制简单
- 串口舵机:支持角度反馈和力矩控制
- 步进电机:定位稳定,适合高端版
保护:
- 上电回零
- 角度限幅
- 堵转检测
- 低电量禁止大动作
- 儿童安全限速
4.5 灯光
灯光驱动:
- 冷暖双色 LED
- 恒流驱动
- ESP32-S3 PWM 调光
控制参数:
- brightness:0~100
- color_temp:2700K~6500K
- mode:阅读 / 护眼 / 夜灯 / 氛围 / 专注
5. 软件系统架构
app_main
├── board_init()
├── nvs_config_init()
├── audio_frontend_start()
├── mcp_uart_bridge_start()
├── network_policy_start()
├── ai_websocket_start()
├── camera_service_start()
├── vision_ai_service_start()
├── servo_arm_start()
├── lamp_driver_start()
├── display_manager_start()
├── ota_manager_start()
└── factory_test_start()
FreeRTOS 任务建议:
| 任务 | 优先级 | 功能 |
|---|---|---|
audio_frontend_task |
高 | VB6824 唤醒、打断、状态同步 |
ai_session_task |
高 | WebSocket、ASR、LLM、TTS |
camera_task |
中高 | 摄像头采集、JPEG 缓存 |
vision_task |
中高 | 图片上传、视觉模型识别 |
servo_task |
中 | 机械臂动作队列 |
lamp_task |
中 | 亮度、色温、场景模式 |
display_task |
中 | 单屏 / 双屏 / 异显 UI |
network_task |
中 | Wi-Fi / 4G / 蓝牙 PAN 策略 |
mcp_uart_task |
中高 | 语义到动作的 MCP 映射 |
ota_task |
低 | 固件与资源 OTA |
factory_task |
低 | 产测与老化 |
6. AI 交互链路
6.1 语音对话链路
用户说话
↓
VB6824 离线唤醒 / AEC / 降噪
↓
ESP32-S3 进入 Listening
↓
WebSocket 上传音频
↓
ASR
↓
LLM / MCP 工具决策
↓
TTS
↓
ESP32-S3 播放
↓
喇叭输出
6.2 视觉问答链路
用户:"小博,看看桌上有什么"
↓
唤醒 + 语音识别
↓
LLM 判断需要视觉工具
↓
ESP32-S3 摄像头拍照
↓
JPEG 上传到后端 VLM
↓
VLM 返回识别结果
↓
LLM 组织语言
↓
TTS 播报 + 屏幕显示
6.3 机械臂动作链路
用户:"把灯转向书本"
↓
语音识别
↓
LLM 调用 vision_detect_book
↓
摄像头识别书本中心点
↓
坐标换算为 pan / tilt 角度
↓
ESP32-S3 控制舵机
↓
灯光切换阅读模式
7. 开发环境与编译
开发宝典建议使用 VSCode + ESP-IDF 扩展进行编译烧录;AI-S3 标准开发板章节使用 ESP-IDF 5.4.1,多模态 Vision 工程说明设置目标芯片为 esp32s3。
7.1 AI-Speaker 基础工程
git clone https://github.com/SmartArduino/DOIT_AI.git
cd DOIT_AI
idf.py set-target esp32s3
idf.py menuconfig
idf.py build
idf.py -p /dev/ttyUSB0 flash monitor
7.2 多模态视觉工程
git clone https://github.com/SmartArduino/DOIT_ESPS3_AI_EYE_Vision.git
cd DOIT_ESPS3_AI_EYE_Vision
idf.py set-target esp32s3
idf.py menuconfig
idf.py build
idf.py -p /dev/ttyUSB0 flash monitor
7.3 推荐 menuconfig 配置
Board Type:
Sibo Pixar Apple AI Lamp Speaker S3
Audio:
VB6824
USE_DEVICE_AEC = y
USE_SERVER_AEC = n
Network:
Wi-Fi = y
BLE BluFi = y
LTE 4G = optional
Bluetooth PAN = optional
Vision:
Camera = y
JPEG Capture = y
VLM Upload = y
Actuator:
Servo Arm = y
Lamp PWM = y
Display:
Single / Dual Mirror / Dual Heterogeneous
MCP:
Enable AT+MCP = y
8. 关键代码示例
下面代码按 ESP-IDF 风格给出,GPIO 仅为示例,实际量产需按 PCB 调整。
8.1 板级配置 board_config.h
#pragma once
#include "driver/gpio.h"
#include "driver/uart.h"
#include "driver/spi_master.h"
/*
* 四博皮克斯苹果 AI 台灯 / AI 智能音箱 S3 视觉机械臂版
*/
#define BOARD_NAME "SIBO_PIXAR_AI_LAMP_SPEAKER_S3"
/* ---------- 主控 ---------- */
#define SOC_NAME "ESP32-S3R8"
#define FLASH_SIZE_MB 16
#define PSRAM_SIZE_MB 8
/* ---------- VB6824 / AI MCP UART ---------- */
#define AI_UART UART_NUM_1
#define AI_UART_BAUD 115200
#define AI_UART_TX_GPIO GPIO_NUM_17
#define AI_UART_RX_GPIO GPIO_NUM_18
#define AI_RESET_GPIO GPIO_NUM_21
/* ---------- 4G Modem,可选 ---------- */
#define LTE_UART UART_NUM_2
#define LTE_UART_BAUD 115200
#define LTE_TX_GPIO GPIO_NUM_39
#define LTE_RX_GPIO GPIO_NUM_40
#define LTE_PWRKEY_GPIO GPIO_NUM_41
#define LTE_RESET_GPIO GPIO_NUM_42
/* ---------- 7014 Bluetooth PAN / A2DP,可选 ---------- */
#define BT7014_UART UART_NUM_0
#define BT7014_TX_GPIO GPIO_NUM_43
#define BT7014_RX_GPIO GPIO_NUM_44
#define BT7014_EN_GPIO GPIO_NUM_45
/* ---------- Camera,GPIO 需按实际摄像头模组调整 ---------- */
#define CAM_PIN_PWDN GPIO_NUM_NC
#define CAM_PIN_RESET GPIO_NUM_NC
#define CAM_PIN_XCLK GPIO_NUM_15
#define CAM_PIN_SIOD GPIO_NUM_4
#define CAM_PIN_SIOC GPIO_NUM_5
#define CAM_PIN_D0 GPIO_NUM_11
#define CAM_PIN_D1 GPIO_NUM_9
#define CAM_PIN_D2 GPIO_NUM_8
#define CAM_PIN_D3 GPIO_NUM_10
#define CAM_PIN_D4 GPIO_NUM_12
#define CAM_PIN_D5 GPIO_NUM_18
#define CAM_PIN_D6 GPIO_NUM_17
#define CAM_PIN_D7 GPIO_NUM_16
#define CAM_PIN_VSYNC GPIO_NUM_6
#define CAM_PIN_HREF GPIO_NUM_7
#define CAM_PIN_PCLK GPIO_NUM_13
/* ---------- Servo Arm ---------- */
#define SERVO_BASE_GPIO GPIO_NUM_1
#define SERVO_SHOULDER_GPIO GPIO_NUM_2
#define SERVO_HEAD_GPIO GPIO_NUM_3
/* ---------- Lamp PWM ---------- */
#define LAMP_WARM_PWM_GPIO GPIO_NUM_35
#define LAMP_COLD_PWM_GPIO GPIO_NUM_36
/* ---------- Audio ---------- */
#define AMP_EN_GPIO GPIO_NUM_46
#define I2S_BCLK_GPIO GPIO_NUM_6
#define I2S_LRCK_GPIO GPIO_NUM_7
#define I2S_DOUT_GPIO GPIO_NUM_8
/* ---------- Display A ---------- */
#define LCD_A_SPI_HOST SPI2_HOST
#define LCD_A_CS_GPIO GPIO_NUM_10
#define LCD_A_DC_GPIO GPIO_NUM_11
#define LCD_A_RST_GPIO GPIO_NUM_12
#define LCD_A_BL_GPIO GPIO_NUM_13
/* ---------- Display B,可选异显 ---------- */
#define LCD_B_SPI_HOST SPI2_HOST
#define LCD_B_CS_GPIO GPIO_NUM_14
#define LCD_B_DC_GPIO GPIO_NUM_15
#define LCD_B_RST_GPIO GPIO_NUM_16
#define LCD_B_BL_GPIO GPIO_NUM_4
/* ---------- Keys ---------- */
#define KEY_BOOT_GPIO GPIO_NUM_0
#define KEY_TOUCH_1_GPIO GPIO_NUM_47
#define KEY_TOUCH_2_GPIO GPIO_NUM_48
/* ---------- Safety ---------- */
#define BAT_ADC_CHANNEL 3
#define SERVO_CURRENT_ADC_CHANNEL 4
8.2 机械臂舵机控制 servo_arm.c
#include <math.h>
#include "esp_log.h"
#include "driver/ledc.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "board_config.h"
#define TAG "SERVO_ARM"
#define SERVO_TIMER LEDC_TIMER_0
#define SERVO_MODE LEDC_LOW_SPEED_MODE
#define SERVO_FREQ_HZ 50
#define SERVO_RESOLUTION LEDC_TIMER_14_BIT
#define SERVO_MIN_US 500
#define SERVO_MAX_US 2500
#define SERVO_PERIOD_US 20000
typedef enum {
SERVO_CH_BASE = 0,
SERVO_CH_SHOULDER,
SERVO_CH_HEAD,
} servo_id_t;
typedef struct {
gpio_num_t gpio;
ledc_channel_t ch;
float min_angle;
float max_angle;
float current_angle;
} servo_t;
static servo_t s_servos[] = {
{
.gpio = SERVO_BASE_GPIO,
.ch = LEDC_CHANNEL_0,
.min_angle = 0,
.max_angle = 180,
.current_angle = 90,
},
{
.gpio = SERVO_SHOULDER_GPIO,
.ch = LEDC_CHANNEL_1,
.min_angle = 20,
.max_angle = 160,
.current_angle = 90,
},
{
.gpio = SERVO_HEAD_GPIO,
.ch = LEDC_CHANNEL_2,
.min_angle = 30,
.max_angle = 150,
.current_angle = 90,
},
};
static uint32_t servo_angle_to_duty(float angle)
{
if (angle < 0) {
angle = 0;
}
if (angle > 180) {
angle = 180;
}
float pulse_us = SERVO_MIN_US +
(SERVO_MAX_US - SERVO_MIN_US) * angle / 180.0f;
uint32_t max_duty = (1 << 14) - 1;
return (uint32_t)(max_duty * pulse_us / SERVO_PERIOD_US);
}
static float clamp_angle(servo_t *servo, float angle)
{
if (angle < servo->min_angle) {
return servo->min_angle;
}
if (angle > servo->max_angle) {
return servo->max_angle;
}
return angle;
}
void servo_arm_init(void)
{
ledc_timer_config_t timer = {
.speed_mode = SERVO_MODE,
.timer_num = SERVO_TIMER,
.duty_resolution = SERVO_RESOLUTION,
.freq_hz = SERVO_FREQ_HZ,
.clk_cfg = LEDC_AUTO_CLK,
};
ESP_ERROR_CHECK(ledc_timer_config(&timer));
for (int i = 0; i < 3; i++) {
ledc_channel_config_t ch = {
.gpio_num = s_servos[i].gpio,
.speed_mode = SERVO_MODE,
.channel = s_servos[i].ch,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = SERVO_TIMER,
.duty = servo_angle_to_duty(s_servos[i].current_angle),
.hpoint = 0,
};
ESP_ERROR_CHECK(ledc_channel_config(&ch));
}
ESP_LOGI(TAG, "servo arm init done");
}
void servo_set_angle(servo_id_t id, float angle)
{
if (id < 0 || id >= 3) {
return;
}
servo_t *servo = &s_servos[id];
angle = clamp_angle(servo, angle);
uint32_t duty = servo_angle_to_duty(angle);
ledc_set_duty(SERVO_MODE, servo->ch, duty);
ledc_update_duty(SERVO_MODE, servo->ch);
servo->current_angle = angle;
ESP_LOGI(TAG, "servo %d angle %.1f", id, angle);
}
void servo_move_smooth(servo_id_t id, float target, float step, int delay_ms)
{
if (id < 0 || id >= 3 || step <= 0) {
return;
}
servo_t *servo = &s_servos[id];
target = clamp_angle(servo, target);
float current = servo->current_angle;
float dir = target > current ? 1.0f : -1.0f;
while (fabsf(target - current) > step) {
current += dir * step;
servo_set_angle(id, current);
vTaskDelay(pdMS_TO_TICKS(delay_ms));
}
servo_set_angle(id, target);
}
void servo_look_at_percent(float x_percent, float y_percent)
{
/*
* x_percent: 0~100, 图像左到右
* y_percent: 0~100, 图像上到下
*
* 简化映射:
* 图像中心 50,50 对应 pan=90, tilt=90。
*/
float pan = 90.0f + (x_percent - 50.0f) * 0.8f;
float tilt = 90.0f + (y_percent - 50.0f) * 0.6f;
servo_move_smooth(SERVO_CH_BASE, pan, 2.0f, 20);
servo_move_smooth(SERVO_CH_HEAD, tilt, 2.0f, 20);
}
void servo_home(void)
{
servo_move_smooth(SERVO_CH_BASE, 90, 2.0f, 15);
servo_move_smooth(SERVO_CH_SHOULDER, 90, 2.0f, 15);
servo_move_smooth(SERVO_CH_HEAD, 90, 2.0f, 15);
}
8.3 台灯亮度与色温控制 lamp_driver.c
#include "esp_log.h"
#include "driver/ledc.h"
#include "board_config.h"
#define TAG "LAMP"
#define LAMP_TIMER LEDC_TIMER_1
#define LAMP_MODE LEDC_LOW_SPEED_MODE
#define LAMP_FREQ_HZ 20000
#define LAMP_RESOLUTION LEDC_TIMER_12_BIT
#define LAMP_MAX_DUTY ((1 << 12) - 1)
typedef enum {
LAMP_MODE_OFF = 0,
LAMP_MODE_READING,
LAMP_MODE_EYE_CARE,
LAMP_MODE_NIGHT,
LAMP_MODE_FOCUS,
LAMP_MODE_AMBIENT,
} lamp_mode_t;
static uint8_t s_brightness = 50;
static uint16_t s_color_temp = 4000;
static uint32_t percent_to_duty(uint8_t percent)
{
if (percent > 100) {
percent = 100;
}
return (uint32_t)(LAMP_MAX_DUTY * percent / 100);
}
void lamp_driver_init(void)
{
ledc_timer_config_t timer = {
.speed_mode = LAMP_MODE,
.timer_num = LAMP_TIMER,
.duty_resolution = LAMP_RESOLUTION,
.freq_hz = LAMP_FREQ_HZ,
.clk_cfg = LEDC_AUTO_CLK,
};
ledc_timer_config(&timer);
ledc_channel_config_t warm = {
.gpio_num = LAMP_WARM_PWM_GPIO,
.speed_mode = LAMP_MODE,
.channel = LEDC_CHANNEL_3,
.timer_sel = LAMP_TIMER,
.duty = 0,
.hpoint = 0,
};
ledc_channel_config_t cold = {
.gpio_num = LAMP_COLD_PWM_GPIO,
.speed_mode = LAMP_MODE,
.channel = LEDC_CHANNEL_4,
.timer_sel = LAMP_TIMER,
.duty = 0,
.hpoint = 0,
};
ledc_channel_config(&warm);
ledc_channel_config(&cold);
ESP_LOGI(TAG, "lamp driver init done");
}
void lamp_set(uint8_t brightness, uint16_t color_temp)
{
if (brightness > 100) {
brightness = 100;
}
if (color_temp < 2700) {
color_temp = 2700;
}
if (color_temp > 6500) {
color_temp = 6500;
}
/*
* 色温线性映射:
* 2700K: warm=100%, cold=0%
* 6500K: warm=0%, cold=100%
*/
float cold_ratio = (float)(color_temp - 2700) / (6500 - 2700);
float warm_ratio = 1.0f - cold_ratio;
uint8_t warm_percent = (uint8_t)(brightness * warm_ratio);
uint8_t cold_percent = (uint8_t)(brightness * cold_ratio);
ledc_set_duty(LAMP_MODE, LEDC_CHANNEL_3, percent_to_duty(warm_percent));
ledc_update_duty(LAMP_MODE, LEDC_CHANNEL_3);
ledc_set_duty(LAMP_MODE, LEDC_CHANNEL_4, percent_to_duty(cold_percent));
ledc_update_duty(LAMP_MODE, LEDC_CHANNEL_4);
s_brightness = brightness;
s_color_temp = color_temp;
ESP_LOGI(TAG, "lamp brightness=%u color_temp=%u warm=%u cold=%u",
brightness, color_temp, warm_percent, cold_percent);
}
void lamp_apply_mode(lamp_mode_t mode)
{
switch (mode) {
case LAMP_MODE_OFF:
lamp_set(0, 4000);
break;
case LAMP_MODE_READING:
lamp_set(85, 4200);
break;
case LAMP_MODE_EYE_CARE:
lamp_set(60, 3600);
break;
case LAMP_MODE_NIGHT:
lamp_set(10, 2700);
break;
case LAMP_MODE_FOCUS:
lamp_set(95, 5000);
break;
case LAMP_MODE_AMBIENT:
lamp_set(35, 3000);
break;
default:
lamp_set(s_brightness, s_color_temp);
break;
}
}
8.4 摄像头初始化与拍照上传框架
#include "esp_log.h"
#include "esp_camera.h"
#include "board_config.h"
#define TAG "CAMERA"
static camera_fb_t *s_last_fb = NULL;
esp_err_t camera_service_init(void)
{
camera_config_t config = {
.pin_pwdn = CAM_PIN_PWDN,
.pin_reset = CAM_PIN_RESET,
.pin_xclk = CAM_PIN_XCLK,
.pin_sccb_sda = CAM_PIN_SIOD,
.pin_sccb_scl = CAM_PIN_SIOC,
.pin_d7 = CAM_PIN_D7,
.pin_d6 = CAM_PIN_D6,
.pin_d5 = CAM_PIN_D5,
.pin_d4 = CAM_PIN_D4,
.pin_d3 = CAM_PIN_D3,
.pin_d2 = CAM_PIN_D2,
.pin_d1 = CAM_PIN_D1,
.pin_d0 = CAM_PIN_D0,
.pin_vsync = CAM_PIN_VSYNC,
.pin_href = CAM_PIN_HREF,
.pin_pclk = CAM_PIN_PCLK,
.xclk_freq_hz = 20000000,
.ledc_timer = LEDC_TIMER_2,
.ledc_channel = LEDC_CHANNEL_5,
.pixel_format = PIXFORMAT_JPEG,
.frame_size = FRAMESIZE_VGA,
.jpeg_quality = 12,
.fb_count = 2,
.fb_location = CAMERA_FB_IN_PSRAM,
.grab_mode = CAMERA_GRAB_LATEST,
};
esp_err_t err = esp_camera_init(&config);
if (err != ESP_OK) {
ESP_LOGE(TAG, "camera init failed: 0x%x", err);
return err;
}
ESP_LOGI(TAG, "camera init done");
return ESP_OK;
}
camera_fb_t *camera_capture_jpeg(void)
{
if (s_last_fb) {
esp_camera_fb_return(s_last_fb);
s_last_fb = NULL;
}
s_last_fb = esp_camera_fb_get();
if (!s_last_fb) {
ESP_LOGE(TAG, "capture failed");
return NULL;
}
ESP_LOGI(TAG, "capture jpeg size=%u", s_last_fb->len);
return s_last_fb;
}
void camera_release_last(void)
{
if (s_last_fb) {
esp_camera_fb_return(s_last_fb);
s_last_fb = NULL;
}
}
/*
* TODO:
* 量产工程中可实现:
* 1. HTTP multipart 上传 JPEG;
* 2. WebSocket binary 上传 JPEG;
* 3. 本地 SD 卡保存;
* 4. 返回 vision_result_t 给机械臂和 TTS 使用。
*/
8.5 视觉结果到机械臂动作
#include <stdint.h>
#include <stdbool.h>
#include "esp_log.h"
#define TAG "VISION_ACTION"
typedef struct {
bool found;
char label[32];
float x_percent;
float y_percent;
float confidence;
} vision_object_t;
extern void servo_look_at_percent(float x_percent, float y_percent);
extern void lamp_apply_mode(int mode);
extern void lamp_set(uint8_t brightness, uint16_t color_temp);
typedef enum {
LAMP_MODE_READING = 1,
LAMP_MODE_EYE_CARE = 2,
LAMP_MODE_FOCUS = 4,
} lamp_mode_t;
void vision_handle_object(const vision_object_t *obj)
{
if (!obj || !obj->found) {
ESP_LOGW(TAG, "object not found");
return;
}
ESP_LOGI(TAG, "object=%s x=%.1f y=%.1f conf=%.2f",
obj->label,
obj->x_percent,
obj->y_percent,
obj->confidence);
/*
* 让灯头看向目标。
*/
servo_look_at_percent(obj->x_percent, obj->y_percent);
/*
* 根据识别物体切换灯光模式。
*/
if (strcmp(obj->label, "book") == 0 ||
strcmp(obj->label, "paper") == 0) {
lamp_apply_mode(LAMP_MODE_READING);
} else if (strcmp(obj->label, "face") == 0) {
lamp_set(45, 3600);
} else {
lamp_apply_mode(LAMP_MODE_FOCUS);
}
}
8.6 AT+MCP:把自然语言变成设备动作
开发宝典中的 AT+MCP 非常适合这类"AI 台灯 + 音箱 + 机械臂"产品。协议使用 UART,默认 115200, 8N1,所有指令以回车换行结束;AT+ADDMCP 可以把"人话"映射成 MCU 可执行的二进制控制帧;模块还会上报开机、配网、联网、监听、说话、升级、激活等状态。 当 MCU 收到 55 AA 01 FC AA 55 时,需要重启 AI 模组并重新发送 MCP 映射。
MCP 命令设计
CMD_LAMP_SET 0xF1
CMD_ARM_MOVE 0xF2
CMD_CAPTURE 0xF3
CMD_VISION_ASK 0xF4
CMD_SCREEN_MODE 0xF5
CMD_NETWORK_MODE 0xF6
CMD_CUSTOMER_API 0xF7
代码
#include <stdio.h>
#include <string.h>
#include <stdbool.h>
#include "esp_log.h"
#include "driver/uart.h"
#include "driver/gpio.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "board_config.h"
#define TAG "MCP"
#define FRAME_H1 0x55
#define FRAME_H2 0xAA
#define FRAME_T1 0xAA
#define FRAME_T2 0x55
#define CMD_STATUS 0xFF
#define CMD_RECOVER 0xFC
#define CMD_LAMP_SET 0xF1
#define CMD_ARM_MOVE 0xF2
#define CMD_CAPTURE 0xF3
#define CMD_VISION_ASK 0xF4
#define CMD_SCREEN_MODE 0xF5
#define CMD_NETWORK_MODE 0xF6
#define CMD_CUSTOMER_API 0xF7
typedef enum {
AI_STARTING = 0x01,
AI_CONFIGURING = 0x02,
AI_IDLE = 0x03,
AI_CONNECTING = 0x04,
AI_LISTENING = 0x05,
AI_SPEAKING = 0x06,
AI_UPGRADING = 0x07,
AI_ACTIVATING = 0x08,
} ai_status_t;
extern void lamp_set(uint8_t brightness, uint16_t color_temp);
extern void servo_move_smooth(int id, float target, float step, int delay_ms);
extern void servo_home(void);
extern void on_capture_and_vision_ask(void);
extern void camera_capture_jpeg(void);
static void ai_reset_module(void)
{
gpio_set_direction(AI_RESET_GPIO, GPIO_MODE_OUTPUT);
gpio_set_level(AI_RESET_GPIO, 0);
vTaskDelay(pdMS_TO_TICKS(300));
gpio_set_level(AI_RESET_GPIO, 1);
vTaskDelay(pdMS_TO_TICKS(1500));
}
static void mcp_send_line(const char *line)
{
uart_write_bytes(AI_UART, line, strlen(line));
uart_write_bytes(AI_UART, "\r\n", 2);
ESP_LOGI(TAG, "MCU -> AI: %s", line);
}
static void ui_on_ai_status(ai_status_t status)
{
switch (status) {
case AI_STARTING:
ESP_LOGI(TAG, "AI starting");
break;
case AI_CONFIGURING:
ESP_LOGI(TAG, "AI configuring");
break;
case AI_IDLE:
ESP_LOGI(TAG, "AI idle");
break;
case AI_CONNECTING:
ESP_LOGI(TAG, "AI connecting");
break;
case AI_LISTENING:
ESP_LOGI(TAG, "AI listening");
break;
case AI_SPEAKING:
ESP_LOGI(TAG, "AI speaking");
break;
case AI_UPGRADING:
ESP_LOGI(TAG, "AI upgrading");
break;
case AI_ACTIVATING:
ESP_LOGI(TAG, "AI activating");
break;
default:
ESP_LOGW(TAG, "unknown AI status: 0x%02X", status);
break;
}
}
static void mcp_register_tools(void)
{
mcp_send_line("AT");
mcp_send_line("AT+WIFICFG=0");
mcp_send_line("AT+CONNECT");
/*
* 用户:"把灯调亮一点 / 色温调暖一点"
* 返回:55 AA 04 F1 brightness color_temp_hi color_temp_lo AA 55
*/
mcp_send_line(
"AT+ADDMCP=1,set_lamp,设置台灯亮度和色温,F1,3,brightness,color_temp_hi,color_temp_lo"
);
/*
* 用户:"台灯转过来看我 / 灯头抬高一点"
* 返回:55 AA 04 F2 servo_id angle_hi angle_lo AA 55
*/
mcp_send_line(
"AT+ADDMCP=1,move_arm,控制机械臂或灯头角度,F2,3,servo_id,angle_hi,angle_lo"
);
/*
* 用户:"拍一张照片"
*/
mcp_send_line(
"AT+ADDMCP=0,capture_photo,控制摄像头拍照,2,F3,01"
);
/*
* 用户:"看看桌上有什么 / 帮我看这道题"
*/
mcp_send_line(
"AT+ADDMCP=0,vision_question,调用摄像头和视觉大模型识别当前画面,2,F4,01"
);
/*
* 用户:"切换到双屏异显 / 只显示时钟"
*/
mcp_send_line(
"AT+ADDMCP=1,set_screen_mode,设置屏幕显示模式,F5,1,mode"
);
/*
* 用户:"切换到 4G 网络 / 打开蓝牙上网"
*/
mcp_send_line(
"AT+ADDMCP=1,set_network_mode,切换联网方式,F6,1,mode"
);
/*
* 用户:"打开客户系统的一号场景"
*/
mcp_send_line(
"AT+ADDMCP=1,customer_api,调用客户系统接口,F7,2,scene_id,action"
);
}
static void mcp_handle_frame(uint8_t cmd, const uint8_t *data, uint8_t len)
{
if (cmd == CMD_RECOVER) {
ai_reset_module();
mcp_register_tools();
return;
}
if (cmd == CMD_STATUS && len >= 1) {
ui_on_ai_status((ai_status_t)data[0]);
return;
}
switch (cmd) {
case CMD_LAMP_SET:
if (len >= 3) {
uint8_t brightness = data[0];
uint16_t color_temp = ((uint16_t)data[1] << 8) | data[2];
lamp_set(brightness, color_temp);
}
break;
case CMD_ARM_MOVE:
if (len >= 3) {
uint8_t servo_id = data[0];
uint16_t angle_raw = ((uint16_t)data[1] << 8) | data[2];
servo_move_smooth(servo_id, (float)angle_raw, 2.0f, 15);
}
break;
case CMD_CAPTURE:
camera_capture_jpeg();
break;
case CMD_VISION_ASK:
on_capture_and_vision_ask();
break;
case CMD_SCREEN_MODE:
if (len >= 1) {
ESP_LOGI(TAG, "screen mode=%u", data[0]);
/*
* TODO:
* display_set_mode(data[0]);
*/
}
break;
case CMD_NETWORK_MODE:
if (len >= 1) {
ESP_LOGI(TAG, "network mode=%u", data[0]);
/*
* mode:
* 1 Wi-Fi
* 2 4G
* 3 Bluetooth PAN
*/
}
break;
case CMD_CUSTOMER_API:
if (len >= 2) {
ESP_LOGI(TAG, "customer scene=%u action=%u", data[0], data[1]);
/*
* TODO:
* mqtt_publish_customer_scene(data[0], data[1]);
* 或 HTTP 调客户系统。
*/
}
break;
default:
ESP_LOGW(TAG, "unhandled cmd=0x%02X len=%u", cmd, len);
break;
}
}
static void mcp_rx_task(void *arg)
{
uint8_t frame[160];
uint8_t pos = 0;
int expected = -1;
while (1) {
uint8_t b = 0;
int n = uart_read_bytes(AI_UART, &b, 1, pdMS_TO_TICKS(100));
if (n <= 0) {
continue;
}
if (pos == 0 && b != FRAME_H1) {
continue;
}
if (pos == 1 && b != FRAME_H2) {
pos = 0;
expected = -1;
continue;
}
frame[pos++] = b;
if (pos == 3) {
uint8_t len = frame[2];
if (len == 0 || len > 150) {
pos = 0;
expected = -1;
continue;
}
expected = 2 + 1 + len + 2;
}
if (expected > 0 && pos >= expected) {
uint8_t len = frame[2];
if (frame[3 + len] == FRAME_T1 &&
frame[4 + len] == FRAME_T2) {
uint8_t cmd = frame[3];
const uint8_t *data = &frame[4];
uint8_t data_len = len - 1;
mcp_handle_frame(cmd, data, data_len);
} else {
ESP_LOGW(TAG, "bad frame tail");
}
pos = 0;
expected = -1;
}
if (pos >= sizeof(frame)) {
pos = 0;
expected = -1;
}
}
}
void mcp_uart_bridge_start(void)
{
uart_config_t cfg = {
.baud_rate = AI_UART_BAUD,
.data_bits = UART_DATA_8_BITS,
.parity = UART_PARITY_DISABLE,
.stop_bits = UART_STOP_BITS_1,
.flow_ctrl = UART_HW_FLOWCTRL_DISABLE,
.source_clk = UART_SCLK_DEFAULT,
};
uart_driver_install(AI_UART, 2048, 2048, 0, NULL, 0);
uart_param_config(AI_UART, &cfg);
uart_set_pin(
AI_UART,
AI_UART_TX_GPIO,
AI_UART_RX_GPIO,
UART_PIN_NO_CHANGE,
UART_PIN_NO_CHANGE
);
ai_reset_module();
mcp_register_tools();
xTaskCreate(mcp_rx_task, "mcp_rx", 4096, NULL, 10, NULL);
}
8.7 视觉问答流程框架
#include "esp_log.h"
#include "esp_http_client.h"
#include "esp_camera.h"
#define TAG "VISION_AI"
extern camera_fb_t *camera_capture_jpeg(void);
extern void camera_release_last(void);
extern void ai_tts_speak_text(const char *text);
typedef struct {
bool found;
char label[32];
float x_percent;
float y_percent;
float confidence;
char answer[256];
} vision_result_t;
static esp_err_t vision_upload_jpeg(camera_fb_t *fb, vision_result_t *result)
{
if (!fb || !result) {
return ESP_ERR_INVALID_ARG;
}
/*
* 这里给框架,不限定具体后端。
* 可以对接:
* 1. 小智私有化后端的视觉工具;
* 2. 客户自己的 VLM 服务;
* 3. OpenAI / 豆包 / 通义 / 自建多模态模型。
*/
esp_http_client_config_t config = {
.url = "https://your-server.com/api/v1/vision/analyze",
.method = HTTP_METHOD_POST,
.timeout_ms = 15000,
};
esp_http_client_handle_t client = esp_http_client_init(&config);
esp_http_client_set_header(client, "Content-Type", "image/jpeg");
esp_http_client_set_post_field(client, (const char *)fb->buf, fb->len);
esp_err_t err = esp_http_client_perform(client);
if (err != ESP_OK) {
ESP_LOGE(TAG, "vision request failed: %s", esp_err_to_name(err));
esp_http_client_cleanup(client);
return err;
}
int status = esp_http_client_get_status_code(client);
ESP_LOGI(TAG, "vision status=%d", status);
/*
* TODO:
* 实际工程中读取 response JSON:
* {
* "answer": "桌面上有一本书和一支笔",
* "object": {
* "label": "book",
* "x": 63.5,
* "y": 54.2,
* "confidence": 0.91
* }
* }
*/
result->found = true;
snprintf(result->label, sizeof(result->label), "book");
result->x_percent = 60.0f;
result->y_percent = 55.0f;
result->confidence = 0.90f;
snprintf(result->answer, sizeof(result->answer),
"我看到了桌面上的书本,已经把灯光转向书本位置。");
esp_http_client_cleanup(client);
return ESP_OK;
}
extern void vision_handle_object(const vision_object_t *obj);
void on_capture_and_vision_ask(void)
{
camera_fb_t *fb = camera_capture_jpeg();
if (!fb) {
ai_tts_speak_text("摄像头打开失败,请检查摄像头连接。");
return;
}
vision_result_t result = {0};
esp_err_t err = vision_upload_jpeg(fb, &result);
camera_release_last();
if (err != ESP_OK) {
ai_tts_speak_text("视觉识别失败,请稍后再试。");
return;
}
vision_object_t obj = {
.found = result.found,
.x_percent = result.x_percent,
.y_percent = result.y_percent,
.confidence = result.confidence,
};
snprintf(obj.label, sizeof(obj.label), "%s", result.label);
vision_handle_object(&obj);
ai_tts_speak_text(result.answer);
}
8.8 主程序 app_main.c
#include "esp_log.h"
#include "nvs_flash.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#define TAG "APP"
extern void servo_arm_init(void);
extern void servo_home(void);
extern void lamp_driver_init(void);
extern void lamp_apply_mode(int mode);
extern esp_err_t camera_service_init(void);
extern void mcp_uart_bridge_start(void);
extern void network_policy_start(void);
extern void display_manager_start(void);
extern void ai_websocket_start(void);
extern void ota_manager_start(void);
void app_main(void)
{
ESP_LOGI(TAG, "boot %s", "SIBO_PIXAR_AI_LAMP_SPEAKER_S3");
ESP_ERROR_CHECK(nvs_flash_init());
/*
* 板级外设
*/
lamp_driver_init();
servo_arm_init();
servo_home();
/*
* 摄像头
*/
if (camera_service_init() != ESP_OK) {
ESP_LOGW(TAG, "camera not ready, continue audio only mode");
}
/*
* 显示与联网
*/
display_manager_start();
network_policy_start();
/*
* AI 服务
*/
ai_websocket_start();
mcp_uart_bridge_start();
/*
* OTA
*/
ota_manager_start();
/*
* 默认护眼模式
*/
lamp_apply_mode(2);
ESP_LOGI(TAG, "system started");
}
9. 三种产品形态
9.1 标准 AI 音箱版
ESP32-S3R8 + 16M Flash
VB6824
Wi-Fi + BLE BluFi
1.3 / 1.54 寸屏
麦克风 + 喇叭
小智 / 豆包 / ChatGPT
MCP 控制灯光、音乐、闹钟、客户系统
适合:智能音箱、桌面助手、儿童故事机、智能家居语音入口。
9.2 AI 台灯音箱版
ESP32-S3R8 + VB6824
摄像头
冷暖双色 LED 台灯
2 自由度云台
单屏 UI
Wi-Fi / BLE / 可选 4G
视觉问答 + 语音控制 + 灯光控制
适合:学习台灯、陪伴台灯、办公桌面 AI 助手。
9.3 皮克斯苹果 AI 台灯高端版
ESP32-S3R8 + 16M Flash + 8M PSRAM
VB6824
摄像头
3 自由度机械臂
双屏 / 异显
4G 模组
7014 蓝牙 PAN / 蓝牙音箱
声音克隆
知识库
MCP 工具
视觉大模型
客户私有化后端
全开源生产资料
适合:品牌 B 端客户、方案商客户、高端 AI 玩具、AI 桌宠、教育台灯、展厅导览、桌面机器人。
10. 后端服务建议
开发宝典中说明,设备默认可连接小智官方服务,也可以运行开源后端服务,让设备连接到自己的后端;后端包括 OTA 接口和 WebSocket 接口,并可配置 LLM、TTS、人设等参数。 文档还提到,如果服务部署在服务器上反馈会更快,有显卡资源时还可以自建 LLM 和 TTS 服务。
推荐后端:
Nginx / Caddy
├── HTTPS OTA
├── WSS WebSocket
├── Device Auth
├── ASR
├── LLM
├── TTS
├── VLM Vision API
├── MCP Tool Server
└── Customer API Gateway
配置示例:
server:
websocket_url: "wss://ai.customer.com/xiaozhi/v1/"
ota_url: "https://ai.customer.com/xiaozhi/ota/"
selected_module:
VAD: SileroVAD
ASR: FunASR
LLM: CustomerLLM
TTS: CustomerTTS
Vision: CustomerVLM
Intent: function_call
device_profile:
name: "四博皮克斯苹果AI台灯"
capabilities:
- voice_wakeup
- realtime_barge_in
- camera_capture
- vision_question
- servo_arm
- lamp_control
- display
- mcp
11. 量产与产测
11.1 产测项目
主控:
- ESP32-S3 Flash / PSRAM 检测
- NVS 写入 SN / Batch ID
- Wi-Fi MAC / BLE MAC 读取
语音:
- VB6824 UART 通信
- 唤醒词测试
- 播放中打断测试
- 麦克风电平
- 喇叭测试
- AEC 回采测试
视觉:
- 摄像头初始化
- 拍照 JPEG 大小检测
- 亮度 / 焦距 / 图像方向测试
机械臂:
- 舵机回零
- pan / tilt / head 动作测试
- 限位测试
- 堵转电流测试
灯光:
- 暖光 PWM
- 冷光 PWM
- 亮度 0/50/100
- 色温 2700K / 4000K / 6500K
屏幕:
- 单屏显示
- 双屏镜像
- 双屏异显
- 背光 PWM
网络:
- Wi-Fi 扫描
- BluFi 配网
- 4G CSQ / 注册 / PPP
- 蓝牙 PAN
云端:
- OTA 请求
- WebSocket 连接
- VLM 请求
- MCP 指令闭环
11.2 工厂串口命令建议
FACTORY ENTER
FACTORY SET_SN=SBOPIXAR20260001
FACTORY WIFI_SCAN
FACTORY LTE_CSQ
FACTORY MIC_LEVEL
FACTORY SPK_PLAY=1000HZ
FACTORY WAKE_TEST
FACTORY CAMERA_CAPTURE
FACTORY SERVO_HOME
FACTORY SERVO_MOVE=0,90
FACTORY LAMP_SET=80,4000
FACTORY LCD_TEST
FACTORY MCP_TEST
FACTORY OTA_CHECK
FACTORY EXIT
12. 安全与可靠性设计
1. 机械臂限位:
所有角度必须软件限幅,避免打到用户或结构件。
2. 堵转保护:
通过电流采样或动作超时判断,异常立即断开舵机电源。
3. 儿童模式:
降低机械臂运动速度,禁用快速甩动动作。
4. 摄像头隐私:
摄像头工作时屏幕 / LED 明确提示。
支持物理遮挡片或隐私开关。
5. 4G 流量控制:
图片上传与 OTA 优先走 Wi-Fi。
4G 下限制高频视觉请求。
6. OTA 回滚:
S3 主控双 OTA 分区,失败自动回滚。
7. VB6824 固件:
语音前端固件独立升级,避免和主控 OTA 混淆。
13. 一句话总结
这套方案可以定义为:基于 ESP32-S3R8 + 16M Flash + VB6824 的四博皮克斯苹果 AI 台灯 / AI 智能音箱一体化平台。S3 负责联网、屏幕、摄像头、机械臂、灯光、WebSocket、OTA 和二次开发;VB6824 负责离线唤醒、远场拾音、AEC、降噪、唤醒词打断和自定义唤醒词;摄像头接入视觉大模型实现"看得见";机械臂和灯光系统实现"会动作、会照明";AT+MCP 把自然语言转成可执行控制帧;小智 / 私有化后端 / 客户大模型负责对话、视觉理解和工具调用。整体硬件和软件可开源,适合快速样机、客户定制和量产落地。