您的位置:首页 > 其它

ViewPager加载页面,底部圆点指示器,圆点拖动效果,支持手势拖动

2016-11-15 17:17 459 查看

效果概述:

随着viewpager中页面的滑动,底部的圆点也有拖动效果,支持手势拖动

效果图如下:



实现原理:

ViewPager 无限轮播,设置了Integer.MAX_VALUE ; 其实也可以设置为前一张后一张,不过麻烦点儿

根据ViewPager中图片个数不同,底部显示不同个数的圆点

动态加载圆点的同时,记录下圆点的位置,放于集合中

ViewPager 的setOnPageChangeListener监听,用于设置ViewPager的页面切换时,圆点的动画效果

支持手势拖动

遇到的问题

装载圆点的layout在onCreate()中未立即装载,需要动态获取圆点位置的方法失败

解决办法: 网上有说其他的方法;我是直接开了子线程,睡了500ms

手势拖动,使用handler,但会触发setOnPageChangeListener监听,导致立即切换到下一个图片,特别不友好

解决办法:onPageScrollStateChanged方法中判断,状态为1(开始滑动)的时候,hanlder移除掉所有的消息,然后5s后重发消息

3 . 手势拖动,右滑的时候,圆点的移动效果和左滑不同

解决办法:根据当前position判断左滑/右滑(我使用的是Integer.MAX_VALUE),设置不同的动画

核心代码

/*

暴漏出去的item点击事件接口:OnPagerItemClickListnener

需要传递的参数:

item 个数

List

Circle 形状,颜色【包括normal和select】

轮播时间间隔

viewpager加载前图片,加载失败图片


*/

public class MainActivity extends AppCompatActivity {

private ViewPager pager;
private LinearLayout layout;

private List<String> urlList=new ArrayList<>();
private List<Integer> posList=new ArrayList<>();
private boolean once=true;
private TextView circle;
private PagerAdapter adapter;
private RelativeLayout main_layout;
private int preItemPos=0;
private boolean right;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

pager = (ViewPager) findViewById(R.id.viewPager);
layout = (LinearLayout) findViewById(R.id.circleLayout);
main_layout = (RelativeLayout) findViewById(R.id.activity_main);

//传入参数为5;传入的url集合为urlList;间隔时间为500ms;传入默认颜色为白,移动颜色为红
final LinearLayout.LayoutParams params=new LinearLayout.LayoutParams(5,5,1);
params.setMargins(5,0,5,0);
for (int i = 0; i < 5; i++) {
TextView circle=(TextView) LayoutInflater.from(this).inflate(R.layout.circle, null);
circle.setLayoutParams(params);
layout.addView(circle);
}

circle = (TextView) LayoutInflater.from(this).inflate(R.layout.circle, null);
RelativeLayout.LayoutParams params1=new RelativeLayout.LayoutParams(5,5);
circle.setLayoutParams(params1);
circle.setBackgroundDrawable(getResources().getDrawable(R.drawable.circle_rotate));
main_layout.addView(circle);

urlList.add("http://img0.imgtn.bdimg.com/it/u=3508535310,2065429756&fm=21&gp=0.jpg");
urlList.add("http://img5.imgtn.bdimg.com/it/u=646811362,1303793773&fm=21&gp=0.jpg");
urlList.add("http://imgsrc.baidu.com/baike/pic/item/0d72994497e8a063510ffee5.jpg");
urlList.add("http://img0.imgtn.bdimg.com/it/u=1342487761,3658569123&fm=21&gp=0.jpg");
urlList.add("http://img1.imgtn.bdimg.com/it/u=2656478986,1405599153&fm=21&gp=0.jpg");

new Thread(new Runnable() {

@Override
public void run() {
try {
Thread.sleep(500);
for (int i = 0; i < layout.getChildCount(); i++) {
if (once){
posList.add(layout.getTop());
posList.add(layout.getLeft());
once=false;
}
posList.add(layout.getChildAt(i).getLeft());
}
runOnUiThread(new Runnable() {
@Override
public void run() {
adapter = new PagerAdapter(MainActivity.this, new tmpListener(), urlList);
pager.setCurrentItem(Integer.MAX_VALUE/2-Integer.MAX_VALUE/2%urlList.size());
pager.setAdapter(adapter);

circle.setTop(posList.get(0));
circle.setLeft(posList.get(1)+posList.get(2));
myHandler.sendEmptyMessageDelayed(100,1000);
pager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {

}

@Override
public void onPageSelected(int position) {
myHandler.sendEmptyMessageDelayed(100,2000);
right=position>preItemPos?true:false;
preItemPos=position;
position%=urlList.size();
//圆点的移动
AnimationSet animationSet=new AnimationSet(true);
Animation animation;
if (position==0){
if (right)animation=setAnim(posList.get(2)-5,posList.get(2));
else animation=setAnim(posList.get(position+3),posList.get(position+2));
}
else {
if (right)animation=setAnim(posList.get(position+1),posList.get(position+2));
else{
if (position==urlList.size()-1)animation=setAnim(posList.get(posList.size()-1)+5,posList.get(posList.size()-1));
else animation=setAnim(posList.get(position+3),posList.get(position+2));
}
}
animation.setDuration(1000);
animationSet.addAnimation(animation);
animationSet.setFillEnabled(true);
animationSet.setFillAfter(true);
circle.startAnimation(animationSet);
}

@Override
public void onPageScrollStateChanged(int state) {
switch (state){
case 1:
myHandler.removeMessages(100);
myHandler.sendEmptyMessageDelayed(100,5000);
Log.e("自定义标签", "类名==MainActivity" + "方法名==onPageScrollStateChanged=====:" + "");
break;
}
}
});
}
});
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}).start();
}

Handler myHandler=new Handler(){
@Override
public void handleMessage(Message msg) {
switch (msg.what){
case 100:
myHandler.removeMessages(100);
pager.setCurrentItem(pager.getCurrentItem()+1);
break;
}
}
};

private Animation setAnim(int from,int to){
return new TranslateAnimation(posList.get(1)+from,posList.get(1)+to,posList.get(0),posList.get(0));
}


}

//暴露出去的接口;在此处实现Viewpager的item的监听

class tmpListener implements OnPagerItemClickListnener{

@Override
public void onClick(int pos) {
Log.e("自定义标签", "类名==tmpListener" + "方法名==onClick=====:" + pos);
}


}

实现源码

欢迎访问我的github,有帮助的话就star/fork一个吧,^3^

https://github.com/liuda555/MyViewFlow
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