2017-09-11 47 views
1

我在做一個應用程序,使當手機收到電話事情發生,所以很多搜索後,我發現我可以用一個BroadcastReceiverService所以我創建了一個Service稱爲PhoneStateServiceAndroid - 爲什麼應用程序崩潰時服務收到來電並且應用程序已關閉?

import android.app.Service; 
import android.content.BroadcastReceiver; 
import android.content.Context; 
import android.content.Intent; 
import android.content.IntentFilter; 
import android.os.IBinder; 
import android.telephony.TelephonyManager; 
import android.widget.Toast; 

public class PhoneStateService extends Service { 

    private static BroadcastReceiver broadcastReceiver; 

    @Override 
    public IBinder onBind(Intent arg0) { 
     return null; 
    } 

    @Override 
    public void onCreate() { 
     registerBroadcastReceiver(); 
    } 

    @Override 
    public void onDestroy() { 
     unregisterReceiver(broadcastReceiver); 
     broadcastReceiver = null; 
    } 

    private void registerBroadcastReceiver() { 
     broadcastReceiver = new BroadcastReceiver() { 
      @Override 
      public void onReceive(Context context, Intent intent) { 
       String stateStr = intent.getExtras().getString(TelephonyManager.EXTRA_STATE); 
       if(stateStr.equals(TelephonyManager.EXTRA_STATE_RINGING)){ 
        new PhoneStateHandler().onIncomingCallStarted(context); 
       } 
      } 
     }; 
     IntentFilter filter = new IntentFilter(TelephonyManager.ACTION_PHONE_STATE_CHANGED); 
     filter.addAction(Intent.ACTION_SCREEN_OFF); 
     registerReceiver(broadcastReceiver, filter); 
    } 
} 

這是用於開始PhoneStateService(內側MainActivity)的代碼:從所述Manifest文件

if(PermissionChecker.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE) == PermissionChecker.PERMISSION_GRANTED) { 
     startService(new Intent(getApplicationContext(), PhoneStateService.class)); 
    } 

部分:

<service android:name=".Service.PhoneStateService" /> 

當手機接到電話並且應用程序正在運行(它仍然沒有銷燬)時,一切正常,但關閉應用程序後,手機接到應用程序崩潰後給我的消息應用已停止工作。

請告訴我是什麼問題,我沒有找到答案。

編輯:

例外:

09-11 10:26:30.598 29461-29461/? E/AndroidRuntime: FATAL EXCEPTION: main 
               Process: com.multiplies.multiring, PID: 29461 
               java.lang.RuntimeException: Error receiving broadcast Intent { act=android.intent.action.SCREEN_OFF flg=0x50000010 } in [email protected] 
                at android.app.LoadedApk$ReceiverDispatcher$Args.run(LoadedApk.java:891) 
                at android.os.Handler.handleCallback(Handler.java:739) 
                at android.os.Handler.dispatchMessage(Handler.java:95) 
                at android.os.Looper.loop(Looper.java:148) 
                at android.app.ActivityThread.main(ActivityThread.java:5417) 
                at java.lang.reflect.Method.invoke(Native Method) 
                at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726) 
                at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616) 
               Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.String android.os.Bundle.getString(java.lang.String)' on a null object reference 
                at com.multiplies.multiring.Service.PhoneStateService$1.onReceive(PhoneStateService.java:36) 
                at android.app.LoadedApk$ReceiverDispatcher$Args.run(LoadedApk.java:881) 
                at android.os.Handler.handleCallback(Handler.java:739)  
                at android.os.Handler.dispatchMessage(Handler.java:95)  
                at android.os.Looper.loop(Looper.java:148)  
                at android.app.ActivityThread.main(ActivityThread.java:5417)  
                at java.lang.reflect.Method.invoke(Native Method)  
                at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)  
                at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)  

編輯:

我做了什麼,有人說:

String stateStr = intent.getExtras() != null ? intent.getExtras().getString(TelephonyManager.EXTRA_STATE) : ""; 

把不能解決的問題。 我認爲它不會工作,因爲如果intent.getExtras()是返回null,則if statement不會因爲它返回null工作,它是想TelephonyManager.EXTRA_STATE_RINGING

