Многослойный ExpandableListView
В настоящее время я работаю над проектом, в котором мне нужно что-то вроде следующего:
- MainGroup 1 (Expandable)
- SubGroup 1 (Expandable)
- SubSubGroup 1 (Expandable)
- Child View
- Child View
- ...
- SubSubGroup 2 (Expandable)
- Child View
- Child View
- ...
- SubGroup 2 (Expandable)
- SubSubGroup 3 (Expandable)
- Child View
- ...
- SubSubGroup 4 (Expandable)
- Child View
- ...
- SubGroup 3 (Expandable)
- Child View
- ...
- MainGroup 2 (Expandable)
- ...
В лучшем случае ExpandableListView
внутри ExpandableListView
внутри ExpandableListView
будет ExpandableListView
- так что 3 слоя ExpandableListView
:
-
MainGroup
будет содержать только другой ExpandableListView
.
-
SubGroup
будет содержать другие ExpandableListView
, за исключением последних двух, которые всегда будут ChildViews
. (Я думаю, что эти два могут быть заменены только на SubSubGroup
)
-
SubSubGroup
всегда будет содержать ChildViews
.
Моя проблема в том, что я думаю, что не понимаю основных принципов того, как макеты ExpandableListView
это дети. Я просмотрел такие примеры, как , но не могу окунуться в функциональность.
Я попробовал просто добавить ExpandableListView
в качестве дочернего в другое, но что-то не работает, поскольку только первый элемент внутреннего ExpandableListView
отображается, если вы расширяете одну из внешних групп. Однако я могу установить высоту контейнера внешних групп вручную, чтобы сделать его достаточно большим, чтобы показать все элементы во внутреннем ExpandableListView
. Чтобы быть оптимальным, расчет высоты должен, конечно, выполняться "на лету".
Итак, чтобы получить более серьезные вопросы:
- Может кто-нибудь дать мне объяснение жизненного цикла
ExpandableListView
"(под этим я подразумеваю создание, повторное использование представлений, расширение/сбой слушателей), в том числе:
- Как и когда
ExpandableListView
уведомляется о том, что дочерний элемент расширен или скомпенсирован?
- Как
ExpandableListView
знает, сколько места сделать, чтобы все дети вписывались в контейнер группы?
- Какая польза от использования
ExpandableListView
для создания выше, по сравнению с просто смешиванием моего собственного решения с использованием некоторых LinearLayouts
и некоторых OnClickListeners
?
Edit
Для моего последнего вопроса я мог бы заметить, что может быть от 1 до 20+ MainGroups
.
Ответы
Ответ 1
Прежде всего, позвольте мне рекомендовать вам GrepCode сайт. У этого есть источники классов Android SDK. Спасибо за них, я нашел основные принципы AdapterViews (я дал вам ссылку на ExpandableListView, но лучше, если вы исследуете не только ее, но и его родителей-классов).
Теперь ваши вопросы и мои ответы:
Как и когда ExpandableListView уведомляет о том, что ребенок расширен/разрушилась?
См. метод handleItemClick (просмотр v, int position, long id)
Как ExpandableListView знает, сколько места для всех дети помещаются в контейнер для групп?
Я не очень хорошо изучил этот вопрос, но, насколько я знаю, он сделал метод requestLayout(). Также мы выяснили, что один прокручиваемый вид не может быть встроен в другой прокручиваемый вид. (Это широко известная ошибка: поставить ListView в ScrollView или ListView в ExpandableListView).
Сколько выгоды при использовании ExpandableListView для создания выше, по сравнению с просто смешиванием моего собственного решения, используя некоторые LinearLayouts и некоторые OnClickListeners?
AdapterViews быстрее. Но ваша конструкция слишком сложна даже для ExpandableListView. Вы можете использовать 2 решения.
- Гуру-решение: если вы профессионально разрабатываете собственные
Просмотры/Просмотр групп с нуля (я имею в виду, вы понимаете методы
requestLayout(), dispatchDraw() и т.д.), а затем написать свой собственный
GrandExpandableListAdapter с 3 уровнями.
- Среднее решение: используйте ExpandableListAdapter для первых двух уровней и используйте LinearLayouts для
3-й уровень.
Ответ 2
Возможно, вы захотите проверить этот проект. Я не пробовал, но думаю, стоит попробовать. По умолчанию ExpanadableListView довольно ограничен, изначально разработанный для поддержки только двух уровней. Вы можете взломать его, чтобы заставить его поддерживать больше уровней, но это будет беспорядочно.
Ответ 3
Несмотря на то, что это не полное решение, все еще его 3-слойный расширяемый список. Таким образом, вы оставили вам то, как вы его стиль.
вот класс
package com.custom.nagee;
import android.app.ExpandableListActivity;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.ExpandableListView;
import android.widget.LinearLayout;
public class CustomemExpandible extends ExpandableListActivity{
LayoutInflater inflator;
boolean flag = true;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
inflator = LayoutInflater.from(getApplicationContext());
setListAdapter(new MyAdapter());
}
@Override
public boolean onChildClick(ExpandableListView parent, View v,
int groupPosition, int childPosition, long id) {
if(flag){
v.findViewById(childPosition).setVisibility(View.VISIBLE);
flag = false;
return true;
}
v.findViewById(childPosition).setVisibility(View.GONE);
flag = true;
return true;
}
class MyAdapter extends BaseExpandableListAdapter{
@Override
public Object getChild(int groupPosition, int childPosition) {
return null;
}
@Override
public long getChildId(int groupPosition, int childPosition) {
return 0;
}
@Override
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View convertView, ViewGroup parent) {
LinearLayout linearLayout = (LinearLayout)inflator.inflate(R.layout.group, null);
linearLayout.getChildAt(1).setId(childPosition);
return linearLayout;
}
@Override
public int getChildrenCount(int groupPosition) {
return 2;
}
@Override
public Object getGroup(int groupPosition) {
return null;
}
@Override
public int getGroupCount() {
return 2;
}
@Override
public long getGroupId(int groupPosition) {
return 0;
}
@Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
return ((LinearLayout)inflator.inflate(R.layout.group, null));
}
@Override
public boolean hasStableIds() {
// TODO Auto-generated method stub
return false;
}
@Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
}
}
и здесь идет xml файл
group.xml
<?xml version="1.0" encoding="utf-8"?>
<TextView
android:id="@+id/editText1"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:textColor="@color/back"
android:layout_marginLeft="30dip"
android:text="DONE" >
</TextView>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:layout_marginLeft="30dip"
android:visibility="gone" >
<TextView
android:id="@+id/editText2"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="DONE">
</TextView>
<TextView
android:id="@+id/editText3"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="DONE" />
<TextView
android:id="@+id/editText4"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="DONE" />
</LinearLayout>
и это находится под цветной папкой для изменения цвета текста, ее осталось, вы даже можете изменить фон для улучшения внешнего вида.
back.xml
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_enabled="false" android:color="#808080"/>
<item android:state_window_focused="false" android:color="#808080"/>
<item android:state_pressed="true" android:color="#808080"/>
<item android:state_selected="true" android:color="#000000"/>
<item android:color="#FF0000"/> <!-- not selected -->
</selector>
надеюсь, что это сработает...