AdMob Ads in an endless RecyclerView with Paging library

白昼怎懂夜的黑 提交于 2019-12-01 22:18:33

There can not be an easy example of it than google example here The only difference is that it takes it data from XML file saved in raw and you take your data from elsewhere. I hope you can easily modify this example according to your needs.

the first step must be declared a field in the adapter like blew

private val ADS_ITEM = 0
private val NORMAL_ITEM = 1

so, the next step you must create two type instance viewHolder

inner class MyViewHolder(itemView: View) : ViewHolder(itemView) {
    var title: TextView = itemView.item_text

}

inner class AdsMyViewHolder(itemView: View) : ViewHolder(itemView) {
    var title: TextView = itemView.item_text
}

and create a new instance suitable viewHolder

override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
    val inflater = LayoutInflater.from(parent.context)
    return if (viewType == NORMAL_ITEM) {
        val v = inflater.inflate(R.layout.item, parent, false)
        vh = MyViewHolder(v)
        vh as MyViewHolder
    } else {
        val v = inflater.inflate(R.layout.item_ads, parent, false)
        vh = AdsMyViewHolder(v)
        vh as AdsMyViewHolder
    }
}

don't forget override getItemViewType

override fun getItemViewType(position: Int): Int {
    return when (getItems()[position]) {
        is AdsSampleModel -> ADS_ITEM
        else -> NORMAL_ITEM
    }
}

last step bind item with suitable data

override fun onBindViewHolder(holder: ViewHolder, position: Int) {
    when (holder) {
        is MyViewHolder -> {
            vh = holder
            val model = getItems()[position] as SampleModel
            (vh as MyViewHolder).title.text = model.getId().toString()
        }
        else -> {
            vh = holder
            val model = getItems()[position] as AdsSampleModel
            (vh as AdsMyViewHolder).title.text = model.getText()
        }
    }
}

add new item after paging

fun view () {
    endless = object : EndlessRecyclerViewScrollListener(layoutManager) {
        fun onLoadMore(page: Int, totalItemsCount: Int, view: RecyclerView) {
            getNext()
        }
    }
    recyclerView.addOnScrollListener(endless)
}


fun getNext() {
    if (hasNextPage) {
        page++
        val callBack = object : YourCallback {
            override fun onSuccess(response: ResponseValue?) {
                if (response!!.getList().size() == 0)
                    hasNextPage = false
                else
                    addData(response!!.getList())
            }
            override fun onError() {
                // error handling
            }
        }
    }
}


private fun addData(models: List<YourModel>?) {
    for (i in models?.indices) {
        if (i % 10 == 0) {
            list.add(ADS_TYPE)
        }
    }

    // notify adapter must be doing by main thread
    runOnUiThread { adapter.notifyDataSetChanged() }
}

You can have a list of ads in the adapter like this:

    private val nativeAds = mutableListOf<UnifiedNativeAd>()

Then your onBindViewHolder will look like this:

   override fun onBindViewHolder(holder: BaseViewHolder<Any>, position: Int) {
    when (getItemViewType(position)) {
        NATIVE_AD -> {
            val adPosition = position * nativeAds.size / itemCount
            val nativeAd = nativeAds[adPosition]
            holder.performBind(nativeAd)
        }
        else ->  holder.performBind(getItem(position))
    }

}

Your getItemViewType like this:

 override fun getItemViewType(position: Int): Int {
    val nativeAdRows = getNativeAdRows()
   return if(hasNativeAds() && nativeAdRows.contains(position)){
        NATIVE_AD
    }else {
       //get other model item
   }
}

The remaining parts of the code:

fun onNativeAdLoaded() {
    val rows = getNativeAdRows()
    Timber.d("Native Ad Rows: $rows")
    Timber.d("Total items: $itemCount")
    rows.forEach {
        notifyItemInserted(it)
    }
}

private fun hasNativeAds(): Boolean {
    return nativeAds.isNotEmpty()
}

private fun getNativeAdRows(): List<Int>{
    val rows = mutableListOf<Int>()
    for (i in 0 .. itemCount){
        if(i != 0 && i % Config.NATIVE_AD_AFTER_POSTS == 0){
            rows.add(i)
        }
    }
    return rows
}

Check this gist for sample code

You can use AdMob Native Advanced Ads in an Android Feed.

Native is a component-based ad format that gives publishers the freedom to customize how ad assets like headlines and calls to action are presented in their apps. By choosing fonts, colors, and other details for themselves, publishers are able to create natural, unobtrusive ad presentations that can add to a rich user experience. Please follow mentioned below link:-

https://codelabs.developers.google.com/codelabs/admob-native-advanced-feed-android/#0

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!