Narrative design scripting reference
Reference for controlling a character's narrative flow from code, covering section events, trigger invocation, scripted speech, and data fetching.
The Inspector workflow covers the majority of use cases. This page documents the full C# surface for situations where you need programmatic control — dynamic character switching, async data fetching at runtime, runtime-generated narrative flows, or deep integration with your own game systems.
All capabilities described here are available through IConvaiNarrativeDesign, exposed on every ConvaiCharacter via the NarrativeDesign property. ConvaiNarrativeDesignManager and ConvaiNarrativeDesignTrigger both delegate to this interface internally, so everything you configure in the Inspector is also reachable from code.
Access the character API
Every ConvaiCharacter exposes a NarrativeDesign property that returns an IConvaiNarrativeDesign implementation:
ConvaiCharacter character = GetComponent<ConvaiCharacter>();
IConvaiNarrativeDesign narrative = character.NarrativeDesign;Properties
TemplateKeys
IReadOnlyDictionary<string, string>
Snapshot of all template keys currently tracked for this character.
CurrentSectionId
string
The section ID most recently received from Convai. Empty string if no section has been received yet.
CurrentSectionData
NarrativeSectionData
Full section payload. Contains SectionId, BehaviorTreeCode, and BehaviorTreeConstants. null until the first section change is received.
Listen to section changes
Subscribe to these events in OnEnable and unsubscribe in OnDisable to avoid stale listeners after a component is disabled or destroyed.
private void OnEnable()
{
character.NarrativeDesign.OnSectionChanged += HandleSectionChanged;
character.NarrativeDesign.OnSectionDataReceived += HandleSectionData;
}
private void OnDisable()
{
character.NarrativeDesign.OnSectionChanged -= HandleSectionChanged;
character.NarrativeDesign.OnSectionDataReceived -= HandleSectionData;
}
private void HandleSectionChanged(string previousId, string newId)
{
Debug.Log($"Section: {previousId} → {newId}");
}
private void HandleSectionData(NarrativeSectionData data)
{
Debug.Log($"Section ID: {data.SectionId}");
// data.BehaviorTreeCode and data.BehaviorTreeConstants available here
}These events are delivered via the SDK's internal EventHub. If your handler touches Unity API (e.g., GameObject.SetActive), use ConvaiNarrativeDesignManager in the scene — it performs main-thread delivery automatically. Raw subscriptions to IConvaiNarrativeDesign events may arrive on a background thread depending on configuration.
Events
OnSectionChanged
Action<string, string>
Fires on every section transition. Parameters: previousId, newId.
OnSectionDataReceived
Action<NarrativeSectionData>
Fires on every section transition with the full payload.
OnTriggerInvoked
Action<ConvaiNarrativeTriggerInvocation>
Fires after a trigger or speech request is accepted locally (before confirmation from Convai).
Invoke triggers from code
InvokeTrigger sends a saved Narrative Design trigger by name. The SDK trims whitespace, rejects an empty name, and sends only trigger_name over RTVI. It returns true when the request is accepted locally and queues the trigger if the session is not yet open.
Use InvokeEvent when you want to send contextual event text instead of a saved graph trigger:
InvokeEvent sends only trigger_message over RTVI. Convai treats the message as inline context and responds naturally; it does not select a saved trigger by name.
Control character speech
InvokeSpeech sends exact scripted speech without advancing the narrative graph. Pass the text you want the character to say; the SDK wraps it in <speak>...</speak> internally before sending trigger_message.
Do not include <speak> tags in Unity code. Use InvokeEvent for contextual events where Convai should decide the wording.
InvokeTrigger("TriggerName")
trigger_name
Invokes a saved Narrative Design trigger and can advance the graph.
InvokeEvent("event text")
trigger_message
Adds inline event context and lets Convai respond naturally.
InvokeSpeech("scripted text")
trigger_message
Sends exact scripted speech; the SDK adds <speak> tags internally.
Listen to trigger invocations
ConvaiNarrativeTriggerInvocation fields:
Request
ConvaiNarrativeTriggerRequest
Typed request accepted by the SDK. Includes the mode, wire field name, and wire field value.
TriggerName
string
Saved trigger name. Empty for inline events and scripted speech.
TriggerMessage
string
Inline event text or SDK-generated scripted speech payload. Empty for saved triggers.
Queued
bool
true if the trigger was deferred because the session was not yet open.
Template keys via code
Both methods send immediately if the session is open, or queue for the next connection if it is not.
The character-level API and ConvaiNarrativeDesignManager's methods converge on the same transport internally. Use the Manager's methods when you want the keys visible and editable in the Inspector; use the character API for purely code-driven flows where Inspector visibility is not needed.
Fetch sections and triggers
Via the character API
NarrativeSectionInfo fields: SectionId, SectionName.
NarrativeTriggerInfo fields: TriggerId, TriggerName, TriggerMessage, DestinationSection.
Via the static fetcher
NarrativeDesignFetcher provides the same data without needing a character component reference — useful in Editor tooling or loading screens:
FetchResult<T> fields:
Success
bool
true if the request succeeded.
Data
T
The fetched data. default if Success is false.
Error
string
Error message. null if Success is true.
Advanced runtime control
Reset controller state
Reconfigure ConvaiNarrativeDesignTrigger from code
All Inspector-configurable settings have corresponding setter methods:
ClearAllSectionConfigs() removes all UnitySectionEventConfig entries and all Unity Event wiring. This cannot be undone at runtime. Call it only when you have confirmed you are switching to a different character and no longer need the existing section event bindings.
Component relationships
ConvaiNarrativeDesignManager and ConvaiNarrativeDesignTrigger both delegate to IConvaiNarrativeDesign. The CharacterNarrativeDesignFacade implements the interface and manages the pending queue; ConnectionService handles the actual RTVI transport.
Next steps
Narrative design usage examplesTroubleshoot narrative designLast updated
Was this helpful?