效果圖如下:
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"
tools:context="com.example.myapplication.MainActivity">
<android.support.v4.view.ViewPager
android:id="@+id/view_pager"
android:layout_width="match_parent"
android:layout_height="230dp">
</android.support.v4.view.ViewPager>
<LinearLayout
android:layout_alignBottom="@id/view_pager"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:background="#77000000"
android:padding="5dp"
android:gravity="center_horizontal"
android:orientation="vertical">
<TextView
android:id="@+id/tv_image_desc"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="16sp"
android:textColor="#bbffffff"
android:text="我是圖片描述信息"/>
</LinearLayout>
</RelativeLayout>
代碼的實(shí)現(xiàn)
工程結(jié)構(gòu)如下圖
第一步:初始化數(shù)據(jù)
/**
*初始化數(shù)據(jù)
*/
//初始化圖片輪播的圖片
private void initData() {
int[] imageResIDs = {
R.mipmap.a,
R.mipmap.b,
R.mipmap.c,
R.mipmap.d,
R.mipmap.e
};
mImageList = new ArrayList<>();
ImageView iv;
for (int i = 0; i < imageResIDs.length; i++) {
iv = new ImageView(this);
iv.setBackgroundResource(imageResIDs[i]);
mImageList.add(iv);
//初始化顯示每張圖片下面現(xiàn)實(shí)的文字
imageDescs= new String[]{
"今年二十七八歲,我最喜歡的事就是睡覺(jué)",
"懶蟲(chóng)具练,起床了,要上班了",
"我翻了個(gè)身,想著如果今天是周末多好",
"終于爬起來(lái)瓣铣,坐在沙發(fā)上一臉懵逼",
"一個(gè)人早餐就隨便吃點(diǎn)"
};
}
}
第二步:設(shè)置viewpager適配器
/**
*新建一個(gè)adapter包,新建適配類(lèi)如下
*/
public class MyPagerAdapter extends PagerAdapter {
private List<ImageView> imageList;
private ViewPager viewPager;
public MyPagerAdapter(List<ImageView> imageList, ViewPager viewPager) {
this.imageList = imageList;
this.viewPager = viewPager;
}
/**
* 返回的int的值, 會(huì)作為ViewPager的總長(zhǎng)度來(lái)使用.
*/
@Override
public int getCount() {
return Integer.MAX_VALUE;//Integer.MAX_VALUE偽無(wú)限循環(huán)
}
/**
* 判斷是否使用緩存, 如果返回的是true, 使用緩存. 不去調(diào)用instantiateItem方法創(chuàng)建一個(gè)新的對(duì)象
*/
@Override
public boolean isViewFromObject(View view, Object object) {
return view == object;
}
/**
* 初始化一個(gè)條目
* position 就是當(dāng)前需要加載條目的索引
*/
@Override
public Object instantiateItem(ViewGroup container, int position) {
// 把position對(duì)應(yīng)位置的ImageView添加到ViewPager中
ImageView iv = imageList.get(position % imageList.size());
viewPager.addView(iv);
// 把當(dāng)前添加ImageView返回回去.
return iv;
}
/**
* 銷(xiāo)毀一個(gè)條目
* position 就是當(dāng)前需要被銷(xiāo)毀的條目的索引
*/
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
// 把ImageView從ViewPager中移除掉
viewPager.removeView(imageList.get(position % imageList.size()));
}
}
第三步:給viewpager設(shè)置輪播監(jiān)聽(tīng)器
/**
* 當(dāng)ViewPager頁(yè)面被選中時(shí), 觸發(fā)此方法.
* @param position 當(dāng)前被選中的頁(yè)面的索引
*/
@Override
public void onPageSelected(int position) {
//偽無(wú)限循環(huán),滑到最后一張圖片又從新進(jìn)入第一張圖片
int newPosition = position % mImageList.size();
// 把當(dāng)前選中的點(diǎn)給切換了, 還有描述信息也切換
mTvImageDesc.setText(imageDescs[newPosition]);//圖片下面設(shè)置顯示文本
// 把當(dāng)前的索引賦值給前一個(gè)索引變量, 方便下一次再切換.
previousPosition = newPosition;
}
@Override
public void onPageScrollStateChanged(int state) {
}
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
第四步:設(shè)置剛打開(kāi)app時(shí)顯示的圖片和文字
/**
* 設(shè)置剛進(jìn)入app時(shí)贷揽,顯示的圖片和文字
*/
private void setFirstLocation() {
mTvImageDesc.setText(imageDescs[previousPosition]);
// 把ViewPager設(shè)置為默認(rèn)選中Integer.MAX_VALUE / 2棠笑,從十幾億次開(kāi)始輪播圖片,達(dá)到無(wú)限循環(huán)目的;
int m = (Integer.MAX_VALUE / 2) % mImageList.size();
int currentPosition = Integer.MAX_VALUE / 2 - m;
mViewPager.setCurrentItem(currentPosition);
}
第五步: 設(shè)置自動(dòng)播放,每隔3秒換一張圖片
/**
* 每隔3秒自動(dòng)播放圖片
*/
private void autoPlayView() {
//自動(dòng)播放圖片
new Thread(new Runnable() {
@Override
public void run() {
while (!isStop){
runOnUiThread(new Runnable() {
@Override
public void run() {
mViewPager.setCurrentItem(mViewPager.getCurrentItem() + 1);
}
});
SystemClock.sleep(3000);
}
}
}).start();
}
第六步: 當(dāng)Activity銷(xiāo)毀時(shí)取消圖片自動(dòng)播放
/**
*當(dāng)Activity銷(xiāo)毀時(shí)取消圖片自動(dòng)播放
*/
@Override
protected void onDestroy() {
super.onDestroy();
isStop = true;
}
細(xì)節(jié)問(wèn)題處理
如果發(fā)現(xiàn)左邊圖片的索引是負(fù)數(shù), 小于0, 就不會(huì)預(yù)加載.
如果發(fā)現(xiàn)右邊的圖片是索引是大于等于總圖片的個(gè)數(shù)禽绪,也不會(huì)預(yù)加載. 例如:總圖片是:5, 右邊的圖片是第6張蓖救。
圖片無(wú)限循環(huán)實(shí)現(xiàn)
1.設(shè)置是適配器返回的長(zhǎng)度為Integer的最大值
@Override
public int getCount() {
return Integer.MAX_VALUE;
}
2.將position設(shè)置為如下
//偽無(wú)限循環(huán),滑到最后一張圖片又從新進(jìn)入第一張圖片
int newPosition = position % mImageList.size();
附上全部的代碼
MainActiviy
public class MainActivity extends AppCompatActivity implements ViewPager.OnPageChangeListener{
@BindView(R.id.view_pager)
ViewPager mViewPager;
@BindView(R.id.tv_image_desc)
TextView mTvImageDesc;
private List<ImageView> mImageList;
private String[] imageDescs;
private int previousPosition = 0; // 前一個(gè)被選中的position
private boolean isStop = false;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this);
initView();
autoPlayView();
}
/**
* 第五步: 設(shè)置自動(dòng)播放,每隔3秒換一張圖片
*/
private void autoPlayView() {
//自動(dòng)播放圖片
new Thread(new Runnable() {
@Override
public void run() {
while (!isStop){
runOnUiThread(new Runnable() {
@Override
public void run() {
mViewPager.setCurrentItem(mViewPager.getCurrentItem() + 1);
}
});
SystemClock.sleep(3000);
}
}
}).start();
}
private void initView() {
initData();
MyPagerAdapter mAdapter = new MyPagerAdapter(mImageList, mViewPager);
mViewPager.setAdapter(mAdapter);//第二步:設(shè)置viewpager適配器
mViewPager.addOnPageChangeListener(this);
setFirstLocation();
}
/**
* 第四步:設(shè)置剛打開(kāi)app時(shí)顯示的圖片和文字
*/
private void setFirstLocation() {
mTvImageDesc.setText(imageDescs[previousPosition]);
// 把ViewPager設(shè)置為默認(rèn)選中Integer.MAX_VALUE / 2丐一,從十幾億次開(kāi)始輪播圖片藻糖,達(dá)到無(wú)限循環(huán)目的;
int m = (Integer.MAX_VALUE / 2) % mImageList.size();
int currentPosition = Integer.MAX_VALUE / 2 - m;
mViewPager.setCurrentItem(currentPosition);
}
/**
* 第一步:初始化數(shù)據(jù)
*/
//初始化圖片輪播的圖片
private void initData() {
int[] imageResIDs = {
R.mipmap.a,
R.mipmap.b,
R.mipmap.c,
R.mipmap.d,
R.mipmap.e
};
mImageList = new ArrayList<>();
ImageView iv;
for (int i = 0; i < imageResIDs.length; i++) {
iv = new ImageView(this);
iv.setBackgroundResource(imageResIDs[i]);
mImageList.add(iv);
//初始化顯示每張圖片下面現(xiàn)實(shí)的文字
imageDescs= new String[]{
"今年二十七八歲,我最喜歡的事就是睡覺(jué)",
"懶蟲(chóng)库车,起床了巨柒,要上班了",
"我翻了個(gè)身,想著如果今天是周末多好",
"終于爬起來(lái)柠衍,坐在沙發(fā)上一臉懵逼",
"一個(gè)人早餐就隨便吃點(diǎn)"
};
}
}
/**
* 第三步:給viewpager設(shè)置輪播監(jiān)聽(tīng)器
* viewpager的監(jiān)聽(tīng)器
* 當(dāng)ViewPager頁(yè)面被選中時(shí), 觸發(fā)此方法.
* @param position 當(dāng)前被選中的頁(yè)面的索引
*/
@Override
public void onPageSelected(int position) {
//偽無(wú)限循環(huán)洋满,滑到最后一張圖片又從新進(jìn)入第一張圖片
int newPosition = position % mImageList.size();
// 把當(dāng)前選中的點(diǎn)給切換了, 還有描述信息也切換
mTvImageDesc.setText(imageDescs[newPosition]);//圖片下面設(shè)置顯示文本
// 把當(dāng)前的索引賦值給前一個(gè)索引變量, 方便下一次再切換.
previousPosition = newPosition;
}
@Override
public void onPageScrollStateChanged(int state) {
}
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
/**
* 第六步: 當(dāng)Activity銷(xiāo)毀時(shí)取消圖片自動(dòng)播放
*/
@Override
protected void onDestroy() {
super.onDestroy();
isStop = true;
}
}
MyPagerAdapter
public class MyPagerAdapter extends PagerAdapter {
private List<ImageView> imageList;
private ViewPager viewPager;
public MyPagerAdapter(List<ImageView> imageList, ViewPager viewPager) {
this.imageList = imageList;
this.viewPager = viewPager;
}
/**
* 返回的int的值, 會(huì)作為ViewPager的總長(zhǎng)度來(lái)使用.
*/
@Override
public int getCount() {
return Integer.MAX_VALUE;//Integer.MAX_VALUE偽無(wú)限循環(huán)
}
/**
* 判斷是否使用緩存, 如果返回的是true, 使用緩存. 不去調(diào)用instantiateItem方法創(chuàng)建一個(gè)新的對(duì)象
*/
@Override
public boolean isViewFromObject(View view, Object object) {
return view == object;
}
/**
* 初始化一個(gè)條目
* position 就是當(dāng)前需要加載條目的索引
*/
@Override
public Object instantiateItem(ViewGroup container, int position) {
// 把position對(duì)應(yīng)位置的ImageView添加到ViewPager中
ImageView iv = imageList.get(position % imageList.size());
viewPager.addView(iv);
// 把當(dāng)前添加ImageView返回回去.
return iv;
}
/**
* 銷(xiāo)毀一個(gè)條目
* position 就是當(dāng)前需要被銷(xiāo)毀的條目的索引
*/
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
// 把ImageView從ViewPager中移除掉
viewPager.removeView(imageList.get(position % imageList.size()));
}
}