2010-12-11 3 views
0

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

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 = [email protected] 
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

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

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

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

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

+0

Хорошо, я изменил его, так что все, что делает BroadcastReceiver, создают службу, которая делает все вещи GPS, благодаря Falmarri. Но моя проблема по-прежнему остается в методе 'onLocationChanged', значение для prefPhoneNum является инициализированным значением 'prefPhoneNum'. Вы знаете, как читать из sharedpreferences в этом методе или обращаться к данным gps в enableGPS(), чтобы перейти к потоку, который я создал? – bobby123

+0

Ошибок в коде нет, но если я вызываю строку sharedpreferences = getSharedPreferences (US, MODE_WORLD_READABLE); в 'onLocationChanged()', то приложение заставляет закрыть – bobby123

+0

Что такое stacktrace? Опубликуйте свой logcat – Falmarri