i am working on a VoIP-Android-App. I would like to accept and decline Calls via a connnected Bluetooth Headset in an Activity.
What I have tried so far:
Using a Media Session to receive Media Button clicks.
Problem: If we start BluetoothSCO we do not receive any Media Button clicks. If we do not start BluetoothSCO we do receive Media Button clicks but we cannot differentiate long and short button clicks because downtime is always 0, the keycode is always KEYCODE_MEDIA_PLAY and the ACTION_DOWN is immediately followed by ACTION_UP. Those problems only occur if we are connected via Bluetooth. If we are connnected over a cable Headset we do get the appropriate keycodes (KEYCODE_HEADSETHOOK) and the downtime is not 0.
Using a BroadcastReceiver to listen for Bluetooth SCO connection changes.
private val scoReceiver = object : BroadcastReceiver() { fun onReceive(context: Context, intent: Intent) { val state = intent.getIntExtra(AudioManager.EXTRA_SCO_AUDIO_STATE, -1) val previousState = intent.getIntExtra(AudioManager.EXTRA_SCO_AUDIO_PREVIOUS_STATE, -1) if (state == AudioManager.SCO_AUDIO_STATE_DISCONNECTED && previousState == AudioManager.SCO_AUDIO_STATE_CONNECTED) { Log.e(TAG, "SCO Disconnected") hangupCall() } } } protected fun onStart() { super.onStart() val intentFilter = IntentFilter() intentFilter.addAction(AudioManager.ACTION_SCO_AUDIO_STATE_UPDATED) registerReceiver(scoReceiver, intentFilter) }
With this approach i can detect when the user wants to hang up the call, for example a long press on the bluetooth headset because this triggers the SCO to disconnect.
Problem: We can not detect if the user wants to accept an incoming call.
Using dispatchKeyEvent, onKeyDown and onKeyUp.
Problem: They never get called at all.
Does anyone has any advice or a best practice how to correctly handle bluetooth headsets? Any help is very appreciated. Thanks in advance!