【问题标题】:Finishing android app完成安卓应用
【发布时间】:2016-03-13 22:53:05
【问题描述】:

我想在按下按钮时完成我的应用程序,但它终止并且 logcat 向我抛出错误。你能看看吗?它说接收者没有注册,但我有。

按钮的代码

stopService(new Intent(MainActivity.this, GPSandSMSService.class));
finish();

GPSandSMSService 代码

public class GPSandSMSService extends Service {
    private IntentFilter mIntentFilter;
    public static final String USER_KEYWORD = "USER_KEYWORD";
    public static final String USER_NUMBER = "USER_NUMBER";
    public static final String HOME_LONGITUDE = "HOME_LONGITUDE";
    public static final String HOME_LATITUDE = "HOME_LATITUDE";
    private final String PROX_ALERT = "com.emmanuilvaresis.oldiefinder.ProximityAlert";
    SharedPreferences prefs;
    Context context;
    double lng, lat, hlat, hlng;
    float radius = 500f; // meters
    long expiration = -1; // do not expire
    protected LocationManager locationManager;
    Location location;
    PackageManager packageManager;
    static int flag = 0;

    @Override
    public void onCreate(){
        context = getApplicationContext();
        prefs = PreferenceManager.getDefaultSharedPreferences(context);

        String svcName = Context.LOCATION_SERVICE;
        locationManager = (LocationManager) getSystemService(svcName);
        Criteria criteria = new Criteria();
        criteria.setAccuracy(Criteria.ACCURACY_FINE);
        criteria.setPowerRequirement(Criteria.POWER_LOW);
        criteria.setAltitudeRequired(false);
        criteria.setBearingRequired(false);
        criteria.setSpeedRequired(false);
        criteria.setCostAllowed(true);
        String provider = locationManager.getBestProvider(criteria, true);
        packageManager = getPackageManager();
        if (packageManager.checkPermission(android.Manifest.permission.ACCESS_FINE_LOCATION, getPackageName())
                == PackageManager.PERMISSION_GRANTED){
            locationManager.requestLocationUpdates(provider, 10 * 1000, 100, locationListener);
            location = locationManager.getLastKnownLocation(provider);
            getCoordinates(location);
        }
        mIntentFilter = new IntentFilter();
        mIntentFilter.addAction("android.provider.Telephony.SMS_RECEIVED");
        registerReceiver(SMSChecker, mIntentFilter);
    }

    private void getCoordinates(Location l){
        if (l != null) {
            lat = l.getLatitude();
            lng = l.getLongitude();
        }

        double templat, templng;
        templat = prefs.getFloat(HOME_LATITUDE, 0);
        templng = prefs.getFloat(HOME_LONGITUDE, 0);
        if((hlat != templat) && (hlng != templng)){
            hlat = templat;
            hlng = templng;
            if((hlat!=0) && (hlng!=0)){
                addProximityAlert(hlat, hlng);
            }
        }
    }

    private final LocationListener locationListener = new LocationListener() {
        @Override
        public void onLocationChanged(Location location) {
            getCoordinates(location);
        }

        @Override
        public void onStatusChanged(String provider, int status, Bundle extras) {
        }

        @Override
        public void onProviderEnabled(String provider) {
        }

        @Override
        public void onProviderDisabled(String provider) {
        }
    };

    @Override
    public void onDestroy(){
        super.onDestroy();
        unregisterReceiver(SMSChecker);
        unregisterReceiver(MapAlertReceiver);
    }



    @Override
    public IBinder onBind(Intent intent) {
        // TODO: Return the communication channel to the service.
        throw new UnsupportedOperationException("Not yet implemented");
    }

    private void addProximityAlert(double latitude, double longitude) {
        if (packageManager.checkPermission(android.Manifest.permission.ACCESS_FINE_LOCATION, getPackageName())
                == PackageManager.PERMISSION_GRANTED){
            Intent intent = new Intent(PROX_ALERT);
            PendingIntent proximityIntent = PendingIntent.getBroadcast(this, 0, intent, 0);
            locationManager.addProximityAlert(latitude, longitude, radius, expiration, proximityIntent);
            IntentFilter filter = new IntentFilter(PROX_ALERT);
            registerReceiver(MapAlertReceiver, filter);
        }
    }

