重构AD部分

This commit is contained in:
姜珂 2025-07-06 15:19:59 +08:00
parent 970b34a8aa
commit 41732c8e51
80 changed files with 904 additions and 1277 deletions

View File

@ -2,42 +2,7 @@ package com.tfq.library.app;
public class BaseConstants {
public static final int URL_REQUEST_ERROR = 401;
public static boolean BASE_APP_DEBUG_PRINT;
public static String APP_ID = "";
public static String CSJ_ID = "";
public static String APP_NAME = "";
public static String CHANNEL = "";
public static String csjIdFeed1;
public static String csjIdFeed2;
public static boolean _isShow;
// 1.开屏 2.激励视频 3.信息流 4.插全屏 5.banner 6.draw信息流
public static boolean AD_SPLASH = false;//开屏广告
public static boolean AD_REWARD = false;//激励视频
public static boolean AD_CQP = false;//插全屏广告
public static boolean AD_NATIVE = false;//原生信息流广告
public static boolean AD_BANNER = false;//banner广告
public static boolean AD_DRAW = false;//draw信息流广告
public static int ADV_Wait = 60;//插全屏两个相差时间
public static boolean adv_csj = true;//穿山甲正常
public static boolean NO_AD = true;//穿山甲正常
public static long request_splash_time = 30;
public static boolean AD_Switch_Requested = false;//请求过广告开关
public static String CODE_AD_SPLASH;
public static String CODE_AD_CQP;
public static String CODE_AD_FEED1;
public static String CODE_AD_FEED2;
public static String CODE_AD_FEED3;
public static String CODE_AD_BANNER;
public static String CODE_AD_REWARD;
public static String CODE_AD_DRAW;
public static boolean PRE_AD = true;
public static int appSplash;
/**
* 底部导航栏颜色 默认白色

View File

@ -3,14 +3,12 @@ plugins {
id 'maven-publish' //
}
//apply plugin: 'com.kezong.fat-aar'
android {
namespace 'com.tfq.libraryad'
compileSdkVersion 34
defaultConfig {
minSdkVersion 21
minSdkVersion 24
targetSdkVersion 34
}
@ -36,38 +34,18 @@ repositories {
}
dependencies {
// implementation fileTree(include: ['*.aar', '*.jar'], dir: 'libs')
compileOnly fileTree(include: ['*.aar', '*.jar'], dir: 'libs')
// implementation name: 'GDTSDK.unionNormal.4.610.1480', ext: 'aar'
// implementation name: 'mediation_gdt_adapter_4.610.1480.0', ext: 'aar'
// implementation name: 'open_ad_sdk_6.6.0.7', ext: 'aar'
//
// implementation 'androidx.appcompat:appcompat:1.4.1'
// implementation 'com.google.android.material:material:1.5.0'
// testImplementation 'junit:junit:4.13.2'
// androidTestImplementation 'androidx.test.ext:junit:1.1.3'
// androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
implementation 'androidx.appcompat:appcompat:1.7.0'
implementation 'com.google.android.material:material:1.11.0'
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
//
// api 'com.gyf.immersionbar:immersionbar:3.0.0-beta05'
//
// api 'com.github.getActivity:XXPermissions:18.63'
// api 'com.github.CymChad:BaseRecyclerViewAdapterHelper:2.9.28'
// api 'androidx.activity:activity:1.3.0'
api project(':BaseLibrary')
// implementation project(':LocalAarModules:AdCSJSdk')
// implementation project(':LocalAarModules:AdGDTSdk')
// implementation project(':LocalAarModules:AdGDTSdk_Adapter')
//noinspection Aligned16KB
// implementation 'com.pangle.cn:mediation-sdk:6.6.0.7' //穿SDK
// implementation 'com.pangle.cn:GDTSDK-unionNormal:4.610.1480' //GDT
// implementation 'com.pangle.cn:mediation-gdt-adapter:4.610.1480.0' //GDT adapter
implementation 'com.gyf.immersionbar:immersionbar:3.0.0-beta05'
//gson
// implementation 'com.google.code.gson:gson:2.13.1'
// implementation 'com.alibaba:fastjson:2.0.57'
}
@ -83,7 +61,6 @@ afterEvaluate {
}
repositories {
maven {
// url = "file://${projectDir.parent}/maven-repo" //
url = "file://${projectDir.parent}/maven" //
}
/*maven {
@ -95,21 +72,4 @@ afterEvaluate {
}*/
}
}
}
/*publishing {
publications {
maven(MavenPublication) {
groupId = 'com.jiangke.group' //
artifactId = 'lib-name' //
version = '1.0.0' //
// AAR
artifact("$buildDir/outputs/aar/${project.name}-release.aar")
}
}
repositories {
maven {
url "file://D:/Android/Code/tfq/JKBaseLib" //
}
}
}*/
}

View File

@ -112,7 +112,6 @@
<activity
android:name="com.tfq.ad.ad.activity.AdSplashActivity"
android:screenOrientation="portrait"
android:theme="@style/SplashTheme"
tools:replace="android:screenOrientation"
/>

View File

@ -0,0 +1,70 @@
package com.tfq.ad.ad;
import android.app.Activity;
import android.content.Context;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
public class ADStateUtils {
private static Activity mContext;
private static String type;
private static SwitchRequestListener switchRequestListener;
public ADStateUtils(String type, Context mContext) {
this.mContext = (Activity) mContext;
this.type = type;
regexSwitch();
}
public static void setSwitchRequestListener(SwitchRequestListener listener) {
switchRequestListener = listener;
}
public boolean regexSwitch() {
ADConstants._isShow = false;
boolean b = false;
if (ADConstants.AD_Switch_Requested) {
boolean _type;
switch (type) {
case "GMSplashAd":
_type = ADConstants.AD_SPLASH;
break;
case "GMRewardAd":
_type = ADConstants.AD_REWARD;
break;
case "GMInterstitialFullAd":
_type = ADConstants.AD_CQP;
break;
case "GMNativeAd":
_type = ADConstants.AD_NATIVE;
break;
case "GMBannerAd":
_type = ADConstants.AD_BANNER;
break;
default:
_type = false;
break;
}
LogAd.e("广告类型=" + type
+ " 穿山甲是否正常=" + ADConstants.adv_csj
+ " 强制无广告=" + AdApp.getInstance().isSlotConfig("NO_AD")
+ " 当前广告类型是开=" + _type);
if (ADConstants.adv_csj && !AdApp.getInstance().isSlotConfig("NO_AD") && _type) {
b = true;
}
} else {
if (switchRequestListener != null) {
switchRequestListener.onSwitchRequestChanged(false);
switchRequestListener = null;
}
}
return b;
}
public interface SwitchRequestListener {
void onSwitchRequestChanged(boolean isRequested);
}
}

View File

@ -1,107 +0,0 @@
package com.tfq.ad.ad;
import android.app.Activity;
import android.content.Context;
import com.google.gson.Gson;
import com.tfq.ad.bean.AdvBean;
import com.tfq.ad.bean.UserInfo;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
public class ADUtils {
private static Activity mContext;
private static String type;
public ADUtils(String type, Context mContext) {
this.mContext = (Activity) mContext;
this.type = type;
regexSwitch();
}
public boolean regexSwitch() {
BaseConstants._isShow = false;
boolean b = false;
if (BaseConstants.AD_Switch_Requested) {
boolean _type;
switch (type) {
case "GMSplashAd"://开屏
_type = BaseConstants.AD_SPLASH;
break;
case "GMRewardAd"://激励
_type = BaseConstants.AD_REWARD;
break;
case "GMInterstitialFullAd"://插全屏
_type = BaseConstants.AD_CQP;
break;
case "GMNativeAd"://信息流
_type = BaseConstants.AD_NATIVE;
break;
case "GMBannerAd"://banner
_type = BaseConstants.AD_BANNER;
break;
default:
_type = false;
break;
}
LogK.e("广告类型=" + type
+ " 穿山甲是否正常=" + BaseConstants.adv_csj
+ " 强制无广告=" + BaseConstants.NO_AD
+ " 当前广告类型是开=" + _type);
if (BaseConstants.adv_csj && !BaseConstants.NO_AD && _type) {
b = true;
}
return b;
} else {
getPlatform();
}
return b;
}
private void getPlatform() {
new UserInfo().getAdvertising(new UserInfo.Success() {
@Override
public void Success(String data, String msg) {
try {
Gson gson = new Gson();
AdvBean entity = gson.fromJson(data, AdvBean.class);
if (entity.getData() != null) {
AdvBean.DataDTO entityData = entity.getData();
if ("1".equals(entityData.getAdv1Flag())) {
BaseConstants.AD_SPLASH = true;
}
if ("1".equals(entityData.getAdv2Flag())) {
BaseConstants.AD_REWARD = true;
}
if ("1".equals(entityData.getAdv3Flag())) {
BaseConstants.AD_NATIVE = true;
}
if ("1".equals(entityData.getAdv4Flag())) {
BaseConstants.AD_CQP = true;
}
if ("1".equals(entityData.getAdv5Flag())) {
BaseConstants.AD_BANNER = true;
}
if ("1".equals(entityData.getAdv6Flag())) {
BaseConstants.AD_DRAW = true;
}
if (entityData.getAdv4Wait() > 0) {
BaseConstants.ADV_Wait = entityData.getAdv4Wait();
}
} else {
BaseConstants.adv_csj = false;
}
} catch (Exception e) {
e.printStackTrace();
}
BaseConstants.AD_Switch_Requested = true;
}
@Override
public void fail(int num, String msg) {
}
});
}
}

View File

