Skip to content

Commit

Permalink
Fix in-call proximity lock for wireless, speaker, and bluetooth.
Browse files Browse the repository at this point in the history
  • Loading branch information
alex-signal authored and greyson-signal committed Dec 19, 2019
1 parent 4c526f0 commit d7c350f
Show file tree
Hide file tree
Showing 4 changed files with 77 additions and 23 deletions.
34 changes: 16 additions & 18 deletions src/org/thoughtcrime/securesms/WebRtcCallActivity.java
Expand Up @@ -24,11 +24,9 @@
import android.content.Intent;
import android.content.res.Configuration;
import android.media.AudioManager;
import android.os.Build;
import android.os.Bundle;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.core.app.ActivityCompat;

import org.thoughtcrime.securesms.logging.Log;
import android.view.View;
Expand Down Expand Up @@ -152,6 +150,20 @@ private void initializeResources() {
callScreen.setBluetoothButtonListener(new BluetoothButtonListener());
}

private void handleSetAudioSpeaker(boolean enabled) {
Intent intent = new Intent(this, WebRtcCallService.class);
intent.setAction(WebRtcCallService.ACTION_SET_AUDIO_SPEAKER);
intent.putExtra(WebRtcCallService.EXTRA_SPEAKER, enabled);
startService(intent);
}

private void handleSetAudioBluetooth(boolean enabled) {
Intent intent = new Intent(this, WebRtcCallService.class);
intent.setAction(WebRtcCallService.ACTION_SET_AUDIO_BLUETOOTH);
intent.putExtra(WebRtcCallService.EXTRA_BLUETOOTH, enabled);
startService(intent);
}

