如何制作水平列表视图



我想做一个水平列表视图,但我不想使用第三方的库。所以,我尝试使用PagerAdapter,但我可以做到。我不知道如何解决它。这是我用来加载照片的代码:

public class GalleryActivity extends AppCompatActivity {
public static final String TAG = "GalleryActivity";
public static final String EXTRA_NAME = "images";
ArrayList<Actor> actors = new ArrayList<>();
private GalleryPagerAdapter _adapter;
@InjectView(R.id.pager) ViewPager _pager;
@InjectView(R.id.thumbnails) LinearLayout _thumbnails;
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_gallery);
    ButterKnife.inject(this);
    importActor();
    _adapter = new GalleryPagerAdapter(this);
    _pager.setAdapter(_adapter);
    _pager.setOffscreenPageLimit(6);
}
public void importActor(){
    Bitmap bitmap = BitmapFactory.decodeResource(GalleryActivity.this.getResources(), R.drawable.nhaphuong);
    Bitmap bitmap1 = BitmapFactory.decodeResource(GalleryActivity.this.getResources(),R.drawable.subo);
    Bitmap bitmap2 = BitmapFactory.decodeResource(GalleryActivity.this.getResources(),R.drawable.truonggiang);
    Actor actor = new Actor(5,"Nhã Phương",bitmap);
    Actor actor1 = new Actor(15,"Trường Giang",bitmap2);
    Actor actor2 = new Actor(999,"Subo",bitmap1);
    actors.add(actor);
    actors.add(actor1);
    actors.add(actor2);
}

class GalleryPagerAdapter extends PagerAdapter {
    Context _context;
    LayoutInflater _inflater;
    public GalleryPagerAdapter(Context context) {
        _context = context;
        _inflater = (LayoutInflater) _context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    }
    @Override
    public int getCount() {
        return actors.size();
    }
    @Override
    public boolean isViewFromObject(View view, Object object) {
        return view == ((RelativeLayout) object);
    }
    @Override
    public Object instantiateItem(ViewGroup container, final int position) {
        View view = _inflater.inflate(R.layout.one_actor, container, false);
        container.addView(view);
        // Get the border size to show around each image
        int borderSize = _thumbnails.getPaddingTop();
        // Get the size of the actual thumbnail image
        int thumbnailSize = ((FrameLayout.LayoutParams)
                _pager.getLayoutParams()).bottomMargin - (borderSize*2);
        // Set the thumbnail layout parameters. Adjust as required
        LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(thumbnailSize, thumbnailSize);
        params.setMargins(0, 0, borderSize, 0);
        OneActor oneActor = new OneActor();
        oneActor.avatar = (ImageView) view.findViewById(R.id.imgActor);
        oneActor.name = (TextView) view.findViewById(R.id.tvActorName);
        oneActor.cmtCount = (TextView) view.findViewById(R.id.tvCmtCount);
        view.setTag(oneActor);
        oneActor.avatar.setImageBitmap(actors.get(position).getAvatar());
        oneActor.cmtCount.setText(actors.get(position).getCmtcout() + "");
        oneActor.name.setText(actors.get(position).getName());
        return view;
    }
    @Override
    public void destroyItem(ViewGroup container, int position, Object object) {
        container.removeView((LinearLayout) object);
    }
    class OneActor{
        ImageView avatar;
        TextView name, cmtCount;
    }
}

这是我的 xml 文件:

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true">
<HorizontalScrollView
    android:layout_width="match_parent"
    android:layout_height="72dp"
    android:layout_gravity="center">
    <LinearLayout
        android:id="@+id/thumbnails"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:gravity="center_vertical"
        android:orientation="horizontal"
        android:paddingTop="2dp"/>
</HorizontalScrollView>

告诉我如何解决它或给我一个家教!

如果您

不必使用它,则必须使用RecyclerView,请使用HorizontalListView。 请参阅下面的水平列表视图代码

