`
学不止
  • 浏览: 238378 次
  • 性别: Icon_minigender_1
社区版块
存档分类
最新评论
阅读更多

个人项目需要做到完美的左右可以循环的加载的ViewPager。一开始很快实现了无限循环。但是单个点击页签时有时会出现View为空的情况。分析可知是由于你当前要加载的View被清除的缘故。因为事实上ViewPager只缓存了3个元素这是为了你拖动能看到下一个考虑的。所以我做了改动。不说了搞了几个小时才调好。分享给大家吧:

package com.hanwei.spoof.who;

import java.util.ArrayList;
import java.util.List;

import android.app.Activity;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
import android.os.Bundle;
import android.os.Parcelable;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;
import android.util.DisplayMetrics;
import android.view.LayoutInflater;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.TranslateAnimation;
import android.widget.ImageView;
import android.widget.LinearLayout.LayoutParams;
import android.widget.TextView;
/**
 * Tab椤甸潰鎵嬪娍婊戝姩鍒囨崲浠ュ強鍔ㄧ敾鏁堟灉
 * 
 * @author D.Winter
 * 
 */
public class SpoofWhoActivity extends Activity {
	//
	private ViewPager mPager;
	private List<View> listViews; 
	private ImageView cursor;
	private TextView t1, t2, t3;
	private int offset = 0;
	private int bmpW;
	int currIndex;
	Matrix matrix;
	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);
		matrix=new Matrix();
		InitImageView();
		InitTextView();
		InitViewPager();
	}

	/**
	 * 鍒濆鍖栧ご鏍�	 */
	private void InitTextView() {
		t1 = (TextView) findViewById(R.id.text1);
		t2 = (TextView) findViewById(R.id.text2);
		t3 = (TextView) findViewById(R.id.text3);

		t1.setOnClickListener(new MyOnClickListener(0));
		t2.setOnClickListener(new MyOnClickListener(1));
		t3.setOnClickListener(new MyOnClickListener(2));
	}

	/**
	 * 鍒濆鍖朧iewPager
	 */
	private void InitViewPager() {
		mPager = (ViewPager) findViewById(R.id.vPager);
		listViews = new ArrayList<View>();
		LayoutInflater mInflater = getLayoutInflater();
		listViews.add(mInflater.inflate(R.layout.lay1, null));
		listViews.add(mInflater.inflate(R.layout.lay2, null));
		listViews.add(mInflater.inflate(R.layout.lay3, null));
		mPager.setAdapter(new MyPagerAdapter(listViews));
		mPager.setCurrentItem(498);
		currIndex=498;
		mPager.setOnPageChangeListener(new MyOnPageChangeListener());
	}

	/**
	 * 鍒濆鍖栧姩鐢�	 */
	private void InitImageView() {
		cursor = (ImageView) findViewById(R.id.image); 
		bmpW = BitmapFactory.decodeResource(getResources(), R.drawable.a)	
				.getWidth();
		DisplayMetrics dm = new DisplayMetrics();
		getWindowManager().getDefaultDisplay().getMetrics(dm);
		int screenW = dm.widthPixels;
		offset = (screenW / 3 - bmpW) / 2;
		matrix.postTranslate(offset, cursor.getTop());
		cursor.setImageMatrix(matrix);
	}

	/**
	 * ViewPager閫傞厤鍣�	 */
	public class MyPagerAdapter extends PagerAdapter {
		public List<View> mListViews;

		public MyPagerAdapter(List<View> mListViews) {
			this.mListViews = mListViews;
		}

	

		@Override
		public void finishUpdate(View arg0) {
		}
		

		@Override
		public void notifyDataSetChanged() {
			super.notifyDataSetChanged();
		}

		@Override
		public int getCount() {
			return 1000;
		}

		@Override
		public Object instantiateItem(View arg0, int arg1) {
			System.out.println("DDDDDD++++"+arg1+"DDDDDDDDDD"+((ViewPager) arg0).getChildCount());
			if(((ViewPager) arg0).getChildCount()==3)
			{
				((ViewPager) arg0).removeView(mListViews.get(arg1%3));
			}
	        ((ViewPager) arg0).addView(mListViews.get(arg1%3), 0);

			return mListViews.get(arg1%3);
		}

		@Override
		public boolean isViewFromObject(View arg0, Object arg1) {
			return arg0 == (arg1);
		}

		@Override
		public void restoreState(Parcelable arg0, ClassLoader arg1) {
		}

		@Override
		public Parcelable saveState() {
			return null;
		}

		@Override
		public void startUpdate(View arg0) {
		}



		@Override
		public void destroyItem(View arg0, int arg1, Object arg2) {
			// TODO Auto-generated method stub
			
		}
	}

	/**
	 * 澶存爣鐐瑰嚮鐩戝惉
	 */
	public class MyOnClickListener implements View.OnClickListener {
		private int index = 0;

		public MyOnClickListener(int i) {
			index = i;
		}

		@Override
		public void onClick(View v) {
			int prePos=currIndex-1;
			int nextPos=currIndex+1;
			if(prePos%3==index)
			{
				mPager.setCurrentItem(prePos);
			}
			else
				if(nextPos%3==index)
				{
					mPager.setCurrentItem(nextPos);
				}
				else
						if(currIndex%3==index)
						{
							mPager.setCurrentItem(currIndex);
						}
		}
	};

	/**
	 * 椤靛崱鍒囨崲鐩戝惉
	 */
	public class MyOnPageChangeListener implements OnPageChangeListener {

		int one = offset * 2 + bmpW;
		int two = one * 2;
		@Override
		public void onPageSelected(int arg0) {
			Animation animation = null;
			currIndex = currIndex%3;
			switch (arg0%3) {
			case 0:
				if (currIndex == 1) {
					animation = new TranslateAnimation(one, 0, 0, 0);
				} else if (currIndex == 2) {
					animation = new TranslateAnimation(two, 0, 0, 0);
				}
				break;
			case 1:
				if (currIndex == 0) {
					animation = new TranslateAnimation(offset, one, 0, 0);
				} else if (currIndex == 2) {
					animation = new TranslateAnimation(two, one, 0, 0);
				}
				break;
			case 2:
				if (currIndex == 0) {
					animation = new TranslateAnimation(offset, two, 0, 0);
				} else if (currIndex == 1) {
					animation = new TranslateAnimation(one, two, 0, 0);
				}
				break;
			}
			currIndex = arg0;
			if(animation!=null)
			{
				animation.setFillAfter(true);
				animation.setDuration(300);
				cursor.startAnimation(animation);
			}
		}

		@Override
		public void onPageScrolled(int arg0, float arg1, int arg2) {
		}

		@Override
		public void onPageScrollStateChanged(int arg0) {
		}
	}
}

 无限循环的原理是:设置尽量多的元素总数比如1000等等。然后把初始位置设为500或者更多。这样其实是假的无限循环但是用户不会左滑500次吧如果他真的做到了的话好吧他赢了,他可以到我这来领500块钱了哈。还有就是在每次加载View的时候先要清除因为相同的View不能有两个parent。点击无错是根据当前的位置判断的。因为你要知道当前位置和它前面和后面的元素都不是空的所以没有问题的。

 

 

3
1
分享到:
评论
6 楼 aplixy 2015-03-17  
关键是destroyItem函数中不能写代码,问题暂时解决了
5 楼 liangsaifei 2013-05-30  
注释乱码啊。。。
4 楼 学不止 2012-11-21  
yuehuaray 写道
按照你的代码 有时候出现 The specified child already has a parent. You must call removeView() on the child's parent first.

你的底部页签是3个吗?确定是像我这样写的?只在instantiateItem(View arg0, int arg1) l里进行添加和删除操作。
3 楼 yuehuaray 2012-11-20  
按照你的代码 有时候出现 The specified child already has a parent. You must call removeView() on the child's parent first.
2 楼 学不止 2012-11-16  
gundumw100 写道
@Override 
        public int getCount() { 
            return Integer.MAX_VALUE; 
        } 

这样写好一些!

这样没什么意义的。只要一般操作用户是不可能滑到低的就可以了。当然你这也很有道理哈关键不在这里哈
1 楼 gundumw100 2012-11-16  
@Override 
        public int getCount() { 
            return Integer.MAX_VALUE; 
        } 

这样写好一些!

相关推荐

    安卓图片轮播广告轮播自动滚屏相关-完美的viewpager左右无限循环实现广告自动手动轮播效果。无BUG.rar

    本教程将探讨如何利用ViewPager实现一个完美的左右无限循环的广告轮播效果,包括自动和手动轮播,并且无BUG。 ViewPager是Android SDK中的一个强大组件,常用于在多个页面间进行滑动切换。在图片轮播广告场景中,每...

    android viewpager 左右无限循环滑动 + 小圆点指示器

    本教程将详细讲解如何实现ViewPager的左右无限循环滑动,并结合自定义小圆点指示器来增强用户体验。 首先,我们需要理解ViewPager的基本用法。ViewPager继承自PagerAdapter,其核心在于`PagerAdapter`的`...

    安卓图片轮播广告轮播自动滚屏相关-基于ViewPager的无限循环自动播放带指示器的轮播图CarouselFigureView.rar

    本项目"安卓图片轮播广告轮播自动滚屏相关-基于ViewPager的无限循环自动播放带指示器的轮播图CarouselFigureView.rar"提供了一个实现这种功能的示例。下面我们将深入探讨这个话题,讲解其核心知识点。 首先,我们要...

    viewpager真正无限循环

    然而,在某些设计需求中,我们可能希望实现ViewPager的无限循环效果,即当用户滑动到第一个页面时能够自动跳转到最后一个页面,反之亦然,给人一种没有边界的感觉。本文将深入探讨如何在Android中实现ViewPager的...

    ViewPager无限循环左右滑动效果

    本教程将详细讲解如何实现ViewPager的无限循环左右滑动效果。 首先,我们需要了解ViewPager的基本用法。ViewPager是Android Support Library中的一个控件,它允许用户通过水平滑动手势在多个页面之间切换。每个页面...

    viewpager无限循环

    本项目标题为 "viewpager无限循环",意味着我们将探讨如何使`ViewPager`在达到最后一个页面后无缝返回到第一个页面,形成一个无限循环的效果。这在创建图片轮播或动态效果时尤其有用。 描述中提到的 "一个viewpager...

    ViewPager 图片无限循环

    本教程将详细介绍如何利用ViewPager实现图片的无限循环展示,这对于构建诸如轮播图等效果是至关重要的。 首先,我们需要理解ViewPager的基本用法。ViewPager继承自PagerAdapter,它可以通过重写`getCount()`方法来...

    Android ViewPager实现无限循环

    当我们想要在ViewPager中实现无限循环的效果时,意味着用户无论向左滑动还是向右滑动,都能无缝地从最后一个页面过渡到第一个页面,反之亦然。这就是"Android ViewPager实现无限循环(1.首尾完美过渡)"这个主题所要...

    ViewPager无限左右循环(优化版)

    然而,原生的ViewPager并不支持无限循环,即当滑动到首尾时无法无缝地跳转回对端。本知识点将探讨如何对ViewPager进行改造,实现无限循环的效果,并对性能进行优化。 【描述】:链接中的博客详细介绍了如何创建一个...

    viewpager无限自动循环demo,

    要实现无限循环,我们需要在`PagerAdapter`中创建额外的起始和结束页面,使其看起来像是在首尾之间无缝滑动。这可以通过在数据源中添加第一个和最后一个元素的副本来实现。 4. **定时切换**: 我们可以使用`...

    Viewpager左右循环滚动

    **标题解析:**"Viewpager左右循环滚动" 这个标题揭示了我们即将讨论的核心技术,即Android开发中的ViewPager组件,以及如何使它实现左右无限循环的滚动效果。ViewPager是Android SDK中的一个强大的布局管理器,常...

    ViewPager无限循环,详细注释!

    本教程将详细讲解如何实现ViewPager的无限循环功能,这对于创建广告轮播或者无缝浏览内容的场景非常有用。 首先,我们需要理解ViewPager的基本工作原理。ViewPager内部通过PagerAdapter来管理其包含的页面。默认...

    viewpager左右循环、定时滑动

    在一些设计中,我们可能需要让ViewPager实现无限循环的效果,即当用户滑动到最后一项时,能够自动滑回第一项,反之亦然。此外,有时我们还希望添加定时滑动的功能,使页面自动在一定时间间隔后切换。这就是...

    ViewPager 图片自动无限循环

    在本示例"ViewPager 图片自动无限循环"中,我们探讨的是如何利用ViewPager来实现图片的自动循环播放,并且支持用户手动滑动切换。这种功能常用于轮播广告、产品展示等场景。 首先,我们需要理解ViewPager的基本用法...

    android viewpager左右无限滑动

    "android viewpager 左右无限滑动"这一主题,意味着我们要创建一个可以无限制地向左或向右滑动的ViewPager实现,即用户在滑动到最后一页时,可以继续滑动到页面的起始位置,形成一种循环的效果。下面将详细介绍如何...

    viewpager伪无限循环

    "ViewPager伪无限循环"是一种设计技巧,使得用户在滑动到最后一页时可以无缝过渡到第一页,反之亦然,从而营造出一种无限循环浏览的用户体验。下面我们将详细探讨如何实现这种效果。 首先,我们要理解ViewPager的...

    ViewPager无限循环滑动+自动播放demo

    本教程将深入讲解如何利用ViewPager实现无限循环滑动和自动播放功能,构建一个Banner(轮播广告)组件。我们将讨论以下几个关键知识点: 1. **ViewPager基本使用**:ViewPager是一个可以左右滑动查看多个Fragment或...

    自动无限循环viewpager

    标题提到的"自动无限循环viewpager"就是这样一个功能的实现,它扩展了原生的`ViewPager`,增加了自动切换和循环滚动的能力。 描述中提到了几个关键点: 1. **自动循环**:这意味着`ViewPager`会自动在页面之间进行...

    无限循环viewPager 自动轮播

    在Android开发中,实现一个无限循环的ViewPager是常见的需求,特别是在设计类似网易云音乐首页的图片轮播功能时。这个实例展示了如何通过自定义适配器和监听器来实现一个功能完善的自动轮播效果,同时支持用户手动...

Global site tag (gtag.js) - Google Analytics