Push Notificatons

1. Android

A. FCM Configurations

Create a unity project in Firebase console with your project package name. For more details, visit FCM guide,

Next add the Firebase Unity SDK to your app by downloading Firebase Unity SDK From https://firebase.google.com/download/unity

In Unity, select the Assets > Import Package > Custom Package menu item.

Import the FirebaseMessaging.unitypackage package from the Firebase Unity SDK, downloaded previously.

When the Import Unity Package window appears, click the Import button.

Delete both google-play-service files under Assets/Plugins/Android/google-play-service-lib/libs to avoid multiple Dex file conflicts.

Uncomment the following line,

#define USE_FIREBASE_MESSAGING

from TapjoySample.cs script file under Assets/TapjoySample/Scripts folder.

Initialize Firebase SDK with the following code before Firebase cloud messaging setup in your project script

Firebase.FirebaseApp.CheckAndFixDependenciesAsync().ContinueWith(task => {
  var dependencyStatus = task.Result;
  if (dependencyStatus == Firebase.DependencyStatus.Available) {
    // Create and hold a reference to your FirebaseApp, i.e.
    //   app = Firebase.FirebaseApp.DefaultInstance;
    // where app is a Firebase.FirebaseApp property of your application class.
    // Set a flag here indicating that Firebase is ready to use by your
    // application.
  } else {
    UnityEngine.Debug.LogError(System.String.Format(
      "Could not resolve all Firebase dependencies: {0}", dependencyStatus));
    // Firebase Unity SDK is not safe to use here.
  }
});

Setup Firebase Cloud Messaging in your script:

public void Start() {
  Firebase.Messaging.FirebaseMessaging.TokenReceived += OnTokenReceived;
  Firebase.Messaging.FirebaseMessaging.MessageReceived += OnMessageReceived;
}
public void OnTokenReceived(object sender, Firebase.Messaging.TokenReceivedEventArgs token) {
  UnityEngine.Debug.Log("Received Registration Token: " + token.Token);
}
public void OnMessageReceived(object sender, Firebase.Messaging.MessageReceivedEventArgs e) {
  UnityEngine.Debug.Log("Received a new message from: " + e.Message.From);
}

Configure the entry point activity:

When SDK is added to Unity, the Firebase Unity SDK replaces the UnityPlayerActivity into MessagingUnityPlayerActivity in Assets/Plugins/AndroidManifest.xml

After FCM SDK overwrote the existing AndroidManifest.xml file, we need to add the following Tapjoy Activities file declaration again:

<activity android:name="com.tapjoy.TJAdUnitActivity" android:configChanges="orientation|keyboardHidden|screenSize" android:theme="@android:style/Theme.Translucent.NoTitleBar.Fullscreen" android:hardwareAccelerated="true" />
<activity android:name="com.tapjoy.TJContentActivity" android:configChanges="orientation|keyboardHidden|screenSize" android:theme="@android:style/Theme.Translucent.NoTitleBar" />
<activity android:name="com.tapjoy.mraid.view.Browser" android:configChanges="orientation|keyboardHidden|screenSize" />
<activity android:name="com.tapjoy.mraid.view.ActionHandler" android:configChanges="orientation|keyboardHidden|screenSize" />
<service android:name="com.google.firebase.messaging.MessageForwardingService" android:exported="false" />
<meta-data android:name="com.google.android.gms.version" android:value="@integer/google_play_services_version" />
<receiver android:name="com.tapjoy.InstallReferrerReceiver" android:exported="true">
<intent-filter>
<action android:name="com.android.vending.INSTALL_REFERRER" />
</intent-filter>
</receiver>
<receiver android:name="com.tapjoy.TapjoyReceiver" />

These files are provided because the default UnityPlayerActivity does not handle onStop, onRestart activity lifecycle transitions or implement the onNewIntent which is necessary for Firebase Cloud Messaging to correctly handle incoming messages.

If you implement the custom entry point activity instead of using UnityPlayerActivity. You will have to implement workaround onNewIntent to receive the notification when the app is on background
To prevent from auto enabling FCM, add the following code in AndroidManifest.xml:

<?xml version="1.0" encoding="utf-8"?>
<application>
	<meta-data android:name="firebase_messaging_auto_init_enabled" android:value="false" />
 	<meta-data android:name="firebase_analytics_collection_enabled" android:value="false" />
 </application>

Note: Firebase SDK added to unity project in project level but not the platform level. Even though we don’t implement FCM to unity iOS, we still need to add Google_service.plist file to Assets. To get Google_service.plist, create an iOS app on Firebase console, generate config plist file, download and add to the Assets.

