Android Service使用误区

来源:互联网 发布:windows正版激活工具 编辑:程序博客网 时间:2024/05/16 18:24

做应用的都应该熟悉Service这个类。Android四大组件之一。Activity的反面,没有界面,后台运行,但是它仍然是运行在主界面的。Activity退出时,Service仍可以继续执行。Service常见用于播放器,Service + Thread + Notification的模式很常见。Service也可以用来远程调用。

有一次遇到一位同事写的定位代码,他使用的service,利用service的特性,在需要定位的时候启动service进行定位。实际使用过程中,会出现这样的情况:定位工作不执行。刚开始没注意,一直以为是百度地图的问题。后来打印Log,发现Service被recycle了,因为内存吃紧,service被回收了。导致这部分工作出了问题。在这里提醒大家下,Service不一定会一直在后台执行,当内存不够时,会触发service回收,等到适当的时候,再根据service中onStartCommand( Intent intent, int flags, int startId);中的flag值进行重启动策略。

public class LocationService extends Service {    private static final String TAG = LocationService.class.getSimpleName();    private ServiceHandler mServiceHandler;    private Looper mServiceLooper;    public  LocationClient locationClient;    private final int UPDATE_TIME = 3*1000;    @Override    public void onCreate() {         super.onCreate();        L.log(AppInterface.LOG_DEBUG , 0 , TAG, "onCreate");        HandlerThread thread = new HandlerThread(TAG,Process.THREAD_PRIORITY_BACKGROUND);        thread.start();        mServiceLooper = thread.getLooper();        mServiceHandler = new ServiceHandler(mServiceLooper);    }    /**     * 开始定位     * @param context     */    public static void startLocation(Context context){        Intent intent = new Intent(context,LocationService.class);        intent.setAction("start_location");        context.startService(intent);    }    /**     * 停止定位     * @param context     */    public static void stopLocation(Context context){        Intent intent = new Intent(context,LocationService.class);        intent.setAction("stop_location");        context.startService(intent);    }    /**     * @param context     */    public static void requestLocation(Context context){        Intent intent = new Intent(context,LocationService.class);        intent.setAction("request_location");        context.startService(intent);    }    @Override    public IBinder onBind(Intent intent) {        // TODO Auto-generated method stub        return null;    }    private final class ServiceHandler extends Handler {        public ServiceHandler(Looper looper) {            super(looper);        }        @Override        public void handleMessage(Message msg) {            Intent intent = (Intent) msg.obj;            if (intent != null) {                String action = intent.getAction();                if("start_location".equals(action)){                     startLocation();                }else if("stop_location".equals(action)){                     stopLocation();                }else if("request_location".equals(action)){                     requestLocation();                }            }            }             }    @Override    public int onStartCommand(final Intent intent, int flags, int startId) {        if(null != intent){            Message msg = mServiceHandler.obtainMessage();            msg.arg1 = startId;            msg.obj = intent;            mServiceHandler.sendMessage(msg);            //被回收时,同时将intent传递进来,重启            return Service.START_REDELIVER_INTENT;        }        return super.onStartCommand(intent, flags, startId);    }    private void initLocationConfig(){        locationClient = new LocationClient(this);          LocationClientOption option = new LocationClientOption();          option.setOpenGps(true);            option.setAddrType("all");        option.setPriority(LocationClientOption.GpsFirst);         option.setCoorType(BDLocation.BDLOCATION_GCJ02_TO_BD09LL);//百度地图的二次加密          //option.setCoorType(BDLocation.BDLOCATION_BD09LL_TO_GCJ02);        option.setLocationMode(LocationClientOption.LocationMode.Hight_Accuracy);//高精度定位        option.setProdName(getString(R.string.app_name));                             option.setScanSpan(UPDATE_TIME);         option.setIsNeedAddress(false);        option.disableCache(false);//不使用缓存定位        locationClient.setLocOption(option);        locationClient.registerLocationListener(new MyBDLocationListener());    }    private void startLocation(){        if(locationClient==null){            initLocationConfig();        }        if(!locationClient.isStarted()){            locationClient.start();        }        locationClient.requestLocation();        L.log(AppInterface.LOG_DEBUG, 0 , TAG , "the location client is start ----------");    }     private void stopLocation(){         if(locationClient!=null){            if(locationClient.isStarted()){                locationClient.stop();                L.log(AppInterface.LOG_DEBUG, 0 , TAG , "the location client is stop ----------");            }        }    }    private void requestLocation(){        if(locationClient!=null){            if(!locationClient.isStarted()){                locationClient.start();            }            locationClient.requestLocation();            L.log(AppInterface.LOG_DEBUG, 0 , TAG ,"the location client is request ----------");        }    }    private class MyBDLocationListener implements BDLocationListener{        @Override          public void onReceiveLocation(BDLocation location) {              L.log(AppInterface.LOG_DEBUG, 0 , TAG ,"onReceiveLocation ----------");            if (location == null) {                 locationClient.start();                   locationClient.requestLocation();                return;              }             L.log(AppInterface.LOG_DEBUG, 0 , TAG , "type = " + location.getLocType() + "(gps type = " + BDLocation.TypeGpsLocation  + "), latitude = " + location.getLatitude() + " , longitude = " + location.getLongitude() + " , speed = " + location.getSpeed() + " , satelite = " + location.getSatelliteNumber()+",radius = " + location.getRadius());            double latitude = location.getLatitude();             double longitude = location.getLongitude();            if((latitude >0 && latitude < 0.0000001) || (longitude >0 && longitude < 0.0000001)){                //非法的经纬度                return ;            }            String address = "";            boolean isLocationValid = false;            if(location.getLocType() == BDLocation.TypeNetWorkLocation){                if(CheckUtil.isNetworkAvailable(LocationService.this)){                    isLocationValid = true;                    address = location.getAddrStr();                }            } else if(location.getLocType() == BDLocation.TypeGpsLocation){                isLocationValid = true;                address = location.getAddrStr();            }            //对位置进行传递,在LocationCallBack中进行回调            LocationCallBack.getInstance(LocationService.this).setLocationData(location);        }    }    @Override    public void onDestroy() {        super.onDestroy();        stopLocation();        L.log(AppInterface.LOG_DEBUG , 0 , TAG, "onDestroy");    }}
0 0
原创粉丝点击