创业者视角:低门槛打造企业级 Agent 大屏产品,从 Demo 到商业化落地
摘要
企业展厅、指挥中心大屏是 B 端高价值刚需场景,但传统数字人方案成本高、落地难、体验差,创业者做这类产品极易陷入 “好看不赚钱、难复制” 的困境。本文从产品 MVP、商业化落地、成本优化角度,拆解基于魔珐星云端侧 Agent+DeepSeek,快速打造可售卖、易部署、强体验的企业级大屏交互产品,解决 B 端客户核心痛点,实现产品从 0 到 1、从 Demo 到规模化复制。
1. 引言:企业大屏产品的创业痛点
1.1 B 端大屏产品的普遍困境
对创业者而言,企业展厅、指挥中心大屏是优质 B 端赛道,但入局后会遇到三大产品死穴:
- 体验差卖不动:传统云端数字人延迟高、易卡顿,客户觉得 “花架子”,不愿付费;
- 成本高难盈利:云端 GPU 按小时计费,单项目成本高,规模化后利润直接被吃掉;
- 落地周期长:定制化开发、强网依赖,客户现场部署难,交付周期拖垮现金流。

图1:传统BI可视化大屏
1.2 产品破局:端侧 Agent 是最优解
真正能跑通商业闭环的大屏产品,核心是低成本、易部署、强交互、可复制。
魔珐星云端侧 Agent,恰好解决创业产品三大死穴:端侧渲染降本、弱网适配易落地、毫秒交互强体验,是创业者快速打造企业级大屏爆款的核心抓手。
1.3 本文产品目标
从创业者做产品的真实路径出发,拆解:
- 如何低成本搭建大屏 Agent 产品 MVP;
- 如何解决 B 端客户核心痛点、提升产品竞争力;
- 如何快速部署、规模化复制,实现盈利;
- 产品商业化场景与客户价值落地。
2. 产品技术选型:创业优先,成本与体验平衡
2.1 传统云端方案:创业产品的致命短板
传统云端数字人,看似成熟,实则是创业产品的高风险选择:
plaintext
用户输入→云端处理→云端渲染→下发展示
- 体验差(产品硬伤):响应 1-3 秒,卡顿频发,客户满意度低,复购难;
- 成本高(盈利杀手):云端 GPU 持续计费,单项目月成本数千元,规模化后亏损;
- 落地难(交付噩梦):强网依赖,客户展厅 / 指挥中心网络复杂,部署周期长、售后多;
- 竞争力弱(同质化严重):行业扎堆云端 Demo,产品无差异化,拼价格内卷。
2.2 端侧 Agent:创业产品最优技术路线

图2:魔珐星云数字人
魔珐星云AI 端渲 + 端侧解算,是创业者做产品的性价比之选:
|
|
|
强体验(产品核心卖点):端到端≤500ms 响应,支持随时打断,交互贴近真人;
低成本(盈利保障):一次接入、云端零算力消耗,仅付模型调用费,规模化利润高;
易落地(交付高效):弱网稳定,终端本地渲染,1 天内完成客户现场部署;
差异化(竞争壁垒):端侧实时交互是行业稀缺能力,产品形成明显竞争优势。
2.3 产品化技术架构
魔珐星云实现端到端全栈能力,打通三层核心架构:

打通感知 - 理解 - 表达 - 端侧渲染全链路,模块化设计、易集成、可定制,适配不同客户大屏需求,降低产品二次开发成本。
3. DeepSeek大模型详解
3.1 为什么选择DeepSeek?
在本项目中,我们需要一个能理解业务数据、生成洞察、回答问题的智能大脑。经过对比测试,选择魔搭社区提供的DeepSeek-V3.2模型:
|
模型 |
参数规模 |
推理能力 |
成本 |
适用场景 |
|
GPT-4 |
1.8T |
⭐⭐⭐⭐⭐ |
高 |
复杂推理 |
|
DeepSeek-V3 |
671B |
⭐⭐⭐⭐⭐ |
低 |
数据分析、对话 |
|
Qwen2.5 |
72B |
⭐⭐⭐⭐ |
低 |
通用对话 |
|
GLM-4 |
130B |
⭐⭐⭐⭐ |
中 |
中文场景 |
DeepSeek的优势:
- 推理能力强:在数学、代码、数据分析等任务上表现优异
- 成本低:通过魔搭社区调用,价格远低于GPT-4
- 中文友好:对中文业务场景的理解更准确
- 流式输出:支持SSE流式响应,适合对话场景
4. 项目架构设计
4.1 整体架构图
本项目采用前后端一体化架构,前端负责数字人展示和数据可视化,后端负责AI数据生成和对话服务:

4.2 核心功能模块
|
模块 |
功能 |
技术实现 |
|
场景切换 |
常规运营/营销活动/销售淡季/特殊事件 |
场景配置 + AI数据生成 |
|
数据可视化 |
7个核心指标 + 地区数据 + 产品数据 |
ECharts图表组件 |
|
智能对话 |
AI助手回答业务问题 |
DeepSeek + SSE流式响应 |
|
数字人播报 |
自动播报数据洞察 |
魔珐星云TTS + 动作控制 |
4.3 数据流程图

5. 核心实现:数字人接入
5.1 SDK控制器实
魔珐星云提供XmovAvatar SDK,我们封装了一个控制器来管理连接、播报和状态切换。

以下是项目中的真实实现源码:
// src/client/components/Avatar/AvatarController.ts
import keyService from '../../services/keyService';
import { useAvatarStore } from '../../store/avatarStore';
/**
* 魔珐星云数字人SDK控制器
* 支持手动连接和断开
*/
declare global {
interface Window {
XmovAvatar: any;
}
}
export interface SpeakOptions {
text: string;
isStart?: boolean;
isEnd?: boolean;
}
class AvatarController {
private sdkInstance: any = null;
private isConnected: boolean = false;
/**
* 初始化并连接SDK(从localStorage读取密钥)
*/
async connect(): Promise<void> {
const keys = keyService.getApiKeys();
if (!keys) {
throw new Error('未配置星云密钥');
}
const { xmovAppId, xmovAppSecret } = keys;
// 等待SDK加载完成
await this.waitForSDK();
// 如果已有实例,先销毁
if (this.sdkInstance) {
this.sdkInstance.destroy();
}
useAvatarStore.getState().setStatus('connecting');
// 创建SDK实例
this.sdkInstance = new window.XmovAvatar({
containerId: '#avatar-container',
appId: xmovAppId,
appSecret: xmovAppSecret,
gatewayServer: 'https://nebula-agent.xingyun3d.com/user/v1/ttsa/session',
enableLogger: true,
onMessage: (message: any) => {
console.log('[Avatar] SDK Message:', message);
if (message.code !== 0) {
useAvatarStore.getState().setError(message.message || 'SDK错误');
}
},
onStateChange: (state: string) => {
console.log('[Avatar] State Change:', state);
},
onStatusChange: (status: any) => {
console.log('[Avatar] Status Change:', status);
},
onVoiceStateChange: (voiceStatus: string) => {
console.log('[Avatar] Voice Status:', voiceStatus);
},
onNetworkInfo: (networkInfo: any) => {
console.log('[Avatar] Network Info:', networkInfo);
}
});
try {
// 初始化SDK
await this.sdkInstance.init({
onDownloadProgress: (progress: number) => {
console.log(`[Avatar] Download Progress: ${progress}%`);
},
onError: (error: any) => {
console.error('[Avatar] Init Error:', error);
this.isConnected = false;
useAvatarStore.getState().setError(error.message || '初始化失败');
},
onClose: () => {
console.log('[Avatar] Connection closed');
this.isConnected = false;
useAvatarStore.getState().setStatus('disconnected');
}
});
// 连接成功,更新状态
this.isConnected = true;
useAvatarStore.getState().setSdkInstance(this.sdkInstance);
useAvatarStore.getState().setStatus('connected');
console.log('[Avatar] Connected successfully');
} catch (error: any) {
console.error('[Avatar] Connect failed:', error);
useAvatarStore.getState().setError(error.message || '连接失败');
throw error;
}
}
/**
* 文本播报
*/
speak(options: SpeakOptions): void {
if (!this.sdkInstance || !this.isConnected) {
throw new Error('数字人未连接');
}
const { text, isStart = true, isEnd = true } = options;
this.sdkInstance.speak(text, isStart, isEnd);
console.log('[Avatar] Speaking:', text);
}
/**
* 切换到待机状态
*/
idle(): void {
if (this.sdkInstance && this.isConnected) {
this.sdkInstance.idle();
}
}
/**
* 切换到倾听状态
*/
listen(): void {
if (this.sdkInstance && this.isConnected) {
this.sdkInstance.listen();
}
}
/**
* 切换到思考状态
*/
think(): void {
if (this.sdkInstance && this.isConnected) {
this.sdkInstance.think();
}
}
}
export default new AvatarController();
上述代码是项目中真实的SDK控制器实现。关键点说明:
- containerId:数字人渲染的DOM容器ID,值为#avatar-container
- gatewayServer:魔珐星云的网关服务器地址
- onMessage/onStateChange/onVoiceStateChange:各种事件回调,用于状态监控
- speak():文本播报方法,isStart和isEnd参数用于分段播报控制
- idle()/listen()/think():状态切换方法,让数字人呈现不同姿态
5.2 数字人状态管理
使用Zustand进行轻量级状态管理,

