0

The idea is to be able to store an object that is passed from the child activity into an array of objects and display it in a list view in the parent activity. I cannot think of how to implement this in the code I already have, but I know the logic of my code is wrong.

This is my main activity.

public class MainActivity extends AppCompatActivity {

    //List<Expense> Expenses = new ArrayList<Expense>();
    ArrayList<Expense>  expenses;
    ListView listView;

    private static CustomArrayAdapter adapter;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Toolbar myToolbar = (Toolbar) findViewById(R.id.toolbarLayout);
        setSupportActionBar(myToolbar);

        listView = (ListView)findViewById(R.id.listView);

        expenses= new ArrayList<>();

        adapter = new CustomArrayAdapter(expenses, getApplicationContext());

        listView.setAdapter(adapter);
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (requestCode == 1) {
            if(resultCode == Activity.RESULT_OK){
                Expense expense = (Expense) data.getParcelableExtra("expense");

                //THIS LINE HERE IS WHAT I AM ON ABOUT.
                expenses.add(expense);
            }
            if (resultCode == Activity.RESULT_CANCELED) {
                //Write your code if there's no result
            }
        }
    }
}

So I created a separate class for the Custom Array Adapter. Here it is

public class CustomArrayAdapter extends ArrayAdapter<Expense> {

    private ArrayList<Expense> expenseDataSet;

    Context mContext;

    private static class ViewHolder {
        TextView txtAmount;
        TextView txtDateAdded;
        TextView txtDateOfExpense;
        TextView txtDes;
        TextView txtDatePaid;
        ImageView expenseImage;
    }

    public CustomArrayAdapter(ArrayList<Expense> data, Context context) {
        super(context, R.layout.list_item, data);
        this.expenseDataSet = data;
        this.mContext=context;
    }
    private int lastPosition = -1;

    @Override
    public View getView(int position, View view, ViewGroup parent) {
        //checking whether there is an instance of the view, inflate this view to make view not null
        Expense currentExpense = expenseDataSet.get(position);

        ViewHolder viewHolder; // view lookup cache stored in tag

        final View result;

        if (view == null)
        {
            viewHolder = new ViewHolder();
            LayoutInflater inflater = LayoutInflater.from(getContext());
            view = inflater.inflate(R.layout.list_item, parent, false);
            //setting the text views in list to the currentContact

            TextView amount = (TextView) view.findViewById(R.id.txtAmount2);

            TextView description= (TextView) view.findViewById(R.id.txtDescription);

            TextView dateOfExpense = (TextView) view.findViewById(R.id.txtDateOfExpense2);

            TextView dateAdded = (TextView) view.findViewById(R.id.txtDateAdded2);

            TextView datePaid = (TextView) view.findViewById(R.id.txtDatePaid2);

            ImageView ivExpenseImage = (ImageView) view.findViewById(R.id.ivExpenseImage);

            result=view;

            view.setTag(viewHolder);
        } else {
            viewHolder = (ViewHolder) view.getTag();
            result=view;
        }

        Animation animation = AnimationUtils.loadAnimation(mContext, (position > lastPosition) ? R.anim.up_from_top : R.anim.down_from_top);
        result.startAnimation(animation);
        lastPosition = position;

        viewHolder.txtAmount.setText(currentExpense.get_amount());
        viewHolder.txtDes.setText(currentExpense.get_amountVat());
        viewHolder.txtDateOfExpense.setText(currentExpense.get_dateOfExpense());
        viewHolder.txtDateAdded.setText(currentExpense.get_dateAdded());
        viewHolder.txtDatePaid.setText(currentExpense.get_datePaid());
        viewHolder.expenseImage.setImageURI(currentExpense.get_imageUri());

        // Return the completed view to render on screen
        return view;
    }

}
ישו אוהב אותך
  • 28,609
  • 11
  • 78
  • 96
KPullet
  • 21
  • 3

2 Answers2

0

try calling notifyDataSetChanged on your adapter after adding your item.

if(resultCode == Activity.RESULT_OK){
        Expense expense = (Expense) data.getParcelableExtra("expense");

        //THIS LINE HERE IS WHAT I AM ON ABOUT.
        expenses.add(expense);
        adapter.notifyDataSetChanged();
    }
    if (resultCode == Activity.RESULT_CANCELED) {
        //Write your code if there's no result
    }

more info notifyDataSetChanged example

Sylwek845
  • 145
  • 9
  • Thank you very much, but i still get this error. java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.TextView.setText(java.lang.CharSequence)' on a null object reference. – KPullet Mar 10 '18 at 00:49
  • I have debugged and I know the object is getting added to the expenses arrayList. – KPullet Mar 10 '18 at 00:54
  • this error means that your TextView object is null, you should refer to ViewHolder vars and assign them,not create new ones, so change to viewHolder.amount = (TextView) view.findViewById(R.id.txtAmount2); and same for the rest and try running you code again – Sylwek845 Mar 10 '18 at 01:18
  • if i put that it highlights the "amount" as there is no amount variable for viewHolder – KPullet Mar 10 '18 at 01:42
0

First, you need to call Adapter.notifyDataSetChanged() whenever your item data is changed.

Second, you need to fix your ViewHolder handling because your view is not recycled with your current code. The correct way to use ViewHolder pattern is something like this:

@Override
public View getView(int position, View view, ViewGroup parent) {
  Expense currentExpense = expenseDataSet.get(position);
  ViewHolder viewHolder; // view lookup cache stored in tag

  if (view == null) {
     // If there's no view to re-use, inflate new view
    viewHolder = new ViewHolder();
    LayoutInflater inflater = LayoutInflater.from(getContext());
    view = inflater.inflate(R.layout.list_item, parent, false);

    viewHolder.txtAmount = (TextView) view.findViewById(R.id.txtAmount2);
    viewHolder.txtDes= (TextView) view.findViewById(R.id.txtDescription);
    viewHolder.txtDateOfExpense = (TextView) view.findViewById(R.id.txtDateOfExpense2);
    viewHolder.txtDateAdded = (TextView) view.findViewById(R.id.txtDateAdded2);
    viewHolder.txtDatePaid = (TextView) view.findViewById(R.id.txtDatePaid2);
    viewHolder.expenseImage = (ImageView) view.findViewById(R.id.ivExpenseImage);
    // Cache viewHolder object inside the new view
    view.setTag(viewHolder);
  } else {
    // Recycle view, retrieve viewHolder object from tag
    viewHolder = (ViewHolder) view.getTag();
  }

  ...

  // Populate the data from the data object
  viewHolder.txtAmount.setText(currentExpense.get_amount());
  viewHolder.txtDes.setText(currentExpense.get_amountVat());

  ...

  // Return the completed view to render on screen
  return view;
}
marc_s
  • 732,580
  • 175
  • 1,330
  • 1,459
ישו אוהב אותך
  • 28,609
  • 11
  • 78
  • 96