Giter VIP home page Giter VIP logo

flutterads / flutter_qq_ads Goto Github PK

View Code? Open in Web Editor NEW
105.0 1.0 16.0 1.17 MB

🔥🔥🔥 Flutter 广告插件 -- 优量汇 、广点通、腾讯广告(支持开屏、插屏、激励视频、Banner、信息流、视频贴片)

Home Page: https://pub.dev/packages/flutter_qq_ads

License: MIT License

Java 37.50% Ruby 1.62% Objective-C 29.54% Dart 31.33%
flutter flutter-plugin flutterads ios android ads

flutter_qq_ads's Introduction

logo

一款优质的 Flutter 广告插件(腾讯广告、广点通、优量汇)

插件特点

  • 🔨 接入简单快速(封装原生端配置,仅需引入即可)
  • 📡 事件统一返回(将原生端各种重要回调事件统一返回,方便业务处理和埋点统计等需求)
  • 🎁 注重优化体验(无闪烁 Logo 开屏、权限申请、隐私跟踪申请等、信息流自动适配宽高)
  • 🏆 极客代码封装(原生端代码不凑合,两端统一基础框架、广告事件封装抽象、易扩展新广告形式、方便开发个性化需求)

支持功能

📣 推荐使用 GroMore

  • Gromore】可进行多家广告瀑布流竞价,让您拥有更高的广告收益,发挥最大的用户价值

下载体验

回复 优量汇体验

💬 App 广告变现群

  • 插件问题解答
  • 变现玩法交流
  • 收益提升探讨
  • 大盘趋势推送
  • 版本更新推送

因微信群入群限制,请添加个人微信备注:变现群,我拉你进群。

wechat:toponelan

入门使用

引入依赖

dependencies:
  flutter_qq_ads: ^2.7.0

初始化广告

/// [appId] 应用媒体ID
FlutterQqAds.initAd(appId);

开屏广告

  • 半屏广告 + Logo
/// [posId] 广告位 id
/// [logo] 如果传值则展示底部logo,不传不展示,则全屏展示
/// [fetchDelay] 拉取广告的超时时间,默认值 3 秒,取值范围[1.5~5]
FlutterQqAds.showSplashAd(
    AdsConfig.splashId,
    logo: 'flutterads_logo',
    fetchDelay: 3,
  );
FlutterQqAds.showSplashAd(posId);

插屏广告

  • 插屏半屏
/// [posId] 广告位 id
/// [showPopup] Popup 形式显示(仅 Android)
/// [autoPlayOnWifi] 是否仅在 WiFi 网络下自动播放
/// [autoPlayMuted] 自动播放是否静音
/// [detailPageMuted] 详情页是否静音
FlutterQqAds.showInterstitialAd(
    posId,
    showPopup: false,
    autoPlayMuted: false,
    autoPlayOnWifi: false,
    detailPageMuted: false,
  );
  • 插屏全屏视频
/// [posId] 广告位 id
/// [showFullScreenVideo] 插屏全屏视频形式显示
FlutterQqAds.showInterstitialAd(
    posId,
    showFullScreenVideo: true,
  );
  • 插屏激励视频
/// [posId] 广告位 id
/// [showRewardVideo] 插屏激励视频形式显示
/// [customData] 设置服务端验证的自定义信息
/// [userId] 设置服务端验证的用户信息
FlutterQqAds.showInterstitialAd(
    posId,
    showRewardVideo: true,
    customData: 'customData',
    userId: 'userId',
  );

激励视频

/// [posId] 广告位 id
/// [playMuted] 是否静音播放
/// [customData] 设置服务端验证的自定义信息
/// [userId] 设置服务端验证的用户信息
FlutterQqAds.showRewardVideoAd(
    posId,
    playMuted: false,
    customData: 'customData',
    userId: 'userId',
  );

Banner

/// [posId] 广告位 id
/// [width] 宽度
/// [height] 高度
/// [interval] 广告刷新间隔,0 或[30~120]之间的数字,单位为 s,默认 30s 
///  Android:0 表示不自动轮播 
///  iOS:0 表示关闭轮播动画,因为 iOS 没有不轮播
/// [show] 是否显示广告
AdBannerWidget(
  posId: AdsConfig.bannerId02,
  width: 375,
  height: 100, 
  interval: 120, 
  show: true,
)

