Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
119 views
in Technique[技术] by (71.8m points)

java - ExpandableListView: Get input values from childs

I'm parsing a JSON into a ExpandableListView, on each child the user can select the amount of each child he wants to have due +/- Buttons. The +/- Buttons are connected to a TextView where the total amount of each child gets displayed and the total cost will be displayed at the end of the line.

At the Bottom of the parent there should be a TextView with the summary of all the values calculated in every child of the ExpListView (Summary) And the OK Button at the Bottom should send the amount of each child to the server (the amount is connected to a ID).

I'm having problems with reading out the amount of each child when I'm clicking on the "OK" Button - how can I build the bridge to the values of my Childs?

I also encounter problems reading out the cost of each childto calculate the total cost at the bottom. The onClickListener in the Child should somehow refresh the TextView at the bottom, but as far as I know, that's not going to be easy, right?

Has anyone an idea how to access the values?

This is the ChildView of my ListAdapter where the magic happens:

public class ExpandableListAdapterDrinks extends BaseExpandableListAdapter {
private Context context;
private List<String> listDataHeader,listDataHeaderPrice;
private HashMap<String,List<String>> listHashMap;
private List<Drink> drinksList;


class ViewHolder {
    TextView childText,counterText, childUnitPrice, childFinalPrice;
    Button btn_plus,btn_minus;

}

class DrinksListChildItem{
    String name;
    int quantity;
    DrinksListChildItem(String name, int quantity){
        this.name = name;
        this.quantity = quantity;
    }
}

class Pos{
    int group;
    int child;
    Pos(int group, int child){
        this.group = group;
        this.child = child;
    }
}




public ExpandableListAdapterDrinks(Context context, List<Drink> drinksList) {
    this.context = context;
    this.drinksList= drinksList;

  }




@Override
public int getGroupCount() {
    return drinksList.size();
}


@Override
public int getChildrenCount(int groupPosition) {

    return drinksList.get(groupPosition).getContent().size();

}

@Override
public Object getGroup(int groupPosition) {
    return drinksList.get(groupPosition);
}


@Override
public Object getChild(int groupPosition, int childPosition) {
    return drinksList.get(groupPosition).getContent();
     listHashMap.get(listDataHeader.get(groupPosition)).get(childPosition);
}

@Override
public long getGroupId(int groupPosition) {
    return groupPosition;
}

@Override
public long getChildId(int groupPosition, int childPosition) {
    return childPosition;
}

@Override
public boolean hasStableIds() {
    return false;
}



@Override
public View getGroupView(final int groupPosition, boolean isExpanded, View view, ViewGroup parent) {
    String headerTitle = (String) drinksList.get(groupPosition).getTitle();

    /** HEADER TEXT HERE */



    if(view==null) {
        LayoutInflater inflater = (LayoutInflater)this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        view = inflater.inflate(R.layout.vip_package_listgroup,null);
    }
    final LinearLayout bgcolor = view.findViewById(R.id.lblListHeaderLayout);
    TextView lblListHeader = (TextView)view.findViewById(R.id.lblListHeader);
    TextView lblListHeaderPrice = (TextView)view.findViewById(R.id.lblListHeader_Price);
    Button lblListHeaderButton = view.findViewById(R.id.lblListHeaderButton);

    lblListHeaderPrice.setVisibility(View.GONE);
    lblListHeaderButton.setVisibility(View.GONE);

    if(!drinksList.get(groupPosition).getBg().get(0).isEmpty() || !drinksList.get(groupPosition).getBg().get(1).isEmpty() ) {

        List<String> colorGradientTopBottom = drinksList.get(groupPosition).getBg();

        int[] colors = {Color.parseColor(colorGradientTopBottom.get(0)),Color.parseColor(colorGradientTopBottom.get(1))};
        GradientDrawable gd = new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM, colors);
        gd.setCornerRadius(0f);
        bgcolor.setBackground(gd);
    } else {

        bgcolor.setBackgroundColor(ContextCompat.getColor(context, R.color.cardview_bg));
    }

    lblListHeader.setText(headerTitle);

    return view;

}