if(stateStr.equals(TelephonyManager.EXTRA_STATE_RINGING)){ 
       new PhoneStateHandler().onIncomingCallStarted(context); 
} 

,但感謝你的幫助。

HUGE EDIT:所述Manifest

部分:

<service android:name=".PhoneState.PhoneStateService" /> 
    <receiver android:name=".PhoneState.PhoneStateBroadcast"> 
    <intent-filter> 
     <action android:name="android.intent.action.PHONE_STATE" /> 
    </intent-filter> 
    </receiver> 

PhoneStateBroadcast

import android.app.Service; 
import android.content.BroadcastReceiver; 
import android.content.Context; 
import android.content.Intent; 
import android.telephony.TelephonyManager; 
import android.util.Log; 

public class PhoneStateBroadcast extends BroadcastReceiver { 

    Context context; 

    public void onReceive(Context context, Intent intent) { 
     this.context = context; 

     try { 

      TelephonyManager telephonyManager = (TelephonyManager) context.getSystemService(Service.TELEPHONY_SERVICE); 

      switch (telephonyManager.getCallState()) { 

       case TelephonyManager.CALL_STATE_RINGING: 
        context.startService(new Intent(context, PhoneStateService.class)); 
        break; 
      } 


     } catch (Exception e) { 
      Log.e("Phone Receive Error", " " + e); 
     } 

    } 
} 

PhoneStateService

import android.app.IntentService; 
import android.content.Intent; 

public class PhoneStateService extends IntentService { 

    public PhoneStateService(String name) { 
     super(name); 
    } 

    @Override 
    protected void onHandleIntent(Intent intent) { 
     new PhoneStateHandler().onIncomingCallStarted(getApplicationContext()); 
    } 
} 

此編輯後我仍然崩潰。

+0

分享堆棧跟蹤 –

+0

我編輯的問題 –

+0

@AzzamAlsharafi看起來像u有NLE在intent.getExtras()的getString(TelephonyManager。 EXTRA_STATE)檢查。 ** intent.getExtras()**爲空 – Raghavendra

回答

2

由於某種原因,額外的東西都是空的。您正在做intent.getExtras().XXX,但intent.getExtras()返回null,調用.XXX會引發錯誤。

更改

String stateStr = intent.getExtras().getString(TelephonyManager.EXTRA_STATE); 

String stateStr = intent.getExtras() != null ? intent.getExtras().getString(TelephonyManager.EXTRA_STATE) : ""; 

將阻止發生崩潰,但你可能想看看是什麼原因,爲什麼你期望的額外的,但沒有任何的意圖。

+0

謝謝,但這意味着,由於某種原因,當應用程序關閉它的返回null,這意味着該服務目前不能工作,如果應用程序關閉,所以如果知道任何東西都可以是有用的,請告訴我。並再次感謝你。 –

+0

您可能想要先嚐試一下,也許廣播接收器會針對不同的呼叫狀態多次調用,並且上述操作會在成功處理您正在查找的某個狀態時忽略某些狀態。 – Frank

1

而不是運行一個服務所有的時間,使它成爲一個BroadcastReciever,它在每次改變呼叫狀態時被觸發(長時間運行服務不是一個好習慣),因此通過使用Broadcast receiver,你的服務會在你想要的時候運行。

public class PhoneStateService extends BroadcastReceiver{ 

     public void onReceive(Context context, Intent intent) { 
      mContext = context; 

       try { 

        TelephonyManager tm = (TelephonyManager) context.getSystemService(Service.TELEPHONY_SERVICE); 
        String deviceId=tm.getDeviceId(); 

        switch (tm.getCallState()) { 

         case TelephonyManager.CALL_STATE_RINGING: // incoming call 

        //do something on Incoming call event 

          break; 

         case TelephonyManager.CALL_STATE_IDLE: //call Ends 

          //do something on Idle phone state i.e set your logic if an incoming call is complete then this block would execute. 


        } 


       } catch (Exception e) { 
        Log.e("Phone Receive Error", " " + e); 
       } 

     } 


    } 

那麼這broadcastReciever添加到您的清單下的應用程序標籤

<receiver android:name="orbitsys.com.prospect_call.CallerState"> 
       <intent-filter> 
        <action android:name="android.intent.action.PHONE_STATE" /> 
       </intent-filter>