diff --git a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdMob.java b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdMob.java index 9c7f1651..4eaae2ed 100644 --- a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdMob.java +++ b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdMob.java @@ -66,6 +66,11 @@ public class RNFirebaseAdMob extends ReactContextBaseJavaModule { rewardedVideo.show(); } + /** + * + * @param adUnit + * @return + */ private RNFirebaseAdmobInterstitial getOrCreateInterstitial(String adUnit) { if (interstitials.containsKey(adUnit)) { return interstitials.get(adUnit); @@ -75,6 +80,11 @@ public class RNFirebaseAdMob extends ReactContextBaseJavaModule { return interstitial; } + /** + * + * @param adUnit + * @return + */ private RNFirebaseRewardedVideo getOrCreateRewardedVideo(String adUnit) { if (rewardedVideos.containsKey(adUnit)) { return rewardedVideos.get(adUnit); diff --git a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdmobInterstitial.java b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdmobInterstitial.java index 25b532a8..2373f33b 100644 --- a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdmobInterstitial.java +++ b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseAdmobInterstitial.java @@ -99,7 +99,7 @@ class RNFirebaseAdmobInterstitial { void sendEvent(String type, final @Nullable WritableMap payload) { WritableMap map = Arguments.createMap(); map.putString("type", type); - map.putString("adunit", adUnit); + map.putString("adUnit", adUnit); if (payload != null) { map.putMap("payload", payload); diff --git a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseRewardedVideo.java b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseRewardedVideo.java index 136d8d7b..3eeaf286 100644 --- a/android/src/main/java/io/invertase/firebase/admob/RNFirebaseRewardedVideo.java +++ b/android/src/main/java/io/invertase/firebase/admob/RNFirebaseRewardedVideo.java @@ -6,9 +6,7 @@ import android.support.annotation.Nullable; import com.facebook.react.bridge.Arguments; import com.facebook.react.bridge.WritableMap; -import com.google.android.gms.ads.AdListener; import com.google.android.gms.ads.AdRequest; -import com.google.android.gms.ads.InterstitialAd; import com.google.android.gms.ads.MobileAds; import com.google.android.gms.ads.reward.RewardItem; import com.google.android.gms.ads.reward.RewardedVideoAd; @@ -28,11 +26,23 @@ public class RNFirebaseRewardedVideo implements RewardedVideoAdListener { adMob = adMobInstance; rewardedVideo = MobileAds.getRewardedVideoAdInstance(adMob.getContext()); - rewardedVideo.setRewardedVideoAdListener(this); + + Activity activity = adMob.getActivity(); + final RNFirebaseRewardedVideo _this = this; + + if (activity != null) { + activity.runOnUiThread(new Runnable() { + @Override + public void run() { + rewardedVideo.setRewardedVideoAdListener(_this); + } + }); + } } /** * Load an Ad with a AdRequest instance + * * @param adRequest */ void loadAd(final AdRequest adRequest) { @@ -66,33 +76,36 @@ public class RNFirebaseRewardedVideo implements RewardedVideoAdListener { @Override public void onRewarded(RewardItem reward) { - sendEvent("onRewarded", null); + WritableMap payload = Arguments.createMap(); + payload.putInt("amount", reward.getAmount()); + payload.putString("type", reward.getType()); + sendEvent("onRewarded", payload); } @Override public void onRewardedVideoAdLeftApplication() { - sendEvent("onRewardedVideoAdLeftApplication", null); + sendEvent("onAdLeftApplication", null); } @Override public void onRewardedVideoAdClosed() { - sendEvent("onRewardedVideoAdClosed", null); + sendEvent("onAdClosed", null); } @Override public void onRewardedVideoAdFailedToLoad(int errorCode) { WritableMap payload = RNFirebaseAdMobUtils.errorCodeToMap(errorCode); - sendEvent("onRewardedVideoAdFailedToLoad", payload); + sendEvent("onAdFailedToLoad", payload); } @Override public void onRewardedVideoAdLoaded() { - sendEvent("onRewardedVideoAdLoaded", null); + sendEvent("onAdLoaded", null); } @Override public void onRewardedVideoAdOpened() { - sendEvent("onRewardedVideoAdOpened", null); + sendEvent("onAdOpened", null); } @Override @@ -104,13 +117,14 @@ public class RNFirebaseRewardedVideo implements RewardedVideoAdListener { /** * Send a native event over the bridge with a type and optional payload + * * @param type * @param payload */ void sendEvent(String type, final @Nullable WritableMap payload) { WritableMap map = Arguments.createMap(); map.putString("type", type); - map.putString("adunit", adUnit); + map.putString("adUnit", adUnit); if (payload != null) { map.putMap("payload", payload); diff --git a/lib/modules/admob/RewardedVideo.js b/lib/modules/admob/RewardedVideo.js new file mode 100644 index 00000000..fc9142f7 --- /dev/null +++ b/lib/modules/admob/RewardedVideo.js @@ -0,0 +1,82 @@ +import { NativeModules } from 'react-native'; +import { statics } from './'; +import { nativeToJSError } from '../../utils'; + +const FirebaseAdMob = NativeModules.RNFirebaseAdmob; + +export default class RewardedVideo { + + constructor(admob: Object, adunit: string) { + this.admob = admob; + this.adUnit = adunit; + this.loaded = false; + this.admob.on(`rewarded_video_${adunit}`, this._onRewardedVideoEvent.bind(this)); + } + + /** + * Handle a JS emit event + * @param event + * @private + */ + _onRewardedVideoEvent(event) { + const eventType = `rewarded_video:${this.adUnit}:${event.type}`; + + let emitData = Object.assign({}, event); + + switch (event.type) { + case 'onAdLoaded': + this.loaded = true; + break; + case 'onAdFailedToLoad': + emitData = nativeToJSError(event.payload.code, event.payload.message); + emitData.type = event.type; + break; + default: + } + + this.admob.emit(eventType, emitData); + this.admob.emit(`rewarded_video:${this.adUnit}:*`, emitData); + } + + /** + * Load an ad with an instance of AdRequest + * @param request + * @returns {*} + */ + loadAd(request: AdRequest) { + return FirebaseAdMob.rewardedVideoLoadAd(this.adUnit, request); + } + + /** + * Return a local instance of isLoaded + * @returns {boolean} + */ + isLoaded() { + return this.loaded; + } + + /** + * Show the advert - will only show if loaded + * @returns {*} + */ + show() { + if (this.loaded) { + FirebaseAdMob.rewardedVideoShowAd(this.adUnit); + } + } + + /** + * Listen to an Ad event + * @param eventType + * @param listenerCb + * @returns {null} + */ + on(eventType, listenerCb) { + if ((eventType !== 'onRewarded' || eventType !== 'onRewardedVideoStarted') && !statics.EventTypes[eventType]) { + console.warn(`Invalid event type provided, must be one of: ${Object.keys(statics.EventTypes).join(', ')}, onRewarded, onRewardedVideoStarted`); + return null; + } + + return this.admob.on(`rewarded_video:${this.adUnit}:${eventType}`, listenerCb); + } +}