当今的app基本上有两个操作,一个是加载数据 ,一个就是把数据显示到页面上。但如果页面特别的多。就每个页面都要加载数据,就要写 loading 页面。我之前就是用dialog写,抽取出来一个类。哪里需要了就在那里添加以下代码。我发现我大多数时间都在 重复的 添加 loading代码。为此总加班。
请无限参考此文章:http://blog.csdn.net/wanghao200906/article/details/46805085
下面是页面多的时候状态
这要再多点儿 一个一个的写不但代码不好看,自己也累得慌
下面我们就来说一下如何高效的写loading了。
一般页面有四种情况
加载中 :就是滚动页面,后台获取加载的数据,每个页面的数据不同所以就让子类来实现,直接抽象abstract了。
加载失败 :一般都需要点击后重新加载
空页面 :也需要点击后重新加载
加载成功 :显示成功的页面,每个页面都不同所以让子类实现,那必须是抽象的 abstract了
我采取的是每个页面都是framelayout来显示 加载的页面。一共有四个页面。通过加载的数据返回来的 状态 进而让页面显示相应的动画
先屡一下思路
1 先加载三个页面,开始都执行loading页面
2 加载数据, 用到了线程池处理耗时炒作,具体如何访问网络让子类来实现判断数据是否可用
3 数据可用显示 成功界面
数据不可用显示 加载失败页面
数据的list比如为0 加载空页面
下面直接上代码时间:
package com.example.every_text.view; import com.wang.cn.manager.ThreadManager; import com.wang.cn.utils.UIUtils; import android.content.Context; import android.os.SystemClock; import android.util.AttributeSet; import android.view.View; import android.widget.FrameLayout; /** * 先加顺序 load -->showPagerView-->createSuccessView * * @author wanghao * *在子类中 耗时操作放到 load中,然后load返回一个状态,在showPagerView中根据状态选择 显示的页面 *如果装在是成功的。那么久显示 createSuccessView */ public abstract class LoadingPager extends FrameLayout { // 加载默认的状态 private static final int STATE_UNLOADED = 1; // 加载的状态 private static final int STATE_LOADING = 2; // 加载失败的状态 private static final int STATE_ERROR = 3; // 加载空的状态 private static final int STATE_EMPTY = 4; // 加载成功的状态 private static final int STATE_SUCCEED = 5; private View mLoadingView;// 转圈的view private View mErrorView;// 错误的view private View mEmptyView;// 空的view private View mSucceedView;// 成功的view private int mState;// 默认的状态 private int loadpage_empty; private int loadpage_error; private int loadpage_loading; public LoadingPager(Context context, int loading, int error, int empty) { super(context); loadpage_empty = empty; loadpage_error = error; loadpage_loading = loading; init(); } public LoadingPager(Context context, AttributeSet attrs, int defStyle, int loading, int error, int empty) { super(context, attrs, defStyle); loadpage_empty = empty; loadpage_error = error; loadpage_loading = loading; init(); } public LoadingPager(Context context, AttributeSet attrs, int loading, int error, int empty) { super(context, attrs); init(); } private void init() { // 初始化状态 mState = STATE_UNLOADED; // 初始化三个 状态的view 这个时候 三个状态的view叠加在一起了 mLoadingView = createLoadingView(); if (null != mLoadingView) { addView(mLoadingView, new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); } mErrorView = createErrorView(); if (null != mErrorView) { addView(mErrorView, new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); } mEmptyView = createEmptyView(); if (null != mEmptyView) { addView(mEmptyView, new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); } showSafePagerView(); } private void showSafePagerView() { // 直接运行到主线程 UIUtils.runInMainThread(new Runnable() { @Override public void run() { showPagerView(); } }); } private void showPagerView() { // 這個時候 都不為空 mState默認是STATE_UNLOADED狀態所以只顯示 lodaing 下面的 error // 和empty暂时不显示 if (null != mLoadingView) { mLoadingView.setVisibility(mState == STATE_UNLOADED || mState == STATE_LOADING ? View.VISIBLE : View.INVISIBLE); } if (null != mErrorView) { mErrorView.setVisibility(mState == STATE_ERROR ? View.VISIBLE : View.INVISIBLE); } if (null != mEmptyView) { mEmptyView.setVisibility(mState == STATE_EMPTY ? View.VISIBLE : View.INVISIBLE); } if (mState == STATE_SUCCEED && mSucceedView == null) { mSucceedView = createSuccessView(); addView(mSucceedView, new LayoutParams (LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); } if (null != mSucceedView) { mSucceedView.setVisibility(mState == STATE_SUCCEED ? View.VISIBLE : View.INVISIBLE); } } public void show() { // 第一次进来肯定要 转圈的 所以就算是 error和empty 也要让状态是 unload if (mState == STATE_ERROR || mState == STATE_EMPTY) { mState = STATE_UNLOADED; } // 如果是unload 就把状态 变为 loading了 这时候从服务器拿数据 if (mState == STATE_UNLOADED) { mState = STATE_LOADING; TaskRunnable task = new TaskRunnable(); ThreadManager.getLongPool().execute(task); } showSafePagerView(); } /** * 制作界面 * * @return */ protected abstract View createSuccessView(); /** * 处理下载 耗时操作 * * @return */ protected abstract LoadResult load(); /** * 空界面 * * @return */ public View createEmptyView() { if (loadpage_empty != 0) { return UIUtils.inflate(loadpage_empty); } return null; } /** * 失败的页面 * * @return */ public View createErrorView() { if (loadpage_empty != 0) { return UIUtils.inflate(loadpage_error); } return null; } /** * 正在旋转的页面 * * @return */ public View createLoadingView() { if (loadpage_empty != 0) { return UIUtils.inflate(loadpage_loading); } return null; } class TaskRunnable implements Runnable { @Override public void run() { final LoadResult loadResult = load(); SystemClock.sleep(500); UIUtils.runInMainThread(new Runnable() { @Override public void run() { mState = loadResult.getValue(); showPagerView(); } }); } } public enum LoadResult { ERROR(3), EMPTY(4), SUCCESS(5); int value; LoadResult(int value) { this.value = value; } public int getValue() { return value; } } }
下面是如何使用了
package com.wang.cn.base; import com.example.every_text.view.LoadingPager; import com.example.every_text.view.LoadingPager.LoadResult; import com.wang.cn.R; import com.wang.cn.utils.UIUtils; import android.app.Activity; import android.os.Bundle; import android.view.View; import android.view.View.OnClickListener; /** * @author wang * @version 创建时间:2015年7月8日 上午11:31:11 类说明 activity的基类 */ public abstract class BaseActivity extends Activity { public LoadingPager loadingPage; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); loadingPage = new LoadingPager(UIUtils.getContext(), R.layout.loadpage_loading, R.layout.loadpage_error, R.layout.loadpage_empty)//加载了三个页面 { @Override protected LoadResult load() { return BaseActivity.this.load();//传递给子类 } @Override protected View createSuccessView() { return BaseActivity.this.createSuccessView();//传递给子类 } }; // 可以点击 loadingPage.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { loadingPage.show(); } }); // 显示 loading的页面 loadingPage.show(); setContentView(loadingPage); } /** * 刷新页面工程 * * @return */ protected abstract View createSuccessView(); /** * 请求服务器 获取当前状态 * */ protected abstract LoadResult load(); }
逼格的来了 基类调用父类怎样呢
package com.wang.cn; import android.content.Intent; import android.os.SystemClock; import android.view.View; import android.view.View.OnClickListener; import android.widget.TextView; import com.example.every_text.view.LoadingPager.LoadResult; import com.wang.cn.base.BaseActivity; import com.wang.cn.utils.UIUtils; import com.wang.cn.utils.ViewUtils; /** * @author wang * @version 创建时间:2015年7月8日 上午11:31:11 类说明 主函数 */ public class MainActivity extends BaseActivity { // 刷新页面工程 @Override protected View createSuccessView() { View inflate = UIUtils.inflate(R.layout.activity_main); TextView tv=ViewUtils.findViewById(inflate, R.id.textView1); tv.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { Intent intent=new Intent(UIUtils.getContext(),FragmetActivity.class); startActivity(intent); } }); return inflate; } // 刷新页面工程 @Override protected LoadResult load() { SystemClock.sleep(2000); return LoadResult.SUCCESS; } }
怎么样,开始我们说的 加载数据 和显示代码 都搞定了。再也不用因为 写loading儿烦恼了吧。也不用因为 handler获取到好多msg儿烦恼在哪里加了。
代码下载地址:http://download.csdn.net/detail/wanghao200906/8880719(有我使用多年的工具类)
作者: 向前冲org