自定义广告Banner条

转载请注明出处:http://blog.csdn.net/qq_26869239/article/details/53378024

经常看到App里面都有广告条这个功能,因为三方框架很多,但是在学习了自定义控件后,就自己突发奇想自己写了一个出来。
觉得要简单简单再简单为好。毕竟是自己写的,觉得用起来还是喜欢一句话为好。
1.先来看看最终效果吧

private void setBanner(String[] bannerUrl) {
        if (bannerUrl.length == 0) {
            return;
        }
        if (isClearBannerHandler) {//如果不是第一次,就需要停止自定义里面的Handler
            vr_banner.removeHandler();
        }

        vr_banner.setViewPagerImages(getActivity().getApplicationContext(), bannerUrl);
    }

是不是很简单呀,就是一个方法setViewPagerImages,里面传的参数,可以是本地图片,也可以是网络Url地址的一个集合。

接下来来看,具体的实现。
具体的就是添加一个类继承RelativeLayout,然后动态添加ViewPager和RadioButton上去

/**
     * 初始化函数 这里只需要初始化一个viewPager出来
     *
     * @param context      上下文
     * @param attrs
     * @param defStyleAttr
     */
    private void init(Context context, AttributeSet attrs, int defStyleAttr) {
        viewPager = addViewPager(context);

        //把这个viewPager添加到这个自定义布局上面
        addView(viewPager);

        // 要进行联动,所以这里要给viewPager添加一个监听器
        ViewPagerAndRadioGroupListener listener = new ViewPagerAndRadioGroupListener();
        viewPager.addOnPageChangeListener(listener);

    }

添加ViewPager的方法很简单,相信大家都会

 /**
     * 初始化一个ViewPager
     *
     * @param context 上下文
     * @return 写好的一个ViewPager控件
     */
    @NonNull
    private ViewPager addViewPager(Context context) {
        //首先先来一个ViewPager控件
        ViewPager viewPager = new ViewPager(context);

        //设置一下位置
        LayoutParams vParams = new LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);

        viewPager.setLayoutParams(vParams);
        //加进布局

        return viewPager;
    }

然后因为RadioButton个数应该是根据传入的图片个数来决定的,所以我写了一个方法,可以把数据传过来,就是
public void setViewPagerImages(Context context, String[] imagePaths, String[] showWebUrls,OnItemClickListener fetchListener)这个方法
参数说明一下,第一个参数不用说了,第二个参数是网络图片Url的一个地址集合,第三个参数是点击跳转的一个Url集合,第四个参数是一个回调接口,把点击效果调出去,一个图片对应一个网址,或者一个事件,我把点击的位置和地址都回调了出来,至于跳转Activity还是Url就看个人喜好啦。

//自己写一个点击事件的接口
    public interface OnItemClickListener {
        void onItemClick(int position, String webUrl);
    }

    public void setOnItemClickListener(OnItemClickListener listener) {
        this.listener = listener;
    }

下面来大概写一下RadioButton的个数添加,根据传入的网址个数来动态添加

/**
     * 初始化RadioButton
     *
     * @param context 上下文
     * @return 写好的一个radioGroup控件
     */
    private RadioGroup addRadioGroup(Context context) {
        //再来一个RadioGroup
        RadioGroup radioGroup = new RadioGroup(context);
        LayoutParams rgParams = new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);

        //设置位置,在viewPager的下中位置
        rgParams.addRule(ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
        rgParams.addRule(CENTER_HORIZONTAL, RelativeLayout.TRUE);
        radioGroup.setLayoutParams(rgParams);

        //设置一下radioGroup的子控件排列顺序
        radioGroup.setOrientation(LinearLayout.HORIZONTAL);

        //在来三个RadioButton
        RadioButton rb = null;
        RadioGroup.LayoutParams rbParams;

        //这里就是来。添加radioButton
        if (str != null) {
            for (int i = 0; i < str.length; i++) {
                rb = new RadioButton(context);

                //添加一个自定义的背景
                rb.setButtonDrawable(R.drawable.selector_radiobutton_fill_empty);
                //间隔太近了
                rbParams = new RadioGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
                rbParams.setMargins(8, 5, 8, 8);
                rb.setLayoutParams(rbParams);

                radioGroup.addView(rb);
            }
        }

        if (reStr != null) {
            for (int i = 0; i < reStr.length; i++) {
                rb = new RadioButton(context);

                //添加一个自定义的背景
                rb.setButtonDrawable(R.drawable.selector_radiobutton_fill_empty);
                //间隔太近了
                rbParams = new RadioGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
                rbParams.setMargins(5, 5, 5, 5);
                rb.setLayoutParams(rbParams);

                radioGroup.addView(rb);
            }
        }
        return radioGroup;

    }

