(项目中需要实现图片轮番效果,就查资料着重学习,本地图片实现)
原理就是利用定时任务器定时切换ViewPager的页面,根据图片个数动态生成下端的圆点。
效果图:
1、获取本地图片实现轮番效果
布局:两部分组成,viewpager和下端圆点的布局
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/ui_home_autoImage"
android:layout_width="fill_parent"
android:layout_height="200dp" >
<android.support.v4.view.ViewPager
android:id="@+id/img_vp"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom|center"
android:orientation="vertical" >
<LinearLayout
android:id="@+id/viewGroup"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|center"
android:layout_marginBottom="3dp"
android:orientation="horizontal" >
</LinearLayout>
</LinearLayout>
</FrameLayout>
主要代码:定时任务,实现PagerAdapter
package com.xinyuan.cycleimage;
import java.lang.ref.SoftReference;
import java.util.ArrayList;
import java.util.List;
import android.annotation.TargetApi;
import android.app.Activity;
import android.app.ActionBar.LayoutParams;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
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.view.View;
import android.view.ViewGroup;
import android.view.ViewParent;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ImageView.ScaleType;
/**
* 轮番展示图片
* @创建时间 :2016-1-6
*
*/
public class MainActivity extends Activity {
private ViewPager viewPager;
private List<ImageView> imageViews; // 滑动的图片集合
private int[] imageResId; // 图片ID
// 圆点图片集合
private ImageView[] tips;
private int currentItem = 0; // 当前图片的索引号
private String[] defaultLength;
private ImageHandler handler = new ImageHandler(
new SoftReference<MainActivity>(this));
// 切换当前显示的图片
private static class ImageHandler extends Handler {
/**
* 请求更新显示的View。
*/
protected static final int MSG_START_IMAGE = 0;
/**
* 请求更新显示的View。
*/
protected static final int MSG_UPDATE_IMAGE = 1;
/**
* 请求暂停轮播。
*/
protected static final int MSG_KEEP_SILENT = 2;
/**
* 请求恢复轮播。
*/
protected static final int MSG_BREAK_SILENT = 3;
/**
* 记录最新的页号,当用户手动滑动时需要记录新页号,否则会使轮播的页面出错。
* 例如当前如果在第一页,本来准备播放的是第二页,而这时候用户滑动到了末页,
* 则应该播放的是第一页,如果继续按照原来的第二页播放,则逻辑上有问题。
*/
protected static final int MSG_PAGE_CHANGED = 4;
// 轮播间隔时间
protected static final long MSG_DELAY = 2000;
// 使用弱引用避免Handler泄露.这里的泛型参数可以不是Activity,也可以是Fragment等
private SoftReference<MainActivity> weakReference;
private int currentItem = 0;
protected ImageHandler(SoftReference<MainActivity> wk) {
weakReference = wk;
}
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
MainActivity activity = weakReference.get();
if (activity == null) { // Activity已经回收,无需再处理UI了
return;
}
// 检查消息队列并移除未发送的消息,这主要是避免在复杂环境下消息出现重复等问题。
if (activity.handler.hasMessages(MSG_UPDATE_IMAGE)) {
activity.handler.removeMessages(MSG_UPDATE_IMAGE);
}
switch (msg.what) {
case MSG_UPDATE_IMAGE:
currentItem++;
activity.viewPager.setCurrentItem(currentItem);
// 准备下次播放
activity.handler.sendEmptyMessageDelayed(MSG_UPDATE_IMAGE,
MSG_DELAY);
break;
case MSG_START_IMAGE:
currentItem++;
activity.viewPager.setCurrentItem(currentItem);
break;
case MSG_KEEP_SILENT:
// 只要不发送消息就暂停了
break;
case MSG_BREAK_SILENT:
activity.handler.sendEmptyMessageDelayed(MSG_UPDATE_IMAGE,
MSG_DELAY);
break;
case MSG_PAGE_CHANGED:
// 记录当前的页号,避免播放的时候页面显示不正确。
currentItem = msg.arg1;
break;
}
}
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
auto_Image();
}
/**
* 图片轮番展示
*
* @创建日期 2016-1-17
*
* @返回值 void
*
*/
private void auto_Image() {
imageViews = new ArrayList<ImageView>();
imageResId = new int[] { R.drawable.banner01, R.drawable.banner02,
R.drawable.banner01, R.drawable.banner02 };
for (int i = 0; i < imageResId.length; i++) {
ImageView imageView = new ImageView(this);
imageView.setImageResource(imageResId[i]);
imageView.setScaleType(ScaleType.CENTER_CROP);
imageViews.add(imageView);
}
defaultLength = new String[imageViews.size()];
dynamicAddition(defaultLength);
viewPager = (ViewPager) findViewById(R.id.img_vp);
viewPager.setAdapter(new MyAdapter());// 设置填充ViewPager页面的适配器
// 设置一个监听器,当ViewPager中的页面改变时调用
viewPager.setOnPageChangeListener(new MyPageChangeListener());
currentItem = imageViews.size() * 100;
viewPager.setCurrentItem(currentItem);
// 开始轮播效果
handler.sendEmptyMessageDelayed(ImageHandler.MSG_START_IMAGE,
ImageHandler.MSG_DELAY);
}
/**
* 设置底部圆点滚动
*
* @创建日期 2016-1-18
*
* @参数 lengthCum 图片个数
* @返回值 void
*
*/
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
private void dynamicAddition(String[] lengthCum) {
// 动态的添加圆点图片设置
ViewGroup group = (ViewGroup) findViewById(R.id.viewGroup);
tips = new ImageView[lengthCum.length];
for (int i = 0; i < tips.length; i++) {
ImageView imageView = new ImageView(this);
imageView.setScaleType(ImageView.ScaleType.FIT_XY);
imageView.setLayoutParams(new LayoutParams(
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
tips[i] = imageView;
if (i == 0) {
tips[i].setBackgroundResource(R.drawable.page_indicator_focused);
} else {
tips[i].setBackgroundResource(R.drawable.page_indicator_unfocused);
}
LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(
new ViewGroup.LayoutParams(LayoutParams.WRAP_CONTENT,
LayoutParams.WRAP_CONTENT));
layoutParams.leftMargin = 5;
layoutParams.rightMargin = 5;
group.addView(imageView, layoutParams);
}
}
/**
* 填充ViewPager页面的适配器
*
* @author Administrator
*
*/
private class MyAdapter extends PagerAdapter {
@Override
public int getCount() {
return Integer.MAX_VALUE;
}
@Override
public Object instantiateItem(ViewGroup container, int position) {
position = position % imageViews.size();
if (position < 0) {
position = imageViews.size() + position;
}
ImageView view = imageViews.get(position);
// 如果View已经在之前添加到了一个父组件,则必须先remove,否则会抛出IllegalStateException。
ViewParent vp = view.getParent();
if (vp != null) {
ViewGroup parent = (ViewGroup) vp;
parent.removeView(view);
}
container.addView(view);
return view;
}
@Override
public void destroyItem(View arg0, int arg1, Object arg2) {
// ((ViewPager) arg0).removeView(imageViews.get(arg1%imageViews.size()));
}
@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 finishUpdate(View arg0) {
}
}
/**
* 当ViewPager中页面的状态发生改变时调用
*
* @author Administrator
*
*/
private class MyPageChangeListener implements OnPageChangeListener {
private int oldPosition = 0;
public void onPageSelected(int position) {
int p = position % imageViews.size();
currentItem = p;
tips[oldPosition]
.setBackgroundResource(R.drawable.page_indicator_unfocused);
tips[p].setBackgroundResource(R.drawable.page_indicator_focused);
oldPosition = p;
handler.sendMessage(Message.obtain(handler,
ImageHandler.MSG_PAGE_CHANGED, position, 0));
}
// 覆写该方法实现轮播效果的暂停和恢复
@Override
public void onPageScrollStateChanged(int arg0) {
switch (arg0) {
case ViewPager.SCROLL_STATE_DRAGGING:
handler.sendEmptyMessage(ImageHandler.MSG_KEEP_SILENT);
break;
case ViewPager.SCROLL_STATE_IDLE:
handler.sendEmptyMessageDelayed(ImageHandler.MSG_UPDATE_IMAGE,
ImageHandler.MSG_DELAY);
break;
default:
break;
}
}
public void onPageScrolled(int arg0, float arg1, int arg2) {
}
}
}
注意:在实现PagerAdapter适配器时需要注意,在instantiateItem方法中,需要获取view.getParent(),如果存在就移除,不需要在destroyItem方法中移除,否则会报下面的错误