Android集成MoPub后插屏广告展示崩溃问题排查求助
我来帮你梳理下代码里的关键问题点,这些大概率是导致崩溃的原因:
1. Facebook中介配置完全错误
你在Facebook的配置里写了:
facebookConfig.apply { put("banner", "") put("interstitial", "true") }
这里的interstitial字段应该填Facebook Audience Network的插屏广告位ID(测试ID或正式ID都可以),而不是字符串"true"。错误的配置会导致中介广告加载逻辑异常,直接引发崩溃。
2. MoPub SDK初始化与广告加载顺序错误
MoPub.initializeSdk是异步方法,你现在直接在初始化语句后就创建MoPubInterstitial并调用load(),这时候SDK可能还没完成初始化,会导致广告加载流程出错。
更严重的是:你给MoPubInterstitial传的第二个参数是MoPub的App ID(b860fe901ec44849975526de44970b4a),但这个参数需要的是插屏广告位ID,不是App ID!这会直接导致广告加载失败,进而触发崩溃。
正确的做法是在SDK初始化完成的回调里创建并加载广告:
MoPub.initializeSdk(this, sdkConfiguration.build()) { // SDK初始化完成后再初始化插屏广告,替换为你的插屏广告位ID mInterstitial = MoPubInterstitial(this, "你的MoPub插屏广告位ID") mInterstitial?.interstitialAdListener = listner mInterstitial?.load() }
3. 未实现onInterstitialShown方法
你在InterstitialAdListener里给onInterstitialShown留了TODO("Not yet implemented"),这个方法在广告展示时会被调用,TODO会抛出未实现的异常,直接导致崩溃。哪怕是空实现也要补全:
override fun onInterstitialShown(p0: MoPubInterstitial?) { // 可以在这里记录广告展示日志,或者空实现 Log.d("Interstitial", "插屏广告已展示") }
4. 状态变量逻辑混乱,易引发生命周期冲突
你的check和check2变量用来控制页面跳转,但逻辑不够严谨,可能导致多次跳转或者在Activity状态异常时启动新页面。比如:
onInterstitialLoaded里直接调用show(),但此时SplashActivity可能还未完全就绪;onResume里的10秒延迟跳转,可能在广告已经展示跳转后仍执行。
建议替换成更清晰的状态变量:
private var hasNavigatedToMain = false // 标记是否已经跳转到主页面
然后封装统一的跳转方法,避免重复操作:
private fun navigateToMain() { if (!hasNavigatedToMain && !isFinishing) { hasNavigatedToMain = true val intent = Intent(this@SplashScreen, MainActivity::class.java) startActivity(intent) finishAffinity() } }
5. 广告展示时未判断Activity状态
在onInterstitialLoaded里展示广告时,要确保当前Activity没有被销毁,避免在异常状态下执行展示操作:
override fun onInterstitialLoaded(p0: MoPubInterstitial?) { if (!hasNavigatedToMain && !isFinishing && mInterstitial?.isReady == true) { try { mInterstitial?.show() } catch (e: Exception) { Log.e("Interstitial", "广告展示失败: ${e.message}") navigateToMain() } } }
完整优化后的关键代码示例
class SplashScreen : AppCompatActivity() { private var hasNavigatedToMain = false private var mInterstitial: MoPubInterstitial? = null override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) val win = this.window win.setFlags( WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN ) setContentView(R.layout.activity_splash_screen) supportActionBar?.hide() // 修正Facebook配置:替换为实际的广告位ID val facebookConfig = HashMap<String, String>(); facebookConfig.apply { put("banner", "你的Facebook Banner广告ID") put("interstitial", "你的Facebook插屏广告ID") } AudienceNetworkAds.initialize(this) val sdkConfiguration = SdkConfiguration.Builder("b860fe901ec44849975526de44970b4a") .withMediatedNetworkConfiguration(FacebookAdapterConfiguration::class.java.name, facebookConfig) .withLogLevel(MoPubLog.LogLevel.INFO) .withLegitimateInterestAllowed(false) .build(); val listner = object : MoPubInterstitial.InterstitialAdListener { override fun onInterstitialLoaded(p0: MoPubInterstitial?) { if (!hasNavigatedToMain && !isFinishing && mInterstitial?.isReady == true) { try { mInterstitial?.show() } catch (e: Exception) { Log.e("Interstitial", "展示失败: ${e.message}") navigateToMain() } } } override fun onInterstitialFailed(p0: MoPubInterstitial?, p1: MoPubErrorCode?) { Log.e("Interstitial", "加载失败: ${p1?.name}") Handler(Looper.getMainLooper()).postDelayed({ navigateToMain() }, 1000) } override fun onInterstitialShown(p0: MoPubInterstitial?) { Log.d("Interstitial", "插屏广告已展示") } override fun onInterstitialClicked(p0: MoPubInterstitial?) { // 可选:记录广告点击事件 } override fun onInterstitialDismissed(p0: MoPubInterstitial?) { navigateToMain() } } // 异步初始化SDK,完成后再创建插屏广告 MoPub.initializeSdk(this, sdkConfiguration.build()) { // 替换为你的MoPub插屏广告位ID mInterstitial = MoPubInterstitial(this, "你的MoPub插屏广告位ID") mInterstitial?.interstitialAdListener = listner mInterstitial?.load() } } private fun navigateToMain() { if (!hasNavigatedToMain && !isFinishing) { hasNavigatedToMain = true val intent = Intent(this@SplashScreen, MainActivity::class.java) startActivity(intent) finishAffinity() } } override fun onPause() { super.onPause() MoPub.onPause(this); } override fun onStop() { super.onStop() MoPub.onStop(this); } override fun onResume() { super.onResume() MoPub.onResume(this); // 10秒超时跳转 Handler(Looper.getMainLooper()).postDelayed({ navigateToMain() }, 10000) } override fun onDestroy() { super.onDestroy() mInterstitial?.let { it.interstitialAdListener = null it.destroy() } mInterstitial = null } }
额外排查建议
- 查看崩溃堆栈:在Android Studio的Logcat里搜索崩溃的具体信息(比如空指针、未初始化异常),这能帮你更快定位核心问题;
- 使用测试广告:确保你用的是MoPub和Facebook官方提供的测试广告位ID,避免正式广告加载异常;
- 检查依赖版本:确认MoPub SDK和Facebook Adapter的版本兼容,建议使用官方推荐的最新稳定版本。
内容的提问来源于stack exchange,提问作者Jalal Khan




