152 lines
4.9 KiB
Dart
152 lines
4.9 KiB
Dart
// Author: fengshengxiong
|
|
// Date: 2024/6/25
|
|
// Description: 开屏广告
|
|
|
|
import 'dart:io' show Platform;
|
|
|
|
import 'package:connectivity_plus/connectivity_plus.dart';
|
|
import 'package:flutter/foundation.dart';
|
|
import 'package:flutter/services.dart';
|
|
import 'package:get/get.dart';
|
|
import 'package:google_mobile_ads/google_mobile_ads.dart';
|
|
import 'package:tone_snap/data/storage/music_box.dart';
|
|
import 'package:tone_snap/modules/launch/launch_controller.dart';
|
|
import 'package:tone_snap/utils/log_util.dart';
|
|
|
|
class AppOpenAdManager {
|
|
AppOpenAdManager._();
|
|
|
|
static final AppOpenAdManager _instance = AppOpenAdManager._();
|
|
|
|
factory AppOpenAdManager() => _instance;
|
|
|
|
AppOpenAd? _appOpenAd;
|
|
bool _isShowingAd = false;
|
|
|
|
/// 加载和显示广告之间允许的最长持续时间
|
|
final Duration _maxCacheDuration = const Duration(minutes: 50);
|
|
|
|
/// 跟踪加载时间,这样我们就不会显示过期的广告
|
|
DateTime? _appOpenLoadTime;
|
|
|
|
/// 记录关闭时的时间,用于下一次展示时计算时间差
|
|
DateTime? _closeDateTime;
|
|
|
|
/// 开屏广告单元id
|
|
final adUnitId = Platform.isAndroid
|
|
? (kReleaseMode ? '' : 'ca-app-pub-3940256099942544/9257395921')
|
|
: (kReleaseMode ? 'ca-app-pub-5684307632319406/2523581084' : 'ca-app-pub-3940256099942544/5575463023');
|
|
|
|
/// 加载广告
|
|
Future<void> loadAd() async {
|
|
final List<ConnectivityResult> connectivityResult = await (Connectivity().checkConnectivity());
|
|
if (connectivityResult.contains(ConnectivityResult.none)) {
|
|
LogUtil.d('当前无网络,不加载广告');
|
|
return;
|
|
}
|
|
if (isAdAvailable) {
|
|
return;
|
|
}
|
|
await AppOpenAd.load(
|
|
adUnitId: adUnitId,
|
|
request: const AdRequest(),
|
|
adLoadCallback: AppOpenAdLoadCallback(
|
|
onAdLoaded: (ad) {
|
|
LogUtil.d('开屏广告加载完成');
|
|
_appOpenAd = ad;
|
|
_appOpenLoadTime = DateTime.now();
|
|
if (AppOpenAdManager().isAdAvailable) {
|
|
if (Get.isRegistered<LaunchController>()) {
|
|
LaunchController.to.editChangeValue();
|
|
}
|
|
}
|
|
},
|
|
onAdFailedToLoad: (error) {
|
|
LogUtil.e('开屏广告加载失败: $error');
|
|
// Handle the error.
|
|
},
|
|
),
|
|
);
|
|
}
|
|
|
|
/// 是否可以播放广告
|
|
bool get isAdAvailable {
|
|
return _appOpenAd != null;
|
|
}
|
|
|
|
/// 显示广告(如果存在且尚未显示)
|
|
/// 如果先前缓存的广告已过期,则只加载并缓存新广告
|
|
void showAdIfAvailable({Function()? onTap}) {
|
|
if (!isAdAvailable) {
|
|
LogUtil.d('尝试在可用之前显示广告');
|
|
loadAd();
|
|
if(onTap != null) onTap();
|
|
return;
|
|
}
|
|
if (_isShowingAd) {
|
|
LogUtil.d('尝试在已显示广告的情况下显示广告');
|
|
if(onTap != null) onTap();
|
|
return;
|
|
}
|
|
if (DateTime.now().subtract(_maxCacheDuration).isAfter(_appOpenLoadTime!)) {
|
|
LogUtil.d('超过了最大缓存持续时间。正在加载另一个广告');
|
|
_appOpenAd!.dispose();
|
|
_appOpenAd = null;
|
|
loadAd();
|
|
if(onTap != null) onTap();
|
|
return;
|
|
}
|
|
if (_closeDateTime != null) {
|
|
// 计算时间差
|
|
Duration timeDifference = DateTime.now().difference(_closeDateTime!);
|
|
// 获取配置的 openAppEventDuration
|
|
int openAppEventDuration = MusicBox().getOpenAppEventDuration();
|
|
// 检查时间差是否小于10秒
|
|
if (timeDifference < Duration(seconds: openAppEventDuration)) {
|
|
return;
|
|
}
|
|
}
|
|
|
|
// 设置 fullScreenContentCallback 并显示广告
|
|
_appOpenAd!.fullScreenContentCallback = FullScreenContentCallback(
|
|
// 暂停应用程序中的活动或记录广告展示的时间
|
|
onAdShowedFullScreenContent: (ad) {
|
|
LogUtil.d('$ad onAdShowedFullScreenContent');
|
|
// 隐藏状态栏
|
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.manual, overlays: <SystemUiOverlay>[]);
|
|
|
|
_isShowingAd = true;
|
|
},
|
|
// 更适合用于跟踪广告展示的次数和效果,以及执行与广告展示相关的操作
|
|
onAdImpression: (ad) {
|
|
LogUtil.d('$ad onAdImpression');
|
|
},
|
|
onAdFailedToShowFullScreenContent: (ad, error) {
|
|
LogUtil.d('$ad onAdFailedToShowFullScreenContent: $error');
|
|
_isShowingAd = false;
|
|
ad.dispose();
|
|
_appOpenAd = null;
|
|
|
|
if(onTap != null) onTap();
|
|
},
|
|
onAdDismissedFullScreenContent: (ad) {
|
|
LogUtil.d('$ad onAdDismissedFullScreenContent');
|
|
_closeDateTime = DateTime.now();
|
|
|
|
// 显示状态栏(用户关闭广告后)
|
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.manual, overlays: SystemUiOverlay.values);
|
|
|
|
_isShowingAd = false;
|
|
ad.dispose();
|
|
_appOpenAd = null;
|
|
loadAd();
|
|
|
|
if(onTap != null) onTap();
|
|
},
|
|
onAdClicked: (ad) {
|
|
LogUtil.d('$ad onAdClicked');
|
|
},
|
|
);
|
|
_appOpenAd!.show();
|
|
}
|
|
} |