Android ListView → Kotlin Android – Custom ListView – CardViews with Images and Text – Camposha

Android ListView

Android ListView

Android ListView

Kotlin Android – Custom ListView – CardViews with Images and Text

In this class we see how to work with ListView, CardView in android. We want to create a simple app to show zen quotes. So we will have a custom listview with text and images. These will be inside a ListView and we will listen to click events of these cardviews and show the quote in a Toast message.

Our programming language is Kotlin.

What is a ListView?

A ListView is a control that displays a list of items vertically.

It is one of the most commonly used widgets in android. This is because most mobile applications involve dispaying list of items. Mostly these items are images and texts.

In a ListView, if we have a list of items that need to be viewed and the number exceeds the beyond the currently visible viewport,users can scroll to see the rest of items.

You can use a ListView in two ways:

  1. Creating an Activity that extends the android.app.ListActivity. With a ListView is added to you implicitly.
  2. Adding a ListView explicitly via XML layout.

Alot of people prefer the second approach as it’s most flexible since we get to design our own UI.

We have a YouTube Channel By the Way

So if you prefer video tutorial check here:

ListView API definition

ListView is concrete class that resides in the android.widget package. So it’s a widget.

package android.widget;

It derives from android.widget.AbsListView:

public class ListView extends AbsListView{..} 

Here’s the clas hierarchy:

java.lang.Object
   ↳    android.view.View
       ↳    android.view.ViewGroup
           ↳    android.widget.AdapterView<android.widget.ListAdapter>
               ↳    android.widget.AbsListView
                   ↳    android.widget.ListView

ListView was added in API level 1 and still stands as one of the most widely used AdapterView, even with the introduction of the RecyclerView.

Adapter

We said ListViews are views that show items in a vertically scrolling list.

Normally these items have to come from somewhere, some data source. Well the bridge between that data source and the ListView(or any AdapterView) is the Adapter.

It is the Adapter that provides the access to the underlying data. The Adapter is also responsible for making a view for each item in the data set.

Normally there are several adapters like:

  1. ArrayAdapter.
  2. CursorAdapter.
  3. SimpleCursorAdapter.
  4. BaseAdapter.

In this class we use the BaseAdapter.

Custom ListView with Images and Text in Kotlin

Let’s now look at our Kotlin custom listview example.

We will show lists with images and texts and handle the itemClicks thus showing a Toast message with the clicked item.

Add ListView in Layout

First add a ListView in your XML layout. Assign the ListView an ID for identification from our Kotlin code.

    <ListView
        android:id="@+id/myListView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />

Specify Imports

We then add our import statements on top of our Kotlin class.

import android.content.Context
import android.support.v7.app.AppCompatActivity
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.*
import java.util.ArrayList

Turn our class into an Activity

We do this by deriving from Activity or AppCompatActivity.

class MainActivity : AppCompatActivity() {..}

Create our Data Object

We will be showing a List of quotes so we need to create a Kotlin data object class to represent a single quote.

    class Quote(private var quote:String, private var author: String, private var image: Int) {

        fun getQuote(): String { return quote  }
        fun getAuthor(): String { return author }
        fun getImage(): Int { return image  }
    }

Create a Custom Adapter

We will create another inner class that will be extending the baseAdapter. This is our adapter class and will adapt our data to our custom view.

It will also inflate our custom row_model layout into an a view object.

  class CustomAdapter(private var c: Context, private var quotes: ArrayList<Quote>) : BaseAdapter() {..}

Check complete source below.

Create Data Source

We will create an arraylist that will act as our data source. This arraylist will be passed to our CustomAdapter constructor:

    private val data: ArrayList<Quote>
        get() {
            val quotes = ArrayList<Quote>()
            ....
            return quotes;
        }

Reference ListView and Set its Adapter

This we do in the onCreate() method of our MainActivity:

        myListView = findViewById(R.id.myListView) as ListView

        //instantiate and set adapter
        adapter = CustomAdapter(this, data)
        myListView.adapter = adapter

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context="info.camposha.kotlinlistviewcardviews.MainActivity">

    <TextView
        android:id="@+id/textView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Zen Quotes App"
        android:textAlignment="center"
        android:textAppearance="@style/TextAppearance.AppCompat.Large"
        android:textColor="@color/colorAccent" />

    <ListView
        android:id="@+id/myListView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />

</LinearLayout>

MainActivity.java

