「SDK 8 Mopub Mediation Native」修訂間的差異
跳至導覽
跳至搜尋
imported>Wikiuser (新頁面: 官方教學:[https://developers.mopub.com/networks/integrate/build-adapters-ios/#quick-start-for-native-ads 連結]<br> NativeAd 需要建立4個客製化class來串接廣告,其...) |
imported>Wikiuser |
||
行 6: | 行 6: | ||
== TAMediaCustomNativeAdEventAdapter(必要) == | == TAMediaCustomNativeAdEventAdapter(必要) == | ||
此 class 是作為 TADNativeAd 與 MPNativeAd 的橋樑,將 TADNativeAd 轉換為 MPNativeAd 所需要的 Dictionary <br> | 此 class 是作為 TADNativeAd 與 MPNativeAd 的橋樑,將 TADNativeAd 轉換為 MPNativeAd 所需要的 Dictionary <br> | ||
#建立一class實做 MPNativeAdAdapter protocol,protocol 有兩必須實作 property:properties 及 defaultActionURL<br> | |||
#建立初始化方法,將TADNativeAd 及 TADNativeAdView 作為參數帶入,將由 TADNativeAd 拿到的 TADNativeAdContent 與 MPNativeAdConstants.h 提供的 key 值建立相對應的 dictionary 後賦予給 proerties <br> | |||
#defaultActionURL 則回傳 nil,點擊的部分將交由 TADNativeAdView 處理<br> | |||
#實作<code>displayContentForURL:rootViewController:completion:</code>當 user 點擊時觸發<br> | |||
參考以下代碼<br> | 參考以下代碼<br> | ||
<source> | |||
#import <Foundation/Foundation.h> | |||
#import <MoPub/MoPub.h> | |||
#import <TAMediaAdsFramework/TAMediaAdsFramework.h> | |||
@interface TAMediaCustomNativeAdEventAdapter : NSObject <MPNativeAdAdapter> | |||
- (instancetype)initTADNativeAd:(TADNativeAd *)nativeAd withNativeView: (TADNativeAdView *)nativeAdView; | |||
@property (nonatomic, readonly) NSDictionary *properties; | |||
@property (nonatomic, readonly) NSURL *defaultActionURL; | |||
@property (nonatomic,strong) TADNativeAdView *nativeAdView; | |||
@property (nonatomic, weak) id<MPNativeAdAdapterDelegate> delegate; | |||
@end | |||
</source> | |||
<source> | |||
#import "TAMediaCustomNativeAdEventAdapter.h" | |||
#import <MoPub/MoPub.h> | |||
@interface TAMediaCustomNativeAdEventAdapter () <TADNativeAdDelegate> | |||
@property (nonatomic,strong) TADNativeAd *nativeAd; | |||
@end | |||
@implementation TAMediaCustomNativeAdEventAdapter | |||
- (instancetype)initTADNativeAd:(TADNativeAd *)nativeAd withNativeView: (TADNativeAdView *)nativeAdView { | |||
self = [super init]; | self = [super init]; | ||
TADNativeAdContent *adContent = nativeAd.adContent; | |||
nativeAd.delegate = self; | nativeAd.delegate = self; | ||
self.nativeAd = nativeAd; | self.nativeAd = nativeAd; | ||
self = | self.nativeAdView = nativeAdView; | ||
_properties = @{kAdTitleKey: adContent.longSubject, | |||
kAdTextKey: adContent.body, | |||
kAdCTATextKey: adContent.callToAction, | |||
kAdIconImageKey: adContent.iconSquare.image, | |||
kAdMainMediaViewKey: nativeAdView.mediaView}; | |||
return self; | return self; | ||
} | |||
#pragma mark - MPNativeAdAdapter | |||
- (BOOL)enableThirdPartyClickTracking { | |||
return YES; | |||
} | |||
- (UIView *)mainMediaView { | |||
return self.nativeAdView.mediaView; | |||
} | |||
- (NSURL *)defaultActionURL { | |||
return nil; | |||
} | |||
#pragma mark - TADNativeAdDelegate | |||
- (void)nativeAdDidClick:(TADNativeAd *)ad { | |||
[self.delegate nativeAdDidClick:self]; | |||
MPLogAdEvent([MPLogEvent adTappedForAdapter:NSStringFromClass(self.class)], nil); | |||
[self.delegate nativeAdWillPresentModalForAdapter:self]; | |||
} | |||
- (void)nativeAdDidImpression:(TADNativeAd *)ad { | |||
[self.delegate nativeAdWillLogImpression:self]; | |||
MPLogAdEvent([MPLogEvent adShowSuccessForAdapter:NSStringFromClass(self.class)], nil); | |||
MPLogAdEvent([MPLogEvent adDidAppearForAdapter:NSStringFromClass(self.class)], nil); | |||
} | |||
- (void)adViewWillLeaveApplication:(TADNativeAd *)adView { | |||
if ([self.delegate respondsToSelector:@selector(nativeAdWillLeaveApplicationFromAdapter:)]) { | |||
[self.delegate nativeAdWillLeaveApplicationFromAdapter:self]; | |||
} | } | ||
MPLogAdEvent([MPLogEvent adWillLeaveApplicationForAdapter:NSStringFromClass(self.class)], nil); | |||
} | |||
@end | |||
</source> | |||
== TAMediaCustomNativeAdRenderer == | == TAMediaCustomNativeAdRenderer(必要) == | ||
此 class 需實做 MPNativeAdRenderer protocol,用於設置客製化事件處理的 class (TAMediaCustomNativeAdEvent) 以及將由 adapter 取得的 Dictionary 呈現到所需的 adView 內並回傳<br> | 此 class 需實做 MPNativeAdRenderer protocol,用於設置客製化事件處理的 class (TAMediaCustomNativeAdEvent) 以及將由 adapter 取得的 Dictionary 呈現到所需的 adView 內並回傳<br> | ||
#實作<code>+ (MPNativeAdRendererConfiguration *)rendererConfigurationWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings</code>建立 MPNativeAdRendererConfiguration物件<br> | |||
#設置 rendering class 為本身class<br> | |||
#設置 rendererSettings 為參數傳入 的rendererSettings<br> | |||
#設置 supportedCustomEvents 為 TAMediaCustomNativeAdEvent class<br> | |||
#實作<code>initWithRendererSettings:</code>設置物件viewSizeHandler,以及任何客製化設定<br> | |||
#實作<code>retrieveViewWithAdapter:</code>回傳要來呈顯在畫面上的 View<br> | |||
參考以下代碼<br> | 參考以下代碼<br> | ||
<source> | |||
#import <Foundation/Foundation.h> | |||
#import <MoPub/MoPub.h> | |||
@interface TAMediaCustomNativeAdRenderer : NSObject <MPNativeAdRenderer> | |||
@property (nonatomic, readonly) MPNativeViewSizeHandler viewSizeHandler; | |||
@end | |||
</source> | |||
<source> | |||
#import "TAMediaCustomNativeAdRenderer.h" | |||
#import "TAMediaCustomNativeAdEventAdapter.h" | |||
#import <MoPub/MoPub.h> | |||
#import "MPNativeAdView.h" | |||
@interface TAMediaCustomNativeAdRenderer() | |||
@property (nonatomic,strong) id<MPNativeAdRendererSettings>setting; | |||
@property (nonatomic,strong) MPNativeAdRendererImageHandler *rendererImageHandler; | |||
@property(nonatomic, strong) Class renderingViewClass; | |||
@end | |||
@implementation TAMediaCustomNativeAdRenderer | |||
+ (MPNativeAdRendererConfiguration *)rendererConfigurationWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings { | |||
MPNativeAdRendererConfiguration *config = [[MPNativeAdRendererConfiguration alloc] init]; | |||
config.rendererSettings = rendererSettings; | |||
config.supportedCustomEvents = @[@"TAMediaCustomNativeAdEvent"];//設置客製化事件處理的class | |||
config.rendererClass = [self class]; | |||
return config; | |||
} | |||
- (instancetype)initWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings { | |||
self = [super init]; | |||
MPStaticNativeAdRendererSettings *settings = | |||
(MPStaticNativeAdRendererSettings *)rendererSettings; | |||
_viewSizeHandler = [rendererSettings.viewSizeHandler copy]; | |||
self.setting = rendererSettings; | |||
_renderingViewClass = settings.renderingViewClass; | |||
return self; | |||
} | |||
- (UIView *)retrieveViewWithAdapter:(id<MPNativeAdAdapter>)adapter error:(NSError **)error { | |||
MPLogAdEvent([MPLogEvent adShowAttemptForAdapter:NSStringFromClass(self.class)], nil); | |||
MPLogAdEvent([MPLogEvent adWillAppearForAdapter:NSStringFromClass(self.class)], nil); | |||
UIView<MPNativeAdRendering> *mpNativeAdView = [self.renderingViewClass new]; | |||
mpNativeAdView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; | |||
TAMediaCustomNativeAdEventAdapter *tadAdpater = (TAMediaCustomNativeAdEventAdapter *)adapter; | |||
TADNativeAdView *tadNativeAdView = tadAdpater.nativeAdView; | |||
tadNativeAdView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; | |||
[tadNativeAdView addSubview:mpNativeAdView]; | |||
[self fillSuperview:mpNativeAdView]; | |||
if([mpNativeAdView respondsToSelector:@selector(nativeTitleTextLabel)]) { | |||
[mpNativeAdView.nativeTitleTextLabel addSubview:tadNativeAdView.longSubjectLabel]; | |||
mpNativeAdView.nativeTitleTextLabel.text = adapter.properties[kAdTitleKey]; | |||
mpNativeAdView.nativeTitleTextLabel.userInteractionEnabled = YES; | |||
tadNativeAdView.longSubjectLabel.userInteractionEnabled = YES; | |||
[self fillSuperview:tadNativeAdView.longSubjectLabel]; | |||
} | |||
if([mpNativeAdView respondsToSelector:@selector(nativeMainTextLabel)]) { | |||
[mpNativeAdView.nativeMainTextLabel addSubview:tadNativeAdView.bodyLabel]; | |||
mpNativeAdView.nativeMainTextLabel.text = adapter.properties[kAdTextKey]; | |||
mpNativeAdView.nativeMainTextLabel.userInteractionEnabled = YES; | |||
tadNativeAdView.bodyLabel.userInteractionEnabled = YES; | |||
[self fillSuperview:tadNativeAdView.bodyLabel]; | |||
} | |||
if([mpNativeAdView respondsToSelector:@selector(nativeCallToActionTextLabel)] && mpNativeAdView.nativeCallToActionTextLabel) { | |||
[mpNativeAdView.nativeCallToActionTextLabel addSubview:tadNativeAdView.callToActionView]; | |||
mpNativeAdView.nativeCallToActionTextLabel.text = adapter.properties[kAdCTATextKey]; | |||
mpNativeAdView.nativeCallToActionTextLabel.userInteractionEnabled = YES; | |||
tadNativeAdView.callToActionView.userInteractionEnabled = YES; | |||
[self fillSuperview:tadNativeAdView.callToActionView]; | |||
} | |||
if([mpNativeAdView respondsToSelector:@selector(nativeIconImageView)]) { | |||
[mpNativeAdView.nativeIconImageView addSubview:tadNativeAdView.squareImgeView]; | |||
mpNativeAdView.nativeIconImageView.image = adapter.properties[kAdIconImageKey]; | |||
mpNativeAdView.nativeIconImageView.userInteractionEnabled = YES; | |||
tadNativeAdView.squareImgeView.userInteractionEnabled = YES; | |||
[self fillSuperview:tadNativeAdView.squareImgeView]; | |||
} | |||
if([mpNativeAdView respondsToSelector:@selector((nativeMainImageView))]) { | |||
tadNativeAdView.mediaView.frame = mpNativeAdView.nativeMainImageView.bounds; | |||
[mpNativeAdView.nativeMainImageView addSubview:tadNativeAdView.mediaView]; | |||
mpNativeAdView.nativeMainImageView.userInteractionEnabled = YES; | |||
[self fillSuperview:tadNativeAdView.mediaView]; | |||
} | |||
MPLogAdEvent([MPLogEvent adShowAttemptForAdapter:NSStringFromClass(self.class)], nil); | |||
MPLogAdEvent([MPLogEvent adWillAppearForAdapter:NSStringFromClass(self.class)], nil); | |||
return tadNativeAdView; | |||
} | |||
- (void)fillSuperview:(UIView *)view { | |||
view.frame = view.superview.bounds; | |||
} | |||
@end | |||
</source> | |||
== TAMediaCustomNativeAdEvent(必要) == | == TAMediaCustomNativeAdEvent(必要) == | ||
此 class 需繼承 MPNativeCustomEvent,用來取得 TAmedia native ad 提供給 MoPub<br> | 此 class 需繼承 MPNativeCustomEvent,用來取得 TAmedia native ad 提供給 MoPub<br> | ||
#建立 class 繼承 MPNativeCustomEvent<br> | |||
#複寫<code> - (void)requestAdWithCustomEventInfo:(NSDictionary *)info</code>在此用 TADNativeAd 去取得廣告<br> | |||
#取得廣告後用取得的 Dictionary 建立 TAMediaCustomNativeAdEventAdapter 後再用 adapter 建立MPNativeAd<br> | |||
#呈現廣告前先呼叫父類別<code>precacheImagesWithURLs:completionBlock:<code/>取得image後,再呼叫<code>customNativeEvent:didLoadAd:</code><br> | |||
<source> | |||
#import <MoPub/MoPub.h> | |||
#import <TAMediaAdsFramework/TAMediaAdsFramework.h> | |||
@interface TAMediaCustomNativeAdEvent : MPNativeCustomEvent <TADNativeAdDelegate> | |||
@property (nonatomic,strong) TADNativeAd *nativeAd; | |||
@end | |||
</source> | |||
TADRequest *request = [TADRequest request]; | <source> | ||
#import "TAMediaCustomNativeAdEvent.h" | |||
#import "TAMediaCustomNativeAdEventAdapter.h" | |||
#import <MoPub/MoPub.h> | |||
@interface TAMediaCustomNativeAdEvent() | |||
@property (nonatomic,strong) NSString *adUnitId; | |||
@end | |||
@implementation TAMediaCustomNativeAdEvent | |||
- (void)requestAdWithCustomEventInfo:(NSDictionary *)info adMarkup:(NSString *)adMarkup { | |||
self.adUnitId = info[@"NativeListId"]; | |||
if (self.adUnitId == nil) { | |||
MPLogAdEvent([MPLogEvent adLoadFailedForAdapter:NSStringFromClass(self.class) | |||
error:MPNativeAdNSErrorForInvalidAdServerResponse(@"Ad unit ID cannot be nil.")], self.adUnitId); | |||
[self.delegate nativeCustomEvent:self | |||
didFailToLoadAdWithError:MPNativeAdNSErrorForInvalidAdServerResponse( | |||
@"Ad unit ID cannot be nil.")]; | |||
return; | |||
} | |||
TADRequest *request = [TADRequest request]; | |||
request.testing = NO; | |||
// Type: TADGender | // Type: TADGender | ||
request.gender = kTADGenderUnknown; | |||
// NAD 物件初始化, 帶入自訂的origin | |||
if (!self.nativeAd) { | |||
self.nativeAd = [[TADNativeAd alloc] initWithAdUnitId: self.adUnitId]; | |||
} | |||
// 必須要設定delegate | |||
self.nativeAd.delegate = self; | |||
MPLogAdEvent([MPLogEvent adLoadAttemptForAdapter:NSStringFromClass(self.class) dspCreativeId:nil dspName:nil], self.adUnitId); | |||
// 載入廣告 | |||
[self.nativeAd loadRequest:request]; | |||
} | |||
- (void)nativeAdDidReceiveAd:(TADNativeAd *)ad { | |||
MPLogAdEvent([MPLogEvent adLoadSuccessForAdapter:NSStringFromClass(self.class)], self.adUnitId); | |||
TADNativeAdView *nativeView = [TADNativeAdView new]; | |||
UILabel *titleLabel = [[UILabel alloc] initWithFrame:CGRectZero]; | |||
UILabel *subTitleLabel = [[UILabel alloc] initWithFrame:CGRectZero]; | |||
UILabel *bodyLabel = [[UILabel alloc] initWithFrame:CGRectZero]; | |||
UILabel *callToActionView = [[UILabel alloc] initWithFrame: CGRectZero]; | |||
UIImageView *smallImageView = [[UIImageView alloc] initWithFrame:CGRectZero]; | |||
UIImageView *bigImageView = [[UIImageView alloc] initWithFrame:CGRectZero]; | |||
TADNativeMediaView *mediaView = [[TADNativeMediaView alloc] initWithFrame:CGRectZero]; | |||
mediaView.mediaContent = ad.adContent.mediaContent; | |||
[nativeView addSubview:titleLabel]; | |||
[nativeView addSubview:subTitleLabel]; | |||
[nativeView addSubview:bodyLabel]; | |||
[nativeView addSubview:callToActionView]; | |||
[nativeView addSubview:smallImageView]; | |||
[nativeView addSubview:bigImageView]; | |||
[nativeView addSubview:mediaView]; | |||
nativeView.longSubjectLabel = titleLabel; | |||
nativeView.shortSubjectLabel = subTitleLabel; | |||
nativeView.bodyLabel = bodyLabel; | |||
nativeView.callToActionView = callToActionView; | |||
nativeView.squareImgeView = smallImageView; | |||
nativeView.rectangleImgeView = bigImageView; | |||
nativeView.mediaView = mediaView; | |||
nativeView.nativeAd = ad; | |||
// 表示本次請求收到廣告 | |||
TAMediaCustomNativeAdEventAdapter *adapter = [[TAMediaCustomNativeAdEventAdapter alloc] initTADNativeAd:ad withNativeView:nativeView]; | |||
MPNativeAd *mpNativeAd = [[MPNativeAd alloc] initWithAdAdapter:adapter]; | |||
[self.delegate nativeCustomEvent:self didLoadAd:mpNativeAd]; | |||
} | |||
- (void)nativeAd:(TADNativeAd *)ad didFailToReceiveAdWithError:(TADRequestError *)error { | |||
MPLogAdEvent([MPLogEvent adLoadFailedForAdapter:NSStringFromClass(self.class) error:error], self.adUnitId); | |||
if ([self.delegate respondsToSelector:@selector(nativeCustomEvent:didFailToLoadAdWithError:)]) { | |||
[self.delegate nativeCustomEvent:self didFailToLoadAdWithError:error]; | |||
} | |||
} | |||
- (void)dealloc { | |||
} | |||
@end | |||
</source> | |||
== TAMediaCustomNativeAdEventSetting == | == TAMediaCustomNativeAdEventSetting == |
於 2021年8月23日 (一) 12:13 的修訂
官方教學:連結
NativeAd 需要建立4個客製化class來串接廣告,其中 TAMediaCustomNativeAdEventSetting 為非必要,其他三個都必須加入專案內。
TAMediaCustomNativeAdEventAdapter(必要)
此 class 是作為 TADNativeAd 與 MPNativeAd 的橋樑,將 TADNativeAd 轉換為 MPNativeAd 所需要的 Dictionary
- 建立一class實做 MPNativeAdAdapter protocol,protocol 有兩必須實作 property:properties 及 defaultActionURL
- 建立初始化方法,將TADNativeAd 及 TADNativeAdView 作為參數帶入,將由 TADNativeAd 拿到的 TADNativeAdContent 與 MPNativeAdConstants.h 提供的 key 值建立相對應的 dictionary 後賦予給 proerties
- defaultActionURL 則回傳 nil,點擊的部分將交由 TADNativeAdView 處理
- 實作
displayContentForURL:rootViewController:completion:
當 user 點擊時觸發
參考以下代碼
#import <Foundation/Foundation.h>
#import <MoPub/MoPub.h>
#import <TAMediaAdsFramework/TAMediaAdsFramework.h>
@interface TAMediaCustomNativeAdEventAdapter : NSObject <MPNativeAdAdapter>
- (instancetype)initTADNativeAd:(TADNativeAd *)nativeAd withNativeView: (TADNativeAdView *)nativeAdView;
@property (nonatomic, readonly) NSDictionary *properties;
@property (nonatomic, readonly) NSURL *defaultActionURL;
@property (nonatomic,strong) TADNativeAdView *nativeAdView;
@property (nonatomic, weak) id<MPNativeAdAdapterDelegate> delegate;
@end
#import "TAMediaCustomNativeAdEventAdapter.h"
#import <MoPub/MoPub.h>
@interface TAMediaCustomNativeAdEventAdapter () <TADNativeAdDelegate>
@property (nonatomic,strong) TADNativeAd *nativeAd;
@end
@implementation TAMediaCustomNativeAdEventAdapter
- (instancetype)initTADNativeAd:(TADNativeAd *)nativeAd withNativeView: (TADNativeAdView *)nativeAdView {
self = [super init];
TADNativeAdContent *adContent = nativeAd.adContent;
nativeAd.delegate = self;
self.nativeAd = nativeAd;
self.nativeAdView = nativeAdView;
_properties = @{kAdTitleKey: adContent.longSubject,
kAdTextKey: adContent.body,
kAdCTATextKey: adContent.callToAction,
kAdIconImageKey: adContent.iconSquare.image,
kAdMainMediaViewKey: nativeAdView.mediaView};
return self;
}
#pragma mark - MPNativeAdAdapter
- (BOOL)enableThirdPartyClickTracking {
return YES;
}
- (UIView *)mainMediaView {
return self.nativeAdView.mediaView;
}
- (NSURL *)defaultActionURL {
return nil;
}
#pragma mark - TADNativeAdDelegate
- (void)nativeAdDidClick:(TADNativeAd *)ad {
[self.delegate nativeAdDidClick:self];
MPLogAdEvent([MPLogEvent adTappedForAdapter:NSStringFromClass(self.class)], nil);
[self.delegate nativeAdWillPresentModalForAdapter:self];
}
- (void)nativeAdDidImpression:(TADNativeAd *)ad {
[self.delegate nativeAdWillLogImpression:self];
MPLogAdEvent([MPLogEvent adShowSuccessForAdapter:NSStringFromClass(self.class)], nil);
MPLogAdEvent([MPLogEvent adDidAppearForAdapter:NSStringFromClass(self.class)], nil);
}
- (void)adViewWillLeaveApplication:(TADNativeAd *)adView {
if ([self.delegate respondsToSelector:@selector(nativeAdWillLeaveApplicationFromAdapter:)]) {
[self.delegate nativeAdWillLeaveApplicationFromAdapter:self];
}
MPLogAdEvent([MPLogEvent adWillLeaveApplicationForAdapter:NSStringFromClass(self.class)], nil);
}
@end
TAMediaCustomNativeAdRenderer(必要)
此 class 需實做 MPNativeAdRenderer protocol,用於設置客製化事件處理的 class (TAMediaCustomNativeAdEvent) 以及將由 adapter 取得的 Dictionary 呈現到所需的 adView 內並回傳
- 實作
+ (MPNativeAdRendererConfiguration *)rendererConfigurationWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings
建立 MPNativeAdRendererConfiguration物件 - 設置 rendering class 為本身class
- 設置 rendererSettings 為參數傳入 的rendererSettings
- 設置 supportedCustomEvents 為 TAMediaCustomNativeAdEvent class
- 實作
initWithRendererSettings:
設置物件viewSizeHandler,以及任何客製化設定 - 實作
retrieveViewWithAdapter:
回傳要來呈顯在畫面上的 View
參考以下代碼
#import <Foundation/Foundation.h>
#import <MoPub/MoPub.h>
@interface TAMediaCustomNativeAdRenderer : NSObject <MPNativeAdRenderer>
@property (nonatomic, readonly) MPNativeViewSizeHandler viewSizeHandler;
@end
#import "TAMediaCustomNativeAdRenderer.h"
#import "TAMediaCustomNativeAdEventAdapter.h"
#import <MoPub/MoPub.h>
#import "MPNativeAdView.h"
@interface TAMediaCustomNativeAdRenderer()
@property (nonatomic,strong) id<MPNativeAdRendererSettings>setting;
@property (nonatomic,strong) MPNativeAdRendererImageHandler *rendererImageHandler;
@property(nonatomic, strong) Class renderingViewClass;
@end
@implementation TAMediaCustomNativeAdRenderer
+ (MPNativeAdRendererConfiguration *)rendererConfigurationWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings {
MPNativeAdRendererConfiguration *config = [[MPNativeAdRendererConfiguration alloc] init];
config.rendererSettings = rendererSettings;
config.supportedCustomEvents = @[@"TAMediaCustomNativeAdEvent"];//設置客製化事件處理的class
config.rendererClass = [self class];
return config;
}
- (instancetype)initWithRendererSettings:(id<MPNativeAdRendererSettings>)rendererSettings {
self = [super init];
MPStaticNativeAdRendererSettings *settings =
(MPStaticNativeAdRendererSettings *)rendererSettings;
_viewSizeHandler = [rendererSettings.viewSizeHandler copy];
self.setting = rendererSettings;
_renderingViewClass = settings.renderingViewClass;
return self;
}
- (UIView *)retrieveViewWithAdapter:(id<MPNativeAdAdapter>)adapter error:(NSError **)error {
MPLogAdEvent([MPLogEvent adShowAttemptForAdapter:NSStringFromClass(self.class)], nil);
MPLogAdEvent([MPLogEvent adWillAppearForAdapter:NSStringFromClass(self.class)], nil);
UIView<MPNativeAdRendering> *mpNativeAdView = [self.renderingViewClass new];
mpNativeAdView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth;
TAMediaCustomNativeAdEventAdapter *tadAdpater = (TAMediaCustomNativeAdEventAdapter *)adapter;
TADNativeAdView *tadNativeAdView = tadAdpater.nativeAdView;
tadNativeAdView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth;
[tadNativeAdView addSubview:mpNativeAdView];
[self fillSuperview:mpNativeAdView];
if([mpNativeAdView respondsToSelector:@selector(nativeTitleTextLabel)]) {
[mpNativeAdView.nativeTitleTextLabel addSubview:tadNativeAdView.longSubjectLabel];
mpNativeAdView.nativeTitleTextLabel.text = adapter.properties[kAdTitleKey];
mpNativeAdView.nativeTitleTextLabel.userInteractionEnabled = YES;
tadNativeAdView.longSubjectLabel.userInteractionEnabled = YES;
[self fillSuperview:tadNativeAdView.longSubjectLabel];
}
if([mpNativeAdView respondsToSelector:@selector(nativeMainTextLabel)]) {
[mpNativeAdView.nativeMainTextLabel addSubview:tadNativeAdView.bodyLabel];
mpNativeAdView.nativeMainTextLabel.text = adapter.properties[kAdTextKey];
mpNativeAdView.nativeMainTextLabel.userInteractionEnabled = YES;
tadNativeAdView.bodyLabel.userInteractionEnabled = YES;
[self fillSuperview:tadNativeAdView.bodyLabel];
}
if([mpNativeAdView respondsToSelector:@selector(nativeCallToActionTextLabel)] && mpNativeAdView.nativeCallToActionTextLabel) {
[mpNativeAdView.nativeCallToActionTextLabel addSubview:tadNativeAdView.callToActionView];
mpNativeAdView.nativeCallToActionTextLabel.text = adapter.properties[kAdCTATextKey];
mpNativeAdView.nativeCallToActionTextLabel.userInteractionEnabled = YES;
tadNativeAdView.callToActionView.userInteractionEnabled = YES;
[self fillSuperview:tadNativeAdView.callToActionView];
}
if([mpNativeAdView respondsToSelector:@selector(nativeIconImageView)]) {
[mpNativeAdView.nativeIconImageView addSubview:tadNativeAdView.squareImgeView];
mpNativeAdView.nativeIconImageView.image = adapter.properties[kAdIconImageKey];
mpNativeAdView.nativeIconImageView.userInteractionEnabled = YES;
tadNativeAdView.squareImgeView.userInteractionEnabled = YES;
[self fillSuperview:tadNativeAdView.squareImgeView];
}
if([mpNativeAdView respondsToSelector:@selector((nativeMainImageView))]) {
tadNativeAdView.mediaView.frame = mpNativeAdView.nativeMainImageView.bounds;
[mpNativeAdView.nativeMainImageView addSubview:tadNativeAdView.mediaView];
mpNativeAdView.nativeMainImageView.userInteractionEnabled = YES;
[self fillSuperview:tadNativeAdView.mediaView];
}
MPLogAdEvent([MPLogEvent adShowAttemptForAdapter:NSStringFromClass(self.class)], nil);
MPLogAdEvent([MPLogEvent adWillAppearForAdapter:NSStringFromClass(self.class)], nil);
return tadNativeAdView;
}
- (void)fillSuperview:(UIView *)view {
view.frame = view.superview.bounds;
}
@end
TAMediaCustomNativeAdEvent(必要)
此 class 需繼承 MPNativeCustomEvent,用來取得 TAmedia native ad 提供給 MoPub
- 建立 class 繼承 MPNativeCustomEvent
- 複寫
- (void)requestAdWithCustomEventInfo:(NSDictionary *)info
在此用 TADNativeAd 去取得廣告 - 取得廣告後用取得的 Dictionary 建立 TAMediaCustomNativeAdEventAdapter 後再用 adapter 建立MPNativeAd
- 呈現廣告前先呼叫父類別
precacheImagesWithURLs:completionBlock:
取得image後,再呼叫
customNativeEvent:didLoadAd:
#import <MoPub/MoPub.h>
#import <TAMediaAdsFramework/TAMediaAdsFramework.h>
@interface TAMediaCustomNativeAdEvent : MPNativeCustomEvent <TADNativeAdDelegate>
@property (nonatomic,strong) TADNativeAd *nativeAd;
@end
#import "TAMediaCustomNativeAdEvent.h"
#import "TAMediaCustomNativeAdEventAdapter.h"
#import <MoPub/MoPub.h>
@interface TAMediaCustomNativeAdEvent()
@property (nonatomic,strong) NSString *adUnitId;
@end
@implementation TAMediaCustomNativeAdEvent
- (void)requestAdWithCustomEventInfo:(NSDictionary *)info adMarkup:(NSString *)adMarkup {
self.adUnitId = info[@"NativeListId"];
if (self.adUnitId == nil) {
MPLogAdEvent([MPLogEvent adLoadFailedForAdapter:NSStringFromClass(self.class)
error:MPNativeAdNSErrorForInvalidAdServerResponse(@"Ad unit ID cannot be nil.")], self.adUnitId);
[self.delegate nativeCustomEvent:self
didFailToLoadAdWithError:MPNativeAdNSErrorForInvalidAdServerResponse(
@"Ad unit ID cannot be nil.")];
return;
}
TADRequest *request = [TADRequest request];
request.testing = NO;
// Type: TADGender
request.gender = kTADGenderUnknown;
// NAD 物件初始化, 帶入自訂的origin
if (!self.nativeAd) {
self.nativeAd = [[TADNativeAd alloc] initWithAdUnitId: self.adUnitId];
}
// 必須要設定delegate
self.nativeAd.delegate = self;
MPLogAdEvent([MPLogEvent adLoadAttemptForAdapter:NSStringFromClass(self.class) dspCreativeId:nil dspName:nil], self.adUnitId);
// 載入廣告
[self.nativeAd loadRequest:request];
}
- (void)nativeAdDidReceiveAd:(TADNativeAd *)ad {
MPLogAdEvent([MPLogEvent adLoadSuccessForAdapter:NSStringFromClass(self.class)], self.adUnitId);
TADNativeAdView *nativeView = [TADNativeAdView new];
UILabel *titleLabel = [[UILabel alloc] initWithFrame:CGRectZero];
UILabel *subTitleLabel = [[UILabel alloc] initWithFrame:CGRectZero];
UILabel *bodyLabel = [[UILabel alloc] initWithFrame:CGRectZero];
UILabel *callToActionView = [[UILabel alloc] initWithFrame: CGRectZero];
UIImageView *smallImageView = [[UIImageView alloc] initWithFrame:CGRectZero];
UIImageView *bigImageView = [[UIImageView alloc] initWithFrame:CGRectZero];
TADNativeMediaView *mediaView = [[TADNativeMediaView alloc] initWithFrame:CGRectZero];
mediaView.mediaContent = ad.adContent.mediaContent;
[nativeView addSubview:titleLabel];
[nativeView addSubview:subTitleLabel];
[nativeView addSubview:bodyLabel];
[nativeView addSubview:callToActionView];
[nativeView addSubview:smallImageView];
[nativeView addSubview:bigImageView];
[nativeView addSubview:mediaView];
nativeView.longSubjectLabel = titleLabel;
nativeView.shortSubjectLabel = subTitleLabel;
nativeView.bodyLabel = bodyLabel;
nativeView.callToActionView = callToActionView;
nativeView.squareImgeView = smallImageView;
nativeView.rectangleImgeView = bigImageView;
nativeView.mediaView = mediaView;
nativeView.nativeAd = ad;
// 表示本次請求收到廣告
TAMediaCustomNativeAdEventAdapter *adapter = [[TAMediaCustomNativeAdEventAdapter alloc] initTADNativeAd:ad withNativeView:nativeView];
MPNativeAd *mpNativeAd = [[MPNativeAd alloc] initWithAdAdapter:adapter];
[self.delegate nativeCustomEvent:self didLoadAd:mpNativeAd];
}
- (void)nativeAd:(TADNativeAd *)ad didFailToReceiveAdWithError:(TADRequestError *)error {
MPLogAdEvent([MPLogEvent adLoadFailedForAdapter:NSStringFromClass(self.class) error:error], self.adUnitId);
if ([self.delegate respondsToSelector:@selector(nativeCustomEvent:didFailToLoadAdWithError:)]) {
[self.delegate nativeCustomEvent:self didFailToLoadAdWithError:error];
}
}
- (void)dealloc {
}
@end
TAMediaCustomNativeAdEventSetting
此class需實做MPNativeAdRendererSettings protocol,用來設定 viewSize,與指定需要來呈現廣告的 View,亦可使用 MPNativeAdRendererSettings 取代
// TAMediaCustomNativeAdEventSetting.h
#import <Foundation/Foundation.h>
#import <MoPub/MoPub.h>
@interface TAMediaCustomNativeAdEventSetting : NSObject <MPNativeAdRendererSettings>
@property (nonatomic, assign) Class renderingViewClass;
@property (nonatomic, readwrite, copy) MPNativeViewSizeHandler viewSizeHandler;
@end
// TAMediaCustomNativeAdEventSetting.m
#import "TAMediaCustomNativeAdEventSetting.h"
@implementation TAMediaCustomNativeAdEventSetting
@end