ListView displaying same data

2019-08-09 23:58发布

问题:

I have a large JSON array. I am reading the data from JSON array and storing it in a list view, But the list view repeats the same data.

i.e the last data from the JSON instead of displaying all the data.

Here is my code.

public class HistoryActivity extends AppCompatActivity {
private Toolbar toolbar;
String strServerResponse = null;
ProgressDialog nDialog;
Pojo pojo;
ArrayList<Pojo> history;
HistoryAdapter myAdapter;
ListView list;
public String date, inTime, outTime, inLat, inLong;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_history);
    toolbar = (Toolbar) findViewById(R.id.app_bar);
    toolbar.setTitle("History");
    setSupportActionBar(toolbar);
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);
    list = (ListView) findViewById(R.id.historyList);
    history = new ArrayList<Pojo>();
    new NetCheck().execute();

}

private class NetCheck extends AsyncTask<Void, Void, Void> {


    @Override
    protected void onPostExecute(Void result) {
        // TODO Auto-generated method stub
        super.onPostExecute(result);

        nDialog.dismiss();
        // TODO Auto-generated method stub
        myAdapter = new HistoryAdapter(HistoryActivity.this, history);
        list.setAdapter(myAdapter);
    }

    @Override
    protected Void doInBackground(Void... params) {
        // TODO Auto-generated method stub

        try {

            HttpClient httpClient = new DefaultHttpClient();

            HttpPost httpRequest = new HttpPost(

                    "http://myurl");
            httpRequest.setHeader("Content-Type", "application/json");
            SharedPreferences mmm = getSharedPreferences(
                    "MyPref", MODE_PRIVATE);

            String logempid = mmm.getString("id", null);

            JSONObject json = new JSONObject();

            json.put("empid", logempid);

            Log.e("JSON Object", json.toString());

            StringEntity se = new StringEntity(json.toString());

            se.setContentEncoding("UTF-8");
            se.setContentType("application/json");

            httpRequest.setEntity(se);
            HttpResponse httpRes = httpClient.execute(httpRequest);

            java.io.InputStream inputStream = httpRes.getEntity()
                    .getContent();
            InputStreamReader inputStreamReader = new InputStreamReader(
                    inputStream);

            BufferedReader reader = new BufferedReader(inputStreamReader);
            StringBuilder sb = new StringBuilder();
            String line = null;
            while ((line = reader.readLine()) != null) {
                sb.append(line + "\n");
            }
            inputStream.close();
            strServerResponse = sb.toString();
            Log.e("Server Response", "" + strServerResponse.toString());

            if (strServerResponse != null) {
                try {

                    JSONArray arr = new JSONArray(strServerResponse);

                    for (int k = 0; k < arr.length(); k++) {

                        JSONObject jsonObj1 = arr.getJSONObject(k);

                        pojo = new Pojo();
                        date = jsonObj1.optString("login_date");
                        inTime = jsonObj1.optString("login_time");
                        outTime = jsonObj1.optString("logout_time");

                        Log.e("login time from server",""+inTime);
                        Log.e("login out from server",""+outTime);
                        Log.e("login date from server",""+date);
                        pojo.setDate(date);
                        pojo.setLoginTime(inTime);
                        pojo.setLogoutTime(outTime);

                        JSONArray subArrayLat = jsonObj1.getJSONArray("lati_long");
                        for (int i = 0; i < subArrayLat.length(); i++) {
                            String lat = subArrayLat.getJSONObject(i).getString("Latitude").toString();
                            String loong = subArrayLat.getJSONObject(i).getString("Longitude").toString();
                            Log.e("jsonarray lat", "" + lat);
                            Log.e("jsonarray longg", "" + loong);
                            pojo.setLat(lat);
                            pojo.setLong(loong);
                        }

                        history.add(pojo);
                    }

                } catch (JSONException e) {
                    e.printStackTrace();
               }
      }

Here is the adapter.

 public class HistoryAdapter extends BaseAdapter {
private Context activity;
TextView tv_date;
TextView tv_loginTime;
TextView tv_logoutTime;
TextView tv_details;
Pojo pojo;
ArrayList<Pojo> list;
private ArrayList<Pojo> arraylist = null;
public static LayoutInflater inflater;
private Context context;

public HistoryAdapter(Context context) {
    this.context = context;
}


public HistoryAdapter(Context a, ArrayList<Pojo> history) {
    // TODO Auto-generated constructor stub
    activity = a;
    list = history;
    inflater = (LayoutInflater) activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    this.arraylist = new ArrayList<Pojo>();
    this.arraylist.addAll(list);

}

@Override
public int getCount() {
    // TODO Auto-generated method stub
    return list.size();
}

@Override
public Object getItem(int position) {
    // TODO Auto-generated method stub
    return list.get(position);
}

@Override
public long getItemId(int position) {
    // TODO Auto-generated method stub
    return position;
}

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    // TODO Auto-generated method stub
    View v = convertView;


    v = inflater.inflate(R.layout.history_item, parent, false);
    pojo = list.get(position);
    tv_date = (TextView) v.findViewById(R.id.historyDate);
    tv_loginTime = (TextView) v.findViewById(R.id.historyLoginTime);
    tv_logoutTime = (TextView) v.findViewById(R.id.historyLogoutTime);
    tv_details = (TextView) v.findViewById(R.id.historyDetails);

    tv_date.setText(pojo.getDate());
    tv_loginTime.setText(pojo.getLoginTime());
    tv_logoutTime.setText(pojo.getLogoutTime());
    final String lat = pojo.getLat().toString();
    String longg = pojo.getLong().toString();
    Log.e("adapter latitude", "" + lat);
    Log.e("adapter longitude", "" + longg);
    tv_details.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Intent i = new Intent(context, MapActivity.class);
            i.putExtra("lat", "" + lat);
            i.putExtra("longg", "+longg");
            context.startActivity(i);
        }
    });

