Search code examples
androidandroid-fragmentsandroid-listfragment

ListFragment is not display Data


I am working on a project where I have to display a list of available Professors for a department. Instead of displaying all professors, I want to allow a student to search professors by Department. As a result, the student will logs in, search for a professor based on name, department, course ID, or all. I am using a custom list adapter. I noticed that Adapter object is not null, but the list is still showing "No records available to display. I think the issue has to do with the way that I am setting the adapter in the ProfessorDetail class. What am I doing wrong here? See codes below:

Professors Class package com.mb.professor;

    import android.os.Bundle;
    import android.support.v4.app.FragmentActivity;
    import android.support.v4.app.FragmentManager;
    import android.support.v4.app.FragmentTransaction;
    import android.view.View;
    import android.widget.AdapterView;
    import android.widget.Button;
    import android.widget.EditText;
    import android.widget.Spinner;

    import com.mb.professor.asynctasks.ProfessorAsyncTask;

    /**
     * Created by Gagouche on 7/25/13.
     */
    public class Professors extends FragmentActivity {
       private Button bSearch;
        private EditText etSearchBy;
        private EditText etCourseId;
        private Spinner spSearchDecision;
        private String searchValue = null;
        private Professor[] _professor = null;
        public Professors()
        {

        }
        public Professors(Professor[] professor)
        {
            this._professor = professor;
        }
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.professor);
            InitialVariables();
        }

        private void InitialVariables()
        {
            bSearch = (Button) this.findViewById(R.id.bSearch);
            etSearchBy = (EditText) this.findViewById(R.id.etSearchByDepartment);
            etCourseId = (EditText) this.findViewById(R.id.etSearchByCouseId);
            spSearchDecision = (Spinner) this.findViewById(R.id.spOption);
            bSearch.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                  if(searchValue == "Department")
                    {

                        ProfessorAsyncTask professor = new ProfessorAsyncTask();
                        professor.execute("");

                        FragmentManager mFragment = getSupportFragmentManager();
                        FragmentTransaction ft = mFragment.beginTransaction();
                        ProfessorDetail pDetail = new ProfessorDetail();
                        pDetail.setProfessorAdapter(_professor);
                        ft.replace(R.id.fprofessorDetail, pDetail);
                        ft.addToBackStack(null);
                        ft.commit();
                    }
                }
            });

            spSearchDecision.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
                @Override
                public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
                     switch (position)
                     {
                         case 0:
                             searchValue = "By All";
                             break;
                         case 1:
                             searchValue = "Department";
                             break;
                         case 2:
                             searchValue = "CourseId";
                             break;
                     }
                }

                @Override
                public void onNothingSelected(AdapterView<?> parent) {
                    searchValue = "By All";
                }
            });
        }
    }

ProfessorDetail Class

  package com.mb.professor;

import android.os.Bundle;
import android.support.v4.app.ListFragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;

import com.mb.professor.adapter.*;

/**
 * Created by Gagouche on 7/25/13.
 */
public class ProfessorDetail extends ListFragment {
   private  ProfessorAdapter adapter = null;
    Professor[] prof = null;
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    }

    public void setProfessorAdapter(Professor[] professor)
    {
        prof = professor;
    }
    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        String [] emptyAdapter = {};
        if(prof == null)
        {
           ArrayAdapter<String> emptyListAdapter = new ArrayAdapter<String>(getActivity(),android.R.layout.simple_list_item_1,emptyAdapter);
           setListAdapter(emptyListAdapter);
        } else
        {
            adapter = new ProfessorAdapter(getActivity(), R.layout.professor_row, prof);
            adapter.notifyDataSetChanged();
            setListAdapter(adapter);
        }

    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.customizelayout, container, false);
    }
}