@Override
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View view, ViewGroup parent) {

    /** Drinks List */
    final ViewHolder viewHolder;

    final List<String> childDrink = drinksList.get(groupPosition).getContent();
    final List<Integer> childPrice = drinksList.get(groupPosition).getPricelist();
    //final String childText =  childDrink.get(childPosition);

    if(view == null) {
        LayoutInflater inflater = (LayoutInflater)this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        view = inflater.inflate(R.layout.vip_drinks_listitem,null);

        final TextView txtListChild = view.findViewById(R.id.lblListItemDrinks);
        final TextView txtListDrinksUnitPrice = view.findViewById(R.id.lblListItemDrinksUnitPrice);
        final TextView txtDrinksAmount = view.findViewById(R.id.vip_drinks_amount);
        final TextView txtListDrinkPriceFinal = view.findViewById(R.id.lblListItemDrinksFinalPrice);
        Button btn_plus = view.findViewById(R.id.vip_drinks_btn_plus);
        Button btn_minus = view.findViewById(R.id.vip_drinks_btn_minus);

        viewHolder = new ViewHolder();
        viewHolder.childText = txtListChild;
        viewHolder.childUnitPrice = txtListDrinksUnitPrice;
        viewHolder.counterText = txtDrinksAmount;
        viewHolder.childFinalPrice = txtListDrinkPriceFinal;
        viewHolder.btn_plus = btn_plus;
        viewHolder.btn_minus = btn_minus;


        viewHolder.childText.setText(childDrink.get(childPosition));
        viewHolder.counterText.setText("0");
        viewHolder.childFinalPrice.setText("0");
        final float headerPrice = childPrice.get(childPosition);
        final int headerPriceInt = (int) headerPrice;
        viewHolder.childUnitPrice.setText(String.format("%.02f",headerPrice).replace(".",",") +"€");

        DrinksListChildItem child = childDrink.get(childPosition);


        viewHolder.btn_plus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {

                int t = Integer.parseInt(viewHolder.counterText.getText().toString());
                ChildItem selectedItem = viewHolder.counterText.getText().toString();
                selectedItem.quantity = selectedItem.quantity+1;
                notifyDataSetChanged();

                viewHolder.counterText.setText(String.valueOf(t + 1));
                viewHolder.childFinalPrice.setText(String.valueOf((t+1)* headerPriceInt) + "€");
            }
        });



        viewHolder.btn_minus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Pos pos = (Pos) v.getTag();
                int t = Integer.parseInt(viewHolder.counterText.getText().toString());
                DrinksListChildItem selectedItem = (DrinksListChildItem) getChild(pos.group,pos.child);
                selectedItem.quantity = selectedItem.quantity-1;
                notifyDataSetChanged();
                viewHolder.counterText.setText(String.valueOf(t - 1));
                viewHolder.counterText.setText(String.valueOf((t-1)* headerPriceInt) + "€");
            }
        });


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


    return view;

I'm having massive problems glueing your code to my Code (expand problem with a TextView): I don't understand exactly how to connect the ChildItem child = childDrink.get(childPosition); to my drinksList to make the setOnCLickListener increase the selectedItem.quantity. The Code works somehow, but it messes up the order of my childs and it also selects the quantity in the other childs

Drinks (Pojo)

public class Drink {
@SerializedName("title")
@Expose
private String title;
@SerializedName("bg")
@Expose
private List<String> bg = null;
@SerializedName("content")
@Expose
private List<String> content = null;
@SerializedName("pricelist")
@Expose
private List<Integer> pricelist = null;

public String getTitle() {
    return title;
}

public void setTitle(String title) {
    this.title = title;
}

public List<String> getBg() {
    return bg;
}

public void setBg(List<String> bg) {
    this.bg = bg;
}

public List<String> getContent() {
    return content;
}

public void setContent(List<String> content) {
    this.content = content;
}

public List<Integer> getPricelist() {
    return pricelist;
}

public void setPricelist(List<Integer> pricelist) {
    this.pricelist = pricelist;
}

}

VipDrinks(Pojo): public class VipDrinks {

@SerializedName("drinks")
@Expose
private List<Drink> drinks = null;

public List<Drink> getDrinks() {
    return drinks;
}

public void setDrinks(List<Drink> drinks) {
    this.drinks = drinks;
}

}