以下是项目中的真实实现源码:
// src/client/store/avatarStore.ts
import { create } from 'zustand';
export type ConnectionStatus = 'disconnected' | 'connecting' | 'connected' | 'error';
interface AvatarState {
// 连接状态
status: ConnectionStatus;
errorMessage: string;
// SDK实例
sdkInstance: any;
// 动作
setStatus: (status: ConnectionStatus) => void;
setError: (message: string) => void;
setSdkInstance: (instance: any) => void;
// 连接控制
disconnect: () => void;
}
export const useAvatarStore = create<AvatarState>()((set) => ({
status: 'disconnected',
errorMessage: '',
sdkInstance: null,
setStatus: (status) => set({ status, errorMessage: '' }),
setError: (errorMessage) => set({ status: 'error', errorMessage }),
setSdkInstance: (sdkInstance) => set({ sdkInstance }),
disconnect: () => {
set({
status: 'disconnected',
sdkInstance: null,
errorMessage: ''
});
}
}));
状态管理非常简洁,只维护三个核心状态:
- status:连接状态(disconnected/connecting/connected/error)
- errorMessage:错误信息
- sdkInstance:SDK实例引用
5.3 数字人容器组件
React组件封装数字人展示区域

以下是项目中的真实实现源码:
// src/client/components/Avatar/AvatarContainer.tsx
import React, { useRef, useEffect, useState } from 'react';
import { useAvatarStore } from '../../store/avatarStore';
import AvatarController from './AvatarController';
export const AvatarContainer: React.FC = () => {
const containerRef = useRef<HTMLDivElement>(null);
const { status, errorMessage } = useAvatarStore();
const [isConnecting, setIsConnecting] = useState(false);
const handleConnect = async () => {
setIsConnecting(true);
try {
await AvatarController.connect();
} catch (error) {
console.error('[AvatarContainer] Connect failed:', error);
} finally {
setIsConnecting(false);
}
};
// 组件卸载时清理
useEffect(() => {
return () => {
AvatarController.dispose();
};
}, []);
return (
<div className="relative h-full">
{/* 数字人渲染容器 */}
<div
id="avatar-container"
ref={containerRef}
className="w-full h-full bg-black/20 rounded-2xl overflow-hidden"
/>
{/* 未连接时显示连接按钮 */}
{status === 'disconnected' && (
<div className="absolute inset-0 flex items-center justify-center">
<button
onClick={handleConnect}
disabled={isConnecting}
className="flex items-center gap-2 px-8 py-4 rounded-full font-medium transition-all bg-blue-500/80 hover:bg-blue-500 text-white disabled:opacity-50 text-lg"
>
<span>{isConnecting ? '⏳' : '🔗'}</span>
<span>{isConnecting ? '连接中...' : '连接数字人'}</span>
</button>
</div>
)}
{/* 连接中状态 */}
{status === 'connecting' && (
<div className="absolute inset-0 flex items-center justify-center bg-black/30 rounded-2xl">
<div className="text-center text-white">
<div className="animate-spin text-5xl mb-3">⚙️</div>
<p className="text-lg">正在连接数字人...</p>
</div>
</div>
)}
{/* 错误状态 */}
{status === 'error' && (
<div className="absolute inset-0 flex items-center justify-center bg-black/50 rounded-2xl">
<div className="text-center">
<div className="text-5xl mb-3">⚠️</div>
<p className="text-red-400 text-lg mb-4">连接失败</p>
{errorMessage && (
<p className="text-white text-sm mb-4">{errorMessage}</p>
)}
<button
onClick={handleConnect}
className="px-6 py-2 bg-blue-500/80 hover:bg-blue-500 text-white rounded-full text-sm"
>
重试
</button>
</div>
</div>
)}
</div>
);
};
组件实现了完整的连接状态UI:
- disconnected:显示"连接数字人"按钮
- connecting:显示加载动画
- connected:数字人正常显示
- error:显示错误信息和重试按钮
6. 核心实现:AI数据生成
6.1 数据结构设计
项目中定义了完整的业务数据结构:

以下是项目中的真实实现源码:
// src/server/services/aiDataGenerator.ts
/**
* 场景类型定义
*/
export type ScenarioType = 'normal' | 'promotion' | 'off_season' | 'anomaly';
/**
* 指标数据
*/
export interface MetricData {
name: string;
value: number;
previousValue: number;
change: number;
changePercent: number;
unit: string;
trend: 'up' | 'down' | 'stable';
}
/**
* 趋势数据点
*/
export interface TrendPoint {
timestamp: number;
value: number;
}
/**
* 地区数据
*/
export interface RegionalData {
name: string;
value: number;
changePercent: number;
}
/**
* 产品分类数据
*/
export interface ProductData {
name: string;
revenue: number;
margin: number;
share: number;
}
/**
* 预警数据
*/
export interface AlertData {
level: 'info' | 'warning' | 'critical';
message: string;
}
/**
* AI生成数据响应
*/
export interface AIGeneratedData {
metrics: MetricData[];
trend: TrendPoint[];
regionalData: RegionalData[];
productData: ProductData[];
insight: string;
suggestion: string;
alerts: AlertData[];
}
数据结构涵盖了BI大屏需要的所有数据类型:
- metrics:7个核心指标(营业收入、订单量、毛利率、活跃用户、转化率、客单价、复购率)
- trend:12小时趋势数据
- regionalData:4个地区数据
- productData:4个产品数据
- insight:数据洞察
- suggestion:业务建议
- alerts:预警信息
6.2 AI数据生成服务
项目中的AI数据生成服务实现如下:
// src/server/services/aiDataGenerator.ts(核心部分)
export class AIDataGeneratorService {
private baseURL: string = 'https://api-inference.modelscope.cn/v1';
/**
* 生成AI数据
*/
async generateData(
request: DataGenerateRequest,
apiKey: string
): Promise<AIGeneratedData> {
const { scenario, previousData } = request;
// 构建场景描述
const scenarioDesc = this.getScenarioDescription(scenario);
// 构建Prompt
const prompt = this.buildPrompt(scenarioDesc, previousData);
try {
// 调用魔搭AI
const response = await axios.post(
`${this.baseURL}/chat/completions`,
{
model: 'deepseek-ai/DeepSeek-V3.2',
messages: [
{
role: 'system',
content: '你是一个专业的BI数据模拟器。你生成的所有数据都必须是真实的、合理的、符合业务逻辑的。严格按照用户要求的格式返回JSON数据。'
},
{ role: 'user', content: prompt }
],
temperature: 0.8,
max_tokens: 2000
},
{
headers: {
'Authorization': `Bearer ${apiKey}`,
'Content-Type': 'application/json'
},
timeout: 120000 // 2分钟超时
}
);
// 解析AI返回的内容
const content = response.data.choices[0].message.content;
return this.parseAIResponse(content);
} catch (error: any) {
console.error('[AIDataGenerator] AI调用失败:', error);
// 如果AI调用失败,返回基于规则的降级数据
return this.getFallbackData(scenario, previousData);
}
}
/**
* 获取场景描述
*/
private getScenarioDescription(scenario: ScenarioType): string {
const descriptions: Record<ScenarioType, string> = {
normal: '常规运营状态,业务平稳发展,各项指标在小幅范围内正常波动,整体呈现缓慢上升趋势。',
promotion: '正在开展大型营销活动,市场反响热烈,各项指标出现明显增长,客流量和销售额大幅提升。',
off_season: '处于销售淡季,市场需求相对疲软,各项指标有所下降,需要在降本增效上下功夫。',
anomaly: '出现突发异常情况(如系统故障、供应链问题等),导致数据出现异常波动,需要紧急处理。'
};
return descriptions[scenario];
}
}
关键配置说明:
- model:使用魔搭社区的deepseek-ai/DeepSeek-V3.2模型
- temperature:设置为0.8,在保证合理性的同时有一定的随机性
- max_tokens:设置为2000,确保能生成完整的数据结构
- timeout:120秒超时,给AI足够的生成时间
6.3 数据生成API路由
后端API路由实现,包含智能降级逻辑:

以下是项目中的真实实现源码:
// src/server/routes/data.routes.ts
import express from 'express';
import aiDataGeneratorService from '../services/aiDataGenerator';
import enhancedDataGenerator from '../services/enhancedDataGenerator';
const router = express.Router();
/**
* POST /api/data/generate
*
* 生成业务数据(优先使用增强生成器,AI失败时自动降级)
*/
router.post('/generate', async (req, res) => {
try {
const { scenario, scenarioDescription, previousData, useAI = true } = req.body;
// 验证scenario
const validScenarios = ['normal', 'promotion', 'off_season', 'anomaly'];
if (!scenario || !validScenarios.includes(scenario)) {
return res.status(400).json({
success: false,
error: '无效的场景类型'
});
}
let data;
// 尝试使用AI生成
if (useAI) {
const apiKey = req.headers['x-modelscope-api-key'] as string;
if (!apiKey) {
// 没有API密钥,使用增强生成器
console.log('[DataAPI] No API key, using enhanced generator');
data = enhancedDataGenerator.generateData(scenario, previousData);
return res.json({ success: true, data, source: 'enhanced' });
}
try {
// 尝试AI生成,设置超时
data = await Promise.race([
aiDataGeneratorService.generateData({ scenario, previousData }, apiKey),
new Promise((_, reject) =>
setTimeout(() => reject(new Error('AI timeout')), 120000)
)
] as any);
return res.json({ success: true, data, source: 'ai' });
} catch (aiError) {
console.log('[DataAPI] AI generation failed, using enhanced generator');
// AI失败,使用增强生成器
data = enhancedDataGenerator.generateData(scenario, previousData);
return res.json({ success: true, data, source: 'enhanced' });
}
}
// 默认使用增强生成器
data = enhancedDataGenerator.generateData(scenario, previousData);
res.json({ success: true, data, source: 'enhanced' });
} catch (error: any) {
console.error('[DataAPI] Generate error:', error);
res.status(500).json({ success: false, error: error.message });
}
});
/**
* GET /api/data/scenarios
*
* 获取可用的场景列表
*/
router.get('/scenarios', (req, res) => {
res.json({
success: true,
scenarios: [
{ value: 'normal', label: '常规运营', description: '业务平稳发展,小幅增长' },
{ value: 'promotion', label: '营销活动', description: '促销带来数据大幅上升' },
{ value: 'off_season', label: '销售淡季', description: '市场需求疲软,数据下降' },
{ value: 'anomaly', label: '特殊事件', description: '突发情况导致数据异常' }
]
});
});
export default router;
API设计的关键点:
- 智能降级:AI失败时自动切换到增强生成器,确保服务可用
- 超时控制:使用Promise.race实现120秒超时
- source字段:返回数据来源(ai/enhanced),便于调试
7. 核心实现:智能对话服务
7.1 对话服务设计
项目中的对话服务实现了流式响应和降级响应:

