經過 ANE(Adobe Native Extension) 啓動Andriod服務 推送消息(二)

着手改造以前,有興趣能夠閱讀下官方文檔:http://help.adobe.com/zh_CN/air/extensions/index.htmlhtml

新建工程 NavService 並建立包 nav.wenbo.service, 這些均可以自定義,但要記住你的包名。java

注意最下方那個jar包,這個是必需的,打開項目的構建目錄(buildPath),引用外部jar包, 目錄在你在Flex sdk目錄下android

 %FlexSDK%\4.x.x\lib\android\FlashRuntimeExtensions.jarapp

個人本地目錄是:F:\Program Files\Adobe\Adobe Flash Builder 4.7\sdks\4.6.0\lib\android\FlashRuntimeExtensions.jaride

首先建立air調用的入口類 ServiceExtension 這個類必需在ane包裏面的extension.xml裏指定(後面會介紹)ui

package nav.wenbo.service;

import android.content.Context;
import android.content.Intent;
import android.util.Log;

import com.adobe.fre.FREContext;
import com.adobe.fre.FREExtension;

public class ServiceExtension implements FREExtension {
    public static final String TAG = "ServiceExtension";
    public static Context appContext;
    public static FREContext extensionContext;
    public static String Msg = "none";
    
    @Override
    public FREContext createContext(String contextType) {
        // TODO Auto-generated method stub
        return new ServiceExtensionContext();
    }

    @Override
    public void dispose() {
        // TODO Auto-generated method stub
        Log.d(TAG, "Extension disposed.");
    }

    @Override
    public void initialize() {
        // TODO Auto-generated method stub
        Log.d(TAG, "Extension initialized.");
    }

}

 

ServiceExtension中關鍵是 createContext 方法,這個方法返回一個可連通air及本地Java代碼的上下文。並在該上下文中定義可供air調用的方法this

下面是ServiceExtensionContext類spa

package nav.wenbo.service;

import java.util.HashMap;
import java.util.Map;

import nav.wenbo.service.functions.InitFunction;
import nav.wenbo.service.functions.SendFunction;
import nav.wenbo.service.functions.StartFunction;

import android.util.Log;

import com.adobe.fre.FREContext;
import com.adobe.fre.FREFunction;

public class ServiceExtensionContext extends FREContext {
    public static final String TAG = "ServiceExtensionContext";
    @Override
    public void dispose() {
        // TODO Auto-generated method stub
        Log.d(TAG,"Context disposed.");
    }

    @Override
    public Map<String, FREFunction> getFunctions() {
        Map<String, FREFunction> functions = new HashMap<String, FREFunction>();
        functions.put("init", new InitFunction());
        functions.put("service", new StartFunction());
        functions.put("send", new SendFunction());
        
        return functions;
    }

}

 

functions.put至關注冊調用邏輯的調用名, 這裏把你全部調用方法都填上。init 用於初始化上下文,service用來啓動和關閉服務, send用於發送消息。 在編寫對應方法以前,code

先把上一節的Backgroundservice 移植過來xml

package nav.wenbo.service;

import com.wenbo.navservice.R;

import android.app.Activity;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.util.Log;

public class NotificationService extends Service {
    private NotificationManager notificationMgr;
    private Thread mthr;
    private int mCount=0;
    private Boolean mSend=true;
    
    @Override
    public void onCreate() {
        super.onCreate();
        notificationMgr = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        displayNotificationMessage("starting Background Service");
        
        if(mthr == null || mSend == false) 
        {
            mSend=true;
            mthr = new Thread(null, new ServiceWorker(), "BackgroundSercie");
            mthr.start();
        }
        if(null != ServiceExtension.extensionContext) ServiceExtension.extensionContext.dispatchStatusEventAsync("start", "1");
    }
    
    @Override
    public void onDestroy()
    {
        super.onDestroy();
        mSend = false;
    }
    
    @Override
    public IBinder onBind(Intent intent) {
        // TODO Auto-generated method stub
        return null;
    }