JSON has the following structure:

{
 "drinks":[ {
              "title":,
              "bg":[],
              "content":[],
              "pricelist":[],
             },
            {...} 
          ]
 }

Here is the Activity with the Parsing Request:

public class drinks_selection extends AppCompatActivity {


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

        final ExpandableListView listView = findViewById(R.id.vip_drinks_listview);


        /** PARSING JSON FROM SERVER */

        final JsonObjectRequest galleryUrls = new JsonObjectRequest(Request.Method.GET, PARSE_URL, null, new Response.Listener<JSONObject>() {
            @Override
            public void onResponse(JSONObject response) {
                try {
                    JSONArray packageArray = response.getJSONArray("drinks");
                    Log.e("response", String.valueOf(response));
                    GsonBuilder gsonBuilder = new GsonBuilder();
                    Gson gson = gsonBuilder.create();
                    List<Drink> vipDrinks = Arrays.asList(gson.fromJson(String.valueOf(packageArray),Drink[].class));
                    List<Drink> arrayList = new ArrayList<>(vipDrinks);

                    ExpandableListAdapterDrinks listAdapter = new ExpandableListAdapterDrinks(getApplicationContext(),arrayList);
                    listView.setAdapter( listAdapter);
                    listView.expandGroup(0);

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

            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {


                Log.e("ERROR", String.valueOf(error));
            }
        });

        RequestQueue rQ = Volley.newRequestQueue(this);
        rQ.add(galleryUrls);

    }
}

VIP Package List Group.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    android:id="@+id/lblListHeaderLayout"
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:padding="@dimen/default_padding"
    android:background="

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

Add a new class SelectedDrink like this:

public class SelectedDrink {
String content;
int qty;
}

Then try this adapter code:

public class ExpandableListAdapterDrinks extends BaseExpandableListAdapter {

private Context context;
private List<Drink> drinksList;

private Button btReset, btOk;
private List<Integer> groupSum;
private List<List<Integer>> qty;
private int totalSum = 0;

class ViewHolder {
    TextView childText,counterText, childUnitPrice, childFinalPrice;
    Button btn_plus,btn_minus;
}

class Pos{
    int group;
    int child;
    Pos(int group, int child){
        this.group = group;
        this.child = child;
    }
}

public ExpandableListAdapterDrinks(Context context, List<Drink> drinksList,
                                   Button btReset, Button btOk) {
    this.context = context;
    this.drinksList= drinksList;
    this.btReset = btReset;
    this.btOk = btOk;

    groupSum = new ArrayList<>();
    qty = new ArrayList<>();
    for(int i=0; i<drinksList.size(); i++) {
        groupSum.add(0);
        List<Integer> orderedQty = new ArrayList<>();
        for(int j=0; j<drinksList.get(i).getContent().size(); j++) orderedQty.add(0);
        qty.add(orderedQty);
    }
}

private void resetGroupSum(int groupPosition) {
    totalSum -= groupSum.get(groupPosition);
    groupSum.set(groupPosition, 0);
    resetGroupChildrenQty(groupPosition);
}

private void resetGroupChildrenQty(int groupPosition) {
    for(int i=0; i<qty.get(groupPosition).size(); i++) qty.get(groupPosition).set(i, 0);
}

@Override
public int getGroupCount() {
    return drinksList.size();
}

@Override
public int getChildrenCount(int groupPosition) {
    return drinksList.get(groupPosition).getContent().size();
}

@Override
public Drink getGroup(int groupPosition) {
    return drinksList.get(groupPosition);
}

@Override
public String getChild(int groupPosition, int childPosition) {
    return drinksList.get(groupPosition).getContent().get(childPosition);
}

@Override
public long getGroupId(int groupPosition) {
    return groupPosition;
}

@Override
public long getChildId(int groupPosition, int childPosition) {
    return childPosition;
}

@Override
public boolean hasStableIds() {
    return false;
}

@Override
public View getGroupView(int groupPosition, boolean isExpanded, View view, ViewGroup parent) {
    String headerTitle = drinksList.get(groupPosition).getTitle();

    /** HEADER TEXT HERE */
    if(view==null) {
        LayoutInflater inflater = (LayoutInflater)this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        view = inflater.inflate(R.layout.vip_package_listgroup,null);
    }
    LinearLayout bgcolor = view.findViewById(R.id.lblListHeaderLayout);
    TextView lblListHeader = (TextView)view.findViewById(R.id.lblListHeader);
    TextView lblListHeaderPrice = (TextView)view.findViewById(R.id.lblListHeader_Price);
    Button lblListHeaderButton = view.findViewById(R.id.lblListHeaderButton);

    if(groupSum.get(groupPosition) > 0){
        lblListHeaderPrice.setVisibility(View.VISIBLE);
        lblListHeaderPrice.setText(String.format("%.02f", (float)groupSum.get(groupPosition)).replace(".", ",") + "€");
    }else{
        lblListHeaderPrice.setVisibility(View.GONE);
        lblListHeaderButton.setVisibility(View.GONE);
    }

    if(!drinksList.get(groupPosition).getBg().get(0).isEmpty() || !drinksList.get(groupPosition).getBg().get(1).isEmpty() ) {
        List<String> colorGradientTopBottom = drinksList.get(groupPosition).getBg();
        int[] colors = {Color.parseColor(colorGradientTopBottom.get(0)),Color.parseColor(colorGradientTopBottom.get(1))};
        GradientDrawable gd = new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM, colors);
        gd.setCornerRadius(0f);
        bgcolor.setBackground(gd);
    } else {
        //bgcolor.setBackgroundColor(ContextCompat.getColor(context, R.color.cardview_bg));
    }
    lblListHeader.setText(headerTitle);