Course Detail Class

    package com.mb.professor;

    import android.os.Bundle;
    import android.support.v4.app.ListFragment;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.ArrayAdapter;

    import com.mb.professor.adapter.CourseAdapter;

    import java.util.List;

    /**
     * Created by Gagouche on 7/25/13.
     */
    public class CourseDetail extends ListFragment {
       private CourseAdapter adapter = null;
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
        }

        public void setCourseData(Course[] course)
        {
          adapter = new CourseAdapter(getActivity(), R.layout.course_row, course);
        }
        @Override
        public void onActivityCreated(Bundle savedInstanceState) {
            super.onActivityCreated(savedInstanceState);
            String[] course = {};
            if(adapter == null)
            {
                ArrayAdapter<String> emptyAdapter = new ArrayAdapter<String>(getActivity(), android.R.layout.simple_list_item_1 , course );
                setListAdapter(adapter);
            } else
            {
                setListAdapter(adapter);
            }
        }

        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
         //   super.onCreateView(inflater, container, savedInstanceState);
            return inflater.inflate(R.layout.customizelayout, container, false);
        }
    }

Login Course

    package com.mb.professor;

    import android.content.Intent;
    import android.os.Bundle;
    import android.app.Activity;
    import android.view.Menu;
    import android.view.View;
    import android.widget.Button;
    import android.widget.EditText;

    public class Login extends Activity implements View.OnClickListener {
        Button btnLogin;
        EditText etUsername, etPassword;
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.login);
            initializeVariables();
        }

        private void initializeVariables()
        {
           btnLogin = (Button) this.findViewById(R.id.btnLogin);
           etUsername = (EditText) this.findViewById(R.id.etUserName);
           etPassword = (EditText) this.findViewById(R.id.etPassword);
            btnLogin.setOnClickListener(this);
        }

        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            // Inflate the menu; this adds items to the action bar if it is present.
            getMenuInflater().inflate(R.menu.login, menu);
            return true;
        }

        @Override
        public void onClick(View v) {
            String uName = etUsername.getText().toString();
            String pWord = etPassword.getText().toString();
            if(uName.equals("college") && pWord.equals("florida"))
            {
               Intent intent = new Intent(this, Professors.class);
                startActivity(intent);
            }
        }
    }

Professor AsyncTask

       package com.mb.professor.asynctasks;

import android.os.AsyncTask;
import android.support.v4.app.FragmentActivity;

import com.mb.professor.Course;
import com.mb.professor.Professor;
import com.mb.professor.ProfessorDetail;
import com.mb.professor.Professors;
import com.mb.professor.R;

/**
 * Created by Gagouche on 8/1/13.
 */
public class ProfessorAsyncTask extends AsyncTask<String,Void,Professor[]> {
   private FragmentActivity fActivity;
    public ProfessorAsyncTask()
    {

    }
    @Override
    protected Professor[] doInBackground(String... params) {
        Professor[] professor = new Professor[5];
        professor[0] = new Professor("Finance", "John", "123", "Accounting");
        professor[1] = new Professor("Accounting", "Cain", "124", "finance");
        professor[2] = new Professor("Database", "Eugene", "125", "Music");
        professor[3] = new Professor("Finance", "Seikei", "126", "Engineer");
        professor[4] = new Professor("Finance", "Bojok", "127", "Math");

        return professor;
    }

    @Override
    protected void onPostExecute(Professor[] professors) {
        super.onPostExecute(professors);
       // ProfessorDetail professorDetailFragment = (ProfessorDetail)fActivity.getSupportFragmentManager().findFragmentById(R.id.fprofessorDetail);
     //   Professors prof = new Professors(professors);
    }
}

Course AsyncTask

    package com.mb.professor.asynctasks;

    import android.app.FragmentTransaction;
    import android.os.AsyncTask;
    import android.support.v4.app.FragmentActivity;

    import com.mb.professor.Course;
    import com.mb.professor.CourseDetail;
    import com.mb.professor.R;

    import java.util.List;

    /**
     * Created by Gagouche on 8/1/13.
     */
    public class CourseAsyncTask extends AsyncTask<String, Void, Course[]> {
    private FragmentActivity mActivity;
       private Course[] course = null;

        public CourseAsyncTask(FragmentActivity activity)
        {
            this.mActivity = activity;
        }
        @Override
        protected Course[] doInBackground(String... params) {
            Course[] course = new Course[5];
            course[0] = new Course("Finance", "John", "123");
            course[1] = new Course("Accounting", "Cain", "124");
            course[2] = new Course("Database", "Eugene", "125");
            course[3] = new Course("Finance", "Seikei", "126");
            course[4] = new Course("Finance", "Bojok", "127");

            return course;
        }

        @Override
        protected void onPostExecute(Course[] courses) {
            super.onPostExecute(courses);
            CourseDetail courseDetailFragment = (CourseDetail) mActivity.getSupportFragmentManager().findFragmentById(R.id.fCourseDetail);
            courseDetailFragment.setCourseData(courses);
        }
    }