    return v;

}

 }

This is JSON data

[
  {
    "login_time": "10:30:28",
    "logout_time": "10:31:47",
    "login_date": "2015- 09-30",
    "lati_long": [
      {
        "date_time": "2015:09:30  11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:52",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:17:16",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      }
    ]
  },
  {
    "login_time": "10:42:56",
    "logout_time": "10:44:41",
    "login_date": "2015-09-30",
    "lati_long": [
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:52",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:17:16",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:52",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:17:16",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      }
    ]
  }
]

Is there anything wrong here? Please help me.

回答1:

You have declared Your CustomObject Pojo's variable is global variable. declare it as Local variable

for (int k = 0; k < arr.length(); k++) {

         JSONObject jsonObj1 = arr.getJSONObject(k);
         Pojo pojo = new Pojo();
         date = jsonObj1.optString("login_date");
         inTime = jsonObj1.optString("login_time");
         outTime = jsonObj1.optString("logout_time");

         Log.e("login time from server",""+inTime);
         Log.e("login out from server",""+outTime);
         Log.e("login date from server",""+date);
         pojo.setDate(date);
         pojo.setLoginTime(inTime);
         pojo.setLogoutTime(outTime);

         JSONArray subArrayLat = jsonObj1.getJSONArray("lati_long");
         for (int i = 0; i < subArrayLat.length(); i++) {
                 String lat = subArrayLat.getJSONObject(i).getString("Latitude").toString();
                 String loong = subArrayLat.getJSONObject(i).getString("Longitude").toString();
                 Log.e("jsonarray lat", "" + lat);
                 Log.e("jsonarray longg", "" + loong);
                 pojo.setLat(lat);
                 pojo.setLong(loong);
          }

         history.add(pojo);
}


回答2:

pojo = new Pojo();

should be declared inside for loop like Pojo pojo = new Pojo();



回答3:

First of all check at this line myAdapter = new HistoryAdapter(HistoryActivity.this, history); that history has a right data (not same, etc).

Second, edit getView function of your adapter

Replace this:

View v = convertView;
v = inflater.inflate(R.layout.history_item, parent, false);

To this:

View v = convertView;
if(convertView == null) {
   v = inflater.inflate(R.layout.history_item, parent, false);
}

UPD: Replace this:

 inflater = (LayoutInflater) activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

To this:

inflater = LayoutInflater.from(a);

Please response about result



回答4:

I have discovered your problem.

The initial/outside JSONArray has only 1 JSONObject as shown below

