Wednesday, May 13, 2015

Android Custom ListView

 Customizing Android ListView with Custom ArrayAdapter.

Dear Followers today I am going to show you the android custom ListView with custom Array Adapter. if someone is newbie on Listview please see my previous post on simple Android Listview.
http://itsjavasinception.blogspot.in/2015/05/android-listview-with-adapter-in.html
all of you know the default look and feel of Listview  in android is not so interactive, so in this tutorial I will show you how to create custom Listview with custom adapter.
I am creating custome listview for college management member list with there profile pic and names.

see the below screenshots of this tutorial.


Create a new Android project in Eclipse with Management as your Activity and management_activity.xml as your layout file. Declare a ListView control in your management_activity.xml layout file as shown in the following code. 


management_activity.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical" >

    <ImageView
        android:id="@+id/imageView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:adjustViewBounds="true"
        android:src="@drawable/banner" />

    <ListView
        android:id="@+id/list"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@drawable/list_selector" />

</LinearLayout>


The above code is using simple LinearLayout with vertical orientation, and a ListView is declared to cover the entire width and height of the parent container using the fill_parent as the value of both android:layout_height and android:layout:width properties. ListView also has a unique id list that will be used in the Management Activity to reference the ListView control.



To create a custom ListView row, create another xml layout file mangmt_list_item.xml in the project layout directory. Android will render this file content in every ListView item and you are free to declare any control you want in it. For this tutorial I am using an ImageView for an profile pic and a TextView for displaying persone names. 

mangmt_list_item.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:background="@drawable/list_selector"
    android:orientation="horizontal" >

    <ImageView
        android:id="@+id/profile_pic"
        android:layout_width="70dp"
        android:layout_height="70dp"
        android:contentDescription="desc"
        android:paddingLeft="10dp"
        android:paddingRight="10dp" />

    <TextView
        android:id="@+id/member_name"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="10dp"
        android:layout_toRightOf="@+id/profile_pic"
        android:paddingBottom="10dp"
        android:text="txt"
        android:textSize="20sp" />

    <TextView
        android:id="@+id/status"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/member_name"
        android:layout_below="@+id/member_name"
        android:text="txt"
        android:textSize="16sp" />
    <!-- Rightend Arrow -->

    <ImageView
        android:id="@+id/contact_type"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignBaseline="@+id/member_name"
        android:layout_alignBottom="@+id/member_name"
        android:layout_alignParentRight="true"
        android:layout_centerVertical="true" />

</RelativeLayout>



Now create one Model class as:


Next create a new Java class in your project and named it ManagementRowItem.java. This class will be used to create a custom ArrayAdapter and to bind the objects with the ListView later in this tutorial. Following is the code of ManagementRowItem.java class. It has four simple properties profile_pic, member_name, status and contactType_id and a typical class constructor to initialize the properties. 
And also this class having getter setter methods. 

ManagementRowItem.java



public class ManagementRowItem {

     private String member_name;
     private int profile_pic_id;
     private String status;
     private int contactType_id;

     public ManagementRowItem(String member_name, int profile_pic_id, String status,
       int contactType_id) {

      this.member_name = member_name;
      this.profile_pic_id = profile_pic_id;
      this.status = status;
      this.contactType_id = contactType_id;
     }

     public String getMember_name() {
      return member_name;
     }

     public void setMember_name(String member_name) {
      this.member_name = member_name;
     }

     public int getProfile_pic_id() {
      return profile_pic_id;
     }

     public void setProfile_pic_id(int profile_pic_id) {
      this.profile_pic_id = profile_pic_id;
     }

     public String getStatus() {
      return status;
     }

     public void setStatus(String status) {
      this.status = status;
     }

     public int getContactType_id() {
      return contactType_id;
     }

     public void setContactType_id(int contactType_id) {
      this.contactType_id = contactType_id;
     }

    }


Notice that the above mangmt_list_item.xml file has four views, which are correspondent to the properties of the ManagementRowItem class. The values of the ManagementRowItem class properties will be displayed on those views and to connect these four pieces together you need to create a custom ArrayAdapter that will inherit the Android BaseAdapter class and will override the getView method. Add a new java class in your project with the name  

