前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Android-UI布局---RecyclerView学习(二)利用它做的相册集效果

Android-UI布局---RecyclerView学习(二)利用它做的相册集效果

作者头像
wust小吴
发布2019-07-08 16:25:08
1.3K0
发布2019-07-08 16:25:08
举报
文章被收录于专栏:风吹杨柳风吹杨柳

这个代码在网上有,

  • 横向ListView的功能,参考Android 自定义RecyclerView 实现真正的Gallery效果

首先说布局文件:

RecyclerView视图中的item的布局:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="120dp"
    android:layout_height="120dp"
    android:background="@drawable/item_bg02" >

    <ImageView
        android:id="@+id/id_index_gallery_item_image"
        android:layout_width="80dp"
        android:layout_height="80dp"
        android:layout_alignParentTop="true"
        android:layout_centerHorizontal="true"
        android:layout_margin="5dp"
        android:scaleType="centerCrop" />

    <TextView
        android:id="@+id/id_index_gallery_item_text"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/id_index_gallery_item_image"
        android:layout_centerHorizontal="true"
        android:layout_marginBottom="5dp"
        android:layout_marginTop="5dp"
        android:textColor="#ff0000"
        android:text="some info"
        android:textSize="12dp" />

</RelativeLayout>

就是一个图片一个文字

接下来是主布局:也就是效果图那页:

代码语言:javascript
复制
<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"
    android:orientation="vertical" >

    <FrameLayout
        android:layout_width="fill_parent"
        android:layout_height="0dp"
        android:layout_weight="1" >

        <ImageView
            android:id="@+id/id_content"
            android:layout_width="fill_parent"
            android:layout_height="fill_parent"
            android:layout_gravity="center"
            android:layout_margin="10dp"
            android:scaleType="centerCrop"
            android:src="@drawable/ic_launcher" />
    </FrameLayout>

    <com.example.zhy_horizontalscrollview03.MyRecyclerView
        android:id="@+id/id_recyclerview_horizontal"
        android:layout_width="match_parent"
        android:layout_height="120dp"
        android:layout_gravity="bottom"
        android:background="#FF0000"
        android:scrollbars="none" />

</LinearLayout>

这个布局下面是高度120dp 宽度填充父窗体,然后整个手机屏幕多余的空间都给了上面的imageview 视图

接下来是就是视图的自定义:com.example.zhy_horizontalscrollview03.MyRecyclerView

代码语言:javascript
复制
public class MyRecyclerView extends RecyclerView implements OnScrollListener
{

	/**
	 *记录当前的第一个View
	 */
	private View mCurrentView;
	/**
	 * 滚动监听器
	 */
	private OnItemScrollChangeListener mItemScrollChangeListener;

	/**
	 * 设置监听器
	 * @param mItemScrollChangeListener
	 */
	public void setOnItemScrollChangeListener(OnItemScrollChangeListener mItemScrollChangeListener)
	{
		this.mItemScrollChangeListener = mItemScrollChangeListener;
	}

	/**
	 * 自定义了一个接口方法,用于ScrollListener 每个item 滚动的点击响应事件
	 */
	public interface OnItemScrollChangeListener
	{
		void onChange(View view, int position);
	}

	/**
	 * 继承 RecyclerView 必须要重写的方法
	 * 构造函数,在这里设置 调用 ScrollListener的滚动事件
	 */
	public MyRecyclerView(Context context, AttributeSet attrs)
	{
		super(context, attrs);
		//implements OnScrollListener 启动
		this.setOnScrollListener(this);
	}

	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b)
	{//左上角的left、top以及右下角right、bottom值
		super.onLayout(changed, l, t, r, b);
		//重载该函数,实现的功能就下面实时监听当前的子View  
		// 首先申明 这里是 水平混动
		//需要实现的效果就是每次你滑动停止之后,srcollView 第一个View 展现在上面的大图片中
		mCurrentView = getChildAt(0);

		if (mItemScrollChangeListener != null)
		{
			mItemScrollChangeListener.onChange(mCurrentView,getChildPosition(mCurrentView));
		}
	}


	/**
	 * implements OnScrollListener 必须要重载的方法
	 */
	@Override
	public void onScrollStateChanged(int arg0)
	{
	}

	/**
	 * implements OnScrollListener 必须要重载的方法
	 *滚动时,判断当前第一个View是否发生变化,发生才回调
	 */
	@Override
	public void onScrolled(int arg0, int arg1)
	{
		View newView = getChildAt(0);

		if (mItemScrollChangeListener != null)
		{
			if (newView != null && newView != mCurrentView)
			{
				mCurrentView = newView ;
				mItemScrollChangeListener.onChange(mCurrentView,getChildPosition(mCurrentView));
			}
		}

	}

}

在使用RecyclerView的时候我们需要定义一个适配器:

代码语言:javascript
复制
public class GalleryAdapter extends	RecyclerView.Adapter<GalleryAdapter.ViewHolder> {

	/**
	 *定义回调接口
	 */
	public interface OnItemClickLitener {
		void onItemClick(View view, int position);//点击事件
	}
	/**
	 * 单击 点击监听事件变量
	 */
	private OnItemClickLitener mOnItemClickLitener;

	/**
	 * 设置
	 * @param mOnItemClickLitener
	 */
	public void setOnItemClickLitener(OnItemClickLitener mOnItemClickLitener) {
		this.mOnItemClickLitener = mOnItemClickLitener;
	}

	private LayoutInflater mInflater;//布局填充器
	private List<Integer> mDatas;//适配器绑定的数据