Professor Adapter

    package com.mb.professor.adapter;

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

    import com.mb.professor.*;

    import java.util.List;

    /**
     * Created by Gagouche on 8/1/13.
     */
    public class ProfessorAdapter extends ArrayAdapter<Professor> {
        private Context context;
        private int layoutResourceId;
        private Professor[] data = null;
        public ProfessorAdapter(Context context, int layoutResourceId, Professor[] data) {
            super(context, layoutResourceId, data);
            this.context = context;
            this.layoutResourceId = layoutResourceId;
            this.data = data;
        }

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            View row = convertView;
            ProfessorHolder holder = null;
            if(row == null)
            {
                LayoutInflater inflater = ((Activity)context).getLayoutInflater();
                row = inflater.inflate(layoutResourceId,parent, false);
                holder = new ProfessorHolder();
                holder.tvFirstName = (TextView) row.findViewById(R.id.tvFirstName);
                holder.tvLastName = (TextView) row.findViewById(R.id.tvLastName);
                holder.tvCourse = (TextView) row.findViewById(R.id.tvCourseID);
                holder.tvDepartment = (TextView) row.findViewById(R.id.tvDepartment);
                row.setTag(holder);
            } else
            {
                holder = (ProfessorHolder) row.getTag();
            }

            Professor item = data[position];
            holder.tvFirstName.setText(item.getFirstName());
            holder.tvLastName.setText(item.getLastName());
            holder.tvDepartment.setText(item.getDepartmentID());
            holder.tvCourse.setText(item.getCourseId());
            return row;
        }

        static class ProfessorHolder
        {
          TextView tvFirstName;
          TextView tvLastName;
          TextView tvDepartment;
          TextView tvCourse;
        }
    }

Course Adapter

    package com.mb.professor.adapter;

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

    import com.mb.professor.Course;
    import com.mb.professor.R;

    /**
     * Created by Gagouche on 8/1/13.
     */
    public class CourseAdapter extends ArrayAdapter<Course> {
        private Context context;
        private int layoutResourceId;
        private Course[] data = null;
        public CourseAdapter(Context context, int resource, Course[] data) {
            super(context, resource, data);
            this.context = context;
            this.layoutResourceId = resource;
            this.data = data;
        }

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            View row = convertView;
            CourseHolder holder = null;
            if(row == null)
            {
                LayoutInflater inflater = ((Activity)context).getLayoutInflater();
                row = inflater.inflate(layoutResourceId, parent, false);
                holder = new CourseHolder();
                holder.tvCourseInstructor = (TextView) row.findViewById(R.id.tvCourseInstructor);
                holder.tvCourseId = (TextView) row.findViewById(R.id.tvCourse);
                holder.tvCourseName = (TextView) row.findViewById(R.id.tvCourseName);
                row.setTag(holder);
            } else {
                holder = (CourseHolder) row.getTag();
            }

            Course item = data[position];
            holder.tvCourseId.setText(item.getCourseId());
            holder.tvCourseName.setText(item.getCourseName());
            holder.tvCourseInstructor.setText(item.getInstructorName());
            return row;
        }

        static class CourseHolder
        {
            TextView tvCourseName;
            TextView tvCourseInstructor;
            TextView tvCourseId;
        }
    }

