Skip to content

PlotChoiceGenerator 选择生成器

字数
805 字
阅读时间
4 分钟

AI 驱动的剧情分支选择生成器,每轮调用 LLM 生成 3 个不同级别的选择项。

基本用法

python
from nbot.plot import PlotChoiceGenerator

generator = PlotChoiceGenerator()
choices = await generator.generate(
    response_text=ai_reply,
    turn_context={"mood": "happy", "relationship": "好感度75"},
    session_context={"recent_topics": ["天气", "动漫"], "current_arc": "校园日常"},
    recent_history=[{"role": "user", "content": "..."}, {"role": "assistant", "content": "..."}],
    session_id="sess_abc",
)
# 返回: [{"level": "normal", "text": "...", "intent": "..."}, ...]

参数

参数类型说明
response_textstrAI 角色的回复文本
turn_contextdict当前轮次上下文(mood, relationship 等)
session_contextdict会话级别上下文(recent_topics, current_arc)
recent_historylist[dict]最近几轮对话 [{role, content}, ...],用于避免重复
session_idstr会话 ID,用于 token 统计

选择生成规则

三个级别

级别推进力度说明
normal小步顺势推进,带出新细节或下一步动作
important中步主动开辟新话题、转移场景或推进关系
turning_point大步时间跳跃、突发事件、新人物或重大决定

核心铁律

每个选择必须引入「上一轮还不存在的新东西」,从以下至少一类取材:

  • 新的行动目标或动作
  • 尚未聊过的新话题
  • 场景或地点转移
  • 时间推移或跳跃
  • 新出场人物或关系进展
  • 突发外部事件

严禁「原地打转」的写法:复述角色刚说过的话、反复追问同一件事、停留在同一场景情绪中纠缠。

文本要求

  • 必须使用第一人称或直接动作("我拉起你往门外走")
  • 禁止元指令句式("告诉她……""问她是否……")
  • 禁止第三人称描述("她/他/角色/玩家")
  • 建议 8-24 字

文本规范化(_normalize_choice_text)

自动将 AI 生成的元指令转换为第一人称可发送消息:

AI 输出转换后
"告诉她你想去看电影""我想告诉你,想去看电影"
"问她是否愿意一起去""我想问你,是否愿意一起去"
"向她表达你的感受""我想对你说,我的感受"
"握住她的手""我握住你的手"

转换规则:

  1. 前缀替换("告诉她" → "我想告诉你,")
  2. 代词替换("她的" → "你的","她" → "你")
  3. 动作前缀补 "我"("握住" → "我握住")

错误回退

AI 无响应或解析失败时,回退到默认选择:

python
_DEFAULT_CHOICES = [
    {"level": "normal", "text": "我拉起你,说走,带你去个地方。", "intent": "顺势推进"},
    {"level": "important", "text": "对了,我一直想跟你聊聊另一件事。", "intent": "主动开辟新话题"},
    {"level": "turning_point", "text": "几天后,我带着一个没人知道的消息回来找你。", "intent": "时间跳跃+突发事件"},
]

AI 调用

使用 ai_client.chat_completion() 发送请求,system prompt 包含完整的分支设计指令。token 用量通过 token_stats 模块记录(purpose: PURPOSE_PLOT)。

页面历史