@ -11,14 +11,15 @@ import com.bytedance.sdk.openadsdk.TTAdDislike;
import com.bytedance.sdk.openadsdk.TTAdNative;
import com.bytedance.sdk.openadsdk.TTFeedAd;
import com.bytedance.sdk.openadsdk.TTNativeExpressAd;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
import java.util.List;
public class AdBannerUtils {
private static Context mContext;
private static String mAdUnitId = BaseConstants.CODE_AD_BANNER;
private static String mAdUnitId = AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_BANNER);
private static int width = 0;
private static Listener listener;
//判断大于多少秒
@ -34,7 +35,7 @@ public class AdBannerUtils {
mContext = context;
mBannerContainer = layout;
if (new ADUtils("GMBannerAd", mContext).regexSwitch()) {
if (new ADStateUtils("GMBannerAd", mContext).regexSwitch()) {
loadAD();
}
}
@ -56,7 +57,7 @@ public class AdBannerUtils {
}
private static boolean interval() {
if (System.currentTimeMillis() - lastTime > (100 * interval)) {
if (System.currentTimeMillis() - lastTime > (100L * interval)) {
return true;
} else {
return false;
@ -69,7 +70,10 @@ public class AdBannerUtils {
int width = (int) (UIUtils.getScreenWidthDp(mContext) - AdBannerUtils.width);
int height = (int) ((UIUtils.getScreenWidthDp(mContext) - AdBannerUtils.width) / 4);
// height = 0;
LogK.e("AdBannerUtils mAdUnitId=" + mAdUnitId);
LogAd.e("mAdUnitId=" + mAdUnitId);
if (mAdUnitId.equals("0")) {
return;
}
AdSlot adSlot = new AdSlot.Builder()
.setCodeId(mAdUnitId)
.setImageAcceptedSize(UIUtils.dp2px(mContext, width), UIUtils.dp2px(mContext, height)) // 单位px
@ -105,7 +109,7 @@ public class AdBannerUtils {
mBannerAd.setSlideIntervalTime(5);
} else {
LogK.e("请先加载广告或等待广告加载完毕后再展示广告");
LogAd.e("请先加载广告或等待广告加载完毕后再展示广告");
}
}
@ -115,19 +119,19 @@ public class AdBannerUtils {
mBannerListener = new TTAdNative.NativeExpressAdListener() {
@Override
public void onError(int i, String s) {
LogK.e("banner load fail: errCode: " + i + ", errMsg: " + s);
LogAd.e("banner load fail: errCode: " + i + ", errMsg: " + s);
}
@Override
public void onNativeExpressAdLoad(List<TTNativeExpressAd> list) {
if (list != null && list.size() > 0) {
LogK.e("banner load success");
LogAd.e("banner load success");
mBannerAd = list.get(0);
showBannerAd();
} else {
LogK.e("banner load success, but list is null");
LogAd.e("banner load success, but list is null");
}
}
};
@ -137,13 +141,13 @@ public class AdBannerUtils {
@Override
public void onAdClicked(View view, int i) {
LogK.e("banner clicked");
LogAd.e("banner clicked");
}
@Override
public void onAdShow(View view, int i) {
LogK.e("banner showed");
LogAd.e("banner showed");
}
@Override
@ -168,7 +172,7 @@ public class AdBannerUtils {
public void onSelected(int i, String s, boolean b) {
if (mBannerContainer != null)
mBannerContainer.removeAllViews();
LogK.e("banner closed");
LogAd.e("banner closed");
}
@Override

View File

@ -8,14 +8,15 @@ import com.bytedance.sdk.openadsdk.TTAdConstant;
import com.bytedance.sdk.openadsdk.TTAdNative;
import com.bytedance.sdk.openadsdk.TTAdSdk;
import com.bytedance.sdk.openadsdk.TTFullScreenVideoAd;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
public class AdCQPUtils {
private CQP listener;
private CQP_Load_Success cqp_load_success;
private String mAdUnitId = BaseConstants.CODE_AD_CQP;
private String mAdUnitId = AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_CQP);
public interface CQP {
void success(boolean b);
@ -26,11 +27,11 @@ public class AdCQPUtils {
}
//判断大于多少秒可以下一次开启
int interval = BaseConstants.ADV_Wait;
int interval = ADConstants.ADV_Wait;
static long lastTime = 0;
private boolean interval() {
if (System.currentTimeMillis() - lastTime > (1000 * interval)) {
if (System.currentTimeMillis() - lastTime > (1000L * interval)) {
return true;
} else {
return false;
@ -58,7 +59,7 @@ public class AdCQPUtils {
public void init(Context mContext, boolean load) {
boolean csj = true;
if (new ADUtils("GMInterstitialFullAd", mContext).regexSwitch() && csj && interval()) {
if (new ADStateUtils("GMInterstitialFullAd", mContext).regexSwitch() && csj && interval()) {
loadInterstitialFullAd(mContext);
} else {
if (listener != null) {
@ -73,6 +74,10 @@ public class AdCQPUtils {
}
private void loadInterstitialFullAd(Context mContext) {
LogAd.e("mAdUnitId=" + mAdUnitId);
if (mAdUnitId.equals("0")) {
return;
}
TTAdNative adNativeLoader = TTAdSdk.getAdManager().createAdNative(mContext);
AdSlot adslot = new AdSlot.Builder()
.setCodeId(mAdUnitId)
@ -82,7 +87,7 @@ public class AdCQPUtils {
adNativeLoader.loadFullScreenVideoAd(adslot, new TTAdNative.FullScreenVideoAdListener() {
@Override
public void onError(int code, String message) {
LogK.e("Screen onError code = " + code + " message = " + message);
LogAd.e("Screen onError code = " + code + " message = " + message);
if (listener != null) {
listener.success(false);
listener = null;
@ -100,12 +105,12 @@ public class AdCQPUtils {
@Override
public void onFullScreenVideoCached() {
LogK.e("onFullScreenVideoCached");
LogAd.e("onFullScreenVideoCached");
}
@Override
public void onFullScreenVideoCached(TTFullScreenVideoAd ttFullScreenVideoAd) {
LogK.e("onFullScreenVideoCached");
LogAd.e("onFullScreenVideoCached");
showInterstitialFullAd(ttFullScreenVideoAd, mContext);
}
});
@ -118,7 +123,7 @@ public class AdCQPUtils {
ttFullScreenVideoAd.setFullScreenVideoAdInteractionListener(new TTFullScreenVideoAd.FullScreenVideoAdInteractionListener() {
@Override
public void onAdShow() {
LogK.e("InterstitialFullActivity onAdShow");
LogAd.e("InterstitialFullActivity onAdShow");
if (cqp_load_success != null) {
cqp_load_success.success(true);
cqp_load_success = null;
@ -128,12 +133,12 @@ public class AdCQPUtils {
@Override
public void onAdVideoBarClick() {
LogK.e("InterstitialFullActivity onAdVideoBarClick");
LogAd.e("InterstitialFullActivity onAdVideoBarClick");
}
@Override
public void onAdClose() {
LogK.e("InterstitialFullActivity onAdClose");
LogAd.e("InterstitialFullActivity onAdClose");
if (listener != null) {
listener.success(false);
listener = null;
@ -142,12 +147,12 @@ public class AdCQPUtils {
@Override
public void onVideoComplete() {
LogK.e("InterstitialFullActivity onVideoComplete");
LogAd.e("InterstitialFullActivity onVideoComplete");
}
@Override
public void onSkippedVideo() {
LogK.e("InterstitialFullActivity onSkippedVideo");
LogAd.e("InterstitialFullActivity onSkippedVideo");
}
});
ttFullScreenVideoAd.showFullScreenVideoAd((Activity) mContext);
@ -160,7 +165,7 @@ public class AdCQPUtils {
public void showInterFullAd(Context mContext, CQP listene) {
this.listener = listene;
boolean csj = true;
if (new ADUtils("GMInterstitialFullAd", mContext).regexSwitch() && csj) {
if (new ADStateUtils("GMInterstitialFullAd", mContext).regexSwitch() && csj) {
loadInterstitialFullAd(mContext);
} else {
if (listener != null) {

View File

@ -1,5 +1,6 @@
package com.tfq.ad.ad;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Context;
import android.text.TextUtils;
@ -13,8 +14,9 @@ import com.bytedance.sdk.openadsdk.TTAdNative;
import com.bytedance.sdk.openadsdk.TTAdSdk;
import com.bytedance.sdk.openadsdk.TTFeedAd;
import com.bytedance.sdk.openadsdk.mediation.ad.MediationExpressRenderListener;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
import java.util.HashMap;
import java.util.List;
@ -23,8 +25,9 @@ import java.util.Map;
public class AdFeedUtils {
public static Map<String, Boolean> map = new HashMap<>();
public static Map<String, Boolean> locationMap;
@SuppressLint("StaticFieldLeak")
private static Context mContext;
private static String mAdUnitId = LoopAd.getCurrentFeedID();
private static String mAdUnitId = AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_FEED1);
private static String tag;
private static int width = 0;
private static TTAdNative adNativeLoader;
@ -33,9 +36,8 @@ public class AdFeedUtils {
private static boolean mIsLoadedAndShow;
private static TTFeedAd mTTFeedAd;
@SuppressLint("StaticFieldLeak")
private static FrameLayout mFeedContainer;
//判断大于多少秒
private static int interval = 10;
private static long lastTime = 0;
private static boolean reload = false;
/**
@ -89,7 +91,7 @@ public class AdFeedUtils {
}
public static void preAD(Context context, int i_width) {
if (new ADUtils("GMNativeAd", context).regexSwitch()) {
if (new ADStateUtils("GMNativeAd", context).regexSwitch()) {
width = i_width;
mContext = context;
mIsLoadedAndShow = false;
@ -100,7 +102,7 @@ public class AdFeedUtils {
}
private static void show_ad(Context context, FrameLayout feedContainer, String s_tag) {
if (new ADUtils("GMNativeAd", context).regexSwitch() && isNoSkip(s_tag)) {
if (new ADStateUtils("GMNativeAd", context).regexSwitch() && isNoSkip(s_tag)) {
mContext = context;
mFeedContainer = feedContainer;
mIsLoadedAndShow = true;
@ -111,9 +113,9 @@ public class AdFeedUtils {
}
}
public static void show_ad(Context mContext, String adUnitId, FrameLayout mFeedContainer, int i_width, String tag, int mPage_type) {
public static void show_ad(Context mContext, String adUnitId_currrent, FrameLayout mFeedContainer, int i_width, String tag, int mPage_type) {
page_type = mPage_type;
mAdUnitId = adUnitId;
mAdUnitId = adUnitId_currrent;
width = i_width;
show_ad(mContext, mFeedContainer, tag);
@ -124,10 +126,10 @@ public class AdFeedUtils {
if (adNativeLoader == null) {
GMNativeADBean bean = CacheADManager.requestHaveAD("feed", mAdUnitId);
if (bean == null) {
LogK.e("bean == null");
LogAd.e("bean == null");
load();
} else {
LogK.e("bean != null");
LogAd.e("bean != null");
if (mIsLoadedAndShow) {
mTTFeedAd = bean.getmGMNativeAD();
show();
@ -142,7 +144,9 @@ public class AdFeedUtils {
}
private static boolean interval() {
if (System.currentTimeMillis() - lastTime > (100 * interval)) {
//判断大于多少秒
int interval = 10;
if (System.currentTimeMillis() - lastTime > (100L * interval)) {
return true;
} else {
return false;
@ -150,7 +154,10 @@ public class AdFeedUtils {
}
private static void load() {
LogK.e("mAdUnitId=" + mAdUnitId);
LogAd.e("mAdUnitId=" + mAdUnitId);
if (mAdUnitId.equals("0")) {
return;
}
if (adNativeLoader == null && interval()) {
lastTime = System.currentTimeMillis();
adNativeLoader = TTAdSdk.getAdManager().createAdNative(mContext);
@ -160,7 +167,7 @@ public class AdFeedUtils {
adNativeLoader.loadFeedAd(adSlot, new TTAdNative.FeedAdListener() {
@Override
public void onError(int i, String s) {
LogK.e("onError code = " + i + " msg = " + s);
LogAd.e("onError code = " + i + " msg = " + s);
removeAD();
if (adNativeLoader != null) {
adNativeLoader = null;
@ -178,14 +185,14 @@ public class AdFeedUtils {
}
mTTFeedAd = ads.get(0);
if (listenerAD != null && map.get(tag)) {
if (listenerAD != null && Boolean.TRUE.equals(map.get(tag))) {
listenerAD.success(ads.get(0));
listenerAD = null;
}
CacheADManager.addAdLoaded("feed", mAdUnitId, ads.get(0));
LogK.e("map.get(tag)=" + map.get(tag));
if (mIsLoadedAndShow && map.get(tag)) {
LogAd.e("map.get(tag)=" + map.get(tag));
if (mIsLoadedAndShow && Boolean.TRUE.equals(map.get(tag))) {
if (mFeedContainer != null) {
// new AdPreAndLevelUtils().setThisTime(page_type);
AdPreAndLevelUtils.setTagTime(tag, System.currentTimeMillis());
@ -202,14 +209,14 @@ public class AdFeedUtils {
private static void show() {
if (mTTFeedAd == null || mTTFeedAd.getMediationManager() == null) {
LogK.e("请先加载广告或等待广告加载完毕后再调用show方法");
LogAd.e("请先加载广告或等待广告加载完毕后再调用show方法");
// loadAD();
if (adNativeLoader != null) {
adNativeLoader = null;
}
return;
}
if (mTTFeedAd.getMediationManager().isExpress() && mFeedContainer != null && map.get(tag)) { //模板
if (mTTFeedAd.getMediationManager().isExpress() && mFeedContainer != null && Boolean.TRUE.equals(map.get(tag))) { //模板
mFeedContainer.setVisibility(View.VISIBLE);
showExpressView(mFeedContainer, mTTFeedAd);
} else {
@ -223,17 +230,17 @@ public class AdFeedUtils {
mTTFeedAd.setExpressRenderListener(new MediationExpressRenderListener() {
@Override
public void onRenderFail(View view, String s, int i) {
LogK.e("onRenderFail");
LogAd.e("onRenderFail");
}
@Override
public void onAdClick() {
LogK.e("onAdClick");
LogAd.e("onAdClick");
}
@Override
public void onAdShow() {
LogK.e("onAdShow");
LogAd.e("onAdShow");
if (listener != null) {
listener.success(true);
@ -247,23 +254,23 @@ public class AdFeedUtils {
}
if (new AdPreAndLevelUtils().getPre(page_type)) {
LogK.e("pre();");
LogAd.e("当前页ad预加载");
pre();
}
}
@Override
public void onRenderSuccess(View view, float v, float v1, boolean b) {
LogK.e("onRenderSuccess");
LogAd.e("onRenderSuccess");
mTTFeedAd.setDislikeCallback((Activity) mContext, new TTAdDislike.DislikeInteractionCallback() {
@Override
public void onShow() {
LogK.e("express dislike 点击show");
LogAd.e("express dislike 点击show");
}
@Override
public void onSelected(int i, String s, boolean b) {
LogK.e("\"express 点击 " + s);
LogAd.e("\"express 点击 " + s);
removeAdView();
if (mFeedContainer != null) {
mFeedContainer.setVisibility(View.GONE);
@ -273,7 +280,7 @@ public class AdFeedUtils {
@Override
public void onCancel() {
LogK.e("express dislike 点击了取消");
LogAd.e("express dislike 点击了取消");
}
});
@ -297,20 +304,18 @@ public class AdFeedUtils {
removeAD();
mTTFeedAd.render();
LogK.e("render");
LogAd.e("render");
}
private static void pre() {
if (BaseConstants.PRE_AD) {
String currentFeedID = LoopAd.getCurrentFeedID();
if (currentFeedID != null) {
if (!CacheADManager.getContentID(currentFeedID)) {
if (false) {//如果轮播就是true
LoopAd.AdFeedIdAdd();
}
mAdUnitId = LoopAd.getCurrentFeedID();
preAD(mContext, 20);
String currentFeedID = LoopAd.getCurrentFeedID();
if (currentFeedID != null) {
if (!CacheADManager.getContentID(currentFeedID)) {
if (false) {//如果轮播就是true
LoopAd.rotateFeedId();
}
mAdUnitId = LoopAd.getCurrentFeedID();
preAD(mContext, 20);
}
}
}
@ -326,7 +331,7 @@ public class AdFeedUtils {
}
private static void removeAdView() {
LogK.e("removeAdView");
LogAd.e("removeAdView");
if (mFeedContainer != null) {
mFeedContainer.removeAllViews();
}

View File

@ -2,7 +2,7 @@ package com.tfq.ad.ad;
import android.text.TextUtils;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import java.util.HashMap;
import java.util.Map;
@ -30,9 +30,9 @@ public class AdPreAndLevelUtils {
}
public boolean getPage_Interval(int page) {
LogK.e("page1_interval=" + page1_interval);
LogK.e("page2_interval=" + page2_interval);
LogK.e("page3_interval=" + page3_interval);
LogAd.e("page1_interval=" + page1_interval);
LogAd.e("page2_interval=" + page2_interval);
LogAd.e("page3_interval=" + page3_interval);
if (page == 1) {
return get_interval_page1();
} else if (page == 2) {
@ -44,9 +44,9 @@ public class AdPreAndLevelUtils {
}
public boolean getPage_Interval(String tag, int page_level) {
/*LogK.e("page1_interval=" + page1_interval);
LogK.e("page2_interval=" + page2_interval);
LogK.e("page3_interval=" + page3_interval);
/*LogAd.e("page1_interval=" + page1_interval);
LogAd.e("page2_interval=" + page2_interval);
LogAd.e("page3_interval=" + page3_interval);
if (page == 1) {
return get_interval_page1();
} else if (page == 2) {

View File

@ -13,18 +13,18 @@ import com.bytedance.sdk.openadsdk.mediation.MediationConstant;
import com.bytedance.sdk.openadsdk.mediation.ad.MediationAdSlot;
import com.bytedance.sdk.openadsdk.mediation.manager.MediationAdEcpmInfo;
import com.bytedance.sdk.openadsdk.mediation.manager.MediationBaseManager;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.library.utils.ToasterUtil;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
public class AdRewardUtils {
static long lastTime = 0;
private static Boolean requestAD = false;
private final String mAdUnitId = AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_REWARD);
//判断大于多少秒可以下一次开启
int interval = BaseConstants.ADV_Wait;
int interval = ADConstants.ADV_Wait;
private Listener listener;
private String mAdUnitId = BaseConstants.CODE_AD_CQP;
private TTRewardVideoAd mTTRewardVideoAd; // 插全屏广告对象
private TTAdNative.RewardVideoAdListener mRewardVideoListener; // 广告加载监听器
private TTRewardVideoAd.RewardAdInteractionListener mRewardVideoAdInteractionListener; // 广告展示监听器
@ -57,7 +57,7 @@ public class AdRewardUtils {
}
public static void logEcpmInfo(MediationAdEcpmInfo item) {
LogK.e("EcpmInfo: \n" +
LogAd.e("EcpmInfo: \n" +
"SdkName: " + item.getSdkName() + ",\n" +
"CustomSdkName: " + item.getCustomSdkName() + ",\n" +
"SlotId: " + item.getSlotId() + ",\n" +
@ -94,14 +94,15 @@ public class AdRewardUtils {
}
public void init(Context mContext, boolean load) {
boolean csj = true;
if (new ADUtils("GMRewardAd", mContext).regexSwitch() && csj) {
LogAd.e("mAdUnitId=" + mAdUnitId);
if (mAdUnitId.equals("0")) {
success();
return;
}
if (new ADStateUtils("GMRewardAd", mContext).regexSwitch()) {
loadRewardVideoAd(mContext);
} else {
if (listener != null) {
listener.success(false);
listener = null;
}
success();
}
}
@ -109,7 +110,7 @@ public class AdRewardUtils {
/** 1、创建AdSlot对象 */
AdSlot adslot = new AdSlot.Builder()
.setCodeId(BaseConstants.CODE_AD_REWARD)
.setCodeId(mAdUnitId)
.setOrientation(TTAdConstant.ORIENTATION_VERTICAL)
.setMediationAdSlot(new MediationAdSlot
.Builder()
@ -137,13 +138,13 @@ public class AdRewardUtils {
this.mRewardVideoListener = new TTAdNative.RewardVideoAdListener() {
@Override
public void onError(int i, String s) {
LogK.e("reward load fail: errCode: " + i + ", errMsg: " + s);
LogAd.e("reward load fail: errCode: " + i + ", errMsg: " + s);
}
@Override
public void onRewardVideoAdLoad(TTRewardVideoAd ttRewardVideoAd) {
LogK.e("reward load success");
LogAd.e("reward load success");
loadingDialog.cancel();
mTTRewardVideoAd = ttRewardVideoAd;
showRewardVideoAd(mContext);
@ -152,13 +153,13 @@ public class AdRewardUtils {
@Override
public void onRewardVideoCached() {
LogK.e("reward cached success");
LogAd.e("reward cached success");
}
@Override
public void onRewardVideoCached(TTRewardVideoAd ttRewardVideoAd) {
LogK.e("reward cached success 2");
LogAd.e("reward cached success 2");
mTTRewardVideoAd = ttRewardVideoAd;
showRewardVideoAd(mContext);
}
@ -169,35 +170,35 @@ public class AdRewardUtils {
@Override
public void onAdShow() {
LogK.e("reward show");
LogAd.e("reward show");
}
@Override
public void onAdVideoBarClick() {
LogK.e("reward click");
LogAd.e("reward click");
}
@Override
public void onAdClose() {
LogK.e("reward close");
LogAd.e("reward close");
}
@Override
public void onVideoComplete() {
LogK.e("reward onVideoComplete");
LogAd.e("reward onVideoComplete");
success();
}
@Override
public void onVideoError() {
LogK.e("reward onVideoError");
LogAd.e("reward onVideoError");
}
@Override
public void onRewardVerify(boolean b, int i, String s, int i1, String s1) {
LogK.e("reward onRewardVerify");
LogAd.e("reward onRewardVerify");
}
@Override
@ -212,9 +213,10 @@ public class AdRewardUtils {
@Override
public void onSkippedVideo() {
LogK.e("reward onSkippedVideo");
LogAd.e("reward onSkippedVideo");
if (!isRewardValid) {
ToasterUtil.show("看完视频才可以获得奖励",3);
// ToasterUtil.show("看完视频才可以获得奖励", 3);
success();
}
}
};
@ -223,7 +225,7 @@ public class AdRewardUtils {
// 广告加载成功后开始展示广告
private void showRewardVideoAd(Context mContext) {
if (mTTRewardVideoAd == null) {
LogK.e("请先加载广告或等待广告加载完毕后再调用show方法");
LogAd.e("请先加载广告或等待广告加载完毕后再调用show方法");
return;
}
@ -233,19 +235,22 @@ public class AdRewardUtils {
mTTRewardVideoAd.showRewardVideoAd((Activity) mContext);
}
public interface Listener {
void success(boolean b);
}
private void success() {
if (listener != null) {
if (isRewardValid) {
listener.success(true);
} else {
if (loadingDialog != null) {
loadingDialog.cancel();
}
listener.success(false);
}
listener = null;
}
}
public interface Listener {
void success(boolean b);
}
}

View File

@ -11,14 +11,18 @@ import com.bytedance.sdk.openadsdk.CSJAdError;
import com.bytedance.sdk.openadsdk.CSJSplashAd;
import com.bytedance.sdk.openadsdk.CSJSplashCloseType;
import com.bytedance.sdk.openadsdk.TTAdNative;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
import java.util.Objects;
public class AdSplashUtils {
private Context mContext;
private FrameLayout mSplashContainer;
private final Context mContext;
private final FrameLayout mSplashContainer;
private CSJSplashAd mCsjSplashAd;
private Listener listener;
private final String mAdUnitId = AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_SPLASH);
public interface Listener {
void success(long time);
@ -37,17 +41,22 @@ public class AdSplashUtils {
private CSJSplashAd.SplashAdListener mCSJSplashInteractionListener;
public void loadAndShowSplashAd() {
if (new ADUtils("GMSplashAd", mContext).regexSwitch()) {
LogK.e("init kaiping");
if (new ADStateUtils("GMSplashAd", mContext).regexSwitch()) {
LogAd.e("init kaiping");
init();
} else if (listener != null) {
listener.success(0);
} else {
finishAndBack(0);
}
}
private void init() {
new Handler(Looper.myLooper()).postDelayed(new Runnable() {
LogAd.e("mAdUnitId=" + mAdUnitId);
if (mAdUnitId.equals("0")) {
finishAndBack(0);
return;
}
new Handler(Objects.requireNonNull(Looper.myLooper())).postDelayed(new Runnable() {
@Override
public void run() {
finishAndBack(0);
@ -55,7 +64,7 @@ public class AdSplashUtils {
}, 9000);
AdSlot adSlot = new AdSlot.Builder()
.setCodeId(BaseConstants.CODE_AD_SPLASH)
.setCodeId(mAdUnitId)
.setImageAcceptedSize(UIUtils.getScreenWidthInPx(mContext), UIUtils.getAllScreenHeight(mContext))
.build();
TTAdNative adNativeLoader = TTAdManagerHolder.get().createAdNative(mContext);
@ -69,7 +78,7 @@ public class AdSplashUtils {
@Override
public void onSplashRenderSuccess(CSJSplashAd csjSplashAd) {
/** 5、渲染成功后展示广告 */
LogK.e("splash render success");
LogAd.e("splash render success");
mCsjSplashAd = csjSplashAd;
csjSplashAd.setSplashAdListener(mCSJSplashInteractionListener);
View splashView = csjSplashAd.getSplashView();
@ -79,7 +88,7 @@ public class AdSplashUtils {
}
public void onSplashLoadSuccess() {
LogK.e("splash load success");
LogAd.e("splash load success");
}
@Override
@ -91,7 +100,7 @@ public class AdSplashUtils {
@Override
public void onSplashLoadFail(CSJAdError csjAdError) {
LogK.e("splash load fail, errCode: " + csjAdError.getCode() + ", errMsg: " + csjAdError.getMsg());
LogAd.e("splash load fail, errCode: " + csjAdError.getCode() + ", errMsg: " + csjAdError.getMsg());
finishAndBack(0);
}
@ -99,7 +108,7 @@ public class AdSplashUtils {
@Override
public void onSplashRenderFail(CSJSplashAd csjSplashAd, CSJAdError csjAdError) {
LogK.e("splash render fail, errCode: " + csjAdError.getCode() + ", errMsg: " + csjAdError.getMsg());
LogAd.e("splash render fail, errCode: " + csjAdError.getCode() + ", errMsg: " + csjAdError.getMsg());
finishAndBack(0);
}
@ -110,26 +119,26 @@ public class AdSplashUtils {
@Override
public void onSplashAdShow(CSJSplashAd csjSplashAd) {
LogK.d("splash show");
LogAd.d("splash show");
}
@Override
public void onSplashAdClick(CSJSplashAd csjSplashAd) {
LogK.d("splash click");
LogAd.d("splash click");
}
@Override
public void onSplashAdClose(CSJSplashAd csjSplashAd, int closeType) {
if (closeType == CSJSplashCloseType.CLICK_SKIP) {
LogK.d("开屏广告点击跳过");
LogAd.d("开屏广告点击跳过");
finishAndBack(0);
} else if (closeType == CSJSplashCloseType.COUNT_DOWN_OVER) {
LogK.d("开屏广告点击倒计时结束");
LogAd.d("开屏广告点击倒计时结束");
finishAndBack(0);
} else if (closeType == CSJSplashCloseType.CLICK_JUMP) {
LogK.d("点击跳转");
LogAd.d("点击跳转");
}
}
};

View File

@ -1,20 +1,19 @@
package com.tfq.ad.ad;
import com.bytedance.sdk.openadsdk.TTFeedAd;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import java.util.ArrayList;
import java.util.List;
public class CacheADManager {
private static List<GMNativeADBean> mGMNativeADBean;
private static int contentID = -1;
public static void init() {
mGMNativeADBean = new ArrayList<>();
}
private static int contentID = -1;
public static List<GMNativeADBean> getAdBean() {
return mGMNativeADBean;
}
@ -60,9 +59,9 @@ public class CacheADManager {
case "feed":
while (getContentID(mAdUnitId)) {
mGMNativeADBean.remove(contentID);
LogK.e("移除该广告");
LogAd.e("移除该广告");
}
LogK.e("移除广告完成! ");
LogAd.e("移除广告完成! ");
break;
}
}

View File

@ -38,7 +38,7 @@ public class LoadingDialog extends Dialog {
}
private void setViews() {
contentView = inflater.inflate(R.layout.layout_dialog_loading, null);
contentView = inflater.inflate(R.layout.ad_dialog_loading, null);
setContentView(contentView);
ImageView loadingImageView = contentView.findViewById(R.id.loading_imageview);

View File

@ -1,94 +1,73 @@
package com.tfq.ad.ad;
import android.util.Log;
import android.os.Build;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import java.util.ArrayList;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.LogAd;
import java.util.Collections;
import java.util.List;
import java.util.stream.IntStream;
public class LoopAd {
private static final List<String> FEED_ADS = initFeedAds();
private static final List<String> SCREEN_ADS = Collections.singletonList("0");
private static final List<String> SPLASH_ADS = Collections.singletonList("0");
private static final List<String> DRAW_ADS = Collections.singletonList("0");
static List<String> feedAD = new ArrayList();
static List<String> newFeedAD = new ArrayList();
static int thisCurrentFeedID = 0;
static List<String> drawAD = new ArrayList();
static int thisCurrentDrawID = 0;
static List<String> screenAD = new ArrayList();
static int thisCurrentScreenID = 0;
static List<String> splashAD = new ArrayList();
static int thisCurrentSplashID = 0;
private static int currentFeedIndex = 0;
public LoopAd() {
init();
}
public static void AdFeedIdAdd() {
if (thisCurrentFeedID < newFeedAD.size() - 1) {
thisCurrentFeedID++;
} else {
thisCurrentFeedID = 0;
/**
* 添加进所有的信息流id
* @return
*/
private static List<String> initFeedAds() {
List<String> ads = null;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) {
ads = IntStream.rangeClosed(1, 3)
.mapToObj(i -> AdApp.getInstance().getSlotConfig(ADConstants.CODE_AD_FEED + i))
.filter(slot -> !"0".equals(slot))
.toList();
}
return ads.isEmpty() ? Collections.singletonList("0") : ads;
}
/**
* 用于循环切换广告索引实现广告轮播效果
* 信息流当前位置+1
*/
public static void rotateFeedId() {
currentFeedIndex = (currentFeedIndex < FEED_ADS.size() - 1) ?
currentFeedIndex + 1 : 0;
}
/**
* 返回当前的信息流id
* @return
*/
public static String getCurrentFeedID() {
return newFeedAD.get(thisCurrentFeedID);
return FEED_ADS.get(currentFeedIndex);
}
public static String getNextFeedID() {
int nextFeedID = 0;
if (thisCurrentFeedID < newFeedAD.size() - 1) {
nextFeedID = thisCurrentFeedID + 1;
} else {
nextFeedID = 0;
}
LogK.e("nextFeedID=" + nextFeedID);
return newFeedAD.get(nextFeedID);
/**
* 获取下一个信息流id
* @return
*/
public static String getNextFeedId() {
int nextIndex = (currentFeedIndex < FEED_ADS.size() - 1) ?
currentFeedIndex + 1 : 0;
LogAd.e("nextFeedIndex=" + nextIndex);
return FEED_ADS.get(nextIndex);
}
private void init() {
newFeedAD = new ArrayList();
newFeedAD.add(BaseConstants.csjIdFeed1);
LogK.e("TT BaseConstants.csjIdFeed1=" + BaseConstants.csjIdFeed1);
newFeedAD.add(BaseConstants.csjIdFeed2);
LogK.e("TT BaseConstants.csjIdFeed2=" + BaseConstants.csjIdFeed2);
if (feedAD.size() == 0) {
feedAD.add("0");
}
if (screenAD.size() == 0) {
screenAD.add("0");
}
if (splashAD.size() == 0) {
splashAD.add("0");
}
if (drawAD.size() == 0) {
drawAD.add("0");
}
/**
* 根据位置获取信息流广告
* @param position
* @return
*/
public static String getAdByPosition(int position) {
return (position >= 0 && position < FEED_ADS.size()) ?
FEED_ADS.get(position) : FEED_ADS.get(0);
}
public String GMNativeAd(int num) {
if (newFeedAD.size() > num) {
if (0 == num) {
String ad = newFeedAD.get(0);
if (ad != null) {
return ad;
} else {
return newFeedAD.get(0);
}
} else if (1 == num) {
String ad = newFeedAD.get(1);
if (ad != null) {
return ad;
} else {
return newFeedAD.get(0);
}
} else {
return newFeedAD.get(0);
}
} else {
return newFeedAD.get(0);
}
}
}

View File

@ -2,12 +2,13 @@ package com.tfq.ad.ad;
import android.app.Activity;
import android.content.Intent;
import android.util.Log;
import com.tfq.ad.ad.activity.AdSplashActivity;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.AppUtil;
import com.tfq.library.utils.DateUtils;
import com.tfq.library.utils.LogK;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.utils.AdAppUtil;
import com.tfq.ad.utils.DateUtils;
import com.tfq.ad.utils.LogAd;
import java.util.Timer;
import java.util.TimerTask;
@ -23,7 +24,7 @@ public class SplashUtils {
* @param mActivity
*/
public void startTimerTask(Activity mActivity) {
BaseConstants.request_splash_time = Long.parseLong(DateUtils.timeStamp());
ADConstants.request_splash_time = DateUtils.currentTimeStamp();
if (task == null) {
Timer timer = new Timer();
task = new TimerTask() {
@ -32,22 +33,23 @@ public class SplashUtils {
mActivity.runOnUiThread(new Runnable() {
@Override
public void run() {
long time = Long.parseLong(DateUtils.timeStamp()) - BaseConstants.request_splash_time;
if (!AppUtil.isRunningForeground(mActivity)) {//前台
// LogK.e("相差time=" + time);
if (Long.parseLong(DateUtils.timeStamp()) - BaseConstants.request_splash_time >= 20) {
LogK.e("应当开启开屏页");
if (!BaseConstants._isShow) {
BaseConstants._isShow = true;
if (new ADUtils("GMSplashAd", mActivity).regexSwitch()) {
long time = DateUtils.currentTimeStamp() - ADConstants.request_splash_time;
if (!AdAppUtil.isRunningForeground(mActivity)) {//前台
LogAd.e("APP处于前台状态");
// LogAd.e("相差time=" + time);
if (DateUtils.currentTimeStamp() - ADConstants.request_splash_time >= 20) {
LogAd.e("应当开启开屏页");
if (!ADConstants._isShow) {
ADConstants._isShow = true;
if (new ADStateUtils("GMSplashAd", mActivity).regexSwitch()) {
Intent intent = new Intent(mActivity, AdSplashActivity.class);
mActivity.startActivity(intent);
}
}
}
BaseConstants.request_splash_time = Long.parseLong(DateUtils.timeStamp());
ADConstants.request_splash_time = DateUtils.currentTimeStamp();
} else {
LogK.e("APP后台状态time=" + time);
LogAd.e("APP后台状态time=" + time + "");
}
}
});

View File

@ -10,9 +10,9 @@ import com.bytedance.sdk.openadsdk.TTCustomController;
import com.bytedance.sdk.openadsdk.mediation.init.MediationConfig;
import com.bytedance.sdk.openadsdk.mediation.init.MediationConfigUserInfoForSegment;
import com.bytedance.sdk.openadsdk.mediation.init.MediationPrivacyConfig;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import org.json.JSONException;
import org.json.JSONObject;
@ -46,11 +46,19 @@ public class TTAdManagerHolder {
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
if (adInitState != 1) {
if (adInitState != 1 && adSuccess != null) {
adSuccess.error();
adSuccess = null;
}
}
}, 5000);
}, 7000);
if (!sInit) {
LogAd.e("没有初始化, 直接回调错误");
adSuccess.error();
adSuccess = null;
}
}
public static TTAdManager get() {
@ -62,6 +70,10 @@ public class TTAdManagerHolder {
doInit(context);
}
public static void init_not() {
}
//step1:接入网盟广告sdk的初始化操作详情见接入文档和穿山甲平台说明
private static void doInit(Context context) {
if (sInit) {
@ -91,7 +103,7 @@ public class TTAdManagerHolder {
TTAdSdk.start(new TTAdSdk.Callback() {
@Override
public void success() {
LogK.i("success: " + TTAdSdk.isInitSuccess());
LogAd.i("success: " + TTAdSdk.isInitSuccess());
// startActivity(context);
adInitState = 1;
if (adSuccess != null) {
@ -102,7 +114,7 @@ public class TTAdManagerHolder {
@Override
public void fail(int code, String msg) {
sStart = false;
LogK.i("fail: code = " + code + " msg = " + msg);
LogAd.i("fail: code = " + code + " msg = " + msg);
adInitState = 2;
if (adSuccess != null) {
adSuccess.error();
@ -114,11 +126,11 @@ public class TTAdManagerHolder {
private static TTAdConfig buildConfig(Context context) {
LogK.e("TT BaseConstants.CSJ_ID="+ BaseConstants.CSJ_ID);
LogAd.e("TT CSJID=" + AdApp.getInstance().getSlotConfig(ADConstants.AD_CSJID));
return new TTAdConfig.Builder()
/**
* 需要替换成在媒体平台申请的appID 切勿直接复制
*/.appId(BaseConstants.CSJ_ID).appName(BaseConstants.APP_NAME).paid(true)
*/.appId(AdApp.getInstance().getSlotConfig(ADConstants.AD_CSJID)).appName(AdApp.getInstance().getAppName()).paid(true)
/**
* 上线前需要关闭debug开关否则会影响性能
*/.debug(false)
@ -135,7 +147,7 @@ public class TTAdManagerHolder {
JSONObject jsonObject = null;
//读取json文件本地缓存的配置
try {
jsonObject = new JSONObject(getJson("site_config_" + BaseConstants.CSJ_ID, context));
jsonObject = new JSONObject(getJson("site_config_" + AdApp.getInstance().getSlotConfig(ADConstants.AD_CSJID), context));
} catch (JSONException e) {
e.printStackTrace();
}
@ -161,7 +173,7 @@ public class TTAdManagerHolder {
MediationConfigUserInfoForSegment userInfo = new MediationConfigUserInfoForSegment();
userInfo.setUserId("msdk-demo");
userInfo.setGender(MediationConfigUserInfoForSegment.GENDER_MALE);
userInfo.setChannel(BaseConstants.CHANNEL);
userInfo.setChannel(AdApp.getInstance().getChannel());
userInfo.setSubChannel("msdk-sub-channel");
userInfo.setAge(999);
userInfo.setUserValueGroup("msdk-demo-user-value-group");
@ -178,8 +190,8 @@ public class TTAdManagerHolder {
@Override
public boolean isCanUseLocation() {
boolean b = true;
String channel = BaseConstants.CHANNEL;
LogK.d("TT channel=" + channel);
String channel = AdApp.getInstance().getChannel();
LogAd.d("TT channel=" + channel);
if (channel != null) {
if (channel.equals("oppo")) {
b = false;
@ -235,8 +247,8 @@ public class TTAdManagerHolder {
@Override
public boolean isCanUseOaid() {
boolean b = true;
String channel = BaseConstants.CHANNEL;
LogK.d("TT channel2=" + channel);
String channel = AdApp.getInstance().getChannel();
LogAd.d("TT channel2=" + channel);
if (channel != null) {
if (channel.equals("honor")) {
b = false;
@ -255,8 +267,8 @@ public class TTAdManagerHolder {
@Override
public boolean alist() {
boolean b = true;
String channel = BaseConstants.CHANNEL;
LogK.d("TT channel3=" + channel);
String channel = AdApp.getInstance().getChannel();
LogAd.d("TT channel3=" + channel);
if (channel != null) {
if (channel.equals("ali") || channel.equals("oppo") || channel.equals("vivo") || channel.equals("huawei")
|| channel.equals("honor") || channel.equals("xiaomi")) {

View File

@ -1,48 +1,59 @@
package com.tfq.ad.ad.activity;
import android.app.Activity;
import android.os.Bundle;
import android.view.KeyEvent;
import android.widget.FrameLayout;
import android.widget.ImageView;
import com.gyf.immersionbar.ImmersionBar;
import com.tfq.ad.ad.AdSplashUtils;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.base.BaseActivity;
import com.tfq.library.utils.AppUtil;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.ad.utils.AdAppUtil;
import com.tfq.libraryad.R;
public class AdSplashActivity extends BaseActivity {
import androidx.annotation.Nullable;
public class AdSplashActivity extends Activity {
FrameLayout mSplashContainer;
ImageView ivSplash;
AdSplashUtils mAdSplashManager;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(getLayoutId());
initView();
initData();
ImmersionBar.with(this)
.transparentStatusBar() //不写也可以默认就是透明色
// .statusBarDarkFont(statusBarDarkFont)
// .navigationBarColor(ADConstants.navigationBarColor)
// .keyboardEnable(true)
.init();
}
protected int getLayoutId() {
return R.layout.ad_splash;
}
@Override
protected void initView() {
AppUtil.setHideBar_StatusAndNavigation(this);
AdAppUtil.setHideBar_StatusAndNavigation(this);
setContentView(R.layout.ad_splash);
mSplashContainer = findViewById(R.id.frameLayout);
ivSplash = findViewById(R.id.iv_splash);
ivSplash.setBackgroundResource(BaseConstants.appSplash);
}
@Override
protected void initData(Bundle savedInstanceState) {
initData();
ivSplash.setBackgroundResource(AdApp.getInstance().getSplash());
}
protected void initData() {
BaseConstants._isShow = true;
ADConstants._isShow = true;
mAdSplashManager = new AdSplashUtils(this, mSplashContainer, new AdSplashUtils.Listener() {
@Override
public void success(long time) {
finish();
BaseConstants._isShow = false;
ADConstants._isShow = false;
}
});
}

View File

@ -10,7 +10,7 @@ import com.bytedance.sdk.openadsdk.mediation.custom.MediationCustomServiceConfig
import com.qq.e.ads.interstitial2.UnifiedInterstitialAD;
import com.qq.e.ads.interstitial2.UnifiedInterstitialADListener;
import com.qq.e.comm.util.AdError;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import java.util.concurrent.Callable;
import java.util.concurrent.Future;
@ -39,13 +39,13 @@ public class GdtCustomerInterstitial extends MediationCustomInterstitialLoader {
@Override
public void onADReceive() {
isLoadSuccess = true;
LogK.i(TAG + "onADReceive");
LogAd.i(TAG + "onADReceive");
if (isClientBidding()) { //bidding类型广告
double ecpm = mUnifiedInterstitialAD.getECPM();//当无权限调用该接口时SDK会返回错误码-1
if (ecpm < 0) {
ecpm = 0;
}
LogK.e(TAG + " ecpm:" + ecpm);
LogAd.e(TAG + " ecpm:" + ecpm);
callLoadSuccess(ecpm);
} else {//普通类型广告
callLoadSuccess();
@ -54,14 +54,14 @@ public class GdtCustomerInterstitial extends MediationCustomInterstitialLoader {
@Override
public void onVideoCached() {
LogK.i(TAG + "onVideoCached");
LogAd.i(TAG + "onVideoCached");
}
@Override
public void onNoAD(AdError adError) {
isLoadSuccess = false;
if (adError != null) {
LogK.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
LogAd.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
callLoadFail(adError.getErrorCode(), adError.getErrorMsg());
} else {
callLoadFail(40000, "no ad");
@ -70,31 +70,31 @@ public class GdtCustomerInterstitial extends MediationCustomInterstitialLoader {
@Override
public void onADOpened() {
LogK.i(TAG + "onADOpened");
LogAd.i(TAG + "onADOpened");
callInterstitialAdOpened();
}
@Override
public void onADExposure() {
LogK.i(TAG + "onADExposure");
LogAd.i(TAG + "onADExposure");
callInterstitialShow();
}
@Override
public void onADClicked() {
LogK.i(TAG + "onADClicked");
LogAd.i(TAG + "onADClicked");
callInterstitialAdClick();
}
@Override
public void onADLeftApplication() {
LogK.i(TAG + "onADLeftApplication");
LogAd.i(TAG + "onADLeftApplication");
callInterstitialAdLeftApplication();
}
@Override
public void onADClosed() {
LogK.i(TAG + "onADClosed");
LogAd.i(TAG + "onADClosed");
callInterstitialClosed();
}
@ -124,7 +124,7 @@ public class GdtCustomerInterstitial extends MediationCustomInterstitialLoader {
@Override
public void showAd(Activity activity) {
LogK.i(TAG + "自定义的showAd");
LogAd.i(TAG + "自定义的showAd");
/**
* 先切子线程再在子线程中切主线程进行广告展示
*/
@ -173,19 +173,19 @@ public class GdtCustomerInterstitial extends MediationCustomInterstitialLoader {
@Override
public void onPause() {
super.onPause();
LogK.i(TAG + "onPause");
LogAd.i(TAG + "onPause");
}
@Override
public void onResume() {
super.onResume();
LogK.i(TAG + "onResume");
LogAd.i(TAG + "onResume");
}
@Override
public void onDestroy() {
super.onDestroy();
LogK.i(TAG + "onDestroy");
LogAd.i(TAG + "onDestroy");
/**
* 在子线程中进行广告销毁

View File

@ -13,7 +13,7 @@ import com.qq.e.ads.nativ.NativeExpressADView;
import com.qq.e.ads.nativ.NativeUnifiedAD;
import com.qq.e.ads.nativ.NativeUnifiedADData;
import com.qq.e.comm.util.AdError;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import java.util.ArrayList;
import java.util.HashMap;
@ -32,12 +32,12 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
/**
* 在子线程中进行广告加载
*/
LogK.e(TAG + "load gdt custom native ad-----");
LogAd.e(TAG + "load gdt custom native ad-----");
ThreadUtils.runOnThreadPool(new Runnable() {
@Override
public void run() {
if (isNativeAd()) {
LogK.i(TAG + "自渲染");
LogAd.i(TAG + "自渲染");
//自渲染类型
NativeUnifiedAD nativeUnifiedAD = null;
NativeADUnifiedListener nativeADUnifiedListener = new NativeADUnifiedListener() {
@ -58,7 +58,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
if (ecpm < 0) {
ecpm = 0;
}
LogK.e(TAG + "ecpm:" + ecpm);
LogAd.e(TAG + "ecpm:" + ecpm);
gdtNativeAd.setBiddingPrice(ecpm); //回传竞价广告价格
}
tempList.add(gdtNativeAd);
@ -69,7 +69,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onNoAD(AdError adError) {
if (adError != null) {
LogK.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
LogAd.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
callLoadFail(adError.getErrorCode(), adError.getErrorMsg());
} else {
callLoadFail(40000, "no ad");
@ -92,7 +92,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
}
nativeUnifiedAD.loadData(1);
} else if (isExpressRender()) {
LogK.i(TAG + "模板");
LogAd.i(TAG + "模板");
//模板类型
NativeExpressAD nativeExpressAD = null;
NativeExpressAD.NativeExpressADListener nativeExpressADListener = new NativeExpressAD.NativeExpressADListener() {
@ -115,7 +115,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
if (ecpm < 0) {
ecpm = 0;
}
LogK.e(TAG + " ecpm:" + ecpm);
LogAd.e(TAG + " ecpm:" + ecpm);
gdtNativeAd.setBiddingPrice(ecpm); //回传竞价广告价格
}
mListenerMap.put(feedAd, gdtNativeAd);
@ -126,7 +126,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onRenderFail(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onRenderFail");
LogAd.i(TAG + "onRenderFail");
GdtNativeExpressAd gdtNativeAd = mListenerMap.get(nativeExpressADView);
if (gdtNativeAd != null) {
gdtNativeAd.callRenderFail(nativeExpressADView, 99999, "render fail");
@ -135,7 +135,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onRenderSuccess(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onRenderSuccess");
LogAd.i(TAG + "onRenderSuccess");
GdtNativeExpressAd gdtNativeAd = mListenerMap.get(nativeExpressADView);
if (gdtNativeAd != null) {
gdtNativeAd.callRenderSuccess(ADSize.FULL_WIDTH, ADSize.AUTO_HEIGHT);
@ -144,7 +144,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onADExposure(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onADExposure");
LogAd.i(TAG + "onADExposure");
GdtNativeExpressAd gdtNativeAd = mListenerMap.get(nativeExpressADView);
if (gdtNativeAd != null) {
gdtNativeAd.callAdShow();
@ -153,7 +153,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onADClicked(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onADClicked");
LogAd.i(TAG + "onADClicked");
GdtNativeExpressAd gdtNativeAd = mListenerMap.get(nativeExpressADView);
if (gdtNativeAd != null) {
gdtNativeAd.callAdClick();
@ -162,7 +162,7 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onADClosed(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onADClosed");
LogAd.i(TAG + "onADClosed");
GdtNativeExpressAd gdtNativeAd = mListenerMap.get(nativeExpressADView);
if (gdtNativeAd != null) {
gdtNativeAd.onDestroy();
@ -172,13 +172,13 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
@Override
public void onADLeftApplication(NativeExpressADView nativeExpressADView) {
LogK.i(TAG + "onADLeftApplication");
LogAd.i(TAG + "onADLeftApplication");
}
@Override
public void onNoAD(AdError adError) {
if (adError != null) {
LogK.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
LogAd.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
callLoadFail(adError.getErrorCode(), adError.getErrorMsg());
} else {
callLoadFail(40000, "no ad");
@ -193,10 +193,10 @@ public class GdtCustomerNative extends MediationCustomNativeLoader {
}
nativeExpressAD.loadAD(1);
} else {
LogK.i(TAG + "其他类型");
LogAd.i(TAG + "其他类型");
//其他类型开发者如果有需要请在平台自行配置json,然后通过 serviceConfig.getCustomAdapterJson() 获取配置
LogK.i(TAG + "1111111111111111111111111111111111111111111111");
LogK.i(TAG + "serviceConfig.getCustomAdapterJson()=" + serviceConfig.getCustomAdapterJson());
LogAd.i(TAG + "1111111111111111111111111111111111111111111111");
LogAd.i(TAG + "serviceConfig.getCustomAdapterJson()=" + serviceConfig.getCustomAdapterJson());
}
}
});

View File

@ -11,7 +11,7 @@ import com.bytedance.sdk.openadsdk.mediation.custom.MediationCustomServiceConfig
import com.qq.e.ads.splash.SplashAD;
import com.qq.e.ads.splash.SplashADListener;
import com.qq.e.comm.util.AdError;
import com.tfq.library.utils.LogK;
import com.tfq.ad.utils.LogAd;
import java.util.concurrent.Callable;
import java.util.concurrent.Future;
@ -32,14 +32,14 @@ public class GdtCustomerSplash extends MediationCustomSplashLoader {
/**
* 在子线程中进行广告加载
*/
LogK.e(TAG + " load gdt custom splash ad-----");
LogAd.e(TAG + " load gdt custom splash ad-----");
ThreadUtils.runOnThreadPool(new Runnable() {
@Override
public void run() {
SplashADListener splashADListener = new SplashADListener() {
@Override
public void onADDismissed() {
LogK.i(TAG + "onADDismissed");
LogAd.i(TAG + "onADDismissed");
callSplashAdDismiss();
}
@ -47,7 +47,7 @@ public class GdtCustomerSplash extends MediationCustomSplashLoader {
public void onNoAD(AdError adError) {
isLoadSuccess = false;
if (adError != null) {
LogK.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
LogAd.i(TAG + "onNoAD errorCode = " + adError.getErrorCode() + " errorMessage = " + adError.getErrorMsg());
callLoadFail(adError.getErrorCode(), adError.getErrorMsg());
} else {
callLoadFail(40000, "no ad");
@ -56,29 +56,29 @@ public class GdtCustomerSplash extends MediationCustomSplashLoader {
@Override
public void onADPresent() {
LogK.i(TAG + "onADPresent");
LogAd.i(TAG + "onADPresent");
}
@Override
public void onADClicked() {
LogK.i(TAG + "onADClicked");
LogAd.i(TAG + "onADClicked");
callSplashAdClicked();
}
@Override
public void onADTick(long l) {
LogK.i(TAG + "onADTick");
LogAd.i(TAG + "onADTick");
}
@Override
public void onADExposure() {
LogK.i(TAG + "onADExposure");
LogAd.i(TAG + "onADExposure");
callSplashAdShow();
}
@Override
public void onADLoaded(long expireTimestamp) {
LogK.i(TAG + "onADLoaded");
LogAd.i(TAG + "onADLoaded");
long timeIntervalSec = expireTimestamp - SystemClock.elapsedRealtime();
if (timeIntervalSec > 1000) {
isLoadSuccess = true;
@ -87,7 +87,7 @@ public class GdtCustomerSplash extends MediationCustomSplashLoader {
if (ecpm < 0) {
ecpm = 0;
}
LogK.e(TAG + " ecpm:" + ecpm);
LogAd.e(TAG + " ecpm:" + ecpm);
callLoadSuccess(ecpm); //bidding广告成功回调回传竞价广告价格
} else { //普通类型广告
callLoadSuccess();
@ -130,19 +130,19 @@ public class GdtCustomerSplash extends MediationCustomSplashLoader {
@Override
public void onPause() {
super.onPause();
LogK.i(TAG + "onPause");
LogAd.i(TAG + "onPause");
}
@Override
public void onResume() {
super.onResume();
LogK.i(TAG + "onResume");
LogAd.i(TAG + "onResume");
}
@Override
public void onDestroy() {
super.onDestroy();
LogK.i(TAG + "onDestroy");
LogAd.i(TAG + "onDestroy");
mSplashAD = null;
}

View File

@ -0,0 +1,66 @@
package com.tfq.ad.app;
public class ADConstants {
public static boolean AD_APP_DEBUG_PRINT = false;
public static boolean _isShow;
// 1.开屏 2.激励视频 3.信息流 4.插全屏 5.banner 6.draw信息流
public static boolean AD_SPLASH = false;//开屏广告
public static boolean AD_REWARD = false;//激励视频
public static boolean AD_CQP = false;//插全屏广告
public static boolean AD_NATIVE = false;//原生信息流广告
public static boolean AD_BANNER = false;//banner广告
public static boolean AD_DRAW = false;//draw信息流广告
public static int ADV_Wait = 60;//插全屏两个相差时间
public static boolean adv_csj = true;//穿山甲正常
public static long request_splash_time = 30;
public static boolean AD_Switch_Requested = false;//请求过广告开关
public static String CODE_AD_FEED = "CODE_AD_FEED";
/**
* 自定义APP_ID
*/
public final static String AD_APPID = "APPID";
/**
* 自定义穿山甲ID
*/
public final static String AD_CSJID = "CSJID";
/**
* 自定义穿山甲开屏ID
*/
public final static String AD_CODE_SPLASH = "AD_CODE_SPLASH";
/**
* 自定义穿山甲插全屏ID
*/
public final static String AD_CODE_CQP = "AD_CODE_CQP";
/**
* 自定义穿山甲激励视频ID
*/
public final static String AD_CODE_REWARD = "AD_CODE_REWARD";
/**
* 自定义穿山甲信息流1_ID
*/
public final static String AD_CODE_FEED1 = "AD_CODE_FEED1";
/**
* 自定义穿山甲信息流2_ID
*/
public final static String AD_CODE_FEED2 = "AD_CODE_FEED2";
/**
* 自定义穿山甲信息流3_ID
*/
public final static String AD_CODE_FEED3 = "AD_CODE_FEED3";
/**
* 自定义穿山甲bannerID
*/
public final static String AD_CODE_BANNER = "AD_CODE_BANNER";
/**
* 自定义穿山甲DRAW_ID
*/
public final static String AD_CODE_DRAW = "AD_CODE_DRAW";
/**
* 穿山甲广告是否关闭,true:无广告;false:有广告;
*/
public final static String NO_AD = "NO_AD";
}

View File

@ -1,75 +1,124 @@
package com.tfq.ad.app;
import android.app.Activity;
import android.app.Application;
import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.os.Bundle;
import com.tfq.ad.ad.LoopAd;
import com.tfq.library.app.IConstituteApp;
import com.tfq.ad.ad.CacheADManager;
import com.tfq.ad.ad.TTAdManagerHolder;
import com.tfq.ad.utils.LogAd;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.Collections;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Objects;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
public final class AdApp {
private static volatile AdApp instance;
private final Context context;
private final String appName;
private final String channel;
private final int splashConfig;
private final Map<String, String> adSlots;
/**
* Created by Administrator on 2016/10/28.
*/
public class AdApp implements IConstituteApp {
public static Activity activityTop;
private static Context mContext;
private static AdApp instance;
public Application application;
private AdApp(Builder builder) {
this.context = builder.context;
this.appName = builder.appName;
this.channel = builder.channel;
this.splashConfig = builder.splashConfig;
this.adSlots = Collections.unmodifiableMap(new HashMap<>(builder.adSlots));
}
private static String validateNonEmpty(String value) {
if (value == null || value.trim().isEmpty()) {
return "";
// throw new IllegalArgumentException("Parameter cannot be empty");
}
return value;
}
public static AdApp getInstance() {
if (instance == null) {
throw new IllegalStateException("Call Builder.initialize() first");
}
return instance;
}
public static Context getContext() {
return mContext;
// 参数暴露接口
public String getAppName() {
return appName;
}
public static Activity getActivityTop() {
return activityTop;
public String getChannel() {
return channel;
}
public static String getChannel() {
try {
PackageManager pm = mContext.getPackageManager();
ApplicationInfo appInfo = pm.getApplicationInfo(mContext.getPackageName(), PackageManager.GET_META_DATA);
return appInfo.metaData.getString("UMENG_CHANNEL");
} catch (PackageManager.NameNotFoundException ignored) {
public int getSplash() {
return splashConfig;
}
public String getSlotConfig(String slotType) {
return adSlots.getOrDefault(slotType, "0"); // 未配置返回默认值
}
public boolean isSlotConfig(String slotType) {
return Boolean.parseBoolean(adSlots.getOrDefault(slotType, String.valueOf(false))); // 未配置返回默认值
}
public static class Builder {
private final Context context;
private final String appName;
private final String channel;
private final int splashConfig;
private final Map<String, String> adSlots = new LinkedHashMap<>();
/**
* 必传的几个选项
* @param ctx
* @param name
* @param channel
* @param splash
*/
public Builder(Context ctx, String name, String channel, int splash) {
this.context = Objects.requireNonNull(ctx);
this.appName = validateNonEmpty(name);
this.channel = validateNonEmpty(channel);
this.splashConfig = splash;
}
return "other";
}
public static String getJson(String fileName, Context context) {
StringBuilder stringBuilder = new StringBuilder();
try {
InputStream is = context.getAssets().open(fileName);
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(is));
String line;
while ((line = bufferedReader.readLine()) != null) {
stringBuilder.append(line);
public Builder addSlot(String slotType, String config) {
if (slotType != null) {
adSlots.put(slotType, config != null ? config : "0"); // 默认值处理
}
} catch (IOException e) {
e.printStackTrace();
return this;
}
return stringBuilder.toString();
}
@Override
public void onCreate(Application application) {
mContext = application.getApplicationContext();
instance = this;
this.application = application;
public synchronized void initialize() {
if (instance == null) {
instance = new AdApp(this);
}
new LoopAd();
// 初始化ad SDK
if (!getInstance().getSlotConfig(ADConstants.AD_CSJID).equals("0")) {
CacheADManager.init();
if (!AdApp.getInstance().isSlotConfig(ADConstants.NO_AD)) {
LogAd.e("初始化AD");
initAdSdk();
}else {
TTAdManagerHolder.init_not();
}
}
try {
if (getInstance().getChannel() != null && getInstance().getChannel().equals("other")) {
LogAd.setDebug(true);
}
} catch (Exception e) {
e.printStackTrace();
}
}
private void initAdSdk() {
TTAdManagerHolder.init(context);
}
}
}

View File

@ -1,11 +0,0 @@
package com.tfq.ad.app;
public class AdUrlCenter {
//base url
public static String BASE_URL = "http://www.90000li.com/app-api/";
//根据广告平台id获取开关
public static String advFlag = BASE_URL + "jwl/app-advertisement/flag";
//问题反馈
public static String feedback = BASE_URL + "jwl/feedback/add";
}

View File

@ -1,36 +0,0 @@
package com.tfq.ad.app;
import android.widget.Toast;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.app.LibraryApp;
import com.tfq.library.utils.AppUtil;
import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.logging.HttpLoggingInterceptor;
public class MyOkHttp {
private static OkHttpClient client;
public static OkHttpClient myClient() {
Interceptor logInterceptor;
if (BaseConstants.BASE_APP_DEBUG_PRINT) {
logInterceptor = new HttpLoggingInterceptor(new HttpLog()).setLevel(HttpLoggingInterceptor.Level.BODY);
} else {
logInterceptor = new HttpLoggingInterceptor(new HttpLog()).setLevel(HttpLoggingInterceptor.Level.NONE);
}
if (client == null) {
client = new OkHttpClient()
.newBuilder()
.addNetworkInterceptor(logInterceptor)
.build();
}
if (!AppUtil.connectStatus()) {
Toast.makeText(LibraryApp.getContext(), "无网络连接", Toast.LENGTH_SHORT).show();
}
return client;
}
}

View File

@ -1,98 +0,0 @@
package com.tfq.ad.bean;
public class AdvBean {
private int code;
private DataDTO data;
private String msg;
public int getCode() {
return code;
}
public void setCode(int code) {
this.code = code;
}
public DataDTO getData() {
return data;
}
public void setData(DataDTO data) {
this.data = data;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
public static class DataDTO {
private String adv1Flag;
private String adv2Flag;
private String adv3Flag;
private String adv4Flag;
private String adv5Flag;
private String adv6Flag;
private int adv4Wait;
public String getAdv1Flag() {
return adv1Flag;
}
public void setAdv1Flag(String adv1Flag) {
this.adv1Flag = adv1Flag;
}
public String getAdv2Flag() {
return adv2Flag;
}
public void setAdv2Flag(String adv2Flag) {
this.adv2Flag = adv2Flag;
}
public String getAdv3Flag() {
return adv3Flag;
}
public void setAdv3Flag(String adv3Flag) {
this.adv3Flag = adv3Flag;
}
public String getAdv4Flag() {
return adv4Flag;
}
public void setAdv4Flag(String adv4Flag) {
this.adv4Flag = adv4Flag;
}
public String getAdv5Flag() {
return adv5Flag;
}
public void setAdv5Flag(String adv5Flag) {
this.adv5Flag = adv5Flag;
}
public String getAdv6Flag() {
return adv6Flag;
}
public void setAdv6Flag(String adv6Flag) {
this.adv6Flag = adv6Flag;
}
public int getAdv4Wait() {
return adv4Wait;
}
public void setAdv4Wait(int adv4Wait) {
this.adv4Wait = adv4Wait;
}
}
}

View File

@ -1,105 +0,0 @@
package com.tfq.ad.bean;
import android.text.TextUtils;
import com.tfq.ad.app.AdUrlCenter;
import com.tfq.ad.app.MyOkHttp;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.AppUtil;
import com.tfq.library.utils.LogK;
import org.json.JSONObject;
import java.io.IOException;
import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.MediaType;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;
public class UserInfo {
private final OkHttpClient client = MyOkHttp.myClient();
private void regexDate(Response response, Success listener) {
try {
String data = response.body().string();
LogK.e(data);
JSONObject jsonObject = new JSONObject(data);
String code = jsonObject.getString("code");
String msg = "";
try {
msg = jsonObject.getString("message");
} catch (Exception e) {
e.printStackTrace();
try {
msg = jsonObject.getString("msg");
} catch (Exception e1) {
e1.printStackTrace();
msg = "";
}
}
if (!TextUtils.isEmpty(code)) {
switch (code) {
case "200":
case "0":
listener.Success(data, msg);
break;
default:
listener.fail(Integer.parseInt(code), msg);
break;
}
} else {
listener.fail(BaseConstants.URL_REQUEST_ERROR, msg);
}
} catch (Exception e) {
e.printStackTrace();
listener.fail(BaseConstants.URL_REQUEST_ERROR, BaseConstants.URL_REQUEST_ERROR + "");
}
}
public void getAdvertising(Success listener) {
new Thread() {
@Override
public void run() {
super.run();
String marketKey = "";
if (!TextUtils.isEmpty(BaseConstants.CHANNEL)) {
marketKey = BaseConstants.CHANNEL;
}
String url = AdUrlCenter.advFlag;
String json = "{" +
" \"appId\":\"" + BaseConstants.APP_ID + "\"," +
" \"appPacketname\": \"" + AppUtil.getPackageName() + "\"," +
" \"channel\": \"" + marketKey + "\"," +
" \"appVersion\": \"" + AppUtil.getAppVersionCode() + "\"" +
"}";
final Request request = new Request.Builder()
.url(url)
.post(RequestBody.create(MediaType.parse("application/json; charset=utf-8"), json))
.build();
Call call = client.newCall(request);
call.enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
listener.fail(BaseConstants.URL_REQUEST_ERROR, "");
}
@Override
public void onResponse(Call call, Response response) {
regexDate(response, listener);
}
});
}
}.start();
}
public interface Success {
void Success(String data, String msg);
void fail(int num, String msg);
}
}

View File

@ -0,0 +1,51 @@
package com.tfq.ad.utils;
import android.app.Activity;
import android.app.ActivityManager;
import android.content.Context;
import com.gyf.immersionbar.BarHide;
import com.gyf.immersionbar.ImmersionBar;
import java.util.List;
public class AdAppUtil {
/**
* 隐藏状态栏和导航栏带安全校验
*/
public static void setHideBar_StatusAndNavigation(Context context) {
if (!(context instanceof Activity)) {
LogAd.e("Context must be Activity instance");
return;
}
try {
ImmersionBar.with((Activity) context)
.hideBar(BarHide.FLAG_HIDE_BAR)
.init();
} catch (Exception e) {
LogAd.e("Hide bar failed: " + e.getMessage());
}
}
/**
* 判断是否处于后台行为
*/
public static boolean isRunningForeground(Context mContext) {
try {
ActivityManager activityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
List<ActivityManager.RunningAppProcessInfo> appProcesses = activityManager.getRunningAppProcesses();
for (ActivityManager.RunningAppProcessInfo appProcess : appProcesses) {
if (appProcess.processName.equals(mContext.getPackageName())) {
return appProcess.importance != ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND;
}
}
} catch (Exception e) {
e.printStackTrace();
return false;
}
return false;
}
}

View File

@ -0,0 +1,75 @@
package com.tfq.ad.utils;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
public final class DateUtils {
private static final String DEFAULT_PATTERN = "yyyy-MM-dd HH:mm:ss";
private static final ConcurrentMap<String, ThreadLocal<SimpleDateFormat>> FORMATTER_CACHE = new ConcurrentHashMap<>();
private DateUtils() {
throw new AssertionError("Utility class cannot be instantiated");
}
/**
* 获取当前时间戳()
*/
public static long currentTimeStamp() {
return System.currentTimeMillis() / 1000;
}
/**
* 获取当前格式化时间默认格式
*/
public static String currentFormattedTime() {
return formatTimestamp(currentTimeStamp());
}
/**
* 获取当前格式化时间自定义格式
*/
public static String currentFormattedTime(String pattern) {
return formatTimestamp(currentTimeStamp(), pattern);
}
/**
* 时间戳转日期字符串默认格式
*/
public static String formatTimestamp(long timestamp) {
return formatTimestamp(timestamp, DEFAULT_PATTERN);
}
/**
* 时间戳转日期字符串自定义格式
*/
public static String formatTimestamp(long timestamp, String pattern) {
return getFormatter(pattern).format(new Date(timestamp * 1000));
}
/**
* 日期字符串转时间戳默认格式
*/
public static long parseToTimestamp(String dateString) throws ParseException {
return parseToTimestamp(dateString, DEFAULT_PATTERN);
}
/**
* 日期字符串转时间戳自定义格式
*/
public static long parseToTimestamp(String dateString, String pattern) throws ParseException {
return getFormatter(pattern).parse(dateString).getTime() / 1000;
}
private static SimpleDateFormat getFormatter(String pattern) {
String actualPattern = pattern == null ? DEFAULT_PATTERN : pattern;
return FORMATTER_CACHE
.computeIfAbsent(actualPattern, p -> ThreadLocal.withInitial(() ->
new SimpleDateFormat(p, Locale.getDefault())))
.get();
}
}

View File

@ -0,0 +1,52 @@
package com.tfq.ad.utils;
import android.util.Log;
public class LogAd {
private static final String TAG_PREFIX = "AdLog_http";
private static boolean DEBUG = false;
public static boolean isDebug() {
return DEBUG;
}
public static void setDebug(boolean debug) {
DEBUG = debug;
}
public static void d(String msg) {
if (DEBUG) Log.d(TAG_PREFIX, buildMessage(msg));
}
public static void e(String msg) {
if (DEBUG) Log.e(TAG_PREFIX, buildMessage(msg));
}
public static void i(String msg) {
if (DEBUG) Log.i(TAG_PREFIX, buildMessage(msg));
}
public static void w(String msg) {
if (DEBUG) Log.w(TAG_PREFIX, buildMessage(msg));
}
public static void v(String msg) {
if (DEBUG) Log.v(TAG_PREFIX, buildMessage(msg));
}
private static String buildMessage(String msg) {
StackTraceElement[] trace = new Throwable().getStackTrace();
String caller = "<unknown>";
for (int i = 3; i < trace.length; i++) {
if (!trace[i].getClassName().equals(LogAd.class.getName())) {
String className = trace[i].getClassName();
caller = className.substring(className.lastIndexOf('.') + 1) +
"." + trace[i].getMethodName() +
":" + trace[i].getLineNumber();
break;
}
}
return "[" + Thread.currentThread().getId() + "] " + caller + "" + msg;
}
}

View File

@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="200"
android:fromYDelta="100%"
android:toYDelta="0" />

View File

@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="200"
android:fromYDelta="0"
android:toYDelta="100%" />

View File

@ -1,7 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
android:duration="150"
android:fromXDelta="100%p"
android:toXDelta="0" />
</set>

View File

@ -1,7 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
android:duration="150"
android:fromXDelta="0"
android:toXDelta="100%p" />
</set>

View File

@ -1,13 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="400"
android:fillAfter="true">
<translate
android:fromXDelta="100%p"
android:fromYDelta="0"
android:toXDelta="0"
android:toYDelta="0" />
<alpha
android:fromAlpha="0"
android:toAlpha="1" />
</set>

View File

@ -1,13 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="400"
android:fillAfter="true">
<translate
android:fromXDelta="0"
android:fromYDelta="0"
android:toXDelta="100%p"
android:toYDelta="0" />
<alpha
android:fromAlpha="1"
android:toAlpha="0" />
</set>

View File

@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="300"
android:fromYDelta="100%"
android:toYDelta="0" />

View File

@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="300"
android:fromYDelta="0"
android:toYDelta="100%" />

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@ -3,51 +3,51 @@
android:oneshot="false"
>
<item
android:drawable="@drawable/loading_1"
android:drawable="@drawable/ad_loading_1"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_2"
android:drawable="@drawable/ad_loading_2"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_3"
android:drawable="@drawable/ad_loading_3"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_4"
android:drawable="@drawable/ad_loading_4"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_5"
android:drawable="@drawable/ad_loading_5"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_6"
android:drawable="@drawable/ad_loading_6"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_7"
android:drawable="@drawable/ad_loading_7"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_8"
android:drawable="@drawable/ad_loading_8"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_9"
android:drawable="@drawable/ad_loading_9"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_10"
android:drawable="@drawable/ad_loading_10"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_11"
android:drawable="@drawable/ad_loading_11"
android:duration="100"
/>
<item
android:drawable="@drawable/loading_12"
android:drawable="@drawable/ad_loading_12"
android:duration="100"
/>
</animation-list>

View File

@ -3,7 +3,7 @@
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@drawable/ll_radio_loading"
android:background="@drawable/ad_ll_radio_loading"
>
<ImageView
@ -11,7 +11,7 @@
android:layout_width="30dp"
android:layout_height="30dp"
android:layout_centerInParent="true"
android:background="@drawable/anim_loading"
android:background="@drawable/ad_anim_loading"
/>
</RelativeLayout>

View File

@ -1,107 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginTop="@dimen/dp_10">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="@dimen/dp_10"
android:layout_marginRight="15dp"
android:background="@drawable/ll_radio_white">
<TextView
android:id="@+id/tv_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="21dp"
android:gravity="center"
android:text="权限申请"
android:textColor="#FC333333"
android:textSize="17sp"
android:textStyle="bold" />
<TextView
android:id="@+id/tv_content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/tv_title"
android:layout_marginTop="15dp"
android:lineSpacingMultiplier="1.2"
android:paddingLeft="22dp"
android:paddingRight="22dp"
android:gravity="center"
android:text="当前手机版本需要‘授予所有文件的管理权限’ 否则将导致应用无法正常使用,请授予所需权限后使用。"
android:textColor="#FF333333"
android:textSize="14sp" />
<View
android:layout_width="match_parent"
android:layout_height="0.5dp"
android:layout_below="@+id/tv_content"
android:layout_marginTop="15dp"
android:background="#D6D6D6" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="50dp"
android:layout_below="@+id/tv_content"
android:layout_marginTop="15dp"
android:gravity="center"
android:orientation="horizontal">
<TextView
android:id="@+id/tv_left"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:text="取消"
android:textStyle="bold" />
<View
android:layout_width="0.5dp"
android:layout_height="match_parent"
android:background="#D6D6D6" />
<TextView
android:id="@+id/tv_right"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:text="确定"
android:textColor="#37A96A"
android:textStyle="bold" />
</LinearLayout>
<LinearLayout
android:visibility="gone"
android:layout_width="match_parent"
android:layout_height="30dp"
android:layout_below="@+id/tv_content"
android:layout_marginTop="23dp"
android:layout_marginBottom="19dp"
android:gravity="center"
android:orientation="horizontal">
<ImageView
android:id="@+id/iv_cancel"
android:layout_width="30dp"
android:layout_height="28dp"
android:layout_weight="1" />
<ImageView
android:id="@+id/iv_confirm"
android:layout_width="30dp"
android:layout_height="28dp"
android:layout_weight="1" />
</LinearLayout>
</RelativeLayout>
</RelativeLayout>

View File

@ -1,222 +1,21 @@
<resources xmlns:tools="http://schemas.android.com/tools">
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">@color/colorPrimaryDark</item>
<item name="colorAccent">@color/colorAccent</item>
</style>
<style name="AppTheme.NoActionBar">
<item name="windowActionBar">false</item>
<item name="windowNoTitle">true</item>
</style>
<style name="AppTheme.AppBarOverlay" parent="ThemeOverlay.AppCompat.Dark.ActionBar" />
<style name="AppTheme.PopupOverlay" parent="ThemeOverlay.AppCompat.Light" />
<!-- 标签栏菜单主样式-->
<style name="menu">
<item name="android:gravity">center</item>
<item name="android:button">@null</item>
<item name="android:textColor">#3d4038</item>
</style>
<style name="BaseAppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<!-- &lt;!&ndash; Customize your theme here. &ndash;&gt;
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">#FFFFFF</item>
<item name="colorAccent">@color/colorAccent</item>
&lt;!&ndash;<item name="android:windowBackground">@android:color/transparent</item>&ndash;&gt;
&lt;!&ndash;<item name="android:windowAnimationStyle">@style/ActivityInOutAnimation</item>&ndash;&gt;
<item name="android:windowIsTranslucent">true</item>-->
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">@color/colorPrimaryDark</item>
<item name="colorAccent">@color/colorAccent</item>
<item name="toolbarStyle">@color/colorAccent</item>
</style>
<style name="SplashTheme" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowIsTranslucent">true</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowLayoutInDisplayCutoutMode" tools:ignore="NewApi">shortEdges</item>
</style>
<style name="AppTheme.Main" parent="BaseAppTheme" />
<!--activity的启动和退出动画-->
<style name="ActivityInOutAnimation" parent="android:style/Animation.Translucent">
<item name="android:activityOpenEnterAnimation">@anim/activity_in_animation</item>
<item name="android:activityOpenExitAnimation">@anim/activity_out_animation</item>
<item name="android:activityCloseEnterAnimation">@anim/activity_in_animation</item>
<item name="android:activityCloseExitAnimation">@anim/activity_out_animation</item>
</style>
<!--项目中的dailog向上滑入的动画-->
<!-- 项目中的Dialog向上滑入的动画样式定义 -->
<style name="CustomDialog" parent="@android:style/Theme.Dialog">
<!-- 去除窗口框架 -->
<item name="android:windowFrame">@null</item>
<!-- 设置窗口为浮动状态 -->
<item name="android:windowIsFloating">true</item>
<!-- 设置窗口不透明 -->
<item name="android:windowIsTranslucent">false</item>
<item name="android:windowBackground">@color/transparent</item>
<!-- 设置窗口背景为透明色 -->
<item name="android:windowBackground">#00000000</item>
<!-- 隐藏标题栏 -->
<item name="android:windowNoTitle">true</item>
<!-- 启用背景变暗效果 -->
<item name="android:backgroundDimEnabled">true</item>
<!-- 设置窗口进入时的动画 -->
<item name="android:windowEnterAnimation">@anim/dialog_show_enter</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exis</item>
</style>
<!--打电话弹窗-->
<style name="CallTelPhoneDialog" parent="@android:style/Theme.Dialog">
<item name="android:windowFrame">@null</item>
<item name="android:windowIsFloating">true</item>
<item name="android:windowIsTranslucent">false</item>
<item name="android:windowBackground">@color/transparent</item>
<item name="android:windowNoTitle">true</item>
<item name="android:backgroundDimEnabled">true</item>
<item name="android:windowEnterAnimation">@anim/dialog_show_enter</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exis</item>
</style>
<style name="choose_register" parent="Theme.AppCompat.Light">
<item name="colorControlNormal">#737070</item>
<item name="colorControlActivated">@color/themeColor</item>
</style>
<style name="FloatWindowAnimation">
<item name="android:windowEnterAnimation">@anim/anim_float_window_enter</item>
<item name="android:windowExitAnimation">@anim/anim_float_window_exit</item>
</style>
<style name="Theme.PictureInPicture" parent="Theme.MaterialComponents.DayNight.NoActionBar" />
<!--继承AppCompatActivity时设置全屏-->
<style name="NoTitleFullscreen" parent="Theme.AppCompat.NoActionBar">
<item name="android:windowNoTitle">true</item>
<item name="windowActionBar">false</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowContentOverlay">@null</item>
</style>
<!--<style name="notitle">
<item name="android:windowNoTitle">true</item>
</style>-->
<declare-styleable name="DoubleHeadedDragonBar">
<!--进度条按钮宽高-->
<attr name="button_width" format="dimension" />
<attr name="button_height" format="dimension" />
<!--进图条按钮图片-->
<attr name="button_img" format="reference" />
<!--单位字体颜色-->
<attr name="text_color" format="color" />
<!--进图条背景颜色-->
<attr name="bg_color" format="color" />
<!--进度条颜色-->
<attr name="value_color" format="color" />
<!--进度条宽-->
<attr name="seek_height" format="dimension" />
</declare-styleable>
<!-- 自定义仿IOS的ActionSheet底部Dialog的样式 ,有模糊效果 -->
<style name="ActionGeneralDialog" parent="@android:style/Theme.Dialog">
<!-- 背景透明 -->
<item name="android:windowBackground">@android:color/transparent</item>
<item name="android:windowContentOverlay">@null</item>
<!-- 浮于Activity之上 -->
<item name="android:windowIsFloating">true</item>
<!-- 边框 -->
<item name="android:windowFrame">@null</item>
<!-- Dialog以外的区域模糊效果 -->
<item name="android:backgroundDimEnabled">true</item>
<!-- 无标题 -->
<item name="android:windowNoTitle">true</item>
<!-- 半透明 -->
<item name="android:windowIsTranslucent">true</item>
<!-- Dialog进入及退出动画 -->
<item name="android:windowAnimationStyle">@style/ActionSheetDialogAnimation</item>
</style>
<!-- ActionSheet进出动画 -->
<style name="ActionSheetDialogAnimation" parent="@android:style/Animation.Dialog">
<item name="android:windowEnterAnimation">@anim/actionsheet_dialog_in</item>
<item name="android:windowExitAnimation">@anim/actionsheet_dialog_out</item>
</style>
<!--从下而上Dialog出场动画主题样式-->
<style name="MenuButtomAnimationStyle" parent="android:style/Theme.Dialog">
<!-- 是否有标题-->
<item name="android:windowNoTitle">true</item>
<!--背景颜色及透明程度-->
<item name="android:windowBackground">@android:color/transparent</item>
<!--是否浮现在activity之上-->
<item name="android:windowIsFloating">true</item>
<!--是否模糊-->
<item name="android:backgroundDimEnabled">true</item>
<item name="android:windowCloseOnTouchOutside">true</item>
<item name="android:windowAnimationStyle">@style/MusicButtomAnimation</item>
</style>
<!--从下而上动画-->
<style name="MusicButtomAnimation">
<!-- 入场动画 -->
<item name="android:windowEnterAnimation">@anim/bottom_menu_enter</item>
<!-- 出厂动画 -->
<item name="android:windowExitAnimation">@anim/bottom_menu_exit</item>
</style>
<!--中间弹窗式Activity-->
<style name="ActivityCenterDialogAnimation" parent="@style/Theme.AppCompat.Light.NoActionBar">
<!-- 是否有标题-->
<item name="android:windowNoTitle">true</item>
<!--背景颜色及透明程度-->
<item name="android:windowBackground">@android:color/transparent</item>
<!--是否浮现在activity之上-->
<item name="android:windowIsFloating">true</item>
<!--是否模糊-->
<item name="android:backgroundDimEnabled">true</item>
<item name="android:windowCloseOnTouchOutside">true</item>
<item name="android:windowAnimationStyle">@android:style/Animation.Dialog</item>
</style>
<!--播放器标题-->
<style name="MusicTitleStyle">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:layout_gravity">center_vertical</item>
<item name="android:gravity">center_vertical</item>
<item name="android:ellipsize">marquee</item>
<item name="android:singleLine">true</item>
<item name="android:textSize">16dp</item>
<item name="android:textColor">#FFFFFF</item>
</style>
<!--播放器时间字体样式-->
<style name="MusicTimeStyle">
<item name="android:layout_width">wrap_content</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:layout_gravity">center_vertical</item>
<item name="android:textSize">12dp</item>
<item name="android:textColor">#FFFFFFFF</item>
<item name="android:background">?attr/selectableItemBackground</item>
</style>
<!--从屏幕中间出场的动画样式-->
<style name="CenterDialogAnimationStyle" parent="Animation.AppCompat.Dialog">
<!-- 是否有标题-->
<item name="android:windowNoTitle">true</item>
<!--背景颜色及透明程度-->
<item name="android:windowBackground">@android:color/transparent</item>
<!--是否浮现在activity之上-->
<item name="android:windowIsFloating">true</item>
<!--是否模糊-->
<item name="android:backgroundDimEnabled">true</item>
</style>
<!--锁屏Theme-->
<style name="MusicLockScreenTheme" parent="Theme.AppCompat.Light.NoActionBar">
<item name="windowActionBar">false</item>
<item name="windowNoTitle">true</item>
<item name="android:windowIsTranslucent">true</item>
<item name="android:windowBackground">@android:color/transparent</item>
<item name="android:colorBackgroundCacheHint">@null</item>
<item name="android:windowNoTitle">true</item>
<item name="android:backgroundDimEnabled">false</item>
<item name="android:windowAnimationStyle">@null</item>
<item name="android:windowContentOverlay">@null</item>
<!-- 设置窗口退出时的动画 -->
<item name="android:windowExitAnimation">@anim/dialog_show_exit</item> <!-- 假设更正为dialog_show_exit -->
</style>
</resources>

View File

@ -5,7 +5,6 @@ ext {
versionCode : 100,
versionName : "1.0.0",
company_name : "济宁同风起网络科技有限公司",
noAD : "false",//广true
APP_DEBUG_PRINT : "false",//true: log
need_login : "true",//

View File

@ -70,7 +70,6 @@ android {
flavor.manifestPlaceholders = [UMENG_CHANNEL_VALUE: name, app_icon: rootProject.ext.channel["appLogo"]]
}
resValue "bool", "noAD", rootProject.ext.base["noAD"]
resValue "string", "company_name", rootProject.ext.base["company_name"]
resValue "string", "appid", rootProject.ext.base["appId"] //appid

View File

@ -28,7 +28,7 @@ android {
namespace rootProject.ext.base.applicationId //
defaultConfig {
applicationId rootProject.ext.base.applicationId
minSdkVersion 21
minSdkVersion 24
targetSdkVersion 34
multiDexEnabled true
versionCode rootProject.ext.base.versionCode

File diff suppressed because one or more lines are too long

View File

@ -1,4 +1,4 @@
package com.tfq.ad.app;
package com.tfq.finances.core.utils;
import android.util.Log;

View File

@ -2,7 +2,6 @@ package com.tfq.finances.core.utils;
import android.widget.Toast;
import com.tfq.ad.app.HttpLog;
import com.tfq.library.utils.AppUtil;
import com.tfq.finances.core.constants.Constants;
import com.tfq.finances.app.App;

View File

@ -8,6 +8,8 @@ import android.widget.ImageView;
import android.widget.TextView;
import com.tfq.ad.ad.AdFeedUtils;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.finances.finances.view.CircleProgressBarWithAnimation;
import com.tfq.finances.jzrcj.R;
import com.tfq.finances.network.api.finances.BudgetsService;
@ -72,7 +74,7 @@ public class Activity_Budgets extends BaseActivity {
}
private void initAd() {
AdFeedUtils.show_ad(this, BaseConstants.CODE_AD_FEED1, fl_content, 20, "budgets", 3);
AdFeedUtils.show_ad(this, AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_FEED1), fl_content, 20, "budgets", 3);
}
@Override

View File

@ -11,6 +11,8 @@ import android.widget.LinearLayout;
import android.widget.TextView;
import com.tfq.ad.ad.AdFeedUtils;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.finances.finances.adapter.TransactionsAdapter;
import com.tfq.finances.jzrcj.R;
import com.tfq.finances.network.api.finances.BillsService;
@ -92,7 +94,7 @@ public class Activity_Transactions extends BaseActivity {
}
private void initAd() {
AdFeedUtils.show_ad(this, BaseConstants.CODE_AD_FEED1, fl_content, 20, "budgets", 3);
AdFeedUtils.show_ad(this, AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_FEED1), fl_content, 20, "budgets", 3);
}
@Override

View File

@ -22,21 +22,17 @@ import android.widget.TextView;
import com.tfq.ad.ad.AdSplashUtils;
import com.tfq.ad.ad.SplashUtils;
import com.tfq.ad.ad.TTAdManagerHolder;
import com.tfq.finances.jzrcj.R;
import com.tfq.finances.app.App;
import com.tfq.finances.core.constants.Constants;
import com.tfq.finances.finances.activity.Activity_Login;
import com.tfq.finances.network.config.ApiCallback;
import com.tfq.finances.jzrcj.R;
import com.tfq.finances.main.activity.Activity_Tw;
import com.tfq.finances.main.activity.Activity_WebView;
import com.tfq.finances.network.api.adv.AdService;
import com.tfq.finances.network.config.token.TokenManager;
import com.tfq.finances.network.model.response.adv.AdvFlagResp;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.utils.AppUtil;
import com.tfq.library.utils.LogK;
import com.tfq.library.utils.SpManager;
import com.tfq.finances.network.api.adv.AdService;
import com.tfq.finances.core.enums.AdvFlagEnum;
import com.tfq.finances.core.constants.Constants;
import com.tfq.finances.app.App;
import com.tfq.finances.main.activity.Activity_Tw;
import com.tfq.finances.main.activity.Activity_WebView;
import androidx.annotation.NonNull;
@ -45,9 +41,9 @@ public class Activity_Splash extends Activity {
private final AdService adService = new AdService(App.getContext());
FrameLayout frameLayout;
boolean onResume = true;
AdSplashUtils adSplashUtils;
private FrameLayout frameLayout;
private boolean onResume = true;
private AdSplashUtils adSplashUtils;
@Override
protected void onCreate(Bundle savedInstanceState) {
@ -58,6 +54,8 @@ public class Activity_Splash extends Activity {
ImageView ivSplash = findViewById(R.id.iv_splash);
ivSplash.setBackgroundResource(App.getInstances().getAppSplash());
run_start();
}
private void run_start() {
@ -120,66 +118,28 @@ public class Activity_Splash extends Activity {
}
private void toMain() {
adService.getAdvFlag(new ApiCallback<AdvFlagResp>() {
AdUtils.getAdvFlag(new AdUtils.AdCallback() {
@Override
public void onSuccess(AdvFlagResp response) {
runOnUiThread(() -> {
try {
// 更新广告开关状态
updateAdFlags(response);
// 处理广告等待时间
if (response.getAdv4Wait() > 0) {
BaseConstants.ADV_Wait = response.getAdv4Wait();
}
// 根据是否禁用广告决定后续流程
if (getResources().getBoolean(R.bool.noAD)) {
toDmMain(500);
} else {
initAdManager();
}
} catch (Exception e) {
e.printStackTrace();
toDmMain(500);
}
});
public void onSuccess() {
initAdManager();
}
@Override
public void onFailure(int errorCode, String errorMessage) {
public void onFailure(String errorMessage) {
// 处理获取广告开关状态失败的情况
LogK.e("Failed to get adv flag: " + errorMessage);
toDmMain(0);
}
});
}
private void toDmMain(long delayMillis) {
runOnUiThread(new Runnable() {
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
to_main();
}
}, delayMillis);
to_main();
}
});
}
/**
* 更新广告开关状态
*/
private void updateAdFlags(AdvFlagResp response) {
BaseConstants.AD_SPLASH = AdvFlagEnum.ON.getValue().equals(response.getAdv1Flag());
BaseConstants.AD_REWARD = AdvFlagEnum.ON.getValue().equals(response.getAdv2Flag());
BaseConstants.AD_NATIVE = AdvFlagEnum.ON.getValue().equals(response.getAdv3Flag());
BaseConstants.AD_CQP = AdvFlagEnum.ON.getValue().equals(response.getAdv4Flag());
BaseConstants.AD_BANNER = AdvFlagEnum.ON.getValue().equals(response.getAdv5Flag());
BaseConstants.AD_DRAW = AdvFlagEnum.ON.getValue().equals(response.getAdv6Flag());
BaseConstants.AD_Switch_Requested = true;
}, delayMillis);
}
/**
@ -194,6 +154,7 @@ public class Activity_Splash extends Activity {
toAd();
});
}
@Override
public void error() {
runOnUiThread(() -> toDmMain(500));
@ -205,9 +166,9 @@ public class Activity_Splash extends Activity {
private void to_main() {
TokenManager instance = TokenManager.getInstance(this);
boolean tokenValid = instance.isTokenValid();
if (!tokenValid){
if (!tokenValid) {
startActivity(new Intent(Activity_Splash.this, Activity_Login.class));
}else {
} else {
startActivity(new Intent(Activity_Splash.this, Activity_Main.class));
}
finish();

View File

@ -0,0 +1,67 @@
package com.tfq.finances.main;
import android.content.Context;
import com.tfq.finances.network.api.adv.AdService;
import com.tfq.finances.network.config.ApiCallback;
import com.tfq.finances.network.model.response.adv.AdvFlagResp;
import com.tfq.finances.app.App;
import com.tfq.finances.core.enums.AdvFlagEnum;
import com.tfq.ad.app.ADConstants;
import com.tfq.library.app.BaseConstants;
public class AdUtils {
private static final AdService adService = new AdService(App.getContext());
private AdUtils() {}
// 新增无回调版本
public static void getAdvFlag() {
getAdvFlag(null);
}
// 修改原有方法支持可选回调
public static void getAdvFlag(final AdCallback callback) {
adService.getAdvFlag(new ApiCallback<AdvFlagResp>() {
@Override
public void onSuccess(AdvFlagResp response) {
try {
updateAdFlags(response);
if (response.getAdv4Wait() > 0) {
ADConstants.ADV_Wait = response.getAdv4Wait();
}
if (callback != null) {
callback.onSuccess();
}
} catch (Exception e) {
e.printStackTrace();
if (callback != null) {
callback.onFailure("Exception: " + e.getMessage());
}
}
}
@Override
public void onFailure(int errorCode, String errorMessage) {
if (callback != null) {
callback.onFailure("Error: " + errorCode + ", " + errorMessage);
}
}
});
}
private static void updateAdFlags(AdvFlagResp response) {
ADConstants.AD_SPLASH = AdvFlagEnum.ON.getValue().equals(response.getAdv1Flag());
ADConstants.AD_REWARD = AdvFlagEnum.ON.getValue().equals(response.getAdv2Flag());
ADConstants.AD_NATIVE = AdvFlagEnum.ON.getValue().equals(response.getAdv3Flag());
ADConstants.AD_CQP = AdvFlagEnum.ON.getValue().equals(response.getAdv4Flag());
ADConstants.AD_BANNER = AdvFlagEnum.ON.getValue().equals(response.getAdv5Flag());
ADConstants.AD_DRAW = AdvFlagEnum.ON.getValue().equals(response.getAdv6Flag());
ADConstants.AD_Switch_Requested = true;
}
public interface AdCallback {
void onSuccess();
void onFailure(String errorMessage);
}
}

View File

@ -11,6 +11,8 @@ import android.widget.LinearLayout;
import android.widget.TextView;
import com.tfq.ad.ad.AdFeedUtils;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.finances.jzrcj.R;
import com.tfq.library.app.BaseConstants;
import com.tfq.library.base.BaseActivity;
@ -64,7 +66,7 @@ public class Activity_About_Us extends BaseActivity {
@Override
public void onResume() {
super.onResume();
AdFeedUtils.show_ad(this, BaseConstants.CODE_AD_FEED1, flContent, 20, "page_about_us", 2);
AdFeedUtils.show_ad(this, AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_FEED1), flContent, 20, "page_about_us", 2);
}
@Override
@ -117,7 +119,7 @@ public class Activity_About_Us extends BaseActivity {
new AuthDialog(this, "authorizatio", new AuthDialog.Listener() {
@Override
public void callBack() {
BaseConstants.AD_Switch_Requested = false;
ADConstants.AD_Switch_Requested = false;
SharedPreferences.Editor editor = SpManager.startWrite(Activity_About_Us.this, Constants.SP_NAME);
editor.putBoolean("no_first_open", false);
editor.commit();

View File

@ -19,6 +19,7 @@ import com.alibaba.fastjson.JSON;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.tfq.ad.ad.AdBannerUtils;
import com.tfq.ad.ad.AdFeedUtils;
import com.tfq.ad.ad.LoadingDialog;
import com.tfq.finances.finances.activity.Activity_Budgets;
import com.tfq.finances.finances.activity.Activity_Detail_Add;
import com.tfq.finances.finances.activity.Activity_Transactions;

View File

@ -15,6 +15,8 @@ import android.widget.TextView;
import com.airbnb.lottie.LottieAnimationView;
import com.airbnb.lottie.RenderMode;
import com.tfq.ad.ad.AdFeedUtils;
import com.tfq.ad.app.ADConstants;
import com.tfq.ad.app.AdApp;
import com.tfq.finances.core.enums.AvatarEnum;
import com.tfq.finances.finances.activity.Activity_Setting_More;
import com.tfq.finances.jzrcj.R;
@ -139,7 +141,7 @@ public class Fm_Page_S extends BaseFragment {
super.onResume();
// AdFeedUtils.show_ad(getActivity(), flContent, 20, "page_setting");
AdFeedUtils.show_ad(getActivity(), BaseConstants.CODE_AD_FEED1, flContent, 20, "page_setting", 1);
AdFeedUtils.show_ad(getActivity(), AdApp.getInstance().getSlotConfig(ADConstants.AD_CODE_FEED1), flContent, 20, "page_setting", 1);
if (Activity_Setting_More.avatar_Id != -1) {
LogK.e("设置页 onResume 设置头像");

View File

@ -1,16 +1,16 @@
<?xml version="1.0" encoding="utf-8"?>
<animation-list android:id="@+id/loading_animation" android:oneshot="false"
xmlns:android="http://schemas.android.com/apk/res/android">
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_1" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_2" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_3" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_4" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_5" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_6" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_7" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_8" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_9" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_10" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_11" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/loading_12" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_1" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_2" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_3" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_4" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_5" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_6" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_7" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_8" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_9" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_10" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_11" />
<item android:duration="@integer/loading_anmi_durtion" android:drawable="@drawable/ad_loading_12" />
</animation-list>

View File

@ -65,7 +65,7 @@
<item name="android:windowNoTitle">true</item>
<item name="android:backgroundDimEnabled">true</item>
<item name="android:windowEnterAnimation">@anim/dialog_show_enter</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exis</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exit</item>
</style>
<!--打电话弹窗-->
@ -77,7 +77,7 @@
<item name="android:windowNoTitle">true</item>
<item name="android:backgroundDimEnabled">true</item>
<item name="android:windowEnterAnimation">@anim/dialog_show_enter</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exis</item>
<item name="android:windowExitAnimation">@anim/dialog_show_exit</item>
</style>
<style name="choose_register" parent="Theme.AppCompat.Light">

View File

@ -1 +1 @@
96872dfbb36af3c211e23afe0dff70cf
ae2ef6e3480a397e70d596a05f81a1c4

View File

@ -1 +1 @@
b1c69c827d69ab65f428370415afc5f4a2a57b3c
b1e687b33ea91a51c177bb6689b60b1925bdc253

View File

@ -1 +1 @@
953fc0af3b8e3312dfa3f99e93490573ed1e5963872c8e2fd126416b9c04bcc8
4d6aefca1b5c8b132ed5f94faf77777721453af864bc2efd6b43894af4153adc

View File

@ -1 +1 @@
b2c988900d798ab384faee14eb5e4cfabe419a46c01a51758be06552536f486ef4f028fdfe017e7ac114d6649d274728d245336f64df8c864ed1c83e8a9aafbc
462d3a02044656c1f9cb7ce680022354332a51e9ada1f509effd81c611423ae8dde993b8164722ecddf58e4183726406b91ac6f3787e2ada0171e679938b681a

View File

@ -8,6 +8,6 @@
<versions>
<version>1.0.0</version>
</versions>
<lastUpdated>20250630060400</lastUpdated>
<lastUpdated>20250706071759</lastUpdated>
</versioning>
</metadata>

View File

@ -1 +1 @@
7c1e64c42991c3fbf68bfcd989152c60
52e9027a82582e286f92e7d833e76b7c

View File

@ -1 +1 @@
6750a593e7a51507e732a85be8c006ccbb207e51
c9ab1812edb9e8937c1f822f9c1dbff3146805c3

View File

@ -1 +1 @@
cf73a5d4df5b588b8b2240fa2fa627ec5a4815b7b463a6dc8c508dc8be693ae6
6de4ea7bc9a2196273eb2e99542027347683aec618cd368e5409f228e8a17afe

View File

@ -1 +1 @@
bc2d58c292a931b0694f1361b18bbfd29e03ef9c558aa80ffc9d9ace4b8c4e7b930f3d2b6998bce019daa63e438a0039e9cc61c075a0b0d7d188b5ff4180cb5e
e00aa8c0cb023ba82460a134d6ed156c8a80f0bcf4ad11e0a79aed8ba784eca071e4d36d621a34c51d1a9ddafff147a517ee121833c25b01bd09a06aa05b8b80