穿山甲sdk部分接入
一、AndroidStudio里面的操作
我使用的AndroidStudio的版本是:AndroidStudio 3.1.4。
Unity接入SDK
1.将unity在安卓平台选择Gradle打包出来,然后在放在AndroidStudio中一顿眼花缭乱的操作。
2.将unity的class.jar包以及将穿山甲SDK压缩包内的open_ad_sdk.aar及android-query-full.0.26.7.jar,导入AndroidStudio中的新建的Library中,然后在导出来放到unity中去调用。
具体操作:
1.Project模式:下在左上角File->New->New Module->Android Library,新建一个Library..........名字叫MyLibrary
2.将unity的class.jar、open_ad_sdk.aar、android-query-full.0.26.7.jar包复制到MyLibrary的libs中。
3.然后选中两个jar后缀的右键他们,找到AddLibrary,编译一下。至于arr包,需要找到你这个Library下的build.gradle,然后在dependencies加入字段implementation(name: 'open_ad_sdk', ext: 'aar')。下面是我的全部引用,主要是有注释那个
apply plugin: 'com.android.library'
android {
compileSdkVersion 28
defaultConfig {
minSdkVersion 16
targetSdkVersion 28
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
//按穿山甲开发文档加入他
repositories {
flatDir {
dirs 'libs'
}
}
dependencies {
implementation fileTree(include: ['*.jar'], dir: 'libs')
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.android.support.constraint:constraint-layout:1.1.3'
testImplementation 'junit:junit:4.12'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
implementation files('libs/classes.jar')
implementation files('libs/android-query-full.0.26.7.jar')
//arr包的导入方式
implementation(name: 'open_ad_sdk', ext: 'aar')
implementation 'pl.droidsonroids.gif:android-gif-drawable:1.2.6'
}
根据穿山甲的文档,在需要在dependencies的上面加入:
repositories {
flatDir {
dirs 'libs'
}
}
4.将模式切换为Android,然后和你的Library名字一样的文件,然后在下面的java文件下的第一个文件中,新建两个Activity。然后根据你的需要去写Java代码.....................
我这里只要激励广告所以只接入激励广告的:
初始化类:
package com.huowu.toutiaosdk2;
import android.content.Context;
import com.bytedance.sdk.openadsdk.TTAdConfig;
import com.bytedance.sdk.openadsdk.TTAdConstant;
import com.bytedance.sdk.openadsdk.TTAdManager;
import com.bytedance.sdk.openadsdk.TTAdSdk;
/**
* 可以用一个单例来保存TTAdManager实例,在需要初始化sdk的时候调用
*/
public class TTAdManagerHolder {
private static boolean sInit;
public static TTAdManager get() {
if (!sInit) {
throw new RuntimeException("TTAdSdk is not init, please check.");
}
return TTAdSdk.getAdManager();
}
//初始化时需要传入UserId,在Unity中调用
public static void init(Context context, String userId)
{
doInit(context, userId);
}
//step1:接入网盟广告sdk的初始化操作,详情见接入文档和穿山甲平台说明
private static void doInit(Context context, String userId) {
if (!sInit) {
TTAdSdk.init(context, buildConfig(context, userId));
sInit = true;
}
}
private static TTAdConfig buildConfig(Context context, String userId) {
return new TTAdConfig.Builder()
.appId(userId)
.useTextureView(true) //使用TextureView控件播放视频,默认为SurfaceView,当有SurfaceView冲突的场景,可以使用TextureView
.appName("APP测试媒体")
.titleBarTheme(TTAdConstant.TITLE_BAR_THEME_DARK)
.allowShowNotify(true) //是否允许sdk展示通知栏提示
.allowShowPageWhenScreenLock(true) //是否在锁屏场景支持展示广告落地页
.debug(true) //测试阶段打开,可以通过日志排查问题,上线时去除该调用
.directDownloadNetworkType(TTAdConstant.NETWORK_STATE_WIFI, TTAdConstant.NETWORK_STATE_3G) //允许直接下载的网络状态集合
.supportMultiProcess(false)
.build();
}
}
继承Unity的方法类
package com.huowu.toutiaosdk2;
import android.content.Context;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import com.bytedance.sdk.openadsdk.AdSlot;
import com.bytedance.sdk.openadsdk.TTAdManager;
import com.bytedance.sdk.openadsdk.TTAdNative;
import com.bytedance.sdk.openadsdk.TTAppDownloadListener;
import com.bytedance.sdk.openadsdk.TTRewardVideoAd;
import com.unity3d.player.UnityPlayerActivity;
public class MainActivity extends UnityPlayerActivity {
private TTAdNative mTTAdNative;
private TTRewardVideoAd mttRewardVideoAd;
private int ErrorCode = -1;
private String ErrorMessage = "Ranner";
private Context mContext;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
//初始化广告SDK接口
public void Init(Context context)
{
mContext = context;
//step1:初始化sdk
TTAdManager ttAdManager = TTAdManagerHolder.get();
//step2:(可选,强烈建议在合适的时机调用):申请部分权限,如read_phone_state,防止获取不了imei时候,下载类广告没有填充的问题。
TTAdManagerHolder.get().requestPermissionIfNecessary(mContext);
//step3:创建TTAdNative对象,用于调用广告请求接口
mTTAdNative = ttAdManager.createAdNative(mContext.getApplicationContext());
}
//得到当前的返回码
public int GetErrorCode()
{
return ErrorCode;
}
//得到当前的返错误信息
public String GetErrorMessage()
{
return ErrorMessage;
}
//加载广告
public void LoadAD(String adscodeId, String rewarName, String userID, int rewardNumber, int type)
{
loadAd(adscodeId, rewarName, userID, rewardNumber, type);
}
//播放广告
public void PlayVedio()
{
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mttRewardVideoAd != null)
{
//step6:在获取到广告后展示
ErrorCode = 1;
ErrorMessage = "视频缓存成功";
mttRewardVideoAd.showRewardVideoAd(MainActivity.this);
//TToast(MainActivity.this,"显示调用完成");
mttRewardVideoAd = null;
}
else
{
//TToast(MainActivity.this,"请先加载广告");
ErrorCode = 0;
ErrorMessage = "加载广告失败";
}
}
});
}
private boolean mHasShowDownloadActive = false;
//加载广告
private void loadAd(String adscodeId, String rewarName, String userID, int rewardNumber, int type) {
//step4:创建广告请求参数AdSlot,具体参数含义参考文档
AdSlot adSlot = new AdSlot.Builder()
.setCodeId(adscodeId) //广告ID
.setSupportDeepLink(true)
.setImageAcceptedSize(1080, 1920)
.setRewardName(rewarName) //奖励的名称
.setRewardAmount(rewardNumber) //奖励的数量
.setUserID(userID)//用户id,必传参数
.setMediaExtra("media_extra") //附加参数,可选
.setOrientation(type) //必填参数,期望视频的播放方向:TTAdConstant.HORIZONTAL 或 TTAdConstant.VERTICAL
.build();
//step5:请求广告
mTTAdNative.loadRewardVideoAd(adSlot, new TTAdNative.RewardVideoAdListener() {
@Override
public void onError(int code, String message)
{
//广告加载错误
ErrorCode = 0;
ErrorMessage = message;
}
//视频广告加载后,视频资源缓存到本地的回调,在此回调后,播放本地视频,流畅不阻塞。
@Override
public void onRewardVideoCached()
{
//广告加载成功
ErrorCode = 1;
ErrorMessage = "视频缓存成功";
}
//视频广告的素材加载完毕,比如视频url等,在此回调后,可以播放在线视频,网络不好可能出现加载缓冲,影响体验。
@Override
public void onRewardVideoAdLoad(TTRewardVideoAd ad)
{
mttRewardVideoAd = ad;
// mttRewardVideoAd.setShowDownLoadBar(false);
mttRewardVideoAd.setRewardAdInteractionListener(new TTRewardVideoAd.RewardAdInteractionListener()
{
@Override
public void onAdShow()
{
ErrorCode = 2;
ErrorMessage = "视频在播放";
}
@Override
public void onAdVideoBarClick() {
ErrorCode = 3;
ErrorMessage = "视频被点击";
}
@Override
public void onAdClose()
{
ErrorCode = 4;
ErrorMessage = "视频被关闭";
}
//视频播放完成回调
@Override
public void onVideoComplete()
{
ErrorCode = 5;
ErrorMessage = "视频播放完毕";
}
@Override
public void onVideoError()
{
ErrorCode = 6;
ErrorMessage = "视频播放出现错误";
}
//视频播放完成后,奖励验证回调,rewardVerify:是否有效,rewardAmount:奖励梳理,rewardName:奖励名称
@Override
public void onRewardVerify(boolean rewardVerify, int rewardAmount, String rewardName)
{
ErrorCode = 7;
ErrorMessage = "视频看完,可发放奖励";
}
});
mttRewardVideoAd.setDownloadListener(new TTAppDownloadListener() {
@Override
public void onIdle() {
mHasShowDownloadActive = false;
}
@Override
public void onDownloadActive(long totalBytes, long currBytes, String fileName, String appName) {
if (!mHasShowDownloadActive) {
mHasShowDownloadActive = true;
//TToast(MainActivity.this, "下载中,点击下载区域暂停");
}
}
@Override
public void onDownloadPaused(long totalBytes, long currBytes, String fileName, String appName) {
//TToast(MainActivity.this, "下载暂停,点击下载区域继续");
}
@Override
public void onDownloadFailed(long totalBytes, long currBytes, String fileName, String appName) {
//TToast(MainActivity.this, "下载失败,点击下载区域重新下载");
}
@Override
public void onDownloadFinished(long totalBytes, String fileName, String appName) {
//TToast(MainActivity.this, "下载完成,点击下载区域重新下载");
}
@Override
public void onInstalled(String fileName, String appName) {
//TToast(MainActivity.this, "安装完成,点击下载区域打开");
}
});
}
});
}
}
5.写完之后,切换到Project模式,选中你的Library,然后在工具栏,找到Build,点击它,选中第二个“Make Module.... ”。如果不报错,一切顺利,完了之后。找到在你的Library文件下/build/outputs/arr/xxxx-debug.aar。这个xxxx-debug.aar就是需要的包。右键-Show in Eplorer。
6.保险起见,你可以复制一份出来,然后打开压缩包,删掉里面的 layout文件夹、libs/class.jar、res/layout......修改AndroidManifest.xml。
修改完成后,将包导入unity中的Unity/Plugins/Android/
对了:open_ad_sdk.aar 这个包也要放到Unity/Plugins/Android/中去
这是我修改的:AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="com.huowu.toutiaosdk"
android:versionCode="1"
android:versionName="1.0" > <!-- minSdkVersion为9时的合并 -->
<!-- minSdkVersion为9时的合并 -->
<uses-sdk tools:overrideLibrary="android.support.v7.appcompat, android.support.v7.recyclerview,com.dingmouren.layoutmanagergroup, com.squareup.leakcanary, com.squareup.leakcanary.analyzer, com.squareup.leakcanary.android.noop" />
<!-- 如果有视频相关的广告且使用textureView播放,请务必添加,否则黑屏 -->
<uses-permission android:name="android.permission.WAKE_LOCK" />
<!-- 必须要有的权限 -->
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
<uses-permission android:name="android.permission.GET_TASKS" />
<!-- 最好能提供的权限 -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<application
android:usesCleartextTraffic="true">
<activity android:name="com.huowu.toutiaosdk2.MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<meta-data
android:name="unityplayer.UnityActivity"
android:value="true" />
</activity>
<provider
android:name="com.bytedance.sdk.openadsdk.multipro.TTMultiProvider"
android:authorities="${applicationId}.TTMultiProvider"
android:exported="false" />
</application>
</manifest>
二、Unity的操作
在场景中新建一个GameObject,挂上下面的脚本:
这是相当于初始化组件,用来初始化穿山甲SDK,以及安卓中的一些方法
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Hotfix;
public class TouTiaoAdsManager : MonoBehaviour {
public static TouTiaoAdsManager Inst;
private string appId = "你的appId ,可以用他Demo里面的";
private string adsId = "你的adsID,可以用他Demo里面的";
private AndroidJavaClass UnityJc;
private AndroidJavaObject UnityJo;
public string EorrMessage { get; set; }
/// <summary>
/// 头条初始化组件
/// </summary>
private AndroidJavaClass ToutiaoJc;
private void Awake()
{
Inst = this;
this.UnityJc = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
this.UnityJo = this.UnityJc.GetStatic<AndroidJavaObject>("currentActivity");
this.ToutiaoJc = new AndroidJavaClass("com.huowu.toutiaosdk2.TTAdManagerHolder");
this.InitToutiaoSdk();
this.InitToutiaoAds();
}
/// <summary>
/// 初始化头条SDK
/// </summary>
public void InitToutiaoSdk()
{
this.ToutiaoJc.CallStatic(TouTiaoMethd.TTAdManagerInit, this.UnityJo, this.appId);
}
/// <summary>
/// 初始化头条广告
/// </summary>
public void InitToutiaoAds()
{
this.UnityJo.Call(TouTiaoMethd.RewardVideoInit, this.UnityJo);
}
/// <summary>
/// 加载头条广告
/// </summary>
public void LoadToutiaoAds()
{
this.UnityJo.Call(TouTiaoMethd.LoadRewardVideo, this.adsId, "广告时间减少", this.appId, 20, 2);
}
/// <summary>
/// 播放头条广告
/// </summary>
public void PlayToutiaoAds()
{
this.UnityJo.Call(TouTiaoMethd.ShowRewardVidwo);
}
/// <summary>
/// 返回错误码
/// </summary>
/// <returns></returns>
public int GetToutiaoErrorCode()
{
return this.UnityJo.Call<int>(TouTiaoMethd.GetErrorCode);
}
/// <summary>
/// 返回错误信息
/// </summary>
/// <returns></returns>
public string GetToutiaoErrorMessage()
{
EorrMessage = this.UnityJo.Call<string>(TouTiaoMethd.GetErrorMessage);
return EorrMessage;
}
}
这是测试脚本
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using Hotfix;
using System;
public class MainTest : MonoBehaviour {
private Button loadBtn;
private Button playBtn;
public Text textMessage;
private bool isLoop = false;
private int State = -1;
private Action CanGetReward;
void Start () {
this.loadBtn = transform.Find("LoadBtn").GetComponent<Button>();
this.playBtn = transform.Find("PlayBtn").GetComponent<Button>();
this.loadBtn.onClick.AddListener(this.LoadBtnOnClick);
this.playBtn.onClick.AddListener(this.PlayBtnOnClick);
//StartCoroutine(InitADS());
}
void Update ()
{
State = TouTiaoAdsManager.Inst.GetToutiaoErrorCode();
if (State == ToutiaoErrorCode.PlayOver || State == ToutiaoErrorCode.BeClose || State == ToutiaoErrorCode.CanGiveReward)
{
textMessage.text = "可以领取奖励";
//CanGetReward.Invoke();
TouTiaoAdsManager.Inst.LoadToutiaoAds();
}
}
public void LoadBtnOnClick()
{
TouTiaoAdsManager.Inst.LoadToutiaoAds();
//this.textMessage.text = TouTiaoAdsManager.Inst.GetToutiaoErrorMessage();
}
public void PlayBtnOnClick()
{
if (State == ToutiaoErrorCode.Succes)
{
TouTiaoAdsManager.Inst.PlayToutiaoAds();
}
else
{
this.textMessage.text = "广告正在加载中...";
}
}
}
我把安卓中的方法名,用一个类给保存了起来:
using System;
namespace Hotfix
{
/// <summary>
/// Ranner: 头条方法名封装,用于调用Java中的方法
/// </summary>
public class TouTiaoMethd
{
/// <summary>
/// 头条初始化方法, 需要传入Context, userID
/// </summary>
public const string TTAdManagerInit = "init";
/// <summary>
/// 头条广告初始化方法, 需要传入Context
/// </summary>
public const string RewardVideoInit = "Init";
/// <summary>
/// 头条广告加载方法, 需要传入入广告ID
/// </summary>
public const string LoadRewardVideo = "LoadAD";
/// <summary>
/// 头条广告播放方法, 需要传入 Activity
/// </summary>
public const string ShowRewardVidwo = "PlayVedio";
/// <summary>
/// 得到当前的返回码
/// </summary>
public const string GetErrorCode = "GetErrorCode";
/// <summary>
/// 得到当前的返错误信息
/// </summary>
public const string GetErrorMessage = "GetErrorMessage";
}
/// <summary>
/// 头条返回的错误码信息
/// </summary>
public class ToutiaoErrorCode
{
/// <summary>
/// 广告加载错误
/// </summary>
public const int Faile = 0;
/// <summary>
/// 广告加载成功
/// </summary>
public const int Succes = 1;
/// <summary>
/// 视频在播放
/// </summary>
public const int Playing = 2;
/// <summary>
/// 视频被点击
/// </summary>
public const int BeTouck = 3;
/// <summary>
/// 视频被关闭
/// </summary>
public const int BeClose = 4;
/// <summary>
/// 视频播放完毕
/// </summary>
public const int PlayOver = 5;
/// <summary>
/// 视频播放出现错误
/// </summary>
public const int PlayFaile = 6;
/// <summary>
/// 视频看完,可发放奖励
/// </summary>
public const int CanGiveReward = 6;
}
}
三、最头疼的
1.Unity/Plugins/Android/AndroidManifest.xml
不知道你们是怎样的,我的是这样的:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="com.huowu.toutiaosdk2"
android:versionCode="1"
android:versionName="1.0" > <!-- minSdkVersion为9时的合并 -->
<uses-sdk
android:minSdkVersion="16"
android:targetSdkVersion="28"
tools:overrideLibrary="android.support.v7.appcompat, android.support.v7.recyclerview,com.dingmouren.layoutmanagergroup, com.squareup.leakcanary, com.squareup.leakcanary.analyzer, com.squareup.leakcanary.android.noop" />
<!-- 如果有视频相关的广告且使用textureView播放,请务必添加,否则黑屏 -->
<uses-permission android:name="android.permission.WAKE_LOCK" />
<!-- 必须要有的权限 -->
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
<uses-permission android:name="android.permission.GET_TASKS" />
<!-- 最好能提供的权限 -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<application
android:label="@string/app_name"
android:usesCleartextTraffic="true" >
<activity android:name="com.huowu.toutiaosdk2.MainActivity" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<meta-data
android:name="unityplayer.UnityActivity"
android:value="true" />
</activity>
<provider
android:name="com.bytedance.sdk.openadsdk.multipro.TTMultiProvider"
android:authorities="${applicationId}.TTMultiProvider"
android:exported="false" />
</application>
</manifest>