修改ViewPage的r预加载,左右滑动,切换经过中间页问题,ViewPager一屏显示多张图片

2017-04-16 19:40:01
1.屏蔽切换的时候需要经过中间页
2.屏蔽ViewPager的滑动
3.预加载问题

复制代码

import android.content.Context;import android.support.v4.view.ViewPager;import android.util.AttributeSet;import android.view.MotionEvent;/**
 * 1.屏蔽切换的时候需要经过中间页
 * 2.屏蔽ViewPager的滑动
 * 3.预加载问题 */public class MyViewPager extends ViewPager {    /**
     * 是否可以滑动     */
    private boolean isCanScroll = false;    public MyViewPager(Context context) {        super(context);
    }    public MyViewPager(Context context, AttributeSet attrs) {        super(context, attrs);
    }    /**
     * 解决切换需要经过中间页     */
    @Override    public void setCurrentItem(int item) {        //super.setCurrentItem(item);源码
        super.setCurrentItem(item,false);//false表示切换的时候,不经过两个页面的中间页    }    /**
     * 让ViewPager不能左右滑动     */
    @Override    public boolean onTouchEvent(MotionEvent ev) {        if(isCanScroll){            return super.onTouchEvent(ev);
        }else{            return false;
        }
    }    /**
     * 暴露出去的方法,屏蔽ViewPager的滑动,默认不可滑动
     * @param isCanScroll 为true可以左右滑动,为false不可滑动     */
    public void setIsCanScroll(boolean isCanScroll){        this.isCanScroll = isCanScroll;
    }

    @Override    public boolean onInterceptTouchEvent(MotionEvent ev) {        if(isCanScroll){            return super.onInterceptTouchEvent(ev);
        }else{            return false;
        }
    }    /* 设置预加载页数的源码,默认为1,当设置的数大于1是有效的,小于1就无效了
       1)如果想预加载多页(默认预加载一页),可以使用setOffscreenPageLimit(int limit),意思为幕后页的限制,默认为1
       2)当你不想要预加载的时候,那是不是只需要将这个值设为0呢?答案是不行的,
      解决办法:复制ViewPager源码将DEFAULT_OFFSCREEN_PAGES这个值改为0就可以了
    public void setOffscreenPageLimit(int limit) {
        if (limit < DEFAULT_OFFSCREEN_PAGES) {
            limit = DEFAULT_OFFSCREEN_PAGES;//可见当设置的值小于1时无效
        }
        if (limit != mOffscreenPageLimit) {
            mOffscreenPageLimit = limit;
            populate();
        }
    }     */}

复制代码

但是切记,复制ViewPager源码别复制高版本的,防止出问题,因为现在Android都7.0了,版本都老高了,其实android虽然每个版本都有v4包,但是这些v4包是有差异的。这就造成高版本v4包里的ViewPager,即使你Copy它,将其DEFAULT_OFFSCREEN_PAGES的值改为0,还是不起作用的,其中的逻辑变了。具体哪里变了导致无效我也没有继续研究了,下面给出一份低版本修改好的(只修改了预加载)

 View Code

2.利用ViewPager实现一屏显示多张图片的问题

MainActivity代码:

复制代码

public class MainActivity extends AppCompatActivity {    private List<ImageView> list;    private int[] imgsId={R.drawable.a,R.drawable.b,R.drawable.c,R.drawable.d};

    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        ViewPager viewPager = (ViewPager) findViewById(R.id.viewPager);
        initData();
        viewPager.setAdapter(new MyPagerAdapter(list));
    }    
    //初始化显示的图片
    private void initData() {
        list = new ArrayList<>();        for (int i : imgsId) {
            ImageView imageView = new ImageView(MainActivity.this);
            imageView.setImageResource(i);
            imageView.setScaleType(ImageView.ScaleType.FIT_XY);
            list.add(imageView);
        }
    }
}

复制代码

适配器:

复制代码

public class MyPagerAdapter extends PagerAdapter {    private List<ImageView> list;    public MyPagerAdapter(List<ImageView> list) {        this.list = list;
    }

    @Override    public int getCount() {        return list.size();
    }

    @Override    public boolean isViewFromObject(View view, Object object) {        return view == object;
    }

    @Override    public Object instantiateItem(ViewGroup container, int position) {
        container.addView(list.get(position));        return list.get(position);
    }

    @Override    public void destroyItem(ViewGroup container, int position, Object object) {
        container.removeView((View) object);
        object = null;
    }    /**
     * 设置该页内容所占屏幕的宽度     */
    @Override    public float getPageWidth(int position) {        //return 1.f; 默认返回1,代表该position占据了ViewPager的一整页,范围(0,1]
        return 0.8f;
    }
}

复制代码

布局文件:

 View Code

效果如下: 如果没重写getPageWidth()方法(左图)              重写后为(右图)

下面看下一屏显示多张图片的具体实现:

由于上面适配器中的getPageWidth方法只能控制一边的距离,不能实现左右两边显示,所以改功能需要删除上面适配器中的getPageWidth()方法

java代码:

