3

В Android (цель 25) У меня есть фоновое обслуживание, а в функции onCreate я инициализировал прослушиватель состояния телефона. Он отлично работает в версиях Android, которые находятся до Nougat, но в Nougat он не работает, хотя разрешения предоставляются.Android Nougat PhoneStateListener не запускается

public class Service extends IntentService 
{ 
    class PhoneListener extends PhoneStateListener 
    { 
     String TAG = getClass().getName(); 
     @Override 
     public void onCallStateChanged(int state, String incomingNumber) 
     { 
      super.onCallStateChanged(state, incomingNumber); 
      switch (state) 
      { 
       case TelephonyManager.CALL_STATE_IDLE: 
       Log.d(TAG,"IDLE"); 
       break; 
       case TelephonyManager.CALL_STATE_OFFHOOK: 
       Log.d(TAG,"OFFHOOK"); 
       break; 
       case TelephonyManager.CALL_STATE_RINGING: 
       Log.d(TAG,"RINGING"); 
       break; 
      } 
     } 
    } 

    public Service() 
    { 
     super("ChatService"); 
    } 
    public Service(String name) 
    { 
     super(name); 
    } 

    @Override 
    public void onCreate() 
    { 
     super.onCreate(); 
     TelephonyManager tm = (TelephonyManager)getApplicationContext().getSystemService(TELEPHONY_SERVICE); 
     PhoneListener listener = new PhoneListener(); 
     tm.listen(listener,PhoneStateListener.LISTEN_CALL_STATE); 
    } 
} 

Я не знаю, что это проблема, похоже, менеджер телефонии не зарегистрирован и поэтому onCallStateChanged не срабатывает. Одним из моих догадок является функция Doze, которая была представлена ​​на Android M, но все же ... этот код отлично работает на Android 6, даже если телефон не найден «в работе»

ответ

2

Так для тех, кто столкнулся с одной и той же проблемой Я нашел решение. Вам не нужно регистрировать BroadcastReceiver для PhoneState.

Таким образом, вместо registere менеджер телефонии для прослушивания внутри метода (службы) OnCreate, я поставил его в onStartCommand и он начал работать.

, но обратите внимание, что в любом случае, что onStartCommand будет запущен, он зарегистрирует менеджера телефонии, поэтому обязательно зарегистрируйте его только один раз.

В моем случае, так как внутри класса обслуживания У меня есть внутренний класс PhoneListener Я создал элемент класса и инициализации его в нуль, и в onStartCommand я проверил, если это нуль, а затем создал и зарегистрировал менеджер телефонии , но вы можете использовать метод singelton.

Так что это мой код, который работал также в Android Нуга:

public class Service extends IntentService 
{ 
    class PhoneListener extends PhoneStateListener 
    { 
     String TAG = getClass().getName(); 
     @Override 
     public void onCallStateChanged(int state, String incomingNumber) 
     { 
      super.onCallStateChanged(state, incomingNumber); 
      switch (state) 
      { 
       case TelephonyManager.CALL_STATE_IDLE: 
        Log.d(TAG,"IDLE"); 
       break; 
       case TelephonyManager.CALL_STATE_OFFHOOK: 
        Log.d(TAG,"OFFHOOK"); 
       break; 
       case TelephonyManager.CALL_STATE_RINGING: 
        Log.d(TAG,"RINGING"); 
       break; 
      } 
    } 
    PhoneListener phoneListener = null; 

    public Service() 
    { 
     super("ChatService"); 
    } 

    @Override 
    public void onCreate() 
    { 
     super.onCreate(); 
     // do what you need here 
    } 

    @Override 
    public int onStartCommand (Intent intent, int flags, int startId) 
    { 
     if (phoneListener == null) 
     { 
      TelephonyManager tm = (TelephonyManager)getApplicationContext().getSystemService(TELEPHONY_SERVICE); 
      phoneListener = new PhoneListener(); 
      tm.listen(listener,PhoneStateListener.LISTEN_CALL_STATE); 
     } 
     // do what you need to do here 

     return START_STICKY; // you can set it as you want 
    } 
}