v1.4.0 开始不再需要外部嵌套,如果需要按比例设置,可以看如下示例:

  • 嵌套宽高比约束布局 AspectRatio
AspectRatio(
  aspectRatio: 6.4 / 1, // 6.4:1 的比例
  child: AdBannerWidget(
    posId: AdsConfig.bannerId02,
    width: double.maxFinite,
    height: double.maxFinite,
    interval: 120,
  ),
),

信息流

  • 获取信息流广告列表
/// [posId] 广告位 id
/// [width] 宽度
/// [height] 高度,0:代表自适应广告高度
/// [count] 获取广告数量,建议 1~3 个
List<int> feedAdList = await FlutterQqAds.loadFeedAd(
    AdsConfig.feedId,
    width: 375,
    height: 0,
    count: 3,
  );
  • 清除信息流广告列表

当你的广告不再需要时,请一定执行清除操作

/// [list] 信息流广告 id 列表
bool result = await FlutterQqAds.clearFeedAd(feedAdList);
  • 页面中展示信息流广告
/// Feed 信息流广告组件
/// [posId]返回的广告 id,这里不是广告位id
/// [width]组件的宽度
/// [height]组件的高度
/// [show]是否显示
AdFeedWidget(
    posId: '${feedAdList[0]}',
    width: 375,
    height: 128,
    show: true,
  )

widthheight 只是展示 widget 组件宽高,最终会自动适配实际广告的宽高,不可设置为 0

设置广告事件监听

FlutterQqAds.onEventListener((event) {
  // 普通广告事件
  String _adEvent = 'adId:${event.adId} action:${event.action}';
  if (event is AdErrorEvent) {
    // 错误事件
    _adEvent += ' errCode:${event.errCode} errMsg:${event.errMsg}';
  } else if (event is AdRewardEvent) {
    // 激励事件
    _adEvent +=
        ' transId:${event.transId} customData:${event.customData} userId:${event.userId}';
  }
  print('onEventListener:$_adEvent');
});

事件列表

事件 说明
onAdLoaded 广告加载成功
onAdPresent 广告填充
onAdExposure 广告曝光
onAdClosed 广告关闭(开屏计时结束或者用户点击关闭)
onAdClicked 广告点击
onAdSkip 广告跳过
onAdComplete 广告播放或计时完毕
onAdError 广告错误
onAdReward 获得广告激励

这里做了统一的抽象,iOS 和 Android 原生 SDK 名称不同,如果觉得对应不上,可以提 Issues(一定要加上 log 截图)

其他配置

信任HTTP请求

苹果公司在iOS9中升级了应用网络通信安全策略,默认推荐开发者使用HTTPS协议来进行网络通信,并限制HTTP协议的请求。为了避免出现无法拉取到广告的情况,我们推荐开发者在info.plist文件中增加如下配置来实现广告的网络访问

  • 修改 info.plist
<key>NSAppTransportSecurity</key>
<dict>
  <key>NSAllowsArbitraryLoads</key>
  <true/>
</dict>

信任HTTP请求

请求应用跟踪透明度授权

此步骤必须要做,不然上架审核时候会被拒绝

bool result = await FlutterQqAds.requestIDFA;
  • 修改 info.plist
<key>NSUserTrackingUsageDescription</key>
<string>为了向您提供更优质、安全的个性化服务及内容,需要您允许使用相关权限</string>

请求应用跟踪透明度授权

  • 效果

预览效果

原生 SDK 版本更新方法

如果是大版本,我会第一时间适配更新,小版本可以自己更新,方法如下:

  • Android

    方法1:可以给我提 Issues 提示我更新,版本号 x.y.z,会更新 z 版本迭代

    方法2:可以自己指定版本,方法如下:

// build.gradle(android.app)
android{
  configurations.all {
      resolutionStrategy {
          force 'com.qq.e.union:union:版本号'
      }
  }
}
  • iOS

    自己手动更新,自己的项目根目录下执行即可

// 可在 ios/Podfile.lock 中查看 SDK 当前版本
cd ios
rm -rf Podfile.lock
pod repo update
pod install

FlutterAds 广告插件系列

