Add customizable prompts editor and reorganize settings panel
- Reorganized settings: moved Auto-update, Narrator Mode, and Debug Mode to Advanced section - Added Customize Prompts button with comprehensive prompts editor modal - Implemented 7 customizable AI prompts: HTML, plot progression (random/natural), avatar generation, tracker instructions, tracker continuation, and combat narrative - Added individual and bulk restore to defaults functionality - Integrated custom prompts across generation modules (plotProgression, promptBuilder, encounterPrompts) - Auto-update toggle now disabled when not in Separate generation mode - Merged XML/Markdown tracker instructions into unified prompt
This commit is contained in:
@@ -513,11 +513,18 @@ export async function buildCombatActionPrompt(action, combatStats) {
|
||||
stateMessage += `If all enemies are defeated or escape: add "combatEnd": true, "result": "victory". If all party defeated: add "combatEnd": true, "result": "defeat". It's also possible for the encounter to be interrupted by external interference (e.g., an explosion knocks everyone out, sudden environmental catastrophe, third party intervention, etc.). If this occurs, add "combatEnd": true, "result": "interrupted". Each status (if applied) has a format: {"name": "Status Name", "emoji": "💀", "duration": X}.\n`;
|
||||
stateMessage += `Scale combat difficulty appropriately: Powerful entities (gods, dragons, legendary creatures) should be formidable challenges requiring multiple rounds and strategic play. Weaker foes (common animals, basic enemies, minions) should be resolved more quickly, typically 2-4 rounds. Match HP damage and combat pacing to the narrative weight of the encounter. A wolf should not take 20 rounds to defeat, nor should a deity fall in one hit.\n`;
|
||||
stateMessage += `For the narrative, write it with intent in ${tense} tense ${person}-person ${narration} from ${pov}'s point of view.\n`;
|
||||
stateMessage += `Build novel prose. Break patterns from your previous responses by varying sentence structures, rhythms, formats, and openings. Track whether a sentence shape, cadence, sensory detail, or a descriptor appeared recently, and replace it with a different one or skip it entirely. If you mentioned a physical feature, mannerism, or expression once, move on. Don't fixate on the same traits every turn. Well-placed humor, unconventional similes, and subverted turns of phrase are encouraged. Avoid GPTisms, purple prose, and anaphoras, especially the negatives with "no/not/wasn't/didn't." Refrain from describing actions or emotions via negation; focus on what does happen, not what doesn't. Absolutely no asterisks, ellipses, or em-dashes. Explicit content is allowed, no plot armor. Do not play for ${userName}. Keep your response length under 150 words. Never end on handover cues; finish naturally.\n`;
|
||||
stateMessage += `CRITICAL: Do not repeat, echo, parrot, or restate distinctive words, phrases, and dialogues from the user's last message. If reacting to speech, show interpretation or response, not repetition.\n`;
|
||||
stateMessage += `EXAMPLE: "Are you a gooner?" User asks.\n`;
|
||||
stateMessage += `BAD: "Gooner?"\n`;
|
||||
stateMessage += `GOOD: A flat look. "What type of question is that?"`;
|
||||
|
||||
// Use custom combat narrative prompt if available
|
||||
const customCombatPrompt = extensionSettings.customCombatNarrativePrompt;
|
||||
if (customCombatPrompt) {
|
||||
stateMessage += customCombatPrompt.replace(/{userName}/g, userName) + '\n';
|
||||
} else {
|
||||
stateMessage += `Build novel prose. Break patterns from your previous responses by varying sentence structures, rhythms, formats, and openings. Track whether a sentence shape, cadence, sensory detail, or a descriptor appeared recently, and replace it with a different one or skip it entirely. If you mentioned a physical feature, mannerism, or expression once, move on. Don't fixate on the same traits every turn. Well-placed humor, unconventional similes, and subverted turns of phrase are encouraged. Avoid GPTisms, purple prose, and anaphoras, especially the negatives with "no/not/wasn't/didn't." Refrain from describing actions or emotions via negation; focus on what does happen, not what doesn't. Absolutely no asterisks, ellipses, or em-dashes. Explicit content is allowed, no plot armor. Do not play for ${userName}. Keep your response length under 150 words. Never end on handover cues; finish naturally.\n`;
|
||||
stateMessage += `CRITICAL: Do not repeat, echo, parrot, or restate distinctive words, phrases, and dialogues from the user's last message. If reacting to speech, show interpretation or response, not repetition.\n`;
|
||||
stateMessage += `EXAMPLE: "Are you a gooner?" User asks.\n`;
|
||||
stateMessage += `BAD: "Gooner?"\n`;
|
||||
stateMessage += `GOOD: A flat look. "What type of question is that?"`;
|
||||
}
|
||||
|
||||
messages.push({
|
||||
role: 'user',
|
||||
|
||||
@@ -236,11 +236,20 @@ export function generateTrackerInstructions(includeHtmlPrompt = true, includeCon
|
||||
|
||||
// Universal instruction header
|
||||
if (useXmlTags) {
|
||||
instructions += `\nAt the start of every reply, you must attach an update to the trackers in EXACTLY the same format as below, enclosed in <trackers></trackers> XML tags. Replace X with actual numbers (e.g., 69) and replace all [placeholders] with concrete in-world details that ${userName} perceives about the current scene and the present characters. Do NOT keep the brackets or placeholder text in your response. For example: [Location] becomes Forest Clearing, [Mood Emoji] becomes 😊. Consider the last trackers in the conversation (if they exist). Manage them accordingly and realistically; raise, lower, change, or keep the values unchanged based on the user's actions, the passage of time, and logical consequences (0% if the time progressed only by a few minutes, 1-5% normally, and above 5% only if a major time-skip/event occurs).
|
||||
`;
|
||||
// Format specification is always hardcoded
|
||||
instructions += `\nAt the start of every reply, you must attach an update to the trackers in EXACTLY the same format as below, enclosed in <trackers></trackers> XML tags. `;
|
||||
} else {
|
||||
instructions += `\nAt the start of every reply, you must attach an update to the trackers in EXACTLY the same format as below, enclosed in separate Markdown code fences. Replace X with actual numbers (e.g., 69) and replace all [placeholders] with concrete in-world details that ${userName} perceives about the current scene and the present characters. Do NOT keep the brackets or placeholder text in your response. For example: [Location] becomes Forest Clearing, [Mood Emoji] becomes 😊. Consider the last trackers in the conversation (if they exist). Manage them accordingly and realistically; raise, lower, change, or keep the values unchanged based on the user's actions, the passage of time, and logical consequences (0% if the time progressed only by a few minutes, 1-5% normally, and above 5% only if a major time-skip/event occurs).
|
||||
`;
|
||||
// Format specification is always hardcoded
|
||||
instructions += `\nAt the start of every reply, you must attach an update to the trackers in EXACTLY the same format as below, enclosed in separate Markdown code fences. `;
|
||||
}
|
||||
|
||||
// Append custom instruction portion if available (same for both XML and Markdown)
|
||||
const customPrompt = extensionSettings.customTrackerInstructionsPrompt;
|
||||
if (customPrompt) {
|
||||
instructions += customPrompt.replace(/{userName}/g, userName);
|
||||
} else {
|
||||
instructions += `Replace X with actual numbers (e.g., 69) and replace all [placeholders] with concrete in-world details that ${userName} perceives about the current scene and the present characters. Do NOT keep the brackets or placeholder text in your response. For example: [Location] becomes Forest Clearing, [Mood Emoji] becomes 😊. `;
|
||||
instructions += `Consider the last trackers in the conversation (if they exist). Manage them accordingly and realistically; raise, lower, change, or keep the values unchanged based on the user's actions, the passage of time, and logical consequences (0% if the time progressed only by a few minutes, 1-5% normally, and above 5% only if a major time-skip/event occurs).`;
|
||||
}
|
||||
|
||||
// Add format specifications for each enabled tracker
|
||||
@@ -394,7 +403,12 @@ export function generateTrackerInstructions(includeHtmlPrompt = true, includeCon
|
||||
|
||||
// Only add continuation instruction if includeContinuation is true
|
||||
if (includeContinuation) {
|
||||
instructions += `After updating the trackers, continue directly from where the last message in the chat history left off. Ensure the trackers you provide naturally reflect and influence the narrative. Character behavior, dialogue, and story events should acknowledge these conditions when relevant, such as fatigue affecting the protagonist's performance, low hygiene influencing their social interactions, environmental factors shaping the scene, a character's emotional state coloring their responses, and so on. Remember, all bracketed placeholders (e.g., [Location], [Mood Emoji]) MUST be replaced with actual content without the square brackets.\n\n`;
|
||||
const customPrompt = extensionSettings.customTrackerContinuationPrompt;
|
||||
if (customPrompt) {
|
||||
instructions += customPrompt + '\n\n';
|
||||
} else {
|
||||
instructions += `After updating the trackers, continue directly from where the last message in the chat history left off. Ensure the trackers you provide naturally reflect and influence the narrative. Character behavior, dialogue, and story events should acknowledge these conditions when relevant, such as fatigue affecting the protagonist's performance, low hygiene influencing their social interactions, environmental factors shaping the scene, a character's emotional state coloring their responses, and so on. Remember, all bracketed placeholders (e.g., [Location], [Mood Emoji]) MUST be replaced with actual content without the square brackets.\n\n`;
|
||||
}
|
||||
}
|
||||
|
||||
// Include attributes based on settings (only if includeAttributes is true)
|
||||
|
||||
Reference in New Issue
Block a user