	/**
	 * 构造函数
	 */
	public GalleryAdapter(Context context, List<Integer> datats) {
		mInflater = LayoutInflater.from(context);
		mDatas = datats;
	}

	/**
	 *ViewHolder 跟listView里面一样  属性是item 布局里面各个视图控件
	 */
	public static class ViewHolder extends RecyclerView.ViewHolder {
		public ViewHolder(View arg0) {
			//这里面可以先找到各个视图控件,
			super(arg0);
		}

		ImageView mImg;
		TextView mTxt;
	}

	@Override
	public int getItemCount() {
		return mDatas.size();
	}

	@Override
	public ViewHolder onCreateViewHolder(ViewGroup viewGroup, int i) {
		//找到对应的布局item
		View view = mInflater.inflate(R.layout.activity_index_gallery_item,viewGroup, false);
		ViewHolder viewHolder = new ViewHolder(view);
		viewHolder.mImg = (ImageView) view.findViewById(R.id.id_index_gallery_item_image);
		return viewHolder;
	}

	/**
	 * 该函数用来进行数据填充的,同时如果有监听事件,也在这里面
	 */
	@Override
	public void onBindViewHolder(final ViewHolder viewHolder, final int i) {
		// 布局填充数据
		viewHolder.mImg.setImageResource(mDatas.get(i));
		// 如果设置了回调,则设置点击事件
		if (mOnItemClickLitener != null) {
			viewHolder.itemView.setOnClickListener(new OnClickListener() {
				@Override
				public void onClick(View v) {
					//设置点击事件 具体的调用执行,由当前的adapter实例进行操作
					mOnItemClickLitener.onItemClick(viewHolder.itemView, i);
				}
			});
		}

	}

}

可以参考下 Listview的适配器时候的写法,基本一致,只是在我们自己定义的适配器中加入了 自定义的点击事件,回调接口

接下来就是对应的activity类了:

代码语言:javascript
复制
public class MainActivity extends Activity
{

	private MyRecyclerView mRecyclerView;
	private GalleryAdapter mAdapter;
	private List<Integer> mDatas;
	private ImageView mImg ; 
	
	
	@Override
	protected void onCreate(Bundle savedInstanceState)
	{
		super.onCreate(savedInstanceState);
		requestWindowFeature(Window.FEATURE_NO_TITLE);
		setContentView(R.layout.activity_main);
		
		mImg = (ImageView) findViewById(R.id.id_content);

		mDatas = new ArrayList<Integer>(Arrays.asList(R.drawable.a,
				R.drawable.b, R.drawable.c, R.drawable.d, R.drawable.e,
				R.drawable.f, R.drawable.g, R.drawable.h, R.drawable.l));

		mRecyclerView = (MyRecyclerView) findViewById(R.id.id_recyclerview_horizontal);
		LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this);
		linearLayoutManager.setOrientation(LinearLayoutManager.HORIZONTAL);

		mRecyclerView.setLayoutManager(linearLayoutManager);
		mAdapter = new GalleryAdapter(this, mDatas);
		mRecyclerView.setAdapter(mAdapter);

		//滚动布局的滑动事件监听 每次滑完展现第一个
		mRecyclerView.setOnItemScrollChangeListener(new OnItemScrollChangeListener()
		{
			@Override
			public void onChange(View view, int position)
			{
				mImg.setImageResource(mDatas.get(position));
			};
		});
		//对每一个item点击事件的处理,这里就不是展现第一个,而是点击谁就展现谁了
		mAdapter.setOnItemClickLitener(new OnItemClickLitener()
		{
			@Override
			public void onItemClick(View view, int position)
			{
				mImg.setImageResource(mDatas.get(position));
			}
		});

	}

}

整个代码就结束了,很清晰也很容易理解  。需要学习的第二个知识点就是:在对应的activity中关于RecyclerView 的使用

RecyclerView的使用代码:

代码语言:javascript
复制
		//找到对应的视图控件
		mRecyclerView = (MyRecyclerView) findViewById(R.id.id_recyclerview_horizontal);
		////设置布局管理器
		LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this);
		linearLayoutManager.setOrientation(LinearLayoutManager.HORIZONTAL);//设置方向水平
		mRecyclerView.setLayoutManager(linearLayoutManager);
		
		mAdapter = new GalleryAdapter(this, mDatas);
		//设置适配器
		mRecyclerView.setAdapter(mAdapter);

只需要这三个关键的地方就可以了  下面是基本使用方法:

基本使用

鉴于我们对于ListView的使用特别的熟悉,对比下RecyclerView的使用代码:后面两点就看你的具体需求了

 mRecyclerView = findView(R.id.id_recyclerview); //设置布局管理器 mRecyclerView.setLayoutManager(layout); //设置adapter mRecyclerView.setAdapter(adapter) //设置Item增加、移除动画 mRecyclerView.setItemAnimator(new DefaultItemAnimator()); //添加分割线 mRecyclerView.addItemDecoration(new DividerItemDecoration(getActivity(), DividerItemDecoration.HORIZONTAL_LIST)); 

相比较于ListView的代码,ListView可能只需要去设置一个adapter就能正常使用了。而RecyclerView基本需要上面一系列的步骤,那么为什么会添加这么多的步骤呢?

那么就必须解释下RecyclerView的这个名字了,从它类名上看,RecyclerView代表的意义是,我只管Recycler View,也就是说RecyclerView只管回收与复用View,其他的你可以自己去设置。可以看出其高度的解耦,给予你充分的定制自由(所以你才可以轻松的通过这个控件实现ListView,GirdView,瀑布流等效果)。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2015年11月16日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 基本使用
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档