欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

一款超酷的Android自定义加载控件

程序员文章站 2024-03-01 13:33:40
在设计应用的时候,我们应该热爱极简主义,简单就是好的,对于很多用户来说,复杂的东西并不受欢迎。 我要实现的是根据不同的情况去显示不同的加载效果,随用随调,效果是借鉴于某...

在设计应用的时候,我们应该热爱极简主义,简单就是好的,对于很多用户来说,复杂的东西并不受欢迎。
我要实现的是根据不同的情况去显示不同的加载效果,随用随调,效果是借鉴于某一项目的效果,我认为有必要提取出来改善封装一下,供以后使用。情况大致分为:加载中、无网络、无数据、加载失败等,这些仅仅就需要一个view 就可以搞定啦!

预览下效果图:

一款超酷的Android自定义加载控件

我们怎么实现这种效果呢
view_loading.xml的布局如下:

<?xml version="1.0" encoding="utf-8"?>
<framelayout xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="match_parent"
 android:layout_height="match_parent">

 <linearlayout
  android:id="@+id/lin_loading"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_gravity="center"
  android:visibility="gone"
  android:orientation="vertical">

  <imageview
   android:id="@+id/img_loading"
   android:layout_width="100dp"
   android:layout_height="100dp"
   android:src="@drawable/loading_animation" />

  <textview
   android:id="@+id/tv_loading"
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:layout_margintop="16dp"
   android:layout_gravity="center_horizontal"
   android:textsize="14sp" />

 </linearlayout>


 <linearlayout
  android:id="@+id/lin_load"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_gravity="center"
  android:gravity="center"
  android:orientation="vertical"
  android:visibility="visible"

  >

  <imageview
   android:id="@+id/iv_load"
   android:layout_width="100dp"
   android:layout_height="100dp"
   android:src="@mipmap/ic_launcher" />

  <textview
   android:id="@+id/tv_load"
   android:layout_width="wrap_content"
   android:layout_gravity="center_horizontal"
   android:layout_height="wrap_content" />


  <button
   android:id="@+id/btn_load"
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:layout_margintop="8dp"
   android:layout_gravity="center_horizontal"
   android:textsize="14sp" />

 </linearlayout>

</framelayout>

从布局来看,我分了两个部分,一个是加载中,另外一个是带有imagview、文字和按钮的布局,有人看到这,就会说,哇靠,这不是很简单吗?根据不同的情况去设置visibility的值就好了啊,没错,原理就是这样。

xhloadingview.java的代码如下:

package com.woyou.loadingdemo.widget;

import android.content.context;
import android.graphics.drawable.animationdrawable;
import android.util.attributeset;
import android.view.layoutinflater;
import android.view.view;
import android.widget.button;
import android.widget.framelayout;
import android.widget.imageview;
import android.widget.linearlayout;
import android.widget.textview;

import com.woyou.loadingdemo.loadingstate;
import com.woyou.loadingdemo.r;


/**
 * created by xiho on 11:21.
 */
public class xhloadingview extends framelayout {

 private context mcontext;
 // 加载中的布局
 private linearlayout mlinearload;
 //其他加载的布局
 private linearlayout mlinearloading;

 private textview mtvloading;

 private textview mtvload;

 private imageview mivloading;

 private imageview mivload;

 private button mbtnload;

 private loadingstate mstate;

 private animationdrawable animation;


 public xhloadingview(context context) {
  super(context);
  mcontext = context;
 }

 public xhloadingview(context context, attributeset attrs) {
  super(context, attrs);
  mcontext = context;
 }

 public xhloadingview(context context, attributeset attrs, int defstyleattr) {
  super(context, attrs, defstyleattr);
  mcontext = context;
 }

 public xhloadingview(context context, attributeset attrs, int defstyleattr, int defstyleres) {
  super(context, attrs, defstyleattr, defstyleres);
  mcontext = context;

 }
 public void build(){
  layoutinflater.from(mcontext).inflate(r.layout.view_loading, this, true);

  mlinearloading = (linearlayout) findviewbyid(r.id.lin_loading);

  mlinearload = (linearlayout) findviewbyid(r.id.lin_load);

  mivloading = (imageview) findviewbyid(r.id.img_loading);

  mivload = (imageview) findviewbyid(r.id.iv_load);

  mtvloading = (textview) findviewbyid(r.id.tv_loading);

  mtvload = (textview) findviewbyid(r.id.tv_load);

  mbtnload = (button) findviewbyid(r.id.btn_load);

  mbtnload.setonclicklistener(new onclicklistener() {
   @override
   public void onclick(view v) {
    setstate(loadingstate.state_loading);
    monretrylistener.onretry();
   }
  });

 }