package info.camposha.kotlinlistviewcardviews
import android.content.Context
import android.support.v7.app.AppCompatActivity
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.*
import java.util.ArrayList
class MainActivity : AppCompatActivity() {
/*
Our data object class.
*/
class Quote(private var quote:String, private var author: String, private var image: Int) {
fun getQuote(): String { return quote  }
fun getAuthor(): String { return author }
fun getImage(): Int { return image  }
}
/*
Our Custom Adapter class. Derives from BaseAdapter.
*/
class CustomAdapter(private var c: Context, private var quotes: ArrayList<Quote>) : BaseAdapter() {
override fun getCount(): Int   {  return quotes.size  }
override fun getItem(i: Int): Any {  return quotes[i] }
override fun getItemId(i: Int): Long { return i.toLong()}
override fun getView(i: Int, view: View?, viewGroup: ViewGroup): View {
var view = view
if (view == null) {
//inflate layout resource if its null
view = LayoutInflater.from(c).inflate(R.layout.row_model, viewGroup, false)
}
//get current quote
val quote = this.getItem(i) as Quote
//reference textviews and imageviews from our layout
val img = view!!.findViewById<ImageView>(R.id.imageView) as ImageView
val nameTxt = view.findViewById<TextView>(R.id.quoteTxt) as TextView
val propTxt = view.findViewById<TextView>(R.id.authorTxt) as TextView
//BIND data to TextView and ImageVoew
nameTxt.text = quote.getQuote()
propTxt.text = quote.getAuthor()
img.setImageResource(quote.getImage())
//handle itemclicks for the ListView
view.setOnClickListener { Toast.makeText(c, quote.getQuote(), Toast.LENGTH_SHORT).show() }
return view
}
}
//Main Activity Instance Fields.
private lateinit var adapter: CustomAdapter
private lateinit var myListView: ListView
// our data source
private val data: ArrayList<Quote>
get() {
val quotes = ArrayList<Quote>()
var quote = Quote("Out beyond ideas of wrongdoing and rightdoing there is a field.I'll meet you there." +
"When the soul lies down in that grass the world is too full to talk about.","Rumi",R.drawable.rumi)
quotes.add(quote)
quote= Quote("Walk as if you are kissing the Earth with your feet.","Thich Nhat Hanh",R.drawable.thich)
quotes.add(quote)
quote= Quote("Man suffers only because he takes seriously what the gods made for fun.","Allan Watts",R.drawable.allan_watts)
quotes.add(quote)
quote= Quote("I have lived with several Zen masters -- all of them cats.","Eckhart Tolle",R.drawable.eckhart)
quotes.add(quote)
quote= Quote("I'm simply saying that there is a way to be sane. I'm saying that you can get rid of all this insanity created" +
" by the past in you. Just by being a simple witness of your thought processes.","Osho",R.drawable.osho)
quotes.add(quote)
quote= Quote("The way out is through the door. Why is it that no one will use this method?","Confucius",R.drawable.confucius)
quotes.add(quote)
quote= Quote("It is the power of the mind to be unconquerable.","Senecca",R.drawable.jiddu)
quotes.add(quote)
quote= Quote("It's like you took a bottle of ink and you threw it at a wall. Smash! And all that ink spread. And in " +
"the middle, it's dense, isn't it? ","Allan Watts",R.drawable.allan_watts)
quotes.add(quote)
quote= Quote("Only the hand that erases can write the true thing.","Meister Eckhart",R.drawable.allan_watts)
quotes.add(quote)
quote= Quote("Many have died; you also will die. The drum of death is being beaten. The world has fallen in love with a " +
"dream. Only sayings of the wise will remain."," Kabir",R.drawable.osho)
quotes.add(quote)
quote= Quote("Where there are humans, You'll find flies,And Buddhas.","Kobayashi Issa",R.drawable.eckhart)
quotes.add(quote)
quote= Quote("Silence is the language of Om. We need silence to be able to reach our Self. Both internal and external " +
"silence is very important to feel the presence of that supreme Love.","Amit Ray",R.drawable.jiddu)
quotes.add(quote)
quote= Quote("One day in my shoes and a day for me in your shoes, the beauty of travel lies in the ease and willingness " +
"to be more open.","Forrest Curran",R.drawable.confucius)
quotes.add(quote)
quote= Quote("Like vanishing dew,a passing apparition or the sudden flashnof lightning -- already gone -- thus should" +
" one regard one's self.","Ikyyu",R.drawable.thich)
quotes.add(quote)
quote= Quote("A student, filled with emotion and crying, implored, 'Why is there so much suffering? Suzuki Roshi " +
"replied, No reason.' ","Suzuki Roshi",R.drawable.rumi)
quotes.add(quote)
return quotes
}
/*
When activity is created, reference ListView and set its adapter
*/
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
myListView = findViewById(R.id.myListView) as ListView
//instantiate and set adapter
adapter = CustomAdapter(this, data)
myListView.adapter = adapter
}
}
Kotlin Android Custom ListView Images text
Kotlin Android Custom ListView Images text

Best regards.

Leave a Reply

Your email address will not be published. Required fields are marked *

Price

Free

Rating

Not enough ratings to display
X