מודעות מותאמות מוצגות למשתמשים באמצעות רכיבי ממשק משתמש מותאמים
View
ב-Android או
UIView
ב-
iOS.
במדריך הזה מוסבר איך לטעון, להציג ולהתאים אישית מודעות מותאמות באמצעות בקוד ספציפי לפלטפורמה.
דרישות מוקדמות
- מבצעים את ההוראות במדריך לתחילת העבודה.
- מומלץ לקרוא על האפשרויות של מודעות מותאמות.
ביצוע בדיקות באמצעות מודעות בדיקה תמיד
כשיוצרים ובודקים אפליקציות, חשוב להשתמש במודעות בדיקה במקום במודעות בדיקה של מודעות בשידור חי. הדרך הקלה ביותר לטעון מודעות בדיקה היא להשתמש מזהה יחידת מודעות לבדיקה של מודעות מותאמות:
Android
ca-app-pub-3940256099942544/2247696110
iOS
ca-app-pub-3940256099942544/3986624511
יחידות המודעות לבדיקה מוגדרות כך שיחזירו מודעות בדיקה לכל בקשה, לכן שאפשר להשתמש בהם באפליקציות משלכם במהלך התכנות, הבדיקה ניפוי באגים – רק ודאו שמחליפים אותם במזהים של יחידות מודעות משלכם מפרסמים את האפליקציה שלך.
הגדרות ספציפיות לפלטפורמה
כדי ליצור מודעות מותאמות, צריך לכתוב קוד ספציפי לפלטפורמה ל-iOS ו-Android, ולאחר מכן משנים את ההטמעה של טבלת ה-Dart כדי את היתרונות של שינויי קוד ה-Native שביצעתם.
Android
ייבוא הפלאגין
כדי להטמיע את הפלאגין של Google Mobile Ads ב-Android, נדרשת מחלקה
להטמיע את
NativeAdFactory
API. כדי להפנות ל-API הזה מפרויקט Android שלך, צריך להוסיף את
השורות הבאות אל settings.gradle:
def flutterProjectRoot = rootProject.projectDir.parentFile.toPath()
def plugins = new Properties()
def pluginsFile = new File(flutterProjectRoot.toFile(), '.flutter-plugins')
if (pluginsFile.exists()) {
pluginsFile.withInputStream { stream -> plugins.load(stream) }
}
plugins.each { name, path ->
def pluginDirectory = flutterProjectRoot.resolve(path).resolve('android').toFile()
include ":$name"
project(":$name").projectDir = pluginDirectory
}
הטמעת מודעות מותאמות
בשלב הבא, יוצרים מחלקה שמממשת את NativeAdFactory
ומחליפת את ברירת המחדל
באמצעות ה-method createNativeAd()
.
package io.flutter.plugins.googlemobileadsexample;
import android.graphics.Color;
import android.view.LayoutInflater;
import android.widget.TextView;
import com.google.android.gms.ads.nativead.NativeAd;
import com.google.android.gms.ads.nativead.NativeAdView;
import io.flutter.plugins.googlemobileads.GoogleMobileAdsPlugin.NativeAdFactory;
import java.util.Map;
/**
* my_native_ad.xml can be found at
* github.com/googleads/googleads-mobile-flutter/blob/main/packages/google_mobile_ads/
* example/android/app/src/main/res/layout/my_native_ad.xml
*/
class NativeAdFactoryExample implements NativeAdFactory {
private final LayoutInflater layoutInflater;
NativeAdFactoryExample(LayoutInflater layoutInflater) {
this.layoutInflater = layoutInflater;
}
@Override
public NativeAdView createNativeAd(
NativeAd nativeAd, Map<String, Object> customOptions) {
final NativeAdView adView =
(NativeAdView) layoutInflater.inflate(R.layout.my_native_ad, null);
// Set the media view.
adView.setMediaView((MediaView) adView.findViewById(R.id.ad_media));
// Set other ad assets.
adView.setHeadlineView(adView.findViewById(R.id.ad_headline));
adView.setBodyView(adView.findViewById(R.id.ad_body));
adView.setCallToActionView(adView.findViewById(R.id.ad_call_to_action));
adView.setIconView(adView.findViewById(R.id.ad_app_icon));
adView.setPriceView(adView.findViewById(R.id.ad_price));
adView.setStarRatingView(adView.findViewById(R.id.ad_stars));
adView.setStoreView(adView.findViewById(R.id.ad_store));
adView.setAdvertiserView(adView.findViewById(R.id.ad_advertiser));
// The headline and mediaContent are guaranteed to be in every NativeAd.
((TextView) adView.getHeadlineView()).setText(nativeAd.getHeadline());
adView.getMediaView().setMediaContent(nativeAd.getMediaContent());
// These assets aren't guaranteed to be in every NativeAd, so it's important to
// check before trying to display them.
if (nativeAd.getBody() == null) {
adView.getBodyView().setVisibility(View.INVISIBLE);
} else {
adView.getBodyView().setVisibility(View.VISIBLE);
((TextView) adView.getBodyView()).setText(nativeAd.getBody());
}
if (nativeAd.getCallToAction() == null) {
adView.getCallToActionView().setVisibility(View.INVISIBLE);
} else {
adView.getCallToActionView().setVisibility(View.VISIBLE);
((Button) adView.getCallToActionView()).setText(nativeAd.getCallToAction());
}
if (nativeAd.getIcon() == null) {
adView.getIconView().setVisibility(View.GONE);
} else {
((ImageView) adView.getIconView()).setImageDrawable(nativeAd.getIcon().getDrawable());
adView.getIconView().setVisibility(View.VISIBLE);
}
if (nativeAd.getPrice() == null) {
adView.getPriceView().setVisibility(View.INVISIBLE);
} else {
adView.getPriceView().setVisibility(View.VISIBLE);
((TextView) adView.getPriceView()).setText(nativeAd.getPrice());
}
if (nativeAd.getStore() == null) {
adView.getStoreView().setVisibility(View.INVISIBLE);
} else {
adView.getStoreView().setVisibility(View.VISIBLE);
((TextView) adView.getStoreView()).setText(nativeAd.getStore());
}
if (nativeAd.getStarRating() == null) {
adView.getStarRatingView().setVisibility(View.INVISIBLE);
} else {
((RatingBar) adView.getStarRatingView()).setRating(nativeAd.getStarRating()
.floatValue());
adView.getStarRatingView().setVisibility(View.VISIBLE);
}
if (nativeAd.getAdvertiser() == null) {
adView.getAdvertiserView().setVisibility(View.INVISIBLE);
} else {
adView.getAdvertiserView().setVisibility(View.VISIBLE);
((TextView) adView.getAdvertiserView()).setText(nativeAd.getAdvertiser());
}
// This method tells the Google Mobile Ads SDK that you have finished populating your
// native ad view with this native ad.
adView.setNativeAd(nativeAd);
return adView;
}
}
דוגמה להגדרת הפריסה של NativeAdView
זמינה בכתובת my_native_ad.xml.
רישום NativeAdManufacturer
על כל הטמעה של NativeAdFactory
צריך להירשם באמצעות
factoryId
, מזהה String
ייחודי, כשמבצעים שיחה
MainActivity.configureFlutterEngine(FlutterEngine)
factoryId
יהיה
להשתמש בו מאוחר יותר במהלך יצירת מודעה מותאמת מקוד של Drt.
אפשר להטמיע NativeAdFactory
ולרשום אותו לכל מודעה מותאמת ייחודית
פריסת מודעה באפליקציה או פריסת מודעה יחידה יכולה לטפל בכל הפריסות.
שימו לב שכאשר יוצרים באמצעות
add-to-app,
צריך לבטל את ההרשמה של NativeAdFactory
גם ב:
cleanUpFlutterEngine(engine)
אחרי יצירת NativeAdFactoryExample
, צריך להגדיר את MainActivity
בתור
ככה:
package my.app.path;
import io.flutter.embedding.android.FlutterActivity;
import io.flutter.embedding.engine.FlutterEngine;
import io.flutter.plugins.googlemobileads.GoogleMobileAdsPlugin;
public class MainActivity extends FlutterActivity {
@Override
public void configureFlutterEngine(FlutterEngine flutterEngine) {
flutterEngine.getPlugins().add(new GoogleMobileAdsPlugin());
super.configureFlutterEngine(flutterEngine);
GoogleMobileAdsPlugin.registerNativeAdFactory(flutterEngine,
"adFactoryExample", NativeAdFactoryExample());
}
@Override
public void cleanUpFlutterEngine(FlutterEngine flutterEngine) {
GoogleMobileAdsPlugin.unregisterNativeAdFactory(flutterEngine, "adFactoryExample");
}
}
iOS
הטמעת מודעות מותאמות
כדי להטמיע את הפלאגין Google Mobile Ads ב-iOS, נדרשת מחלקה
להטמיע את
FLTNativeAdFactory
API. יוצרים מחלקה שמממשת את NativeAdFactory
ומטמיעה את
createNativeAd()
.
#import "FLTGoogleMobileAdsPlugin.h"
/**
* The example NativeAdView.xib can be found at
* github.com/googleads/googleads-mobile-flutter/blob/main/packages/google_mobile_ads/
* example/ios/Runner/NativeAdView.xib
*/
@interface NativeAdFactoryExample : NSObject <FLTNativeAdFactory>
@end
@implementation NativeAdFactoryExample
- (GADNativeAdView *)createNativeAd:(GADNativeAd *)nativeAd
customOptions:(NSDictionary *)customOptions {
// Create and place the ad in the view hierarchy.
GADNativeAdView *adView =
[[NSBundle mainBundle] loadNibNamed:@"NativeAdView" owner:nil options:nil].firstObject;
// Populate the native ad view with the native ad assets.
// The headline is guaranteed to be present in every native ad.
((UILabel *)adView.headlineView).text = nativeAd.headline;
// These assets are not guaranteed to be present. Check that they are before
// showing or hiding them.
((UILabel *)adView.bodyView).text = nativeAd.body;
adView.bodyView.hidden = nativeAd.body ? NO : YES;
[((UIButton *)adView.callToActionView) setTitle:nativeAd.callToAction
forState:UIControlStateNormal];
adView.callToActionView.hidden = nativeAd.callToAction ? NO : YES;
((UIImageView *)adView.iconView).image = nativeAd.icon.image;
adView.iconView.hidden = nativeAd.icon ? NO : YES;
((UILabel *)adView.storeView).text = nativeAd.store;
adView.storeView.hidden = nativeAd.store ? NO : YES;
((UILabel *)adView.priceView).text = nativeAd.price;
adView.priceView.hidden = nativeAd.price ? NO : YES;
((UILabel *)adView.advertiserView).text = nativeAd.advertiser;
adView.advertiserView.hidden = nativeAd.advertiser ? NO : YES;
// In order for the SDK to process touch events properly, user interaction
// should be disabled.
adView.callToActionView.userInteractionEnabled = NO;
// Associate the native ad view with the native ad object. This is
// required to make the ad clickable.
// Note: this should always be done after populating the ad views.
adView.nativeAd = nativeAd;
return adView;
}
@end
דוגמה להגדרת הפריסה של GADNativeAdView
זמינה בכתובת NativeAdView.xib.
רישום NativeAdManufacturer
צריך לרשום כל FLTNativeAdFactory
ב-factoryId
,
מזהה String
, בתיקייה registerNativeAdFactory:factoryId:nativeAdFactory:
.
ייעשה שימוש בfactoryId
בשלב מאוחר יותר במהלך יצירת מודעה מותאמת
מ-Dart.
אפשר להטמיע FLTNativeAdFactory
ולרשום אותו לכל ערך ייחודי
אם האפליקציה משתמשת בפריסת מודעות מותאמת, או פריסת מודעה יחידה יכולה לטפל בכל הפריסות.
לאחר יצירת FLTNativeAdFactory
, צריך להגדיר את AppDelegate
בתור
ככה:
#import "FLTGoogleMobileAdsPlugin.h"
#import "NativeAdFactoryExample.h"
@implementation AppDelegate
- (BOOL)application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
[GeneratedPluginRegistrant registerWithRegistry:self];
// Must be added after GeneratedPluginRegistrant registerWithRegistry:self];
// is called.
NativeAdFactoryExample *nativeAdFactory = [[NativeAdFactoryExample alloc] init];
[FLTGoogleMobileAdsPlugin registerNativeAdFactory:self
factoryId:@"adFactoryExample"
nativeAdFactory:nativeAdFactory];
return [super application:application didFinishLaunchingWithOptions:launchOptions];
}
@end
טעינת מודעה
אחרי שמוסיפים את הקוד הספציפי לפלטפורמה, צריך לעבור ל-Dart כדי לטעון מודעות. יצרן
חשוב לוודא שהתעודה המזהה factoryID
תואמת לתעודה המזהה שרשמת קודם.
class NativeExampleState extends State<NativeExample> {
NativeAd? _nativeAd;
bool _nativeAdIsLoaded = false;
// TODO: replace this test ad unit with your own ad unit.
final String _adUnitId = Platform.isAndroid
? 'ca-app-pub-3940256099942544/2247696110'
: 'ca-app-pub-3940256099942544/3986624511';
/// Loads a native ad.
void loadAd() {
_nativeAd = NativeAd(
adUnitId: _adUnitId,
// Factory ID registered by your native ad factory implementation.
factoryId: 'adFactoryExample',
listener: NativeAdListener(
onAdLoaded: (ad) {
print('$NativeAd loaded.');
setState(() {
_nativeAdIsLoaded = true;
});
},
onAdFailedToLoad: (ad, error) {
// Dispose the ad here to free resources.
print('$NativeAd failedToLoad: $error');
ad.dispose();
},
),
request: const AdRequest(),
// Optional: Pass custom options to your native ad factory implementation.
customOptions: {'custom-option-1', 'custom-value-1'}
);
_nativeAd.load();
}
}
אירועים של מודעות מותאמות
כדי לקבל התראות על אירועים שקשורים לאינטראקציות עם המודעות המותאמות, צריך להשתמש ב
listener
מאפיין של המודעה. לאחר מכן, מטמיעים
NativeAdListener
כדי לקבל קריאות חוזרות (callback) מאירועי מודעות.
class NativeExampleState extends State<NativeExample> {
NativeAd? _nativeAd;
bool _nativeAdIsLoaded = false;
// TODO: replace this test ad unit with your own ad unit.
final String _adUnitId = Platform.isAndroid
? 'ca-app-pub-3940256099942544/2247696110'
: 'ca-app-pub-3940256099942544/3986624511';
/// Loads a native ad.
void loadAd() {
_nativeAd = NativeAd(
adUnitId: _adUnitId,
// Factory ID registered by your native ad factory implementation.
factoryId: 'adFactoryExample',
listener: NativeAdListener(
onAdLoaded: (ad) {
print('$NativeAd loaded.');
setState(() {
_nativeAdIsLoaded = true;
});
},
onAdFailedToLoad: (ad, error) {
// Dispose the ad here to free resources.
print('$NativeAd failedToLoad: $error');
ad.dispose();
},
// Called when a click is recorded for a NativeAd.
onAdClicked: (ad) {},
// Called when an impression occurs on the ad.
onAdImpression: (ad) {},
// Called when an ad removes an overlay that covers the screen.
onAdClosed: (ad) {},
// Called when an ad opens an overlay that covers the screen.
onAdOpened: (ad) {},
// For iOS only. Called before dismissing a full screen view
onAdWillDismissScreen: (ad) {},
// Called when an ad receives revenue value.
onPaidEvent: (ad, valueMicros, precision, currencyCode) {},
),
request: const AdRequest(),
// Optional: Pass custom options to your native ad factory implementation.
customOptions: {'custom-option-1', 'custom-value-1'}
);
_nativeAd.load();
}
}
מודעה ברשת המדיה
כדי להציג NativeAd
כווידג'ט, צריך ליצור מופע של
AdWidget
עם מודעה נתמכת לאחר חיוג אל load()
. אפשר ליצור את הווידג'ט לפני
קוראים לפונקציה load()
, אבל צריך לקרוא ל-load()
לפני שמוסיפים את המספר לווידג'ט
עץ.
האפליקציה AdWidget
יורשת מהכיתה Widget
של Flutter ואפשר להשתמש בה כמו כל משתמש אחר
לווידג'ט הזה. ב-iOS, צריך למקם את הווידג'ט בקונטיינר שצוין בו
רוחב וגובה. אחרת, ייתכן שהמודעה לא תוצג.
final Container adContainer = Container(
alignment: Alignment.center,
child: AdWidget adWidget = AdWidget(ad: _nativeAd!),
width: WIDTH,
height: HEIGHT,
);
מחיקת מודעה
א'
NativeAd
כאשר אין יותר צורך בגישה אליו. השיטה המומלצת
מתי לקרוא ל-dispose()
אחרי הערך AdWidget
שמשויך למודעה המותאמת
מוסר מעץ הווידג'ט וב-AdListener.onAdFailedToLoad()
קריאה חוזרת.
השלבים הבאים
- מידע נוסף על מודעות מותאמות זמין במודעות המותאמות שלנו את ה-Playbook.
- אפשר לעיין במדיניות בנושא מודעות מותאמות הנחיות.
- ריכזנו בשבילכם כמה סיפורי הצלחה של לקוחות: מקרה לדוגמה 1, מקרה לדוגמה 2.