Skip to content

Instantly share code, notes, and snippets.

@mdzzohrabi
Created September 28, 2017 09:40
Show Gist options
  • Save mdzzohrabi/50ab6a822646af3a93537f9eaf5015a2 to your computer and use it in GitHub Desktop.
Save mdzzohrabi/50ab6a822646af3a93537f9eaf5015a2 to your computer and use it in GitHub Desktop.
Simple End-less RecyclerView Adapter (Kotlin)
package mdzzohrabi.adapter
import android.support.v7.widget.RecyclerView
import java.util.ArrayList
/**
* Endless Recycler view adapter
* @author Masoud Zohrabi <mdzzohrabi@gmail.com>
*/
abstract class EndlessAdapter<VH: RecyclerView.ViewHolder, T>: RecyclerView.Adapter<VH>() {
// Adapter loaded items
private val items: ArrayList<T> = ArrayList()
// Get items loading threshold
protected open fun getThreshold(): Int = 5
override fun onBindViewHolder(holder: VH, position: Int) {
if ( position >= ( items.size - getThreshold() ) ) {
load( items.size )
}
}
override fun onAttachedToRecyclerView(recyclerView: RecyclerView?) {
super.onAttachedToRecyclerView(recyclerView)
load(items.size)
}
override fun getItemCount(): Int = items.size
// Insert item to loaded items
protected fun insert(item: T) { items.add(item) }
// Clear loaded items
protected fun clearItems() { items.clear() }
// Get loaded items
protected fun getItems() = items
// Get loaded item by position
protected fun getItem(position: Int): T = items[position]
// Load items called when needed to load more items
abstract fun load(offset: Int, listener: OnLoadListener? = null)
abstract class OnLoadListener {
open fun onDataChanged() {}
open fun onDataReceive() {}
}
}
package mdzzohrabi.adapter
import android.content.Context
import android.os.Build
import android.support.v7.widget.RecyclerView
import android.transition.TransitionManager
import android.view.LayoutInflater
import android.view.ViewGroup
import com.android.volley.Request
import com.android.volley.RequestQueue
import com.android.volley.Response
import com.android.volley.toolbox.JsonObjectRequest
import com.android.volley.toolbox.Volley
import org.json.JSONObject
class ExampleEndlessRecycler() : EndlessAdapter<ContentViewHolder, JSONObject>() {
private val limit = 10
private val queue: RequestQueue = Volley.newRequestQueue(this.context)
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ContentViewHolder {
val view = LayoutInflater.from(parent.context)
.inflate(R.layout.fragment_content, parent, false)
return ContentViewHolder(view as ViewGroup)
}
override fun onBindViewHolder(holder: ContentViewHolder, position: Int) {
super.onBindViewHolder(holder, position)
val content = getItem(position)
// Bind item to view
holder.bind(content)
}
fun refresh(callback: OnRefreshListener? = null) {
load(0, object: OnLoadListener() {
override fun onDataChanged() { callback?.onRefresh() }
override fun onDataReceive() { clearItems() }
})
}
override fun load(offset: Int, listener: OnLoadListener?) {
val url = API.Builder(API.LATEST_CONTENTS)
.appendQueryParameter("topic", filters.topicId)
.appendQueryParameter("offset", offset.toString())
.appendQueryParameter("limit", limit.toString())
.build().toString()
val request = JsonObjectRequest(
Request.Method.GET,
url,
null,
Response.Listener<JSONObject> { response ->
listener?.onDataReceive()
// Add received contents to cached contents
response.getJSONArray("contents").let {
(0 until it.length())
.forEach { i -> insert( it.getJSONObject(i) ) }
}
notifyDataSetChanged()
listener?.onDataChanged()
}, Response.ErrorListener { })
queue.add(request)
queue.start()
}
interface OnRefreshListener {
fun onRefresh()
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment