Merge branch 'staging' into neo-server

This commit is contained in:
Cohee 2024-04-11 21:47:10 +03:00
commit 31ba3cf039
13 changed files with 894 additions and 642 deletions

View File

@ -1763,6 +1763,19 @@
<span data-i18n="Use the appropriate tokenizer for Google models via their API. Slower prompt processing, but offers much more accurate token counting.">Use the appropriate tokenizer for Google models via their API. Slower prompt processing, but offers much more accurate token counting.</span>
</div>
</div>
<div class="range-block" data-source="makersuite">
<label for="use_makersuite_sysprompt" class="checkbox_label widthFreeExpand">
<input id="use_makersuite_sysprompt" type="checkbox" />
<span data-i18n="Use system prompt (Gemini 1.5 pro+ only)">
Use system prompt (Gemini 1.5 pro+ only)
</span>
</label>
<div class="toggle-description justifyLeft marginBot5">
<span data-i18n="Merges all system messages up until the first message with a non system role, and sends them through google's system_instruction field instead of with the rest of the prompt contents.">
Merges all system messages up until the first message with a non system role, and sends them through google's system_instruction field instead of with the rest of the prompt contents.
</span>
</div>
</div>
<div data-newbie-hidden class="range-block" data-source="claude">
<div class="wide100p">
<span id="claude_assistant_prefill_text" data-i18n="Assistant Prefill">Assistant Prefill</span>
@ -2249,7 +2262,7 @@
</div>
<div class="flex-container">
<div id="api_button_textgenerationwebui" class="api_button menu_button" type="submit" data-i18n="Connect" data-server-connect="ooba_blocking,aphrodite,tabby,koboldcpp">Connect</div>
<div data-tg-type="openrouter" class="menu_button menu_button_icon openrouter_authorize" title="Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai" data-i18n="[title]Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai">Authorize</div>
<div data-tg-type="openrouter" class="menu_button menu_button_icon openrouter_authorize" title="Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai" data-i18n="Authorize;[title]Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai">Authorize</div>
<div class="api_loading menu_button" data-i18n="Cancel">Cancel</div>
</div>
<label data-tg-type="ooba,aphrodite" class="checkbox_label margin-bot-10px" for="legacy_api_textgenerationwebui">
@ -2339,7 +2352,7 @@
<div class="wide100p">
<input id="openai_reverse_proxy" type="text" class="text_pole" placeholder="https://api.openai.com/v1" maxlength="500" />
<small class="reverse_proxy_warning">
Doesn't work? Try adding <code>/v1</code> at the end!
<span data-i18n="Doesn't work? Try adding">Doesn't work? Try adding</span> <code>/v1</code> <span data-i18n="at the end!">at the end!</span>
</small>
</div>
<div class="range-block-title justifyLeft" data-i18n="Proxy Password">
@ -2744,7 +2757,7 @@
<div id="api_button_openai" class="api_button menu_button menu_button_icon" type="submit" data-i18n="Connect">Connect</div>
<div class="api_loading menu_button" data-i18n="Cancel">Cancel</div>
<div data-source="custom" id="customize_additional_parameters" class="menu_button menu_button_icon">Additional Parameters</div>
<div data-source="openrouter" class="menu_button menu_button_icon openrouter_authorize" title="Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai" data-i18n="[title]Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai">Authorize</div>
<div data-source="openrouter" class="menu_button menu_button_icon openrouter_authorize" title="Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai" data-i18n="Authorize;[title]Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai">Authorize</div>
<div id="test_api_button" class="menu_button menu_button_icon" title="Verifies your API connection by sending a short test message. Be aware that you'll be credited for it!" data-i18n="[title]Verifies your API connection by sending a short test message. Be aware that you'll be credited for it!"><span data-i18n="Test Message">Test Message</span></div>
</div>
<div class="online_status">
@ -4107,7 +4120,7 @@
<div id="persona_pagination_container" class="flex1"></div>
<i id="persona_grid_toggle" class="fa-solid fa-table-cells-large menu_button" data-i18n="[title]Toggle grid view" title="Toggle grid view"></i>
</div>
<div id="user_avatar_block">
<div id="user_avatar_block" data-i18n="[no_desc_text]No persona description" no_desc_text="[No description]">
<div class="avatar_upload">+</div>
</div>
<form id="form_upload_avatar" action="javascript:void(null);" method="post" enctype="multipart/form-data">
@ -4174,7 +4187,7 @@
<div class="right_menu_button fa-solid fa-list-ul" id="rm_button_characters" title="Select/Create Characters" data-i18n="[title]Select/Create Characters"></div>
</div>
<div id="HotSwapWrapper" class="alignitemscenter flex-container margin0auto wide100p">
<div class="hotswap avatars_inline flex-container expander"></div>
<div class="hotswap avatars_inline flex-container expander" data-i18n="[no_favs]Favorite characters to add them to HotSwaps" no_favs="Favorite characters to add them to HotSwaps"></div>
</div>
</div>
<hr>
@ -5857,7 +5870,7 @@
<div id="leftSendForm" class="alignContentCenter">
<div id="options_button" class="fa-solid fa-bars"></div>
</div>
<textarea id="send_textarea" data-i18n="[placeholder]Not connected to API!" placeholder="Not connected to API!" name="text"></textarea>
<textarea id="send_textarea" name="text" data-i18n="[no_connection_text]Not connected to API!;[connected_text]Type a message, or /? for help" placeholder="Not connected to API!" no_connection_text="Not connected to API!" connected_text="Type a message, or /? for help"></textarea>
<div id="rightSendForm" class="alignContentCenter">
<div id="mes_stop" title="Abort request" class="mes_stop" data-i18n="[title]Abort request">
<i class="fa-solid fa-circle-stop"></i>

File diff suppressed because it is too large Load Diff

View File