 @override
 public void setvisibility(int visibility) {
  super.setvisibility(visibility);
  if(view.gone==visibility && mstate==loadingstate.state_loading && animation!=null&&animation.isrunning()){
   animation.stop();
  }
 }

 /**
  * 加载中提示文字
  */
 private string mloadingtext;
 private int mloadingicon;
 public xhloadingview withloadingicon(int resid){
  mloadingicon = resid;
  return this;
 }

 /**
  * 加载数据为空提示文字
  */
 private string mloademptytext;
 private int mloademptyicon;
 public xhloadingview withemptyicon(int resid){
  mloademptyicon = resid;
  return this;
 }

 /**
  * 无网络提示
  */
 private string mloadnonetworktext;
 private int mnonetworkicon;
 public xhloadingview withnoneticon(int resid){
  mnonetworkicon = resid;
  return this;
 }

 private onretrylistener monretrylistener;

 /**
  * 定义重试的的接口
  */
 public interface onretrylistener {
  void onretry();
 }

 public xhloadingview withonretrylistener(onretrylistener monretrylistener){
  this.monretrylistener = monretrylistener;
  return this;
 }

 /**
  * 设置加载的状态
  * @param state
  */
 public void setstate(loadingstate state){
  if(mstate==state){
   return;
  }else if(state==loadingstate.state_loading){
   mlinearloading.setvisibility(visible);
   mlinearload.setvisibility(gone);
  }else if(state!=loadingstate.state_loading){
   mlinearloading.setvisibility(gone);
   mlinearload.setvisibility(visible);
   if(animation!=null && mstate==loadingstate.state_loading)
    animation.stop();
  }
  changestate(state);
 }


 public boolean btnemptyenable = true;
 public boolean btnerrorenable = true;
 public boolean btnnonetworkenable = true;

 public xhloadingview withbtnnonetennable(boolean ennable) {
  btnnonetworkenable = ennable;
  return this;
 }

 public xhloadingview withbtnerrorennable(boolean ennable) {
  btnerrorenable = ennable;
  return this;
 }


 public xhloadingview withbtnemptyennable(boolean ennable) {
  btnemptyenable = ennable;
  return this;
 }

 /**
  * 改变状态
  * @param state
  */
 private void changestate(loadingstate state) {
  switch (state) {
   //加载中
   case state_loading:
    mstate = loadingstate.state_loading;
    mivloading.setimageresource(mloadingicon);
    mtvloading.settext(mloadingtext);
    if (animation == null) {
     animation = (animationdrawable) mivloading.getdrawable();
    }
    if (animation != null)
     animation.start();
    break;
   //数据为空
   case state_empty:
    mstate = loadingstate.state_empty;
    mivload.setimageresource(mloademptyicon);
    mtvload.settext(mloademptytext);
    if (btnemptyenable) {
     mbtnload.setvisibility(visible);
     mbtnload.settext(btn_empty_text);
    } else {
     mbtnload.setvisibility(gone);
    }
    break;
   //加载失败
   case state_error:
    mstate = loadingstate.state_error;
    mivload.setimageresource(merrorico);
    mtvload.settext(mloaderrortext);
    if (btnerrorenable) {
     mbtnload.setvisibility(visible);
     mbtnload.settext(btn_error_text);
    } else {
     mbtnload.setvisibility(gone);
    }
    break;
   //无网络
   case state_no_net:
    mstate = loadingstate.state_no_net;
    mivload.setimageresource(mnonetworkicon);
    mtvload.settext(mloadnonetworktext);
    if (btnnonetworkenable) {
     mbtnload.setvisibility(visible);
     mbtnload.settext(btn_nonet_text);
    } else {
     mbtnload.setvisibility(gone);
    }
    break;
  }

 }


 /**
  * 后台或者本地出现错误提示
  */
 private string mloaderrortext;
 private int merrorico;

 public xhloadingview witherrorico(int resid) {
  merrorico = resid;
  return this;
 }

