admob_flutterでreward広告が表示されない

admob_flutter で reward 広告がうまく表示できない場合の解決策を紹介します。

原因

admob_flutter のWikiの通り実装したところ、うまく表示されませんでした。

<Google> Cannot find an ad network adapter with the name(s): com.google.DummyAdapter. Remember to link all required ad network adapters and SDKs, and set -ObjC in the 'Other Linker Flags' setting of your build target.

こんなメッセージが出るので、何か設定が漏れているのかと思っていましたが、バナー広告は表示されていました。

そしてリワード広告も出たり出なかったり、広告のリクエストした結果も返ってきていることがわかったので、ロードのタイミングにあたりをつけてみました。

if (await rewardAd.isLoaded) {
  rewardAd.show();
}

上記のコードでそもそも勘違いしていたのが isLoaded プロパティの戻り値が Future だったことで、事前に load()を実行していれば結果が常に true になるとばかり思い込んでいました。

そのため、load()からisLoadedまでの間がスムーズに行けば、show()が呼び出されるということでした。

対策

それならば isLoaded が true になるまで評価を繰り返せばいいはずと考えて、Timer で実装をラップしてみました。

_timer = Timer.periodic(Duration(seconds: 1), (_) async {
  if (await _rewardAd.isLoaded) {
    _rewardAd.show();
    _timer.cancel();
  }
  print('wait for loading ad');
});

想定した通り、数秒の待機でリワード広告が表示されました!

あとは listener の中で AdmobAdEvent の状態で処理を分ければ OK です。

dispose のタイミングについて

AdmobReward のインスタンスを dispose するタイミングも作り方によっては注意が必要です。

私の書き方が悪いのかもしれないですが、ドキュメント通りに show メソッドの後に dispose メソッドを入れると、AdmobAdEvent がいずれも実行されることなく終了してしまいます。

show()の直後に dispose()があると、即座に dispose()されるためタイミングを AdmobAdEvent.closed で実装しました。

listener: (AdmobAdEvent event, Map<String, dynamic> args) async {
  if (event == AdmobAdEvent.closed) {
    // ここにdispose()
    _rewardAd.dispose();
  }
}