Reference: https://firebase.google.com/docs/cloud-messaging/unity/client

Set your GCM Sender ID in the Tapjoy Window. You can register multiple sender IDs separated by a ",".

Before sending push notification, you need to configure API server key and sender ID on Tapjoy Dashboard. Please configure your key by going to "App Setting" on the bottom-left of the Tapjoy dashboard and then selecting "Push" from the left menu bar.

You can find your Sender ID and API Key in Google API Console. Please refer to How to find sender id and api key for gcm for further information.

B. Unity Android configuration

Due to recent Unity’s FCM implementations, MessageReceived delegation will not invoked when application is in background/inactive. To receive notifications when app is in background/inactive, you need to implement additional receivers in Android native code.

  1. make a subclass of com.google.firebase.messaging.cpp.ListenerService (as Unity FCM uses C++ interface) and override onMessageReceived to call Tapjoy.setReceiveRemoteNotification
  import com.google.firebase.messaging.RemoteMessage;
  import com.google.firebase.messaging.cpp.ListenerService;
  import com.tapjoy.Tapjoy;
  
  public class FCMMessageService extends ListenerService {
      @Override
      public void onMessageReceived(RemoteMessage message) {
  //        super.onMessageReceived(message);
          Tapjoy.setReceiveRemoteNotification(getApplicationContext(), message.getData());
      }
  }
  1. add receiver of the class into AndroidManifest
<service android:name=".pushnotification.FCMMessageService">
    <intent-filter>
      <action android:name="com.google.firebase.MESSAGING_EVENT"/>
    </intent-filter>
  </service>

C. Customizing Notification Icon

The application icon will be displayed as the default notification icon when you send push notifications (GCM message) through Tapjoy dashboard.
You may change notification icon by specifying a resource in <application> tag of AndroidManifest.xml file of application project as follows:

<manifest ...>	 
   ... 	
   <application ...>	 	 
      ... 	 	
      <meta-data android:name="com.tapjoy.notification.icon" android:resource="@drawable/ic_notify"/&gt 	 	 
      ... 	  
   </application>
   ... 	 	 
</manifest>

D. Android Push Opt-Out API

In SDK 11.9.0 and later, there is an API that lets you opt the user out of push notifications, and lets you query whether push notifications are enabled for that user:

  /**
  * @brief Returns true if the push notification is disabled when target platform is Android
  *        Returns false otherwise
  */
  public static bool IsPushNotificationDisabled()

  /**
  * @brief Sets whether the push notification is disabled. (Only for Android)
  * @param disabled
  *        true to disable the push notification
  */
  public static void SetPushNotificationDisabled(bool disabled)

2. iOS

Our Unity plugin does not have a C# interface for iOS push notifications, so you will have to modify the Xcode project that Unity outputs as a result of the build process. Modify the Xcode project in the following way:

For Push Notification support, call the specified Tapjoy method in following delegate methods:

objective-c
swift
// called when the remote notification is registered
- (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {
  [Tapjoy setDeviceToken:deviceToken];
}

  // called when the user click the push message
- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {
  [Tapjoy setApplicationLaunchingOptions:launchOptions];
}

  // called when the user get push message while playing the app
- (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo {
  [Tapjoy setReceiveRemoteNotification:userInfo];
}

Don’t forget to register the push notification service. Otherwise, you will not able to see the confirm dialog for allowing permission.

objective-c
swift
// Registering for remote notifications
  if ([application respondsToSelector:@selector(isRegisteredForRemoteNotifications)]) {
      // iOS 8 Notifications
      [application registerUserNotificationSettings:[UIUserNotificationSettings settingsForTypes:(UIUserNotificationTypeSound | UIUserNotificationTypeAlert | UIUserNotificationTypeBadge) categories:nil]];

      [application registerForRemoteNotifications];
  } else {
      // iOS < 8 Notifications
      [application registerForRemoteNotificationTypes:
          (UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound)];
  }

For detailed information, please refer to iOS Local and Remote Notification Programming Guide.

Sending push notifications requires an Apple Push Notification Service push certificate. Refer to Local Notifications and Remote Notifications Guide for more information. Once you obtain the certificate, upload it to the Tapjoy Dashboard. Read How to Configure Push Certificates for more information. Please upload your certificate file to by going to "App Setting" on the bottom-left of the Tapjoy dashboard and then selecting "Push Certificates" from the left menu bar.

3. Notes

Can I use another push provider or my own push server simultaneously with Tapjoy?

Yes. Please refer to this article

My Push certificate is about to expire soon.

Please replace your current certificate with a new one before it expires.

Can I redirect users to certain point of app?

Yes. Using custom payload, you can redirect users. Please refer to this article.