以下是项目中的真实实现源码:
// src/server/services/chatService.ts
export class ChatService {
private baseURL = 'https://api-inference.modelscope.cn/v1';
private model = 'deepseek-ai/DeepSeek-V3.2';
/**
* 构建系统提示词
*/
private buildSystemPrompt(currentData?: any): string {
let prompt = `你是一个专业的BI数据讲解助手,名为"小数据"。
你的职责:
1. 解读和讲解企业BI业务数据
2. 用通俗易懂的语言解释复杂数据
3. 发现数据中的趋势和异常
4. 回答用户关于数据的各种问题
5. 提供数据洞察和决策建议
讲解风格:
- 专业但不晦涩,善于用比喻解释数据
- 数据敏感,能快速发现异常和趋势
- 主动分享有价值的洞察
- 回答简洁明了,通常不超过3句话`;
if (currentData) {
prompt += `\n\n当前业务数据概况:\n`;
prompt += `场景:${currentData.scenario || '常规运营'}\n`;
if (currentData.metrics && Array.isArray(currentData.metrics)) {
prompt += `\n【核心指标】\n`;
currentData.metrics.slice(0, 7).forEach((m: any) => {
const trendIcon = m.changePercent > 0 ? '↑' : m.changePercent < 0 ? '↓' : '→';
prompt += `- ${m.name}: ${m.value.toLocaleString()}${m.unit} (${trendIcon}${Math.abs(m.changePercent).toFixed(2)}%)\n`;
});
}
if (currentData.alerts && currentData.alerts.length > 0) {
prompt += `\n【当前预警】\n`;
currentData.alerts.forEach((alert: any) => {
prompt += `- [${alert.level}] ${alert.message}\n`;
});
}
}
return prompt;
}
/**
* 流式对话
*/
async *chatStream(request: ChatRequest): AsyncGenerator<string> {
const { message, conversationHistory = [], currentData, apiKey } = request;
// 构建消息列表
const messages = [
{ role: 'system', content: this.buildSystemPrompt(currentData) },
...conversationHistory.slice(-10), // 最近10条历史
{ role: 'user', content: message }
];
try {
const response = await axios.post(
`${this.baseURL}/chat/completions`,
{
model: this.model,
messages: messages.map(m => ({ role: m.role, content: m.content })),
temperature: 0.7,
max_tokens: 1000,
stream: true // 启用流式输出
},
{
headers: {
'Authorization': `Bearer ${apiKey}`,
'Content-Type': 'application/json'
},
responseType: 'stream',
timeout: 30000
}
);
const stream = response.data;
for await (const chunk of stream) {
const lines = chunk.toString().split('\n').filter((line: string) => line.trim() !== '');
for (const line of lines) {
if (line.startsWith('data: ')) {
const data = line.slice(6);
if (data === '[DONE]') return;
try {
const parsed = JSON.parse(data);
const content = parsed.choices[0]?.delta?.content;
if (content) {
yield content;
}
} catch (e) {
// 忽略解析错误
}
}
}
}
} catch (error: any) {
console.error('[ChatService] Stream error:', error);
// AI失败时返回降级响应
const fallbackResponse = this.getFallbackResponse(message, currentData);
yield fallbackResponse;
}
}
}
对话服务的关键设计:
- 动态系统提示词:根据当前数据动态构建,包含所有指标、预警、洞察
- 流式输出:使用stream: true和AsyncGenerator实现打字机效果
- 历史消息限制:只保留最近10条历史,控制Token消耗
- 降级响应:AI失败时返回基于关键词匹配的响应
7.2 降级响应实现
当AI服务不可用时,使用关键词匹配提供基础回答:
// src/server/services/chatService.ts(降级响应部分)
private getFallbackResponse(message: string, currentData?: any): string {
const lowerMessage = message.toLowerCase();
// 关于营收
if (lowerMessage.includes('营收') || lowerMessage.includes('收入')) {
const revenue = currentData?.metrics?.find((m: any) => m.name === '营业收入');
if (revenue) {
const trend = revenue.changePercent > 0 ? '增长' : revenue.changePercent < 0 ? '下降' : '持平';
return `当前营业收入为${revenue.value.toLocaleString()}元,较上期${trend}${Math.abs(revenue.changePercent).toFixed(2)}%。`;
}
}
// 关于地区
if (lowerMessage.includes('地区') || lowerMessage.includes('区域')) {
if (currentData?.regionalData && currentData.regionalData.length > 0) {
const topRegion = currentData.regionalData[0];
return `${topRegion.name}表现最好,营收为${topRegion.value.toLocaleString()}元,增长${topRegion.changePercent.toFixed(2)}%。`;
}
}
// 关于产品
if (lowerMessage.includes('产品') || lowerMessage.includes('品类')) {
if (currentData?.productData && currentData.productData.length > 0) {
const topProduct = currentData.productData[0];
return `${topProduct.name}营收最高,为${topProduct.revenue.toLocaleString()}元,毛利率${topProduct.margin.toFixed(2)}%。`;
}
}
// 关于预警
if (lowerMessage.includes('预警') || lowerMessage.includes('异常')) {
const alerts = currentData?.alerts || [];
if (alerts.length > 0) {
return `当前有${alerts.length}条预警:${alerts.map((a: any) => a.message).join(';')}`;
}
return '当前各项指标正常,无预警信息。';
}
// 默认响应
if (currentData?.insight) {
return currentData.insight;
}
return '抱歉,我暂时无法回答这个问题。请确保已配置有效的魔搭API密钥。';
}
降级响应覆盖了常见的业务问题:
- 营收/收入查询
- 地区/区域表现
- 产品/品类分析
- 预警/异常信息
- 默认返回数据洞察
8. 前端应用集成
8.1 主应用组件
前端主应用整合了所有功能模块

