Custom Updates for Cross Play

This feature has been deprecated.

With Custom Update, you can send a custom message in a Messenger conversation between the people who are playing. This is a popular feature by Instant Game, and now available across platforms with Cross Play.

Integrate with Context APIs

We added three APIs to the iOS SDK to access the context ID. These APIs will trigger a dialog for user to interact with and return a context token ID, which you will need to make custom update.

Create Context

Create Context API is used to let two players play together for the first time. To call the Create Context API, you need the player ID of player which the current player wishes to play with, who needs be a Facebook friend of the current logged-in user. You can retrieve the playerID using the following graphAPI Endpoint:

GET /{user-id}/friends

Once retrieved the PlayerID, you can build a CreateContextContent object and trigger the dialog:

let createContextContent = CreateContextContent(playerID: "playerID")
try ContextDialogPresenter().makeAndShowCreateContextDialog(
    content: createContextContent,
    delegate: delegate
)
String playerID = "123456";
ContextCreateContent.Builder builder = new ContextCreateContent.Builder();
builder.setSuggestedPlayerID(playerID);

// Create the Dialog Content and prepare the Dialog itself.
ContextCreateContent content = builder.build();
ContextCreateDialog dialog = new ContextCreateDialog(this /* activity */);

dialog.registerCallback(
    this.callbackManager,
    new FacebookCallback<ContextCreateDialog.Result>() {
        
});

dialog.show(content);

Switch Context

Swtich Context API is used to swtich into a context that is created earlier. To call the Create Context API, you need the context Token ID.

After user's confirmation on the dialog, the Facebook SDK update with the current context token identifier it saves in its state.

let switchContextContent = SwitchContextContent(contextID: "contextID")
try ContextDialogPresenter().makeAndShowCreateContextDialog(
    content: switchContextContent,
    delegate: delegate
)
String contextID = "13456"; // existing context id
ContextSwitchContent.Builder builder = new ContextSwitchContent.Builder();
builder.setContextID(contextID);

ContextSwitchContent content = builder.build();

ContextSwitchDialog dialog = new ContextSwitchDialog(this /* activity */);
dialog.registerCallback(
    this.callbackManager,
    new FacebookCallback<ContextSwitchDialog.Result>() {
        @Override
        public void onSuccess(ContextSwitchDialog.Result result) {
            // do something with result.getContextID()
        }

        @Override
        public void onCancel() {
            // dialog was cancelled
        }

        @Override
        public void onError(FacebookException exception) {
            // an error happened
        }
    });

// actually show the dialog now that we have defined a callback for it.
dialog.show(content);

Context Choose

The context Choose dialog is works differently than the switch and create. This dialog performs an app switch if the Facebook app is installed on the device. If the Facebook app is not installed we switch into safari browser and display the m-site version of context choose dialog.

To call this API, you need to create a ChooseContextContent object. ChooseContextContent holds the required data such as Filter, Min and Max Participants to show the dialog.

let chooseContextContent = ChooseContextContent()
chooseContextContent.filter = .newPlayersOnly
chooseContextContent.minParticipants = 1;
chooseContextContent.maxParticipants = 2;
    
ContextDialogPresenter().makeAndShowChooseContextDialog(
    content: chooseContextContent,
    delegate: delegate
)
int minSize = 1;
int maxSize = 1;
List<String> filters = new ArrayList<String>();
filters.add("NEW_PLAYERS_ONLY");
ContextChooseContent.Builder builder = new ContextChooseContent.Builder();
builder.setFilters(filters);
builder.setMinSize(minSize);
builder.setMaxSize(maxSize);


ContextChooseContent content = builder.build();
ContextChooseDialog dialog = new ContextChooseDialog(this);
dialog.registerCallback(
    this.callbackManager,
    new FacebookCallback<ContextChooseDialog.Result>() {
       @Override
       public void onSuccess(ContextChooseDialog.Result result) {
         // do something with result.getContextID()
       }

        @Override
        public void onCancel() {
          // dialog was cancelled
        }

        @Override
        public void onError(FacebookException exception) {
           // an error happened
        }
});

dialog.show(content);

Handling Completion And Errors

ContextDialogDelegate: The delegate that will be triggered when dialog Cancels, Fails or Completes. While the dialogs return the current context when invoked, it is best to use the GamingContext helper class to keep track of the current context. This will allow you to know what context the player is in even if they join a session from messenger.

func contextDialogDidComplete(_ contextDialog: ContextWebDialog) {
      //Dialog succeed check GamingContext.Current for current context
    }
func contextDialog(_ contextDialog: ContextWebDialog, didFailWithError error: Error) {
      //Dialog failed with error
    }
func contextDialogDidCancel(_ contextDialog: ContextWebDialog) {
      //Dialog cancelled
    }

// Getting current context
GamingContext.Current
// Retrieve the current gaming context (if any).
GamingContext currentContext = GamingContext.getCurrentGamingContext();

When contextDialogDidComplete is invoked,that means the context create, switch, or choose dialog completed succesfully. You should check the gaming context for the current context identifier and perform a custom update.

When contextDialogDidCancel is invoked, this either means the user returned to the game without interacting with the dialog or they cancelled on the dialog without completing. At this point it’s up to you to prompt the user to retry or wait for a later time.

When contextDialog:didFailWithError is invoked it means the dialog encountered some sort of error while attempting to show the dialog or during the user’s interaction with the dialog. You will receive the dialog that encountered an error and the error, to handle the next steps.

Perform a Custom Update with Graph API

Custom updates allows you to send a messenger attachment to the players in the current context to let them know of an in-game event. This is done via the following Graph API.

POST /me/custom_update

To make calling this API easier we provide a high level wrapper in the SDK which will allow you to use strong data types.

// Using customUpdateContentMedia with a url representing a gif will be displayed
CustomUpdateGraphRequest().request(content: customUpdateContentMedia, completionHandler: completion)

// Using customUpdateContentImage with a UIimage that a bitmap will be displayed
CustomUpdateGraphRequest().request(content: customUpdateContentImage, completionHandler: completion)
// Localized Text
// Custom Updates supports text localizations for the main message and the CTA button
// you can use the CustomUpdateLocalizedText class to define your strings.
HashMap<String, String> text_localizations = new HashMap<>();
text_localizations.put("es_MX", "Es tu turno");
CustomUpdateLocalizedText text =
  new CustomUpdateLocalizedText("It is your turn!", text_localizations);
  
HashMap<String, String> cta_localizations = new HashMap<>();
cta_localizations.put("es_MX", "Presiona Aquí");
CustomUpdateLocalizedText cta = new CustomUpdateLocalizedText("Click Here", localizations)
      
// Preparing the content for a Custom Update using an Image Bitmap
Bitmap bm = BitmapFactory.decodeResource(getResources(), R.drawable.fb_gaming);
CustomUpdateContent.Builder builder =
    new CustomUpdateContent.Builder(currentContext, text, bm);
CustomUpdateContent bitmapContent = builder
    .setCta(cta)
    // this is a payload that will be attached when the game is launched
    // from messenger
    .setData("{'data': true}")
    .build();
           
GamingContext currentContext = GamingContext.getCurrentGamingContext();
if (currentContext == null) {
   return;
}

// Sending the actual Custom Update via the Graph API wrapper
CustomUpdate.newCustomUpdateRequest(
    content,
    response -> {
        Log.e("MY_TAG", response.toString());
    }).executeAsync();

The graph request will return a success value to indicate whether the custom update was successfully sent.