React Native中如何在返回页面或切换首页时展示InterstitialAd
解决方案
一、核心思路
要实现离开TestAds页面(点击默认返回按钮)和切换底部Tab页面时展示插屏广告,需要分两步处理:
- 在TestAds页面监听导航返回事件,页面卸载前触发广告。
- 在底部Tab导航中监听Tab切换事件,切换前触发广告。
- 预加载广告并管理加载状态,确保广告可用时才显示,避免报错。
二、代码修改
1. 优化TestAds页面(处理返回按钮事件)
import React, { useState, useEffect, useRef } from "react"; import { View, Text, ScrollView } from 'react-native'; import { InterstitialAd, TestIds, AdEventType } from 'react-native-google-mobile-ads'; const TestAds = ({ navigation }) => { // 保存广告实例,避免重复创建 const interstitialRef = useRef(null); // 标记广告是否加载完成 const [adLoaded, setAdLoaded] = useState(false); useEffect(() => { // 创建插屏广告实例 const interstitial = InterstitialAd.createForAdRequest(TestIds.INTERSTITIAL, { requestNonPersonalizedAdsOnly: true, keywords: ['fashion', 'clothing'], }); interstitialRef.current = interstitial; // 监听广告加载成功 const loadedListener = interstitial.addAdEventListener(AdEventType.LOADED, () => { setAdLoaded(true); }); // 监听广告加载失败 const failedListener = interstitial.addAdEventListener(AdEventType.FAILED_TO_LOAD, (error) => { console.log('插屏广告加载失败:', error); setAdLoaded(false); }); // 初始化加载广告 interstitial.load(); // 监听页面离开事件(默认返回按钮触发) const unsubscribe = navigation.addListener('beforeRemove', (e) => { if (adLoaded) { // 先阻止默认导航行为 e.preventDefault(); // 显示广告,完成后再执行导航 interstitialRef.current.show().then(() => { navigation.dispatch(e.data.action); // 广告显示后重新加载,以备下次使用 interstitialRef.current.load(); setAdLoaded(false); }).catch((error) => { console.log('广告显示失败:', error); // 显示失败时直接执行导航 navigation.dispatch(e.data.action); }); } }); // 清理监听器和广告实例,防止内存泄漏 return () => { unsubscribe(); loadedListener?.remove(); failedListener?.remove(); interstitialRef.current = null; }; }, [navigation, adLoaded]); return ( <ScrollView> <View style={{ marginTop: 20, padding: 16 }}> <Text> Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, </Text> </View> </ScrollView> ); }; export default TestAds;
2. 优化HomeTabs组件(处理Tab切换事件)
import * as React from 'react'; import { createBottomTabNavigator } from '@react-navigation/bottom-tabs'; import Contact from './Contact'; import Test from './Test'; import { InterstitialAd, TestIds, AdEventType } from 'react-native-google-mobile-ads'; const Tab = createBottomTabNavigator(); const HomeTabs = () => { const interstitialRef = React.useRef(null); const [adLoaded, setAdLoaded] = React.useState(false); React.useEffect(() => { // 创建并预加载广告 const interstitial = InterstitialAd.createForAdRequest(TestIds.INTERSTITIAL, { requestNonPersonalizedAdsOnly: true, keywords: ['fashion', 'clothing'], }); interstitialRef.current = interstitial; const loadedListener = interstitial.addAdEventListener(AdEventType.LOADED, () => { setAdLoaded(true); }); const failedListener = interstitial.addAdEventListener(AdEventType.FAILED_TO_LOAD, (error) => { console.log('插屏广告加载失败:', error); setAdLoaded(false); }); interstitial.load(); return () => { loadedListener?.remove(); failedListener?.remove(); interstitialRef.current = null; }; }, []); return ( <Tab.Navigator screenOptions={{ headerShown: false }}> <Tab.Screen name="Contact" component={Contact} listeners={{ tabPress: (e) => { if (adLoaded) { e.preventDefault(); interstitialRef.current.show().then(() => { e.target.navigate('Contact'); // 重新加载广告 interstitialRef.current.load(); setAdLoaded(false); }).catch((error) => { console.log('广告显示失败:', error); e.target.navigate('Contact'); }); } } }} /> <Tab.Screen name="Test" component={Test} listeners={{ tabPress: (e) => { if (adLoaded) { e.preventDefault(); interstitialRef.current.show().then(() => { e.target.navigate('Test'); interstitialRef.current.load(); setAdLoaded(false); }).catch((error) => { console.log('广告显示失败:', error); e.target.navigate('Test'); }); } } }} /> </Tab.Navigator> ); }; export default HomeTabs;
3. 修复App.js的导航错误
原代码中TestAds页面错误使用了<Tab.Screen>,改为<Stack.Screen>:
import * as React from 'react'; import { NavigationContainer } from '@react-navigation/native'; import { createNativeStackNavigator } from '@react-navigation/native-stack'; import TestAds from './TestAds'; import HomeTabs from './HomeTabs'; const Stack = createNativeStackNavigator(); export default function App () { return ( <NavigationContainer> <Stack.Navigator> <Stack.Screen name="Home" component={HomeTabs} /> <Stack.Screen name="TestAds" component={TestAds} /> </Stack.Navigator> </NavigationContainer> ); }
三、关键说明
- 广告预加载:在组件挂载时提前加载广告,确保触发时机有可用广告。
- 事件监听:使用
beforeRemove监听页面返回,tabPress监听Tab切换,拦截默认行为后显示广告。 - 错误处理:广告加载/显示失败时,保证导航流程正常执行,不阻塞用户操作。
- 内存管理:及时清理事件监听器和广告实例,避免内存泄漏。
内容的提问来源于stack exchange,提问作者Rahul Aadam
相关产品推荐
相关产品推荐