复制代码

import android.os.Bundle;import android.support.v4.view.ViewPager;import android.support.v7.app.AppCompatActivity;import android.view.MotionEvent;import android.view.View;import android.widget.ImageView;import android.widget.LinearLayout;import java.util.ArrayList;import java.util.List;/**
 * ViewPager显示多张图片 */public class MainActivity extends AppCompatActivity {    private List<ImageView> list;    private int[] imgsId={R.drawable.a, R.drawable.b, R.drawable.c, R.drawable.d};

    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        initData();//初始化数据        //ViewPager的父布局
        final LinearLayout viewPagerContainer  = (LinearLayout) findViewById(R.id.viewPager_layout);        final ViewPager viewPager = (ViewPager) findViewById(R.id.viewPager);
        viewPager.setOffscreenPageLimit(3); // viewPager的缓存页数
        viewPager.setPageMargin(30); // 设置各页面的间距        // 将父节点Layout事件分发给viewpager,否则只能滑动中间的一个view对象
        viewPagerContainer.setOnTouchListener(new View.OnTouchListener() {
            @Override            public boolean onTouch(View v, MotionEvent event) {                return viewPager.dispatchTouchEvent(event);
            }
        });        //设置ViewPager的滑动监听,必须在滑动的时候刷新界面才能看到效果
        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {                //必须刷新页面,才能看到效果
                if (viewPagerContainer != null) {
                    viewPagerContainer.invalidate();
                }
            }

            @Override            public void onPageSelected(int position) {

            }

            @Override            public void onPageScrollStateChanged(int state) {

            }
        });        //设置适配器
        viewPager.setAdapter(new MyPagerAdapter(list));
    }    //初始化显示的图片
    private void initData() {
        list = new ArrayList<>();        for (int i : imgsId) {
            ImageView imageView = new ImageView(MainActivity.this);
            imageView.setScaleType(ImageView.ScaleType.FIT_XY);
            imageView.setImageResource(i);
            list.add(imageView);
        }
    }
}

复制代码

布局文件:

复制代码

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/viewPager_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal"
    android:layerType="software"
    android:clipChildren="false">

    <!--
        一屏显示多张图片的步骤:
        1.配置ViewPager和其父布局的 android:clipChildren属性为”false”.
            (android:clipChildren表示是否限制子View在其范围内,默认为true. 代码设置setClipChildren(false))
            因为如果clipChildren属性设置为true,就表明我们要将children给clip掉,
            就是说对于子元素来说,超出当前view的部分都会被切掉,那我们在这里把它设置成false,
            就表明超出view的部分,不要切掉,依然显示。

        2.设置ViewPager的父布局,android:layerType="software",这样才能显示左右两边的图片,否则不显示为空白

        3.设置幕后item的缓存数目。如果一屏展示的pager数目多的话就需要设置此项。
            viewPager.setOffscreenPageLimit(3); //具体缓存页数看需求

        4.设置页与页之间的间距
            viewPager.setPageMargin(int marginPixls);// setPageMargin表示设置page之间的间距

        5.将ViewPager的父布局触摸事件分发给viewpager,否则只能滑动ViewPager中间的那个view对象

        6.必须在ViewPager的滑动监听中刷新界面才能看到效果
        
        具体代码见MainActivity的onCreate方法两空行之间的代码     -->

    <!--android:layout_marginLeft="50dp"
        android:layout_marginRight="50dp"代表居中显示的pager距离屏幕左右两边的距离-->
    <android.support.v4.view.ViewPager        android:id="@+id/viewPager"
        android:clipChildren="false"
        android:layout_marginLeft="50dp"
        android:layout_marginRight="50dp"
        android:layout_width="match_parent"
        android:layout_height="300dp">
    </android.support.v4.view.ViewPager></LinearLayout>

复制代码

效果如下:

 如果需要切换效果可以看鸿洋大神的:   巧用ViewPager 打造不一样的广告轮播切换效果

https://github.com/hongyangAndroid/MagicViewPager


  • 2017-02-10 16:22:13

    git历史记录查询

    查看提交历史:git log 查看提交历史并显示版本间的差异:git log -p 查看指定历史:git log xxx(sha1值) -p 查看提交历史(指定时间):

  • 2017-02-13 17:50:05

    cURL error 60: SSL certificate problem: unable to get local issuer certificate

    Drupal 8 version uses Guzzle Http Client internally, but under the hood it may use cURL or PHP internals. If you installed PHP cURL on your PHP server it typically uses cURL and you may see an exception with error Peer certificate cannot be authenticated with known CA certificates or error code CURLE_SSL_CACERT (60).

  • 2017-02-16 08:09:01

    HTML中PRE和p的区别

    pre 元素可定义预格式化的文本。被包围在 pre 元素中的文本通常会保留空格和换行符。而文本也会呈现为等宽字体。 <pre> 标签的一个常见应用就是用来表示计算机的源代码。

  • 2017-02-16 15:14:14

    动态加载js和css

    开发过程中经常需要动态加载js和css,今天特意总结了一下常用的方法。