ViewPager实现炫酷的滑动缩放广告页
来源:互联网 发布:工作督促软件 编辑:程序博客网 时间:2024/04/24 02:33
ViewPager是Android开发中一个重要的控件,其轻量级的多页展示功能简化了开发过程,使我们能够快速构建一个App的引导页。但是,如果只是用来做引导页,那就太浪费了,其实我们可以将它打造的更炫酷一点。
效果图
(制作的gif图不知道为什么不能显示,所以只能用一张静态图片代替了)
需求分析
- 页面滑动过程中,中间页向两边滑动的过程中进行缩小,两边页面向中间滑动的过程中进行放大,
- 页面滑动过程中底部显示选中页标志;
- 页面范围内都可以滑动;
实现
通过对上面的需求进行分析,我们先确定要实现的位置,需求一要求在缩放过程中进行缩放,那只能在ViewPager的滑动监听过程中实现了。
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } @Override public void onPageSelected(int position) { } @Override public void onPageScrollStateChanged(int i) { }});
ViewPager的滑动监听中有三个方法, onPageScrolled在滑动过程中被调用,onPageSelected当一个新的页面被选中时被调用(注意:动画此时不一定结束),onPageScrollStateChanged在滑动状态改变时被调用(i==1表示开始滑动,i==2表示当前页被选中,i==0表示滑动和动画都已结束,注意:i==2的状态后会迅速调用i==0的状态,所以滑动过程中i的变化过程为:i=1 --> i=2 –> i=0)。了解了滑动监听的过程,我们很容易看出,滑动过程的动画只能在onPageScrolled进行实现了。
onPageScrolled函数原型中的参数说明:
- position:当前选中页的index, 当posistionOffset为非零时position++;
- positionOffset:当前选中页的位置偏移量,取值范围[0, 1)。
- positionOffsetPixels:当前选中页的偏移距离, 取值范围[0, viewpager的宽度+ViewPager中页面的间距)。
滑动过程中参数的变化:
- 左滑过程中positionOffset和positionOffsetPixels逐渐变大,变到 最大后都又变成0,此时position++;
- 右滑过程中positionOffset和positionOffsetPixels从最大值逐渐变为0,此过程中position始终是当前选中页的前一页的index;
了解了上面函数的参数含义后开始实现我们的需求一:
@Overridepublic void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { // 虽然一屏只显示三页,但是当我们滑动的过程中需要设置四页的缩放效果,因为左边的页面被滑出去之后,页面上将显示的是后面的三页 View leftImage = activityMap.get(position - 1); View currentImage = activityMap.get(position); View rightImage = activityMap.get(position + 1); View rightImage2 = activityMap.get(position + 2); if (positionOffset > 0) { float scaleAlpha1 = 1 - positionOffset / 4.0f; float scaleAlpha2 = 0.75f + positionOffset / 4.0f; // 设置页面滑动过程中的缩放效果 currentImage.setAlpha(scaleAlpha1); currentImage.setScaleX(scaleAlpha1); currentImage.setScaleY(scaleAlpha1); if (leftImage != null) { leftImage.setAlpha(scaleAlpha2); leftImage.setScaleX(scaleAlpha2); leftImage.setScaleY(scaleAlpha2); } if (rightImage != null) { rightImage.setAlpha(scaleAlpha2); rightImage.setScaleX(scaleAlpha2); rightImage.setScaleY(scaleAlpha2); } if (rightImage2 != null) { rightImage2.setAlpha(scaleAlpha1); rightImage2.setScaleX(scaleAlpha1); rightImage2.setScaleY(scaleAlpha1); } } else { // 设置页面初次启动时的缩放效果 if (leftImage != null && currentImage.getAlpha() == 1) { leftImage.setAlpha(0.75f); leftImage.setScaleX(0.75f); leftImage.setScaleY(0.75f); } if (rightImage != null && currentImage.getAlpha() == 1) { rightImage.setAlpha(0.75f); rightImage.setScaleX(0.75f); rightImage.setScaleY(0.75f); } }}
需求二其实简单,只需要在onPageSelected重新设置选中状态即可:
@Overridepublic void onPageSelected(int position) { selectCurrentDot(position);}/** * 设置当前选中页的选中状态(只有一页时不显示选中状态) * @param position 当前选中页的index */private void selectCurrentDot(int position) { if (imageList.size() > 1) { for (int i = 0; i < indicatorIcon.length; i++) { if (i == position) { indicatorIcon[i].setBackgroundResource(R.drawable.indicator_selected); } else { indicatorIcon[i].setBackgroundResource(R.drawable.indicatorunselect); } } }}
到这一步,我们的滑动缩放广告栏看起来已经完成了,但是滑动的过程中发现只有ViewPager页面范围内可以滑动,两边的位置都不能滑动,看了下ViewPager的源码, 发现它重写了ViewGroup的dispatchTouchEvent函数,并且也是是公开的,那我们在ViewPager的父View的onTouch事件中返回ViewPager的dispatchTouchEvent应该就可以像ViewPager一样滑动了。
containLayout.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { return viewPager.dispatchTouchEvent(event); }});
再次运行发现可以在ViewPager的父View范围内滑动了。至此,整个滑动过程就完成了。下面贴一下ViewPagerAdapter的代码:
private class MyPagerAdapter extends PagerAdapter { @Override public int getCount() { return imageList.size(); } @Override public boolean isViewFromObject(View view, Object obj) { return view == obj; } @Override public Object instantiateItem(ViewGroup container, final int position) { RoundImageView imageView = new RoundImageView(context); ViewGroup.LayoutParams params = container.getLayoutParams(); params.width = getScreenWidth() - dpToPx(140); params.height = (int)(params.width * H_W); imageView.setLayoutParams(params); imageView.setScaleType(ImageView.ScaleType.CENTER_CROP); imageView.setImageDrawable(imageList.get(position)); imageView.setTag(position); container.addView(imageView); activityMap.put(position, imageView); imageView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Toast.makeText(context, "触发了点击事件", Toast.LENGTH_SHORT).show(); } }); return imageView; } @Override public void destroyItem(ViewGroup container, int position, Object object) { }}
源码
源码下载:可滑动缩放的ViewPager
遇到的问题
- ViewPager一屏不能显示三页;
- 只有ViewPager的位置可以滑动,两边不能滑动;
- ViewPager滑动过程中出现卡顿,多次滑动后App卡死;
解决方案
- 在ViewPager,ViewPager的父布局和ViewPager的根布局中添加属性android:clipChildren=”false”(注意:ViewPager不加此属性时有些手机会显示异常);
- 重写ViewPager父布局的onTouch事件;
- 先读取所有的图片内容,得到drawable或bitmap, 然后设置给ViewPager中的图片,同时设置ViewPager的预加载时需要预加载所有的Item,只有这样ViewPager滑动过程中才不会出现卡顿(具体原因有待进一步深究)。通过这种方案,加载了30页1080*540大小的图片没有出现卡顿情况。
如果有什么错误之处,欢迎指正!顺便问一下,你们都用什么软件来做gif截屏,尝试了一下感觉很麻烦,而且还不理想。
- ViewPager实现炫酷的滑动缩放广告页
- viewpager+fragment嵌套viewpager图片广告导致广告图片不能滑动的问题用LinearLayout实现
- Android利用ViewPager实现滑动广告板
- Android利用ViewPager实现滑动广告板
- 使用ViewPager实现广告滑动效果
- Android利用ViewPager实现滑动广告板
- ViewPager实现广告条自动滑动
- 基于viewpager的广告滑动效果
- Android 实现可以自由移动缩放的图片控件并实现ViewPager滑动
- andorid---通过Viewpager实现图片滑动以及缩放
- ViewPager实现滑动引导页
- ViewPager 可左右滑动和缩放的图片浏览
- viewpager 滑动,缩放,子控件偏移引导页
- 慕课网实现自定义多指触控双击缩放的IamgeView以及解决和ViewPager的滑动冲突代码摘要
- android FragmentTabhost+ViewPager实现可滑动的标签页
- viewpager+listview+fragment实现简单的滑动标签页
- TabLayout+ViewPager 实现页签滑动的效果
- ViewPager实现循环广告
- 现实的巧合?精心的设计?砍价模型?以退为进?
- 使用工具
- android坐标
- Android Launcher 自定义View 炫酷换壁纸效果,水瓶加水进度显示效果
- mysql输入输出参数存储过程简单使用
- ViewPager实现炫酷的滑动缩放广告页
- 计算机期刊
- log4j按天生成日志文件
- MYSQL中INET_ATON(expr)函数的调查
- 欧拉函数模版
- VS2013与MySql建立连接;您的项目引用了最新实体框架;
- 安卓汉字转拼音字符串,进行模糊搜索时使用
- 国内计算机期刊
- letcode 118