原文出自:方杰| http://fangjie.info/?p=62 转载请注明出处
提前声明的是,我是按照Ivan的这套教程学下来的。
首先,对于任何应用我们都需要建立一套消息处理机制,就是当用户在UI界面上点击了什么,你应该做出什么样的处理,处理完成之后又要将结果 反馈给用户,显示在UI界面上。简而言之:主框架在这里主要是搭建起一个异步消息处理机制,UI线程中发送消息,service处理消息,处理完了调用UI线程实例更新UI界面。先看看这里是怎么处理的,如下图:
解析:在程序启动时开启MainService,MainService中新开个线程来不断循环的监听Tasks中是否有任务。当UI界面的主线程接收到用户的某个操作时,就会调用MainService.newTask()将这个任务放进Tasks中,并且把Activity放进Activities。这样在MainService中的第二线程就会监听到这个任务,就会调用MainService.doTask(),当做完处理后MainService第二线程就会向MainService主线程发送Handler消息,将处理得一些数据发送到Acitivity中,然后调用的Activity.refresh()就能刷新页面了。这里要强调的是UI层的Activity都要实现IWeiboActivity这样一个接口,实现他的refresh(),init()两个抽象方法。
MainService.java
package com.fangjie.weibo.logic; import java.util.ArrayList; import java.util.LinkedList; import java.util.List; import java.util.Queue; import android.app.Activity; import android.app.Service; import android.content.Intent; import android.os.Handler; import android.os.IBinder; import android.os.Message; import android.util.Log; import com.fangjie.weibo.bean.*; import com.fangjie.weibo.db.DBUserInfo; import com.fangjie.weibo.ui.IWeiboAcitivity; import com.fangjie.weibo.util.GetUserInfo; import com.weibo.sdk.android.Oauth2AccessToken; public class MainService extends Service implements Runnable{ private static Queue<Task> tasks=new LinkedList<Task>(); private static ArrayList<Activity> appActivities=new ArrayList<Activity>(); private boolean isRun; private Handler handler; @Override public void onCreate() { // TODO Auto-generated method stub /** * 在MainService中开启第二线程来处理任务 * 主要是不断监听Tasks堆栈,从Tasks中处理task */ isRun=true; Thread thread =new Thread(this); thread.start(); super.onCreate(); /** * 主要是获取从MainService第二线程(doTask)中获取处理完任务的数据 * 并通知更新UI界面 */ handler =new Handler(){ public void handleMessage(Message msg) { IWeiboAcitivity activity=null; switch(msg.what) { case Task.WEIBO_LOGIN: activity=(IWeiboAcitivity)getActivityByName("LoginActivity"); activity.refresh(Task.WEIBO_LOGIN,msg.obj); break; case Task.GET_USERINFO_BY_TOKEN: break; case Task.GET_USERINFO_IN_LOGIN: break; default: break; } } }; } @Override public void run() { // TODO Auto-generated method stub while(isRun) { if(!tasks.isEmpty()) { doTask(tasks.poll()); } } } /** * UI层向MainService中发送任务task * UI层调用,所以static * @param task */ public static void newTask(Task task) { tasks.add(task); } /** * UI层向MainService中发送任务的同时,同样要发送自己Activity, * 以便在MainService中调用refresh(); * @param task */ public static void addActivty(Activity activity) { appActivities.add(activity); } /** * UI层中有向MainService中传递Activity,在任务结束后(refresh),应去除该Activity,防止混淆! * @param activity */ public static void reMoveActivty(Activity activity) { appActivities.remove(activity); } /** * 通过name获取新开任务时传递过来的Activity实例 * @param name * @return */ public Activity getActivityByName(String name) { if(!appActivities.isEmpty()) { for(Activity activity:appActivities) { if(activity.getClass().getName().indexOf(name)>0) { return activity; } } } return null; } /** * 处理Tasks堆栈中的task * @param task */ public void doTask(Task task) { Message msg=handler.obtainMessage(); msg.what=task.getTaskID(); switch(task.getTaskID()) { //登录操作 case Task.WEIBO_LOGIN: System.out.println("login successful"); msg.obj="登录成功"; break; //通过access_token获取用户信息,并保存到数据库操作 case Task.GET_USERINFO_BY_TOKEN: msg.obj="成功"; break; //登录界面获取用户信息显示操作 case Task.GET_USERINFO_IN_LOGIN: msg.obj="成功"; break; default : break; } handler.sendMessage(msg); } @Override public IBinder onBind(Intent intent) { // TODO Auto-generated method stub return null; } }
再看看我的工程文件架构,如下图:
Task.java是任务的实体类,包含任务的ID,任务的参数成员变量,IWeiboActivity就是所有Activity要实现的接口。