Login XML

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="User Name"
                android:id="@+id/textView"
                android:layout_alignParentTop="true"
                android:layout_marginTop="30dp"
                android:layout_gravity="center_horizontal"
                android:layout_centerHorizontal="true"
                android:textSize="30sp"
                />

        <EditText
                android:layout_width="200sp"
                android:layout_height="wrap_content"
                android:id="@+id/etUserName"
                android:layout_below="@+id/textView"
                android:layout_centerHorizontal="true"
                android:layout_gravity="center_horizontal"
                android:layout_marginTop="10dp"/>

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="Password"
                android:id="@+id/textView2"
                android:layout_below="@+id/editText"
                android:layout_centerHorizontal="true"
                android:layout_gravity="center_horizontal"
                android:layout_marginTop="10dp"
                android:textSize="30sp"
                />

        <EditText
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:inputType="textPassword"
                android:ems="10"
                android:id="@+id/etPassword"
                android:layout_below="@+id/textView2"
                android:layout_centerHorizontal="true"
                android:layout_gravity="center_horizontal"
                android:layout_marginTop="10dp"
                />

        <Button
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="Login"
                android:id="@+id/btnLogin"
                android:layout_gravity="center_horizontal"
                android:layout_centerVertical="true"
                android:layout_centerHorizontal="true"/>
    </LinearLayout>

Professor XML

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


        <LinearLayout
                android:layout_width="0dp"
                android:layout_height="fill_parent"
                android:orientation="vertical"
                android:layout_weight="1"
                >
            <TextView
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:text="Search For Professor"
                    android:id="@+id/textView"
                    android:layout_marginTop="10dp"
                    android:layout_marginLeft="10dp"
                    android:textSize="30sp"
                    />
            <EditText
                    android:layout_width="250dp"
                    android:layout_height="wrap_content"
                    android:hint="search by Department"
                    android:id="@+id/etSearchByDepartment"
                    android:layout_marginLeft="10dp"
                    android:layout_marginTop="5dp"
                    />

            <TextView
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:text="Search by Course ID"
                    android:id="@+id/textView2"
                    android:layout_marginTop="10dp"
                    android:layout_marginLeft="10dp"
                    android:textSize="30sp"
                    />

            <EditText
                    android:layout_width="250dp"
                    android:layout_height="wrap_content"
                    android:id="@+id/etSearchByCouseId"
                    android:layout_marginLeft="10dp"
                    android:layout_marginTop="5dp"
                    />

            <Spinner
                    android:layout_width="321dp"
                    android:layout_height="wrap_content"
                    android:id="@+id/spOption"
                    android:entries="@array/searchOption"
                    android:layout_marginLeft="10dp"
                    android:layout_marginTop="5dp"

                    />
            <Button
                    android:id="@+id/bSearch"
                    android:text="Search"
                    android:layout_height="wrap_content"
                    android:layout_width="wrap_content"
                    android:layout_marginTop="10dp"
                    android:layout_marginLeft="5dp"
                    />

        </LinearLayout>

        <LinearLayout
                android:layout_width="0dp"
                android:layout_height="fill_parent"
                android:layout_weight="2"
                android:orientation="vertical"
                >

            <fragment
                    android:layout_width="match_parent"
                    android:layout_height="0dp"
                    android:name="com.mb.professor.ProfessorDetail"
                    android:id="@+id/fprofessorDetail"
                    android:layout_weight="1"
                    android:layout_gravity="center"/>

            <fragment
                    android:layout_width="match_parent"
                    android:layout_height="0dp"
                    android:layout_weight="2"
                    android:name="com.mb.professor.CourseDetail"
                    android:id="@+id/fCourseDetail"
                    android:layout_gravity="center"/>


        </LinearLayout>
    </LinearLayout>

Professor Row Custom XML

    <?xml version="1.0" encoding="utf-8"?>

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
                  android:orientation="horizontal"
                  android:layout_width="match_parent"
                  android:layout_height="match_parent">

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="First Name"
                android:layout_marginLeft="10dp"
                android:id="@id/tvFirstName"
                android:layout_gravity="center_horizontal|top"/>

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="Last Name"
                android:layout_marginLeft="10dp"
                android:id="@id/tvFirstName"
                android:layout_gravity="center_horizontal|top"/>

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="New Text"
                android:layout_marginLeft="10dp"
                android:id="@id/tvDepartment"
                android:layout_gravity="center_horizontal|top"/>

        <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginLeft="10dp"
                android:text="New Text"
                android:id="@id/tvCourseID"
                android:layout_gravity="center_horizontal|top"/>
    </LinearLayout>