 /**
  * 加载空数据
  * @param resid
  * @return
  */
 public xhloadingview withloademptytext(int resid) {
  mloademptytext = getresources().getstring(resid);
  return this;
 }

 public xhloadingview withloademptytext(string mloademptytext) {
  this.mloademptytext = mloademptytext;
  return this;
 }

 /**
  * 无网络时候加载文字
  * @param resid
  * @return
  */
 public xhloadingview withloadnonetworktext(int resid) {
  mloadnonetworktext = getresources().getstring(resid);
  return this;
 }

 public string btn_empty_text = "重试";
 public string btn_error_text = "重试";
 public string btn_nonet_text = "重试";

 /**
  * 数据为空的button的文字提示
  * @param text
  * @return
  */
 public xhloadingview withbtnemptytext(string text) {
  this.btn_empty_text = text;
  return this;
 }

 /**
  * 加载错误的button的文字提示
  * @param text
  * @return
  */
 public xhloadingview withbtnerrortext(string text) {
  this.btn_error_text = text;
  return this;
 }

 /**
  * 加载错误的文字提示
  * @param resid
  * @return
  */
 public xhloadingview withloaderrortext(int resid) {
  this.mloaderrortext = getresources().getstring(resid);
  return this;
 }
 public xhloadingview withloaderrortext(string mloadederrortext) {
  this.mloaderrortext = mloadederrortext;
  return this;
 }

 /**
  * 加载无网络的button的文字提示
  * @param text
  * @return
  */
 public xhloadingview withbtnnonettext(string text) {
  this.btn_nonet_text = text;
  return this;
 }

 /**
  * 加载没有网路的文字提示
  * @param mloadednonettext
  * @return
  */
 public xhloadingview withloadnonetworktext(string mloadednonettext) {
  this.mloadnonetworktext = mloadednonettext;
  return this;
 }

 public xhloadingview withloadingtext(int resid) {
  this.mloadingtext = getresources().getstring(resid);
  return this;
 }

 public xhloadingview withloadingtext(string mloadingtext) {
  this.mloadingtext = mloadingtext;
  return this;
 }

}

针对不同的情况作了不同的处理,然后我们在需要的activity调用。

 private xhloadingview mloadingview;

 @override
 protected void oncreate(bundle savedinstancestate) {
  super.oncreate(savedinstancestate);
  setcontentview(r.layout.activity_display);
  mloadingview = (xhloadingview) findviewbyid(r.id.lv_loading);
  mloadingview.withloademptytext("≥﹏≤ , 啥也木有 !").withemptyicon(r.drawable.disk_file_no_data).withbtnemptyennable(false)
     .witherrorico(r.drawable.ic_chat_empty).withloaderrortext("(῀( ˙᷄ỏ˙᷅ )῀)ᵒᵐᵍᵎᵎᵎ,我家程序猿跑路了 !").withbtnerrortext("臭*!!!")
     .withloadnonetworktext("你挡着信号啦o( ̄ヘ ̄o)☞ᗒᗒ 你走").withnoneticon(r.drawable.ic_chat_empty).withbtnnonettext("网弄好了,重试")
     .withloadingicon(r.drawable.loading_animation).withloadingtext("加载中...").withonretrylistener(new xhloadingview.onretrylistener() {
    @override
    public void onretry() {
     snackbarutil.show(mloadingview,"已经在努力重试了",0);
    }
   }).build();
  }

........

 //加载中
  mloadingview.setvisibility(view.visible);
  mloadingview.setstate(loadingstate.state_loading);

 //空数据
  mloadingview.setvisibility(view.visible);
  mloadingview.setstate(loadingstate.state_empty)
 //无网络
  mloadingview.setvisibility(view.visible);
  mloadingview.setstate(loadingstate.state_no_net);

 //加载错误
  mloadingview.setvisibility(view.visible);
  mloadingview.setstate(loadingstate.state_error);

.......


 }

上面我是为了展示不同的效果,所以写了几个点击事件呢,实际中不是这样的,初始化过后,在需要的地方调用ok, 源码中注释详细,就不用再做过多的解释了吧!

完整代码:xhloadingview

作者:xuhao
qq:504105930
转载请注明出处:http://blog.csdn.net/u011974987/article/details/51455333

以上就是本文的全部内容,希望对大家学习android软件编程有所帮助。