package com.example.istroweil.ichfahrcar; import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import android.os.Build; import android.support.annotation.RequiresApi; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.ImageView; import android.widget.Space; import android.widget.TextView; import org.json.JSONArray; import org.json.JSONException; import org.json.JSONObject; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.util.ArrayList; import java.util.HashMap; import java.util.Map; import java.util.regex.Matcher; import java.util.regex.Pattern; /** * Created by kivaari on 27.12.2016. */ public class POIListAdapter extends ArrayAdapter implements AsyncResponse{ //TODO change this to HashMap, give Map to downloader task and access them from here, store position in json Map bmpContainer; public POIListAdapter(Context context, ArrayList pois){ super(context, 0, pois); bmpContainer = new HashMap<>(); } //TODO make it like this:http://stackoverflow.com/questions/14188685/android-onclick-event-on-custom-listview-adapter-not-working @RequiresApi(api = Build.VERSION_CODES.M) @Override public View getView(int position, View convertView, ViewGroup parent){ JSONObject jsonItem = getItem(position); String name = ""; String type = ""; String address = ""; String distance = ""; Boolean selected = false; Boolean visible = false; try { selected = jsonItem.getBoolean("selected"); visible = jsonItem.getBoolean("visible"); name = jsonItem.getString("name"); type = jsonItem.getString("type"); address = jsonItem.getString("address"); } catch (JSONException e) { e.printStackTrace(); } Bitmap bmp = null; Drawable icon = null; View test = new Space(getContext()); //dummy to test for class equivalence if(visible){ if((convertView == null) || (convertView.getClass() == test.getClass())) convertView = LayoutInflater.from(getContext()).inflate(R.layout.component_poi, parent, false); } if(!visible) { convertView = new Space(getContext()); return convertView; } TextView tvName = (TextView) convertView.findViewById(R.id.tvName); TextView tvAddress = (TextView) convertView.findViewById(R.id.tvAddress); TextView tvDistance = (TextView) convertView.findViewById(R.id.tvDistance); ImageView ivIcon = (ImageView) convertView.findViewById(R.id.ivIcon); if(selected) convertView.setBackgroundColor(getContext().getResources().getColor(R.color.colorLvSelected, null)); else convertView.setBackgroundColor(getContext().getResources().getColor(R.color.colorLvUnselected, null)); try { distance = calculateDistance(jsonItem.getDouble("lat"), jsonItem.getDouble("lon")); } catch (JSONException e) { e.printStackTrace(); } if(jsonItem.toString().contains("icon")){ //check if there is an icon link present if(jsonItem.toString().contains("bmp") == false){ //download bitmap if it is not set yet try { File file = new File(getContext().getFilesDir(), jsonItem.getString("icon")); if(!file.exists()) { DownloadImageTask task = (DownloadImageTask) new DownloadImageTask(ivIcon, getContext(), position) .execute("https://www.fbi.h-da.de/fileadmin/personal/h.wiedling/daten/" + jsonItem.getString("icon")); task.delegate = this; } else{ try { BitmapFactory.Options options = new BitmapFactory.Options(); options.inPreferredConfig = Bitmap.Config.ARGB_8888; Bitmap bmp_file = BitmapFactory.decodeFile(file.getAbsolutePath(), options); ivIcon.setImageBitmap(bmp_file); bmpContainer.put(position, (Bitmap) bmp_file); try { jsonItem.put("bmp", position); } catch (JSONException e) { e.printStackTrace(); } } catch (Exception e) { e.printStackTrace(); } } } catch (JSONException e) { e.printStackTrace(); } } else{ //set ivIcon image if bitmap has already been saved try { //ISSUE this will cause bugs if bmps get removed or moved around, never redownload icons without clearing list bmp = bmpContainer.get(jsonItem.getInt("bmp")); } catch (JSONException e) { e.printStackTrace(); } Drawable drawable = new BitmapDrawable(getContext().getResources(), bmp); ivIcon.setImageDrawable(drawable); } } else{ switch (type) { case "fuel": if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { icon = getContext().getDrawable(R.drawable.fuel_poi); } else { icon = getContext().getResources().getDrawable(R.drawable.fuel_poi); } break; case "amenity": if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { icon = getContext().getDrawable(R.drawable.amenity); } else { icon = getContext().getResources().getDrawable(R.drawable.amenity); } break; case "pub": if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { icon = getContext().getDrawable(R.drawable.pub); } else { icon = getContext().getResources().getDrawable(R.drawable.pub); } break; } ivIcon.setImageDrawable(icon); } tvAddress.setText(address); tvName.setText(name); tvDistance.setText(distance); return convertView; } public String calculateDistance(Double lat, Double lon/*, Coordinate start*/){ //TODO add actual distance calculation Double dist = Car.distance(lat, lon, 1); if(dist == -1){ return ""; } String unit = "m"; String result = Integer.toString(dist.intValue()); result = result.concat(unit); return result; } @Override public void processFinish(Object output, int position, processIDs processID) { JSONObject jsonObject = getItem(position); Bitmap bmp = (Bitmap) output ; FileOutputStream out = null; try { File file = new File(getContext().getFilesDir(), jsonObject.getString("icon")); file.createNewFile(); out = new FileOutputStream(file); bmp.compress(Bitmap.CompressFormat.PNG, 100, out); // bmp is your Bitmap instance // PNG is a lossless format, the compression factor (100) is ignored } catch (Exception e) { e.printStackTrace(); } finally { try { if (out != null) { out.close(); } } catch (IOException e) { e.printStackTrace(); } } bmpContainer.put(position, (Bitmap) output); try { jsonObject.put("bmp", position); } catch (JSONException e) { e.printStackTrace(); } } @Override public void processFinish(Object output, processIDs processID) { } @Override public void processFinish(processIDs processID) { //clear selected from adapter once drive is done if(processID.equals(processIDs.DRIVEFINISHED)){ for(int i = 0; i < getCount(); i++){ try { getItem(i).put("selected", false); } catch (JSONException e) { e.printStackTrace(); } } } } public void filterPOIs(JSONObject newFilter){ String namef; String typef; for(int i = 0; i < getCount(); i++){ try { getItem(i).put("visible", false); } catch (JSONException e) { e.printStackTrace(); } } try { if (newFilter.toString().contains("namef")) { namef = newFilter.getString("namef").toUpperCase(); Pattern p = Pattern.compile(namef); Matcher m; for (int i = 0; i < getCount(); i++) { String name = getItem(i).getString("name").toUpperCase(); m = p.matcher(name); if(m.find()) getItem(i).put("visible", true); } } } catch(Exception e){ } try { if (newFilter.toString().contains("typef")) { typef = newFilter.getString("typef").toUpperCase(); Pattern p = Pattern.compile(typef); Matcher m; for (int i = 0; i < getCount(); i++) { String type = getItem(i).getString("type").toUpperCase(); m = p.matcher(type); if(m.find() || typef.equals("ALL")) getItem(i).put("visible", true); } } } catch(Exception e){ } try { if (newFilter.toString().contains("history")) { for(int i = 0; i < getCount(); i++){ JSONObject jsonObject = getItem(i); if(jsonObject.getBoolean("history")){ jsonObject.put("visible", true); } else{ jsonObject.put("visible", false); } } } } catch(Exception e){ } notifyDataSetChanged(); } public void updateHistory(JSONArray h){ try { for(int i = 0; i < getCount(); i++){ getItem(i).put("history", false); } for (int i = 0; i < h.length(); i++) { JSONObject jsonHistory = h.getJSONObject(i); for(int j = 0; j < getCount(); j++){ JSONObject jsonAdapter = getItem(j); if (jsonHistory.getString("name").equals(jsonAdapter.getString("name")) && jsonHistory.getString("address").equals(jsonAdapter.getString("address"))){ jsonAdapter.put("history", true); } } } } catch (Exception e){ } } public void makeAllInvisible(){ for(int i = 0; i < getCount(); i++){ try { getItem(i).put("visible", false); } catch (JSONException e) { e.printStackTrace(); } } } public void unselectAll() { for(int i = 0; i < getCount(); i++){ try { getItem(i).put("selected", false); } catch (JSONException e) { e.printStackTrace(); } } } public void makeAllVisible() { for(int i = 0; i < getCount(); i++){ try { getItem(i).put("visible", true); } catch (JSONException e) { e.printStackTrace(); } } } public int getSelectedAmount() { int x = 0; for(int i = 0; i < getCount(); i++){ try { if(getItem(i).getBoolean("selected")) x++; } catch (JSONException e) { e.printStackTrace(); } } return x; } }