水平列表视图.java

 import java.util.LinkedList;
 import java.util.Queue;
 import android.content.Context;
 import android.database.DataSetObserver;
 import android.graphics.Rect;
 import android.util.AttributeSet;
 import android.util.Log;
 import android.view.GestureDetector;
 import android.view.GestureDetector.OnGestureListener;
 import android.view.MotionEvent;
 import android.view.View;
 import android.widget.AdapterView;
 import android.widget.ListAdapter;
 import android.widget.Scroller;
 public class HorizontalListView extends AdapterView<ListAdapter> {
public boolean mAlwaysOverrideTouch = true;
protected ListAdapter mAdapter;
private int mLeftViewIndex = -1;
private int mRightViewIndex = 0;
protected int mCurrentX;
protected int mNextX;
private int mMaxX = Integer.MAX_VALUE;
private int mDisplayOffset = 0;
protected Scroller mScroller;
private GestureDetector mGesture;
private Queue<View> mRemovedViewQueue = new LinkedList<View>();
private OnItemSelectedListener mOnItemSelected;
private OnItemClickListener mOnItemClicked;
public HorizontalListView(Context context, AttributeSet attrs) {
    super(context, attrs);
    initView();
}
private void initView() {
    mLeftViewIndex = -1;
    mRightViewIndex = 0;
    mDisplayOffset = 0;
    mCurrentX = 0;
    mNextX = 0;
    mMaxX = Integer.MAX_VALUE;
    mScroller = new Scroller(getContext());
    mGesture = new GestureDetector(getContext(), mOnGesture);
}
@Override
public void setOnItemSelectedListener(AdapterView.OnItemSelectedListener listener) {
    mOnItemSelected = listener;
    Log.v("log_tag", "Message is set On Clicked");
}
@Override
public void setOnItemClickListener(AdapterView.OnItemClickListener listener) {
    mOnItemClicked = listener;
    Log.v("log_tag", "Set on Item Clicked");
}
private DataSetObserver mDataObserver=new DataSetObserver(){
@Override public void onChanged(){
// TODO Auto-generated method stub
super.onChanged();}
@Override public void onInvalidated(){
// TODO Auto-generated method stub
super.onInvalidated();}
};
@Override
public ListAdapter getAdapter() {
    return mAdapter;
}
@Override
public View getSelectedView() {
    // TODO: implement
    return null;
}
@Override
public void setAdapter(ListAdapter adapter) {
    if (mAdapter != null) {
        mAdapter.unregisterDataSetObserver(mDataObserver);
    }
    mAdapter = adapter;
    mAdapter.registerDataSetObserver(mDataObserver);
    initView();
    removeAllViewsInLayout();
    requestLayout();
}
@Override
public void setSelection(int position) {
    // TODO: implement
}
private void addAndMeasureChild(final View child, int viewPos) {
    LayoutParams params = child.getLayoutParams();
    if (params == null) {
        params = new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT);
    }
    addViewInLayout(child, viewPos, params, true);
    child.measure(MeasureSpec.makeMeasureSpec(getWidth(), MeasureSpec.AT_MOST),
            MeasureSpec.makeMeasureSpec(getHeight(), MeasureSpec.AT_MOST));
}
@Override
protected synchronized void onLayout(boolean changed, int left, int top, int right, int bottom) {
    super.onLayout(changed, left, top, right, bottom);
    if (mAdapter == null) {
        return;
    }
    if (mScroller.computeScrollOffset()) {
        int scrollx = mScroller.getCurrX();
        mNextX = scrollx;
    }
    if (mNextX < 0) {
        mNextX = 0;
        mScroller.forceFinished(true);
    }
    if (mNextX > mMaxX) {
        mNextX = mMaxX;
        mScroller.forceFinished(true);
    }
    int dx = mCurrentX - mNextX;
    removeNonVisibleItems(dx);
    fillList(dx);
    positionItems(dx);
    mCurrentX = mNextX;
    if (!mScroller.isFinished()) {
        post(new Runnable() {
            @Override
            public void run() {
                requestLayout();
            }
        });
    }
}
private void fillList(final int dx) {
    int edge = 0;
    View child = getChildAt(getChildCount() - 1);
    if (child != null) {
        edge = child.getRight();
    }
    fillListRight(edge, dx);
    edge = 0;
    child = getChildAt(0);
    if (child != null) {
        edge = child.getLeft();
    }
    fillListLeft(edge, dx);
}
private void fillListRight(int rightEdge, final int dx) {
    while (rightEdge + dx < getWidth() && mRightViewIndex < mAdapter.getCount()) {
        View child = mAdapter.getView(mRightViewIndex, mRemovedViewQueue.poll(), this);
        addAndMeasureChild(child, -1);
        rightEdge += child.getMeasuredWidth();
        if (mRightViewIndex == mAdapter.getCount() - 1) {
            mMaxX = mCurrentX + rightEdge - getWidth();
        }
        mRightViewIndex++;
    }
}
private void fillListLeft(int leftEdge, final int dx) {
    while (leftEdge + dx > 0 && mLeftViewIndex >= 0) {
        View child = mAdapter.getView(mLeftViewIndex, mRemovedViewQueue.poll(), this);
        addAndMeasureChild(child, 0);
        leftEdge -= child.getMeasuredWidth();
        mLeftViewIndex--;
        mDisplayOffset -= child.getMeasuredWidth();
    }
}
private void removeNonVisibleItems(final int dx) {
    View child = getChildAt(0);
    while (child != null && child.getRight() + dx <= 0) {
        mDisplayOffset += child.getMeasuredWidth();
        mRemovedViewQueue.offer(child);
        removeViewInLayout(child);
        mLeftViewIndex++;
        child = getChildAt(0);
    }
    child = getChildAt(getChildCount() - 1);
    while (child != null && child.getLeft() + dx >= getWidth()) {
        mRemovedViewQueue.offer(child);
        removeViewInLayout(child);
        mRightViewIndex--;
        child = getChildAt(getChildCount() - 1);
    }
}
private void positionItems(final int dx) {
    if (getChildCount() > 0) {
        mDisplayOffset += dx;
        int left = mDisplayOffset;
        for (int i = 0; i < getChildCount(); i++) {
            View child = getChildAt(i);
            int childWidth = child.getMeasuredWidth();
            child.layout(left, 0, left + childWidth, child.getMeasuredHeight());
            left += childWidth;
        }
    }
}
public synchronized void scrollTo(int x) {
    mScroller.startScroll(mNextX, 0, x - mNextX, 0);
    requestLayout();
}
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
    boolean handled = mGesture.onTouchEvent(ev);
    return super.dispatchTouchEvent(ev);
}
protected boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
    synchronized (HorizontalListView.this) {
        mScroller.fling(mNextX, 0, (int) -velocityX, 0, 0, mMaxX, 0, 0);
    }
    requestLayout();
    return true;
}
protected boolean onDown(MotionEvent e) {
    mScroller.forceFinished(true);
    return true;
}
private OnGestureListener mOnGesture=new GestureDetector.SimpleOnGestureListener(){
@Override public boolean onDown(MotionEvent e){return HorizontalListView.this.onDown(e);}
@Override public boolean onFling(MotionEvent e1,MotionEvent e2,float velocityX,float velocityY){return HorizontalListView.this.onFling(e1,e2,velocityX,velocityY);}
@Override public boolean onScroll(MotionEvent e1,MotionEvent e2,float distanceX,float distanceY){
synchronized(HorizontalListView.this){mNextX+=(int)distanceX;}requestLayout();
return true;}
@Override public boolean onSingleTapConfirmed(MotionEvent e){Rect viewRect=new Rect();for(int i=0;i<getChildCount();i++){View child=getChildAt(i);int left=child.getLeft();int right=child.getRight();int top=child.getTop();int bottom=child.getBottom();viewRect.set(left,top,right,bottom);if(viewRect.contains((int)e.getX(),(int)e.getY())){if(mOnItemClicked!=null){mOnItemClicked.onItemClick(HorizontalListView.this,child,mLeftViewIndex+1+i,0);}if(mOnItemSelected!=null){mOnItemSelected.onItemSelected(HorizontalListView.this,child,mLeftViewIndex+1+i,0);}break;}
}return true;}
};
}

在 xml 中用作列表视图,如下所示

<youpackage.HorizantalListView
 android:layout_width="match_parent"
android:layout_height="match_parent"/>

最好使用RecyclerView。 它也可以作为HorizontalListView工作,并且不需要任何第三方库。为此,您需要做这样的事情

LinearLayoutManager layoutManager
= new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);
RecyclerView myList = (RecyclerView) findViewById(R.id.my_recycler_view);
myList.setLayoutManager(layoutManager);

最新更新