    return view;
}

@Override
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View view, ViewGroup parent) {

    /** Drinks List */
    ViewHolder viewHolder;

    String childDrink = getChild(groupPosition, childPosition);
    int childPrice = getGroup(groupPosition).getPricelist().get(childPosition);

    if (view == null) {
        LayoutInflater inflater = (LayoutInflater) this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        view = inflater.inflate(R.layout.vip_drinks_listitem, null);

        viewHolder = new ViewHolder();
        viewHolder.childText = view.findViewById(R.id.lblListItemDrinks);
        viewHolder.childUnitPrice = view.findViewById(R.id.lblListItemDrinksUnitPrice);
        viewHolder.counterText = view.findViewById(R.id.vip_drinks_amount);
        viewHolder.childFinalPrice = view.findViewById(R.id.lblListItemDrinksFinalPrice);
        viewHolder.btn_plus = view.findViewById(R.id.vip_drinks_btn_plus);
        viewHolder.btn_minus = view.findViewById(R.id.vip_drinks_btn_minus);

        viewHolder.btn_plus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Pos pos = (Pos) v.getTag();
                int orderedQty = qty.get(pos.group).get(pos.child);
                orderedQty++;
                qty.get((pos.group)).set(pos.child, orderedQty);
                groupSum.set(pos.group, groupSum.get(pos.group) + getGroup(pos.group).getPricelist().get(pos.child));
                notifyDataSetChanged();
                totalSum += getGroup(pos.group).getPricelist().get(pos.child);
                btOk.setText(String.format("%.02f", (float)totalSum).replace(".", ",") + "€");
                btReset.setEnabled(true);
            }
        });

        viewHolder.btn_minus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Pos pos = (Pos) v.getTag();
                int orderedQty = qty.get(pos.group).get(pos.child);
                if (orderedQty > 0) {
                    orderedQty--;
                    qty.get((pos.group)).set(pos.child, orderedQty);
                    groupSum.set(pos.group, groupSum.get(pos.group) - getGroup(pos.group).getPricelist().get(pos.child));
                    notifyDataSetChanged();
                    totalSum -= getGroup(pos.group).getPricelist().get(pos.child);
                    if (totalSum == 0) resetTotalSum();
                    else btOk.setText(String.format("%.02f", (float)totalSum).replace(".", ",") + "€");
                }
            }
        });
    } else {
        viewHolder = (ViewHolder) view.getTag();
    }

    viewHolder.childText.setText(childDrink);
    viewHolder.childUnitPrice.setText(String.format("%.02f", (float)childPrice).replace(".", ",") + "€");
    int orderedQty = qty.get(groupPosition).get(childPosition);
    viewHolder.counterText.setText(String.valueOf(orderedQty));
    viewHolder.childFinalPrice.setText(String.format("%.02f", (float)orderedQty*childPrice).replace(".", ",") + "€");

    viewHolder.btn_minus.setTag(new Pos(groupPosition, childPosition));
    viewHolder.btn_plus.setTag(new Pos(groupPosition, childPosition));
    view.setTag(viewHolder);
    return view;
}

