Skip to main content

Sending, accepting and rejecting friend invites

With EOS Online Subsystem, you can send friend invites to other EOS users. You don't need to be using Epic Games accounts for this to work.

Friends who are added to the friends list in this manner are specific to the game's product ID. They won't appear in other games owned by your organisation, because the friends list is stored in Player Data Storage, which is specific to the game.

In order for a friend invite to be sent, both the sender and receiver need to be online at the same time. That's because friend invites, as well as acceptance and rejection messages, are sent over EOS P2P. The game clients directly talk to each other over P2P to communicate friend invites and other messages.

If you send a friend invite to someone, and they're not currently online, the friend invite will be stored as a "pending invite" in Player Data Storage. The plugin automatically retries every 10 minutes to send the invite again, and will resume retrying to send it even across game launches.

Sending an invite to another player

To send a friends list invitation to another player, use SendInvite. You'll first need to get the friends interface:

#include "OnlineSubsystem.h"
#include "OnlineSubsystemUtils.h"
#include "Interfaces/OnlineFriendsInterface.h"

// ...

IOnlineSubsystem *Subsystem = Online::GetSubsystem(this->GetWorld());
IOnlineFriendsPtr Friends = Subsystem->GetFriendsInterface();

Then, call SendInvite with the user ID of the target player:

if (!Friends->SendInvite(
0 /* LocalUserNum */,
TargetUserId /* The user to send the invite to */,
TEXT("") /* ListName, unused by EOS */,
FOnSendInviteComplete::CreateUObject(
this,
&UMyClass::OnInviteSendComplete)))
{
// Call failed to start
}

// ...

void UMyClass::OnInviteSendComplete(
int32 LocalUserNum,
bool bWasSuccessful,
const FUniqueNetId &FriendId,
const FString &ListName,
const FString &ErrorStr)
{
if (bWasSuccessful)
{
// Invite was successfully sent to the other player, or
// stored for later sending because the target player is offline.
}
else
{
// The invite could not be sent.
}
}

Getting notified of an incoming friend invite

You'll want to be notified when a friend invite arrives in your game so you can prompt the user to accept or reject the invite. To know when a new friend invitation arrives, listen for the OnInviteReceived event:

FDelegateHandle Handle = Friends->AddOnInviteReceivedDelegate_Handle(
FOnInviteReceivedDelegate::CreateUObject(this, &UMyClass::OnInviteReceived));
// You can use `Handle` later to call `Friends->ClearOnInviteReceivedDelegate_Handle(Handle)`
// if you want to unregister the event handler.

// ...

void UMyClass::OnInviteReceived(const FUniqueNetId& UserId, const FUniqueNetId& FriendId)
{
// Notify the user that FriendId has sent them a friend invite.
}

Accepting a friend invite

Once you've received an invite and the user has accepted it through your game's user interface, call AcceptInvite to accept the invite. The sender will receive the OnInviteAccepted event (see "Getting notified when a friend invite is accepted or rejected" below):

if (!Friends->AcceptInvite(
0 /* LocalUserNum */,
TargetUserId /* The user who sent the original invite */,
TEXT("") /* ListName, unused by EOS */,
FOnAcceptInviteComplete::CreateUObject(
this,
&UMyClass::OnInviteAcceptComplete)))
{
// Call failed to start
}

// ...

void UMyClass::OnInviteAcceptComplete(
int32 LocalUserNum,
bool bWasSuccessful,
const FUniqueNetId &FriendId,
const FString &ListName,
const FString &ErrorStr)
{
if (bWasSuccessful)
{
// Invite was successfully accepted. The "acceptance" notification might be
// stored for later sending if the original sender of the friend request
// is currently offline.
}
else
{
// The invite could not be accepted.
}
}

Rejecting a friend invite

Once you've received an invite and the user has rejected it through your game's user interface, call RejectInvite to reject the invite. The sender will receive the OnInviteRejected event (see "Getting notified when a friend invite is accepted or rejected" below):

// Store the delegate handle, as you'll need to unregister it
// in the OnInviteRejectComplete callback.
this->RejectFriendInviteCompleteHandle = Friends->AddOnRejectInviteCompleteDelegate_Handle(
0 /* LocalUserNum */,
FOnRejectInviteCompleteDelegate::CreateUObject(
this,
&UMyClass::OnInviteRejectComplete));

if (!Friends->RejectInvite(
0 /* LocalUserNum */,
TargetUserId /* The user who sent the original invite */,
TEXT("") /* ListName, unused by EOS */))
{
// Call failed to start
}

// ...

void UMyClass::OnInviteRejectComplete(
int32 LocalUserNum,
bool bWasSuccessful,
const FUniqueNetId &FriendId,
const FString &ListName,
const FString &ErrorStr)
{
IOnlineSubsystem *Subsystem = Online::GetSubsystem(this->GetWorld());
IOnlineFriendsPtr Friends = Subsystem->GetFriendsInterface();

// NOTE: If you're sending multiple rejections in parallel, you'll need to
// capture the original FriendId for the RejectInvite call as a user parameter
// to this callback, and then compare the FriendId the event is for with the
// FriendId you called RejectInvite for. You'll also need to store the delegate
// handle (RejectFriendInviteCompleteHandle) per friend you are rejecting.

// Remove the event handler.
Friends->ClearOnRejectInviteCompleteDelegate_Handle(LocalUserNum, this->RejectFriendInviteCompleteHandle);

if (bWasSuccessful)
{
// Invite was successfully rejected. The "reject" notification might be
// stored for later sending if the original sender of the friend request
// is currently offline.
}
else
{
// The invite could not be rejected.
}
}

Getting notified when a friend invite is accepted or rejected

You'll want to be notified when your outbound friend invites are accepted or rejected by other players. To know when this happens, listen for the OnInviteAccepted and OnInviteRejected events:

FDelegateHandle AcceptHandle = Friends->AddOnInviteAcceptedDelegate_Handle(
FOnInviteAcceptedDelegate::CreateUObject(this, &UMyClass::OnInviteAccepted));
FDelegateHandle RejectHandle = Friends->AddOnInviteRejectedDelegate_Handle(
FOnInviteRejectedDelegate::CreateUObject(this, &UMyClass::OnInviteRejected));
// Store the handles if you want to unregister the event handlers later.

// ...

void UMyClass::OnInviteAccepted(const FUniqueNetId& UserId, const FUniqueNetId& FriendId)
{
// Notify the user that FriendId has accepted their friend invite.
}

void UMyClass::OnInviteRejected(const FUniqueNetId& UserId, const FUniqueNetId& FriendId)
{
// Notify the user that FriendId has rejected their friend invite.
}