在listview中的android:listview

我试图在listviewitem里放置一个listview。 内部列表视图不应该滚动,但需要显示所有行的所有大小。 有没有更好的方法来呢? 表格,…? 我现在面临的问题是,内部列表视图不占用它需要的空间,所以它在第一个listitem的结尾处被截断。 如果我尝试滚动,只是外部列表视图正在滚动,这正是我想要的。

how_it_should_look_like 谢谢,我的最终解决scheme是

LinearLayout layout = (LinearLayout) row.findViewById(R.id.LLBroadcasts); layout.removeAllViews(); for (Item b : bs.getItems()) { View child = _inflater.inflate(R.layout.item_row, null); TextView tvTitle = (TextView) child.findViewById(R.id.TVItemTitle); tvTitle.setText(b.getTitle()); TextView tvDesc = (TextView) child.findViewById(R.id.TVItemDescription); tvDesc.setText(b.getDescription()); layout.addView(child); } 

Solutions Collecting From Web of "在listview中的android:listview"

从Android文档 – 列表视图ListView是一个视图组,显示可滚动项目列表

你不是真的想滚动内部列表视图,你想滚动外部列表视图。 然而,我认为,内部的列表视图可能会因为它包含的元素的数量而有所不同。

而不是内部列表视图,你可以使用一个

  • 线性布局 ,请参阅本教程或查看将内容dynamic添加到线性布局?
  • 表格布局 ,请参阅本教程

对于线性布局(一些示例代码):

 // access your linear layout LinearLayout layout = (LinearLayout)findViewById(R.id.layout); // load the xml structure of your row View child = getLayoutInflater().inflate(R.layout.row); // now fill the row as you would do with listview //eg (TextView) child.findViewById(... ... // and than add it layout.addView(child); 

您应该将线性布局保存在视图保持器中(请参阅查看保持器模式 )。 我认为removeAllViews()只有在当前行的内部行less于重用行时才是必要的,所以我也将行数保存在视图持有者中。

如果内部行的最大数量不高,你也可以考虑将它们caching在视图持有者中,以避免膨胀和findByViewId(可以说在ArrayList中)。

我在我的应用程序中有同样的问题,但我需要使用ListView,因为它是一个共享的项目,我不想复制相同的组件。 所以..我只是固定的内部ListView的大小编程方式显示所有行和..瞧! 问题解决了:

 ViewGroup.LayoutParams layoutParams = innerListView.getLayoutParams(); layoutParams.height = (int) context.getResources().getDimension(R.dimen.rowheight) * innerListView.getCount(); innerListView.setLayoutParams(layoutParams); CustomAdapter adapter = new CustomAdapter(context, blabla..); innerListView.setAdapter(adapter); rowListView.invalidate(); 