@ -4,122 +4,123 @@
"guikoboldaisettings": "KoboldAI 用户界面设置",
"novelaipreserts": "NovelAI 预设",
"default": "默认",
"openaipresets": "OpenAI 预设",
"openaipresets": "对话补全预设",
"text gen webio(ooba) presets": "WebUI(ooba) 预设",
"response legth(tokens)": "响应长度Token",
"select": "选择",
"context size(tokens)": "上下文长度Token",
"unlocked": "已解锁",
"Only select models support context sizes greater than 4096 tokens. Increase only if you know what you're doing.": "仅选择的模型支持大于 4096 个Token的上下文大小。只有在知道自己在做什么的情况下才增加。",
"Only select models support context sizes greater than 4096 tokens. Increase only if you know what you're doing.": "只有特定的模型支持超过4096 Tokens的上下文长度。仅在你清楚自己在做什么的情况下再增加这个值。",
"rep.pen": "重复惩罚",
"WI Entry Status:🔵 Constant🟢 Normal❌ Disabled": "WI 输入状态:\n🔵 恒定\n🟢 正常\n❌ 禁用",
"WI Entry Status:🔵 Constant🟢 Normal❌ Disabled": "条目输入状态:\n🔵 常开\n🟢 触发\n❌ 禁用",
"rep.pen range": "重复惩罚范围",
"Temperature controls the randomness in token selection": "温度控制Token选择中的随机性\n- 低温(<1.0导致更可预测的文本优先选择高概率的Token。\n- 高温(>1.0鼓励创造性和输出的多样性更多地选择低概率的Token。\n将值设置为 1.0 以使用原始概率。",
"temperature": "温度",
"Top K sets a maximum amount of top tokens that can be chosen from": "Top K 设置可以从中选择的顶级Token的最大数量。",
"Top P (a.k.a. nucleus sampling)": "Top P又称核心采样将所有必需的顶级Token合并到一个特定百分比中。\n换句话说如果前两个Token代表 25%,而 Top-P 为 0.50则只考虑这两个Token。\n将值设置为 1.0 以禁用。",
"Typical P Sampling prioritizes tokens based on their deviation from the average entropy of the set": "典型的 P 采样根据它们与集合平均熵的偏差对Token进行优先排序。\n保留概率累积接近指定阈值例如 0.5的Token区分包含平均信息的那些。\n将值设置为 1.0 以禁用。",
"Min P sets a base minimum probability": "Min P 设置基本最小概率。它根据顶级Token的概率进行优化。\n如果顶级Token的概率为 80%,而 Min P 为 0.1,则只考虑概率高于 8% 的Token。\n将值设置为 0 以禁用。",
"Top A sets a threshold for token selection based on the square of the highest token probability": "Top A 根据最高Token概率的平方设置Token选择的阈值。\n如果 Top A 为 0.2最高Token概率为 50%,则排除概率低于 5% 的Token0.2 * 0.5^2。\n将值设置为 0 以禁用。",
"Tail-Free Sampling (TFS)": "无尾采样TFS查找分布中概率较低的尾部Token\n 通过分析Token概率的变化率以及二阶导数。 Token保留到阈值例如 0.3),取决于统一的二阶导数。\n值越接近 0被拒绝的Token数量就越多。将值设置为 1.0 以禁用。",
"Epsilon cutoff sets a probability floor below which tokens are excluded from being sampled": "ε 截止设置了一个概率下限低于该下限的Token将被排除在样本之外。\n以 1e-4 单位;合适的值为 3。将其设置为 0 以禁用。",
"Scale Temperature dynamically per token, based on the variation of probabilities": "根据概率的变化动态地按Token缩放温度。",
"Temperature": "温度",
"Top K sets a maximum amount of top tokens that can be chosen from": "Top K 限定了可供选择的最高概率 Token 的最大数目。",
"Top P (a.k.a. nucleus sampling)": "Top P又称 nucleus sampling累加所有需要达到目标百分比的最高概率 Token 。\n例如如果前两个最高概率标记都是 25%,并且 Top P 设置为 0.50,那么只有这前两个 Token 会被考虑。\n如果将 Top P 设置为 1.0,则表示禁用该功能。",
"Typical P Sampling prioritizes tokens based on their deviation from the average entropy of the set": "典型的 P 采样根据令牌与集合平均熵的偏差来确定令牌的优先级。\n它保留累积概率接近预定义阈值例如0.5)的令牌,强调那些具有平均信息内容的令牌。\n设置为1.0可禁用该功能。",
"Min P sets a base minimum probability": "最小概率Min P设置了一个基本的最小概率。这个概率会根据概率最高的令牌top token的概率进行缩放。\n例如,如果概率最高的令牌的概率为80%,且最小概率设置为0.1,则只有概率高于8%的令牌会被考虑。\n将最小概率设置为0可以禁用该功能。",
"Top A sets a threshold for token selection based on the square of the highest token probability": "Top A 根据最高令牌概率的平方设置令牌选择的阈值。\n例如,如果 Top-A 值为0.2,且概率最高的令牌的概率为50%,则概率低于5%0.2 × 0.5^2的令牌会被排除在外。\n将 Top A 设置为0可以禁用该功能。",
"Tail-Free Sampling (TFS)": "无尾采样TFS查找分布中概率较低的尾部Token\n 通过分析Token概率的变化率以及二阶导数。Token保留到阈值例如 0.3),取决于统一的二阶导数。\n值越接近 0被拒绝的Token数量就越多。将值设置为 1.0 以禁用。",
"Epsilon cutoff sets a probability floor below which tokens are excluded from being sampled": "Epsilon 截止设置了一个概率下限低于该下限的Token将被排除在样本之外。\n以 1e-4 单位;合适的值为 3。将其设置为 0 以禁用。",
"Scale Temperature dynamically per token, based on the variation of probabilities": "根据概率的变化,动态地调整每个令牌的温度Temperature",
"Minimum Temp": "最小温度",
"Maximum Temp": "最大温度",
"Exponent": "指数",
"Mirostat Mode": "Mirostat 模式",
"Mirostat Tau": "Mirostat Tau",
"Mirostat Eta": "Mirostat Eta",
"Variability parameter for Mirostat outputs": "Mirostat 输出的性参数",
"Learning rate of Mirostat": "Mirostat 的学习率",
"Strength of the Contrastive Search regularization term. Set to 0 to disable CS": "对比搜索正则化项的强度。 将值设置为 0 以禁用 CS。",
"Temperature Last": "最后温度",
"Use the temperature sampler last": "最后使用温度采样器。 通常是合理的。\n当启用时首先进行潜在Token的选择然后应用温度来修正它们的相对概率技术上是对数似然。\n当禁用时首先应用温度来修正所有Token的相对概率然后从中选择潜在Token。\n禁用最后的温度。",
"LLaMA / Mistral / Yi models only": "仅限 LLaMA / Mistral / Yi 模型。 确保首先选择适当的分析师。\n结果中不应出现串。\n每行一个串。 文本或 [Token标识符]。\n许多Token以空格开头。 如果不确定,请使用Token计数器。",
"Variability parameter for Mirostat outputs": "Mirostat 输出的变性参数",
"Learning rate of Mirostat": "Mirostat 的学习率",
"Strength of the Contrastive Search regularization term. Set to 0 to disable CS": "对比搜索Contrastive Search正则化项的强度。设置为 0 可禁用对比搜索。",
"Temperature Last": "温度采样器后置",
"Use the temperature sampler last": "最后再使用温度采样器。这几乎总是明智的做法。\n当启用时:首先对一组合理的令牌进行采样,然后应用温度来调整它们的相对概率(技术上称为对数概率)。\n当禁用时:首先应用温度来调整所有令牌的相对概率,然后从中采样出合理的令牌。\n禁用会提高分布尾部的概率,这往往会增加得到不连贯响应的几率。",
"LLaMA / Mistral / Yi models only": "仅适用于 LLaMA / Mistral / Yi 模型。请确保首先选择适当的分词器。\n每行输入一个你不希望出现在输出中的序列,可以是文本或 [Token ID]。\n大多数Token前面都有一个空格。如果不确定,请使用Token计数器。",
"Example: some text [42, 69, 1337]": "例如:\n一些文本\n[42, 69, 1337]",
"Classifier Free Guidance. More helpful tip coming soon": "免费的分类器指导。 更多有用的提示即将推出。",
"Classifier Free Guidance. More helpful tip coming soon": "免费的分类器指导。更多有用的提示即将推出。",
"Scale": "比例",
"GBNF Grammar": "GBNF 语法",
"Usage Stats": "使用统计",
"Click for stats!": "点击查看统计!",
"Backup": "备份",
"Backup your personas to a file": "将您的人设备份到文件中",
"Backup your personas to a file": "将我的角色备份到文件中",
"Restore": "恢复",
"Restore your personas from a file": "从文件中恢复您的人设",
"Restore your personas from a file": "从文件中恢复我的角色",
"Type in the desired custom grammar": "输入所需的自定义语法",
"Encoder Rep. Pen.": "编码器重复惩罚",
"Smoothing Factor": "平滑系数",
"No Repeat Ngram Size": "无重复 n-gram 大小",
"No Repeat Ngram Size": "无重复n-gram大小",
"Min Length": "最小长度",
"OpenAI Reverse Proxy": "OpenAI 反向代理",
"Alternative server URL (leave empty to use the default value).": "备用服务器 URL留空以使用默认值。",
"Remove your real OAI API Key from the API panel BEFORE typing anything into this box": "在键入任何内容之前,从 API 面板中删除您的真实 OAI API 密钥",
"We cannot provide support for problems encountered while using an unofficial OpenAI proxy": "我们无法为使用非官方 OpenAI 代理时遇到的问题提供支持",
"Alternative server URL (leave empty to use the default value).": "备用服务器URL留空以使用默认值。",
"Remove your real OAI API Key from the API panel BEFORE typing anything into this box": "在键入任何内容之前,从API面板中删除您的真实OpenAI API密钥",
"We cannot provide support for problems encountered while using an unofficial OpenAI proxy": "我们无法为使用非官方OpenAI代理时遇到的问题提供支持",
"Legacy Streaming Processing": "传统流处理",
"Enable this if the streaming doesn't work with your proxy": "如果流媒体与您的代理不兼容,请启用此选项",
"Enable this if the streaming doesn't work with your proxy": "如果流式传输与您的代理不兼容,请启用此选项",
"Context Size (tokens)": "上下文长度Token",
"Max Response Length (tokens)": "最大回复长度Token",
"Frequency Penalty": "Frequency Penalty 频率惩罚",
"Presence Penalty": "Presence Penalty 存在惩罚",
"Top-p": "Top-p",
"Frequency Penalty": "频率惩罚",
"Presence Penalty": "存在惩罚",
"Top-p": "Top P",
"Display bot response text chunks as they are generated": "生成时显示机器人响应文本片段",
"Top A": "Top A",
"Typical Sampling": "Typical Sampling 典型采样",
"Tail Free Sampling": "Tail Free Sampling 无尾采样",
"Rep. Pen. Slope": "Rep. Pen. Slope 重复惩罚斜率",
"Single-line mode": "Single-line 单行模式",
"Typical Sampling": "典型采样",
"Tail Free Sampling": "无尾采样",
"Rep. Pen. Slope": "重复惩罚斜率",
"Single-line mode": "单行模式",
"Top K": "Top K",
"Top P": "Top P",
"Do Sample": "进行采样",
"Add BOS Token": "添加 BOS Token",
"Add the bos_token to the beginning of prompts. Disabling this can make the replies more creative": "在提示词的开头添加 bos_token。 禁用此功能可以使回复更具创意",
"Ban EOS Token": "禁止 EOS Token",
"Ban the eos_token. This forces the model to never end the generation prematurely": "禁止 eos_token。 这将强制模型永远不会提前结束生成",
"Add BOS Token": "添加BOS Token",
"Add the bos_token to the beginning of prompts. Disabling this can make the replies more creative": "在提示词的开头添加BOS Token。禁用此功能可以使回复更具创意",
"Ban EOS Token": "禁止EOS Token",
"Ban the eos_token. This forces the model to never end the generation prematurely": "禁止EOS Token。这将强制模型永远不会提前结束生成",
"Skip Special Tokens": "跳过特殊Token",
"Beam search": "束搜索",
"Number of Beams": "束数量",
"Length Penalty": "长度惩罚",
"Early Stopping": "提前停止",
"Contrastive search": "对比搜索",
"Penalty Alpha": "惩罚 Alpha",
"Penalty Alpha": "惩罚Alpha",
"Seed": "Seed 种子",
"Epsilon Cutoff": "Epsilon Cutoff",
"Eta Cutoff": "Eta Cutoff",
"Epsilon Cutoff": "Epsilon截断",
"Eta Cutoff": "Eta截断",
"Negative Prompt": "负面提示词",
"Mirostat (mode=1 is only for llama.cpp)": "Mirostatmode=1 仅用于 llama.cpp",
"Mirostat is a thermostat for output perplexity": "Mirostat 是输出困惑度的恒温器",
"Add text here that would make the AI generate things you don't want in your outputs.": "在这里添加文本,使 AI 生成您不希望在输出中出现的内容。",
"Mirostat is a thermostat for output perplexity": "Mirostat控制输出困惑度的恒温器",
"Add text here that would make the AI generate things you don't want in your outputs.": "在此处添加可能导致AI生成你不想要的内容的文本。",
"Phrase Repetition Penalty": "短语重复惩罚",
"Preamble": "序文",
"Use style tags to modify the writing style of the output.": "使用样式标签修改输出的写作风格。",
"Banned Tokens": "禁用的Token",
"Sequences you don't want to appear in the output. One per line.": "您不希望出现在输出中的序列。 每行一个。",
"Sequences you don't want to appear in the output. One per line.": "您不希望出现在输出中的序列。每行一个。",
"AI Module": "AI 模块",
"Changes the style of the generated text.": "更改生成文本的样式。",
"Used if CFG Scale is unset globally, per chat or character": "如果 CFG Scal在全局未设置、它将作用于每个聊天或每个角色",
"Inserts jailbreak as a last system message.": "将 jailbreak 插入为最后一个系统消息。",
"This tells the AI to ignore its usual content restrictions.": "这告诉 AI 忽略其通常的内容限制。",
"NSFW Encouraged": "鼓励 NSFW",
"Tell the AI that NSFW is allowed.": "告诉 AI NSFW 是允许的。",
"NSFW Prioritized": "优先考虑 NSFW",
"NSFW prompt text goes first in the prompt to emphasize its effect.": "NSFW 提示词文本首先出现在提示词中以强调其效果。",
"Streaming": "Streaming 流式传输",
"Dynamic Temperature": "Dynamic Temperature 动态温度",
"Used if CFG Scale is unset globally, per chat or character": "如果CFG Scale未在全局设置此项将作用于每个聊天或角色",
"Inserts jailbreak as a last system message.": "将jailbreak插入为最后一条系统消息。",
"This tells the AI to ignore its usual content restrictions.": "这告诉AI忽略其通常的内容限制。",
"NSFW Encouraged": "鼓励NSFW",
"Tell the AI that NSFW is allowed.": "告诉AI NSFW是允许的。",
"NSFW Prioritized": "优先NSFW",
"NSFW prompt text goes first in the prompt to emphasize its effect.": "NSFW提示词文本首先出现在提示词中以强调其效果。",
"Streaming": "流式传输",
"Dynamic Temperature": "动态温度",
"Restore current preset": "恢复当前预设",
"Neutralize Samplers": "Neutralize Samplers 中和采样器",
"Neutralize Samplers": "中和采样器",
"Text Completion presets": "文本补全预设",
"Documentation on sampling parameters": "有关采样参数的文档",
"Set all samplers to their neutral/disabled state.": "将所有采样器设置为中性/禁用状态。",
"Only enable this if your model supports context sizes greater than 4096 tokens": "仅在您的模型支持大于4096个标记的上下文大小时启用此选项",
"Display the response bit by bit as it is generated": "逐位显示生成的响应",
"Only enable this if your model supports context sizes greater than 4096 tokens": "仅在您的模型支持大于4096 Tokens的上下文长度时启用此选项",
"Display the response bit by bit as it is generated": "随着响应的生成,逐步显示结果",
"Generate only one line per request (KoboldAI only, ignored by KoboldCpp).": "每个请求仅生成一行仅限KoboldAIKoboldCpp不支持。",
"Ban the End-of-Sequence (EOS) token (with KoboldCpp, and possibly also other tokens with KoboldAI).": "禁止序列末尾EOS标记与KoboldCpp一起可能还有其他与KoboldAI的标记。",
"Good for story writing, but should not be used for chat and instruct mode.": "适用于写故事,但不应用于聊天和指导模式。",
"Ban the End-of-Sequence (EOS) token (with KoboldCpp, and possibly also other tokens with KoboldAI).": "禁用序列结束EOSToken使用KoboldCpp可能还包括KoboldAI中的其他Token。",
"Good for story writing, but should not be used for chat and instruct mode.": "适合用于故事写作,但不应用于聊天和指令模式。",
"Enhance Definitions": "增强定义",
"Use OAI knowledge base to enhance definitions for public figures and known fictional characters": "使用OAI知识库来增强公众人物和已知虚构角色的定义",
"Wrap in Quotes": "用引号括起来",
"Wrap entire user message in quotes before sending.": "在发送之前用引号括起整个用户消息。",
"Leave off if you use quotes manually for speech.": "如果您手动使用引号进行讲话,请省略。",
"Use OAI knowledge base to enhance definitions for public figures and known fictional characters": "使用OpenAI知识库来增强公众人物和已知虚构角色的定义",
"Wrap in Quotes": "用引号包裹",
"Wrap entire user message in quotes before sending.": "在发送之前用引号包裹整个用户消息。",
"Leave off if you use quotes manually for speech.": "如果您手动使用引号包裹对话,请忽略此项。",
"Main prompt": "主提示词",
"The main prompt used to set the model behavior": "用于设置模型行为的主提示词",
"NSFW prompt": "NSFW提示词",
@ -128,26 +129,26 @@
"Prompt that is used when the Jailbreak toggle is on": "在越狱开关打开时使用的提示词",
"Impersonation prompt": "冒名顶替提示词",
"Prompt that is used for Impersonation function": "用于冒名顶替功能的提示词",
"Logit Bias": "对数偏",
"Logit Bias": "对数偏",
"Helps to ban or reenforce the usage of certain words": "有助于禁止或加强某些单词的使用",
"View / Edit bias preset": "查看/编辑偏置预设",
"Add bias entry": "添加偏置条目",
"Jailbreak activation message": "越狱激活消息",
"Jailbreak activation message": "越狱启用消息",
"Message to send when auto-jailbreak is on.": "自动越狱时发送的消息。",
"Jailbreak confirmation reply": "越狱确认回复",
"Bot must send this back to confirm jailbreak": "机器人必须发送此内容以确认越狱",
"Character Note": "角色注",
"Character Note": "角色注",
"Influences bot behavior in its responses": "影响机器人在其响应中的行为",
"Connect": "连接",
"Test Message": "发送测试消息",
"API": "API",
"KoboldAI": "KoboldAI",
"Use Horde": "使用部落",
"API url": "API地址",
"PygmalionAI/aphrodite-engine": "PygmalionAI/aphrodite-engine用于OpenAI API的包装器",
"Register a Horde account for faster queue times": "注册Horde部落帐户以加快排队时间",
"Learn how to contribute your idle GPU cycles to the Hord": "了解如何将闲置的GPU周期贡献给部落",
"Adjust context size to worker capabilities": "根据工作人员的能力调整上下文大小",
"Use Horde": "使用 Horde",
"API url": "API URL",
"PygmalionAI/aphrodite-engine": "PygmalionAI/aphrodite-engine (OpenAI API wrapper 模式)",
"Register a Horde account for faster queue times": "注册Horde帐户以减少排队时间",
"Learn how to contribute your idle GPU cycles to the Hord": "了解如何将闲置的GPU算力贡献给Horde",
"Adjust context size to worker capabilities": "根据工作人员的能力调整上下文长度",
"Adjust response length to worker capabilities": "根据工作人员的能力调整响应长度",
"API key": "API密钥",
"Tabby API key": "Tabby API密钥",
@ -168,7 +169,7 @@
"For privacy reasons": "出于隐私考虑",
"Models": "模型",
"Hold Control / Command key to select multiple models.": "按住Control / Command键选择多个模型。",
"Horde models not loaded": "部落模型未加载",
"Horde models not loaded": "Horde模型未加载",
"Not connected...": "未连接...",
"Novel API key": "Novel AI API密钥",
"Follow": "跟随",
@ -181,16 +182,16 @@
"Make sure you run it with": "确保您用以下方式运行它",
"flag": "标志",
"API key (optional)": "API密钥可选",
"Server url": "服务器地址",
"Server url": "服务器URL",
"Custom model (optional)": "自定义模型(可选)",
"Bypass API status check": "绕过API状态检查",
"Mancer AI": "Mancer AI",
"Use API key (Only required for Mancer)": "使用API密钥仅Mancer需要",
"Blocking API url": "阻止API地址",
"Blocking API url": "阻止API URL",
"Example: 127.0.0.1:5000": "示例127.0.0.1:5000",
"Legacy API (pre-OAI, no streaming)": "传统APIOAI之前无流式传输",
"Bypass status check": "绕过状态检查",
"Streaming API url": "流式API地址",
"Streaming API url": "流式传输API地址",
"Example: ws://127.0.0.1:5005/api/v1/stream": "示例ws://127.0.0.1:5005/api/v1/stream",
"Mancer API key": "Mancer API密钥",
"Example: https://neuro.mancer.tech/webui/MODEL/api": "示例https://neuro.mancer.tech/webui/MODEL/api",
@ -209,36 +210,36 @@
"View API Usage Metrics": "查看API使用指标",
"Show External models (provided by API)": "显示外部模型由API提供",
"Bot": "机器人",
"Allow fallback routes": "允许后备路由",
"Allow fallback routes": "允许路由回退",
"Allow fallback routes Description": "如果所选模型无法响应您的请求,则自动选择备用模型。",
"OpenRouter API Key": "OpenRouter API密钥",
"Connect to the API": "连接到API",
"OpenRouter Model": "OpenRouter模型",
"View Remaining Credits": "查看剩余信用额",
"View Remaining Credits": "查看剩余",
"Click Authorize below or get the key from": "点击下方授权或从以下位置获取密钥",
"Auto-connect to Last Server": "自动连接到上次的服务器",
"View hidden API keys": "查看隐藏的API密钥",
"Advanced Formatting": "高级格式设置",
"Advanced Formatting": "高级格式设置",
"Context Template": "上下文模板",
"AutoFormat Overrides": "自动格式覆盖",
"Disable description formatting": "禁用描述格式",
"Disable personality formatting": "禁用人格格式",
"Disable scenario formatting": "禁用情景格式",
"Disable example chats formatting": "禁用示例聊天格式",
"Disable chat start formatting": "禁用聊天开始格式",
"Disable description formatting": "禁用描述格式",
"Disable personality formatting": "禁用人格格式",
"Disable scenario formatting": "禁用情景格式",
"Disable example chats formatting": "禁用示例聊天格式",
"Disable chat start formatting": "禁用聊天开始格式",
"Custom Chat Separator": "自定义聊天分隔符",
"Replace Macro in Custom Stopping Strings": "自定义停止字符串替换宏",
"Replace Macro in Custom Stopping Strings": "自定义停止字符串替换宏",
"Strip Example Messages from Prompt": "从提示词中删除示例消息",
"Story String": "Story String 故事字符串",
"Story String": "故事字符串",
"Example Separator": "示例分隔符",
"Chat Start": "聊天开始",
"Activation Regex": "激活正则表达式",
"Instruct Mode": "指模式",
"Wrap Sequences with Newline": "用换行符包序列",
"Activation Regex": "启用正则表达式",
"Instruct Mode": "指模式",
"Wrap Sequences with Newline": "用换行符包序列",
"Include Names": "包括名称",
"Force for Groups and Personas": "强制适配群组和人物",
"Force for Groups and Personas": "强制适用于群聊和我的角色",
"System Prompt": "系统提示词",
"Instruct Mode Sequences": "Instruct Mode Sequences 指导模式序列",
"Instruct Mode Sequences": "指令模式序列",
"Input Sequence": "输入序列",
"Output Sequence": "输出序列",
"First Output Sequence": "第一个输出序列",
@ -246,7 +247,7 @@
"System Sequence Prefix": "系统序列前缀",
"System Sequence Suffix": "系统序列后缀",
"Stop Sequence": "停止序列",
"Context Formatting": "上下文格式",
"Context Formatting": "上下文格式",
"(Saved to Context Template)": "(保存到上下文模板)",
"Tokenizer": "分词器",
"None / Estimated": "无 / 估计",
@ -256,11 +257,11 @@
"Always add character's name to prompt": "始终将角色名称添加到提示词",
"Use as Stop Strings": "用作停止字符串",
"Bind to Context": "绑定到上下文",
"Generate only one line per request": "每请求只生成一行",
"Generate only one line per request": "每请求只生成一行",
"Misc. Settings": "其他设置",
"Auto-Continue": "自动继续",
"Collapse Consecutive Newlines": "折叠连续的换行符",
"Allow for Chat Completion APIs": "允许聊天完成API",
"Allow for Chat Completion APIs": "允许对话补全API",
"Target length (tokens)": "目标长度Token",
"Keep Example Messages in Prompt": "在提示词中保留示例消息",
"Remove Empty New Lines from Output": "从输出中删除空行",
@ -272,7 +273,7 @@
"Style then Character": "样式然后角色",
"Character Anchor": "角色锚点",
"Style Anchor": "样式锚点",
"World Info": "世界信息",
"World Info": "世界",
"Scan Depth": "扫描深度",
"Case-Sensitive": "区分大小写",
"Match Whole Words": "匹配整个单词",
@ -280,7 +281,7 @@
"Yes": "是",
"No": "否",
"Context %": "上下文百分比",
"Budget Cap": "预算上限",
"Budget Cap": "Token预算上限",
"(0 = disabled)": "(0 = 禁用)",
"depth": "深度",
"Token Budget": "Token预算",
@ -289,7 +290,7 @@
"None": "无",
"User Settings": "用户设置",
"UI Mode": "UI 模式",
"UI Language": "语言",
"UI Language": "UI 语言",
"MovingUI Preset": "MovingUI 预设",
"UI Customization": "UI 自定义",
"Avatar Style": "头像样式",
@ -301,8 +302,8 @@
"Bubbles": "气泡",
"No Blur Effect": "禁用模糊效果",
"No Text Shadows": "禁用文本阴影",
"Waifu Mode": "AI老婆模式",
"Message Timer": "AI回复消息计时器",
"Waifu Mode": "视觉小说模式",
"Message Timer": "AI回复计时器",
"Model Icon": "模型图标",
"# of messages (0 = disabled)": "消息数量0 = 禁用)",
"Advanced Character Search": "高级角色搜索",
@ -310,7 +311,7 @@
"Allow {{user}}: in bot messages": "在机器人消息中允许 {{user}}",
"Show tags in responses": "在响应中显示标签",
"Aux List Field": "辅助列表字段",
"Lorebook Import Dialog": "Lorebook 导入对话框",
"Lorebook Import Dialog": "世界书导入对话框",
"MUI Preset": "可移动UI 预设",
"If set in the advanced character definitions, this field will be displayed in the characters list.": "如果在高级角色定义中设置,此字段将显示在角色列表中。",
"Relaxed API URLS": "宽松的API URL",
@ -319,10 +320,10 @@
"Mancer Model": "Mancer 模型",
"API Type": "API 类型",
"Aphrodite API key": "Aphrodite API 密钥",
"Relax message trim in Groups": "放松群组中的消息修剪",
"Relax message trim in Groups": "宽松的群聊消息修剪",
"Characters Hotswap": "收藏角色卡置顶显示",
"Request token probabilities": "请求Token概率",
"Movable UI Panels": "可移动UI 面板",
"Movable UI Panels": "可移动UI 面板",
"Reset Panels": "重置面板",
"UI Colors": "UI 颜色",
"Main Text": "主要文本",
@ -362,15 +363,15 @@
"System Backgrounds": "系统背景",
"Name": "名称",
"Your Avatar": "您的头像",
"Extensions API:": "扩展 API地址:",
"SillyTavern-extras": "SillyTavern-额外功能",
"Extensions API:": "扩展API地址:",
"SillyTavern-extras": "SillyTavern扩展",
"Auto-connect": "自动连接",
"Active extensions": "激活扩展",
"Active extensions": "启用扩展",
"Extension settings": "扩展设置",
"Description": "描述",
"First message": "第一条消息",
"Group Controls": "群控制",
"Group reply strategy": "群回复策略",
"Group Controls": "群控制",
"Group reply strategy": "群回复策略",
"Natural order": "自然顺序",
"List order": "列表顺序",
"Allow self responses": "允许自我回复",
@ -385,42 +386,42 @@
"A brief description of the personality": "个性的简要描述",
"Scenario": "情景",
"Circumstances and context of the dialogue": "对话的情况和背景",
"Talkativeness": "健谈",
"Talkativeness": "健谈",
"How often the chracter speaks in": "角色在其中讲话的频率",
"group chats!": "群聊中!",
"Shy": "害羞",
"Normal": "正常",
"Normal": "普通",
"Chatty": "话多",
"Examples of dialogue": "对话示例",
"Forms a personality more clearly": "更清晰地形成个性",
"Save": "保存",
"World Info Editor": "世界信息编辑器",
"World Info Editor": "世界编辑器",
"New summary": "新摘要",
"Export": "导出",
"Delete World": "删除世界",
"Chat History": "聊天记录",
"Group Chat Scenario Override": "群组聊天情景替代",
"All group members will use the following scenario text instead of what is specified in their character cards.": "所有群成员将使用以下情景文本,而不是在其角色卡中指定的内容。",
"Group Chat Scenario Override": "群聊情景覆盖",
"All group members will use the following scenario text instead of what is specified in their character cards.": "所有群成员将使用以下情景文本,而不是在其角色卡中指定的内容。",
"Keywords": "关键词",
"Separate with commas": "用逗号分隔",
"Secondary Required Keywords": "次要必需关键词",
"Secondary Required Keywords": "第二个必需关键词",
"Content": "内容",
"What this keyword should mean to the AI": "这个关键词对 AI 的含义",
"Memo/Note": "备忘录/注释",
"Not sent to AI": "不发送给 AI",
"Constant": "常量",
"Selective": "选择性",
"Before Char": "角色之前",
"After Char": "角色之后",
"Before Char": "角色定义之前",
"After Char": "角色定义之后",
"Insertion Order": "插入顺序",
"Tokens:": "Token",
"Tokens:": "Tokens",
"Disable": "禁用",
"${characterName}": "${角色名称}",
"CHAR": "角色",
"is typing": "正在输入...",
"Back to parent chat": "返回到父级聊天",
"Save bookmark": "保存书签",
"Convert to group": "转换为群",
"Convert to group": "转换为群",
"Start new chat": "开始新聊天",
"View past chats": "查看过去的聊天记录",
"Delete messages": "删除消息",
@ -437,13 +438,13 @@
"NSFW avoidance prompt": "禁止 NSFW 提示词",
"Prompt that is used when the NSFW toggle is off": "NSFW 开关关闭时使用的提示词",
"Advanced prompt bits": "高级提示词位",
"World Info format": "世界信息格式",
"Wraps activated World Info entries before inserting into the prompt. Use {0} to mark a place where the content is inserted.": "在插入到提示词中之前包装激活的世界信息条目。使用 {0} 标记内容插入的位置。",
"Unrestricted maximum value for the context slider": "AI可见的最大上下文长度",
"Chat Completion Source": "聊天补全来源",
"World Info format": "世界格式",
"Wraps activated World Info entries before inserting into the prompt. Use {0} to mark a place where the content is inserted.": "在插入到提示词中之前包裹启用的世界书条目。使用 {0} 标记内容插入的位置。",
"Unrestricted maximum value for the context slider": "上下文长度滑块的最大值无限制,仅在你知道自己在做什么的情况下才启用。",
"Chat Completion Source": "对话补全来源",
"Avoid sending sensitive information to the Horde.": "避免向 Horde 发送敏感信息。",
"Review the Privacy statement": "查看隐私声明",
"Learn how to contribute your idel GPU cycles to the Horde": "了解如何将您的空闲 GPU 周期贡献给 Horde",
"Learn how to contribute your idel GPU cycles to the Horde": "了解如何将您的空闲 GPU 算力贡献给 Horde",
"Trusted workers only": "仅信任的工作人员",
"For privacy reasons, your API key will be hidden after you reload the page.": "出于隐私原因,重新加载页面后您的 API 密钥将被隐藏。",
"-- Horde models not loaded --": "-- Horde 模型未加载 --",
@ -451,9 +452,9 @@
"No connection...": "没有连接...",
"Get your NovelAI API Key": "获取您的 NovelAI API 密钥",
"KoboldAI Horde": "KoboldAI Horde",
"Text Gen WebUI (ooba)": "文本生成 WebUIooba",
"Text Gen WebUI (ooba)": "Text Gen WebUIooba",
"NovelAI": "NovelAI",
"Chat Completion (OpenAI, Claude, Window/OpenRouter, Scale)": "聊天补全OpenAI、Claude、Window/OpenRouter、Scale",
"Chat Completion (OpenAI, Claude, Window/OpenRouter, Scale)": "对话补全OpenAI、Claude、Window/OpenRouter、Scale",
"OpenAI API key": "OpenAI API 密钥",
"Trim spaces": "修剪空格",
"Trim Incomplete Sentences": "修剪不完整的句子",
@ -464,16 +465,16 @@
"Separator": "分隔符",
"Start Reply With": "以...开始回复",
"Show reply prefix in chat": "在聊天中显示回复前缀",
"Worlds/Lorebooks": "世界/传说书",
"Active World(s)": "活动世界",
"Activation Settings": "激活配置",
"Character Lore Insertion Strategy": "角色传说插入策略",
"Worlds/Lorebooks": "世界/传说书",
"Active World(s)": "当前启用的世界书",
"Activation Settings": "启用配置",
"Character Lore Insertion Strategy": "角色世界书条目插入策略",
"Sorted Evenly": "均匀排序",
"Active World(s) for all chats": "已启用的世界书(全局有效)",
"-- World Info not found --": "-- 未找到世界信息 --",
"-- World Info not found --": "-- 未找到世界 --",
"--- Pick to Edit ---": "--- 选择以编辑 ---",
"or": "或",
"New": "新",
"New": "新",
"Priority": "优先级",
"Custom": "自定义",
"Title A-Z": "标题 A-Z",
@ -486,23 +487,23 @@
"Order ↘": "顺序 ↘",
"UID ↗": "UID ↗",
"UID ↘": "UID ↘",
"Trigger% ↗": "触发% ↗",
"Trigger% ↘": "触发% ↘",
"Trigger% ↗": "触发频率% ↗",
"Trigger% ↘": "触发频率% ↘",
"Order:": "顺序:",
"Depth:": "深度:",
"Character Lore First": "角色传说优先",
"Global Lore First": "全局传说优先",
"Character Lore First": "角色世界书优先",
"Global Lore First": "全局世界书优先",
"Recursive Scan": "递归扫描",
"Case Sensitive": "区分大小写",
"Match whole words": "完整匹配单词",
"Alert On Overflow": "溢出警报",
"World/Lore Editor": "世界/传说编辑器",
"World/Lore Editor": "世界编辑器",
"--- None ---": "--- 无 ---",
"Use Probability": "使用概率",
"Exclude from recursion": "排除递归",
"Exclude from recursion": "从递归中排除",
"Entry Title/Memo": "条目标题/备忘录",
"Position:": "位置:",
"T_Position": "↑Char在角色定义之前\n↓Char在角色定义之后\n↑AN在作者注释之前\n↓AN在作者注释之后\n@D在深度处",
"T_Position": "↑Char在角色定义之前\n↓Char在角色定义之后\n↑AN在作者注释之前\n↓AN在作者注释之后\n@D在深度D处",
"Before Char Defs": "角色定义之前",
"After Char Defs": "角色定义之后",
"Before AN": "作者注释之前",
@ -512,7 +513,7 @@
"Probability:": "概率:",
"Update a theme file": "更新主题文件",
"Save as a new theme": "另存为新主题",
"Minimum number of blacklisted words detected to trigger an auto-swipe": "检测到触发自动滑动的黑名单词语的最小数量",
"Minimum number of blacklisted words detected to trigger an auto-swipe": "触发自动滑动的检测到的黑名单词汇的最小数量",
"Delete Entry": "删除条目",
"User Message Blur Tint": "用户消息模糊色调",
"AI Message Blur Tint": "AI 消息模糊色调",
@ -522,7 +523,7 @@
"Mad Lab Mode": "疯狂实验室模式",
"Show Message Token Count": "显示消息Token计数",
"Compact Input Area (Mobile)": "紧凑输入区域(移动端)",
"Zen Sliders": "禅滑块",
"Zen Sliders": "禅滑块",
"UI Border": "UI 边框",
"Chat Style:": "聊天风格:",
"Chat Width (PC)": "聊天宽度PC",
@ -535,18 +536,18 @@
"Message IDs": "显示消息编号",
"Prefer Character Card Prompt": "角色卡提示词优先",
"Prefer Character Card Jailbreak": "角色卡越狱优先",
"Press Send to continue": "按发送键继续",
"Press Send to continue": "按发送键继续",
"Quick 'Continue' button": "快速“继续”按钮",
"Log prompts to console": "将提示词记录到控制台",
"Never resize avatars": "不调整头像大小",
"Show avatar filenames": "显示头像文件名",
"Import Card Tags": "导入卡片标签",
"Confirm message deletion": "确认删除消息",
"Confirm message deletion": "删除消息前确认",
"Spoiler Free Mode": "隐藏角色卡信息",
"Auto-swipe": "自动滑动",
"Minimum generated message length": "生成的消息的最小长度",
"Blacklisted words": "黑名单词",
"Blacklisted word count to swipe": "滑动的黑名单词数量",
"Blacklisted words": "黑名单词",
"Blacklisted word count to swipe": "滑动的黑名单词数量",
"Reload Chat": "重新加载聊天",
"Search Settings": "搜索设置",
"Disabled": "已禁用",
@ -571,8 +572,8 @@
"Show tagged character folders in the character list": "在角色列表中显示已标记的角色文件夹",
"Play a sound when a message generation finishes": "当消息生成完成时播放声音",
"Only play a sound when ST's browser tab is unfocused": "仅在ST的浏览器选项卡未聚焦时播放声音",
"Reduce the formatting requirements on API URLs": "减少API URL的格式要求",
"Ask to import the World Info/Lorebook for every new character with embedded lorebook. If unchecked, a brief message will be shown instead": "询问是否为每个具有嵌入式传说书的新角色导入世界信息/传说书。如果未选中,则会显示简短的消息",
"Reduce the formatting requirements on API URLs": "减少API URL的格式要求",
"Ask to import the World Info/Lorebook for every new character with embedded lorebook. If unchecked, a brief message will be shown instead": "询问是否为每个具有嵌入的世界书的新角色导入世界书。如果未选中,则会显示简短的消息",
"Restore unsaved user input on page refresh": "在页面刷新时恢复未保存的用户输入",
"Allow repositioning certain UI elements by dragging them. PC only, no effect on mobile": "允许通过拖动重新定位某些UI元素。仅适用于PC对移动设备无影响",
"MovingUI preset. Predefined/saved draggable positions": "MovingUI预设。预定义/保存的可拖动位置",
@ -600,20 +601,20 @@
"Reload and redraw the currently open chat": "重新加载和重绘当前打开的聊天",
"Auto-Expand Message Actions": "自动展开消息操作菜单",
"Not Connected": "未连接",
"Persona Management": "角色管理",
"Persona Description": "角色描述",
"Your Persona": "的角色",
"Show notifications on switching personas": "切换角色时显示通知",
"Persona Management": "我的角色管理",
"Persona Description": "我的角色描述",
"Your Persona": "的角色",
"Show notifications on switching personas": "切换我的角色时显示通知",
"Blank": "空白",
"In Story String / Chat Completion: Before Character Card": "故事模式/聊天补全模式:在角色卡之前",
"In Story String / Chat Completion: After Character Card": "故事模式/聊天补全模式:在角色卡之后",
"In Story String / Chat Completion: Before Character Card": "故事模式/对话补全模式:在角色卡之前",
"In Story String / Chat Completion: After Character Card": "故事模式/对话补全模式:在角色卡之后",
"In Story String / Prompt Manager": "在故事字符串/提示词管理器",
"Top of Author's Note": "作者注的顶部",
"Bottom of Author's Note": "作者注的底部",
"Top of Author's Note": "作者注的顶部",
"Bottom of Author's Note": "作者注的底部",
"How do I use this?": "怎样使用?",
"More...": "更多...",
"Link to World Info": "链接到世界信息",
"Import Card Lore": "导入卡片知识",
"Link to World Info": "链接到世界",
"Import Card Lore": "导入人物卡的世界书",
"Scenario Override": "场景覆盖",
"Rename": "重命名",
"Character Description": "角色描述",
@ -627,13 +628,13 @@
"Most chats": "最多聊天",
"Least chats": "最少聊天",
"Back": "返回",
"Prompt Overrides (For OpenAI/Claude/Scale APIs, Window/OpenRouter, and Instruct mode)": "提示词覆盖适用于OpenAI/Claude/Scale API、Window/OpenRouter和Instruct模式)",
"Prompt Overrides (For OpenAI/Claude/Scale APIs, Window/OpenRouter, and Instruct mode)": "提示词覆盖适用于OpenAI/Claude/Scale API、Window/OpenRouter和指令模式)",
"Insert {{original}} into either box to include the respective default prompt from system settings.": "将{{original}}插入到任一框中,以包含系统设置中的相应默认提示词。",
"Main Prompt": "主要提示词",
"Jailbreak": "越狱",
"Creator's Metadata (Not sent with the AI prompt)": "创作者的元数据不与AI提示词一起发送",
"Everything here is optional": "这里的一切都是可选的",
"Created by": "作者",
"Created by": "作者",
"Character Version": "角色版本",
"Tags to Embed": "嵌入的标签",
"How often the character speaks in group chats!": "角色在群聊中说话的频率!",
@ -642,7 +643,7 @@
"Samplers Order": "采样器顺序",
"Samplers will be applied in a top-down order. Use with caution.": "采样器将按自上而下的顺序应用。请谨慎使用。",
"Repetition Penalty": "重复惩罚",
"Rep. Pen. Range.": "重复惩罚范围",
"Rep. Pen. Range.": "重复惩罚范围",
"Rep. Pen. Freq.": "重复惩罚频率",
"Rep. Pen. Presence": "重复惩罚存在",
"Enter it in the box below:": "在下面的框中输入它:",
@ -651,9 +652,9 @@
"Suggest replies": "建议回复",
"Show suggested replies. Not all bots support this.": "显示建议的回复。并非所有机器人都支持此功能。",
"Use 'Unlocked Context' to enable chunked generation.": "使用'Unlocked Context'启用分块生成。",
"It extends the context window in exchange for reply generation speed.": "它扩展了上下文窗口,以换取回复生成速度。",
"It extends the context window in exchange for reply generation speed.": "它以回复生成速度为代价,扩展了上下文窗口",
"Continue": "继续",
"CFG Scale": "CFG规模",
"CFG Scale": "CFG Scale",
"Editing:": "编辑:",
"AI reply prefix": "AI回复前缀",
"Custom Stopping Strings": "自定义停止字符串",
@ -664,8 +665,8 @@
"Enter your name": "输入您的名字",
"Name this character": "为这个角色命名",
"Search / Create Tags": "搜索/创建标签",
"Describe your character's physical and mental traits here.": "在这里描述您角色的身体和精神特征。",
"This will be the first message from the character that starts every chat.": "这将是每次开始角色的第一条消息。",
"Describe your character's physical and mental traits here.": "在这里描述您角色的身体和心理特征。",
"This will be the first message from the character that starts every chat.": "这将是每次开始对话时角色的第一条消息。",
"Chat Name (Optional)": "聊天名称(可选)",
"Filter...": "过滤...",
"Search...": "搜索...",
@ -674,10 +675,10 @@
"(Botmaker's name / Contact Info)": "(机器人制作者的姓名/联系信息)",
"(If you want to track character versions)": "(如果您想跟踪角色版本)",
"(Describe the bot, give use tips, or list the chat models it has been tested on. This will be displayed in the character list.)": "(描述机器人,提供使用技巧,或列出已经测试过的聊天模型。这将显示在角色列表中。)",
"(Write a comma-separated list of tags)": "(编写逗号分隔的标签列表)",
"(Write a comma-separated list of tags)": "(编写一个以逗号分隔的标签列表)",
"(A brief description of the personality)": "(性格的简要描述)",
"(Circumstances and context of the interaction)": "(交互的情况和背景)",
"(Examples of chat dialog. Begin each example with START on a new line.)": "(聊天对话的示例。每个示例都以新行上的START开头。)",
"(Examples of chat dialog. Begin each example with START on a new line.)": "(聊天对话的示例,每个示例都另起一行以<START>开头。)",
"Injection text (supports parameters)": "注入文本(支持参数)",
"Injection depth": "注入深度",
"Type here...": "在此处输入...",
@ -687,23 +688,23 @@
"Filter to Character(s)": "过滤到角色",
"Character Exclusion": "角色排除",
"Inclusion Group": "包含组",
"Only one entry with the same label will be activated": "只有一个带有相同标签的条目将被激活",
"Only one entry with the same label will be activated": "只有一个带有相同标签的条目将被启用",
"-- Characters not found --": "-- 未找到角色 --",
"Not sent to the AI": "不发送到AI",
"(This will be the first message from the character that starts every chat)": "(这将是每次开始的角色的第一条消息)",
"(This will be the first message from the character that starts every chat)": "(这将是每次开始对话时角色的第一条消息。)",
"Not connected to API!": "未连接到API",
"AI Response Configuration": "AI响应配置",
"AI Configuration panel will stay open": "AI配置面板将保持打开状态",
"AI Configuration panel will stay open": "AI配置面板将保持打开",
"Update current preset": "更新当前预设",
"Create new preset": "创建新预设",
"Import preset": "导入预设",
"Export preset": "导出预设",
"Delete the preset": "删除预设",
"Auto-select this preset for Instruct Mode": "自动选择此预设以进行指示模式",
"Auto-select this preset for Instruct Mode": "为指令模式自动选择此预设",
"Auto-select this preset on API connection": "在API连接时自动选择此预设",
"NSFW block goes first in the resulting prompt": "结果提示词中首先是NSFW块",
"Enables OpenAI completion streaming": "启用OpenAI完成流",
"Wrap user messages in quotes before sending": "在发送之前将用户消息用引号起来",
"Enables OpenAI completion streaming": "启用OpenAI补全流式传输",
"Wrap user messages in quotes before sending": "在发送之前将用户消息用引号包裹起来",
"Restore default prompt": "恢复默认提示词",
"New preset": "新预设",
"Delete preset": "删除预设",
@ -711,56 +712,56 @@
"Restore default reply": "恢复默认回复",
"Restore defaul note": "恢复默认备注",
"API Connections": "API连接",
"Can help with bad responses by queueing only the approved workers. May slowdown the response time.": "可以通过仅排队批准的工作人员来帮助处理不良响应。可能会减慢响应时间。",
"Can help with bad responses by queueing only the approved workers. May slowdown the response time.": "可以通过仅将批准的工作人员加入排队来帮助处理不良响应。可能会延长响应时间。",
"Clear your API key": "清除您的API密钥",
"Refresh models": "刷新模型",
"Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai": "使用OAuth流程获取您的OpenRouter APIToken。您将被重定向到openrouter.ai",
"Verifies your API connection by sending a short test message. Be aware that you'll be credited for it!": "通过发送简短的测试消息验证您的API连接。请注意您将因此而获得信用",
"Create New": "创建新",
"Get your OpenRouter API token using OAuth flow. You will be redirected to openrouter.ai": "使用OAuth流程获取您的OpenRouter API Token。您将被重定向到openrouter.ai",
"Verifies your API connection by sending a short test message. Be aware that you'll be credited for it!": "通过发送简短的测试消息验证您的API连接。请注意这也将被纳入计费",
"Create New": "新建",
"Edit": "编辑",
"Locked = World Editor will stay open": "锁定=世界编辑器将保持打开状态",
"Entries can activate other entries by mentioning their keywords": "条目可以通过提及它们的关键字来激活其他条目",
"Locked = World Editor will stay open": "锁定 = 世界编辑器将保持打开状态",
"Entries can activate other entries by mentioning their keywords": "条目可以通过提及对应的关键字来启用其他条目",
"Lookup for the entry keys in the context will respect the case": "在上下文中查找条目键将保持大小写敏感",
"If the entry key consists of only one word, it would not be matched as part of other words": "如果条目键只由一个单词组成,则不会作为其他单词的一部分匹配",
"Open all Entries": "打开所有条目",
"Close all Entries": "关闭所有条目",
"Create": "创建",
"Import World Info": "导入世界信息",
"Export World Info": "导出世界信息",
"Delete World Info": "删除世界信息",
"Duplicate World Info": "复制世界信息",
"Rename World Info": "重命名世界信息",
"Import World Info": "导入世界",
"Export World Info": "导出世界",
"Delete World Info": "删除世界",
"Duplicate World Info": "复制世界",
"Rename World Info": "重命名世界",
"Refresh": "刷新",
"Primary Keywords": "主要关键字",
"Logic": "逻辑",
"AND ANY": "任意",
"AND ALL": "所有",
"NOT ALL": "不是所有",
"NOT ANY": "没有任何",
"AND ANY": "任意",
"AND ALL": "所有",
"NOT ALL": "所有",
"NOT ANY": "任何",
"Optional Filter": "可选过滤器",
"New Entry": "新条目",
"Fill empty Memo/Titles with Keywords": "使用关键字填充空的备忘录/标题",
"Save changes to a new theme file": "将更改保存到新的主题文件",
"removes blur and uses alternative background color for divs": "消除模糊并为div使用替代背景颜色",
"AI Response Formatting": "AI响应格式",
"AI Response Formatting": "AI响应格式",
"Change Background Image": "更改背景图片",
"Extensions": "扩展管理",
"Extensions": "扩展",
"Click to set a new User Name": "点击设置新的用户名",
"Click to lock your selected persona to the current chat. Click again to remove the lock.": "单击以将您选择的角色锁定到当前聊天。再次单击以移除锁定。",
"Click to lock your selected persona to the current chat. Click again to remove the lock.": "单击以将您选择的我的角色锁定到当前聊天。再次单击以移除锁定。",
"Click to set user name for all messages": "点击为所有消息设置用户名",
"Create a dummy persona": "创建虚拟角色",
"Create a dummy persona": "创建虚拟我的角色",
"Character Management": "角色管理",
"Locked = Character Management panel will stay open": "已锁定=角色管理面板将保持打开状态",
"Locked = Character Management panel will stay open": "已锁定 = 角色管理面板将保持打开状态",
"Select/Create Characters": "选择/创建角色",
"Token counts may be inaccurate and provided just for reference.": "Token计数可能不准确仅供参考。",
"Click to select a new avatar for this character": "单击以为此角色选择新的头像",
"Example: [{{user}} is a 28-year-old Romanian cat girl.]": "示例:[{{user}}是一个28岁的罗马尼亚猫女孩。]",
"Example: [{{user}} is a 28-year-old Romanian cat girl.]": "示例:[{{user}}是一个28岁的罗马尼亚猫。]",
"Toggle grid view": "切换网格视图",
"Add to Favorites": "添加到收藏夹",
"Advanced Definition": "高级定义",
"Character Lore": "角色传说",
"Character Lore": "角色世界书",
"Export and Download": "导出并下载",
"Duplicate Character": "复制角色",
"Duplicate Character": "创建角色副本",
"Create Character": "创建角色",
"Delete Character": "删除角色",
"View all tags": "查看所有标签",
@ -769,22 +770,22 @@
"Click to select a new avatar for this group": "单击以为该组选择新的头像",
"Set a group chat scenario": "设置群组聊天场景",
"Restore collage avatar": "恢复拼贴头像",
"Create New Character": "创建新角色",
"Create New Character": "新建角色",
"Import Character from File": "从文件导入角色",
"Import content from external URL": "从外部URL导入内容",
"Create New Chat Group": "创建新的天组",
"Create New Chat Group": "创建新的聊",
"Characters sorting order": "角色排序顺序",
"Add chat injection": "添加聊天注入",
"Remove injection": "移除注入",
"Remove": "移除",
"Select a World Info file for": "为...选择一个世界信息文件",
"Primary Lorebook": "主要传说书",
"A selected World Info will be bound to this character as its own Lorebook.": "所选的世界信息将作为该角色自己的传说书绑定到此角色。",
"When generating an AI reply, it will be combined with the entries from a global World Info selector.": "在生成AI回复时它将与全局世界信息选择器中的条目结合。",
"Exporting a character would also export the selected Lorebook file embedded in the JSON data.": "导出角色还将导出嵌入在JSON数据中的所选传说书文件。",
"Additional Lorebooks": "附加传说书",
"Associate one or more auxillary Lorebooks with this character.": "将一个或多个辅助传说书与此角色关联。",
"NOTE: These choices are optional and won't be preserved on character export!": "注意:这些选择是可选的,并且不会在角色导出时保留",
"Select a World Info file for": "为...选择一个世界文件",
"Primary Lorebook": "主要世界书",
"A selected World Info will be bound to this character as its own Lorebook.": "所选的世界书将会于该角色绑定,作为该角色自己的世界书",
"When generating an AI reply, it will be combined with the entries from a global World Info selector.": "在生成AI回复时它将与全局世界书选择器中的条目相结合。",
"Exporting a character would also export the selected Lorebook file embedded in the JSON data.": "导出角色还将导出嵌入在JSON数据中的所选世界书文件。",
"Additional Lorebooks": "附加世界书",
"Associate one or more auxillary Lorebooks with this character.": "将一个或多个辅助世界书与此角色关联。",
"NOTE: These choices are optional and won't be preserved on character export!": "注意:这些选项是可选的,并且不会在角色导出时被一并导出",
"Rename chat file": "重命名聊天文件",
"Export JSONL chat file": "导出JSONL聊天文件",
"Download chat as plain text document": "将聊天下载为纯文本文档",
@ -817,9 +818,9 @@
"Ask AI to write your message for you": "请求AI为您撰写消息",
"Continue the last message": "继续上一条消息",
"Bind user name to that avatar": "将用户名称绑定到该头像",
"Select this as default persona for the new chats.": "选择此项作为新聊天的默认人物。",
"Change persona image": "更改人物形象",
"Delete persona": "删除人物",
"Select this as default persona for the new chats.": "将这个设置为新聊天的默认我的角色。",
"Change persona image": "更改我的角色头像",
"Delete persona": "删除我的角色",
"Reduced Motion": "减少动态效果",
"Auto-select": "自动选择",
"Automatically select a background based on the chat context": "根据聊天上下文自动选择背景",
@ -832,7 +833,7 @@
"UI Theme": "UI主题",
"This message is invisible for the AI": "此消息对AI不可见",
"Sampler Priority": "采样器优先级",
"Ooba only. Determines the order of samplers.": "仅适用于Ooba。确定采样器的顺序。",
"Ooba only. Determines the order of samplers.": "确定采样器的顺序仅适用于Ooba",
"Load default order": "加载默认顺序",
"Max Tokens Second": "每秒最大Token数",
"CFG": "CFG",
@ -850,30 +851,30 @@
"Import Extension From Git Repo": "从Git存储库导入扩展",
"Install extension": "安装扩展",
"Manage extensions": "管理扩展",
"Tokens persona description": "Token人物描述",
"Most tokens": "大多数Token",
"Least tokens": "最少Token",
"Tokens persona description": "我的角色描述 Tokens",
"Most tokens": "最多Tokens",
"Least tokens": "最少Tokens",
"Random": "随机",
"Skip Example Dialogues Formatting": "跳过示例对话格式",
"Skip Example Dialogues Formatting": "跳过示例对话格式",
"Import a theme file": "导入主题文件",
"Export a theme file": "导出主题文件",
"Unlocked Context Size": "解锁上下文长度",
"Display the response bit by bit as it is generated.": "逐位显示生成的响应。",
"When this is off, responses will be displayed all at once when they are complete.": "当此选项关闭时,响应将在完成一次性显示。",
"Display the response bit by bit as it is generated.": "随着响应的生成,逐步显示结果。",
"When this is off, responses will be displayed all at once when they are complete.": "当此选项关闭时,响应将在完成一次性显示。",
"Quick Prompts Edit": "快速提示词编辑",
"Enable OpenAI completion streaming": "启用OpenAI完成流",
"Enable OpenAI completion streaming": "启用OpenAI式传输补全",
"Main": "主要",
"Utility Prompts": "Utility Prompts 实用提示词",
"Utility Prompts": "实用提示词",
"Add character names": "添加角色名称",
"Send names in the message objects. Helps the model to associate messages with characters.": "在消息对象中发送名称有助于模型将消息与角色关联起来。",
"Continue prefill": "继续预填充",
"Continue sends the last message as assistant role instead of system message with instruction.": "继续将上一条消息发送为助手角色,而不是带有说明的系统消息。",
"Send names in the message objects. Helps the model to associate messages with characters.": "在消息对象中发送名称有助于模型将消息与角色关联起来。",
"Continue prefill": "继续预填充",
"Continue sends the last message as assistant role instead of system message with instruction.": "继续以AI助手的角色发送最后一条消息而不是带有指令的系统消息。",
"Squash system messages": "压缩系统消息",
"Combines consecutive system messages into one (excluding example dialogues). May improve coherence for some models.": "将连续的系统消息合并为一条(不包括示例对话)可能会提高一些模型的连贯性。",
"Combines consecutive system messages into one (excluding example dialogues). May improve coherence for some models.": "将连续的系统消息合并为一条(不包括示例对话)可能会提高一些模型的连贯性。",
"Send inline images": "发送内联图像",
"Assistant Prefill": "助手预填充",
"Start Claude's answer with...": "以以下内容开始Claude克劳德的回答...",
"Use system prompt (Claude 2.1+ only)": "使用系统提示词仅适用于Claude 2.1+",
"Start Claude's answer with...": "以如下内容开始Claude的回答...",
"Use system prompt (Claude 2.1+ only)": "使用系统提示词仅适用于Claude 2.1+",
"Send the system prompt for supported models. If disabled, the user message is added to the beginning of the prompt.": "为支持的模型发送系统提示词。如果禁用,则用户消息将添加到提示词的开头。",
"Prompts": "提示词",
"Total Tokens:": "总Token数",
@ -883,7 +884,7 @@
"Export this prompt list": "导出此提示词列表",
"Reset current character": "重置当前角色",
"New prompt": "新提示词",
"Tokens": "Tokens Token",
"Tokens": "Tokens",
"Want to update?": "获取最新版本",
"How to start chatting?": "如何快速开始聊天?",
"Click": "点击",
@ -899,8 +900,8 @@
"Join the SillyTavern Discord": "加入SillyTavern Discord",
"Post a GitHub issue": "发布GitHub问题",
"Contact the developers": "联系开发人员",
"Nucleus Sampling": "核采样",
"Typical P": "Typical P 典型P",
"Nucleus Sampling": "核采样",
"Typical P": "典型P",
"Top K Sampling": "Top K 采样",
"Top A Sampling": "Top A 采样",
"Off": "关闭",
@ -909,9 +910,9 @@
"Medium": "中",
"Aggressive": "激进",
"Very aggressive": "非常激进",
"Eta cutoff is the main parameter of the special Eta Sampling technique.&#13;In units of 1e-4; a reasonable value is 3.&#13;Set to 0 to disable.&#13;See the paper Truncation Sampling as Language Model Desmoothing by Hewitt et al. (2022) for details.": "Eta截止是特殊Eta采样技术的主要参数。&#13;以1e-4为单位合理的值为3。&#13;设置为0以禁用。&#13;有关详细信息请参阅Hewitt等人的论文《Truncation Sampling as Language Model Desmoothing》2022年",
"Learn how to contribute your idle GPU cycles to the Horde": "了解如何将您的空闲GPU时间分享给Horde",
"Use the appropriate tokenizer for Google models via their API. Slower prompt processing, but offers much more accurate token counting.": "通过其API为Google模型使用适当的标记器。处理速度较慢但提供更准确的Token计数。",
"Eta cutoff is the main parameter of the special Eta Sampling technique.\nIn units of 1e-4; a reasonable value is 3.\nSet to 0 to disable.\nSee the paper Truncation Sampling as Language Model Desmoothing by Hewitt et al. (2022) for details.": "Eta截止是特殊Eta采样技术的主要参数。\n以1e-4为单位合理的值为3。\n设置为0以禁用。\n有关详细信息请参阅Hewitt等人的论文 Truncation Sampling as Language Model Desmoothing (2022)",
"Learn how to contribute your idle GPU cycles to the Horde": "了解如何将您的空闲GPU算力分享给Horde",
"Use the appropriate tokenizer for Google models via their API. Slower prompt processing, but offers much more accurate token counting.": "通过其API为Google模型使用适当的分词器。处理速度较慢但提供更准确的Token计数。",
"Load koboldcpp order": "加载koboldcpp顺序",
"Use Google Tokenizer": "使用Google标记器"
"Use Google Tokenizer": "使用Google分词器"
}