MangmtCustomAdapter .java

import java.util.List;

import com.sumago.portal.R;

import android.app.Activity;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;

public class MangmtCustomAdapter extends BaseAdapter {

 Context context;
 List<ManagementRowItem> managementRowItems;

 public MangmtCustomAdapter(Context context, List<ManagementRowItem> managementRowItems) {
  this.context = context;
  this.managementRowItems = managementRowItems;
 }

 @Override
 public int getCount() {
  return managementRowItems.size();
 }

 @Override
 public Object getItem(int position) {
  return managementRowItems.get(position);
 }

 @Override
 public long getItemId(int position) {
  return managementRowItems.indexOf(getItem(position));
 }

 /* private view holder class */
 private class ViewHolder {
  ImageView profile_pic;
  TextView member_name;
  TextView status;
  ImageView contactType;
 }

 @Override
 public View getView(int position, View convertView, ViewGroup parent) {

  ViewHolder holder = null;

  LayoutInflater mInflater = (LayoutInflater) context
    .getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
  if (convertView == null) {
   convertView = mInflater.inflate(R.layout.mangmt_list_item, null);
   holder = new ViewHolder();

   holder.member_name = (TextView) convertView
     .findViewById(R.id.member_name);
   holder.profile_pic = (ImageView) convertView
     .findViewById(R.id.profile_pic);
   holder.status = (TextView) convertView.findViewById(R.id.status);
   holder.contactType = (ImageView) convertView
     .findViewById(R.id.contact_type);

   ManagementRowItem row_pos = managementRowItems.get(position);

   holder.profile_pic.setImageResource(row_pos.getProfile_pic_id());
   holder.member_name.setText(row_pos.getMember_name());
   holder.status.setText(row_pos.getStatus());
   holder.contactType.setImageResource(row_pos.getContactType_id());

   convertView.setTag(holder);
  } else {
   holder = (ViewHolder) convertView.getTag();
  }

  return convertView;
 }

}



In the above code, the first important thing is the constructor of the class that takes two parameters. The first parameter is the Context and we can pass the reference of the activity in which we will use MangmtCustomAdapter class.
The second parameter is an List of ManagementRowItem class objects that will be used by the Adapter to display data. 
Next the parent class getView method is overridden. This method will be called for every item in the ListView to create views with their properties set as we want. The getView method is also using a temporary holder class declared inside the MangmtCustomAdapter class. This class will be used to cache the ImageView and TextView so they can be reused for every row in the ListView and this will provide us a great performance improvement as we are recycling the same two views with different properties and we don’t need to find ImageView and TextView for every ListView item.

The final piece of code is our application MainActivity in which we will be using all the above objects we declared. Following is the code of the Management.java file.

 Management.java

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import android.app.Activity;
import android.content.Intent;
import android.content.res.TypedArray;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ListView;

import com.sumago.portal.CollageApp;
import com.sumago.portal.LoginPage;
import com.sumago.portal.R;
import com.sumago.portal.utility.ManagementRowItem;
import com.sumago.portal.utility.Managementinfo;
import com.sumago.portal.utility.MangmtCustomAdapter;

public class Management extends Activity implements OnItemClickListener {