也许有人会发现我的解决scheme有用。 它基于@ChrLipp的答案,并使用LinearLayout。

 public class NotScrollableListView extends LinearLayout { private ListAdapter adapter; private DataChangeObserver dataChangeObserver; private Drawable divider; private int dividerHeight; private List<View> reusableViews = new ArrayList<>(); public NotScrollableListView(Context context) { super(context); } public NotScrollableListView(Context context, AttributeSet attrs) { super(context, attrs); setAttributes(attrs); } public NotScrollableListView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); setAttributes(attrs); } public ListAdapter getAdapter() { return adapter; } public void setAdapter(ListAdapter adapter) { if (this.adapter != null && dataChangeObserver != null) { this.adapter.unregisterDataSetObserver(dataChangeObserver); } this.adapter = adapter; } @Override protected void onAttachedToWindow() { super.onAttachedToWindow(); if (adapter != null) { dataChangeObserver = new DataChangeObserver(); adapter.registerDataSetObserver(dataChangeObserver); fillContents(); } } @Override protected void onDetachedFromWindow() { super.onDetachedFromWindow(); if (adapter != null) { adapter.unregisterDataSetObserver(dataChangeObserver); dataChangeObserver = null; } } private void fillContents() { // clearing contents this.removeAllViews(); final int count = adapter.getCount(); // item count final int reusableCount = reusableViews.size(); // count of cached reusable views // calculating of divider properties ViewGroup.LayoutParams dividerLayoutParams = null; if (divider != null && dividerHeight > 0) { dividerLayoutParams = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, dividerHeight); } // adding items for (int i = 0; i < count; i++) { // adding item View converView = null; if (i < reusableCount) { // we have cached view converView = reusableViews.get(i); } View view = adapter.getView(i, converView, this); if (i >= reusableCount) { // caching view reusableViews.add(view); } addView(view); // adding divider if (divider != null && dividerHeight > 0) { if (i < count - 1) { ImageView dividerView = new ImageView(getContext()); dividerView.setImageDrawable(divider); dividerView.setLayoutParams(dividerLayoutParams); addView(dividerView); } } } } private void setAttributes(AttributeSet attributes) { int[] dividerAttrs = new int[]{android.R.attr.divider, android.R.attr.dividerHeight}; TypedArray a = getContext().obtainStyledAttributes(attributes, dividerAttrs); try { divider = a.getDrawable(0); dividerHeight = a.getDimensionPixelSize(1, 0); } finally { a.recycle(); } setOrientation(VERTICAL); } private class DataChangeObserver extends DataSetObserver { @Override public void onChanged() { super.onChanged(); fillContents(); } @Override public void onInvalidated() { super.onInvalidated(); fillContents(); } } } <com.sample.ui.view.NotScrollableListView android:id="@+id/internalList" android:layout_width="match_parent" android:layout_height="wrap_content" android:divider="@color/list_divider_color" android:dividerHeight="@dimen/list_divider_width" /> 

@尝试这个嵌套类

这适用于listview内的滚动listView或在同一activity 2 listview

  <com.example.taskgrptaskslistview.NestedListView android:id="@+id/listviewTasks" android:layout_width="0dip" android:layout_height="wrap_content" android:layout_marginBottom="2dp" android:layout_weight="1" android:cacheColorHint="#00000000" > </com.example.taskgrptaskslistview.NestedListView> </LinearLayout> 

NestedListView:

 import android.content.Context; import android.util.AttributeSet; import android.view.MotionEvent; import android.view.View; import android.view.View.OnTouchListener; import android.view.ViewGroup; import android.widget.AbsListView; import android.widget.AbsListView.OnScrollListener; import android.widget.ListAdapter; import android.widget.ListView; public class NestedListView extends ListView implements OnTouchListener, OnScrollListener { private int listViewTouchAction; private static final int MAXIMUM_LIST_ITEMS_VIEWABLE = 99; public NestedListView(Context context, AttributeSet attrs) { super(context, attrs); listViewTouchAction = -1; setOnScrollListener(this); setOnTouchListener(this); } @Override public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) { if (getAdapter() != null && getAdapter().getCount() > MAXIMUM_LIST_ITEMS_VIEWABLE) { if (listViewTouchAction == MotionEvent.ACTION_MOVE) { scrollBy(0, -1); } } } @Override public void onScrollStateChanged(AbsListView view, int scrollState) { } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); int newHeight = 0; final int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); if (heightMode != MeasureSpec.EXACTLY) { ListAdapter listAdapter = getAdapter(); if (listAdapter != null && !listAdapter.isEmpty()) { int listPosition = 0; for (listPosition = 0; listPosition < listAdapter.getCount() && listPosition < MAXIMUM_LIST_ITEMS_VIEWABLE; listPosition++) { View listItem = listAdapter.getView(listPosition, null, this); //now it will not throw a NPE if listItem is a ViewGroup instance if (listItem instanceof ViewGroup) { listItem.setLayoutParams(new LayoutParams( LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT)); } listItem.measure(widthMeasureSpec, heightMeasureSpec); newHeight += listItem.getMeasuredHeight(); } newHeight += getDividerHeight() * listPosition; } if ((heightMode == MeasureSpec.AT_MOST) && (newHeight > heightSize)) { if (newHeight > heightSize) { newHeight = heightSize; } } } else { newHeight = getMeasuredHeight(); } setMeasuredDimension(getMeasuredWidth(), newHeight); } @Override public boolean onTouch(View v, MotionEvent event) { if (getAdapter() != null && getAdapter().getCount() > MAXIMUM_LIST_ITEMS_VIEWABLE) { if (listViewTouchAction == MotionEvent.ACTION_MOVE) { scrollBy(0, 1); } } return false; } } 

我试着做这个确切的结构( ListView里面的一个ListView ),并有相同的问题,它只显示内部ListView的第一个项目。 我通过将内部列表的layout_heightmatch_parent更改为set dp来修复它。

它看起来像我想要的那样工作。