    public final BroadcastReceiver SMSChecker = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            if(action.equals("android.provider.Telephony.SMS_RECEIVED")){
                String msgBody = "";
                SmsMessage[] messages;
                Bundle bundle = intent.getExtras();

                if (bundle != null){
                    Object[] pdus = (Object[]) bundle.get("pdus");
                    messages = new SmsMessage[pdus.length];
                    for (int i = 0; i < pdus.length; i++){
                        messages[i] = SmsMessage.createFromPdu((byte []) pdus[i]);
                        msgBody = messages[i].getDisplayMessageBody().toString();
                    }
                    String msg1;
                    prefs = context.getSharedPreferences("com.emmanuilvaresis.oldiefinder_preferences", Context.MODE_PRIVATE);

                    msg1 = prefs.getString(USER_KEYWORD, "0");
                    if (msgBody.equals(msg1)){
                        String msgText = context.getString(R.string.msgforloc) + " http://google.com/maps/place/" + lat + "," + lng;
                        String number = prefs.getString(USER_NUMBER, "0");
                        try {
                            if ((lat!=0) && (lng!=0) && !(number.equals("0"))){
                                SmsManager smsManager = SmsManager.getDefault();
                                smsManager.sendTextMessage(number, null, msgText, null, null);
                                Toast.makeText(context, context.getString(R.string.messagesent), Toast.LENGTH_SHORT).show();
                            }
                            else {
                                Toast.makeText(context, context.getString(R.string.messagenotsent), Toast.LENGTH_SHORT).show();
                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }

                    }
                }
            }
        }
    };

    public final BroadcastReceiver MapAlertReceiver = new BroadcastReceiver() {

        @Override
        public void onReceive(Context context, Intent intent) {

            final String key = LocationManager.KEY_PROXIMITY_ENTERING;
            final Boolean entering = intent.getBooleanExtra(key, false);
            if (!entering) {
                if (flag == 0) {
                    String msgBody = context.getString(R.string.msgformap);
                    String number = prefs.getString(USER_NUMBER, "0");
                    try {
                        if ((lat != 0) && (lng != 0) && !(number.equals("0"))) {
                            SmsManager smsManager = SmsManager.getDefault();
                            smsManager.sendTextMessage(number, null, msgBody, null, null);
                            Toast.makeText(context, context.getString(R.string.messagesent), Toast.LENGTH_SHORT).show();
                        } else {
                            Toast.makeText(context, context.getString(R.string.messagenotsent), Toast.LENGTH_SHORT).show();
                        }
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                    flag = 1;
                }
            } else {
                flag = 0;
            }
        }
    };
}

LogCat 错误

12-08 22:34:56.714 24399-24399/com.emmanuilvaresis.oldiefinder E/AndroidRuntime: FATAL EXCEPTION: main
     Process: com.emmanuilvaresis.oldiefinder, PID: 24399
     java.lang.RuntimeException: Unable to stop service com.emmanuilvaresis.oldiefinder.GPSandSMSService@1b58cbb2: java.lang.IllegalArgumentException: Receiver not registered: com.emmanuilvaresis.oldiefinder.GPSandSMSService$3@2ce31c80
         at android.app.ActivityThread.handleStopService(ActivityThread.java:3363)
         at android.app.ActivityThread.access$2300(ActivityThread.java:177)
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1552)
         at android.os.Handler.dispatchMessage(Handler.java:102)
         at android.os.Looper.loop(Looper.java:145)
         at android.app.ActivityThread.main(ActivityThread.java:5951)
         at java.lang.reflect.Method.invoke(Native Method)
         at java.lang.reflect.Method.invoke(Method.java:372)
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1400)
         at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1195)
      Caused by: java.lang.IllegalArgumentException: Receiver not registered: com.emmanuilvaresis.oldiefinder.GPSandSMSService$3@2ce31c80
         at android.app.LoadedApk.forgetReceiverDispatcher(LoadedApk.java:822)
         at android.app.ContextImpl.unregisterReceiver(ContextImpl.java:2038)
         at android.content.ContextWrapper.unregisterReceiver(ContextWrapper.java:528)
         at com.emmanuilvaresis.oldiefinder.GPSandSMSService.onDestroy(GPSandSMSService.java:107)
         at android.app.ActivityThread.handleStopService(ActivityThread.java:3346)
         at android.app.ActivityThread.access$2300(ActivityThread.java:177) 
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1552) 
         at android.os.Handler.dispatchMessage(Handler.java:102) 
         at android.os.Looper.loop(Looper.java:145) 
         at android.app.ActivityThread.main(ActivityThread.java:5951) 
         at java.lang.reflect.Method.invoke(Native Method) 
         at java.lang.reflect.Method.invoke(Method.java:372) 
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1400) 
         at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1195) 

【问题讨论】:

  • 根据您的日志,您似乎没有在 onCreate() 中注册 BroadcastReceiver (com.emmanuilvaresis.oldiefinder.GPSandSMSService),而在 onDestroy() 中未注册。
  • @Trinimon,GPSandSMSService 是一项服务。它不是广播接收器。

标签: android terminate receiver


【解决方案1】:

来自您的 LogCat:Receiver not registered

您无法取消注册从未注册过的内容...

您的onCreate只保证注册1个接收者(SMSChecker),

但是你的onDestroy 这样做:

@Override
public void onDestroy(){
    super.onDestroy();
    unregisterReceiver(SMSChecker);
    unregisterReceiver(MapAlertReceiver);
}

因此,MapAlertReceiver 仅在某些时候被注册,当它未注册并且您尝试关闭应用程序时,您崩溃了。

【讨论】:

  • 我已经注册了两个广播接收器。第一个 (SMSChecker) 在 onCreate() 中注册,第二个 (MapAlertReceiver) 在 private void addProximityAlert(double latitude, double longitude) 中注册
  • 是的,但不能保证第二个接收器会被注册 - 看看它之前的所有逻辑!我敢打赌它没有在某些场景中注册
  • 好的,所以在我取消注册第二个接收器之前,我需要先检查它是否已注册。对吗???
  • 非常感谢您的帮助。我试了一下,工作起来就像一个魅力。
【解决方案2】:

你好像在打电话:

unregisterReceiver(MapAlertReceiver);

来自onDestroy,但可能还没有注册。

【讨论】:

    猜你喜欢
    • 2017-08-08
    • 1970-01-01
    • 2014-08-19
    • 2014-02-23
    • 1970-01-01
    • 2012-10-14
    • 1970-01-01
    • 1970-01-01
    • 2012-05-19
    相关资源
    最近更新 更多