以下是项目中的真实实现(核心部分):
// src/client/App.tsx(核心部分)
function App() {
const { isConfigured, setConfigured } = useKeyStore();
const { status } = useAvatarStore();
const [currentScenario, setCurrentScenario] = useState<string>('normal');
const [aiData, setAiData] = useState<AIGeneratedData | null>(null);
const [viewMode, setViewMode] = useState<ViewMode>('overview');
// 数字人播报
const handleAvatarSpeak = (text: string) => {
if (status === 'connected') {
try {
AvatarController.speak({ text });
} catch (error) {
console.error('[Avatar] Speak error:', error);
}
}
};
// 生成播报内容
const generateBroadcastContent = (): string => {
if (!aiData || !aiData.metrics) return '暂无数据可播报';
const metrics = aiData.metrics;
const revenue = metrics.find(m => m.name === '营业收入');
const margin = metrics.find(m => m.name === '毛利率');
const users = metrics.find(m => m.name === '活跃用户');
let content = '现在为您播报本次业务数据概况。';
if (revenue) {
const trend = revenue.changePercent > 0 ? '增长' : '下降';
content += `营业收入为${(revenue.value / 10000).toFixed(0)}万元,较上期${trend}${Math.abs(revenue.changePercent).toFixed(2)}%。`;
}
if (margin) {
content += `毛利率为${margin.value.toFixed(2)}%。`;
}
if (users) {
content += `活跃用户数为${users.value.toLocaleString()}人。`;
}
// 预警播报(最多2条)
if (aiData.alerts && aiData.alerts.length > 0) {
content += `需要注意的是,`;
aiData.alerts.slice(0, 2).forEach((alert, index) => {
content += alert.message;
if (index < Math.min(aiData.alerts.length, 2) - 1) {
content += ';';
}
});
content += '。';
}
if (aiData.insight) {
content += aiData.insight;
}
content += '播报完毕。';
return content;
};
// 生成数据并播报
const generateData = async (scenario: string, speak: boolean = true) => {
const data = await dataService.generateData({
scenario: scenario as any,
useAI: true,
previousData: previousData ? { metrics: previousData.metrics } : undefined
});
setAiData(data);
// 自动播报数据摘要
if (speak && data.insight) {
setTimeout(() => {
handleAvatarSpeak(`数据更新完毕。${data.insight}`);
}, 1000);
}
};
return (
<DashboardLayout>
<div className="h-full flex gap-3">
{/* 主要内容区 - 占4/6 */}
<div className="w-[66.666%]">
{/* 场景切换 */}
<ScenarioSwitcher
onScenarioChange={handleScenarioChange}
currentScenario={currentScenario}
/>
{/* 指标卡片 */}
<div className="grid grid-cols-4 gap-3">
{aiData?.metrics.slice(0, 8).map((metric, index) => (
<MetricCard
key={index}
title={metric.name}
value={metric.value}
unit={metric.unit}
change={metric.changePercent}
icon={iconMap[metric.name]}
/>
))}
</div>
{/* 图表区域 */}
{viewMode === 'overview' && (
<div className="grid grid-cols-3 gap-4">
<TrendChart data={aiData?.trend} />
<GaugeChart value={calculateTargetCompletion()} />
</div>
)}
</div>
{/* 数字人区域 - 占2/6 */}
<div className="w-[33.333%]">
<AvatarContainer />
{/* 播报按钮 */}
{status === 'connected' && (
<button onClick={handleBroadcast}>
📢 开始播报
</button>
)}
</div>
</div>
</DashboardLayout>
);
}
前端应用的核心流程:
- 初始化:检查密钥配置,连接数字人
- 场景切换:触发数据生成,自动播报洞察
- 数据展示:7个指标卡片 + 趋势图 + 仪表盘
- 播报控制:手动播报完整摘要
8.2 大屏布局适配
项目实现了响应式大屏布局:

以下是项目中的真实实现源码:
// src/client/hooks/useScale.ts
import { useState, useEffect } from 'react';
export const useScale = () => {
const [scale, setScale] = useState(1);
useEffect(() => {
const updateScale = () => {
const width = window.innerWidth;
const height = window.innerHeight;
const targetWidth = 1920;
const targetHeight = 1080;
const scaleX = width / targetWidth;
const scaleY = height / targetHeight;
const newScale = Math.min(scaleX, scaleY);
setScale(newScale);
};
updateScale();
window.addEventListener('resize', updateScale);
return () => window.removeEventListener('resize', updateScale);
}, []);
return scale;
};
布局适配方案:
- 设计尺寸:1920x1080(16:9)
- 缩放策略:保持宽高比,取较小的缩放值
- 响应式:监听窗口resize事件,动态调整
9. 落地场景与效果展示
9.1 企业展厅场景

在企业展厅中,BI数据讲解智能体可以:
|
功能 |
效果 |
价值 |
|
主动讲解 |
访客进入展厅,数字人自动介绍企业运营数据 |
提升参观体验 |
|
互动问答 |
访客询问"今年增长情况?",数字人即时回答 |
增强互动性 |
|
场景切换 |
切换到"营销活动"场景,展示促销效果 |
展示多维度 |
9.2 指挥中心场景
在运营指挥中心,智能体可以:

9.3 效果展示

9.4 产品竞争力对比(创业核心)
| 维度 | 传统云端大屏产品 | 端侧 Agent 大屏产品(创业优选) |
| 产品体验 | 延迟高、卡顿 | 毫秒响应、实时交互 |
| 产品成本 | 高(云端计费) | 低(端侧免费) |
| 落地周期 | 长(强网 + 定制) | 短(1 天部署) |
| 产品差异化 | 弱(同质化 Demo) | 强(端侧交互壁垒) |
| 盈利空间 | 薄(成本高) | 厚(低成本高毛利) |
10. 常见问题与解决方案
Q1:数字人连接失败怎么办?
原因分析:
- App ID或App Secret配置错误
- 网络无法访问魔珐星云服务
- 浏览器不支持WebGL
解决方案:
检查密钥配置,确保从星云控制台获取正确的App ID和App Secret。检查网络连接,确保能访问https://nebula-agent.xingyun3d.com。检查浏览器支持,建议使用Chrome/Firefox/Edge最新版本。
Q2:AI数据生成超时怎么办?
原因分析:
- 模型推理时间过长
- 网络请求超时
- API服务繁忙
解决方案:
项目已内置降级机制,AI失败时自动使用增强生成器,确保服务可用。建议设置合理的超时时间(项目中设置为120秒),并实现重试机制。
Q3:如何扩展更多场景?
扩展方式:
在aiDataGenerator.ts中添加新的场景类型和描述,在enhancedDataGenerator.ts中添加对应的降级数据生成逻辑。项目已预留scenarioDescription参数支持自定义场景。
11. 总结:创业破局,做可商业化的 Agent 大屏产品
对创业者而言,企业大屏赛道的机会,从来不是做好看的 Demo,而是做能落地、能赚钱、能规模化的产品。传统云端方案,体验差、成本高、落地难,是创业陷阱;而端侧 Agent,强体验、低成本、易部署,是破局关键。依托端侧 Agent 打造大屏交互产品,既能解决 B 端客户核心痛点,又能构建产品差异化壁垒,实现从 0 到 1 快速落地、从 1 到 N 规模化盈利 —— 这才是企业级 Agent 产品的正确创业路径。
魔珐星云官网:https://xingyun3d.com/?utm_campaign=daily&utm_source=jixinghuiKoc149
文章出自:七夜zippoe
原文链接:https://blog.csdn.net/sinat_41617212/article/details/161080860
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐





所有评论(0)