Customize Layout for the ListViews

    <?xml version="1.0" encoding="utf-8"?>

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
                  android:orientation="vertical"
                  android:layout_width="match_parent"
                  android:layout_height="match_parent">
        <ListView
                android:id="@id/android:list"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="left|center_vertical"/>
        <TextView
                android:id="@id/android:empty"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="No Record to be displayed."
                android:textSize="25sp"
                android:layout_gravity="left|center_vertical"/>


    </LinearLayout>

Here is the exception:

08-05 13:26:25.619 716-731/com.android.exchange D/ExchangeService: Received deviceId from Email app: null 08-05 13:26:25.619 716-731/com.android.exchange D/ExchangeService: !!! deviceId unknown; stopping self and retrying 08-05 13:26:27.242 1055-1055/com.mb.professor D/AndroidRuntime: Shutting down VM 08-05 13:26:27.242 1055-1055/com.mb.professor W/dalvikvm: threadid=1: thread exiting with uncaught exception (group=0x40a71930) 08-05 13:26:27.302 1055-1055/com.mb.professor E/AndroidRuntime: FATAL EXCEPTION: main java.lang.NullPointerException: storage == null at java.util.Arrays$ArrayList.(Arrays.java:38) at java.util.Arrays.asList(Arrays.java:154) at android.widget.ArrayAdapter.(ArrayAdapter.java:128) at com.mb.professor.adapter.ProfessorAdapter.(ProfessorAdapter.java:23) at com.mb.professor.ProfessorDetail.setProfessorAdapter(ProfessorDetail.java:23) at com.mb.professor.Professors$1.onClick(Professors.java:57) at android.view.View.performClick(View.java:4204) at android.view.View$PerformClick.run(View.java:17355) at android.os.Handler.handleCallback(Handler.java:725) at android.os.Handler.dispatchMessage(Handler.java:92) at android.os.Looper.loop(Looper.java:137) at android.app.ActivityThread.main(ActivityThread.java:5041) at java.lang.reflect.Method.invokeNative(Native Method) at java.lang.reflect.Method.invoke(Method.java:511) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560) at dalvik.system.NativeStart.main(Native Method)


Solution

  • Am I mistaking ? but you call notifyDataSetChange before the asynctask is finished. You have to call notifyDataSetChange in the onPostExecute of your async task. And therefore your list is empty.

    In your code you do in the Professor detail class

    adapter = new ProfessorAdapter(getActivity(), R.layout.professor_row, prof);
    adapter.notifyDataSetChanged();
    setListAdapter(adapter);
    

    you notify the data change and link the adapter to the list. But you never do it again. Your onPost Execute is empty.

    What you have to do is move the adapter.notifyDataSetChanged(); to the onPostExecute and your list will be refreshed.

    EDIT

    Let me show you an example of my code.

    public class MyAsyncTaskFragment extends Fragment {
        private ListView lv;
        private CustomAdapter adapter;
        private ArrayList<...your custom type here...> listItems = new ArrayList<...your custom type here...>(); 
    
        ...
    
        @Override
        public void onActivityCreated (Bundle savedInstanceState){ 
            //get the listView
            lv = (ListView) getView().findViewById(R.id.my_listview_name); 
    
            //create new adapter
            adapter = new CustomAdapter();
    
            //link adapter to listview
            lv.setAdapter(adapter);
    
            //in my case I want the async task to start over when the activity is created
            new DoAsyncTask().execute(); 
        }
    
        private class DoAsyncTask extends AsyncTask<Void, Integer, Integer>{
            protected void onPreExecute() {                                        
                listItems.clear(); 
            }
    
            protected Integer doInBackground(Void...voids) {
                //add items to the list                
                listItems.add(...your custom type here ...);
                return null;
            }
    
            protected void onPostExecute(Integer result) {
                if (listItems.size() > 0){ 
                    adapter.notifyDataSetChanged(); 
                }
            }
    
        }    
    }