View File

@ -5981,7 +5981,7 @@ function getUserAvatarBlock(name) {
const personaName = power_user.personas[name];
const personaDescription = power_user.persona_descriptions[name]?.description;
template.find('.ch_name').text(personaName || '[Unnamed Persona]');
template.find('.ch_description').text(personaDescription || '[No description]').toggleClass('text_muted', !personaDescription);
template.find('.ch_description').text(personaDescription || $('#user_avatar_block').attr('no_desc_text')).toggleClass('text_muted', !personaDescription);
template.attr('imgfile', name);
template.find('.avatar').attr('imgfile', name).attr('title', name);
template.toggleClass('default_persona', name === power_user.default_persona);

View File

@ -275,7 +275,7 @@ export async function favsToHotswap() {
//helpful instruction message if no characters are favorited
if (favs.length == 0) {
container.html('<small><span><i class="fa-solid fa-star"></i> <span data-i18n="Favorite characters to add them to HotSwaps">Favorite characters to add them to HotSwaps</span></span></small>');
container.html(`<small><span><i class="fa-solid fa-star"></i>${DOMPurify.sanitize(container.attr('no_favs'))}</span></small>`);
return;
}
@ -285,7 +285,8 @@ export async function favsToHotswap() {
//changes input bar and send button display depending on connection status
function RA_checkOnlineStatus() {
if (online_status == 'no_connection') {
$('#send_textarea').attr('placeholder', 'Not connected to API!'); //Input bar placeholder tells users they are not connected
const send_textarea = $('#send_textarea');
send_textarea.attr('placeholder', send_textarea.attr('no_connection_text')); //Input bar placeholder tells users they are not connected
$('#send_form').addClass('no-connection'); //entire input form area is red when not connected
$('#send_but').addClass('displayNone'); //send button is hidden when not connected;
$('#mes_continue').addClass('displayNone'); //continue button is hidden when not connected;
@ -294,7 +295,8 @@ function RA_checkOnlineStatus() {
connection_made = false;
} else {
if (online_status !== undefined && online_status !== 'no_connection') {
$('#send_textarea').attr('placeholder', 'Type a message, or /? for help'); //on connect, placeholder tells user to type message
const send_textarea = $('#send_textarea');
send_textarea.attr('placeholder', send_textarea.attr('connected_text')); //on connect, placeholder tells user to type message
$('#send_form').removeClass('no-connection');
$('#API-status-top').removeClass('fa-plug-circle-exclamation redOverlayGlow');
$('#API-status-top').addClass('fa-plug');

View File

@ -14,6 +14,8 @@ class ElevenLabsTtsProvider {
defaultSettings = {
stability: 0.75,
similarity_boost: 0.75,
style_exaggeration: 0.00,
speaker_boost: true,
apiKey: '',
model: 'eleven_monolingual_v1',
voiceMap: {},
@ -26,27 +28,57 @@ class ElevenLabsTtsProvider {
<input id="elevenlabs_tts_api_key" type="text" class="text_pole" placeholder="<API Key>"/>
<label for="elevenlabs_tts_model">Model</label>
<select id="elevenlabs_tts_model" class="text_pole">
<option value="eleven_monolingual_v1">Monolingual</option>
<option value="eleven_monolingual_v1">English v1</option>
<option value="eleven_multilingual_v1">Multilingual v1</option>
<option value="eleven_multilingual_v2">Multilingual v2</option>
<option value="eleven_turbo_v2">Turbo v2</option>
</select>
<input id="eleven_labs_connect" class="menu_button" type="button" value="Connect" />
<label for="elevenlabs_tts_stability">Stability: <span id="elevenlabs_tts_stability_output"></span></label>
<input id="elevenlabs_tts_stability" type="range" value="${this.defaultSettings.stability}" min="0" max="1" step="0.05" />
<input id="elevenlabs_tts_stability" type="range" value="${this.defaultSettings.stability}" min="0" max="1" step="0.01" />
<label for="elevenlabs_tts_similarity_boost">Similarity Boost: <span id="elevenlabs_tts_similarity_boost_output"></span></label>
<input id="elevenlabs_tts_similarity_boost" type="range" value="${this.defaultSettings.similarity_boost}" min="0" max="1" step="0.05" />
<input id="elevenlabs_tts_similarity_boost" type="range" value="${this.defaultSettings.similarity_boost}" min="0" max="1" step="0.01" />
<div id="elevenlabs_tts_v2_options" style="display: none;">
<label for="elevenlabs_tts_style_exaggeration">Style Exaggeration: <span id="elevenlabs_tts_style_exaggeration_output"></span></label>
<input id="elevenlabs_tts_style_exaggeration" type="range" value="${this.defaultSettings.style_exaggeration}" min="0" max="1" step="0.01" />
<label for="elevenlabs_tts_speaker_boost">Speaker Boost:</label>
<input id="elevenlabs_tts_speaker_boost" style="display: inline-grid" type="checkbox" />
</div>
<hr>
<div id="elevenlabs_tts_voice_cloning">
<span>Instant Voice Cloning</span><br>
<input id="elevenlabs_tts_voice_cloning_name" type="text" class="text_pole" placeholder="Voice Name"/>
<input id="elevenlabs_tts_voice_cloning_description" type="text" class="text_pole" placeholder="Voice Description"/>
<input id="elevenlabs_tts_voice_cloning_labels" type="text" class="text_pole" placeholder="Labels"/>
<div class="menu_button menu_button_icon" id="upload_audio_file">
<i class="fa-solid fa-file-import"></i>
<span>Upload Audio Files</span>
</div>
<input id="elevenlabs_tts_audio_files" type="file" name="audio_files" accept="audio/*" style="display: none;" multiple>
<div id="elevenlabs_tts_selected_files_list"></div>
<input id="elevenlabs_tts_clone_voice_button" class="menu_button menu_button_icon" type="button" value="Clone Voice">
</div>
<hr>
</div>
`;
return html;
}
shouldInvolveExtendedSettings() {
return this.settings.model === 'eleven_multilingual_v2';
}
onSettingsChange() {
// Update dynamically
this.settings.stability = $('#elevenlabs_tts_stability').val();
this.settings.similarity_boost = $('#elevenlabs_tts_similarity_boost').val();
this.settings.style_exaggeration = $('#elevenlabs_tts_style_exaggeration').val();
this.settings.speaker_boost = $('#elevenlabs_tts_speaker_boost').is(':checked');
this.settings.model = $('#elevenlabs_tts_model').find(':selected').val();
$('#elevenlabs_tts_stability_output').text(this.settings.stability);
$('#elevenlabs_tts_similarity_boost_output').text(this.settings.similarity_boost);
$('#elevenlabs_tts_stability_output').text(this.settings.stability * 100 + '%');
$('#elevenlabs_tts_similarity_boost_output').text(this.settings.similarity_boost * 100 + '%');
$('#elevenlabs_tts_style_exaggeration_output').text(this.settings.style_exaggeration * 100 + '%');
$('#elevenlabs_tts_v2_options').toggle(this.shouldInvolveExtendedSettings());
saveTtsProviderSettings();
}
@ -75,21 +107,28 @@ class ElevenLabsTtsProvider {
$('#elevenlabs_tts_stability').val(this.settings.stability);
$('#elevenlabs_tts_similarity_boost').val(this.settings.similarity_boost);
$('#elevenlabs_tts_style_exaggeration').val(this.settings.style_exaggeration);
$('#elevenlabs_tts_speaker_boost').prop('checked', this.settings.speaker_boost);
$('#elevenlabs_tts_api_key').val(this.settings.apiKey);
$('#elevenlabs_tts_model').val(this.settings.model);
$('#eleven_labs_connect').on('click', () => { this.onConnectClick(); });
$('#elevenlabs_tts_similarity_boost').on('input', this.onSettingsChange.bind(this));
$('#elevenlabs_tts_stability').on('input', this.onSettingsChange.bind(this));
$('#elevenlabs_tts_style_exaggeration').on('input', this.onSettingsChange.bind(this));
$('#elevenlabs_tts_speaker_boost').on('change', this.onSettingsChange.bind(this));
$('#elevenlabs_tts_model').on('change', this.onSettingsChange.bind(this));
$('#elevenlabs_tts_stability_output').text(this.settings.stability);
$('#elevenlabs_tts_similarity_boost_output').text(this.settings.similarity_boost);
$('#elevenlabs_tts_style_exaggeration_output').text(this.settings.style_exaggeration);
$('#elevenlabs_tts_v2_options').toggle(this.shouldInvolveExtendedSettings());
try {
await this.checkReady();
console.debug('ElevenLabs: Settings loaded');
} catch {
console.debug('ElevenLabs: Settings loaded, but not ready');
}
this.setupVoiceCloningMenu();
}
// Perform a simple readiness check by trying to fetch voiceIds
@ -107,6 +146,63 @@ class ElevenLabsTtsProvider {
});
}
setupVoiceCloningMenu() {
const audioFilesInput = document.getElementById('elevenlabs_tts_audio_files');
const selectedFilesListElement = document.getElementById('elevenlabs_tts_selected_files_list');
const cloneVoiceButton = document.getElementById('elevenlabs_tts_clone_voice_button');
const uploadAudioFileButton = document.getElementById('upload_audio_file');
const voiceCloningNameInput = document.getElementById('elevenlabs_tts_voice_cloning_name');
const voiceCloningDescriptionInput = document.getElementById('elevenlabs_tts_voice_cloning_description');
const voiceCloningLabelsInput = document.getElementById('elevenlabs_tts_voice_cloning_labels');
const updateCloneVoiceButtonVisibility = () => {
cloneVoiceButton.style.display = audioFilesInput.files.length > 0 ? 'inline-block' : 'none';
};
const clearSelectedFiles = () => {
audioFilesInput.value = '';
selectedFilesListElement.innerHTML = '';
updateCloneVoiceButtonVisibility();
};
uploadAudioFileButton.addEventListener('click', () => {
audioFilesInput.click();
});
audioFilesInput.addEventListener('change', () => {
selectedFilesListElement.innerHTML = '';
for (const file of audioFilesInput.files) {
const listItem = document.createElement('div');
listItem.textContent = file.name;
selectedFilesListElement.appendChild(listItem);
}
updateCloneVoiceButtonVisibility();
});
cloneVoiceButton.addEventListener('click', async () => {
const voiceName = voiceCloningNameInput.value.trim();
const voiceDescription = voiceCloningDescriptionInput.value.trim();
const voiceLabels = voiceCloningLabelsInput.value.trim();
if (!voiceName) {
toastr.error('Please provide a name for the cloned voice.');
return;
}
try {
await this.addVoice(voiceName, voiceDescription, voiceLabels);
toastr.success('Voice cloned successfully. Hit reload to see the new voice in the voice listing.');
clearSelectedFiles();
voiceCloningNameInput.value = '';
voiceCloningDescriptionInput.value = '';
voiceCloningLabelsInput.value = '';
} catch (error) {
toastr.error(`Failed to clone voice: ${error.message}`);
}
});
updateCloneVoiceButtonVisibility();
}
async updateApiKey() {
// Using this call to validate API key
@ -206,24 +302,26 @@ class ElevenLabsTtsProvider {
async fetchTtsGeneration(text, voiceId) {
let model = this.settings.model ?? 'eleven_monolingual_v1';
console.info(`Generating new TTS for voice_id ${voiceId}, model ${model}`);
const response = await fetch(
`https://api.elevenlabs.io/v1/text-to-speech/${voiceId}`,
{
method: 'POST',
headers: {
'xi-api-key': this.settings.apiKey,
'Content-Type': 'application/json',
},
body: JSON.stringify({
model_id: model,
text: text,
voice_settings: {
stability: Number(this.settings.stability),
similarity_boost: Number(this.settings.similarity_boost),
},
}),
const request = {
model_id: model,
text: text,
voice_settings: {
stability: Number(this.settings.stability),
similarity_boost: Number(this.settings.similarity_boost),
},
);
};
if (this.shouldInvolveExtendedSettings()) {
request.voice_settings.style_exaggeration = Number(this.settings.style_exaggeration);
request.voice_settings.speaker_boost = Boolean(this.settings.speaker_boost);
}
const response = await fetch(`https://api.elevenlabs.io/v1/text-to-speech/${voiceId}`, {
method: 'POST',
headers: {
'xi-api-key': this.settings.apiKey,
'Content-Type': 'application/json',
},
body: JSON.stringify(request),
});
if (!response.ok) {
toastr.error(response.statusText, 'TTS Generation Failed');
throw new Error(`HTTP ${response.status}: ${await response.text()}`);
@ -260,4 +358,33 @@ class ElevenLabsTtsProvider {
const responseJson = await response.json();
return responseJson.history;
}
async addVoice(name, description, labels) {
const selected_files = document.querySelectorAll('input[type="file"][name="audio_files"]');
const formData = new FormData();
formData.append('name', name);
formData.append('description', description);
formData.append('labels', labels);
for (const file of selected_files) {
if (file.files.length > 0) {
formData.append('files', file.files[0]);
}
}
const response = await fetch('https://api.elevenlabs.io/v1/voices/add', {
method: 'POST',
headers: {
'xi-api-key': this.settings.apiKey,
},
body: formData,
});
if (!response.ok) {
throw new Error(`HTTP ${response.status}: ${await response.text()}`);
}
return await response.json();
}
}

View File

@ -260,6 +260,7 @@ const default_settings = {
use_ai21_tokenizer: false,
use_google_tokenizer: false,
claude_use_sysprompt: false,
use_makersuite_sysprompt: true,
use_alt_scale: false,
squash_system_messages: false,
image_inlining: false,
@ -330,6 +331,7 @@ const oai_settings = {
use_ai21_tokenizer: false,
use_google_tokenizer: false,
claude_use_sysprompt: false,
use_makersuite_sysprompt: true,
use_alt_scale: false,
squash_system_messages: false,
image_inlining: false,
@ -1733,6 +1735,7 @@ async function sendOpenAIRequest(type, messages, signal) {
const stopStringsLimit = 3; // 5 - 2 (nameStopString and new_chat_prompt)
generate_data['top_k'] = Number(oai_settings.top_k_openai);
generate_data['stop'] = [nameStopString, substituteParams(oai_settings.new_chat_prompt), ...getCustomStoppingStrings(stopStringsLimit)];
generate_data['use_makersuite_sysprompt'] = oai_settings.use_makersuite_sysprompt;
}
if (isAI21) {
@ -2668,6 +2671,7 @@ function loadOpenAISettings(data, settings) {
if (settings.use_ai21_tokenizer !== undefined) { oai_settings.use_ai21_tokenizer = !!settings.use_ai21_tokenizer; oai_settings.use_ai21_tokenizer ? ai21_max = 8191 : ai21_max = 9200; }
if (settings.use_google_tokenizer !== undefined) oai_settings.use_google_tokenizer = !!settings.use_google_tokenizer;
if (settings.claude_use_sysprompt !== undefined) oai_settings.claude_use_sysprompt = !!settings.claude_use_sysprompt;
if (settings.use_makersuite_sysprompt !== undefined) oai_settings.use_makersuite_sysprompt = !!settings.use_makersuite_sysprompt;
if (settings.use_alt_scale !== undefined) { oai_settings.use_alt_scale = !!settings.use_alt_scale; updateScaleForm(); }
$('#stream_toggle').prop('checked', oai_settings.stream_openai);
$('#api_url_scale').val(oai_settings.api_url_scale);
@ -2707,6 +2711,7 @@ function loadOpenAISettings(data, settings) {
$('#use_ai21_tokenizer').prop('checked', oai_settings.use_ai21_tokenizer);
$('#use_google_tokenizer').prop('checked', oai_settings.use_google_tokenizer);
$('#claude_use_sysprompt').prop('checked', oai_settings.claude_use_sysprompt);
$('#use_makersuite_sysprompt').prop('checked', oai_settings.use_makersuite_sysprompt);
$('#scale-alt').prop('checked', oai_settings.use_alt_scale);
$('#openrouter_use_fallback').prop('checked', oai_settings.openrouter_use_fallback);
$('#openrouter_force_instruct').prop('checked', oai_settings.openrouter_force_instruct);
@ -2976,6 +2981,7 @@ async function saveOpenAIPreset(name, settings, triggerUi = true) {
use_ai21_tokenizer: settings.use_ai21_tokenizer,
use_google_tokenizer: settings.use_google_tokenizer,
claude_use_sysprompt: settings.claude_use_sysprompt,
use_makersuite_sysprompt: settings.use_makersuite_sysprompt,
use_alt_scale: settings.use_alt_scale,
squash_system_messages: settings.squash_system_messages,
image_inlining: settings.image_inlining,
@ -3354,6 +3360,7 @@ function onSettingsPresetChange() {
use_ai21_tokenizer: ['#use_ai21_tokenizer', 'use_ai21_tokenizer', true],
use_google_tokenizer: ['#use_google_tokenizer', 'use_google_tokenizer', true],
claude_use_sysprompt: ['#claude_use_sysprompt', 'claude_use_sysprompt', true],
use_makersuite_sysprompt: ['#use_makersuite_sysprompt', 'use_makersuite_sysprompt', true],
use_alt_scale: ['#use_alt_scale', 'use_alt_scale', true],
squash_system_messages: ['#squash_system_messages', 'squash_system_messages', true],
image_inlining: ['#openai_image_inlining', 'image_inlining', true],
@ -4290,6 +4297,11 @@ $(document).ready(async function () {
saveSettingsDebounced();
});
$('#use_makersuite_sysprompt').on('change', function () {
oai_settings.use_makersuite_sysprompt = !!$('#use_makersuite_sysprompt').prop('checked');
saveSettingsDebounced();
});
$('#send_if_empty_textarea').on('input', function () {
oai_settings.send_if_empty = String($('#send_if_empty_textarea').val());
saveSettingsDebounced();

View File

@ -404,7 +404,7 @@ function onPersonaDescriptionInput() {
}
$(`.avatar-container[imgfile="${user_avatar}"] .ch_description`)
.text(power_user.persona_description || '[No description]')
.text(power_user.persona_description || $('#user_avatar_block').attr('no_desc_text'))
.toggleClass('text_muted', !power_user.persona_description);
saveSettingsDebounced();
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 122 KiB

After

Width:  |  Height:  |  Size: 119 KiB

BIN
public/st.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 122 KiB

View File

@ -252,17 +252,25 @@ async function sendMakerSuiteRequest(request, response) {
};
function getGeminiBody() {
return {
contents: convertGooglePrompt(request.body.messages, model),
const should_use_system_prompt = model === 'gemini-1.5-pro-latest' && request.body.use_makersuite_sysprompt;
const prompt = convertGooglePrompt(request.body.messages, model, should_use_system_prompt, request.body.char_name, request.body.user_name);
let body = {
contents: prompt.contents,
safetySettings: GEMINI_SAFETY,
generationConfig: generationConfig,
};
if (should_use_system_prompt) {
body.system_instruction = prompt.system_instruction;
}
return body;
}
function getBisonBody() {
const prompt = isText
? ({ text: convertTextCompletionPrompt(request.body.messages) })
: ({ messages: convertGooglePrompt(request.body.messages, model) });
: ({ messages: convertGooglePrompt(request.body.messages, model).contents });
/** @type {any} Shut the lint up */
const bisonBody = {
@ -558,7 +566,7 @@ async function sendCohereRequest(request, response) {
}
try {
const convertedHistory = convertCohereMessages(request.body.messages);
const convertedHistory = convertCohereMessages(request.body.messages, request.body.char_name, request.body.user_name);
// https://docs.cohere.com/reference/chat
const requestBody = {

View File

@ -399,7 +399,7 @@ router.post('/google/count', jsonParser, async function (req, res) {
accept: 'application/json',
'content-type': 'application/json',
},
body: JSON.stringify({ contents: convertGooglePrompt(req.body, String(req.query.model)) }),
body: JSON.stringify({ contents: convertGooglePrompt(req.body, String(req.query.model)).contents }),
};
try {
const key = readSecret(req.user.directories, SECRET_KEYS.MAKERSUITE);

View File

@ -252,9 +252,12 @@ function convertCohereMessages(messages, charName = '', userName = '') {
* Convert a prompt from the ChatML objects to the format used by Google MakerSuite models.
* @param {object[]} messages Array of messages
* @param {string} model Model name
* @returns {object[]} Prompt for Google MakerSuite models
* @param {boolean} useSysPrompt Use system prompt
* @param {string} charName Character name
* @param {string} userName User name
* @returns {{contents: *[], system_instruction: {parts: {text: string}}}} Prompt for Google MakerSuite models
*/
function convertGooglePrompt(messages, model) {
function convertGooglePrompt(messages, model, useSysPrompt = false, charName = '', userName = '') {
// This is a 1x1 transparent PNG
const PNG_PIXEL = 'iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII=';
@ -267,6 +270,27 @@ function convertGooglePrompt(messages, model) {
const isMultimodal = visionSupportedModels.includes(model);
let hasImage = false;
let sys_prompt = '';
if (useSysPrompt) {
while (messages.length > 1 && messages[0].role === 'system') {
// Append example names if not already done by the frontend (e.g. for group chats).
if (userName && messages[0].name === 'example_user') {
if (!messages[0].content.startsWith(`${userName}: `)) {
messages[0].content = `${userName}: ${messages[0].content}`;
}
}
if (charName && messages[0].name === 'example_assistant') {
if (!messages[0].content.startsWith(`${charName}: `)) {
messages[0].content = `${charName}: ${messages[0].content}`;
}
}
sys_prompt += `${messages[0].content}\n\n`;
messages.shift();
}
}
const system_instruction = { parts: { text: sys_prompt.trim() } };
const contents = [];
messages.forEach((message, index) => {
// fix the roles
@ -327,7 +351,7 @@ function convertGooglePrompt(messages, model) {
});
}
return contents;
return { contents: contents, system_instruction: system_instruction };
}
/**