    class ServiceWorker implements Runnable {
        @Override
        public void run() {
            // do background processing here.....
            // stop the service when done...
            // BackgroundService.this.stopSelf()
            while(mSend)
            {
                try{
                    Thread.sleep(1000);
                    Log.d("", "runnable" + mCount);
                    displayNotificationMessage(ServiceExtension.Msg);
                }
                catch (InterruptedException e)
                {
                    e.printStackTrace();
                }
            }
        }
    }
    
    private void displayNotificationMessage(String message) {
        if(message == "none") return;
        
        Log.d("", message);
        mCount++;
        Notification notification = new Notification(R.drawable.ic_launcher, message,
                System.currentTimeMillis());
        
        PendingIntent contentIntent = PendingIntent.getActivity(this, 0, new Intent(this, Activity.class), 0);
        
        notification.setLatestEventInfo(this, "女神之賤", message, contentIntent);
        
        notificationMgr.notify(1000, notification);
    }
}

 

這裏改動很小,發送的消息從ServiceExtension類裏面取,當message != none時顯示該通知,另ServiceExtension.extensionContext.dispatchStatusEventAsync 是用來給air程序發消息, 在air中監聽StatusEvent.STATUS 能夠捕獲這條消息並獲取對應參數。在這裏用處是通知服務啓動成功。

下面就剩下實際調用的方法了。

首先是初始化上下文,這裏主要是ServiceExtension.extensionContext 主要用於往air發消息。

package nav.wenbo.service.functions;

import nav.wenbo.service.ServiceExtension;

import android.content.Context;
import android.util.Log;

import com.adobe.fre.FREContext;
import com.adobe.fre.FREFunction;
import com.adobe.fre.FREObject;

public class InitFunction implements FREFunction {
    public static final String TAG = "InitFunction";
    @Override
    public FREObject call(FREContext context, FREObject[] args) {
        ServiceExtension.extensionContext = context;
        
        Context appContext = context.getActivity().getApplicationContext();
        ServiceExtension.appContext = appContext;
        
        
        Log.i(TAG, "in init");
        
        return null;
    }

}

這裏注意了,由於咱們沒有獨立的Android入口文件,咱們 只能從 FREContext.getActivity() 來取得咱們所需的上下文,並用這上下文啓動咱們的服務,這是跟前一節例子最大不一樣的地方。

執行後通知air:context.dispatchStatusEventAsync("start", "2");

package nav.wenbo.service.functions;

import nav.wenbo.service.NotificationService;
import android.content.Context;
import android.content.Intent;

import com.adobe.fre.FREContext;
import com.adobe.fre.FREFunction;
import com.adobe.fre.FREObject;

public class StartFunction implements FREFunction {

    @Override
    public FREObject call(FREContext context, FREObject[] args) {
        Context appContext = context.getActivity().getApplicationContext();
        Boolean isStart=true;
        try {
            isStart = args[0].getAsBool();
        } catch (Exception e) {
            
        }
        if(isStart) context.getActivity().startService(new Intent(appContext, NotificationService.class));
        else context.getActivity().stopService(new Intent(appContext, NotificationService.class));
        
        context.dispatchStatusEventAsync("start", "2");
        return null;
    }

}

 

最後這個最簡單,僅僅設置下所要推送的消息.

package nav.wenbo.service.functions;

import nav.wenbo.service.ServiceExtension;

import com.adobe.fre.FREContext;
import com.adobe.fre.FREFunction;
import com.adobe.fre.FREObject;

public class SendFunction implements FREFunction {

    @Override
    public FREObject call(FREContext context, FREObject[] args) {
        // TODO Auto-generated method stub
        String msg="none";
        try
        {
            msg = args[0].getAsString();
        }
        catch(Exception e)
        {
            
        }
        ServiceExtension.Msg = msg;
        return null;
    }

}

 

 

作完這些,並設置好權限後,把項目導出jar包, 命名爲 libAndroidServiceLib.jar

下一節我將介紹air中跟此jar包對接。

相關文章
相關標籤/搜索