插件 描述
flutter_gromore_pro 🏆🏆🏆 帮你大幅提升广告收益,发挥出最大的用户价值
flutter_gromore_ads 字节跳动、穿山甲、GroMore 聚合 Flutter 广告开源版插件
flutter_pangle_ads 字节跳动、穿山甲 Flutter 广告插件
flutter_qq_ads 腾讯广告、广点通、优量汇 Flutter 广告插件
flutter_adspark 巨量广告/穿山甲的广告监测、增长分析、归因上报、事件管理 Flutter 版插件
flutter_adcontent 穿山甲内容输出,支持「短剧」和「小视频」的 Flutter 版插件

flutter_qq_ads's People

Contributors

byteszero avatar zerobytesx avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar

flutter_qq_ads's Issues

如何实现 应用下载弹窗确认?请求实现此功能

https://developers.adnet.qq.com/doc/android/union/union_download_confirm
在广告播放中(广告展示和落地页),点击触发广告下载时对开发者注册的回调函数进行回调,开发者可以使用回调获取应用名称、版本等相关信息,并进行弹窗提示用户是否确认进行下载。
适用场景:在合规的场景,点击下载类广告必须向用户展示应用信息并二次确认是否下载,而sdk的内部弹窗的格式不符合开发者UI要求的时候。

有助于应用更加合理合规

Code=5004 "没有广告"

错误原因:
a、错误为常规报错,没有广告填充,非sdk接入异常。
b、广告位请求匹配广告本身是一套复杂的逻辑,有人群画像、广告位效果、底价、屏蔽等多方面原因。
c、如果是新接入测试阶段新建广告位通常原因是缺乏历史数据模型,广告位竞争力差并且设备画像简陋导致匹配不到广告。
优化建议:
1、如果使用的是测试机,可以更换使用人群画像更丰富的设备尝试拉取(比如个人设备)或者在设备登录QQ,微信等丰富用户画像;
2、sdk接入可以考虑使用我们官方sdkdemo工程中所用到的广告位id,来尝试拉取广告进行测试;

💬 开通变现沟通群啦

  • 插件问题解答
  • 变现玩法交流
  • 收益提升探讨
  • 大盘趋势推送
  • 版本更新推送

因微信群入群限制,请添加个人微信备注:变现群,我拉你进群。

wechat:toponelan

升级2.5.0版本后出现大量崩溃错误

经过测试,升级2.5.0版本后出现大量崩溃错误,降级到之前的2x分支未出现如下错误

2.5.0的版本错误如图,相关日志已经贴出来

截屏2022-04-20 09 10 26

Thread Name: 'main'
Back traces starts.
java.lang.NullPointerException: Attempt to write to field 'com.qq.e.ads.nativ.NativeExpressADView$ViewBindStatusListener com.qq.e.comm.plugin.gdtnativead.o.d' on a null object reference
at com.qq.e.comm.plugin.gdtnativead.o.setViewBindStatusListener(A:1)
at com.qq.e.comm.plugin.intersitial2.a$a.run(A:173)
at android.os.Handler.handleCallback(Handler.java:938)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:257)
at android.app.ActivityThread.main(ActivityThread.java:8215)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:626)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1031)
Back traces ends.

//=========================================================

Thread Name: 'main'
Back traces starts.
java.lang.IllegalArgumentException: Unsupported value: '[Ljava.util.List;@39a9ba6' of type 'class [Ljava.util.List;'
at f.a.c.a.q.p(Unknown Source:444)
at f.a.c.a.r.c(Unknown Source:11)
at f.a.c.a.j$a$a.a(Unknown Source:10)
at com.zero.flutter_qq_ads.d.a.onNoAD(Unknown Source:68)
at com.qq.e.ads.nativ.NativeExpressAD.d(Unknown Source:352)
at com.qq.e.ads.nativ.NativeExpressAD$ADListenerAdapter.onADEvent(Unknown Source:16)
at com.qq.e.comm.plugin.gdtnativead.h$d.run(A:1)
at android.os.Handler.handleCallback(Handler.java:883)
at android.os.Handler.dispatchMessage(Handler.java:100)
at android.os.Looper.loop(Looper.java:230)
at android.app.ActivityThread.main(ActivityThread.java:7880)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:526)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1034)
Back traces ends.

