BroadcastReceiver не читает сохраненное значение из SharedPreferences - PullRequest
0 голосов
/ 12 декабря 2010

В моем приложении есть широковещательный приемник, который включает GPS при получении заданной строки текста.В методе onLocationChanged я хочу передать данные GPS и значение из моих общих настроек потоку в строке.
У меня есть запись потока в журнал, и я могу видеть все значения GPS в строке, кроме последнего значенияиз моих общих настроек просто отображается как prefPhoneNum, которому я инициализировал строку в начале класса получателя.У меня есть тот же код для чтения prefPhoneNum из общих настроек в основном классе, и он работает там, кто-нибудь может увидеть, что я могу делать не так?

public class SmsReceiver extends BroadcastReceiver implements LocationListener
{
     LocationManager lm;
     LocationListener loc;
     public SharedPreferences sharedpreferences;    
     public static final String US = "usersettings";
     public String prefPhoneNum = "prefPhoneNum";

    @Override
    public void onReceive(Context context, Intent intent) 
    {    
        sharedpreferences = context.getSharedPreferences(US, Context.MODE_PRIVATE);
        prefPhoneNum = sharedpreferences.getString("prefPhoneNum" , "");
        lm = (LocationManager)context.getSystemService(Context.LOCATION_SERVICE);
        loc = new SmsReceiver();

        //---get the SMS message passed in---
        Bundle bundle = intent.getExtras();   
        SmsMessage[] msgs = null;
        String str = ""; 

        if (bundle != null)
        {
            //---retrieve the SMS message received---
            Object[] pdus = (Object[]) bundle.get("pdus");
            msgs = new SmsMessage[pdus.length];            
            for (int i=0; i<msgs.length; i++)
            {
                msgs[i] = SmsMessage.createFromPdu((byte[])pdus[i]);
                str += msgs[i].getMessageBody().toString() + "\n";        
            } 

             Toast.makeText(context, str, Toast.LENGTH_SHORT).show();     //Display SMS

            if ((msgs[0].getMessageBody().toString().equals("Enable")) ||
                    (msgs[0].getMessageBody().toString().equals("enable")))
            {             
                enableGPS();
            }    
            else {  /* Do Nothing*/ }
        }              
    }

    public void enableGPS() {  
      //new CountDownTimer(10000, 1000) {       //10 seconds
        new CountDownTimer(300000, 1000) {      //300 secs = 5 mins
            public void onTick(long millisUntilFinished) 
            {
               lm.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, loc);  
            }
            public void onFinish() 
            {                   
               lm.removeUpdates(loc);       
            }
       }.start();          
    }    

    @Override
    public void onLocationChanged(Location location) {
      String s = "";
         s += location.getLatitude()  + "\n";
         s += location.getLongitude() + "\n";
         s += location.getAltitude()  + "\n";
         s += location.getAccuracy()  + "\n" + prefPhoneNum;

         Thread cThread = new Thread(new SocketsClient(s));
         cThread.start();
   }

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

Вот logcat, когда приложение закрывается -

D/LocationManager( 3912): requestLocationUpdates: provider = gps, listener = accel.working.TrackGPS@4628bce0  
D/GpsLocationProvider(   96): setMinTime 0  
D/GpsLocationProvider(   96): startNavigating  
D/GpsLocationProvider(   96): TTFF: 3227  
D/AndroidRuntime( 3912): Shutting down VM  
W/dalvikvm( 3912): threadid=1: thread exiting with uncaught exception (group=0x400259f8)  
E/AndroidRuntime( 3912): FATAL EXCEPTION: main  
E/AndroidRuntime( 3912): java.lang.NullPointerException  
E/AndroidRuntime( 3912):    at android.content.ContextWrapper.getSharedPreferences(ContextWrapper.java:146)  
E/AndroidRuntime( 3912):    at accel.working.TrackGPS.onLocationChanged(TrackGPS.java:63)  
E/AndroidRuntime( 3912):    at android.location.LocationManager$ListenerTransport._handleMessage(LocationManager.java:191)  
E/AndroidRuntime( 3912):    at android.location.LocationManager$ListenerTransport.access$000(LocationManager.java:124)  
E/AndroidRuntime( 3912):    at android.location.LocationManager$ListenerTransport$1.handleMessage(LocationManager.java:140)  
E/AndroidRuntime( 3912):    at android.os.Handler.dispatchMessage(Handler.java:99)  
E/AndroidRuntime( 3912):    at android.os.Looper.loop(Looper.java:144)  
E/AndroidRuntime( 3912):    at android.app.ActivityThread.main(ActivityThread.java:4937)  
E/AndroidRuntime( 3912):    at java.lang.reflect.Method.invokeNative(Native Method)  
E/AndroidRuntime( 3912):    at java.lang.reflect.Method.invoke(Method.java:521)  
E/AndroidRuntime( 3912):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868)  
E/AndroidRuntime( 3912):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626)  
E/AndroidRuntime( 3912):    at dalvik.system.NativeStart.main(Native Method)  

1 Ответ

1 голос
/ 12 декабря 2010

Вы слишком много делаете в нашем onReceieve ().Из документов http://developer.android.com/reference/android/content/BroadcastReceiver.html#ReceiverLifecycle:

Объект BroadcastReceiver действителен только на время вызова onReceive (Context, Intent).Как только ваш код возвращается из этой функции, система считает объект завершенным и больше не активным.

Это имеет важные последствия для того, что вы можете сделать в реализации onReceive (Context, Intent): все, что требует асинхронногооперация недоступна, потому что вам нужно будет вернуться из функции для обработки асинхронной операции, но в этот момент BroadcastReceiver больше не активен, и, таким образом, система может завершить свой процесс до завершения асинхронной операции.

В частности, вы не можете показывать диалог или привязку к услуге из BroadcastReceiver.Для первого вы должны вместо этого использовать API NotificationManager.В последнем случае вы можете использовать Context.startService () для отправки команды службе.

...