    String[] member_names;
    TypedArray profile_pics, contactType;
    String[] statues;
    static final String TAG_IMAGES = "images";
    List<ManagementRowItem> managementRowItems;
    ListView mylistview;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.management_activity);

        managementRowItems = new ArrayList<ManagementRowItem>();

        member_names = getResources().getStringArray(R.array.Member_names);

        profile_pics = getResources().obtainTypedArray(R.array.profile_pics);

        statues = getResources().getStringArray(R.array.statues);

        contactType = getResources().obtainTypedArray(R.array.contactType);

        for (int i = 0; i < member_names.length; i++) {
            ManagementRowItem item = new ManagementRowItem(member_names[i],
                    profile_pics.getResourceId(i, -1), statues[i],
                    contactType.getResourceId(i, -1));
            managementRowItems.add(item);
        }

        mylistview = (ListView) findViewById(R.id.list);
        MangmtCustomAdapter adapter = new MangmtCustomAdapter(this,
                managementRowItems);
        mylistview.setAdapter(adapter);
        profile_pics.recycle();
        mylistview.setOnItemClickListener(this);

    }

    @Override
    public void onItemClick(AdapterView<?> parent, View view, int position,
            long id) {
        String selected = managementRowItems.get(position).getMember_name();
        int imgs = managementRowItems.get(position).getProfile_pic_id();
        Log.v("item selected", "on item click " + selected);
        Intent i = new Intent(getApplicationContext(), Managementinfo.class);

        Bundle b = new Bundle();
        b.putString("name", selected);

        i.putExtras(b);
        i.putExtra("imgss", imgs);
        startActivity(i);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        MenuInflater inflater = getMenuInflater();
        inflater.inflate(R.menu.managemnt, menu);
        return true;

    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {

        case R.id.logout:

            Intent logout = new Intent(Management.this, LoginPage.class);
            startActivity(logout);
            overridePendingTransition(R.anim.slide_in, R.anim.slide_out);

            return true;

        case R.id.home:

            Intent home = new Intent(Management.this, CollageApp.class);
            startActivity(home);
            overridePendingTransition(R.anim.slide_in, R.anim.slide_out);

            return true;

        }
        return false;
    }

    @Override
    protected void onResume() {
        // adapter.notifyDataSetChanged();
        super.onResume();
    }

    @Override
    public void onBackPressed() {
        Intent intent = new Intent(this, CollageInformation.class);
        intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP
                | Intent.FLAG_ACTIVITY_NEW_TASK);
        startActivity(intent);
    }




string.xml file for getting array values 

 /*
 <!-- management Person list -->
    <!-- Names -->
    <string-array name="Member_names">
        <item>Shri.Balasaheb D. Wagh.</item>
        <item>Shri.Kashinath B. Tarle.</item>
        <item>Shri.Ashok R.Merchant.</item>
        <item>Shri.Changdeorao B.Holkar</item>
        <item>Shri.D.S. Shinde</item>
         <item>Dr(Mrs.)Priti D.Bhamare</item>
      <!--   <item>Dr. K.N.Nandurkar</item>
        <item>Dr(Mrs.)Priti D.Bhamare</item>
        <item>Dr.Shirish S.Sane</item> -->
    </string-array>

    <!-- Pictures -->
    <array name="profile_pics">
        <item>@drawable/bhau</item>
        <item>@drawable/bhaua</item>
        <item>@drawable/bhaub</item>
        <item>@drawable/bhauc</item>
        <item>@drawable/bhaud</item>
         <item>@drawable/mavshi</item>
      <!--   <item>@drawable/bhaue</item>
      
        <item>@drawable/bhauf</item> -->
    </array>

    <!-- Status -->
    <string-array name="statues">
        <item>President KKW</item>
        <item>Vice President</item>
        <item>Trustee</item>
        <item>Trustee</item>
        <item>Trustee</item>
          <item>Staff Representative</item>
        <!-- <item>Trustee</item>
     
        <item>Trustee</item> -->
    </string-array>

    <!-- contact type -->
    <string-array name="contactType">
        <item>@drawable/right_arrow_icon</item>
        <item>@drawable/right_arrow_icon</item>
        <item>@drawable/right_arrow_icon</item>
        <item>@drawable/right_arrow_icon</item>
        <item>@drawable/right_arrow_icon</item>
        <item>@drawable/right_arrow_icon</item>
    </string-array>

*/ 

There are few things in the Management that required explanation for your better understanding. First notice, we are creating an array of each properties those we initialized in Model class (ManagementRowItem) class here I am getting array values from string.xml file passed as constructor parameters. 
Finally we are passing our custom adapter to ListView setAdapter method. That’s about it. You are ready to build and run our project. If everything implemented properly you will see the following output.



Note: you have to get your images with there specific names to run this project perfectely. Thanks!


stay tune for next session..happy codding :)


   

No comments:

Post a Comment