1. 介绍
自渲染广告集成,必看原生广告平台注意项。
自渲染广告在原生广告中是相对比较高级的用法,开发者可获取广告的所有素材内容进行自定义布局的广告渲染。一般开发者会嵌套在产品自身的布局中实现。如以下截图:
| 固定位置展示 | 信息流列表展示 | 
|---|---|
![]()  | 
![]()  | 
2. 集成建议
注意: SDK不会持有广告实例(ATNative)和回调实例(ATNativeNetworkListener),所以需要开发者保证广告结束之前广告实例不会被回收掉,以避免回调丢失的情况
(1) 启动应用通过ATNative.makeAdRequest来执行加载广告。提前进行广告的请求,以便需要触发广告时可以快速展示。
(2) 建议进入可展示广告场景后调用entryAdScenario(placementId,scenarioId)统计当前广告位的缓存状态,具体的统计说明可查看广告场景区分不同业务场景的数据
(3) 禁止在onNativeAdLoadFail回调中执行广告加载的方法,否则会引起很多无用请求且可能会导致应用卡顿。
(4) 在需要展示原生广告的位置通过ATNative.getNativeAd获取广告对象是否为空:
- 为空:重新执行
ATNative.makeAdRequest来加载广告 - 不为空:展示NativeAd的广告对象,这时可直接再执行
ATNative.makeAdRequest来预加载下一次的广告(只要调用ATNative.getNativeAd之后就可以直接预加载下一次广告) 
(5) 建议配置预置策略:提高首次冷启动的广告加载效果,具体说明和接入教程见SDK预置策略使用说明
3. API说明
3.1 加载广告
ATNative: Native广告加载的类
| API | 说明 | 
|---|---|
| ATNative(Context context, String nativeTakuPlacementID, ATNativeNetworkListener listener) | 原生广告初始化方法,其中nativeTakuPlacementID是通过Taku后台创建原生广告位获取的 | 
| onNativeAdLoaded | 广告加载成功 | 
| onNativeAdLoadFail(AdError error) | 广告加载失败,可通过AdError.getFullErrorInfo()获取全部错误信息,请参考 AdError 注意:禁止在此回调中执行广告的加载方法进行重试,否则会引起很多无用请求且可能会导致应用卡顿 | 
| makeAdRequest | 发起Native广告请求 | 
注意事项
华为:华为原生广告展示时可能会自带华为关闭按钮,如果开发者调用了ATNativePrepareInfo#setCloseView()设置关闭按钮,可能会在华为原生广告展示时出现两个关闭按钮。
解决方案: 在原生广告加载前通过setLocalExtra传入HuaweiATConst.CUSTOM_DISLIKE为true,ATAdConst.KEY.AD_CHOICES_PLACEMENT为ATAdConst.AD_CHOICES_PLACEMENT_INVISIBLE,屏蔽华为关闭按钮展示
ATNative atNative;
NativeAd mNativeAd;
int adViewWidth;
int adViewHeight;
public void loadNativeAd() {
  if (atNative == null) {
     //初始化广告加载对象
     atNative = new ATNative(this, nativeTakuPlacementID, new ATNativeNetworkListener() {
                @Override
                public void onNativeAdLoaded() {
                    Log.i(TAG, "onNativeAdLoaded");
                }
                @Override
                public void onNativeAdLoadFail(AdError adError) {
                    //注意:禁止在此回调中执行广告的加载方法进行重试,否则会引起很多无用请求且可能会导致应用卡顿
                    //AdError,请参考 https://newdocs.takuad.com/docs/55cxNt
                    Log.i(TAG, "onNativeAdLoadFail:" + adError.getFullErrorInfo());
                }
            });
   }
  // 解决华为原生广告会同时出现两个关闭按钮,在加载前加上此代码屏蔽华为关闭按钮展示
  // Map localMap = new HashMap<>(); 
  // localMap.put(HuaweiATConst.CUSTOM_DISLIKE, true);
  // localMap.put(ATAdConst.KEY.AD_CHOICES_PLACEMENT, ATAdConst.AD_CHOICES_PLACEMENT_INVISIBLE);
  // atNative.setLocalExtra(localMap)
    //发起广告请求
    atNative.makeAdRequest();
}
3.2 展示广告
NativeAd: 通过ATNative.getNativeAd()获取到的广告对象
注意:建议了解原生广告平台注意项避免出现展示,点击异常
| 方法 | 说明 | 
|---|---|
| isNativeExpress | 是否为模板渲染类型的广告 | 
| renderAdContainer(ATNativeAdView view, View selfRenderView) | 用于广告渲染,其中view必须使用我们提供的ATNativeAdView 注意:调用isNativeExpress()返回false(即自渲染)时,selfRenderView必须传入开发者自定义的View,返回true(模板渲染)时可传null | 
| prepare(ATNativeAdView view, ATNativePrepareInfo nativePrepareInfo) | 用于配置广告点击事件、绑定自渲染时的关闭按钮、控制广告标识的展示位置和大小等,在renderAdContainer方法之后调用(默认全部view可点击,存在广告标识的会有默认展示位置和大小) | 
ATNativeAdView mATNativeAdView; //渲染广告必须创建的容器
View mSelfRenderView; //开发者自定义布局的容器
public void showNativeAd(ViewGroup adContainer, int adViewWidth) {
    /*
     为了统计场景到达率,相关信息可查阅 "https://help.takuad.com/docs/1RWLAv"
     在满足广告触发条件时调用“进入广告场景”方法,比如:
     ** 广告场景是在清理结束后弹出广告,则在清理结束时调用;
     * 1、先调用 "entryAdScenario"
     * 2、在调用 "ATNative#checkAdStatus#isReady" 是否可展示
     * 3、最后调用 "getNativeAd" 展示
     * 4、scenario 传入场景id后台漏斗报表才会到达场景数据(非必须)
     */
    ATNative.entryAdScenario("your Native placementID", "your scenarioID");
    if (atNative == null) {
        return;
    }
    
    if (!atNative.checkAdStatus().isReady()) {
        return;
    }
    if (mATNativeAdView == null) {
        mATNativeAdView = findViewById(R.id.native_ad_view); //可在xml布局定义
    }
    if (mSelfRenderView == null) {
        mSelfRenderView = mATNativeAdView.findViewById(R.id.native_selfrender_view); //可在xml布局定义
    }
    NativeAd nativeAd = atNative.getNativeAd();
    //开发者可以在调用getNativeAd后直接使用ATNative#makeAdRequest发起预加载下一次的广告
    //loadNativeAd();
    if (nativeAd != null) {
        // 销毁上一次展示的广告对象
        if (mNativeAd != null) {
            mNativeAd.destory();
        }
        mNativeAd = nativeAd;
        mNativeAd.setNativeEventListener(new ATNativeEventListener() {
            @Override
            public void onAdImpressed(ATNativeAdView view, ATAdInfo atAdInfo) {
                //ATAdInfo可区分广告平台以及获取广告平台的广告位ID等
                //请参考 https://newdocs.takuad.com/docs/JSLSJN
                Log.i(TAG, "native ad onAdImpressed:\n" + atAdInfo.toString());
            }
            @Override
            public void onAdClicked(ATNativeAdView view, ATAdInfo atAdInfo) {
                Log.i(TAG, "native ad onAdClicked:\n" + atAdInfo.toString());
            }
            @Override
            public void onAdVideoStart(ATNativeAdView view) {
                Log.i(TAG, "native ad onAdVideoStart");
            }
            @Override
            public void onAdVideoEnd(ATNativeAdView view) {
                Log.i(TAG, "native ad onAdVideoEnd");
            }
            @Override
            public void onAdVideoProgress(ATNativeAdView view, int progress) {
                Log.i(TAG, "native ad onAdVideoProgress:" + progress);
            }
        });
        ATNativePrepareInfo nativePrepareInfo;
        if (!mNativeAd.isNativeExpress()) {
            //自渲染
            nativePrepareInfo = new ATNativePrepareInfo();
            bindSelfRenderView(this, mNativeAd.getAdMaterial(), mSelfRenderView,
                    nativePrepareInfo);
            mNativeAd.renderAdContainer(mATNativeAdView, mSelfRenderView);
        } else {
            //模板渲染
            mNativeAd.renderAdContainer(mATNativeAdView, null);
        }
        mNativeAd.prepare(mATNativeAdView, nativePrepareInfo);
    }
}
public static void bindSelfRenderView(Context context, ATNativeMaterial adMaterial,
                                      View selfRenderView,
                                      ATNativePrepareInfo nativePrepareInfo) {
    int padding = dip2px(context, 5);
    selfRenderView.setPadding(padding, padding, padding, padding);
    TextView titleView = (TextView) selfRenderView.findViewById(R.id.native_ad_title);
    TextView descView = (TextView) selfRenderView.findViewById(R.id.native_ad_desc);
    TextView ctaView = (TextView) selfRenderView.findViewById(R.id.native_ad_install_btn);
    TextView adFromView = (TextView) selfRenderView.findViewById(R.id.native_ad_from);
    FrameLayout iconArea = (FrameLayout) selfRenderView.findViewById(R.id.native_ad_image);
    FrameLayout contentArea = (FrameLayout) selfRenderView.findViewById(R.id.native_ad_content_image_area);
    final ATNativeImageView logoView = (ATNativeImageView) selfRenderView.findViewById(R.id.native_ad_logo);
    View closeView = selfRenderView.findViewById(R.id.native_ad_close);
    FrameLayout shakeViewContainer = (FrameLayout) selfRenderView.findViewById(R.id.native_ad_shake_view_container);
    FrameLayout slideViewContainer = (FrameLayout) selfRenderView.findViewById(R.id.native_ad_slide_view_container);
    FrameLayout adLogoContainer = selfRenderView.findViewById(R.id.native_ad_logo_container);
    // bind view
    if (nativePrepareInfo == null) {
        nativePrepareInfo = new ATNativePrepareInfo();
    }
    //click views
    List clickViewList = new ArrayList<>();
    String title = adMaterial.getTitle();
    // title
    if (!TextUtils.isEmpty(title)) {
        titleView.setText(title);
        nativePrepareInfo.setTitleView(titleView);//bind title
        clickViewList.add(titleView);
        titleView.setVisibility(View.VISIBLE);
    } else {
        titleView.setVisibility(View.GONE);
    }
     // desc
    String descriptionText = adMaterial.getDescriptionText();
    if (!TextUtils.isEmpty(descriptionText)) {
        descView.setText(descriptionText);
        nativePrepareInfo.setDescView(descView);//bind desc
        clickViewList.add(descView);
        descView.setVisibility(View.VISIBLE);
    } else {
        descView.setVisibility(View.GONE);
    }
    // icon
    View adIconView = adMaterial.getAdIconView();
    String iconImageUrl = adMaterial.getIconImageUrl();
    iconArea.removeAllViews();
    final ATNativeImageView iconView = new ATNativeImageView(context);
    if (adIconView != null) {
        iconArea.addView(adIconView);
        nativePrepareInfo.setIconView(adIconView);//bind icon
        clickViewList.add(adIconView);
        iconArea.setVisibility(View.VISIBLE);
    } else if (!TextUtils.isEmpty(iconImageUrl)) {
        iconArea.addView(iconView);
        iconView.setImage(iconImageUrl);
        nativePrepareInfo.setIconView(iconView);//bind icon
        clickViewList.add(iconView);
        iconArea.setVisibility(View.VISIBLE);
    } else {
        iconArea.setVisibility(View.INVISIBLE);
    }
    // cta button
    String callToActionText = adMaterial.getCallToActionText();
    if (!TextUtils.isEmpty(callToActionText)) {
        ctaView.setText(callToActionText);
        nativePrepareInfo.setCtaView(ctaView);//bind cta button
        clickViewList.add(ctaView);
        ctaView.setVisibility(View.VISIBLE);
    } else {
        ctaView.setVisibility(View.GONE);
    }
    // media view
    View mediaView = adMaterial.getAdMediaView(contentArea);
    List imageList = adMaterial.getImageUrlList();
    
    //some network support return main image width、height,if not support return -1
    int mainImageHeight = adMaterial.getMainImageHeight();
    int mainImageWidth = adMaterial.getMainImageWidth();
    int realMainImageWidth = context.getResources().getDisplayMetrics().widthPixels - dip2px(
            context, 10);
    int realMainHeight = 0;
    //media view or mainImage layout params
    FrameLayout.LayoutParams mainImageParam = new FrameLayout.LayoutParams(
            FrameLayout.LayoutParams.MATCH_PARENT
            , FrameLayout.LayoutParams.WRAP_CONTENT);
    if (mainImageWidth > 0 && mainImageHeight > 0 && mainImageWidth > mainImageHeight) {
        realMainHeight = realMainImageWidth * mainImageHeight / mainImageWidth;
        mainImageParam.width = realMainImageWidth;
        mainImageParam.height = realMainHeight;
    } else {
        mainImageParam.width = FrameLayout.LayoutParams.MATCH_PARENT;
        //contentArea radio
        mainImageParam.height = realMainImageWidth * 600 / 1024;
    }
    contentArea.removeAllViews();
    if (mediaView != null) {
        if (mediaView.getParent() != null) {
            ((ViewGroup) mediaView.getParent()).removeView(mediaView);
        }
        mainImageParam.gravity = Gravity.CENTER;
        mediaView.setLayoutParams(mainImageParam);
        contentArea.addView(mediaView, mainImageParam);
        contentArea.setVisibility(View.VISIBLE);
    } else if (imageList != null && imageList.size() > 1) {
        MutiImageView mutiImageView = new MutiImageView(context);
        mutiImageView.setImageList(imageList, mainImageWidth, mainImageHeight);
        nativePrepareInfo.setMainImageView(mutiImageView);//bind main image
        contentArea.addView(mutiImageView,
                new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
                        ViewGroup.LayoutParams.WRAP_CONTENT));
        clickViewList.add(mutiImageView);
        contentArea.setVisibility(View.VISIBLE);
    } else if (!TextUtils.isEmpty(adMaterial.getMainImageUrl())) {
        ATNativeImageView imageView = new ATNativeImageView(context);
        imageView.setImage(adMaterial.getMainImageUrl());
        imageView.setLayoutParams(mainImageParam);
        contentArea.addView(imageView, mainImageParam);
        nativePrepareInfo.setMainImageView(imageView);//bind main image
        clickViewList.add(imageView);
        contentArea.setVisibility(View.VISIBLE);
    } else {
        contentArea.removeAllViews();
        contentArea.setVisibility(View.GONE);
    }
    //Ad Logo
    View adLogoView = adMaterial.getAdLogoView();
    if (adLogoView != null) {
        adLogoContainer.setVisibility(View.VISIBLE);
        adLogoContainer.removeAllViews();
        adLogoContainer.addView(adLogoView);
    } else {
        adLogoContainer.setVisibility(View.GONE);
        String adChoiceIconUrl = adMaterial.getAdChoiceIconUrl();
        Bitmap adLogoBitmap = adMaterial.getAdLogo();
        if (!TextUtils.isEmpty(adChoiceIconUrl)) {
            logoView.setImage(adChoiceIconUrl);
            logoView.setVisibility(View.VISIBLE);
            nativePrepareInfo.setAdLogoView(logoView);//bind ad choice
        } else if (adLogoBitmap != null) {
            logoView.setImageBitmap(adLogoBitmap);
            logoView.setVisibility(View.VISIBLE);
            nativePrepareInfo.setAdLogoView(logoView);//bind ad choice
        } else {
            logoView.setImageBitmap(null);
            logoView.setVisibility(View.GONE);
        }
    }
    //bind layout params for ad choice
    FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(dip2px(context, 40),
            dip2px(context, 10));//ad choice
    layoutParams.gravity = Gravity.BOTTOM | Gravity.RIGHT;
    nativePrepareInfo.setChoiceViewLayoutParams(layoutParams);
    // ad from
    String adFrom = adMaterial.getAdFrom();
    if (!TextUtils.isEmpty(adFrom)) {
        adFromView.setText(adFrom);
        adFromView.setVisibility(View.VISIBLE);
    } else {
        adFromView.setVisibility(View.GONE);
    }
    nativePrepareInfo.setAdFromView(adFromView);//bind ad from
    nativePrepareInfo.setCloseView(closeView);//bind close button
    
  
    TextView domainView = selfRenderView.findViewById(R.id.native_ad_domain);
    TextView warningView = selfRenderView.findViewById(R.id.native_ad_warning);
     //Yandex require render domain
    String domain = adMaterial.getDomain();
    if (!TextUtils.isEmpty(domain)) {
        domainView.setVisibility(View.VISIBLE);
        domainView.setText(domain);
        clickViewList.add(domainView);
        nativePrepareInfo.setDomainView(domainView);
    } else {
        domainView.setVisibility(View.GONE);
    }
    //Yandex require render warning
    String warning = adMaterial.getWarning();
    if (!TextUtils.isEmpty(warning)) {
        warningView.setVisibility(View.VISIBLE);
        warningView.setText(warning);
        clickViewList.add(warningView);
        nativePrepareInfo.setWarningView(warningView);
    } else {
        warningView.setVisibility(View.GONE);
    }
    
    nativePrepareInfo.setClickViewList(clickViewList);//bind click view list
    //set direct download views
    //if (nativePrepareInfo instanceof ATNativePrepareExInfo) {
    //    List creativeClickViewList = new ArrayList<>();//click views
    //    creativeClickViewList.add(ctaView);
    //    ((ATNativePrepareExInfo) nativePrepareInfo).setCreativeClickViewList(creativeClickViewList);//bind custom view list
    //}
}
public static int dip2px(Context context, float dipValue) {
        float scale = context.getResources().getDisplayMetrics().density;
        return (int) (dipValue * scale + 0.5f);
}
3.3 关闭按钮说明(可选)
(1) 开发者可通过调用ATNativePrepareInfo#setCloseView()方法,将关闭按钮设置到ATNativePrepareInfo中,进行关闭按钮的绑定。(必须在调用prepare方法之前调用)
public void showNativeAd() {
    ...
    int height = adViewWidth * 600 / 1024;
    height = height <= 0 ? FrameLayout.LayoutParams.WRAP_CONTENT : height;
    ATNativePrepareInfo nativePrepareInfo = new ATNativePrepareInfo();
    View selfRenderView = LayoutInflater.from(this).inflate(R.layout.native_ad_item, null);
    bindSelfRenderView(this, mNativeAd.getAdMaterial(), selfRenderView, nativePrepareInfo, height)
    //渲染广告
    mNativeAd.renderAdContainer(anyThinkNativeAdView, selfRenderView);
    mNativeAd.prepare(anyThinkNativeAdView, nativePrepareInfo);
}
public void bindSelfRenderView(Context context, ATNativeMaterial adMaterial, View selfRenderView,     ATNativePrepareInfo nativePrepareInfo, int height) {
    ...
    View closeView = selfRenderView.findViewById(R.id.native_ad_close);//开发者自己的关闭按钮
    ...
    nativePrepareInfo.setCloseView(closeView);//bind close button
}
(2) 正确绑定关闭按钮后,设置关闭按钮的监听
 mNativeAd.setDislikeCallbackListener(new ATNativeDislikeListener() {
                @Override
                public void onAdCloseButtonClick(ATNativeAdView view, ATAdInfo entity) {
                    Log.i(TAG, "native ad onAdCloseButtonClick");
                      //在这里开发者可实现广告View的移除操作
                }
});
3.4 销毁广告
public void destroyAd() {
    if (mNativeAd != null) {
        mNativeAd.destory();
    }
}
4. 示例代码
ATNative atNative;
NativeAd mNativeAd;
int adViewWidth;
int adViewHeight;
public void loadNativeAd() {
  if (atNative == null) {
     //初始化广告加载对象
      atNative = new ATNative(this, nativeTakuPlacementID, new ATNativeNetworkListener() {
                @Override
                public void onNativeAdLoaded() {
                    Log.i(TAG, "onNativeAdLoaded");
                }
                @Override
                public void onNativeAdLoadFail(AdError adError) {
                    //注意:禁止在此回调中执行广告的加载方法进行重试,否则会引起很多无用请求且可能会导致应用卡顿
                    //AdError,请参考 https://docs.takuad.com/#/zh-cn/android/android_doc/android_test?id=aderror
                    Log.i(TAG, "onNativeAdLoadFail:" + adError.getFullErrorInfo());
                }
            });
   }
  // 解决华为原生广告会同时出现两个关闭按钮,在加载前加上此代码屏蔽华为关闭按钮展示
  // Map localMap = new HashMap<>(); 
  // localMap.put(HuaweiATConst.CUSTOM_DISLIKE, true);
  // localMap.put(ATAdConst.KEY.AD_CHOICES_PLACEMENT, ATAdConst.AD_CHOICES_PLACEMENT_INVISIBLE);
  // atNative.setLocalExtra(localMap)
    //发起广告请求
    atNative.makeAdRequest();
}
ATNativeAdView mATNativeAdView; //渲染广告必须创建的容器
View mSelfRenderView; //开发者自定义布局的容器
public void showNativeAd(ViewGroup adContainer, int adViewWidth) {
/*
 为了统计场景到达率,相关信息可查阅 "https://docs.takuad.com/#/zh-cn/android/NetworkAccess/scenario/scenario"
 在满足广告触发条件时调用“进入广告场景”方法,比如:
 ** 广告场景是在清理结束后弹出广告,则在清理结束时调用;
 * 1、先调用 "entryAdScenario"
 * 2、在调用 "ATNative#checkAdStatus#isReady" 是否可展示
 * 3、最后调用 "getNativeAd" 展示
 * 4、scenario 传入场景id后台漏斗报表才会到达场景数据(非必须)
 */
    ATNative.entryAdScenario("your Native placementID", "your scenarioID");
    if (atNative == null) {
        return;
    }
    if (!atNative.checkAdStatus().isReady()) {
        return;
    }
    if (mATNativeAdView == null) {
        mATNativeAdView = findViewById(R.id.native_ad_view); //可在xml布局定义
    }
    if (mSelfRenderView == null) {
        mSelfRenderView = mATNativeAdView.findViewById(R.id.native_selfrender_view); //可在xml布局定义
    }
    NativeAd nativeAd = atNative.getNativeAd();
    //开发者可以在调用getNativeAd后直接使用ATNative#makeAdRequest发起预加载下一次的广告
    //loadNativeAd();
    if (nativeAd != null) {
        // 销毁上一次展示的广告对象
        if (mNativeAd != null) {
            mNativeAd.destory();
        }
        mNativeAd = nativeAd;
        mNativeAd.setNativeEventListener(new ATNativeEventListener() {
            @Override
            public void onAdImpressed(ATNativeAdView view, ATAdInfo atAdInfo) {
                //ATAdInfo可区分广告平台以及获取广告平台的广告位ID等
                //请参考 https://docs.takuad.com/#/zh-cn/android/android_doc/android_sdk_callback_access?id=callback_info
                Log.i(TAG, "native ad onAdImpressed:\n" + atAdInfo.toString());
            }
            @Override
            public void onAdClicked(ATNativeAdView view, ATAdInfo atAdInfo) {
                Log.i(TAG, "native ad onAdClicked:\n" + atAdInfo.toString());
            }
            @Override
            public void onAdVideoStart(ATNativeAdView view) {
                Log.i(TAG, "native ad onAdVideoStart");
            }
            @Override
            public void onAdVideoEnd(ATNativeAdView view) {
                Log.i(TAG, "native ad onAdVideoEnd");
            }
            @Override
            public void onAdVideoProgress(ATNativeAdView view, int progress) {
                Log.i(TAG, "native ad onAdVideoProgress:" + progress);
            }
        });
        ATNativePrepareInfo nativePrepareInfo;
        if (!mNativeAd.isNativeExpress()) {
            //自渲染
            nativePrepareInfo = new ATNativePrepareInfo();
            bindSelfRenderView(this, mNativeAd.getAdMaterial(), mSelfRenderView,
                    nativePrepareInfo);
            mNativeAd.renderAdContainer(mATNativeAdView, mSelfRenderView);
        } else {
            //模板渲染
            mNativeAd.renderAdContainer(mATNativeAdView, null);
        }
        mNativeAd.prepare(mATNativeAdView, nativePrepareInfo);
    }
}
详细自渲染广告示例代码请参考:Demo的NativeAdActivity类,bindSelfRenderView请参考SelfRenderViewUtil类
5. 广告素材说明
NativeAd: 通过ATNative.getNativeAd()获取到的广告对象
| 方法 | 说明 | 
|---|---|
| getAdMaterial | 返回广告素材对象ATNativeMaterial •ATNativeMaterial: 广告素材对象(以下素材都可能会出现为null的情况,因为部分广告平台不一定存在所有素材信息)  | 
| 方法 | 说明 | 广告平台Native广告规范 | 
|---|---|---|
| getIconImageUrl | 获取广告图标的url | getAdIconView、getIconImageUrl同时返回时,优先选择getAdIconView,只需渲染其中一个 | 
| getAdIconView | 获取广告IconView | getAdIconView、getIconImageUrl同时返回时,优先选择getAdIconView,只需渲染其中一个 | 
| getAdMediaView | 获取广告大图的渲染容器(仅部分广告平台会存在),有可能是静态图和视频。参数描述:view:广告父容器, width: MediaView的宽度配置 | getAdMediaView,getMainImageUrl同时返回时,优先选择getAdMediaView ,只需渲染其中一个 | 
| getMainImageUrl | 获取大图Url | getAdMediaView,getMainImageUrl同时返回时,优先选择getAdMediaView,只需渲染其中一个 | 
| getTitle | 获取广告标题 | 有返回时需要渲染 | 
| getDescriptionText | 获取广告描述 | 有返回时需要渲染 | 
| getCallToActionText | 获取广告CTA按钮文字 | 有返回时需要渲染 | 
| getAdFrom | 获取广告来源 | Nend广告平台必须渲染该信息 | 
| getAdChoiceIconUrl | 获取广告标识的图标url | 和getAdLogo、getAdLogoView之间选择其中一个渲染即可,不一定会存在 | 
| getAdLogo | 获取AdLogo的Bitmap | 和getAdChoiceIconUrl、getAdLogoView之间选择其中一个渲染即可,不一定会存在 | 
| getAdLogoView | 获取AdLogo的View | 和getAdChoiceIconUrl、getAdLogo之间选择其中一个渲染即可,不一定会存在 | 
| getImageUrlList | 获取图片的url列表 | - | 
| getStarRating | 获取广告的评分 | - | 
| getAdType | 获取广告类型(视频、图片): CustomNativeAd.NativeAdConst.VIDEO_TYPE:视频类型 CustomNativeAd.NativeAdConst.IMAGE_TYPE:图片类型 CustomNativeAd.NativeAdConst.UNKNOWN_TYPE:未知广告类型(不支持的平台或者获取不到的,均为未知广告类型) | - | 
| getNativeAdInteractionType | 获取广告的交互类型:NativeAdInteractionType.APP_DOWNLOAD_TYPE:下载类广告; NativeAdInteractionType.H5_TYPE: 网页类广告 NativeAdInteractionType.DEEPLINK_TYPE: 应用跳转类广告 NativeAdInteractionType.UNKNOW: 未知广告类型 | - | 
| getNativeType | 获取广告类型 CustomNativeAd.NativeType.FEED:信息流广告(原生广告) CustomNativeAd.NativeType.PATCH:贴片广告 | - | 
| getVideoDuration | 获取视频总时长(double类型,单位:秒) | - | 
| getAdAppInfo | 获取下载的apk信息对象,具体支持平台可参考下方ATAdAppInfo说明 | - | 
| getMainImageWidth | 获取大图的宽度,不支持的平台会返回-1 (v5.9.96及以上支持返回) | - | 
| getMainImageHeight | 获取大图的高度,不支持的平台会返回-1(v5.9.96及以上支持返回) | - | 
| getVideoWidth | 获取视频的宽度,不支持的平台会返回-1(v5.9.96及以上支持返回) | - | 
| getVideoHeight | 获取视频的高度,不支持的平台会返回-1(v5.9.96及以上支持返回) | - | 
| getAdvertiserName | 获取广告主名字 | - | 
| getShakeView(int width, int height, ATShakeViewListener listener) | 获取摇一摇组件,若广告不支持摇一摇能力则返回null width: 组件的宽,不小于80dp height: 组件的高,不小于80dp listener: 组件的回调 (v6.1.40及以上支持,目前只有百度支持) | 具体调用示例代码可参考自渲染摇一摇 | 
| getSlideView(int width, int height, int repeat, final ATShakeViewListener listener) | 获取滑一滑组件,滑动区域受容器大小控制,若广告不支持滑一滑则返回null width: 滑动引导区域的宽 height: 滑动引导区域的高 repeat: 动画的重复次数,结束后自动隐藏组件 listener: 组件的回调 (v6.2.60及以上版本支持,目前只有百度支持) | 具体调用示例代码可参考Demo的SelfRenderViewUtil类的renderSlideView()方法 | 
| getDomain | 返回广告商的域名 | 仅yandex支持 | 
| getWarning | 返回警告文本 | 仅yandex支持 | 
| getDownloadProgress | 返回Apk文件下载进度 | 仅优量汇、百度支持 | 
| getDownloadStatus | 返回Apk文件下载状态 具体状态可以参考ApkDownloadStatus | 仅Adx、优量汇、百度支持 | 
ATNativeImageView:SDK提供的,用于显示网络图片(可选,建议开发者使用自身的图片加载框架)
| 方法 | 说明 | 
|---|---|
| setImage(String imageUrl) | 显示网络图片 imageUrl:网络图片url | 
| setImage(String imageUrl, int width, int height) | 显示网络图片 imageUrl:网络图片url width:图片宽度 height:图片高度 | 
6. 绑定
ATNativePrepareInfo:绑定关系封装类
| 方法 | 说明 | 
|---|---|
| setParentView(View parentView) | 绑定 父View | 
| setTitleView(View titleView) | 绑定 标题View,建议绑定 | 
| setIconView(View iconView) | 绑定 应用图标 View,建议绑定 | 
| setMainImageView(View mainImageView) | 绑定 大图View,建议绑定 | 
| setDescView(View descView) | 绑定 描述View,建议绑定 | 
| setCtaView(View ctaView) | 绑定 CTA按钮View,建议绑定 | 
| setChoiceViewLayoutParams(FrameLayout.LayoutParams choiceViewLayoutParams) | 设置 广告标识的大小、位置 | 
| setClickViewList(List | 绑定 可触发点击的View集合 | 
| setCloseView(View closeView) | 绑定 关闭按钮 | 
| setAdFromView(View adFromView) | 绑定 广告来源View,建议绑定 | 
| setAdLogoView(View adLogoView) | 绑定 AdLogo View | 
| setDomainView(View domainView) | 绑定 domainView(yandex必须绑定) | 
| setWarningView(View warningView) | 绑定 warningView(yandex必须绑定) | 
ATNativePrepareExInfo:继承自ATNativePrepareInfo,方法同ATNativePrepareInfo,额外方法说明如下:
| 方法 | 说明 | 
|---|---|
| setCreativeClickViewList(List <View> creativeClickViewList) | 绑定 直接下载广告的点击View集合 | 
| 
 setPermissionClickViewList(List <View> premissionClickViewList)  | 
绑定 查看权限的点击View集合 | 
| 
 setPrivacyClickViewList(List <View> privacyClickViewList)  | 
绑定 查看隐私协议的点击View集合 | 
| 
 setAppInfoClickViewList(List <View> appInfoClickViewList)  | 
绑定 查看产品的点击View集合 | 
7. 国内下载类广告下载类六要素
针对国内平台原生自渲染下载类广告返回六要素
7.1 接入建议
开发者通过判断NativeAd.getAdMaterial().getAdAppInfo()【下载类广告六要素信息对象】是否为空,不为空则把六要素信息渲染到布局上
注意:不是所有平台都提供完整的六要素,所以在渲染时需要判断要素返回是否为空,不为空再进行渲染
7.2 示例代码
View sixInfoView = selfRenderView.findViewById(R.id.six_info);
ATAdAppInfo adAppInfo = adMaterial.getAdAppInfo();
if (adAppInfo != null) {
    sixInfoView.setVisibility(View.VISIBLE);
    TextView functionTextView = sixInfoView.findViewById(R.id.function_test);
    TextView developerTextView = sixInfoView.findViewById(R.id.developer_test);
    TextView appnameTextView = sixInfoView.findViewById(R.id.appname_test);
    TextView versionTextView = sixInfoView.findViewById(R.id.version_test);
    TextView privacyTextView = sixInfoView.findViewById(R.id.privacy_test);
    TextView permissionTextView = sixInfoView.findViewById(R.id.permission_test);
    List appInfoClickViewList = new ArrayList<>();
    List privacyClickViewList = new ArrayList<>();
    List permissionClickViewList = new ArrayList<>();
    //获取应用名称,可以使用TitleView显示AppName
    appnameTextView.setText(TextUtils.isEmpty(adAppInfo.getAppName()) ? "" : adAppInfo.getAppName());
    //获取获取开发者公司名称
    developerTextView.setText(
            TextUtils.isEmpty(adAppInfo.getPublisher()) ? "" : adAppInfo.getPublisher());
    //获取应用版本号
    versionTextView.setText(
            TextUtils.isEmpty(adAppInfo.getAppVersion()) ? "" : adAppInfo.getAppVersion());
    appInfoClickViewList.add(developerTextView);
    appInfoClickViewList.add(versionTextView);
    //获取产品功能url
    appInfoClickViewList.add(functionTextView);
    if (!TextUtils.isEmpty(adAppInfo.getFunctionUrl())) {
        functionTextView.setVisibility(View.VISIBLE);
        setOpenUrlClickListener(functionTextView, adAppInfo.getFunctionUrl());
    } else {
        functionTextView.setOnClickListener(null);
        functionTextView.setVisibility(View.GONE);
    }
    //获取隐私协议url
    privacyClickViewList.add(privacyTextView);
    if (!TextUtils.isEmpty(adAppInfo.getAppPrivacyUrl())) {
        privacyTextView.setVisibility(View.VISIBLE);
        setOpenUrlClickListener(privacyTextView, adAppInfo.getAppPrivacyUrl());
    } else {
        privacyTextView.setVisibility(View.GONE);
        privacyTextView.setOnClickListener(null);
    }
    //获取权限列表url
    permissionClickViewList.add(permissionTextView);
    if (!TextUtils.isEmpty(adAppInfo.getAppPermissonUrl())) {
        permissionTextView.setVisibility(View.VISIBLE);
        setOpenUrlClickListener(permissionTextView, adAppInfo.getAppPermissonUrl());
    } else {
        permissionTextView.setVisibility(View.GONE);
        permissionTextView.setOnClickListener(null);
    }
    //绑定查看权限、隐私、产品功能点击View集合
    if (nativePrepareInfo instanceof ATNativePrepareExInfo) {
        ((ATNativePrepareExInfo) nativePrepareInfo).setAppInfoClickViewList(
                appInfoClickViewList);
        ((ATNativePrepareExInfo) nativePrepareInfo).setPermissionClickViewList(
                permissionClickViewList);
        ((ATNativePrepareExInfo) nativePrepareInfo).setPrivacyClickViewList(
                privacyClickViewList);
    }
} else {
    sixInfoView.setVisibility(View.GONE);
}
7.3 ATAdAppInfo下载类广告的六要素信息对象API说明
| 方法 | 说明 | 支持Network | 
|---|---|---|
| getAppName获取应用名称 | 优量汇、百度、快手、穿山甲、Mintegral、米盟、Taptap、Sigmob、Vivo、Oppo、华为 | |
| getPublisher | 获取开发者公司名称 | 优量汇、百度、快手、穿山甲、Mintegral、游可赢、米盟、Taptap、Sigmob、Vivo、Oppo、华为 | 
| getAppVersion | 获取应用版本号 | 优量汇、百度、快手、穿山甲、Mintegral、游可赢、米盟、Taptap、Sigmob、Vivo、Oppo、华为 | 
| getAppPrivacyUrl | 获取隐私协议url | 优量汇、百度、快手、穿山甲、Mintegral、游可赢、米盟、Sigmob、Taptap、Vivo | 
| getAppPermissonUrl | 获取权限列表url | 优量汇、百度、快手、穿山甲、米盟、Sigmob、Taptap、Vivo | 
| getFunctionUrl | 获取产品功能url//v6.2.37新增 | 优量汇、百度、穿山甲、Sigmob、Taptap、Vivo、快手 | 
getAppPrivacyUrl,getAppPermissonUrl,getFunctionUrl如果为空可参考上述示例代码ATNativePrepareExInfo绑定查看权限、隐私、产品功能点击View集合
