I have a problem statement in my booking app such that user can delete all the booking of the particular date or all the dates, see this image:
I have tried to add data to the grid view using multiple adapters for listview and the inner gridview, but it's taking data replication. How can I solve this problem?
Each date represents the listview with checkbox,and the UH,U1 etc represents the item of gridview. I want to pass the selected venue id ie. UH,U! etc in a listview and its corresponding dates
Try the sample below :)
MainActivity.java:
public class MainActivity extends Activity {
Button clearChecks;
ExpandableListView expandableListView;
ExpandableListGridAdapter expandableListAdapter;
int lastExpandedPosition = -1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
expandableListView = findViewById(R.id.expandedListView);
clearChecks = findViewById(R.id.btnClearChecks);
List<String> listTitle = genGroupList();
expandableListAdapter = new ExpandableListGridAdapter(this, listTitle, genChildList(listTitle));
expandableListView.setAdapter(expandableListAdapter);
expandableListView.setOnGroupExpandListener(new ExpandableListView.OnGroupExpandListener() {
#Override
public void onGroupExpand(int groupPosition) {
if(lastExpandedPosition != -1 && (lastExpandedPosition != groupPosition)){
expandableListView.collapseGroup(lastExpandedPosition);
}
lastExpandedPosition = groupPosition;
}
});
clearChecks.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
expandableListAdapter.clearChecks();
}
});
}
private List<String> genGroupList(){
List<String> listGroup = new ArrayList<>();
for(int i=1; i<10; i++){
listGroup.add("Group: " + i);
}
return listGroup;
}
private Map<String, List<ChildItemSample>> genChildList(List<String> header){
Map<String, List<ChildItemSample>> listChild = new HashMap<>();
for(int i=0; i<header.size(); i++){
List<ChildItemSample> testDataList = new ArrayList<>();
int a = (int)(Math.random() * 8);
for(int j=0; j<a; j++){
ChildItemSample testItem = new ChildItemSample("Child " + (j + 1));
testDataList.add(testItem);
}
listChild.put(header.get(i), testDataList);
}
return listChild;
}
}
ChildItemSample.java:
public class ChildItemSample {
private boolean checked;
private String name;
public boolean isChecked() {
return checked;
}
public void setChecked(boolean checked) {
this.checked = checked;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public ChildItemSample(){
checked = false;
name = "";
}
public ChildItemSample(String name){
checked = false;
this.name = name;
}
}
ExpandableListGridAdapter.java:
public class ExpandableListGridAdapter extends BaseExpandableListAdapter {
private Context context;
private List<String> listGroup;
private Map<String, List<ChildItemSample>> listChild;
private int checkedBoxesCount;
private boolean[] checkedGroup;
public ExpandableListGridAdapter(Context context, List<String> listGroup, Map<String,
List<ChildItemSample>> listChild) {
this.context = context;
this.listGroup = listGroup;
this.listChild = listChild;
checkedBoxesCount = 0;
checkedGroup = new boolean[listGroup.size()];
}
#Override
public int getGroupCount() {
return listGroup.size();
}
#Override
public int getChildrenCount(int groupPosition) {
return 1;
}
#Override
public String getGroup(int groupPosition) {
return listGroup.get(groupPosition);
}
#Override
public ChildItemSample getChild(int groupPosition, int childPosition) {
return listChild.get(listGroup.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(int groupPosition, boolean b, View view, ViewGroup viewGroup) {
String itemGroup = getGroup(groupPosition);
GroupViewHolder groupViewHolder;
if(view == null){
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.expanded_list_group, null);
groupViewHolder = new GroupViewHolder();
groupViewHolder.tvGroup = view.findViewById(R.id.tv_group);
groupViewHolder.cbGroup = view.findViewById(R.id.cb_group);
groupViewHolder.cbGroup.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int pos = (int)view.getTag();
checkedGroup[pos] = !checkedGroup[pos];
for(ChildItemSample item : listChild.get(listGroup.get(pos))){
item.setChecked(checkedGroup[pos]);
}
notifyDataSetChanged();
}
});
view.setTag(groupViewHolder);
}else {
groupViewHolder = (GroupViewHolder)view.getTag();
}
groupViewHolder.tvGroup.setText(String.format("%s (%d)", itemGroup, listChild.get(listGroup.get(groupPosition)).size()));
if(checkedGroup[groupPosition]) groupViewHolder.cbGroup.setChecked(true);
else groupViewHolder.cbGroup.setChecked(false);
groupViewHolder.cbGroup.setTag(groupPosition);
return view;
}
#Override
public View getChildView(final int groupPosition, int childPosition, boolean b, View view, ViewGroup viewGroup) {
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.list_grid_item, null);
GridLayout childLayout = view.findViewById(R.id.layout_child);
for(int i = 0; i < listChild.get(listGroup.get(groupPosition)).size(); i++){
ChildItemSample expandedListText = getChild(groupPosition, i);
CheckBox cbChild = new CheckBox(context);
GridLayout.LayoutParams params = new GridLayout.LayoutParams();
params.width = (int)(80 * context.getResources().getDisplayMetrics().density);
cbChild.setLayoutParams(params);
cbChild.setChecked(expandedListText.isChecked());
cbChild.setText(expandedListText.getName());
cbChild.setTag(i);
childLayout.addView(cbChild);
cbChild.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
CheckBox cb = (CheckBox) view;
int pos = (int) view.getTag();;
ChildItemSample selectedItem = listChild.get(listGroup.get(groupPosition)).get(pos);
selectedItem.setChecked(cb.isChecked());
if(cb.isChecked()){
checkedBoxesCount++;
Toast.makeText(context,"Checked value is: " +
listChild.get(listGroup.get(groupPosition)).get(pos).getName(),
Toast.LENGTH_SHORT).show();
}else {
checkedBoxesCount--;
if(checkedBoxesCount == 0){
Toast.makeText(context,"nothing checked",Toast.LENGTH_SHORT).show();
}else {
Toast.makeText(context,"unchecked",Toast.LENGTH_SHORT).show();
}
}
notifyDataSetChanged();
}
});
}
return view;
}
public void clearChecks() {
for(int i=0; i<checkedGroup.length; i++) checkedGroup[i] = false;
for(List<ChildItemSample> value : listChild.values()) {
for (ChildItemSample sample : value) {
sample.setChecked(false);
}
}
checkedBoxesCount = 0;
notifyDataSetChanged();
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
private class GroupViewHolder {
CheckBox cbGroup;
TextView tvGroup;
}
}
activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<Button
android:id="#+id/btnClearChecks"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Clear Checks" />
<ExpandableListView
android:id="#+id/expandedListView"
android:layout_width="match_parent"
android:layout_height="match_parent">
</ExpandableListView>
</LinearLayout>
expanded_list_group.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="wrap_content"
android:descendantFocusability="blocksDescendants" >
<CheckBox
android:id="#+id/cb_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="40dp"
android:layout_gravity="center_vertical" />
<TextView
android:id="#+id/tv_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Text"
android:textSize="30sp" />
</LinearLayout>
list_grid_item.xml:
<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/layout_child"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingStart="60dp"
android:columnCount="3"
android:orientation="horizontal">
</GridLayout>
Hope that helps!
Related
I am trying to inflate data from "Map<ArrayList<String>, Object>"
Where I have store the Header as ArrayList<String> and the child list as Object. The problem is that it is crashing when I run the code.
Here is my Debug Console:
E/JavaBinder: !!! FAILED BINDER TRANSACTION !!!
E/AndroidRuntime: Error reporting crash
android.os.TransactionTooLargeException
at android.os.BinderProxy.transactNative(Native Method)
at android.os.BinderProxy.transact(Binder.java:496)
at android.app.ActivityManagerProxy.handleApplicationCrash(ActivityManagerNative.java:4164)
at com.android.internal.os.RuntimeInit$UncaughtHandler.uncaughtException(RuntimeInit.java:89)
at java.lang.ThreadGroup.uncaughtException(ThreadGroup.java:693)
at java.lang.ThreadGroup.uncaughtException(ThreadGroup.java:690)
ERROR:
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.chonang.chonangclientlogin, PID: 12175
java.lang.StackOverflowError: stack size 8MB
at com.chonang.chonangclientlogin.listViewAdapter.TestExpandableView.getGroupId(TestExpandableView.java:65)
The error is indicating at line 65
Here is my adapter code:
public TestExpandableView(String allow, Map<ArrayList<String>, Object> headerListArrayList, String country, String state, String city, String tree, Context context) {
this.allow=allow;
this.country=country;
this.state=state;
this.city=city;
this.TREE=tree;
this.data=headerListArrayList;
this.context= context;
}
#Override
public int getGroupCount() {
return data.size();
}
#Override
public int getChildrenCount(int groupPosition) {
return (int) data.get(getChildrenCount(groupPosition));
}
#Override
public Object getGroup(int groupPosition) {
return groupPosition;
}
#Override
public Object getChild(int groupPosition, int childPosition) {
return data.get(getChild(groupPosition,childPosition)); // THE ERROR IS INDICATION HERE
}
#Override
public long getGroupId(int groupPosition) {
return (long) data.get(getGroupId(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 convertView, ViewGroup parent) {
String headerTitle = (String) data.get(getGroup(groupPosition));
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.expandable_view_header, null);
}
ExpandableListView mExpandableListView = (ExpandableListView) parent;
mExpandableListView.expandGroup(groupPosition,isExpanded);
TextView headerName = convertView.findViewById(R.id.headerName);
headerName.setText(headerTitle);
return convertView;
}
#Override
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) {
initializedData(convertView);
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) this.context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.card_view, null);
}
ItemListProduct data;
data= (ItemListProduct) getChild(groupPosition,childPosition);
itemName.setText(String.valueOf(data.getITEM_NAME()));
return convertView;
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return false;
}
private void initializedData(View convertView) {
itemView= convertView.findViewById(R.id.itemView);
itemName = convertView.findViewById(R.id.ListViewItemNameAdapter);
}
}
I made a complete sample which acts like guiding user to find the available hotel from a single data list (ArrayList<HashMap<String, String>>). Take a try, it does not answer your problem directly but contains something useful.
MainActivity.java:
public class MainActivity extends AppCompatActivity {
ArrayList<HashMap<String, String>> dataList;
CustomExpandableListViewAdapter adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ArrayList<String> header = new ArrayList<>();
header.add("Country");
header.add("State");
header.add("City");
header.add("Hotel");
dataList = createSampleDataList(header);
debugSampleDataList(header, dataList);
ExpandableListView expandableListView = findViewById(R.id.eLV);
adapter = new CustomExpandableListViewAdapter(this, header, dataList);
expandableListView.setAdapter(adapter);
expandableListView.expandGroup(0);
expandableListView.setOnGroupClickListener(new ExpandableListView.OnGroupClickListener() {
#Override
public boolean onGroupClick(ExpandableListView expandableListView, View view, int i, long l) {
return true;
}
});
expandableListView.setOnChildClickListener(new ExpandableListView.OnChildClickListener() {
#Override
public boolean onChildClick(ExpandableListView expandableListView, View view, int i, int i1, long l) {
for (int j = adapter.getGroupCount() - 1; j > i; j--)
expandableListView.collapseGroup(j);
adapter.updateViewsOnClick(i, i1);
if (i < adapter.getGroupCount() - 1) expandableListView.expandGroup(i + 1);
else {
int index = adapter.getFinalSelectedItemIndex(i1);
Toast.makeText(getApplicationContext(), "(" + index + ")\n" +
dataList.get(index).toString(), Toast.LENGTH_LONG).show();
}
return true;
}
});
}
private ArrayList<HashMap<String, String>> createSampleDataList(ArrayList<String> header) {
ArrayList<HashMap<String, String>> dataList = new ArrayList<>();
for (int i = 0; i < 27; i++) {
HashMap<String, String> data = new HashMap<>();
data.put(header.get(0), header.get(0) + (i % 5 + 1));
data.put(header.get(1), (i % 5 + 1) + header.get(1) + (i % 4 + 1));
data.put(header.get(2), (i % 5 + 1) + header.get(2) + (i % 3 + 1));
data.put(header.get(3), (i % 5 + 1) + header.get(3) + (i % 2 + 1));
// If more items in header, add data fields here accordingly.
dataList.add(data);
}
return dataList;
}
// Printing the whole data list to Logcat for debug.
private void debugSampleDataList(ArrayList<String> header, ArrayList<HashMap<String, String>> dataList) {
String msg = "\n";
for (HashMap<String, String> data : dataList) {
for (String heading : header) {
msg += data.get(heading) + " ";
}
msg += "\n";
}
Log.d("debug", msg);
}
}
CustomExpandableListViewAdapter.java:
public class CustomExpandableListViewAdapter extends BaseExpandableListAdapter {
Activity context;
ArrayList<String> groupList;
ArrayList<HashMap<String, String>> childList;
ArrayList<ArrayList<ArrayList<HashMap<String, String>>>> childListInViewArray = new ArrayList<>();
int[] selectedPositions;
LayoutInflater inflater;
public CustomExpandableListViewAdapter(Activity context, ArrayList<String> groupList, ArrayList<HashMap<String, String>> childList) {
this.context = context;
this.groupList = groupList;
this.childList = childList;
inflater = this.context.getLayoutInflater();
selectedPositions = new int[groupList.size()];
for (int i = 0; i < selectedPositions.length; i++) selectedPositions[i] = -1;
ArrayList<HashMap<String, String>> singleChild;
ArrayList<ArrayList<HashMap<String, String>>> childListInView = new ArrayList<>();
for (HashMap<String, String> rawData : childList) {
boolean found = false;
int foundPosition = -1;
if (childListInView.size() > 0) {
for (foundPosition = 0; foundPosition < childListInView.size(); foundPosition++) {
if (childListInView.get(foundPosition).get(0).get(groupList.get(0)).equals(rawData.get(groupList.get(0)))) {
singleChild = childListInView.get(foundPosition);
singleChild.add(rawData);
found = true;
break;
}
}
if (!found) {
singleChild = new ArrayList<>();
singleChild.add(rawData);
childListInView.add(singleChild);
}
} else {
singleChild = new ArrayList<>();
singleChild.add(rawData);
childListInView.add(singleChild);
}
}
childListInViewArray.add(childListInView);
}
#Override
public int getGroupCount() {
return groupList.size();
}
#Override
public int getChildrenCount(int i) {
return childListInViewArray.get(i).size();
}
#Override
public String getGroup(int i) {
return groupList.get(i);
}
#Override
public ArrayList<HashMap<String, String>> getChild(int i, int i1) {
return childListInViewArray.get(i).get(i1);
}
#Override
public long getGroupId(int i) {
return 0;
}
#Override
public long getChildId(int i, int i1) {
return 0;
}
#Override
public boolean hasStableIds() {
return false;
}
#Override
public View getGroupView(int i, boolean b, View view, ViewGroup viewGroup) {
if (view == null) {
view = inflater.inflate(R.layout.item_group, null);
}
TextView tv = view.findViewById(R.id.group);
tv.setText(getGroup(i));
return view;
}
#Override
public View getChildView(int i, int i1, boolean b, View view, ViewGroup viewGroup) {
if (view == null) {
view = inflater.inflate(R.layout.item_child, null);
}
TextView tv = view.findViewById(R.id.child);
ArrayList<HashMap<String, String>> child = getChild(i, i1);
tv.setText(child.get(0).get(groupList.get(i)) + " (" + childListInViewArray.get(i).get(i1).size() + ")");
if (selectedPositions[i] == i1) tv.setTextColor(Color.RED);
else tv.setTextColor(Color.BLACK);
return view;
}
#Override
public boolean isChildSelectable(int i, int i1) {
return true;
}
public void updateViewsOnClick(int group, int child) {
for (int i = group; i < selectedPositions.length; i++) selectedPositions[i] = -1;
selectedPositions[group] = child;
for (int i = childListInViewArray.size() - 1; i > group; i--)
childListInViewArray.remove(i);
if (group == groupList.size() - 1) {
notifyDataSetChanged();
} else {
updateNextGroup(group, child);
}
}
private void updateNextGroup(int group, int child) {
ArrayList<HashMap<String, String>> singleChild;
ArrayList<ArrayList<HashMap<String, String>>> childListInView = new ArrayList<>();
for (HashMap<String, String> rawData : childListInViewArray.get(group).get(child)) {
boolean found = false;
int foundPosition = -1;
if (childListInView.size() > 0) {
for (foundPosition = 0; foundPosition < childListInView.size(); foundPosition++) {
if (childListInView.get(foundPosition).get(0).get(groupList.get(group + 1)).equals(rawData.get(groupList.get(group + 1)))) {
singleChild = childListInView.get(foundPosition);
singleChild.add(rawData);
found = true;
break;
}
}
if (!found) {
singleChild = new ArrayList<>();
singleChild.add(rawData);
childListInView.add(singleChild);
}
} else {
singleChild = new ArrayList<>();
singleChild.add(rawData);
childListInView.add(singleChild);
}
}
childListInViewArray.add(group + 1, childListInView);
notifyDataSetChanged();
}
public int getFinalSelectedItemIndex(int child) {
HashMap<String, String> selectedData = childListInViewArray.get(groupList.size() - 1).get(child).get(0);
return childList.indexOf(selectedData);
}
}
activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<ExpandableListView
android:id="#+id/eLV"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</LinearLayout>
item_group.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:id="#+id/group"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingLeft="30dp"
android:textSize="30sp"/>
</LinearLayout>
item_child.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:id="#+id/child"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingLeft="40dp"
android:textSize="20sp"/>
</LinearLayout>
UPDATE - Added experimentation result
Is it possible to implement an ExpandableListView to have a viewpager child?
I tried to put viewpager as a child in ExpandableListView but it is not showing :( I also tried to add it under ScrollView but same result so I think it is a problem being under a scrollable view? But when I removed ScrollView it showed up. What can I do so they can go together?
This is what I am aiming for to do
And this is what happen when I tried to implement on my own code.
P.S. This is just a sampler and not yet finished. I have 3 children and my layout displayed thrice also with each item inside
can you check this API
https://developer.android.com/reference/android/widget/ExpandableListView
A view that shows items in a vertically scrolling two-level list
I made a sample in Java. Hope that helps!
activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<Button
android:id="#+id/btnClearChecks"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Clear Checks" />
<Button
android:id="#+id/btnPutOrder"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Put Order" />
</LinearLayout>
<ExpandableListView
android:id="#+id/expandedListView"
android:layout_width="match_parent"
android:layout_height="match_parent">
</ExpandableListView>
</LinearLayout>
expanded_list_group.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="wrap_content"
android:descendantFocusability="blocksDescendants" >
<CheckBox
android:id="#+id/cb_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="40dp"
android:layout_gravity="center_vertical" />
<TextView
android:id="#+id/tv_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Text"
android:textSize="30sp" />
</LinearLayout>
list_child_pager.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingStart="60dp">
<android.support.v4.view.ViewPager
android:id="#+id/layout_child"
android:layout_width="match_parent"
android:layout_height="200dp" />
</LinearLayout>
list_pager_item.xml:
<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:columnCount="#integer/pager_col_count"
android:rowCount="#integer/pager_row_count">
</GridLayout>
integers.xml:
<?xml version="1.0" encoding="utf-8"?>
<resources>
<integer name="pager_col_count">3</integer>
<integer name="pager_row_count">3</integer>
</resources>
ChildItemSample.java
public class ChildItemSample {
private boolean checked = false;
private String name;
private int qty;
public int getQty() {
return qty;
}
public void setQty(int qty) {
this.qty = qty;
}
public boolean isChecked() {
return checked;
}
public void setChecked(boolean checked) {
this.checked = checked;
}
public String getName() {
return name;
}
public ChildItemSample(String name, int qty){
this.name = name;
this.qty = qty;
}
}
MainActivity.java:
public class MainActivity extends AppCompatActivity {
Button clearChecks, putOrder;
ExpandableListView expandableListView;
ExpandableListPagerAdapter expandableListAdapter;
int lastExpandedPosition = -1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
expandableListView = findViewById(R.id.expandedListView);
clearChecks = findViewById(R.id.btnClearChecks);
putOrder = findViewById(R.id.btnPutOrder);
List<String> listTitle = genGroupList();
expandableListAdapter = new ExpandableListPagerAdapter(this, getSupportFragmentManager(), listTitle, genChildList(listTitle));
expandableListView.setAdapter(expandableListAdapter);
expandableListView.setOnGroupExpandListener(new ExpandableListView.OnGroupExpandListener() {
#Override
public void onGroupExpand(int groupPosition) {
if(lastExpandedPosition != -1 && (lastExpandedPosition != groupPosition)){
expandableListView.collapseGroup(lastExpandedPosition);
}
lastExpandedPosition = groupPosition;
}
});
clearChecks.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
expandableListAdapter.clearChecks();
}
});
putOrder.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
ArrayList<String> putOrder = expandableListAdapter.getOrderList();
StringBuilder msg = new StringBuilder();
for(int i=0; i<putOrder.size(); i++){
msg.append(putOrder.get(i));
msg.append("\n");
}
Toast.makeText(getBaseContext(), msg, Toast.LENGTH_LONG).show();
}
});
}
private ArrayList<String> genGroupList(){
ArrayList<String> listGroup = new ArrayList<>();
for(int i=1; i<10; i++){
listGroup.add("Group: " + i);
}
return listGroup;
}
private Map<String, List<ChildItemSample>> genChildList(List<String> header){
Map<String, List<ChildItemSample>> listChild = new HashMap<>();
for(int i=0; i<header.size(); i++){
List<ChildItemSample> testDataList = new ArrayList<>();
int a = (int)(Math.random()*28);
for(int j=0; j<a; j++){
ChildItemSample testItem = new ChildItemSample("Child " + (j + 1), 0);
testDataList.add(testItem);
}
listChild.put(header.get(i), testDataList);
}
return listChild;
}
}
ExpandableListPagerAdapter.java:
public class ExpandableListPagerAdapter extends BaseExpandableListAdapter {
private int child_items_per_page;
private Context context;
private FragmentManager fm;
private List<String> listGroup;
private Map<String, List<ChildItemSample>> listChild;
private static int checkedBoxesCount;
private boolean[] checkedGroup;
ExpandableListPagerAdapter(Context context, FragmentManager manager, List<String> listGroup, Map<String,
List<ChildItemSample>> listChild) {
this.context = context;
fm = manager;
this.listGroup = listGroup;
this.listChild = listChild;
checkedBoxesCount = 0;
checkedGroup = new boolean[listGroup.size()];
child_items_per_page = context.getResources().getInteger(R.integer.pager_col_count) *
context.getResources().getInteger(R.integer.pager_row_count);
}
#Override
public int getGroupCount() {
return listGroup.size();
}
#Override
//******* Special *******
public int getChildrenCount(int groupPosition) {
return 1;
}
#Override
public String getGroup(int groupPosition) {
return listGroup.get(groupPosition);
}
#Override
public ChildItemSample getChild(int groupPosition, int childPosition) {
return listChild.get(listGroup.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(int groupPosition, boolean b, View view, ViewGroup viewGroup) {
String itemGroup = getGroup(groupPosition);
GroupViewHolder groupViewHolder;
if(view == null){
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.expanded_list_group, null);
groupViewHolder = new GroupViewHolder();
groupViewHolder.tvGroup = view.findViewById(R.id.tv_group);
groupViewHolder.cbGroup = view.findViewById(R.id.cb_group);
groupViewHolder.cbGroup.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int pos = (int)view.getTag();
checkedGroup[pos] = !checkedGroup[pos];
for(ChildItemSample item : listChild.get(listGroup.get(pos))){
item.setChecked(checkedGroup[pos]);
}
notifyDataSetChanged();
}
});
view.setTag(groupViewHolder);
}else {
groupViewHolder = (GroupViewHolder)view.getTag();
}
groupViewHolder.tvGroup.setText(String.format("%s (%d)", itemGroup, listChild.get(listGroup.get(groupPosition)).size()));
if(checkedGroup[groupPosition]) groupViewHolder.cbGroup.setChecked(true);
else groupViewHolder.cbGroup.setChecked(false);
groupViewHolder.cbGroup.setTag(groupPosition);
return view;
}
#Override
public View getChildView(final int groupPosition, int childPosition, boolean b, View view, ViewGroup viewGroup) {
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View rowView = inflater.inflate(R.layout.list_child_pager, null);
ViewPager childLayout = rowView.findViewById(R.id.layout_child);
List<ChildItemSample> childItemSampleList = listChild.get(listGroup.get(groupPosition));
ChildPagerAdapter adapter = new ChildPagerAdapter(fm, childItemSampleList, child_items_per_page);
childLayout.setAdapter(adapter);
return rowView;
}
public class ChildPagerAdapter extends FragmentStatePagerAdapter {
private List<ChildItemSample> pagerItemList;
private int items_per_page;
ChildPagerAdapter(FragmentManager fm, List<ChildItemSample> pagerItemList, int items_per_page) {
super(fm);
this.pagerItemList = pagerItemList;
this.items_per_page = items_per_page;
}
#Override
public Fragment getItem(int position) {
return ChildFragment.newInstance(position, pagerItemList, items_per_page);
}
#Override
public int getCount() {
int remainedItemCount = pagerItemList.size()%child_items_per_page;
if(remainedItemCount == 0)
return (pagerItemList.size()/child_items_per_page);
else
return (pagerItemList.size()/child_items_per_page + 1);
}
}
public static class ChildFragment extends Fragment {
private static final String SECTION_NUMBER = "section_number";
private static final String ITEMS_PER_PAGE = "items/page";
private static List<ChildItemSample> itemList;
public ChildFragment() {}
public static ChildFragment newInstance(int sectionNumber, List<ChildItemSample> pagerItemList,
int itemPerPage) {
ChildFragment fragment = new ChildFragment();
Bundle args = new Bundle();
args.putInt(SECTION_NUMBER, sectionNumber);
args.putInt(ITEMS_PER_PAGE, itemPerPage);
fragment.setArguments(args);
itemList = pagerItemList;
return fragment;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
int child_items_per_page = getArguments().getInt(ITEMS_PER_PAGE);
int start_item = getArguments().getInt(SECTION_NUMBER)*child_items_per_page;
int itemCount = itemList.size() - getArguments().getInt(SECTION_NUMBER)*child_items_per_page;
if(itemCount > child_items_per_page) itemCount = child_items_per_page;
itemCount += getArguments().getInt(SECTION_NUMBER)*child_items_per_page;
GridLayout pageView = (GridLayout)inflater.inflate(R.layout.list_pager_item, container, false);
for(int i=start_item; i<itemCount; i++){
ChildItemSample expandedListText = itemList.get(i);
CheckBox cbChild = new CheckBox(getContext());
GridLayout.LayoutParams params = new GridLayout.LayoutParams();
params.width = (int)(80 * getContext().getResources().getDisplayMetrics().density);
cbChild.setLayoutParams(params);
cbChild.setChecked(expandedListText.isChecked());
cbChild.setText(expandedListText.getName());
cbChild.setTag(i);
pageView.addView(cbChild);
cbChild.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
CheckBox cb = (CheckBox) view;
int pos = (int) view.getTag();
ChildItemSample selectedItem = itemList.get(pos);
selectedItem.setChecked(cb.isChecked());
if(cb.isChecked()){
checkedBoxesCount++;
Toast.makeText(getContext(),"Checked value is: " +
itemList.get(pos).getName(),
Toast.LENGTH_SHORT).show();
}else {
checkedBoxesCount--;
if(checkedBoxesCount == 0){
Toast.makeText(getContext(),"nothing checked",Toast.LENGTH_SHORT).show();
}else {
Toast.makeText(getContext(),"unchecked",Toast.LENGTH_SHORT).show();
}
}
}
});
}
return pageView;
}
}
public void clearChecks() {
for(int i=0; i<checkedGroup.length; i++) checkedGroup[i] = false;
for(List<ChildItemSample> value : listChild.values()) {
for (ChildItemSample sample : value) {
sample.setChecked(false);
}
}
checkedBoxesCount = 0;
notifyDataSetChanged();
}
public ArrayList<String> getOrderList(){
ArrayList<String> overallOrder = new ArrayList<>();
for(int i=0; i<getGroupCount(); i++){
//for(int j=0; j<getChildrenCount(i); j++){
for(int j=0; j<listChild.get(getGroup(i)).size(); j++){
if(getChild(i,j).isChecked()){
String newOrder = getGroup(i) + ">" + getChild(i, j).getName();
overallOrder.add(newOrder);
}
}
}
return overallOrder;
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
private class GroupViewHolder {
CheckBox cbGroup;
TextView tvGroup;
}
}
Another sample adapter that has ViewPager child (Without fragment)
public class ExpandableListPagerAdapter2 extends BaseExpandableListAdapter {
private Context context;
private List<String> listGroup;
private Map<String, List<ChildItemSample>> listChild;
private int checkedBoxesCount;
private boolean[] checkedGroup;
private int child_items_per_page;
ExpandableListPagerAdapter2(Context context, List<String> listGroup, Map<String,
List<ChildItemSample>> listChild) {
this.context = context;
this.listGroup = listGroup;
this.listChild = listChild;
checkedBoxesCount = 0;
checkedGroup = new boolean[listGroup.size()];
child_items_per_page = context.getResources().getInteger(R.integer.pager_col_count) *
context.getResources().getInteger(R.integer.pager_row_count);
}
#Override
public int getGroupCount() {
return listGroup.size();
}
// ******* Special *******
#Override
public int getChildrenCount(int groupPosition) {
return 1;
}
#Override
public String getGroup(int groupPosition) {
return listGroup.get(groupPosition);
}
#Override
public ChildItemSample getChild(int groupPosition, int childPosition) {
return listChild.get(listGroup.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(int groupPosition, boolean b, View view, ViewGroup viewGroup) {
String itemGroup = getGroup(groupPosition);
GroupViewHolder groupViewHolder;
if(view == null){
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.expanded_list_group, null);
groupViewHolder = new GroupViewHolder();
groupViewHolder.tvGroup = view.findViewById(R.id.tv_group);
groupViewHolder.cbGroup = view.findViewById(R.id.cb_group);
groupViewHolder.cbGroup.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int pos = (int)view.getTag();
checkedGroup[pos] = !checkedGroup[pos];
for(ChildItemSample item : listChild.get(listGroup.get(pos))){
item.setChecked(checkedGroup[pos]);
}
notifyDataSetChanged();
}
});
view.setTag(groupViewHolder);
}else {
groupViewHolder = (GroupViewHolder)view.getTag();
}
groupViewHolder.tvGroup.setText(String.format("%s (%d)", itemGroup, listChild.get(listGroup.get(groupPosition)).size()));
if(checkedGroup[groupPosition]) groupViewHolder.cbGroup.setChecked(true);
else groupViewHolder.cbGroup.setChecked(false);
groupViewHolder.cbGroup.setTag(groupPosition);
return view;
}
#Override
public View getChildView(int groupPosition, int childPosition, boolean b, View view, ViewGroup viewGroup) {
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View rowView = inflater.inflate(R.layout.list_child_pager, null);
ViewPager childLayout = rowView.findViewById(R.id.layout_child);
List<ChildItemSample> childItemSampleList = listChild.get(listGroup.get(groupPosition));
ChildPagerAdapter adapter = new ChildPagerAdapter(childItemSampleList);
childLayout.setAdapter(adapter);
return rowView;
}
public class ChildPagerAdapter extends PagerAdapter {
private List<ChildItemSample> pagerItemList;
ChildPagerAdapter(List<ChildItemSample> pagerItemList) {
this.pagerItemList = pagerItemList;
}
#Override
public Object instantiateItem(ViewGroup container, int position) {
int start_item = position*child_items_per_page;
int itemCount = pagerItemList.size() - start_item;
if(itemCount > child_items_per_page) itemCount = child_items_per_page;
itemCount += start_item;
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
GridLayout pageView = (GridLayout)inflater.inflate(R.layout.list_pager_item, container, false);
for(int i=start_item; i<itemCount; i++){
ChildItemSample expandedListText = pagerItemList.get(i);
CheckBox cbChild = new CheckBox(context);
GridLayout.LayoutParams params = new GridLayout.LayoutParams();
params.width = (int)(80 * context.getResources().getDisplayMetrics().density);
cbChild.setLayoutParams(params);
cbChild.setChecked(expandedListText.isChecked());
cbChild.setText(expandedListText.getName() + "(" + expandedListText.getQty() + ")");
cbChild.setTag(i);
pageView.addView(cbChild);
cbChild.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int pos = (int) view.getTag();
final ChildItemSample selectedItem = pagerItemList.get(pos);
AlertDialog.Builder builder = new AlertDialog.Builder(context);
builder.setTitle(selectedItem.getName());
final EditText editText = new EditText(context);
editText.setText("");
editText.append(String.valueOf(selectedItem.getQty()));
builder.setView(editText);
builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
selectedItem.setQty(Integer.parseInt(editText.getText().toString()));
ExpandableListPagerAdapter2.this.notifyDataSetChanged();
}
});
builder.setNegativeButton("Cancel", null);;
builder.show();
editText.requestFocus();
editText.postDelayed(new Runnable() {
#Override
public void run() {
InputMethodManager keyboard = (InputMethodManager)
context.getSystemService(Context.INPUT_METHOD_SERVICE);
keyboard.showSoftInput(editText, 0);
}
},200);
}
});
}
container.addView(pageView);
return pageView;
}
#Override
public void destroyItem(ViewGroup container, int position, Object object) {
container.removeView((View)object);
}
#Override
public int getCount() {
int remainedItemCount = pagerItemList.size()%child_items_per_page;
if(remainedItemCount == 0)
return (pagerItemList.size()/child_items_per_page);
else
return (pagerItemList.size()/child_items_per_page + 1);
}
#Override
public boolean isViewFromObject(View view, Object object) {
return view == object;
}
}
public void clearChecks() {
for(int i=0; i<checkedGroup.length; i++) checkedGroup[i] = false;
for(List<ChildItemSample> value : listChild.values()) {
for (ChildItemSample sample : value) {
sample.setChecked(false);
}
}
checkedBoxesCount = 0;
notifyDataSetChanged();
}
public ArrayList<ChildItemSample> getOrderList(){
ArrayList<ChildItemSample> overallOrder = new ArrayList<>();
for(int i=0; i<getGroupCount(); i++){
for(int j=0; j<listChild.get(getGroup(i)).size(); j++){
if(getChild(i,j).getQty() > 0){
ChildItemSample newOrder = new ChildItemSample(getGroup(i) + ">" +
getChild(i, j).getName(), getChild(i, j).getQty());
overallOrder.add(newOrder);
}
}
}
return overallOrder;
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
private class GroupViewHolder {
CheckBox cbGroup;
TextView tvGroup;
}
}
I am searching for a way to load data into an Expandale List View, the output I want to resemble the one of the picture attached here
In order this to be done dynamically, is it better to be read from a csv? Or to create a DB? Furthermore, on a sub-item press, I want a ScrollView to appear.
Here is the code so far:
The layout of the activity:
<?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="wrap_content">
<ExpandableListView
android:id= "#+id/android:list"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
<TextView
android:id="#+id/android:empty"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
</LinearLayout>
The itemlayout:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView android:id="#+id/grp_child"
android:paddingLeft="50dp"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
</LinearLayout>
And the subitem:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView android:id="#+id/row_name"
android:paddingLeft="50dp"
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
</LinearLayout>
In the activity, I have hardcoded some values so far, using some tutorials I came across:
public void onCreate(Bundle savedInstanceState) {
try{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_photographers);
SimpleExpandableListAdapter expListAdapter =
new SimpleExpandableListAdapter(
this,
createGroupList(),
R.layout.group_row,
new String[] { "Group Item" },
new int[] { R.id.row_name },
createChildList(),
R.layout.child_row,
new String[] {"Sub Item"},
new int[] { R.id.grp_child}
);
setListAdapter( expListAdapter );
}catch(Exception e){
System.out.println("Errrr +++ " + e.getMessage());
}
}
/* Creating the Hashmap for the row */
#SuppressWarnings("unchecked")
private List createGroupList() {
ArrayList result = new ArrayList();
for( int i = 0 ; i < 15 ; ++i ) { // 15 groups........
HashMap m = new HashMap();
m.put( "Group Item","Group Item " + i ); // the key and it's value.
result.add( m );
}
return (List)result;
}
#SuppressWarnings("unchecked")
private List createChildList() {
ArrayList result = new ArrayList();
for( int i = 0 ; i < 15 ; ++i ) { // this -15 is the number of groups(Here it's fifteen)
/* each group need each HashMap-Here for each group we have 3 subgroups */
ArrayList secList = new ArrayList();
for( int n = 0 ; n < 3 ; n++ ) {
HashMap child = new HashMap();
child.put( "Sub Item", "Sub Item " + n );
secList.add( child );
}
result.add( secList );
}
return result;
}
public void onContentChanged () {
System.out.println("onContentChanged");
super.onContentChanged();
}
/* This function is called on each child click */
public boolean onChildClick( ExpandableListView parent, View v, int groupPosition,int childPosition,long id) {
System.out.println("Inside onChildClick at groupPosition = " + groupPosition +" Child clicked at position " + childPosition);
return true;
}
/* This function is called on expansion of the group */
public void onGroupExpand (int groupPosition) {
try{
System.out.println("Group expanding Listener => groupPosition = " + groupPosition);
}catch(Exception e){
System.out.println(" groupPosition Errrr +++ " + e.getMessage());
}
}
I am wondering if it is a good idea to store the data I want to show in separate csv files (one storing the data for the items, one for the subitems. one for the extra information in the ScrollView), to have id-s for identification and to directly read from the CSVs with the OpenCSVReader?
I would appreciate any pieces of advice,
Thanks
create adapter for your expandable listView. like that
public class ExpandableAdapter extends BaseExpandableListAdapter {
private final Context context;
private final List<Menu> parentObjects;
public ExpandableAdapter(Context context, ArrayList<Menu> parentObjects) {
this.context = context;
this.parentObjects = parentObjects;
}
#Override
public int getGroupCount() {
return parentObjects.size();
}
#Override
public int getChildrenCount(int i) {
return parentObjects.get(i).childMenu.size();
}
#Override
public Menu getGroup(int i) {
return parentObjects.get(i);
}
#Override
public Menu.ChildMenu getChild(int i, int i2) {
return parentObjects.get(i).childMenu.get(i2);
}
#Override
public long getGroupId(int i) {
return i;
}
#Override
public long getChildId(int i, int i2) {
return 0;
}
#Override
public boolean hasStableIds() {
return false;
}
#Override
public View getGroupView(int i, boolean b, View view, ViewGroup viewGroup) {
Menu currentParent = parentObjects.get(i);
if (view == null) {
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context
.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.navdrawer_parent_item, viewGroup,false);
}
ImageView imageViewIndicator = (ImageView) view.findViewById(R.id.imageViewNav);
if (getChildrenCount(i) == 0)
imageViewIndicator.setVisibility(View.GONE);
else
imageViewIndicator.setVisibility(View.VISIBLE);
TextView textViewNavMenuName = (TextView) view.findViewById(R.id.textViewNavParentMenuName);
ImageView imageViewIcon = (ImageView) view.findViewById(R.id.imageViewIcon);
String base64 = currentParent.getImage();
if (base64 != null && !base64.equals("")) {
byte[] imageAsBytes = Base64.decode(currentParent.getImage().getBytes(), Base64
.DEFAULT);
imageViewIcon.setImageBitmap(BitmapFactory.decodeByteArray(imageAsBytes, 0,
imageAsBytes.length));
} else
imageViewIcon.setImageResource(R.drawable.ic_action_android);
textViewNavMenuName.setText(currentParent.getMenuName());
return view;
}
#Override
public View getChildView(int groupPosition, int childPosition, boolean b, View view,
ViewGroup viewGroup) {
Menu currentChild = getGroup(groupPosition);
if (view == null) {
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context
.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.navdrawer_child_item, viewGroup,false);
}
View divider = view.findViewById(R.id.divider);
if (b)
divider.setVisibility(View.VISIBLE);
else
divider.setVisibility(View.GONE);
TextView textViewNavMenuName = (TextView) view.findViewById(R.id.textViewNavChildMenuName);
textViewNavMenuName.setText(currentChild.childMenu.get(childPosition).getMenuName());
return view;
}
#Override
public boolean isChildSelectable(int i, int i2) {
return true;
}
}
and the model for the expandable listView like
public class Menu {
private int AssociatedApp;
private String MenuName;
private String NavigateURL;
private String ActivityName;
private String Image;
private int MenuID;
public ArrayList<ChildMenu> childMenu;
public ArrayList<ChildMenu> getChildMenu() {
return childMenu;
}
public void setChildMenu(ArrayList<ChildMenu> childMenu) {
this.childMenu = childMenu;
}
public int getAssociatedApp() {
return AssociatedApp;
}
public void setAssociatedApp(int associatedApp) {
AssociatedApp = associatedApp;
}
public String getMenuName() {
return MenuName;
}
public void setMenuName(String menuName) {
MenuName = menuName;
}
public String getNavigateURL() {
return NavigateURL;
}
public void setNavigateURL(String navigateURL) {
NavigateURL = navigateURL;
}
public String getActivityName() {
return ActivityName;
}
public void setActivityName(String activityName) {
ActivityName = activityName;
}
public String getImage() {
return Image;
}
public void setImage(String image) {
Image = image;
}
public Menu() {
}
public int getMenuID() {
return MenuID;
}
public class ChildMenu {
private int AssociatedApp;
private String MenuName;
private String NavigateURL;
private String ActivityName;
private String Image;
private int MenuID;
public ChildMenu(String menuName, String activityName) {
this.MenuName = menuName;
this.ActivityName=activityName;
}
public ChildMenu() {
}
public int getAssociatedApp() {
return AssociatedApp;
}
public void setAssociatedApp(int associatedApp) {
AssociatedApp = associatedApp;
}
public String getMenuName() {
return MenuName;
}
public void setMenuName(String menuName) {
MenuName = menuName;
}
public String getNavigateURL() {
return NavigateURL;
}
public void setNavigateURL(String navigateURL) {
NavigateURL = navigateURL;
}
public String getActivityName() {
return ActivityName;
}
public void setActivityName(String activityName) {
ActivityName = activityName;
}
public String getImage() {
return Image;
}
public void setImage(String image) {
Image = image;
}
public int getMenuID() {
return MenuID;
}
}
}
ok now you can create your menu with data and bindwith expandable listview
elv = (ExpandableListView)findViewById(R.id.elv);
elv.setOnGroupExpandListener(onGroupExpandListenser);
MyExpandableAdapter adapter = new MyExpandableAdapter(this, getData());//where getData() will return list of data.
elv.setAdapter(adapter);
parent xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="match_parent"
android:paddingBottom="12dp"
android:paddingLeft="12dp"
android:paddingTop="12dp">
<ImageView
android:contentDescription="#string/app_name"
android:id="#+id/imageViewIcon"
android:layout_width="35dp"
android:layout_height="35dp"
android:layout_alignParentLeft="true"
android:layout_margin="4dp"
/>
<TextView
android:id="#+id/textViewNavParentMenuName"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerInParent="true"
android:layout_centerVertical="true"
android:layout_toLeftOf="#+id/imageViewNav"
android:layout_toRightOf="#+id/imageViewIcon"
android:padding="10dp"
android:textSize="15sp"/>
<ImageView
android:contentDescription="#string/app_name"
android:id="#+id/imageViewNav"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_margin="4dp"
android:src="#drawable/ic_action_more_nav"
/>
</RelativeLayout>
<include
layout="#layout/divider"
android:layout_width="fill_parent"
android:layout_height="fill_parent"/>
</LinearLayout>
child xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:orientation="vertical">
<TextView
android:id="#+id/textViewNavChildMenuName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="45dp"
android:gravity="center_vertical"
android:text="TextView"
android:padding="16dp"/>
<include
layout="#layout/divider"
android:layout_width="match_parent"
android:layout_height="fill_parent"/>
</LinearLayout>
adding listener for expandable listView like this. groupExpandlistener is used for collasping other groups while open one
private int lastExpandedPosition = -1;
for setting up listener
elv.setOnChildClickListener(new DrawerItemClickListener());
elv.setOnGroupClickListener(new DrawerItemClickListener());
elv.setOnGroupExpandListener(new DrawerItemClickListener());
private class DrawerItemClickListener implements ExpandableListView.OnChildClickListener,
ExpandableListView.OnGroupClickListener, ExpandableListView.OnGroupExpandListener {
#Override
public boolean onChildClick(ExpandableListView parent, View v, int groupPosition, int
childPosition, long id) {
selectItem(childPosition, navigationConfig.getBaseExpandableListAdapter
().getChild
(groupPosition, childPosition));
return true;
}
#Override
public boolean onGroupClick(ExpandableListView parent, View v, int groupPosition, long id) {
selectItem(groupPosition, navigationConfig.getBaseExpandableListAdapter
().getGroup
(groupPosition));
return false;
}
#Override
public void onGroupExpand(int groupPosition) {
if (lastExpandedPosition != -1
&& groupPosition != lastExpandedPosition) {
expandableListView.collapseGroup(lastExpandedPosition);
}
lastExpandedPosition = groupPosition;
}
}
for sample data use to bind with getData(). note create constructor in model class as given in getData()
//Sample data for expandable list view.
public List<Menu> getData()
{
List<Menu> parentObjects = new ArrayList<Menu>();
for (int i = 0; i<20; i++)
{
parentObjects.add(new Menu("Mother " +i, "Father " +i, "Header " + i, "Footer " +i, getChildren(i)));
}
return parentObjects;
}
private List<Menu.ChildMenu> getChildren(int childCount)
{
List<Menu.ChildMenu> childObjects = new ArrayList<Menu.ChildMenu>();
for (int i =0; i<childCount; i++)
{
childObjects.add(new Menu.ChildMenu("Child " + (i+1), 10 +i ));
}
return childObjects;
}
I have several classes. First class extends from FragmentActivity, second class is adapter extends from BaseExpandableListAdapter. And Model Class.
First class:
public class CloseInformationTaskActivityList extends FragmentActivity implements ExpandableListView.OnChildClickListener {
private DAOFactory dao;
private ExpandListAdapter expAdapter;
private ExpandableListView expandList;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Bundle b = getIntent().getExtras();
//task with all information passed in intent by reference
PRTarea task = (PRTarea) b.getSerializable("Task");
dao = new DAOFactory(this.getApplicationContext());
List<PRParametros> parametrosList = dao.getParametrosDAO().getParamsByTaskId(task.getId());
if (parametrosList.size() > 0) {
setContentView(R.layout.activity_task_parameters_list);
expandList = (ExpandableListView) findViewById(R.id.paramsExpandableListView);
ArrayList<Group> expListItems = setParamsGroups(parametrosList);
expAdapter = new ExpandListAdapter(CloseInformationTaskActivityList.this, expListItems, this);
expandList.setOnChildClickListener(this);
expandList.setAdapter(expAdapter);
} else {
setContentView(R.layout.activity_no_param_error);
}
// Set up the action bar.
final ActionBar actionBar = getActionBar();
// Specify that the Home/Up button should not be enabled, since there is no hierarchical
// parent.
assert actionBar != null;
actionBar.setDisplayUseLogoEnabled(false);
actionBar.setHomeButtonEnabled(true);
actionBar.setDisplayHomeAsUpEnabled(false);
actionBar.setTitle(R.string.task_information_title);
actionBar.setIcon(R.drawable.ic_arrow_back_white_24dp);
}
private ArrayList<Group> setParamsGroups(List<PRParametros> parametrosList) {
ArrayList<Group> paramGroupList = new ArrayList<>();
ArrayList<Child> ch_list = null;
Group grupo;
String holdIdGroup = "0";
//secure check
if (parametrosList != null && parametrosList.size() > 0) {
for (int i = 0; i < parametrosList.size(); i++) {
PRParametros parametro = parametrosList.get(i);
String idGrupo = parametro.getIdGrupo();
if (!idGrupo.equals(holdIdGroup)) {
holdIdGroup = idGrupo;
grupo = new Group();
ch_list = new ArrayList<>();
grupo.setName(dao.getGruposParametrosDAO().getGrupoById(idGrupo).getDescripcion());
grupo.setItems(ch_list);
paramGroupList.add(grupo);
}
Child child = new Child();
child.setName(parametro.getNombre());
if(parametro.getIdTipo().equals("12")){
if(parametro.getValor() != null){
paramValue = dao.getListaParametrosDAO().getValueParamById(Integer.valueOf(parametro.getValor()));
}
}
child.setValue(paramValue);
child.setType(Integer.valueOf(parametro.getIdTipo()));
child.setParamId(Integer.valueOf(parametro.getId()));
if (ch_list != null) {
ch_list.add(child);
}
}
}
return paramGroupList;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
finish();
return true;
case R.id.btn_save_param:
saveParameters();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
private void saveParameters() {
Toast.makeText(getApplicationContext(),"Save parameters click", Toast.LENGTH_SHORT).show();
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.save_parameters, menu);
return super.onCreateOptionsMenu(menu);
}
#Override
public boolean onChildClick(ExpandableListView parent, View v, int groupPosition, int childPosition, long id) {
Child child = (Child) parent.getExpandableListAdapter().getChild(groupPosition,childPosition);
int itemType = child.getType();
switch (itemType){
case 12:
onCreateDialogSingleChoice(child, v);
break;
case 9:
openDateDialog(child, v);
break;
}
return false;
}
/**
* Open popup with single choice, refresh model data of child
* and assign selected value to textView
*
* #param child model with data
* #param view to asign selected value
*/
public void onCreateDialogSingleChoice(final Child child, final View view) {
final AlertDialog.Builder builder = new AlertDialog.Builder(this);
List<PRListaParametros> listaParametros = dao.getListaParametrosDAO().getListParamsById(child.getParamId());
List<String> values = new ArrayList<>();
for(int i = 0; i < listaParametros.size(); i++){
values.add(listaParametros.get(i).getDescripcion());
}
final String[] items = values.toArray(new String[listaParametros.size()]);
final TextView label = (TextView) ((RelativeLayout) view).getChildAt(1);
builder.setTitle(R.string.task_information_param_popup_title);
builder.setSingleChoiceItems(items, 75, new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
label.setText(items[which]);
child.setValue(items[which]);
dialog.dismiss();
}
});
builder.setNegativeButton(R.string.task_information_param_popup_negative_button,new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
label.setText("");
}
});
builder.show();
}
}
Second class:
/**
* Adapter for expandable list with parameters
*/
public class ExpandListAdapter extends BaseExpandableListAdapter {
private Context mContext;
private ArrayList<Group> groups;
private LayoutInflater mInflater;
public ExpandListAdapter(Context mContext, ArrayList<Group> groups) {
this.mContext = mContext;
this.groups = groups;
mInflater = (LayoutInflater) mContext
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
#Override
public Object getChild(int groupPosition, int childPosition) {
ArrayList<Child> chList = groups.get(groupPosition).getItems();
return chList.get(childPosition);
}
#Override
public boolean areAllItemsEnabled() {
return super.areAllItemsEnabled();
}
#Override
public View getChildView(int groupPosition, final int childPosition,
final boolean isLastChild, View convertView, ViewGroup parent) {
final Child child = (Child) getChild(groupPosition, childPosition);
final ViewHolder holder;
int itemType = child.getType();
holder = new ViewHolder();
if (itemType >= 1 && itemType <= 7) {
convertView = mInflater.inflate(R.layout.layout_edit_text_close_information, null);
holder.txtLabel = (TextView) convertView.findViewById(R.id.txt_task_detail_info_param);
holder.editText = (EditText) convertView.findViewById(R.id.txt_task_detail_info_param_input);
holder.editText.addTextChangedListener(new TextWatcher() {
#Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
#Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
#Override
public void afterTextChanged(Editable s) {
//refresh data in model
child.setValue(holder.editText.getText().toString());
}
});
}else if(itemType == 8){
convertView = mInflater.inflate(R.layout.layout_boolean_close_information, null);
holder.txtLabel = (TextView) convertView.findViewById(R.id.txt_task_detail_info_param_boolean_title);
holder.booleanSwitch = (Switch) convertView.findViewById(R.id.param_boolean_switch);
holder.booleanSwitch.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String switchValue = "false";
if(holder.booleanSwitch.isChecked()){
switchValue = "true";
}
child.setValue(switchValue);
//mParamListener.onParameterViewClick(v, child);
}
});
}else {
convertView = mInflater.inflate(R.layout.layout_text_view_close_information, null);
holder.txtLabel = (TextView) convertView.findViewById(R.id.txt_task_detail_info_param_text_view);
holder.txtClickWithValue = (TextView) convertView.findViewById(R.id.txt_task_detail_info_param_click_text_view);
}
convertView.setTag(holder);
if (itemType >= 1 && itemType <= 7) {
holder.txtLabel.setText(child.getName());
holder.editText.setText(child.getValue());
switch (itemType){
case 1:
holder.editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_CLASS_NUMBER);
holder.editText.setKeyListener(DigitsKeyListener.getInstance("0123456789"));
break;
case 2:
holder.editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_CLASS_NUMBER);
holder.editText.setKeyListener(DigitsKeyListener.getInstance("0123456789."));
break;
case 6:
holder.editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_CLASS_NUMBER);
holder.editText.setKeyListener(DigitsKeyListener.getInstance("0123456789."));
if(!holder.editText.getText().toString().isEmpty()){
if(!isValidIp(holder.editText.getText().toString())){
holder.editText.setError("IPv 4 no valido");
}
}
break;
case 7:
holder.editText.setInputType(InputType.TYPE_TEXT_FLAG_CAP_CHARACTERS);
if(!holder.editText.getText().toString().equals("")){
if(!isValidIp(holder.editText.getText().toString())){
holder.editText.setError("IPv 6 no valido");
}
}
holder.editText.addTextChangedListener(new TextWatcher() {
#Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
#Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
#Override
public void afterTextChanged(Editable s) {
if(!isValidIp(holder.editText.getText().toString())){
holder.editText.setError("IPv 6 no valido");
}
}
});
break;
}
}else if(itemType == 8) {
boolean value = Boolean.valueOf(child.getValue());
holder.txtLabel.setText(child.getName());
if(value){
holder.booleanSwitch.setTextOn(mContext.getResources().getString(R.string.task_information_param_boolean_switch_on));
holder.booleanSwitch.setChecked(true);
}else{
holder.booleanSwitch.setTextOff(mContext.getResources().getString(R.string.task_information_param_boolean_switch_off));
holder.booleanSwitch.setChecked(false);
}
}else {
holder.txtLabel.setText(child.getName());
holder.txtClickWithValue.setText(child.getValue());
}
return convertView;
}
#Override
public void registerDataSetObserver(DataSetObserver observer) {
super.registerDataSetObserver(observer);
//call notifyDataSetChanged() for refresh data model in view
}
public static class ViewHolder {
public TextView txtLabel;
public EditText editText;
public TextView txtClickWithValue;
public Switch booleanSwitch;
}
#Override
public long getChildId(int groupPosition, int childPosition) {
return childPosition;
}
#Override
public int getChildrenCount(int groupPosition) {
ArrayList<Child> chList = groups.get(groupPosition).getItems();
return chList.size();
}
#Override
public Object getGroup(int groupPosition) {
return groups.get(groupPosition);
}
#Override
public int getGroupCount() {
return groups.size();
}
#Override
public long getGroupId(int groupPosition) {
return groupPosition;
}
#Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
Group group = (Group) getGroup(groupPosition);
if (convertView == null) {
LayoutInflater inf = (LayoutInflater) mContext
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inf.inflate(R.layout.activity_task_parameters_group, null);
}
TextView groupTitle = (TextView) convertView.findViewById(R.id.param_group_name);
groupTitle.setText(group.getName());
TextView groupCount = (TextView) convertView.findViewById(R.id.param_group_count);
int countParam = getChildrenCount(groupPosition);
if(countParam > 1){
groupCount.setText(getChildrenCount(groupPosition) + " " +
mContext.getResources().getString(R.string.task_information_param_group_count_title));
}else{
groupCount.setText(getChildrenCount(groupPosition) + " " +
mContext.getResources().getString(R.string.task_information_param_group_count_title_single));
}
if (isExpanded) {
convertView.setBackgroundResource(R.color.group_param_expanded);
} else {
convertView.setBackgroundResource(0);
}
return convertView;
}
#Override
public int getChildType(int groupPosition, int childPosition) {
return super.getChildType(groupPosition, childPosition);
}
#Override
public boolean hasStableIds() {
return true;
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
/**
* #param ip the ip
* #return check if the ip is valid ipv4 or ipv6
*/
private static boolean isValidIp(final String ip) {
return InetAddressUtils.isIPv4Address(ip) || InetAddressUtils.isIPv6Address(ip);
}
}
Model Class
/**
* Model of each parameters
*/
public class Child {
private String name;
private String value;
private int type;
private int paramId;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getValue() {
return value;
}
public void setValue(String value) {
this.value = value;
}
public int getType() {
return type;
}
public void setType(int type) {
this.type = type;
}
public int getParamId() {
return paramId;
}
public void setParamId(int paramId) {
this.paramId = paramId;
}
}
XML View of each child by type, possible type is EditText, TextView, Switch, popup list with single choice.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="60dp">
<TextView
android:id="#+id/txt_task_detail_info_param"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="1"
android:minWidth="150dp"
android:focusable="false"
android:clickable="false"
android:padding="20dp"
android:textSize="14sp"
android:layout_toLeftOf="#+id/txt_task_detail_info_param_input"
android:layout_alignParentLeft="true" />
<EditText
android:id="#+id/txt_task_detail_info_param_input"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:minWidth="150dp"
android:maxWidth="200dp"
android:ellipsize="end"
android:maxLines="1"
android:textSize="14sp"
android:layout_centerVertical="true"
android:layout_alignParentRight="true" />
</RelativeLayout>
Layout have action bar with save button:
|------------------Save button--|
| <ExpandableList> | |
| group1 | |
| child1: textView EditText | |
| child2: textView Switch | |
| group2 | |
| child1: textView TextView | |
|-------------------------------|
I am trying to get values of child view for save it in database, before i need check each field by type for valid data.
Currently i am checking the values in adapter and works well. Possibly not the right way...
But how to get value of each view by type only clicking save button in FragmentActivity in action bar??
I am trying onChildClick but click event by editText not working. Thanks!
SOLVED
Now I have resolved, but I think is not the right way for do it.
In model class Child i created new field with View.
private View view;
and assigned complete View by type (editText,TextView, etc) in adapter getChildView for example:
child.setView(holder.editText);
and finally use in FragmentActivity
private void checkParameters() {
boolean validated = true;
int groupCount = expandList.getExpandableListAdapter().getGroupCount();
for (int i = 0; i < groupCount; i++) {
int childCount = expandList.getExpandableListAdapter().getChildrenCount(i);
for (int j = 0; j < childCount; j++) {
Child child = (Child) expandList.getExpandableListAdapter().getChild(i, j);
//secure check
if (child.getView() != null) {
int itemType = child.getType();
//only editText
if (itemType >= 1 && itemType <= 7) {
EditText ed = (EditText) child.getView();
//do something
}
}
}
}
}
Anyone know how to do this more efficiently???
I have followed this example tutorial and developed a sample application http://www.androidhive.info/2013/07/android-expandable-list-view-tutorial/
If i click on Core i want to load one more list in the same Screen under Core,How Could i do this?using my below code i am able to load the child list in another Screen,help?
My Code for ChildClickListener goes here:
#Override
public boolean onChildClick(ExpandableListView parent, View v,
int groupPosition, int childPosition, long id) {
// TODO Auto-generated method stub
Log.d("onChildClick", "onChildClick");
String position = (String) parentItems.get(groupPosition);
Log.d("position", position);
String child = listDataChild.get(position).get(childPosition);
Log.d("child", child);
if (child.equalsIgnoreCase("Core")) {
ArrayList<String> parentItems = new ArrayList<String>();
HashMap<String, List<String>> listDataChild = new HashMap<String, List<String>>();
ArrayList<String> childItems = new ArrayList<String>();
childItems.add("corejava");
childItems.add("corejava");
childItems.add("corejava");
childItems.add("corejava");
parentItems.add(position);
listDataChild.put(parentItems.get(0), childItems);
expandableList = (ExpandableListView) findViewById(R.id.lvExp);
CoreAdapter adapter = new CoreAdapter(parentItems,
listDataChild);
CustExpListview SecondLevelexplv = new CustExpListview(
MainActivity.this);
adapter.setInflater(
(LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE),
MainActivity.this);
SecondLevelexplv.setAdapter(adapter);
SecondLevelexplv.setGroupIndicator(null);
expandableList.setAdapter(adapter);
}
i write one treeView adapter for you, you can use this and put many level as you want, for that you need just copy following code:
MainActivity:
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// add data for test on one list<AccountHierarchical>
AccountHierarchical obj = new AccountHierarchical();
obj.setLevelId(1);
obj.setTitle("level 1");
AccountHierarchical obj2 = new AccountHierarchical();
obj2.setLevelId(1);
obj2.setTitle("level 2");
AccountHierarchical obj3 = new AccountHierarchical();
obj3.setLevelId(1);
obj3.setTitle("level 3");
List<AccountHierarchical> emptyList = new ArrayList<AccountHierarchical>();
obj3.setList(emptyList);
List<AccountHierarchical> list2 = new ArrayList<AccountHierarchical>();
list2.add(obj3);list2.add(obj3);list2.add(obj3);list2.add(obj3);list2.add(obj3);
obj2.setList(list2);
List<AccountHierarchical> list = new ArrayList<AccountHierarchical>();
list.add(obj2);list.add(obj2);list.add(obj2);list.add(obj2);list.add(obj2);
obj.setList(list);
List<AccountHierarchical> result = new ArrayList<AccountHierarchical>();
result.add(obj);result.add(obj);result.add(obj);result.add(obj);
// create Adapter
TreeView adapter = new TreeView(result, this,
getLayoutInflater() , false, 0);
ExpandableListView expandList = (ExpandableListView)findViewById(R.id.expandableList_tree);
expandList.setGroupIndicator(null);
expandList.setAdapter(adapter);
}
CustExpListview:
public class CustExpListview extends ExpandableListView {
int intGroupPosition, intChildPosition, intGroupid;
public CustExpListview(Context context) {
super(context);
}
#Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// widthMeasureSpec = MeasureSpec.makeMeasureSpec(400,
// MeasureSpec.AT_MOST);
heightMeasureSpec = MeasureSpec.makeMeasureSpec(600,
MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
}
AccountHierarchical:
public class AccountHierarchical {
List<AccountHierarchical> list;
private String Title;
private int Id;
public int getId() {
return Id;
}
public void setLevelId(int Id) {
this.Id = Id;
}
public String getTitle() {
return Title;
}
public void setTitle(String title) {
Title = title;
}
public List<AccountHierarchical> getList() {
return list;
}
public void setList(List<AccountHierarchical> list) {
this.list = list;
}
}
TreeView:
public class TreeView extends BaseExpandableListAdapter implements
OnClickListener {
List<AccountHierarchical> list;
LayoutInflater inflatter;
static Context context;
boolean checkGroup;
int position;
static ProgressDialog ProgressDialog;
public TreeView( List<AccountHierarchical> list, Context context,
LayoutInflater inflatter, boolean checkGroup, int position
) {
this.list = list;
TreeView.context = context;
this.inflatter = inflatter;
this.checkGroup = checkGroup; // this is true when you call from inner.
this.position = position;
}
#Override
public Object getChild(int groupPosition, int childPosition) {
return list.get(groupPosition).getList().get(childPosition);
}
#Override
public long getChildId(int groupPosition, int childPosition) {
return list.get(groupPosition).getList().get(childPosition).getId();
}
#Override
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View convertView, ViewGroup parent) {
if (checkGroup)
groupPosition = position;
List<AccountHierarchical> childtemp = list.get(groupPosition)
.getList();
// call this adapter again for creating another level
if (childtemp.get(childPosition).getList().size() > 0) {
CustExpListview SecondLevelexplv = new CustExpListview(context);
TreeView adapter = null;
adapter = new TreeView(childtemp, context,
inflatter, true, childPosition);
SecondLevelexplv.setGroupIndicator(null);
SecondLevelexplv.setAdapter(adapter);
return SecondLevelexplv;
}
// call one layout, this is last child
else {
convertView = inflatter.inflate(R.layout.grouprow, null);
TextView tv = (TextView) convertView.findViewById(R.id.grouprow);
tv.setText(list.get(groupPosition).getList().get(childPosition)
.getTitle());
tv.setPadding(0, 0, 20, 0);
convertView.setTag(list.get(groupPosition).getList()
.get(childPosition) );
convertView.setId(position);
convertView.setOnClickListener(this);
return convertView;
}
}
#Override
public int getChildrenCount(int groupPosition) {
return list.get(groupPosition).getList().size();
}
#Override
public Object getGroup(int groupPosition) {
return list.get(groupPosition);
}
#Override
public int getGroupCount() {
if (checkGroup)
return 1;
return list.size();
}
#Override
public long getGroupId(int groupPosition) {
return list.get(groupPosition).getId();
}
#Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
if (convertView == null)
convertView = inflatter.inflate(R.layout.grouprow, null);
TextView tv = (TextView) convertView.findViewById(R.id.grouprow);
if (checkGroup)
tv.setText(list.get(position).getTitle());
else
tv.setText(list.get(groupPosition).getTitle());
return convertView;
}
#Override
public boolean hasStableIds() {
return false;
}
#Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return false;
}
#Override
public void onClick(View v) {
// your onClick method
}
}
activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/RelativeLayout1"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>
<ExpandableListView
android:id="#+id/expandableList_tree"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true" >
</ExpandableListView>
</RelativeLayout>
grouprow.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/RelativeLayout1"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:id="#+id/grouprow"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_marginBottom="20dp"
android:layout_marginRight="20dp"
android:layout_marginTop="20dp"
android:text=""/>
</RelativeLayout>
snap:
You have to create a layout in the xml file (from where your core textview comes from) and display an image view below
onClick of that imageView you will just have to make your layout Gone and Visible
I have just given you direction rest relies on your skill :)
<RelativeLayout
android:id="#+id/option"
android:layout_width="fill_parent"
android:layout_height="40dp"
android:gravity="center"
android:orientation="horizontal" >
</RelativeLayout>
<RelativeLayout
android:id="#+id/linear"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_margin="10dp"
android:orientation="horizontal" >
<ImageView
android:id="#+id/navigationIcon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:src="#drawable/nn" />
<ImageView
android:id="#+id/callOption"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/phonee" />
<ImageView
android:id="#+id/imageViewfeedback"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:src="#drawable/editer" />
</RelativeLayout>
In Jave File
linear.setVisibility(View.GONE);
option.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
try {
if(count==0)
{
linear.setVisibility(View.VISIBLE);
count=1;
}
else
{
linear.setVisibility(View.GONE);
count=0;
}
}
});
You need to switch to Three-Level of Expandable ListView which contains the subchild inside child.
Also check out ExpandableListView with 3 Childs