@Override
public boolean isChildSelectable(int i, int i1) {
    return false;
}

public void resetTotalSum() {
    for(int i=0; i<drinksList.size(); i++) {
        resetGroupSum(i);
    }
    notifyDataSetChanged();
    btReset.setEnabled(false);
    btOk.setText(String.valueOf(0));
}

public ArrayList<SelectedDrink> getOrderList() {
    ArrayList<SelectedDrink> orderList = new ArrayList<>();
    for(int i=0; i<drinksList.size(); i++) {
        for(int j=0; j<drinksList.get(i).getContent().size(); j++) {
            if(qty.get(i).get(j) > 0) {
                SelectedDrink selectedDrink = new SelectedDrink();
                selectedDrink.content = getGroup(i).getContent().get(j);
                selectedDrink.qty = qty.get(i).get(j);
                orderList.add(selectedDrink);
            }
        }
    }
    return orderList;
}
}

I test the above with this activity:

public class MainActivity extends AppCompatActivity {
final private static int NUM_OF_GROUP = 5;
List<Drink> drinksList;
ExpandableListView listView;
ExpandableListAdapterDrinks expandableListAdapterDrinks;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    Button btRest = findViewById(R.id.btReset);
    Button btOk = findViewById(R.id.btOK);
    listView = findViewById(R.id.elvDrinks);

    initDataList();
    expandableListAdapterDrinks =
            new ExpandableListAdapterDrinks(getApplicationContext(), drinksList, btRest, btOk);
    listView.setAdapter(expandableListAdapterDrinks);
    listView.expandGroup(0);

    btRest.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            expandableListAdapterDrinks.resetTotalSum();
            for(int i=0; i<drinksList.size(); i++) listView.collapseGroup(i);
            listView.expandGroup(0);
        }
    });
    btOk.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            String msg = "Nothing Selected";
            Button button = (Button)view;
            if(!button.getText().equals("0")) {
                msg = "Upload!
";
                ArrayList<SelectedDrink> selectedDrinks = expandableListAdapterDrinks.getOrderList();
                for(SelectedDrink selectedDrink: selectedDrinks) {
                    msg += selectedDrink.content + "    " + selectedDrink.qty + "
";
                }
                msg += "Total: " + button.getText();
            }
            Toast.makeText(getApplicationContext(), msg, Toast.LENGTH_LONG).show();
        }
    });
}

private void initDataList(){
    drinksList = new ArrayList<>();
    List<String> content;
    List<Integer> pricelist;
    List<String> bg;
    for(int i=1; i<=NUM_OF_GROUP; i++) {
        content = new ArrayList<>();
        pricelist = new ArrayList<>();
        bg = new ArrayList<>();
        for(int j = 1; j<(NUM_OF_GROUP + new Random().nextInt(5)); j++){
            content.add("Drink " + i + "-" + j);
            pricelist.add(new Random().nextInt(1000));
            bg.add("#008577");
            bg.add("#D81B60");
        }
        Drink drink = new Drink();
        drink.setTitle("Group " + i);
        drink.setContent(content);
        drink.setPricelist(pricelist);
        drink.setBg(bg);
        drinksList.add(drink);
    }
}
}

and this layout:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">

<LinearLayout
    android:id="@+id/llBtns"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true"
    android:orientation="horizontal">

    <Button
        android:id="@+id/btReset"
        android:layout_width="match_parent"
        android:layout_height="wrap_content

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...