Integrating AdMob in Android with Jetpack Compose

Last updated Jan 06, 2025

In today's mobile app ecosystem, monetization plays a crucial role in sustaining app development and maintenance. Google's AdMob is one of the most popular advertising platforms for mobile applications, offering various ad formats and robust integration options. This guide will walk you through the process of integrating AdMob into your Android Compose project, covering everything from initial setup to implementing different ad formats.

Prerequisites

Before we begin the integration process, ensure you have:

  • An active Google AdMob account
  • Android Studio (latest version recommended)
  • A Compose-based Android project
  • Basic knowledge of Kotlin and Jetpack Compose

Initial Setup

Step 1: Create an AdMob App

  1. Go to the AdMob console (https://admob.google.com/)
  2. Click on "Apps" in the sidebar
  3. Select "Add App"
  4. Choose Android as the platform
  5. Follow the prompts to register your app
  6. Save your Application ID for later use

Step 2: Add Dependencies

Open your app-level build.gradle.kts file and add the following dependencies

dependencies {
    // AdMob dependency
    implementation("com.google.android.gms:play-services-ads:22.6.0")
    
    // Other existing dependencies
    implementation("androidx.core:core-ktx:1.12.0")
    implementation("androidx.compose.ui:ui:1.5.4")
    // ... other dependencies
}

 

Step 3: Update AndroidManifest.xml

Add the required permissions and metadata to your AndroidManifest.xml:

    package="your.package.name">

   
   
   

            android:name=".YourApplication"
        ... >

       
                    android:name="com.google.android.gms.ads.APPLICATION_ID"
            android:value="ca-app-pub-xxxxxxxxxxxxxxxx~yyyyyyyyyyyy"/>

   

 

Initializing AdMob

Create an Application class to initialize AdMob when your app starts:

class YourApplication : Application() {
    override fun onCreate() {
        super.onCreate()
        
        // Initialize the Mobile Ads SDK
        MobileAds.initialize(this) { initializationStatus ->
            val statusMap = initializationStatus.adapterStatusMap
            for ((adapterClass, status) in statusMap) {
                println("Adapter name: $adapterClass, Description: ${status.description}, Latency: ${status.latency}")
            }
        }
    }
}

 

Understanding the AdMob initialization process:

  • MobileAds.initialize() is called once when your app starts
  • It prepares the SDK to load ads throughout your app
  • The initialization process is asynchronous
  • The callback provides status information about different ad adapters

 

Implementing Banner Ads

Banner ads are the most common ad format. Here's how to implement them in Compose:

@Composable
fun BannerAdView() {
    AndroidView(
        modifier = Modifier
            .fillMaxWidth()
            .height(50.dp),
        factory = { context ->
            AdView(context).apply {
                setAdSize(AdSize.BANNER)
                adUnitId = "ca-app-pub-xxxxxxxxxxxxxxxx/yyyyyyyyyyyy" // Your banner ad unit ID
                loadAd(AdRequest.Builder().build())
            }
        }
    )
}

 

Usage in your Compose UI:

@Composable
fun MainScreen() {
    Column(
        modifier = Modifier.fillMaxSize()
    ) {
        // Your content here
        
        Spacer(modifier = Modifier.weight(1f))
        
        // Banner ad at the bottom
        BannerAdView()
    }
}
 

 

Implementing Interstitial Ads

Interstitial ads are full-screen ads that cover the interface of their host app. Here's how to implement them

class InterstitialAdManager(private val context: Context) {
    private var interstitialAd: InterstitialAd? = null
    
    init {
        loadInterstitialAd()
    }
    
    private fun loadInterstitialAd() {
        val adRequest = AdRequest.Builder().build()
        
        InterstitialAd.load(
            context,
            "ca-app-pub-xxxxxxxxxxxxxxxx/yyyyyyyyyyyy", // Your interstitial ad unit ID
            adRequest,
            object : InterstitialAdLoadCallback() {
                override fun onAdLoaded(ad: InterstitialAd) {
                    interstitialAd = ad
                }
                
                override fun onAdFailedToLoad(error: LoadAdError) {
                    interstitialAd = null
                    println("Interstitial ad failed to load: ${error.message}")
                }
            }
        )
    }
    
    fun showAd(activity: Activity) {
        if (interstitialAd != null) {
            interstitialAd?.show(activity)
            interstitialAd?.fullScreenContentCallback = object : FullScreenContentCallback() {
                override fun onAdDismissedFullScreenContent() {
                    interstitialAd = null
                    loadInterstitialAd()
                }
                
                override fun onAdFailedToShowFullScreenContent(error: AdError) {
                    interstitialAd = null
                    println("Failed to show interstitial ad: ${error.message}")
                }
            }
        } else {
            println("Interstitial ad wasn't ready yet")
            loadInterstitialAd()
        }
    }
}

 

Implementing Reward Ads

Reward ads offer users in-app rewards for watching video ads. Here's the implementation:

class RewardedAdManager(private val context: Context) {
    private var rewardedAd: RewardedAd? = null
    
    init {
        loadRewardedAd()
    }
    
    private fun loadRewardedAd() {
        val adRequest = AdRequest.Builder().build()
        
        RewardedAd.load(
            context,
            "ca-app-pub-xxxxxxxxxxxxxxxx/yyyyyyyyyyyy", // Your rewarded ad unit ID
            adRequest,
            object : RewardedAdLoadCallback() {
                override fun onAdLoaded(ad: RewardedAd) {
                    rewardedAd = ad
                }
                
                override fun onAdFailedToLoad(error: LoadAdError) {
                    rewardedAd = null
                    println("Rewarded ad failed to load: ${error.message}")
                }
            }
        )
    }
    
    fun showAd(
        activity: Activity,
        onRewarded: (RewardItem) -> Unit
    ) {
        if (rewardedAd != null) {
            rewardedAd?.show(activity) { rewardItem ->
                onRewarded(rewardItem)
            }
            
            rewardedAd?.fullScreenContentCallback = object : FullScreenContentCallback() {
                override fun onAdDismissedFullScreenContent() {
                    rewardedAd = null
                    loadRewardedAd()
                }
                
                override fun onAdFailedToShowFullScreenContent(error: AdError) {
                    rewardedAd = null
                    println("Failed to show rewarded ad: ${error.message}")
                }
            }
        } else {
            println("Rewarded ad wasn't ready yet")
            loadRewardedAd()
        }
    }
}

 

 

Important considerations:

  1. Initialization Timing:

    • Initialize AdMob as early as possible in your app's lifecycle
    • The Application class's onCreate is the ideal place
    • Consider using background initialization for better app startup performance
  2. Error Handling:
    • Always implement proper error handling
    • Log initialization status for debugging
    • Have a fallback plan if initialization fails
  3. Testing:
    • Use test devices during development
    • Enable detailed logging in debug builds
    • Test initialization under different network conditions
  4. Configuration:
    • Set appropriate content ratings
    • Configure child-directed settings if applicable
    • Set up test device IDs in debug builds
  5. Monitoring:
    • Log initialization status
    • Track initialization time
    • Monitor for any initialization failures

This initialization process is fundamental to using AdMob in your app. Once properly initialized, you can start loading and displaying ads anywhere in your application. Would you like me to explain any specific part of this in more detail?

 

Best Practices and Tips

  1. Test with Test Ads Always use test ad unit IDs during development to avoid violations of AdMob policies. Google provides specific test ad unit IDs for this purpose
object AdMobConstants {
    const val TEST_BANNER_AD_UNIT_ID = "ca-app-pub-3940256099942544/6300978111"
    const val TEST_INTERSTITIAL_AD_UNIT_ID = "ca-app-pub-3940256099942544/1033173712"
    const val TEST_REWARDED_AD_UNIT_ID = "ca-app-pub-3940256099942544/5224354917"
}
  1. Handle Configuration Changes Ensure your ad implementation handles configuration changes properly. For interstitial and rewarded ads, consider using ViewModel to retain ad instances.
  2. Implement Error Handling Always implement proper error handling for ad loading and showing failures. This helps maintain a good user experience even when ads fail to load.
  3. Respect User Experience
    1. Don't show too many ads too frequently
    2. Place banner ads in appropriate locations
    3. Show interstitial ads at natural transition points
    4. Make reward ad benefits clear to users
  4. Performance Considerations
    1. Load ads in advance when possible
    2. Implement proper lifecycle management
    3. Clear ad references when no longer needed
    4. Use proper scoping for ad managers

Conclusion

Integrating AdMob into your Android Compose project requires careful planning and implementation. By following this guide and adhering to best practices, you can successfully monetize your app while maintaining a good user experience. Remember to always test thoroughly with test ads before switching to real ad unit IDs for production.

Remember that ad revenue can vary significantly based on factors like placement, frequency, and user engagement. Continuously monitor your AdMob dashboard and user feedback to optimize your ad implementation for the best results

 

 

Article Contributed By :
https://www.rrtutors.com/site_assets/profile/assets/img/avataaars.svg

86 Views