因为博主能力有限,所以封装的时候都写在了一起,O(∩_∩)O哈哈~

然后要让Banner条滚动起来,我用了Handler,但是Handler可能会造成内存泄漏,无意间我在网上看到了一个WeakHandler,有兴趣的童鞋可以去搜搜开,避免内存泄漏的,我就用了这个Handler

 //自己滚动起来
    //Handler handler = new Handler();
    WeakHandler handler = new WeakHandler();
    int currentItemId;
    Runnable runnable = new Runnable() {
        @Override
        public void run() {
            if (isWebImagePath) {
                //发送当前位置
                currentItemId = viewPager.getCurrentItem() + 1 % str.length;
            } else {
                currentItemId = viewPager.getCurrentItem() + 1 % reStr.length;
            }
            //设置一下
            viewPager.setCurrentItem(currentItemId);
            handler.postDelayed(runnable, 4000);

        }
    };

但是后来调用的时候也发现,因为setViewPagerImages这个方法,因为是写在网络请求里面的,当刷新的时候,由于内部的Handler会多次创建,会导致出现一些小问题,所以我又加了一个清除Handler的方法:

**
     * 停止线程
     */
    public void removeHandler(){
        if(handler != null && runnable != null) {
            handler.removeCallbacks(runnable);
            ((RadioButton) (radioGroup.getChildAt(viewPager.getCurrentItem() % str.length))).setChecked(false);
        }
    }

所以在请求数据的时候,第二次开始的时候判断一下,要清除Handler,给一个boolean值判断即可,清楚以后在调用setViewPagerImages就没有问题了,

/**
     * 模拟设置广告条
     */
    private void setBanner(String[] bannerUrl) {
        if (bannerUrl.length == 0) {
            return;
        }
        if (isClearBannerHandler) {//如果不是第一次,就需要停止自定义里面的Handler
            vr_banner.removeHandler();
        }

        vr_banner.setViewPagerImages(getActivity().getApplicationContext(), bannerUrl);
    }

毕竟能力有限,这也是自己动手写的第一个自定义的View,大家-,-有需要的就去下来用吧。
具体用法:
1.添加Viewpager_RadioButton_View.java到自己的项目中,
2.添加
selector_radiobutton_fill_empty,shape_radiobutton_empty,shape_radiobutton_fill三个文件到res/drawable资源下面,

3.gradle里面添加WeakHanlder和Picasso的三方:

    compile 'com.squareup.picasso:picasso:2.5.2'
    repositories {
        maven {
            repositories {
                url 'https://oss.sonatype.org/content/repositories/releases/'
            }
        }
    }

    dependencies {
        compile 'com.badoo.mobile:android-weak-handler:1.1'
    }

4.最后别忘记开权限啦

<uses-permission android:name="android.permission.INTERNET"/>

。。
5. 然后在xml文件中直接添加这个自定义控件:

 <com.jimmy.banner.Viewpager_RadioButton_View
        android:id="@+id/banner"
        android:layout_width="match_parent"
        android:layout_height="150dp"
        />

直接用啦

public class MainActivity extends AppCompatActivity {
    private Viewpager_RadioButton_View banner;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        banner = (Viewpager_RadioButton_View) findViewById(R.id.banner);

        banner.setViewPagerImages(
                getApplicationContext(),
                new String[]{"http://img5.imgtn.bdimg.com/it/u=2748753796,1780454549&fm=23&gp=0.jpg",
                                "http://img5.imgtn.bdimg.com/it/u=2748753796,1780454549&fm=23&gp=0.jpg"});
    }
}

效果:
这里写图片描述

最后附上源码地址:
http://download.csdn.net/detail/qq_26869239/9695970

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值