Create message drafts
A MessageDraft
object is an abstraction for composing a message that has not yet been published. You can use it to:
- Edit text before it is published
- Add channel references, user mentions, links
You can display user mentions, channel references, and links (collectively called "message elements") to the user on the front end of your application by adding a message draft state listener.
- Basics
- Class diagram
- Example
- Internal mention format
Message drafts consist of MessageElement
objects, which can be either instances of Text
or MentionTarget
.
Text
are simple strings, while MentionTarget
elements are used for user mentions, channel references, and URLs. They contain a text and a reference to the linked element regardless if it's a user, a channel, or a URL.
Each MentionTarget
has a MentionType
enum property, which defines the type of mention. Available targets include:
MentionTarget::user
MentionTarget::channel
MentionTarget::url
Store draft messages locally
Unreal Chat SDK does not provide a method for storing the drafted message on the client, so whenever a user drafts a message in a chat app, changes a channel, and goes back to that channel, the drafted message gets lost.
To save drafted messages before they are published on channels, implement your own local storage mechanism suitable for the platform you use.
Consider the message Hey, I sent Alex this link on the #offtopic channel.
where:
Alex
is a reference to the user with the ID ofalex_d
link
is a URL of thewww.pubnub.com
website#offtopic
is a reference to the channel with the ID ofgroup.offtopic
The list of MessageElement
objects returned by the MessageDraftChangeListener
is as follows:
By internally leveraging a Markdown-like syntax, the message draft format integrates links directly into the message text using the pattern [link text](link target)
understood by the Unreal Chat SDK.
Mention Type | Example |
---|---|
user | [John Doe](pn-user://john_doe) |
channel | [General Chat](pn-channel://group.chat.123) |
url | [PubNub](https://www.pubnub.com) |
Custom schemas like pn-user://
and pn-channel://
are used to identify user and channel mentions, while traditional URLs are supported as-is.
Adding message elements
You don't use this Markdown-like syntax when adding message elements. It's only a representation of your message elements under the hood.
For more information, refer to Add message element.
Create a draft message
CreateMessageDraft()
creates a (MessageDraft
object) that can consist of:
- Plain text
- Mentioned users
- Referenced channels
- Links
Method signature
- Blueprint
- C++ / Input parameters
Channel->CreateMessageDraft(FPubnubMessageDraftConfig MessageDraftConfig = FPubnubMessageDraftConfig())
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
MessageDraftConfig | FPubnubMessageDraftConfig | No | FMessageDraftConfig() | Configuration for the message draft, including settings such as initial content and metadata. |
FPubnubMessageDraftConfig
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
InitialContent | FString | No | "" | The initial text content for the message draft. This can be empty and updated later. |
Metadata | FString | No | "" | JSON providing custom data related to the message, such as tags or other metadata that might be needed during the message lifecycle. |
ChannelID | FString | Yes | n/a | ID of the channel for which the message draft is being created. Each draft is associated with a specific channel. |
Output
Parameter | Type | Description |
---|---|---|
UPubnubMessageDraft* | UPubnubMessageDraft* | Pointer to the created MessageDraft object, which can be used to edit the draft, insert mentions, and eventually send the message. |
Basic usage
Create a draft message containing just plain text.
// Assuming you have a valid UPubnubChannel* pointer named Channel
// Define a configuration for the message draft if needed (using default configuration here)
FPubnubMessageDraftConfig DraftConfig; // This might include settings like initial content or behaviors
// Create a message draft from the channel with the specified configuration
UPubnubMessageDraft* MyMessageDraft = Channel->CreateMessageDraft(DraftConfig);
// Now MyMessageDraft can be used to build and send messages
MyMessageDraft->InsertText(0, "Hello there! Please review and confirm.");
MyMessageDraft->Send();
Add message draft change listener
Add a callback to listen for changes to the message draft along with receiving suggestions for user mentions, links, and channel references.
AddChangeListener()
returns all links referenced in the draft message that match the provided 3-letter string from your app's keyset.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->AddChangeListener(FOnPubnubDraftUpdated DraftUpdateCallback)
Parameter | Type | Description |
---|---|---|
DraftUpdateCallback | FOnPubnubDraftUpdated | A delegate that takes a list of current message elements (TArray<UPubnubMessageElement*> ) captured upon changes to the draft. This callback function is triggered whenever the message draft's content is updated. |
Output
This method doesn't return any data.
Basic usage
Add the listener to your message draft.
// Assuming you have a UPubnubMessageDraft pointer named MyMessageDraft
// Define your callback function to handle updates
void AMyActor::OnMessageDraftUpdate(const TArray<UPubnubMessageElement*>& MessageElements)
{
// Iterate through the current message elements and handle updates
for (const UPubnubMessageElement* Element : MessageElements)
{
// Process each element as needed
// Example: Output the text of each element to the log
UE_LOG(LogTemp, Log, TEXT("Draft Element Text: %s"), *Element->GetText());
}
}
// Set up the delegate to bind your callback
show all 23 linesAdd message draft change listener (with suggestions)
Add a callback to listen for changes to the message draft along with receiving suggestions for user mentions, links, and channel references.
AddChangeListenerWithSuggestions()
returns all links referenced in the draft message that match the provided 3-letter string from your app's keyset.
For example, if you type #Sup
, you will get the list of channels starting with Sup
like Support
or Support-Agents
. The default number of returned suggested channel names is 10
, configurable to a maximum value of 100
.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->AddChangeListenerWithSuggestions(FOnPubnubDraftUpdatedWithSuggestions DraftUpdateCallback)
Parameter | Type | Description |
---|---|---|
DraftUpdateCallback | FOnPubnubDraftUpdatedWithSuggestions | A delegate that receives updates on the current state of message elements (TArray<UPubnubMessageElement*> ) and a list of suggested mentions (TArray<FPubnubSuggestedMention> ) based on the draft's text input. This callback is triggered when there are changes to the content and suggested mentions within the message draft. |
Output
This method doesn't return any data.
Basic usage
Add the listener to your message draft.
// Assuming you have a UPubnubMessageDraft pointer named MyMessageDraft
// Define your callback function to handle updates with suggestions
void AMyActor::OnMessageDraftUpdateWithSuggestions(const TArray<UPubnubMessageElement*>& MessageElements, const TArray<FPubnubSuggestedMention>& SuggestedMentions)
{
// Iterate through the current message elements and handle updates
for (const UPubnubMessageElement* Element : MessageElements)
{
// Process each element as needed
UE_LOG(LogTemp, Log, TEXT("Draft Element Text: %s"), *Element->GetText());
}
// Process suggested mentions
for (const FPubnubSuggestedMention& Suggestion : SuggestedMentions)
{
show all 29 linesAdd message element
AddMention()
adds a user mention, channel reference or a link specified by a mention target at a given position.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->AddMention(int Position, int Length, UPubnubMentionTarget* MentionTarget)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
Position | int | Yes | n/a | Position of a character in a message where the message element you want to insert starts. It's counted from the beginning of the message (including spaces), with 0 as the first character. |
Length | int | Yes | n/a | Number of characters the message element should occupy in the draft message's text. |
MentionTarget | UPubnubMentionTarget | Yes | n/a | Mention target type. Available mention types include:
|
Output
This method returns no output data.
Basic usage
Create the Hello Alex! I have sent you this link on the #offtopic channel.
message where Alex
is a user mention, link
is a URL, and #offtopic
is a channel reference.
// Create a message draft
UPubnubMessageDraft* MyMessageDraft = Channel->CreateMessageDraft();
// Insert greeting text before the mention of Alex
MyMessageDraft->InsertText(0, "Hello Alex! I have sent you this link on the #offtopic channel.");
// Create a user mention target for Alex
FString UserName = "Alex";
UPubnubMentionTarget* UserMentionTarget = UPubnubMentionTarget::CreateUserMentionTarget(UserName);
// Add the user mention for Alex
MyMessageDraft->AddMention(6, UserName.Len(), UserMentionTarget); // 'Hello ' is 6 characters long
// Create a URL mention target for the link
FString Url = "https://www.example.com";
show all 31 linesRemove message element
RemoveMention()
removes a user mention, channel reference, or a link at a given position.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->RemoveMention(int Position)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
Position | int | Yes | n/a | Position of the first character of the message element you want to remove. |
Position value
If you don't provide the position of the first character of the message element to remove, it isn't removed.
Output
This method returns no output data.
Basic usage
Remove the URL element from the word link
in the Hello Alex! I have sent you this link on the #offtopic channel.
message.
// Assume the message reads:
// Hello Alex! I have sent you this link on the #offtopic channel.
// Remove the link mention
MessageDraft->RemoveMention(33);
Update message text
Update()
lets you replace the text of a draft message with new content.
Removing message elements
As a best effort, the optimal set of insertions and removals that converts the current text to the provided text is calculated to preserve any message elements.
If any message element text is found to be modified in the updated text, the message element is removed.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->Update(FString Text)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
Text | FString | Yes | n/a | Text of the message that you want to update. |
Output
This method returns no output data.
Basic usage
Change the message I sent Alex this picture.
to I did not send Alex this picture.
where Alex
is a user mention.
// the message reads:
// I sent [Alex] this picture.
// where [Alex] is a user mention
MessageDraft->Update("I did not send Alex this picture.");
// the message now reads:
// I did not send [Alex] this picture.
// the mention is preserved because its text wasn't changed
Mention text changes
If you decided to change the name Alex
to some other name, the mention would be removed because your updated text's index coincided with an existing mention.
For more manual control over inserting and removing parts of a message, refer to Insert message text and Remove message text.
Insert suggested message element
Inserts a message element returned by the MessageDraft change listener into the MessageDraft
.
Text must match
The SuggestedMention
must be up to date with the message text, that is, SuggestedMention.ReplaceFrom
must match the message draft at position SuggestedMention.ReplaceFrom
, otherwise an exception is thrown.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->InsertSuggestedMention(FPubnubSuggestedMention SuggestedMention, FString Text)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
SuggestedMention | FPubnubSuggestedMention | Yes | n/a | A user, channel, or URL suggestion obtained from MessageDraftChangeListener . |
Text | FString | Yes | n/a | The text you want the message element to display. |
Output
This method returns no output data.
Basic usage
Register a listener and insert a suggested element.
// Assuming you have a UPubnubMessageDraft pointer named MyMessageDraft
// Define your callback function that handles draft updates with suggestions
void AMyActor::OnMessageDraftUpdateWithSuggestions(const TArray<UPubnubMessageElement*>& MessageElements, const TArray<FPubnubSuggestedMention>& SuggestedMentions)
{
// Check if there are any suggested mentions
if (SuggestedMentions.Num() > 0)
{
// Insert the first suggested mention into the draft
const FPubnubSuggestedMention& FirstSuggestion = SuggestedMentions[0];
MyMessageDraft->InsertSuggestedMention(FirstSuggestion, FirstSuggestion.ReplaceTo);
// Log the action for debugging purposes
UE_LOG(LogTemp, Log, TEXT("Inserted suggested mention: %s"), *FirstSuggestion.ReplaceTo);
}
show all 26 linesInsert message text
InsertText()
lets you insert plain text in the draft message at a given position from the beginning of the message.
Removing message elements
If the position of the text you want to insert corresponds to an existing message element, this element is removed.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->InsertText(int Position, FString Text)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
Position | int | Yes | n/a | Position of a character in a message where the text you want to insert starts. It's counted from the beginning of the message (including spaces), with 0 as the first character. |
Text | FString | Yes | n/a | Text that you want to insert. |
Output
This method returns no output data.
Basic usage
In the message Check this support article https://www.support-article.com/.
, add the word out
between the words Check
and this
.
// Assuming you have a UPubnubMessageDraft pointer named MyMessageDraft
// Start by setting the initial text in the message draft
MyMessageDraft->Update(TEXT("Check this support article https://www.support-article.com/."));
// Find the position to insert "out"
// "Check " is 6 characters long, so "out" should be inserted at position 6
int InsertPosition = 6;
// Use InsertText to add the word "out" at the specified position
MyMessageDraft->InsertText(InsertPosition, TEXT("out "));
// At this point, the draft should read: "Check out this support article https://www.support-article.com/."
// You may Log the resulting draft for clarity
show all 16 linesRemove message text
RemoveText()
lets you remove plain text from the draft message at a given position from the beginning of the message.
Removing message elements
If the position of the text you want to remove corresponds to an existing message element, this element is removed.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->RemoveText(int Position, int Length)
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
Position | int | Yes | n/a | Position of a character in a message where the text you want to insert starts. It's counted from the beginning of the message (including spaces), with 0 as the first character. |
Length | int | Yes | n/a | How many characters to remove, starting at the given Position . |
Output
This method returns no output data.
Basic usage
In the message Check out this support article https://www.support-article.com/.
, remove the word out
.
// Assuming you have a UPubnubMessageDraft pointer named MyMessageDraft
// Start by setting the initial text in the message draft
MyMessageDraft->Update(TEXT("Check out this support article https://www.support-article.com/."));
// Determine the position and length of the text to remove
// "Check " is 6 characters long, so "out" starts at position 6 and has a length of 4 (including the trailing space)
int RemovePosition = 6;
int RemoveLength = 4;
// Use RemoveText to delete the word "out " from the draft
MyMessageDraft->RemoveText(RemovePosition, RemoveLength);
// At this point, the draft should read: "Check this support article https://www.support-article.com/."
show all 17 linesSend a draft message
Send()
publishes the draft text message with all mentioned users, links, and referenced channels.
Whenever you mention any users, Send()
also emits events of type mention
.
Method signature
- Blueprint
- C++ / Input parameters
MessageDraft->Send(FPubnubSendTextParams SendTextParams = FPubnubSendTextParams())
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
SendTextParams | FSendTextParams | No | n/a | Struct providing additional parameters. |
→ StoreInHistory | bool | No | true | If true , the messages are stored in Message Persistence. If StoreInHistory is not specified, the Message Persistence configuration specified on the Admin Portal keyset is used. |
→ SendByPost | bool | No | false | When true , the SDK uses HTTP POST to publish the messages. The message is sent in the BODY of the request instead of the query string when HTTP GET is used. The messages are also compressed to reduce their size. |
→ Meta | FString | No | n/a | Publish additional details with the request. |
→ MentionedUsers | TMap<int, FPubnubMentionedUser> | No | n/a | Object mapping a mentioned user (FString ID , FString Name ) with the number of mention (nameOccurrenceIndex ) in the message: export type MessageMentionedUsers = { [nameOccurrenceIndex: number]: { id: string; name: string } } . For example, { 0: { id: 123, name: "Mark" }, 2: { id: 345, name: "Rob" } } means that Mark will be shown on the first mention in the message and Rob on the third. |
→ ReferencedChannels | TMap<int, FPubnubReferencedChannel> | No | n/a | Object mapping the referenced channel (FString ID , FString Name ) with the place where this reference (nameOccurrenceIndex ) was mentioned in the message: export type MessageReferencedChannels = { [nameOccurrenceIndex: number]: { id: string; name: string } } . For example, { 0: { id: 123, name: "Support" }, 2: { id: 345, name: "Off-topic" } } means that Support will be shown on the first reference in the message and Off-topic on the third. Refer to Reference channels for more details. |
→ TextLinks | TArray<FPubnubTextLink> | No | n/a | Returned array of FPubnubTextLink (int Start_Index = 0 , int End_Index = 0 , FString Link = "" ) that are shown as text in the message. |
→ QuotedMessage | UPubnubMessage* | No | n/a | Message object added to a message when you quote another message. This object stores the following info about the quoted message: { timetoken: quotedMessage.timetoken, text: quotedMessage.text, userId: quotedMessage.userId } , where timetoken is the time when the quoted message was published, text contains the original message content, and userId is the identifier of the user who published the quoted message. |
Suppose a user adds elements to the message draft, such as links, quotes, other user mentions, or channel references. In that case, these are not explicitly passed in the Send()
method but get added to the MessageDraft
object through the AddMention()
and AddQuote()
methods.
Output
This method returns no output data.
Basic usage
Send a draft message containing just plain text.
// Create a message draft
var messageDraft = Channel->CreateMessageDraft();
// Add initial text
MessageDraft->Update("Hello Alex!");
// Send the message
MessageDraft->Send();