admanagekit-mcp-server 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/content/README.md +851 -0
- package/content/docs/AD_FREQUENCY_CONTROL.md +450 -0
- package/content/docs/AD_LOADING_STRATEGIES.md +369 -0
- package/content/docs/API_REFERENCE.md +734 -0
- package/content/docs/APP_PURCHASE_GUIDE.md +704 -0
- package/content/docs/BANNER_AD_IMPROVEMENTS.md +325 -0
- package/content/docs/COMPOSE_INTEGRATION.md +477 -0
- package/content/docs/CONFIGURATION_USAGE.md +168 -0
- package/content/docs/INTERSTITIAL_BUILDER_GUIDE.md +518 -0
- package/content/docs/JAVA_USAGE_GUIDE.md +785 -0
- package/content/docs/LOADING_STRATEGY_EXAMPLES.md +463 -0
- package/content/docs/NATIVE_AD_MANAGER_ENHANCEMENTS.md +347 -0
- package/content/docs/NATIVE_AD_PRELOADING.md +467 -0
- package/content/docs/NATIVE_TEMPLATE_VIEW.md +413 -0
- package/content/docs/app-open-ads.md +412 -0
- package/content/docs/interstitial-ads.md +269 -0
- package/content/docs/native-ads-caching.md +182 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.1.0.md +156 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.2.0.md +248 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.3.0.md +280 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.5.0.md +73 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.6.0.md +265 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.7.0.md +168 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.8.0.md +153 -0
- package/content/docs/release-notes/RELEASE_NOTES_v2.9.0.md +479 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.0.0.md +343 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.1.0.md +131 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.3.0.md +252 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.3.2.md +215 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.3.3.md +116 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.3.4.md +142 -0
- package/content/docs/release-notes/RELEASE_NOTES_v3.3.5.md +94 -0
- package/content/docs/rewarded-ads.md +623 -0
- package/content/wiki/Ad-Loading-Strategies.md +209 -0
- package/content/wiki/App-Open-Ads.md +189 -0
- package/content/wiki/Banner-Ads.md +133 -0
- package/content/wiki/Billing-Integration.md +69 -0
- package/content/wiki/Configuration.md +252 -0
- package/content/wiki/Consumable-Products.md +166 -0
- package/content/wiki/Home.md +144 -0
- package/content/wiki/Interstitial-Ads.md +313 -0
- package/content/wiki/Jetpack-Compose.md +270 -0
- package/content/wiki/NativeAdManager.md +220 -0
- package/content/wiki/Purchase-Categories.md +94 -0
- package/content/wiki/Rewarded-Ads.md +420 -0
- package/content/wiki/Subscription-Upgrades.md +278 -0
- package/content/wiki/Subscriptions.md +368 -0
- package/content/wiki/_Footer.md +3 -0
- package/content/wiki/_Sidebar.md +18 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +6 -0
- package/dist/index.js.map +1 -0
- package/dist/server.d.ts +1 -0
- package/dist/server.js +18 -0
- package/dist/server.js.map +1 -0
- package/dist/tools/code-generation.d.ts +2 -0
- package/dist/tools/code-generation.js +264 -0
- package/dist/tools/code-generation.js.map +1 -0
- package/dist/tools/documentation.d.ts +2 -0
- package/dist/tools/documentation.js +202 -0
- package/dist/tools/documentation.js.map +1 -0
- package/dist/types.d.ts +18 -0
- package/dist/types.js +83 -0
- package/dist/types.js.map +1 -0
- package/dist/utils/doc-loader.d.ts +17 -0
- package/dist/utils/doc-loader.js +245 -0
- package/dist/utils/doc-loader.js.map +1 -0
- package/dist/utils/search.d.ts +2 -0
- package/dist/utils/search.js +62 -0
- package/dist/utils/search.js.map +1 -0
- package/dist/utils/templates.d.ts +60 -0
- package/dist/utils/templates.js +793 -0
- package/dist/utils/templates.js.map +1 -0
- package/package.json +51 -0
|
@@ -0,0 +1,518 @@
|
|
|
1
|
+
# InterstitialAdBuilder - Complete Guide
|
|
2
|
+
|
|
3
|
+
## ✨ Overview
|
|
4
|
+
|
|
5
|
+
The `InterstitialAdBuilder` provides a modern, fluent API for loading and showing interstitial ads with advanced features like fallback support, automatic retry, and customizable callbacks.
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## 🚀 Basic Usage
|
|
10
|
+
|
|
11
|
+
### 1. Simple Show
|
|
12
|
+
```kotlin
|
|
13
|
+
InterstitialAdBuilder.with(this)
|
|
14
|
+
.adUnit("ca-app-pub-xxxxx/yyyyy")
|
|
15
|
+
.show {
|
|
16
|
+
// Continue with next action
|
|
17
|
+
startNextActivity()
|
|
18
|
+
}
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
### 2. Using Extension Function
|
|
22
|
+
```kotlin
|
|
23
|
+
showInterstitialAd("ca-app-pub-xxxxx/yyyyy") {
|
|
24
|
+
startNextActivity()
|
|
25
|
+
}
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
---
|
|
29
|
+
|
|
30
|
+
## 🔧 Builder Methods
|
|
31
|
+
|
|
32
|
+
### Configuration Methods
|
|
33
|
+
|
|
34
|
+
| Method | Description | Example |
|
|
35
|
+
|--------|-------------|---------|
|
|
36
|
+
| `.adUnit(String)` | Set primary ad unit ID (**required**) | `.adUnit("ca-app-pub-xxx/123")` |
|
|
37
|
+
| `.fallback(String)` | Add single fallback ad unit | `.fallback("ca-app-pub-xxx/456")` |
|
|
38
|
+
| `.fallbacks(vararg String)` | Add multiple fallback units | `.fallbacks("unit1", "unit2", "unit3")` |
|
|
39
|
+
| `.force()` | Show ad ignoring time interval | `.force()` |
|
|
40
|
+
| `.respectInterval(Boolean)` | Respect time interval (default: true) | `.respectInterval(false)` |
|
|
41
|
+
| `.timeout(Long)` | Set load timeout in milliseconds | `.timeout(5000)` |
|
|
42
|
+
| `.timeoutSeconds(Int)` | Set load timeout in seconds | `.timeoutSeconds(5)` |
|
|
43
|
+
| `.debug()` | Enable debug logging | `.debug()` |
|
|
44
|
+
|
|
45
|
+
### Loading Strategy Methods
|
|
46
|
+
|
|
47
|
+
| Method | Description | Example |
|
|
48
|
+
|--------|-------------|---------|
|
|
49
|
+
| `.loadingStrategy(Strategy)` | Set how ads are loaded/shown | `.loadingStrategy(AdLoadingStrategy.HYBRID)` |
|
|
50
|
+
| `.waitForLoading()` | Smart wait for splash screens (see below) | `.waitForLoading()` |
|
|
51
|
+
|
|
52
|
+
### Frequency Control Methods
|
|
53
|
+
|
|
54
|
+
| Method | Description | Example |
|
|
55
|
+
|--------|-------------|---------|
|
|
56
|
+
| `.everyNthTime(Int)` | Show only every Nth call | `.everyNthTime(3)` |
|
|
57
|
+
| `.maxShows(Int)` | Maximum total shows in session | `.maxShows(5)` |
|
|
58
|
+
| `.minInterval(Long)` | Minimum ms between shows | `.minInterval(30000)` |
|
|
59
|
+
| `.minIntervalSeconds(Int)` | Minimum seconds between shows | `.minIntervalSeconds(30)` |
|
|
60
|
+
|
|
61
|
+
### Callback Methods
|
|
62
|
+
|
|
63
|
+
| Method | Description | Parameters |
|
|
64
|
+
|--------|-------------|------------|
|
|
65
|
+
| `.onAdLoaded(() -> Unit)` | Called when ad loaded successfully | None |
|
|
66
|
+
| `.onAdShown(() -> Unit)` | Called when ad is displayed | None |
|
|
67
|
+
| `.onFailed((LoadAdError) -> Unit)` | Called when loading/showing fails | error: LoadAdError |
|
|
68
|
+
|
|
69
|
+
### Terminal Methods
|
|
70
|
+
|
|
71
|
+
| Method | Description |
|
|
72
|
+
|--------|-------------|
|
|
73
|
+
| `.show(() -> Unit)` | Load and show ad, then execute callback |
|
|
74
|
+
| `.preload()` | Just preload ad without showing |
|
|
75
|
+
|
|
76
|
+
---
|
|
77
|
+
|
|
78
|
+
## 🎯 Loading Strategies
|
|
79
|
+
|
|
80
|
+
### Available Strategies
|
|
81
|
+
|
|
82
|
+
| Strategy | Behavior | Best For |
|
|
83
|
+
|----------|----------|----------|
|
|
84
|
+
| `ON_DEMAND` | Always fetch fresh ad with loading dialog | Important moments, max revenue |
|
|
85
|
+
| `ONLY_CACHE` | Only show if cached, skip otherwise | Smooth gameplay, no interruption |
|
|
86
|
+
| `HYBRID` | Check cache first, fetch if needed (default) | Balanced UX and fill rate |
|
|
87
|
+
|
|
88
|
+
### Strategy Examples
|
|
89
|
+
|
|
90
|
+
```kotlin
|
|
91
|
+
// ON_DEMAND: Always fetch fresh (shows loading dialog)
|
|
92
|
+
InterstitialAdBuilder.with(activity)
|
|
93
|
+
.adUnit(adUnitId)
|
|
94
|
+
.loadingStrategy(AdLoadingStrategy.ON_DEMAND)
|
|
95
|
+
.show { next() }
|
|
96
|
+
|
|
97
|
+
// ONLY_CACHE: Show only if ready, no network request
|
|
98
|
+
InterstitialAdBuilder.with(activity)
|
|
99
|
+
.adUnit(adUnitId)
|
|
100
|
+
.loadingStrategy(AdLoadingStrategy.ONLY_CACHE)
|
|
101
|
+
.show { next() }
|
|
102
|
+
|
|
103
|
+
// HYBRID: Try cache first, fetch with dialog if needed
|
|
104
|
+
InterstitialAdBuilder.with(activity)
|
|
105
|
+
.adUnit(adUnitId)
|
|
106
|
+
.loadingStrategy(AdLoadingStrategy.HYBRID)
|
|
107
|
+
.show { next() }
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
---
|
|
111
|
+
|
|
112
|
+
## 🚀 Splash Screen Pattern
|
|
113
|
+
|
|
114
|
+
Use `.waitForLoading()` for optimal splash screen ad experience:
|
|
115
|
+
|
|
116
|
+
### How It Works
|
|
117
|
+
|
|
118
|
+
| Ad State | Action |
|
|
119
|
+
|----------|--------|
|
|
120
|
+
| **READY** | Shows immediately |
|
|
121
|
+
| **LOADING** | Waits with timeout, then shows |
|
|
122
|
+
| **NEITHER** | Force fetches with dialog |
|
|
123
|
+
|
|
124
|
+
### Recommended Pattern
|
|
125
|
+
|
|
126
|
+
```kotlin
|
|
127
|
+
// Step 1: In Application.onCreate() - Start loading early
|
|
128
|
+
class MyApplication : Application() {
|
|
129
|
+
override fun onCreate() {
|
|
130
|
+
super.onCreate()
|
|
131
|
+
AdManager.getInstance().loadInterstitialAd(this, "ca-app-pub-xxx/yyy")
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
// Step 2: In SplashActivity - Use waitForLoading()
|
|
136
|
+
class SplashActivity : AppCompatActivity() {
|
|
137
|
+
|
|
138
|
+
override fun onCreate(savedInstanceState: Bundle?) {
|
|
139
|
+
super.onCreate(savedInstanceState)
|
|
140
|
+
|
|
141
|
+
// Smart wait: shows cached, waits for loading, or force fetches
|
|
142
|
+
InterstitialAdBuilder.with(this)
|
|
143
|
+
.adUnit("ca-app-pub-xxx/yyy")
|
|
144
|
+
.waitForLoading() // Smart splash behavior
|
|
145
|
+
.timeout(5000) // 5 second max wait
|
|
146
|
+
.show {
|
|
147
|
+
startMainActivity()
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
### Alternative: Direct AdManager Usage
|
|
154
|
+
|
|
155
|
+
```kotlin
|
|
156
|
+
// Check states manually
|
|
157
|
+
val adManager = AdManager.getInstance()
|
|
158
|
+
|
|
159
|
+
when {
|
|
160
|
+
adManager.isReady() -> {
|
|
161
|
+
// Ad cached, show immediately
|
|
162
|
+
adManager.forceShowInterstitial(activity, callback)
|
|
163
|
+
}
|
|
164
|
+
adManager.isLoading() -> {
|
|
165
|
+
// Ad loading, use showOrWaitForAd
|
|
166
|
+
adManager.showOrWaitForAd(activity, callback, timeoutMillis = 5000)
|
|
167
|
+
}
|
|
168
|
+
else -> {
|
|
169
|
+
// Nothing happening, force fetch
|
|
170
|
+
adManager.forceShowInterstitialWithDialog(activity, callback)
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
---
|
|
176
|
+
|
|
177
|
+
## 📚 Complete Examples
|
|
178
|
+
|
|
179
|
+
### Example 1: Basic Navigation
|
|
180
|
+
```kotlin
|
|
181
|
+
class GameOverActivity : AppCompatActivity() {
|
|
182
|
+
|
|
183
|
+
private fun playAgain() {
|
|
184
|
+
InterstitialAdBuilder.with(this)
|
|
185
|
+
.adUnit(getString(R.string.interstitial_ad_unit))
|
|
186
|
+
.show {
|
|
187
|
+
// Ad shown (or failed), restart game
|
|
188
|
+
startActivity(Intent(this, GameActivity::class.java))
|
|
189
|
+
finish()
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
### Example 2: With Fallback Chain
|
|
196
|
+
```kotlin
|
|
197
|
+
InterstitialAdBuilder.with(this)
|
|
198
|
+
.adUnit("ca-app-pub-xxxxx/primary")
|
|
199
|
+
.fallback("ca-app-pub-xxxxx/backup-1")
|
|
200
|
+
.fallback("ca-app-pub-xxxxx/backup-2")
|
|
201
|
+
.force() // Ignore time interval
|
|
202
|
+
.show {
|
|
203
|
+
goToNextScreen()
|
|
204
|
+
}
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
### Example 3: With All Callbacks
|
|
208
|
+
```kotlin
|
|
209
|
+
InterstitialAdBuilder.with(this)
|
|
210
|
+
.adUnit("ca-app-pub-xxxxx/yyyyy")
|
|
211
|
+
.onAdLoaded {
|
|
212
|
+
Log.d("Ads", "Ad loaded successfully")
|
|
213
|
+
analytics.log("ad_loaded")
|
|
214
|
+
}
|
|
215
|
+
.onAdShown {
|
|
216
|
+
Log.d("Ads", "Ad shown to user")
|
|
217
|
+
analytics.log("ad_shown")
|
|
218
|
+
}
|
|
219
|
+
.onFailed { error ->
|
|
220
|
+
Log.e("Ads", "Ad failed: ${error.message}")
|
|
221
|
+
analytics.log("ad_failed", "error_code" to error.code)
|
|
222
|
+
}
|
|
223
|
+
.show {
|
|
224
|
+
proceedToNextScreen()
|
|
225
|
+
}
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
### Example 4: With Loading Dialog
|
|
229
|
+
```kotlin
|
|
230
|
+
// Show "Please wait..." dialog while ad loads
|
|
231
|
+
InterstitialAdBuilder.with(this)
|
|
232
|
+
.adUnit("ca-app-pub-xxxxx/yyyyy")
|
|
233
|
+
.withLoadingDialog()
|
|
234
|
+
.show {
|
|
235
|
+
continueFlow()
|
|
236
|
+
}
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
### Example 5: Count-Limited Ads
|
|
240
|
+
```kotlin
|
|
241
|
+
// Only show ad first 5 times
|
|
242
|
+
InterstitialAdBuilder.with(this)
|
|
243
|
+
.adUnit("ca-app-pub-xxxxx/yyyyy")
|
|
244
|
+
.maxShows(5) // After 5 displays, skip ad
|
|
245
|
+
.show {
|
|
246
|
+
nextAction()
|
|
247
|
+
}
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
### Example 6: Debug Mode
|
|
251
|
+
```kotlin
|
|
252
|
+
// Enable debug logging for development
|
|
253
|
+
InterstitialAdBuilder.with(this)
|
|
254
|
+
.adUnit("ca-app-pub-xxxxx/yyyyy")
|
|
255
|
+
.debug() // Logs all events
|
|
256
|
+
.show {
|
|
257
|
+
next()
|
|
258
|
+
}
|
|
259
|
+
```
|
|
260
|
+
|
|
261
|
+
### Example 7: Preload Pattern
|
|
262
|
+
```kotlin
|
|
263
|
+
class MainActivity : AppCompatActivity() {
|
|
264
|
+
|
|
265
|
+
override fun onCreate(savedInstanceState: Bundle?) {
|
|
266
|
+
super.onCreate(savedInstanceState)
|
|
267
|
+
|
|
268
|
+
// Preload ad on activity create
|
|
269
|
+
preloadInterstitialAd("ca-app-pub-xxxxx/yyyyy")
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
private fun showAdBeforeExit() {
|
|
273
|
+
// Ad already preloaded, shows instantly
|
|
274
|
+
showInterstitialAd("ca-app-pub-xxxxx/yyyyy") {
|
|
275
|
+
finish()
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
}
|
|
279
|
+
```
|
|
280
|
+
|
|
281
|
+
### Example 8: Complex Configuration
|
|
282
|
+
```kotlin
|
|
283
|
+
InterstitialAdBuilder.with(this)
|
|
284
|
+
.adUnit("ca-app-pub-xxxxx/primary")
|
|
285
|
+
.fallbacks("backup-1", "backup-2", "backup-3")
|
|
286
|
+
.force()
|
|
287
|
+
.autoReload(true)
|
|
288
|
+
.withLoadingDialog()
|
|
289
|
+
.onAdLoaded {
|
|
290
|
+
Toast.makeText(this, "Ad ready!", Toast.LENGTH_SHORT).show()
|
|
291
|
+
}
|
|
292
|
+
.onAdShown {
|
|
293
|
+
FirebaseAnalytics.getInstance(this).logEvent("interstitial_shown", null)
|
|
294
|
+
}
|
|
295
|
+
.onFailed { error ->
|
|
296
|
+
Toast.makeText(this, "No ad available", Toast.LENGTH_SHORT).show()
|
|
297
|
+
}
|
|
298
|
+
.debug()
|
|
299
|
+
.show {
|
|
300
|
+
startActivity(Intent(this, NextActivity::class.java))
|
|
301
|
+
finish()
|
|
302
|
+
}
|
|
303
|
+
```
|
|
304
|
+
|
|
305
|
+
---
|
|
306
|
+
|
|
307
|
+
## 🎯 Best Practices
|
|
308
|
+
|
|
309
|
+
### 1. Always Use Fallbacks
|
|
310
|
+
```kotlin
|
|
311
|
+
// ✅ GOOD: Multiple ad units for higher fill rate
|
|
312
|
+
InterstitialAdBuilder.with(this)
|
|
313
|
+
.adUnit("primary")
|
|
314
|
+
.fallbacks("backup-1", "backup-2")
|
|
315
|
+
.show { next() }
|
|
316
|
+
|
|
317
|
+
// ❌ BAD: Single ad unit
|
|
318
|
+
InterstitialAdBuilder.with(this)
|
|
319
|
+
.adUnit("primary")
|
|
320
|
+
.show { next() }
|
|
321
|
+
```
|
|
322
|
+
|
|
323
|
+
### 2. Preload for Better UX
|
|
324
|
+
```kotlin
|
|
325
|
+
// ✅ GOOD: Preload early
|
|
326
|
+
class MyActivity : AppCompatActivity() {
|
|
327
|
+
override fun onCreate(savedInstanceState: Bundle?) {
|
|
328
|
+
super.onCreate(savedInstanceState)
|
|
329
|
+
// Preload immediately
|
|
330
|
+
preloadInterstitialAd("ad-unit-id")
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
fun showAd() {
|
|
334
|
+
// Ad already loaded, instant display
|
|
335
|
+
showInterstitialAd("ad-unit-id") { next() }
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
```
|
|
339
|
+
|
|
340
|
+
### 3. Handle Failures Gracefully
|
|
341
|
+
```kotlin
|
|
342
|
+
// ✅ GOOD: Always handle errors
|
|
343
|
+
InterstitialAdBuilder.with(this)
|
|
344
|
+
.adUnit("ad-unit")
|
|
345
|
+
.onFailed { error ->
|
|
346
|
+
// Log error but continue
|
|
347
|
+
Log.e("Ads", "Failed: ${error.message}")
|
|
348
|
+
}
|
|
349
|
+
.show {
|
|
350
|
+
// Always proceed regardless of ad result
|
|
351
|
+
continueFlow()
|
|
352
|
+
}
|
|
353
|
+
```
|
|
354
|
+
|
|
355
|
+
### 4. Use Debug Mode in Development
|
|
356
|
+
```kotlin
|
|
357
|
+
// ✅ GOOD: Debug mode for testing
|
|
358
|
+
if (BuildConfig.DEBUG) {
|
|
359
|
+
InterstitialAdBuilder.with(this)
|
|
360
|
+
.adUnit("ad-unit")
|
|
361
|
+
.debug() // See all logs
|
|
362
|
+
.show { next() }
|
|
363
|
+
}
|
|
364
|
+
```
|
|
365
|
+
|
|
366
|
+
---
|
|
367
|
+
|
|
368
|
+
## ⚡ Performance Tips
|
|
369
|
+
|
|
370
|
+
1. **Preload Early**: Load ads when app starts or on previous screen
|
|
371
|
+
2. **Use Multiple Fallbacks**: 3-5 ad units for best fill rate
|
|
372
|
+
3. **Enable Auto-Reload**: Ensures next ad is always ready
|
|
373
|
+
4. **Respect Intervals**: Don't spam users with too many ads
|
|
374
|
+
5. **Track Analytics**: Monitor success rates to optimize
|
|
375
|
+
|
|
376
|
+
---
|
|
377
|
+
|
|
378
|
+
## 🔍 Comparison: Old vs New API
|
|
379
|
+
|
|
380
|
+
### Old Approach (Verbose)
|
|
381
|
+
```kotlin
|
|
382
|
+
val adManager = AdManager.getInstance()
|
|
383
|
+
adManager.loadInterstitialAd(this, "ad-unit",
|
|
384
|
+
object : InterstitialAdLoadCallback() {
|
|
385
|
+
override fun onAdLoaded(ad: InterstitialAd) {
|
|
386
|
+
adManager.forceShowInterstitial(this@Activity,
|
|
387
|
+
object : AdManagerCallback {
|
|
388
|
+
override fun onAdLoaded() {}
|
|
389
|
+
override fun onNextAction() {
|
|
390
|
+
nextScreen()
|
|
391
|
+
}
|
|
392
|
+
override fun onFailedToLoad(error: AdError?) {
|
|
393
|
+
nextScreen()
|
|
394
|
+
}
|
|
395
|
+
})
|
|
396
|
+
}
|
|
397
|
+
override fun onAdFailedToLoad(error: LoadAdError) {
|
|
398
|
+
nextScreen()
|
|
399
|
+
}
|
|
400
|
+
})
|
|
401
|
+
```
|
|
402
|
+
**Lines: 18** | **Readability: Poor**
|
|
403
|
+
|
|
404
|
+
### New Approach (Builder)
|
|
405
|
+
```kotlin
|
|
406
|
+
showInterstitialAd("ad-unit") {
|
|
407
|
+
nextScreen()
|
|
408
|
+
}
|
|
409
|
+
```
|
|
410
|
+
**Lines: 3** | **Readability: Excellent** ✨
|
|
411
|
+
|
|
412
|
+
---
|
|
413
|
+
|
|
414
|
+
## 📊 Feature Matrix
|
|
415
|
+
|
|
416
|
+
| Feature | Old API | Builder API |
|
|
417
|
+
|---------|---------|-------------|
|
|
418
|
+
| Lines of code | 15-20 | **1-5** ✅ |
|
|
419
|
+
| Fallback support | Manual | **Built-in** ✅ |
|
|
420
|
+
| Loading dialog | Separate method | **.withLoadingDialog()** ✅ |
|
|
421
|
+
| Debug mode | N/A | **.debug()** ✅ |
|
|
422
|
+
| Count limiting | Manual tracking | **.maxShows()** ✅ |
|
|
423
|
+
| Callbacks | Nested | **Fluent** ✅ |
|
|
424
|
+
| Type safety | Weak | **Strong** ✅ |
|
|
425
|
+
| Extension functions | No | **Yes** ✅ |
|
|
426
|
+
|
|
427
|
+
---
|
|
428
|
+
|
|
429
|
+
## 🎓 Advanced Patterns
|
|
430
|
+
|
|
431
|
+
### Pattern 1: Context-Aware Ads
|
|
432
|
+
```kotlin
|
|
433
|
+
fun showContextualAd(activity: Activity, context: String) {
|
|
434
|
+
val adUnit = when (context) {
|
|
435
|
+
"game_over" -> "ca-app-pub-xxx/game-over"
|
|
436
|
+
"level_complete" -> "ca-app-pub-xxx/level-complete"
|
|
437
|
+
else -> "ca-app-pub-xxx/default"
|
|
438
|
+
}
|
|
439
|
+
|
|
440
|
+
InterstitialAdBuilder.with(activity)
|
|
441
|
+
.adUnit(adUnit)
|
|
442
|
+
.show { activity.finish() }
|
|
443
|
+
}
|
|
444
|
+
```
|
|
445
|
+
|
|
446
|
+
### Pattern 2: Retry with Different Unit
|
|
447
|
+
```kotlin
|
|
448
|
+
var retryCount = 0
|
|
449
|
+
fun showAdWithRetry() {
|
|
450
|
+
val units = listOf("primary", "backup-1", "backup-2")
|
|
451
|
+
|
|
452
|
+
InterstitialAdBuilder.with(this)
|
|
453
|
+
.adUnit(units[retryCount])
|
|
454
|
+
.onFailed {
|
|
455
|
+
if (retryCount < units.size - 1) {
|
|
456
|
+
retryCount++
|
|
457
|
+
showAdWithRetry() // Retry with next unit
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
.show { next() }
|
|
461
|
+
}
|
|
462
|
+
```
|
|
463
|
+
|
|
464
|
+
### Pattern 3: A/B Testing
|
|
465
|
+
```kotlin
|
|
466
|
+
fun showAdWithABTest() {
|
|
467
|
+
val variant = if (Random.nextBoolean()) "variant-a" else "variant-b"
|
|
468
|
+
|
|
469
|
+
InterstitialAdBuilder.with(this)
|
|
470
|
+
.adUnit("ca-app-pub-xxx/$variant")
|
|
471
|
+
.onAdShown {
|
|
472
|
+
analytics.log("ab_test_shown", "variant" to variant)
|
|
473
|
+
}
|
|
474
|
+
.show { next() }
|
|
475
|
+
}
|
|
476
|
+
```
|
|
477
|
+
|
|
478
|
+
---
|
|
479
|
+
|
|
480
|
+
## 🐛 Troubleshooting
|
|
481
|
+
|
|
482
|
+
### Ad Not Showing?
|
|
483
|
+
```kotlin
|
|
484
|
+
// Enable debug mode to see logs
|
|
485
|
+
InterstitialAdBuilder.with(this)
|
|
486
|
+
.adUnit("your-ad-unit")
|
|
487
|
+
.debug() // ← Add this
|
|
488
|
+
.show { next() }
|
|
489
|
+
```
|
|
490
|
+
|
|
491
|
+
### Want Loading Indicator?
|
|
492
|
+
```kotlin
|
|
493
|
+
InterstitialAdBuilder.with(this)
|
|
494
|
+
.adUnit("your-ad-unit")
|
|
495
|
+
.withLoadingDialog() // ← Shows "Please wait..."
|
|
496
|
+
.show { next() }
|
|
497
|
+
```
|
|
498
|
+
|
|
499
|
+
### Need Multiple Attempts?
|
|
500
|
+
```kotlin
|
|
501
|
+
InterstitialAdBuilder.with(this)
|
|
502
|
+
.adUnit("primary")
|
|
503
|
+
.fallback("backup-1") // ← Try this if primary fails
|
|
504
|
+
.fallback("backup-2") // ← Try this if backup-1 fails
|
|
505
|
+
.show { next() }
|
|
506
|
+
```
|
|
507
|
+
|
|
508
|
+
---
|
|
509
|
+
|
|
510
|
+
## 📝 Summary
|
|
511
|
+
|
|
512
|
+
The `InterstitialAdBuilder` makes showing ads:
|
|
513
|
+
- ✅ **Simpler**: 1-3 lines vs 15-20
|
|
514
|
+
- ✅ **Safer**: Type-safe, required validation
|
|
515
|
+
- ✅ **Smarter**: Built-in fallbacks & retry
|
|
516
|
+
- ✅ **Better**: Debug mode, callbacks, customization
|
|
517
|
+
|
|
518
|
+
**Start using it today for cleaner, more maintainable ad code!** 🚀
|