[
  { // object 1 start
    "login_time": "10:30:28",
    "logout_time": "10:31:47",
    "login_date": "2015- 09-30",
    "lati_long": [
      {
        "date_time": "2015:09:30  11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:14:53",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:01",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:15",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:15:52",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      },
      {
        "date_time": "2015:09:30 11:17:16",
        "Latitude": "21.121776",
        "Longitude": "79.047563"
      }
    ]
  } // object 1 end
]

Thus your outside for loop for (int k = 0; k < arr.length(); k++) { is called only once, thus giving you only 1 item in your List View.

Also the reason you're seeing only the latest long and lat values is commented below

for (int i = 0; i < subArrayLat.length(); i++) {
    String lat = subArrayLat.getJSONObject(i).getString("Latitude").toString();
    String loong = subArrayLat.getJSONObject(i).getString("Longitude").toString();
    Log.e("jsonarray lat", "" + lat);
    Log.e("jsonarray longg", "" + loong);

    // These two are called everytime but set the same pojo field
    // The result is that at the end of the loop, only the last set value is retained
    pojo.setLat(lat);
    pojo.setLong(loong);
}

And so you have one pojo object with the latest long and lat values.

Going by what I think you want to achieve, I'll say use the 'sub'arraylist gotten from parsing the inner json array in server respone to populate your list view.

UPDATE - A more specific answer

Create the pojo inside the inner for loop

if (strServerResponse != null) {
    try {

    JSONArray arr = new JSONArray(strServerResponse);

    for (int k = 0; k < arr.length(); k++) {

        JSONObject jsonObj1 = arr.getJSONObject(k);

        // Comment these out:

        //1 pojo = new Pojo();
        date = jsonObj1.optString("login_date");
        inTime = jsonObj1.optString("login_time");
        outTime = jsonObj1.optString("logout_time");

        Log.e("login time from server",""+inTime);
        Log.e("login out from server",""+outTime);
        Log.e("login date from server",""+date);
        //2 pojo.setDate(date);
        //3 pojo.setLoginTime(inTime);
        //4 pojo.setLogoutTime(outTime);

        JSONArray subArrayLat = jsonObj1.getJSONArray("lati_long");
        for (int i = 0; i < subArrayLat.length(); i++) {

            // And put them here

            pojo = new Pojo();

            pojo.setDate(date);
            pojo.setLoginTime(inTime);
            pojo.setLogoutTime(outTime);

            String lat = subArrayLat.getJSONObject(i).getString("Latitude").toString();
            String loong = subArrayLat.getJSONObject(i).getString("Longitude").toString();
            Log.e("jsonarray lat", "" + lat);
            Log.e("jsonarray longg", "" + loong);
            pojo.setLat(lat);
            pojo.setLong(loong);

            // Same with this too
            history.add(pojo);
        }

        // history.add(pojo);
    }
}  


回答5:

Put this code in your getView()

View v = convertView;
    ViewHolder holder;

    v = inflater.inflate(R.layout.history_item, parent, false);
    if(v==null)
    {
        holder=new ViewHolder();
        pojo = list.get(position);
        holder.date = (TextView) v.findViewById(R.id.historyDate);
        holder.logintime = (TextView) v.findViewById(R.id.historyLoginTime);
        holder.lougouttime = (TextView) v.findViewById(R.id.historyLogoutTime);
        holder.details = (TextView) v.findViewById(R.id.historyDetails);
        v.setTag(holder);
    }else{
        holder=(ViewHolder)v.getTag();
    }
    holder.date.setText(pojo.getDate());
    holder.logintime.setText(pojo.getLoginTime());
    holder.lougouttime.setText(pojo.getLogoutTime());
    final String lat = pojo.getLat().toString();
    String longg = pojo.getLong().toString();
    Log.e("adapter latitude", "" + lat);
    Log.e("adapter longitude", "" + longg);
    holder.details .setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Intent i = new Intent(context, MapActivity.class);
            i.putExtra("lat", "" + lat);
            i.putExtra("longg", "+longg");
            context.startActivity(i);
        }
    });

    return v;

The view holder class

protected  class ViewHolder{
        TextView date,logintime,lougouttime,details;

    }

paste this in your adapter class



回答6:

Few changes which should work in your case

First [Pojo Class]

Change Pojo class definition to store latitude and longitude in list

class Pojo{
   List<String> lat;
   List<String> longi;

   private List<String> getLat(){
       return this.lat;
   }

   private List<String> getLongi(){
       return this.longi;  
   }

   private void setLat(List<String> lat){
     this.lat = lat;
   }

   private void setLongi(List<String> longi){
    this.longi = longi;

   }

Second[For loop logic]

List<String> lati = new ArrayList<String>();
List<String> longi = new ArrayList<String>();
  for (int i = 0; i < subArrayLat.length(); i++) {
         String lat = subArrayLat.getJSONObject(i).getString("Latitude").toString();
         String loong = subArrayLat.getJSONObject(i).getString("Longitude").toString();
         lati.add(lat);
         longi.add(loong);
   }
    pojo.setLat(lati);//adding latitude list
    pojo.setLongi(longi); //adding longitude list

Third [ Inside getview]

Access those list in following way

List<String> lat = pojo.getLat();
List<String> longg = pojo.getLongi();

Hope it helps!