private void handleSetMuteAudio(boolean enabled) {
Intent intent = new Intent(this, WebRtcCallService.class);
intent.setAction(WebRtcCallService.ACTION_SET_MUTE_AUDIO);
Expand Down Expand Up @@ -376,28 +388,14 @@ public void onToggle() {
private class SpeakerButtonListener implements WebRtcCallControls.SpeakerButtonListener {
@Override
public void onSpeakerChange(boolean isSpeaker) {
AudioManager audioManager = ServiceUtil.getAudioManager(WebRtcCallActivity.this);
audioManager.setSpeakerphoneOn(isSpeaker);

if (isSpeaker && audioManager.isBluetoothScoOn()) {
audioManager.stopBluetoothSco();
audioManager.setBluetoothScoOn(false);
}
WebRtcCallActivity.this.handleSetAudioSpeaker(isSpeaker);
}
}

private class BluetoothButtonListener implements WebRtcCallControls.BluetoothButtonListener {
@Override
public void onBluetoothChange(boolean isBluetooth) {
AudioManager audioManager = ServiceUtil.getAudioManager(WebRtcCallActivity.this);

if (isBluetooth) {
audioManager.startBluetoothSco();
audioManager.setBluetoothScoOn(true);
} else {
audioManager.stopBluetoothSco();
audioManager.setBluetoothScoOn(false);
}
WebRtcCallActivity.this.handleSetAudioBluetooth(isBluetooth);
}
}

Expand Down
Expand Up @@ -100,7 +100,6 @@ public void setSpeakerButtonListener(final SpeakerButtonListener listener) {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
listener.onSpeakerChange(isChecked);
updateAudioState(bluetoothButton.getVisibility() == View.VISIBLE);
}
});
}
Expand All @@ -110,7 +109,6 @@ public void setBluetoothButtonListener(final BluetoothButtonListener listener) {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
listener.onBluetoothChange(isChecked);
updateAudioState(true);
}
});
}
Expand Down
58 changes: 55 additions & 3 deletions src/org/thoughtcrime/securesms/service/WebRtcCallService.java
Expand Up @@ -116,6 +116,8 @@ private enum CallState {
public static final String EXTRA_RESULT_RECEIVER = "result_receiver";
public static final String EXTRA_CALL_ERROR = "call_error";
public static final String EXTRA_IDENTITY_KEY_BYTES = "identity_key_bytes";
public static final String EXTRA_SPEAKER = "audio_speaker";
public static final String EXTRA_BLUETOOTH = "audio_bluetooth";

public static final String ACTION_INCOMING_CALL = "CALL_INCOMING";
public static final String ACTION_OUTGOING_CALL = "CALL_OUTGOING";
Expand All @@ -130,6 +132,8 @@ private enum CallState {
public static final String ACTION_SCREEN_OFF = "SCREEN_OFF";
public static final String ACTION_CHECK_TIMEOUT = "CHECK_TIMEOUT";
public static final String ACTION_IS_IN_CALL_QUERY = "IS_IN_CALL";
public static final String ACTION_SET_AUDIO_SPEAKER = "SET_AUDIO_SPEAKER";
public static final String ACTION_SET_AUDIO_BLUETOOTH = "SET_AUDIO_BLUETOOTH";

public static final String ACTION_RESPONSE_MESSAGE = "RESPONSE_MESSAGE";
public static final String ACTION_ICE_MESSAGE = "ICE_MESSAGE";
Expand Down Expand Up @@ -217,6 +221,8 @@ public int onStartCommand(final Intent intent, int flags, int startId) {
else if (intent.getAction().equals(ACTION_CHECK_TIMEOUT)) handleCheckTimeout(intent);
else if (intent.getAction().equals(ACTION_IS_IN_CALL_QUERY)) handleIsInCallQuery(intent);
else if (intent.getAction().equals(ACTION_CALL_ERROR)) handleCallError(intent);
else if (intent.getAction().equals(ACTION_SET_AUDIO_SPEAKER)) handleSetSpeakerAudio(intent);
else if (intent.getAction().equals(ACTION_SET_AUDIO_BLUETOOTH)) handleSetBluetoothAudio(intent);
});

return START_NOT_STICKY;
Expand Down Expand Up @@ -406,7 +412,7 @@ private void handleOutgoingCall(Intent intent) {
initializeVideo();

sendMessage(WebRtcViewModel.State.CALL_OUTGOING, recipient, localCameraState, remoteVideoEnabled, bluetoothAvailable, microphoneEnabled);
lockManager.updatePhoneState(LockManager.PhoneState.IN_CALL);
lockManager.updatePhoneState(getInCallPhoneState());
audioManager.initializeAudioForCall();
audioManager.startOutgoingRinger(OutgoingRinger.Type.RINGING);
bluetoothStateManager.setWantsConnection(true);
Expand Down Expand Up @@ -534,7 +540,7 @@ private void activateCallMedia() {
callState = CallState.STATE_CONNECTED;

if (localCameraState.isEnabled()) lockManager.updatePhoneState(LockManager.PhoneState.IN_VIDEO);
else lockManager.updatePhoneState(LockManager.PhoneState.IN_CALL);
else lockManager.updatePhoneState(getInCallPhoneState());

sendMessage(WebRtcViewModel.State.CALL_CONNECTED, recipient, localCameraState, remoteVideoEnabled, bluetoothAvailable, microphoneEnabled);

Expand Down Expand Up @@ -746,6 +752,43 @@ private void handleRemoteHangup(Intent intent) {
terminate();
}

private void handleSetSpeakerAudio(Intent intent) {
boolean isSpeaker = intent.getBooleanExtra(EXTRA_SPEAKER, false);
AudioManager audioManager = ServiceUtil.getAudioManager(this);

audioManager.setSpeakerphoneOn(isSpeaker);

if (isSpeaker && audioManager.isBluetoothScoOn()) {
audioManager.stopBluetoothSco();
audioManager.setBluetoothScoOn(false);
}

if (!localCameraState.isEnabled()) {
lockManager.updatePhoneState(getInCallPhoneState());
}

sendMessage(viewModelStateFor(callState), recipient, localCameraState, remoteVideoEnabled, bluetoothAvailable, microphoneEnabled);
}

private void handleSetBluetoothAudio(Intent intent) {
boolean isBluetooth = intent.getBooleanExtra(EXTRA_BLUETOOTH, false);
AudioManager audioManager = ServiceUtil.getAudioManager(this);

if (isBluetooth) {
audioManager.startBluetoothSco();
audioManager.setBluetoothScoOn(true);
} else {
audioManager.stopBluetoothSco();
audioManager.setBluetoothScoOn(false);
}

if (!localCameraState.isEnabled()) {
lockManager.updatePhoneState(getInCallPhoneState());
}

sendMessage(viewModelStateFor(callState), recipient, localCameraState, remoteVideoEnabled, bluetoothAvailable, microphoneEnabled);
}

private void handleSetMuteAudio(Intent intent) {
boolean muted = intent.getBooleanExtra(EXTRA_MUTE, false);
this.microphoneEnabled = !muted;
Expand Down Expand Up @@ -777,7 +820,7 @@ private void handleSetMuteVideo(Intent intent) {

if (callState == CallState.STATE_CONNECTED) {
if (localCameraState.isEnabled()) this.lockManager.updatePhoneState(LockManager.PhoneState.IN_VIDEO);
else this.lockManager.updatePhoneState(LockManager.PhoneState.IN_CALL);
else this.lockManager.updatePhoneState(getInCallPhoneState());
}

if (localCameraState.isEnabled() &&
Expand Down Expand Up @@ -1346,4 +1389,13 @@ public void onAddStream(SignalMessageRecipient eventRecipient,
}
}

private LockManager.PhoneState getInCallPhoneState() {
AudioManager audioManager = ServiceUtil.getAudioManager(this);
if (audioManager.isSpeakerphoneOn() || audioManager.isBluetoothScoOn() || audioManager.isWiredHeadsetOn()) {
return LockManager.PhoneState.IN_HANDS_FREE_CALL;
} else {
return LockManager.PhoneState.IN_CALL;
}
}

}
6 changes: 6 additions & 0 deletions src/org/thoughtcrime/securesms/webrtc/locks/LockManager.java
Expand Up @@ -32,6 +32,7 @@ public enum PhoneState {
PROCESSING, //used when the phone is active but before the user should be alerted.
INTERACTIVE,
IN_CALL,
IN_HANDS_FREE_CALL,
IN_VIDEO
}

Expand Down Expand Up @@ -100,6 +101,11 @@ public void updatePhoneState(PhoneState state) {
setLockState(LockState.FULL);
accelerometerListener.enable(false);
break;
case IN_HANDS_FREE_CALL:
setLockState(LockState.PARTIAL);
proximityDisabled = true;
accelerometerListener.enable(false);
break;
case IN_VIDEO:
proximityDisabled = true;
accelerometerListener.enable(false);
Expand Down

0 comments on commit d7c350f

Please sign in to comment.