//=========================================================
Thread Name: 'main'
Back traces starts.
java.lang.IncompatibleClassChangeError: Class 'com.qq.e.ads.banner2.ADListenerAdapter' does not implement interface 'com.qq.e.comm.pi.NEADVI' in call to 'void com.qq.e.comm.pi.NEADVI.render()' (declaration of 'com.qq.e.comm.plugin.gdtnativead.o' appears in gdt_plugin.jar)
at com.qq.e.comm.plugin.gdtnativead.o.render(A:2)
at com.qq.e.comm.plugin.banner2.a$a.run(A:70)
at android.os.Handler.handleCallback(Handler.java:938)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:236)
at android.app.ActivityThread.main(ActivityThread.java:8073)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:620)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1011)
Back traces ends.

//========================================================

Thread Name: 'main'
Back traces starts.
java.lang.NullPointerException: Attempt to invoke interface method 'void com.qq.e.comm.pi.NEADVI.setAdListener(com.qq.e.comm.adevent.ADListener)' on a null object reference
at com.qq.e.comm.plugin.gdtnativead.o.a(A:17)
at com.qq.e.comm.plugin.gdtnativead.o.a(A:3)
at com.qq.e.comm.plugin.gdtnativead.o$a.run(A:3)
at android.os.Handler.handleCallback(Handler.java:900)
at android.os.Handler.dispatchMessage(Handler.java:103)
at android.os.Looper.loop(Looper.java:219)
at android.app.ActivityThread.main(ActivityThread.java:8668)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:513)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1109)
Back traces ends.

iOS 在 Xcode 12.4 上构建报错 _OBJC_CLASS_$_SKAdImpression", referenced from objc-class-ref in libGDTMobSDK.a(GDTAppStoreAdNetWorkModel.o

  • 错误信息
Undefined symbols for architecture armv7:
      "_OBJC_CLASS_$_SKAdImpression", referenced from:
          objc-class-ref in libGDTMobSDK.a(GDTAppStoreAdNetWorkModel.o)
    ld: symbol(s) not found for architecture armv7
    clang: error: linker command failed with exit code 1 (use -v to see invocation)
  • 环境情况
Xcode:12.4
GDTMobSDK:4.13.02
flutter_qq_ads::1.1.1

信息流能支持设置静音吗?

(可选方法)指定视频广告的播放配置,配置包含:

  1. autoPlayPolicy,指定不同网络下的视频播放策略,可选项包括:AutoPlayPolicy.WIFI(WiFi 网络自动播放,4G 网络手动点击播放),AutoPlayPolicy.ALWAYS(WiFi 和4G 网络都自动播放),默认值为 AutoPlayPolicy.ALWAYS。
  2. autoPlayMuted,指定视频自动播放时是否静音,可选项包括:true(自动播放时静音),false(自动播放时有声),默认值为 true。
    注:AutoPlayPolicy.ALWAYS 的配置能够一定程度优化广告收益
  3. detailPageMuted,指定视频详情页是否静音播放,可选项包括:true(视频详情页静音播放),false(视频详情页有声播放),默认值为 false。
    我看文档有这个参数设置

请问怎么解决弹出广告后的点击穿透问题

是我自己写的一个插件但是无法解决弹出原生页面后点击穿透的问题,网上查的解决办法不适用,也是看到大佬也是弹SDK内容类型的插件 flutter我是菜鸟不怎么懂 但是又没在原生代码里看到相关的处理 所以想问一下怎么解决的 拜谢

跑demo onNoAD adError:初始化错误,详细码:200102

/gdt_ad_mob( 7231): ... 16 more
D/AdSplashActivity( 7231): onNoAD adError:初始化错误,详细码:200102
D/PluginDelegate( 7231): EventChannel addEvent event:{adId=8022311121246224, errCode=2001, errMsg=初始化错误,详细码:200102, action=onAdError}
D/EGL_emulation( 7231): eglMakeCurrent: 0xec1e0e20: ver 3 0 (tinfo 0xebd36e90)
D/EGL_emulation( 7231): eglMakeCurrent: 0xec1e0e20: ver 3 0 (tinfo 0xebd36e90)
I/flutter ( 7231): onEventListener:adId:8022311121246224 action:onAdError
D/PluginDelegate( 7231): MethodChannel onMethodCall method:showSplashAd arguments:{posId=8022311121246224, logo=ic_logo2}
W/ActivityThread( 7231): handleWindowVisibility: no activity for token android.os.BinderProxy@f684af4
I/xiaoguanjia.ap( 7231): Rejecting re-init on previously-failed class java.lang.Class<com.qq.e.comm.plugin.POFactoryImpl>: java.lang.ExceptionInInitializerError:

android获取到的广告宽高非常小

不知道是什么原因导致 android获取到的广告宽高非常小 我只能暂时这样修改使用

/**
 * 重新计算真实的广告 View 的宽高
 */
private void resizeAdView() {
    this.fad.measure(100, 100);
    int mw = this.fad.getMeasuredWidth();
    int mh = this.fad.getMeasuredHeight();

    //修改
    mw = activity.getResources().getDisplayMetrics().widthPixels;
    mh = (mw / 4) * 3;

    Log.d(TAG, "resizeAdView width:" + mw + " height:" + mh);
    FrameLayout.LayoutParams params=new FrameLayout.LayoutParams(mw,mh);
    frameLayout.setLayoutParams(params);
    frameLayout.requestLayout();
    setFlutterViewSize(mw,mh);
}

开屏广告展示不全

新建一个项目,导入2.4.1插件,然后把4个文件拖进去项目里边,开屏总是展示不全
图片

请教问题:使用Admob中介的情况,应该如何处理呢?

之前一直使用的Admob,然后最近才申请到的优量汇。
想问一下,使用Admob的中介功能,后台配置好优量汇的情况下,客户端应该是怎样的呢?
引入该插件并初始化后,在调用广告的地方如果只使用admob的广告展示代码,会不会自动通过中介显示优量汇的广告呢?

nclude of non-modular header inside framework module 'flutter_qq_ads.InterstitialPage':

  • 错误信息
Include of non-modular header inside framework module 'flutter_qq_ads.InterstitialPage'
Include of non-modular header inside framework module 'flutter_qq_ads.RewardVideoPage'
Include of non-modular header inside framework module 'flutter_qq_ads.SplashPage'
  • 平台
    iOS

  • 解决方法
    设置 Allow Non-modular includes in Framework Modules 设置为 Yes 即可

image

关于视频广告会影响fijkplayer播放器声音问题

播放器版本:fijkplayer: ^0.10.1
手机默认静音状态
系统:iOS

1.经过下载Demo集成fijkplayer在主页跟信息流页面手机静音测试,显示了视频广告后播放器声音消失。
2.广告设置静音播放也会影响播放器声音。
3.不展示视频广告情况下,手机静音模式播放器是有声音的,只有视频广告展示后就影响了播放器
4.经过测试只要是视频广告都会影响

目前通过播放器重新设置音量都无法再次播放声音,不知道是不是广告影响的。

如下代码可以加到Demo工程主页或者信息流进行测试验证

// 播放

final FijkPlayer player = FijkPlayer();

player.setDataSource('http://player.alicdn.com/video/aliyunmedia.mp4',
    autoPlay: true);

 SliverToBoxAdapter(
            child: FijkView(
          height: MediaQuery.of(context).size.width / (16 / 9),
          player: player,
        ))

加入个性化广告控制开关

现在APP在国内应用市场上架时会检查app是否有个性化广告功能,如果有的话需要app提供配置开关,让用户能够关闭个性化广告。对于Flutter开发的APP,需要在Flutter代码中能够对此进行控制。

onNoAD:未知错误,详细码:102006

错误原因:
a、错误为常规报错,没有广告填充,非sdk接入异常。
b、广告位请求匹配广告本身是一套复杂的逻辑,有人群画像、广告位效果、底价、屏蔽等多方面原因。
c、如果是新接入测试阶段新建广告位通常原因是缺乏历史数据模型,广告位竞争力差并且设备画像简陋导致匹配不到广告。
优化建议:
1、如果使用的是测试机,可以更换使用人群画像更丰富的设备尝试拉取(比如个人设备)或者在设备登录QQ,微信等丰富用户画像;
2、sdk接入可以考虑使用我们官方sdkdemo工程中所用到的广告位id,来尝试拉取广告进行测试;

未知错误,详细码: 107011

平台:iOS
官方回复:出现这个提示一般是因为,请求中的操作系统类型与广告位在联盟平台的设置不匹配

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.