你项目中有没有使用到ViewPager相互嵌套的滑动问题,或者ListView中ViewPager的滑动问题?
前段时间在实现ViewPager的相互嵌套时,遇到了一些手势问题,从网上找了一些资料之后发现,没有一个是完全契合自己需求的,故此手动敲打这一部分代码,实现了一个简单的无限轮滑的ViewPager。
1.首先需要实现外层的ViewPager,此步骤比较简单,不做赘述
2.在FirstFragment中再次嵌入一个ViewPager,此时外层ViewPager和内层ViewPager就会出现滑动冲突事件,利用ChildAdapter解决滑动冲突
3.使用定时器实现FirstFragment中的ViewPager无限滑动(可以自定义设置最大值,此处使用MAX_COUNT=5000)
先看一下效果:
下面就是代码实现:
MainActivity中代码:
package com.example.tm.myapplication;
import android.support.v4.app.Fragment;
import android.support.v4.view.ViewPager;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends AppCompatActivity{
private ViewPager parentViewpager;
private List<Fragment> fragments;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
initData();
}
private static final String TAG = "MainActivity";
private void initData() {
//初始化外层Fragment的数据源
fragments=new ArrayList<>();
FirstFragment firstFragment=new FirstFragment();
SecondFragment secondFragment=new SecondFragment();
ThirdFragment thirdFragment=new ThirdFragment();
fragments.add(firstFragment);
fragments.add(secondFragment);
fragments.add(thirdFragment);
ParentAdapter adapter=new ParentAdapter(getSupportFragmentManager(),fragments);
parentViewpager.setAdapter(adapter);
}
private void initView() {
parentViewpager= (ViewPager) findViewById(R.id.parent_viewPager);
}
}
FirstFragment中代码:
package com.example.tm.myapplication;
import android.os.Bundle;
import android.os.Handler;
import android.support.v4.app.Fragment;
import android.support.v4.view.ViewPager;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.Toast;
import java.util.ArrayList;
import java.util.List;
public class FirstFragment extends Fragment {
private static final String TAG = "FirstFragment";
private View view;
private ChildViewpager childViewpager;
private List<ImageView> data;
private int[] imageArray={R.mipmap.first,R.mipmap.second,R.mipmap.third,R.mipmap.forth,R.mipmap.fifth};
private int maxCount=5000;
//启动一个定时器
private Handler handler=new Handler();
private Runnable runnable=new Runnable() {
@Override
public void run() {
childViewpager.setCurrentItem(maxCount++);
handler.postDelayed(this,2000);//开启定时器
}
};
public FirstFragment() {
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view = inflater.inflate(R.layout.fragment_first, container, false);
childViewpager= (ChildViewpager) view.findViewById(R.id.child_viewPager);
initData();
return view;
}
private void initData() {
data=new ArrayList<>();
for(int i=0;i<5;i++){
ImageView imageView=new ImageView(getActivity());
imageView.setBackgroundResource(imageArray[i]);
final int j=i;
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Toast.makeText(getActivity(), "点击了"+j+"Fragment", Toast.LENGTH_SHORT).show();
}
});
data.add(imageView);
}
ChildAdapter adapter=new ChildAdapter(data,getActivity());
childViewpager.setAdapter(adapter);
childViewpager.setCurrentItem(maxCount);//设置一个比较大的数用来为viewpager初始化第一个页面
childViewpager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
Log.i(TAG, "onPageScrolled: position"+position);
handler.removeCallbacks(runnable);
maxCount=position;//由于setCurrent()方法每次只能比原来的position多一个,所以将现在的position记录下来,为累加做初值
handler.postDelayed(runnable,2000);
}
@Override
public void onPageSelected(int position) {
}
@Override
public void onPageScrollStateChanged(int state) {
}
});
handler.removeCallbacks(runnable);
handler.postDelayed(runnable,2000);
}
@Override
public void onPause() {
super.onPause();
handler.removeCallbacks(runnable);
}
@Override
public void onResume() {
super.onResume();
handler.postDelayed(runnable,2000);
}
}
SecondFragment中代码:
package com.example.tm.myapplication;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
public class SecondFragment extends Fragment {
public SecondFragment() {
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_second, container, false);
}
}
ThirdFragment中代码:
package com.example.tm.myapplication;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
public class ThirdFragment extends Fragment {
public ThirdFragment() {
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_third, container, false);
}
}
ChildAdapter中代码:
package com.example.tm.myapplication;
import android.content.Context;
import android.support.v4.view.PagerAdapter;
import android.util.Log;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import java.util.List;
public class ChildAdapter extends PagerAdapter {
private List<ImageView> data;
private Context context;
private static final String TAG = "ChildAdapter";
public ChildAdapter(List<ImageView> data, Context context) {
this.data = data;
this.context = context;
}
@Override
public int getCount() {
//规定viewpager的最大页数
return Integer.MAX_VALUE;
}
@Override
public boolean isViewFromObject(View view, Object object) {
return view==object;
}
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
Log.i(TAG, "destroyItem: 销毁了一个item");
container.removeView(data.get((position)%data.size()));
}
@Override
public Object instantiateItem(ViewGroup container, int position) {//position是0-4
Log.i(TAG, "instantiateItem: 新建了一个item");
container.addView(data.get(position%data.size()));
return data.get(position%data.size());
}
}
ParentAdapter中代码:
package com.example.tm.myapplication;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import java.util.List;
public class ParentAdapter extends FragmentPagerAdapter {
private List<Fragment> data;
public ParentAdapter(FragmentManager fm,List<Fragment> data) {
super(fm);
this.data=data;
}
@Override
public Fragment getItem(int position) {
return data.get(position);
}
@Override
public int getCount() {
int ret=0;
if(data!=null){
ret=data.size();
}
return ret;
}
}
ChildViewPager中(该文件源地址:http://blog.csdn.net/leewenjin/article/details/21011841)
package com.example.tm.myapplication;
import android.content.Context;
import android.graphics.PointF;
import android.support.v4.view.ViewPager;
import android.text.style.ClickableSpan;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
public class ChildViewpager extends ViewPager {
/** 触摸时按下的点 **/
PointF downP = new PointF();
/** 触摸时当前的点 **/
PointF curP = new PointF();
public ChildViewpager(Context context) {
super(context);
}
public ChildViewpager(Context context, AttributeSet attrs) {
super(context, attrs);
}
private static final String TAG = "ChildViewpager";
@Override
public boolean onTouchEvent(MotionEvent arg0) {
//每次进行onTouch事件都记录当前的按下的坐标
if(getChildCount()<=1)
{
return super.onTouchEvent(arg0);
}
curP.x = arg0.getX();
curP.y = arg0.getY();
if(arg0.getAction() == MotionEvent.ACTION_DOWN)
{
//记录按下时候的坐标
//切记不可用 downP = curP ,这样在改变curP的时候,downP也会改变
downP.x = arg0.getX();
downP.y = arg0.getY();
//此句代码是为了通知他的父ViewPager现在进行的是本控件的操作,不要对我的操作进行干扰
getParent().requestDisallowInterceptTouchEvent(true);
}
if(arg0.getAction() == MotionEvent.ACTION_MOVE){
//此句代码是为了通知他的父ViewPager现在进行的是本控件的操作,不要对我的操作进行干扰
getParent().requestDisallowInterceptTouchEvent(true);
}
if(arg0.getAction() == MotionEvent.ACTION_UP || arg0.getAction() == MotionEvent.ACTION_CANCEL){
//在up时判断是否按下和松手的坐标为一个点
//如果是一个点,将执行点击事件,这是我自己写的点击事件,而不是onclick
getParent().requestDisallowInterceptTouchEvent(false);
if(downP.x==curP.x && downP.y==curP.y){
return true;
}
}
super.onTouchEvent(arg0); //注意这句不能 return super.onTouchEvent(arg0); 否则触发parent滑动
return true;
}
}
布局文件:
activity_main.xml中代码:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout 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:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.tm.myapplication.MainActivity">
<android.support.v4.view.ViewPager
android:id="@+id/parent_viewPager"
android:layout_width="match_parent"
android:layout_height="match_parent">
</android.support.v4.view.ViewPager>
</RelativeLayout>
fragment_first中代码:
<FrameLayout 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:background="#0f0"
tools:context="com.example.tm.myapplication.FirstFragment">
<com.example.tm.myapplication.ChildViewpager
android:id="@+id/child_viewPager"
android:layout_width="match_parent"
android:layout_height="200dp"
/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/hello_blank_fragment"
android:gravity="center"
android:layout_marginTop="300dp"/>
</FrameLayout>
fragment_second中代码:
<FrameLayout 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"
tools:context="com.example.tm.myapplication.SecondFragment">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="@string/hello_blank_fragment"
android:gravity="center"
android:background="#00f"/>
</FrameLayout>
fragment_third中代码:
<FrameLayout 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"
tools:context="com.example.tm.myapplication.ThirdFragment">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="@string/hello_blank_fragment"
android:gravity="center"
android:background="#f00"/>
</FrameLayout>
是不是特别简单,有些问题是需要静下心来慢慢来探索的,希望小伙伴能喜欢这篇文章!如有问题你也可以联系我,微信:cai-niao-bu-ke-yi;QQ:1125325256;个人网站:www.sevenyoung.net(不日将开通)