2015-08-28 153 views
4

我需要检测蓝牙设备上按下“电话”按钮时,大多数人都会有一个按钮来应答/挂断。检测Android蓝牙应答/挂断按钮事件

使用audioManager.registerMediaButtonEventReceiver()与意向过滤器MEDIA_BUTTON,我能够检测除手机按钮(即:跳过下一个,跳过上一个,播放/暂停)以外的所有按钮。

使用CALL或CALL_BUTTON过滤器不起作用(未收到任何事件)。

该按钮的默认行为是断开音频并切换回听筒。在Skype应用程序中发生同样的行为,但是,在进行正常的GSM呼叫时,内置的电话应用程序会正确处理该按钮,并可以应答并挂断呼叫。

我在试图找到电话应用程序如何处理这个问题,但一直未能找到代码。

有谁知道如何正确检测蓝牙电话按钮事件?

+0

你有没有想过这个? – jobbert

+0

不,看起来不可能 – behelit

+1

我实际上找到了一种方法来做到这一点。这感觉有点不好意思,如果你有兴趣,我可以发布它?当然是 – jobbert

回答

2

很难找出如何做到这一点,只发现一个hacky挂断解决方案。我将此代码用于SIP呼叫应用程序。我将活动对话的音频路由到蓝牙耳机,将音频模式设置为通信(audioManager.setMode(AudioManager.MODE_IN_COMMUNICATION);)。当在对话期间按下蓝牙耳机的挂断按钮时,意向STATE_AUDIO_DISCONNECTED get被调用。我使用该意图操作来挂断当前通话。我在改变音频模式(部分使用其他来源)后使用以下呼叫:

public class BluetoothIntentListener { 
    private static final String TAG = "BluetoothIntent"; 
    private static BluetoothIntentListener bluetoothIntentListener; 
    protected BluetoothAdapter mBluetoothAdapter; 
    protected BluetoothHeadset mBluetoothHeadset; 
    protected AudioManager mAudioManager; 
    private Context context; 

    private BluetoothIntentListener(Context context) { 
     this.context = context; 
    } 

    public static BluetoothIntentListener getInstance(Context context) { 
     if (bluetoothIntentListener == null) { 
      bluetoothIntentListener = new BluetoothIntentListener(context); 
     } 
     return bluetoothIntentListener; 
    } 

    public void init() { 
     mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); 
     if (mBluetoothAdapter != null) { 
      mAudioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE); 
      if (mAudioManager.isBluetoothScoAvailableOffCall()) { 
       mBluetoothAdapter.getProfileProxy(context, mHeadsetProfileListener, BluetoothProfile.HEADSET); 
      } 
     } 
    } 

    public void destroy() { 

mHeadsetProfileListener.onServiceDisconnected(BluetoothProfile.HEADSET); 
    } 

    protected BluetoothProfile.ServiceListener mHeadsetProfileListener = new BluetoothProfile.ServiceListener() { 
     @Override 
     public void onServiceDisconnected(int profile) { 
      try { 
       context.unregisterReceiver(mHeadsetBroadcastReceiver); 
       mBluetoothHeadset = null; 
      } catch (IllegalArgumentException il) { 
       Log.i(TAG, "Headset broadcast receiver wasn't registered yet."); 
      } 
     } 

     @Override 
     public void onServiceConnected(int profile, BluetoothProfile proxy) { 
      mBluetoothHeadset = (BluetoothHeadset) proxy; 
      context.registerReceiver(mHeadsetBroadcastReceiver, 
       new IntentFilter(BluetoothHeadset.ACTION_CONNECTION_STATE_CHANGED)); 
     IntentFilter f = new IntentFilter(BluetoothHeadset.ACTION_AUDIO_STATE_CHANGED); 
     f.setPriority(Integer.MAX_VALUE); 
      context.registerReceiver(mHeadsetBroadcastReceiver, f); 
     } 
    }; 

    protected BroadcastReceiver mHeadsetBroadcastReceiver = new BroadcastReceiver() { 
     @Override 
     public void onReceive(Context context, Intent intent) { 
      String action = intent.getAction(); 
      int state; 

      if (action.equals(BluetoothHeadset.ACTION_AUDIO_STATE_CHANGED)) { 
       state = intent.getIntExtra(BluetoothHeadset.EXTRA_STATE, BluetoothHeadset.STATE_DISCONNECTED); 
       if (state == BluetoothHeadset.STATE_AUDIO_CONNECTED) { 
        Log.d(TAG, "Connected"); 
       } else if (state == BluetoothHeadset.STATE_AUDIO_DISCONNECTED) { 
        // Hangup of bluetooth headset pressed. 
       } 
      } 
     } 
    }; 
} 

我希望这可以帮助任何人。

+1

不像我想的那样哈克:)会给它一个镜头 – behelit

+0

它是否为你做了诡计? – jobbert