码道英语短句AI情景会话台

码道英语短句AI情景会话台
一个基于情景对话练习英语口语的零依赖 Web 应用。AI 扮演情景中的角色(咖啡师、地勤、前台……),用一句句地道短句带你在真实场景里开口说英语;每句回复都自动配好中文翻译、音标、重点词拆解、口语贴士与接话建议,并支持一键朗读与收藏复读。
纯前端实现:HTML5 + CSS3 + JavaScript,无需构建,直接打开即可使用。
功能特性
- 情景化角色扮演:内置 6 个高频生活情景(咖啡店、机场、酒店、餐厅、问路、面试),也支持自定义任意情景
- JSON 结构化回复:AI 每次回复返回固定结构的 JSON,前端按「英文原句 → 中文翻译 → 音标 → 重点词 → 口语贴士 → 接话建议」分层渲染
- 流式渐进刷新:SSE 流式输出,英文原句先浮现,随后各字段逐块补齐,等待感为零
- 语音增强:
- 朗读:
speechSynthesis朗读英文原句(en-US 音色) - 语音输入:
Web Speech API语音识别,说完自动上屏
- 朗读:
- 收藏夹:收藏地道短句,持久化到
localStorage,支持朗读 / 复制 / 移除 - 完整交互状态:空状态引导、骨架屏加载、错误内联提示、Toast 反馈
- 自适应布局:桌面双栏沉浸式、移动端单列降级
技术栈
| 层次 | 方案 |
|---|---|
| 页面结构 | HTML5 语义化标签 |
| 样式 | CSS3 原生(CSS 变量、Grid、渐变、微动效),未引入任何 UI 框架 |
| 逻辑 | 原生 JavaScript(Fetch API + ReadableStream 流式读取 + async generator) |
快速开始
方式一:直接打开
用浏览器打开 index.html 即可,无需任何服务器。
方式二:本地 HTTP 服务(推荐)
# 任意静态服务器皆可
python3 -m http.server 8080 --directory .
# 然后访问 http://localhost:8080
语音输入(麦克风)仅在
https或localhost环境下可用。
配置说明
所有接口参数集中在 js/config.js:
const CONFIG = {
API_URL: "https://api-ai.gitcode.com/v1/chat/completions",
API_KEY: "你的 API Key",
MODEL: "deepseek-ai/DeepSeek-V4-Flash",
PARAMS: {
stream: true,
max_tokens: 2048,
temperature: 0.6,
top_p: 0.95,
frequency_penalty: 0,
thinking_budget: 2048
}
};
⚠️ 安全提醒:纯前端项目无法隐藏
API_KEY。演示场景直接使用即可;
生产环境务必改为「前端 → 你的后端代理 → 大模型 API」的架构,避免密钥泄露。
AI 回复 JSON 协议
系统提示词(见 js/config.js 的 SYSTEM_PROMPT)要求 AI 只输出一个纯 JSON 对象,禁止任何多余文字,结构如下:
{
"speaker": "Barista",
"speaker_cn": "咖啡师",
"reply": "Hi there! What can I get started for you today?",
"translation": "你好!今天想喝点什么?",
"phonetic": "/haɪ ðeər | wɒt kæn aɪ get ˈstɑːtɪd fə jə təˈdeɪ/",
"keywords": [
{ "word": "get started", "meaning": "开始,先来点什么" },
{ "word": "for you", "meaning": "为你" }
],
"tip": "咖啡店常用开场白,比 order 更口语、亲切。",
"suggestion": "你可以回答:I'd like a latte, please. 或者先问推荐。",
"suggestion_en": "You can say: I'd like a latte, please.",
"done": false
}
| 字段 | 说明 |
|---|---|
speaker / speaker_cn | 当前说话的角色(中/英文名) |
reply | AI 角色的这句地道英语 |
translation | 中文翻译 |
phonetic | 参考国际音标 |
keywords | 本句重点词/短语及释义(1~3 个) |
tip | 口语贴士(中文,≤40 字) |
suggestion / suggestion_en | 引导学员接话的中文建议 + 英文提示 |
done | 学员表示结束时置 true,AI 道别收尾 |
渐进式 JSON 渲染
流式返回的是不断增量的 JSON 文本,前端并不等它完全结束,而是通过 tryParseJson() 实时尝试解析:
从文本尾部倒序扫描
},取最后一个合法完整的 JSON 前缀进行渲染。
因此用户会先看到英文突然浮现,随后翻译、音标、关键词、贴士逐块补齐,体验接近打字机效果,且不需要等待完整响应。
目录结构
.
├── index.html # 页面结构
├── css/
│ └── style.css # 全部样式(变量 / Grid / 动效)
├── js/
│ ├── config.js # API 配置 + 系统提示词(JSON 协议)
│ ├── api.js # 流式请求封装(Python 参考代码的 JS 移植)
│ └── app.js # 应用逻辑(情景 / 对话 / 渲染 / 语音 / 收藏)
├── e2e_test.py # Playwright 端到端验证脚本(可选)
└── README.md
Python 参考代码 → JavaScript 对照
原始 Python 通过 requests 的流式接口逐行消费 SSE 帧:
response = requests.post(API_URL, headers=headers, json=payload, stream=True)
for line in response.iter_lines():
if not line.startswith(b"data:"):
continue
if line.strip() == b"data:[DONE]":
return
yield json.loads(line.decode("utf-8").lstrip("data:").rstrip("/n"))
js/api.js 中用 fetch + ReadableStream 实现了完全等价的能力:
const response = await fetch(CONFIG.API_URL, {
method: "POST",
headers: { "Content-Type": "application/json", Authorization: `Bearer ${CONFIG.API_KEY}` },
body: JSON.stringify(payload),
signal: options.signal // 支持中止
});
const reader = response.body.getReader(); // ReadableStream
const decoder = new TextDecoder("utf-8");
// 按行扫描 "data:" 前缀 → 跳过空行 → "[DONE]" 结束 → 逐帧 yield
调用方以 async generator 形式消费:
for await (const chunk of chatStream(buildPayload(messages))) {
const delta = chunk.choices[0].delta.content; // 累积增量文本
}
本地测试
准备好 Python3 + Playwright 后可跑端到端验证(会真实调用一次 API,消耗少量配额):
python3 -m http.server 8123 --directory . & # 先起服务
python3 e2e_test.py
脚本会依次断言:情景渲染 → 高亮 → AI 开场(流式)→ 结构化字段 → 两轮对话 → 收藏 → 收藏面板 → 情景切换重置,并收集 console 错误。
已知说明
- 语音朗读与语音输入依赖浏览器能力(Chrome / Edge / Safari 支持较好)。
- 收藏数据保存在当前浏览器
localStorage,跨设备不共享。 - API 为 OpenAI 兼容格式,替换
API_URL、API_KEY、MODEL即可接入其它同协议服务。
更多推荐



所有评论(0)