From 50cb0905a80ba837c1a6f469dffc6ea8524afcee Mon Sep 17 00:00:00 2001 From: Ergyun Syuleyman Date: Mon, 15 Jun 2020 02:00:57 +0300 Subject: [PATCH 1/2] NY-10519: [AN]: Put NYNJA call on hold when the user takes a PSTN call NY-10519: [AN]: Put NYNJA call on hold when the user takes a PSTN call --- app/src/main/AndroidManifest.xml | 9 + .../data/conference/ActiveCallBase.java | 13 -- .../conference/ConferenceVideoModule.java | 8 +- .../data/conference/PhoneCallReceiver.java | 43 ++++ .../data/sdk/ConferenceSDKPresenter.java | 7 +- .../data/sdk/calls/ActiveConferenceCall.java | 14 +- .../calls/BluetoothConnectivityListener.java | 8 + .../data/sdk/calls/CallStateData.java | 68 ++++++ .../data/sdk/calls/ConferenceCallData.java | 4 +- .../data/sdk/calls/ConferenceSDKListener.java | 6 +- .../data/sdk/calls/ConferenceSDKModule.java | 212 +++++++++++------- .../data/sdk/calls/ConferenceService.java | 8 +- .../mvp/presenters/CallActivityPresenter.java | 26 +-- .../presenters/CallTapToSpeakPresenter.java | 13 +- .../presenters/ConferenceCallPresenter.java | 18 +- .../mvp/view/CallActivityView.java | 2 + .../mvp/view/CallTapToSpeakView.java | 6 +- .../communicator/mvp/view/CallView.java | 6 +- .../ui/activities/MainActivity.java | 11 +- .../ui/activities/calls/CallActivity.java | 103 +++------ .../communicator/ui/base/BaseActivity.java | 2 +- .../conference/CallTapToSpeakFragment.java | 36 +-- .../conference/ConferenceCallFragment.java | 98 ++++---- .../conference/ConferenceVideoFragment.java | 6 +- .../main/res/layout/layout_call_paused.xml | 52 +++++ .../main/res/layout/paged_activity_call.xml | 9 + app/src/main/res/values-en/strings.xml | 1 + app/src/main/res/values-es/strings.xml | 1 + app/src/main/res/values-ko/strings.xml | 1 + app/src/main/res/values-zh-rCN/strings.xml | 1 + app/src/main/res/values-zh/strings.xml | 1 + app/src/main/res/values/strings.xml | 1 + 32 files changed, 517 insertions(+), 277 deletions(-) create mode 100644 app/src/main/java/com/nynja/mobile/communicator/data/conference/PhoneCallReceiver.java create mode 100644 app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/BluetoothConnectivityListener.java create mode 100644 app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/CallStateData.java create mode 100644 app/src/main/res/layout/layout_call_paused.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 36e1aa2b85..ebac35fcd4 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -282,6 +282,15 @@ + + + + + diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/conference/ActiveCallBase.java b/app/src/main/java/com/nynja/mobile/communicator/data/conference/ActiveCallBase.java index fce484df70..a1960465e8 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/conference/ActiveCallBase.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/conference/ActiveCallBase.java @@ -12,20 +12,10 @@ public abstract class ActiveCallBase { P2PCall, ConferenceCall } - public enum AudioRouteType { - SPEAKER, - EARPIECE, - BLUETOOTH, - NOT_SET - } - public String name; public String mEndPointId; public CallType mCallType; public boolean isOutgoingCall; - public boolean isMuted; - public boolean isSpeakerOn; - public AudioRouteType mAudioRouteType; public boolean isCallInProgress; public boolean isRinging; public boolean isSwitchToAudio; @@ -43,9 +33,6 @@ public abstract class ActiveCallBase { isVideoEnabled = true;//(callType == CallType.P2PCall); isVideoFullScreen = false; isOutgoingCall = outgoingCall; - isMuted = false; - isSpeakerOn = false; - mAudioRouteType = AudioRouteType.NOT_SET; isRinging = false; isCallInProgress = false; isSwitchToAudio = false; diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/conference/ConferenceVideoModule.java b/app/src/main/java/com/nynja/mobile/communicator/data/conference/ConferenceVideoModule.java index 21c32cc160..4af37d954e 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/conference/ConferenceVideoModule.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/conference/ConferenceVideoModule.java @@ -98,7 +98,7 @@ public class ConferenceVideoModule { if (activeConferenceCall.mData.mParticipantArray != null) { for (int index = 0; index < activeConferenceCall.mData.mParticipantArray.size(); index++) { NYNCallParticipant participant = activeConferenceCall.mData.mParticipantArray.get(index); - ConferenceListItem item = conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mData.isOwnStreamActive); + ConferenceListItem item = conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mState.isOwnStreamActive); tempParticipants.add(item); if (//participant.hasVideo() || activeConferenceCall.mData.mActiveParticipanTracks.containsValue(participant.getParticipantId())) { @@ -112,7 +112,7 @@ public class ConferenceVideoModule { } else if (//participant.hasVideo() && participant.getParticipantId().contentEquals(activeConferenceCall.mConference.participantId()) && participant.isMe() && - activeConferenceCall.mData.isOwnStreamActive) { + activeConferenceCall.mState.isOwnStreamActive) { ////////////////////////////////////////////////////////////////////////////////////////////////// // WORKAROUND !!!!!!!!!! item.hasVideo = true; @@ -129,9 +129,9 @@ public class ConferenceVideoModule { // if (participant == null) participant = activeConferenceCall.mConference.getParticipantById(set.getValue()); // if (participant != null && // (participant.hasVideo() || -// (participant.isMe() && activeConferenceCall.mData.isOwnStreamActive) || +// (participant.isMe() && activeConferenceCall.mState.isOwnStreamActive) || // activeConferenceCall.mData.mActiveParticipanTracks.containsKey(participant.getParticipantId()))) { -// ConferenceListItem item = conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mData.isOwnStreamActive); +// ConferenceListItem item = conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mState.isOwnStreamActive); // item.hasVideo = true; // item.participantId = set.getValue(); // mActiveVideoParticipantsMap.put(item.participantId, item); diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/conference/PhoneCallReceiver.java b/app/src/main/java/com/nynja/mobile/communicator/data/conference/PhoneCallReceiver.java new file mode 100644 index 0000000000..f18d171d0c --- /dev/null +++ b/app/src/main/java/com/nynja/mobile/communicator/data/conference/PhoneCallReceiver.java @@ -0,0 +1,43 @@ +package com.nynja.mobile.communicator.data.conference; + +import android.app.Service; +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.telephony.TelephonyManager; + +import com.nynja.mobile.communicator.NynjaApp; +import com.nynja.mobile.communicator.data.DataManager; + +import timber.log.Timber; + +public class PhoneCallReceiver extends BroadcastReceiver { + +// public static final String PHONE_STATE = "android.intent.action.PHONE_STATE"; + + private DataManager mDataManager; + TelephonyManager mTelephonyManager; + private int mLastPhoneCallState = TelephonyManager.CALL_STATE_IDLE; + + public PhoneCallReceiver() { + super(); + mDataManager = NynjaApp.getComponent().dataManager(); + mTelephonyManager = (TelephonyManager) mDataManager.getContext().getSystemService(Service.TELEPHONY_SERVICE); + if (mTelephonyManager != null) mLastPhoneCallState = mTelephonyManager.getCallState(); + } + + @Override + public void onReceive(Context context, Intent intent) { + Timber.d("PhoneCallReceiver::onReceive(): Telephony service event"); + String action = intent.getAction(); + if (action != null && action.equals(TelephonyManager.ACTION_PHONE_STATE_CHANGED)) { + if (mTelephonyManager != null) { + mDataManager.getConferenceSDK().onPstnCallState(mLastPhoneCallState, mTelephonyManager.getCallState()); + mLastPhoneCallState = mTelephonyManager.getCallState(); + } else { + Timber.w("PhoneCallReceiver::onReceive(): Telephony Manager is NULL !!!!"); + } + } + } +} + diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/ConferenceSDKPresenter.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/ConferenceSDKPresenter.java index cf1044ccef..2db01bbfd4 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/ConferenceSDKPresenter.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/ConferenceSDKPresenter.java @@ -2,6 +2,7 @@ package com.nynja.mobile.communicator.data.sdk; import com.nynja.mobile.communicator.data.conference.ActiveCallBase; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; import com.nynja.mobile.communicator.data.sdk.calls.ConferenceSDKListener; import com.nynja.mobile.communicator.data.sdk.calls.RejoinConferenceCallData; import com.nynja.mobile.communicator.mvp.presenters.BaseErrorPresenter; @@ -73,7 +74,7 @@ public abstract class ConferenceSDKPresenter extends Bas @Override public void onSpeakerStateChanged(boolean isSpeakerOn) {} - @Override public void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType) { } + @Override public void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType) { } @Override public void tryCallCameraStateChange(boolean pause) {} @@ -100,4 +101,8 @@ public abstract class ConferenceSDKPresenter extends Bas @Override public void showPurchaseDialog(boolean isModerator, final String message) {} @Override public void onPurchaseFinished() {} + + @Override public void onBluetoothConnectivityChanged(boolean connected) {} + + @Override public void onCallPauseStateChanged(boolean paused) {} } diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ActiveConferenceCall.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ActiveConferenceCall.java index d613e9b7b8..4de6c6f647 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ActiveConferenceCall.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ActiveConferenceCall.java @@ -25,6 +25,7 @@ public class ActiveConferenceCall extends ActiveCallBase { public boolean mWaiting; public boolean mAutoCreateAndStart; public ConferenceCallData mData; + public CallStateData mState; public static final int ANDROID_10_PUSH_CALL_NTFN_ID = 1234567890; @@ -32,7 +33,8 @@ public class ActiveConferenceCall extends ActiveCallBase { public ActiveConferenceCall(NYNCall conference, String endPointId, CallType callType, boolean isVideoEnabled, boolean outgoingCall) { super(endPointId, callType, isVideoEnabled, outgoingCall); - mData = new ConferenceCallData((callType == CallType.P2PCall), isVideoEnabled); + mData = new ConferenceCallData((callType == CallType.P2PCall)); + mState = new CallStateData(false, isVideoEnabled); mConference = conference; mMembers = new ArrayList(); mMyDisplayName = ""; @@ -98,7 +100,7 @@ public class ActiveConferenceCall extends ActiveCallBase { public boolean isCameraRunning() { return (mConference != null - && mData.isOwnStreamActive + && mState.isOwnStreamActive && isCallInProgress() && mConference.isCameraRunning()); } @@ -191,11 +193,11 @@ public class ActiveConferenceCall extends ActiveCallBase { "name='" + name + '\'' + ", isOutComingConference=" + isOutgoingCall + ", mEndPointId='" + mEndPointId + '\'' + - ", isMuted=" + isMuted + - ", isSpeakerOn=" + isSpeakerOn + - ", mAudioRouteType=" + mAudioRouteType.toString() + + ", isMuted=" + mState.isMuted + + ", isSpeakerOn=" + mState.isSpeakerOn + + ", mAudioRouteType=" + mState.mAudioRouteType.toString() + ", mConference=" + mConference + - ", isOwnStreamActive=" + mData.isOwnStreamActive + + ", isOwnStreamActive=" + mState.isOwnStreamActive + ", hasRemoteVideoTrack=" + mData.hasRemoteVideoTrack + ", hasRemoteScreenShareTrack=" + mData.hasRemoteScreenShareTrack + ", isVideoEnabled=" + isVideoEnabled + diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/BluetoothConnectivityListener.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/BluetoothConnectivityListener.java new file mode 100644 index 0000000000..71f1a6981f --- /dev/null +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/BluetoothConnectivityListener.java @@ -0,0 +1,8 @@ +package com.nynja.mobile.communicator.data.sdk.calls; + +public interface BluetoothConnectivityListener { + + void onBluetoothDeviceConnected(); + + void onBluetoothDeviceDisconnected(); +} diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/CallStateData.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/CallStateData.java new file mode 100644 index 0000000000..9775359f09 --- /dev/null +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/CallStateData.java @@ -0,0 +1,68 @@ +package com.nynja.mobile.communicator.data.sdk.calls; + +public class CallStateData { + + public enum AudioRouteType { + SPEAKER, + EARPIECE, + BLUETOOTH, + NOT_SET + } + + public boolean isPaused; + public boolean isMuted; + public boolean isSpeakerOn; + public boolean isOwnSSActive; + public boolean isOwnStreamActive; + public AudioRouteType mAudioRouteType; + + //////////////////////////////////////////////// + // store paused state + public CallStateData pauseRestoreState; + + + public CallStateData() { + init(); + } + + public CallStateData(CallStateData copy) { + this.isPaused = copy.isPaused; + this.isMuted = copy.isMuted; + this.isSpeakerOn = copy.isSpeakerOn; + this.isOwnSSActive = copy.isOwnSSActive; + this.isOwnStreamActive = copy.isOwnStreamActive; + this.mAudioRouteType = copy.mAudioRouteType; + } + + public void resume() { + if (pauseRestoreState != null) { + this.isPaused = false; + this.isMuted = pauseRestoreState.isMuted; + this.isSpeakerOn = pauseRestoreState.isSpeakerOn; + this.isOwnSSActive = pauseRestoreState.isOwnSSActive; + this.isOwnStreamActive = pauseRestoreState.isOwnStreamActive; + this.mAudioRouteType = pauseRestoreState.mAudioRouteType; + pauseRestoreState = null; + } + } + + public void pause() { + this.isPaused = true; + pauseRestoreState = new CallStateData(this); + } + + public CallStateData(boolean isOwnSSActive, boolean isOwnStreamActive) { + init(); + this.isOwnSSActive = isOwnSSActive; + this.isOwnStreamActive = isOwnStreamActive; + } + + private void init() { + isPaused = false; + isMuted = false; + isSpeakerOn = false; + isOwnSSActive = false; + isOwnStreamActive = false; + mAudioRouteType = AudioRouteType.NOT_SET; + } +} diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceCallData.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceCallData.java index 5fac62702a..f03dfddcf8 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceCallData.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceCallData.java @@ -25,17 +25,15 @@ public class ConferenceCallData { public boolean hasRemoteVideoTrack; public boolean hasRemoteScreenShareTrack; public boolean mIsConference; - public boolean isOwnStreamActive; public ConferenceCallData() { init(); mIsConference = false; } - public ConferenceCallData(boolean isConference, boolean videoEnabled) { + public ConferenceCallData(boolean isConference) { init(); mIsConference = isConference; - isOwnStreamActive = videoEnabled; } private void init() { diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKListener.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKListener.java index b6bbde5325..38d424094b 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKListener.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKListener.java @@ -58,7 +58,7 @@ public interface ConferenceSDKListener { void onSpeakerStateChanged(boolean isSpeakerOn); - void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType); + void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType); void tryCallCameraStateChange(boolean pause); @@ -85,4 +85,8 @@ public interface ConferenceSDKListener { void showPurchaseDialog(boolean isModerator, final String message); void onPurchaseFinished(); + + void onBluetoothConnectivityChanged(boolean connected); + + void onCallPauseStateChanged(boolean paused); } diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKModule.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKModule.java index ad8ff305ed..99fe601a5f 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKModule.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceSDKModule.java @@ -97,7 +97,6 @@ public class ConferenceSDKModule extends BaseSDKModule { private static final int TOAST_COUNT_DOWN_INTERVAL = TOAST_DURATION_IN_MILLISECONDS / 2; private static final int SECOND = 1000; private static final int SECOND_IN_MINUTE = 60; - private static final String PHONE_STATE = "android.intent.action.PHONE_STATE"; private static final String FREE_TRIAL_180_DAYS = "ndfg9e58u9e8vh0w948t"; public static long READ_PHONE_STATE_RECORD_AUDIO_FLAG = 3; // (1|2) @@ -148,8 +147,6 @@ public class ConferenceSDKModule extends BaseSDKModule { private HashMap mConferenceWaitingRoomLNames = new HashMap<>(); private HashMap mMyAcceptedElsewhereCalls = new HashMap<>(); - private int mLastPhoneCallState = TelephonyManager.CALL_STATE_IDLE; - private enum States { Connecting, Connected, Disconnecting, Disconnected } @@ -191,19 +188,7 @@ public class ConferenceSDKModule extends BaseSDKModule { } public void mute() { - if (mActiveConference == null) return; - if (mActiveConference.mConference != null) { - if (mActiveConference.isMuted) { - mActiveConference.mConference.unmute(); - } else { - mActiveConference.mConference.mute(); - } - mActiveConference.isMuted = !mActiveConference.isMuted; - - - for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) - conferenceSDKListener.onMicrophoneStateChanged(mActiveConference.isMuted); - } + muteMic(!mActiveConference.mState.isMuted); } public void resetCallLink() { @@ -213,17 +198,17 @@ public class ConferenceSDKModule extends BaseSDKModule { public void setMuteState(boolean mute) { if (mActiveConference == null) return; if (mActiveConference.mConference != null) { - if (mute == mActiveConference.isMuted) return; + if (mute == mActiveConference.mState.isMuted) return; if (mute) { mActiveConference.mConference.mute(); } else { mActiveConference.mConference.unmute(); } - mActiveConference.isMuted = mute; + mActiveConference.mState.isMuted = mute; for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) - conferenceSDKListener.onMicrophoneStateChanged(mActiveConference.isMuted); + conferenceSDKListener.onMicrophoneStateChanged(mActiveConference.mState.isMuted); } } @@ -248,6 +233,25 @@ public class ConferenceSDKModule extends BaseSDKModule { } } + public void muteMic(boolean mute) { + if (mActiveConference == null) return; + if (mActiveConference.mConference != null) { + boolean changed = false; + if (mActiveConference.mState.isMuted && !mute) { + mActiveConference.mConference.unmute(); + changed = true; + } else if (!mActiveConference.mState.isMuted && mute) { + mActiveConference.mConference.mute(); + changed = true; + } + if (changed) { + mActiveConference.mState.isMuted = mute; + } + for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) + conferenceSDKListener.onMicrophoneStateChanged(mActiveConference.mState.isMuted); + } + } + private boolean isCallAdHoc() { if (!hasCreatedActiveCall()) return false; if (mActiveConference.mConference == null) return false; @@ -570,7 +574,7 @@ public class ConferenceSDKModule extends BaseSDKModule { } if (hasCreatedActiveCall()) { - mActiveConference.isSpeakerOn = on; + mActiveConference.mState.isSpeakerOn = on; if (forced) mActiveConference.mIsSpeakerForceStopped = (forced && !on); } @@ -581,11 +585,11 @@ public class ConferenceSDKModule extends BaseSDKModule { } } - public void setAudioRoute(ActiveCallBase.AudioRouteType routeType) { + public void setAudioRoute(CallStateData.AudioRouteType routeType) { setAudioRoute(routeType, true); } - public void setAudioRoute(ActiveCallBase.AudioRouteType routeType, boolean updateWith, boolean delayed) { + public void setAudioRoute(CallStateData.AudioRouteType routeType, boolean updateWith, boolean delayed) { if (delayed) { mHandler.postDelayed(() -> { setAudioRoute(routeType, true); @@ -595,7 +599,7 @@ public class ConferenceSDKModule extends BaseSDKModule { } } - public void setAudioRoute(ActiveCallBase.AudioRouteType routeType, boolean updateWith) { + public void setAudioRoute(CallStateData.AudioRouteType routeType, boolean updateWith) { if (mConferenceAudioManager == null) { mConferenceAudioManager = AppRTCAudioManager.create(getContext()); } @@ -615,7 +619,7 @@ public class ConferenceSDKModule extends BaseSDKModule { break; } if (updateWith && hasCreatedActiveCall()) { - mActiveConference.mAudioRouteType = routeType; + mActiveConference.mState.mAudioRouteType = routeType; } for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) @@ -1138,7 +1142,7 @@ public class ConferenceSDKModule extends BaseSDKModule { NYNCallParticipant participant = participantArray.get(index); if (!participant.isSpeaking()) { continue; - } else if (participant.isMe() && mActiveConference.isMuted) { + } else if (participant.isMe() && mActiveConference.mState.isMuted) { continue; } if (!activeSpeakers.isEmpty()) activeSpeakers += ", "; @@ -1159,8 +1163,8 @@ public class ConferenceSDKModule extends BaseSDKModule { NYNCallParticipant participant = participantArray.get(index); if (participant.isMe()) { for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) { - mActiveConference.isMuted = isMuted; - conferenceSDKListener.onMuteStateChangedByHost(mActiveConference.isMuted); + mActiveConference.mState.isMuted = isMuted; + conferenceSDKListener.onMuteStateChangedByHost(mActiveConference.mState.isMuted); } return; } @@ -1292,11 +1296,7 @@ public class ConferenceSDKModule extends BaseSDKModule { }); } - public boolean isReadPhoneStatePermissionGranted() { - return (ActivityCompat.checkSelfPermission(getContext(), Manifest.permission.READ_PHONE_STATE) == PackageManager.PERMISSION_GRANTED); - } - - public boolean isForAudioCallsPermissionGranted() { + public boolean isForAudioCallsPermissionGranted() { return (ActivityCompat.checkSelfPermission(getContext(), Manifest.permission.RECORD_AUDIO) == PackageManager.PERMISSION_GRANTED); } @@ -1330,9 +1330,7 @@ public class ConferenceSDKModule extends BaseSDKModule { } private void addCallManagerListener() { - if (isReadPhoneStatePermissionGranted()) { - registerIncomingCallReceiver(getContext()); - } + // TODO: request READ_PHONE_STATE permission!!!! mCallManagerListener = new INYNCallManagerListener() { @Override @@ -1610,6 +1608,9 @@ public class ConferenceSDKModule extends BaseSDKModule { private void onScreenShareState(String callId, boolean active) { // not need twice for active call or not!!! + if (mActiveConference != null) { + mActiveConference.mState.isOwnSSActive = active; + } for (ConferenceSDKListener conferenceListener : mConferenceSDKListener) { conferenceListener.onScreenShareState(active); } @@ -1706,7 +1707,7 @@ public class ConferenceSDKModule extends BaseSDKModule { if (!hasCreatedActiveCall()) return; if (mActiveConference.mConference == null) return; if (mActiveConference.mConference.callId().contentEquals(callId)) { - mActiveConference.mData.isOwnStreamActive = true; + mActiveConference.mState.isOwnStreamActive = true; for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) { conferenceSDKListener.onLocalVideoCapturerStarted(mActiveConference); } @@ -1717,7 +1718,7 @@ public class ConferenceSDKModule extends BaseSDKModule { if (!hasCreatedActiveCall()) return; if (mActiveConference.mConference == null) return; if (mActiveConference.mConference.callId().contentEquals(callId)) { - mActiveConference.mData.isOwnStreamActive = false; + mActiveConference.mState.isOwnStreamActive = false; if (mActiveConference.isConference()) { new Handler(Looper.getMainLooper()).post(() -> { mActiveConference.mConference.setLocalVideoRenderer(null); @@ -2150,7 +2151,7 @@ public class ConferenceSDKModule extends BaseSDKModule { mConferenceDetails = new ConferenceDetails(getDeviceId()); mActiveConference = createActiveConference(null, contact.phoneId, true, isVideoEnabled, ActiveCallBase.CallType.P2PCall); - mActiveConference.mData.isOwnStreamActive = isVideoEnabled; + mActiveConference.mState.isOwnStreamActive = isVideoEnabled; mActiveConference.addMember(contact); setConferenceCallName(mActiveConference, contact.getFullName()); AppsTrackerUtils.getCleverTapInstance().trackEvent(getContext(), AppsTrackerConsts.ATEventMakeP2PCall); @@ -2663,9 +2664,9 @@ public class ConferenceSDKModule extends BaseSDKModule { if (mActiveConference.isCallInProgress()) return; if (mConferenceAudioManager != null) { mConferenceAudioManager.start(null); - mActiveConference.isSpeakerOn = mActiveConference.isReceivingVideo(); + mActiveConference.mState.isSpeakerOn = mActiveConference.isReceivingVideo(); if (!isSpeakerPhoneForced) { - if (mActiveConference.isSpeakerOn) { + if (mActiveConference.mState.isSpeakerOn) { mConferenceAudioManager.setDefaultAudioDevice(AppRTCAudioManager.AudioDevice.SPEAKER_PHONE); } else { mConferenceAudioManager.setDefaultAudioDevice(AppRTCAudioManager.AudioDevice.EARPIECE); @@ -2917,7 +2918,7 @@ public class ConferenceSDKModule extends BaseSDKModule { mConferenceDetails = new ConferenceDetails(getDeviceId(), iConference.callId()); mActiveConference = createActiveConference(iConference); if (!hasCreatedActiveCall()) return false; - mActiveConference.mData.isOwnStreamActive = false; + mActiveConference.mState.isOwnStreamActive = false; initConferenceCall(startActivity); Timber.d("createIncomingCallAndStartRinging with \'ConferenceId\'=\'" + callId + "; startActivity=" + (startActivity?"true": "false")); @@ -3110,7 +3111,7 @@ public class ConferenceSDKModule extends BaseSDKModule { onCallReady(callId, videoEnabled); if (mActiveConference != null && mActiveConference.mInitialStartCapturer && - mActiveConference.mData.isOwnStreamActive && + mActiveConference.mState.isOwnStreamActive && mActiveConference.isOutgoingCall && mActiveConference.mConference != null && mActiveConference.mConference.isModerator()) { @@ -3143,7 +3144,7 @@ public class ConferenceSDKModule extends BaseSDKModule { mActiveConference.mCallStartTime = System.currentTimeMillis(); } stopRinging(); - mActiveConference.isSpeakerOn = mActiveConference.isReceivingVideo(); + mActiveConference.mState.isSpeakerOn = mActiveConference.isReceivingVideo(); for (ConferenceSDKListener conferenceSDKListener : mConferenceSDKListener) conferenceSDKListener.onConferenceConnected(mActiveConference); startTimer(); @@ -3468,13 +3469,6 @@ public class ConferenceSDKModule extends BaseSDKModule { } } - private void registerIncomingCallReceiver(Context context) { - IntentFilter phoneCall = new IntentFilter(); - phoneCall.addAction(PHONE_STATE); - incomingCallReceiver = new PhoneCallReceiver(); - context.registerReceiver(incomingCallReceiver, phoneCall); - } - public void endActiveCall() { if (mActiveConference != null && mActiveConference.mConference != null && !mActiveConference.mConference.isOutgoing()) { @@ -3490,34 +3484,6 @@ public class ConferenceSDKModule extends BaseSDKModule { } } - private class PhoneCallReceiver extends BroadcastReceiver { - - @Override - public void onReceive(Context context, Intent intent) { - Timber.d("ConferenceModule::onReceive(): Telephony service event"); - String action = intent.getAction(); - if (action != null && action.equals(PHONE_STATE)) { - TelephonyManager tm = (TelephonyManager) context.getSystemService(Service.TELEPHONY_SERVICE); - if (isConferenceActive()) { - if (tm != null) { - if (tm.getCallState() == TelephonyManager.CALL_STATE_OFFHOOK) { - endActiveCall(); - } else if (tm.getCallState() == TelephonyManager.CALL_STATE_RINGING) { - setAudioRoute(ActiveCallBase.AudioRouteType.EARPIECE, false); - //setSpeakerState(false, true, true); - } else if (mLastPhoneCallState == TelephonyManager.CALL_STATE_RINGING - && tm.getCallState() == TelephonyManager.CALL_STATE_IDLE) { - setAudioRoute(mActiveConference.mAudioRouteType, true); - } - } - } - if (tm != null) { - mLastPhoneCallState = tm.getCallState();//TelephonyManager.CALL_STATE_IDLE; - } - } - } - } - public void createConferenceEx(String subject, String chatRoomId, boolean deleteGroupIfNoMessages, @@ -3538,7 +3504,7 @@ public class ConferenceSDKModule extends BaseSDKModule { replaceCallEx(subject, deleteGroupIfNoMessages, deleteAfterCall, isVideoConference, mActiveConference.mConference.callId(), - contacts, mActiveConference.mData.isOwnStreamActive); + contacts, mActiveConference.mState.isOwnStreamActive); } else { createAndStartConferenceEx(subject, chatRoomId, deleteGroupIfNoMessages, deleteAfterCall, isVideoConference, contacts); @@ -3728,7 +3694,15 @@ public class ConferenceSDKModule extends BaseSDKModule { private void switchToBTDevice() { setSpeakerState(false, true, false); - setAudioRoute(ActiveCallBase.AudioRouteType.BLUETOOTH, true, true); + setAudioRoute(CallStateData.AudioRouteType.BLUETOOTH, true, true); + } + + private void onBluetoothConnectivityChanged(boolean connected) { + synchronized (mConferenceSDKListener) { + for (ConferenceSDKListener sdkListener : mConferenceSDKListener) { + sdkListener.onBluetoothConnectivityChanged(connected); + } + } } @Override @@ -3738,9 +3712,11 @@ public class ConferenceSDKModule extends BaseSDKModule { switch (hs.getState()) { case Connected: switchToBTDevice(); + onBluetoothConnectivityChanged(true); break; case Disconnected: - setAudioRoute(ActiveCallBase.AudioRouteType.EARPIECE, true, true); + setAudioRoute(CallStateData.AudioRouteType.EARPIECE, true, true); + onBluetoothConnectivityChanged(false); break; case Play: case Pause: @@ -3792,6 +3768,80 @@ public class ConferenceSDKModule extends BaseSDKModule { return false; } + // PSTN calls state handling + public void onPstnCallState(int oldState, int newState) { + if (isConferenceActive()) { + switch (newState) { + case TelephonyManager.CALL_STATE_OFFHOOK: { +// endActiveCall(); + onPstnCallStateChaged(true); + } + break; + case TelephonyManager.CALL_STATE_RINGING: { + setAudioRoute(CallStateData.AudioRouteType.EARPIECE, false); + } + break; + case TelephonyManager.CALL_STATE_IDLE: { + if (oldState == TelephonyManager.CALL_STATE_RINGING) { + setAudioRoute(mActiveConference.mState.mAudioRouteType, true); + } else if (oldState == TelephonyManager.CALL_STATE_OFFHOOK) { + onPstnCallStateChaged(false); + } + } + break; + } + } + } + + public synchronized boolean isCallPaused() { + if (mActiveConference == null) return false; + return (mActiveConference.mState.isPaused && + mActiveConference.mState.pauseRestoreState != null); + } + + private synchronized void pauseCall() { + mActiveConference.mState.pause(); + pauseCallVideoCapturer(); + muteMic(true); + stopScreenCapture(); + + synchronized (mConferenceSDKListener) { + for (ConferenceSDKListener sdkListener : mConferenceSDKListener) { + sdkListener.onCallPauseStateChanged(mActiveConference.mState.isPaused); + } + } + } + + + public synchronized void resumeCall() { + mActiveConference.mState.isPaused = false; + if (mActiveConference.mState.pauseRestoreState != null) { + if (mActiveConference.mState.pauseRestoreState.isOwnStreamActive) { + resumeCallVideoCapturer(); + } + muteMic(mActiveConference.mState.pauseRestoreState.isMuted); + setAudioRoute(mActiveConference.mState.pauseRestoreState.mAudioRouteType, true); + if (mActiveConference.mState.pauseRestoreState.isOwnSSActive) { + startScreenCapture(); + } + mActiveConference.mState.resume(); + } + + synchronized (mConferenceSDKListener) { + for (ConferenceSDKListener sdkListener : mConferenceSDKListener) { + sdkListener.onCallPauseStateChanged(mActiveConference.mState.isPaused); + } + } + } + + private void onPstnCallStateChaged(boolean pstnActive) { + if (pstnActive) { + pauseCall(); + } else { + resumeCall(); + } + } + private class AsyncJoinToConferenceByLink extends AsyncTask { @Override protected Void doInBackground(String... strings) { diff --git a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceService.java b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceService.java index 125887423e..7be8384755 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceService.java +++ b/app/src/main/java/com/nynja/mobile/communicator/data/sdk/calls/ConferenceService.java @@ -259,11 +259,11 @@ public class ConferenceService extends Service implements SensorEventListener { private void setSpeakerData(boolean isProximityNear) { ConferenceSDKModule conferenceSDKModule = mDataManager.getConferenceSDK(); ActiveConferenceCall activeConference = conferenceSDKModule.getActiveConference(); - if (activeConference != null && ((activeConference.isSpeakerOn && isProximityNear) - || (!activeConference.isSpeakerOn && !isProximityNear))) { - if ((activeConference.isSpeakerOn && isProximityNear)) { + if (activeConference != null && ((activeConference.mState.isSpeakerOn && isProximityNear) + || (!activeConference.mState.isSpeakerOn && !isProximityNear))) { + if ((activeConference.mState.isSpeakerOn && isProximityNear)) { conferenceSDKModule.setSpeakerState(false); - } else if ((!activeConference.isSpeakerOn && !isProximityNear)) { + } else if ((!activeConference.mState.isSpeakerOn && !isProximityNear)) { // set speaker on - if not forced stop... if (!activeConference.mIsSpeakerForceStopped) conferenceSDKModule.setSpeakerState(true); diff --git a/app/src/main/java/com/nynja/mobile/communicator/mvp/presenters/CallActivityPresenter.java b/app/src/main/java/com/nynja/mobile/communicator/mvp/presenters/CallActivityPresenter.java index 23b74d341e..29945a56c3 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/mvp/presenters/CallActivityPresenter.java +++ b/app/src/main/java/com/nynja/mobile/communicator/mvp/presenters/CallActivityPresenter.java @@ -6,6 +6,7 @@ import com.nynja.mobile.communicator.data.models.events.local.Event; import com.nynja.mobile.communicator.data.models.events.local.SimpleEvent; import com.nynja.mobile.communicator.data.sdk.ConferenceSDKPresenter; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; import com.nynja.mobile.communicator.mvp.view.CallActivityView; /** @@ -101,25 +102,22 @@ public class CallActivityPresenter extends ConferenceSDKPresenter public boolean isMuted() { - return mDataManager.getConferenceSDK().getActiveConference().isMuted; + return mDataManager.getConferenceSDK().getActiveConference().mState.isMuted; } - public void setAudioRoute(ActiveCallBase.AudioRouteType audioRouteType) { + public void setAudioRoute(CallStateData.AudioRouteType audioRouteType) { mDataManager.getConferenceSDK().setAudioRoute(audioRouteType); } @@ -326,7 +327,7 @@ public class ConferenceCallPresenter extends ConferenceSDKPresenter if (activeConferenceCall.mData.mParticipantArray != null) { for (int index = 0; index < activeConferenceCall.mData.mParticipantArray.size(); index++) { NYNCallParticipant participant = activeConferenceCall.mData.mParticipantArray.get(index); - members.add(conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mData.isOwnStreamActive)); + members.add(conferenceParticipant(participant, participant.isOwner(), activeConferenceCall.mState.isOwnStreamActive)); } } else { for (int index = 0; index < activeConferenceCall.getMembers().size(); index++) { @@ -401,7 +402,7 @@ public class ConferenceCallPresenter extends ConferenceSDKPresenter } @Override - public void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType) { + public void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType) { if (getAttachedViews().size() == 0) return; getViewState().onAudioRouteChange(audioRouteType); } @@ -426,6 +427,11 @@ public class ConferenceCallPresenter extends ConferenceSDKPresenter getViewState().updateMicrophonState(isMuted); } + @Override public void onBluetoothConnectivityChanged(boolean connected) { + if (getAttachedViews().size() == 0) return; + getViewState().onBluetoothConnectivityChanged(connected); + } + public void onClickPortOut() { //TODO StasS implement it } @@ -647,10 +653,6 @@ public class ConferenceCallPresenter extends ConferenceSDKPresenter return mDataManager.getConferenceSDK().getIsCallFromHome(); } - public boolean isReadPhoneStatePermissionGranted() { - return mDataManager.getConferenceSDK().isReadPhoneStatePermissionGranted(); - } - public boolean isForAudioCallsPermissionGranted() { return mDataManager.getConferenceSDK().isForAudioCallsPermissionGranted(); } diff --git a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallActivityView.java b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallActivityView.java index 2ffd3c3131..974bced6a0 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallActivityView.java +++ b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallActivityView.java @@ -29,4 +29,6 @@ public interface CallActivityView extends ErrorMvpView { void showPurchaseDialog(boolean isModerator, final String message); void closeActivity(); + + void onCallPauseStateChanged(boolean paused); } \ No newline at end of file diff --git a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallTapToSpeakView.java b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallTapToSpeakView.java index 2f87ef0293..8ea6de3f4a 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallTapToSpeakView.java +++ b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallTapToSpeakView.java @@ -1,6 +1,6 @@ package com.nynja.mobile.communicator.mvp.view; -import com.nynja.mobile.communicator.data.conference.ActiveCallBase; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; /** * Created by Ergyun Syuleyman on 9/14/18. @@ -19,6 +19,8 @@ public interface CallTapToSpeakView extends BaseMvpView, ErrorMvpView { void onSpeakerStateChanged(boolean isSpeakerOn); - void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType); + void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType); + + void onBluetoothConnectivityChanged(boolean connected); } diff --git a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallView.java b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallView.java index da0f547e22..e02de31161 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallView.java +++ b/app/src/main/java/com/nynja/mobile/communicator/mvp/view/CallView.java @@ -2,8 +2,8 @@ package com.nynja.mobile.communicator.mvp.view; import android.support.annotation.StringRes; -import com.nynja.mobile.communicator.data.conference.ActiveCallBase; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; import com.nynja.mobile.communicator.data.sdk.calls.ConferenceListItem; import com.nynja.mobile.communicator.data.models.nynjamodels.ContactModel; import com.nynja.mobile.communicator.data.models.nynjamodels.RoomModel; @@ -76,7 +76,7 @@ public interface CallView extends ErrorMvpView { void showLeaveConferenceCallConfirmation(); - void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType); + void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType); void closenConference(); @@ -90,4 +90,6 @@ public interface CallView extends ErrorMvpView { void continueWithScreenshare(); + void onBluetoothConnectivityChanged(boolean connected); + } diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/activities/MainActivity.java b/app/src/main/java/com/nynja/mobile/communicator/ui/activities/MainActivity.java index 8a05b760f4..95187f2dcd 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/activities/MainActivity.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/activities/MainActivity.java @@ -196,6 +196,8 @@ public class MainActivity extends BaseActivity implements MainActivityView, mNynjaNavigationView.hideAllWheels(); initFirstWheel(); }); + + requestStorageAndPhoneStatePermissions(); } @Override @@ -217,7 +219,6 @@ public class MainActivity extends BaseActivity implements MainActivityView, @Override protected void onStart() { super.onStart(); - requestStoragePermissions(); } @Override @@ -246,8 +247,9 @@ public class MainActivity extends BaseActivity implements MainActivityView, } } - private void requestStoragePermissions() { - addDisposable(mRxPermissions.requestEachCombined(Manifest.permission.WRITE_EXTERNAL_STORAGE, + private void requestStorageAndPhoneStatePermissions() { + addDisposable(mRxPermissions.requestEachCombined(Manifest.permission.READ_PHONE_STATE, + Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE) .subscribe(permission -> { }, Timber::e)); @@ -611,7 +613,7 @@ public class MainActivity extends BaseActivity implements MainActivityView, chatAudioLayout.setVisibility(View.VISIBLE); mPresenter.requestUser(); //TODO: video feeds support in next features - //if (!activeConferenceCall.mData.isOwnStreamActive || !activeConferenceCall.hasRemoteVideoTrack) { + //if (!activeConferenceCall.mState.isOwnStreamActive || !activeConferenceCall.hasRemoteVideoTrack) { // video.setVisibility(View.GONE); // chatAudioLayout.setVisibility(View.VISIBLE); // mPresenter.requestUser(); @@ -985,4 +987,5 @@ public class MainActivity extends BaseActivity implements MainActivityView, } ); } + } diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/activities/calls/CallActivity.java b/app/src/main/java/com/nynja/mobile/communicator/ui/activities/calls/CallActivity.java index 41540caf4a..b7ba56b0fa 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/activities/calls/CallActivity.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/activities/calls/CallActivity.java @@ -14,10 +14,16 @@ import android.media.projection.MediaProjectionManager; import android.os.Build; import android.os.Bundle; import android.support.v4.view.ViewPager; +import android.view.MotionEvent; +import android.view.View; +import android.widget.RelativeLayout; import com.arellomobile.mvp.presenter.InjectPresenter; import com.nynja.mobile.communicator.R; +import com.nynja.mobile.communicator.data.audio.headphones.HeadphoneMonitoringService; +import com.nynja.mobile.communicator.data.audio.headphones.HeadphoneStateBroadcastReceiver; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.BluetoothConnectivityListener; import com.nynja.mobile.communicator.mvp.presenters.CallActivityPresenter; import com.nynja.mobile.communicator.mvp.view.CallActivityView; import com.nynja.mobile.communicator.ui.adapters.conference.ActiveCallPagerAdapter; @@ -31,6 +37,7 @@ import org.webrtc.ContextUtils; import org.webrtc.VideoSourceUtility; import butterknife.BindView; +import butterknife.OnClick; import kotlin.jvm.Synchronized; import ru.terrakok.cicerone.Navigator; import timber.log.Timber; @@ -41,17 +48,12 @@ public class CallActivity extends BaseActivity implements CallActivityView { @BindView(R.id.active_call_viewpager) CustomViewPager mViewPager; @BindView(R.id.active_call_indicator) CirclePageIndicator mIndicator; + @BindView(R.id.active_call_paused_content) RelativeLayout mCallPaused; // @BindView(R.id.active_call_rv) RecyclerView mRecyclerView; @InjectPresenter CallActivityPresenter mPresenter; - public interface BluetoothConnectivityListener { - void onBluetoothDeviceConnected(); - - void onBluetoothDeviceDisconnected(); - } - private ActiveCallPagerAdapter mPagerAdapter; private int mSelectedPage = -1; @@ -71,13 +73,13 @@ public class CallActivity extends BaseActivity implements CallActivityView { ContextUtils.createRootEglBase(); ContextUtils.createSSEglBase(); - if (isBluetoothHeadsetConnected()) { - mPresenter.bluetoothConnected(); - } - initUI(); + } - registerBluetoothReceiver(); + @Override + protected void onStart() { + mCallPaused.setVisibility(mPresenter.isCallPaused() ? View.VISIBLE : View.GONE); + super.onStart(); } private void initUI() { @@ -88,6 +90,12 @@ public class CallActivity extends BaseActivity implements CallActivityView { mIndicator.setSaveEnabled(false); mIndicator.setViewPager(mViewPager, mPagerAdapter.getFragmentPositionByType(ActiveCallPagerAdapter.CallPages.CallPageActiveCallFragment)); mIndicator.notifyDataSetChanged(); + mCallPaused.setOnTouchListener(new View.OnTouchListener() { + @Override + public boolean onTouch(View view, MotionEvent motionEvent) { + return true; + } + }); } private void initUIRv() { @@ -183,7 +191,6 @@ public class CallActivity extends BaseActivity implements CallActivityView { @Override protected void onDestroy() { - unregisterReceiver(mBluetoothReceiver); mPagerAdapter.reset(); mViewPager.removeAllViews(); releaseWakeLockActivity(); @@ -253,7 +260,7 @@ public class CallActivity extends BaseActivity implements CallActivityView { if (mPagerAdapter != null) { mPagerAdapter.initFlags(activeConferenceCall.mData.hasRemoteScreenShareTrack, ((activeConferenceCall.mData.hasRemoteVideoTrack() || - activeConferenceCall.mData.isOwnStreamActive) && + activeConferenceCall.mState.isOwnStreamActive) && activeConferenceCall.isConference())); } } @@ -288,57 +295,6 @@ public class CallActivity extends BaseActivity implements CallActivityView { finish(); } - public boolean isBluetoothHeadsetConnected() { - BluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); - return mBluetoothAdapter != null && - mBluetoothAdapter.isEnabled() && - mBluetoothAdapter.getProfileConnectionState(BluetoothHeadset.HEADSET) == BluetoothHeadset.STATE_CONNECTED; - } - - - //The BroadcastReceiver that listens for bluetooth broadcasts - private final BroadcastReceiver mBluetoothReceiver = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - String action = intent.getAction(); - - if (BluetoothDevice.ACTION_FOUND.equals(action)) { - //Device found - } else if (BluetoothDevice.ACTION_ACL_CONNECTED.equals(action)) { - //Device is now connected - bluetoothConnected(); - } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(action)) { - //Done searching - } else if (BluetoothDevice.ACTION_ACL_DISCONNECT_REQUESTED.equals(action)) { - //Device is about to disconnect - } else if (BluetoothDevice.ACTION_ACL_DISCONNECTED.equals(action)) { - //Device has disconnected - bluetoothDisconnected(); - } - } - }; - - private void registerBluetoothReceiver() { - IntentFilter filter = new IntentFilter(); - filter.addAction(BluetoothDevice.ACTION_ACL_CONNECTED); - filter.addAction(BluetoothDevice.ACTION_ACL_DISCONNECT_REQUESTED); - filter.addAction(BluetoothDevice.ACTION_ACL_DISCONNECTED); - registerReceiver(mBluetoothReceiver, filter); - } - - private void bluetoothConnected() { - mPresenter.bluetoothConnected(); - for (int i = 0; i < mPagerAdapter.getCount(); i++) { - if (mPagerAdapter.getItem(i) instanceof BluetoothConnectivityListener) { - ((BluetoothConnectivityListener) mPagerAdapter.getItem(i)).onBluetoothDeviceConnected(); - } - } - } - - private void bluetoothDisconnected() { - mPresenter.bluetoothDisconnected(); - } - @Override public void onRemoteScreenShareTrackAdded(ActiveConferenceCall activeConferenceCall, String trackId) { final boolean hasRemoteScreenShareTrack = (activeConferenceCall != null && activeConferenceCall.mData.hasRemoteScreenShareTrack); @@ -410,14 +366,14 @@ public class CallActivity extends BaseActivity implements CallActivityView { boolean updated = false; synchronized (mPagerAdapter) { - if (show && (activeConferenceCall.mData.hasRemoteVideoTrack() || activeConferenceCall.mData.isOwnStreamActive)) { + if (show && (activeConferenceCall.mData.hasRemoteVideoTrack() || activeConferenceCall.mState.isOwnStreamActive)) { mViewPager.removeOnPageChangeListener(mOnPageChangeListener); mViewPager.setAdapter(null); mPagerAdapter.showConferenceVideoScreen(); mViewPager.addOnPageChangeListener(mOnPageChangeListener); mViewPager.setAdapter(mPagerAdapter); updated = true; - } else if (!activeConferenceCall.mData.hasRemoteVideoTrack() && !activeConferenceCall.mData.isOwnStreamActive){ + } else if (!activeConferenceCall.mData.hasRemoteVideoTrack() && !activeConferenceCall.mState.isOwnStreamActive){ mViewPager.removeOnPageChangeListener(mOnPageChangeListener); mViewPager.setAdapter(null); mPagerAdapter.hideConferenceVideoScreen(); @@ -441,4 +397,19 @@ public class CallActivity extends BaseActivity implements CallActivityView { } } + @Override public void onCallPauseStateChanged(boolean paused) { + mHandler.post(() -> { + mCallPaused.setVisibility(paused ? View.VISIBLE : View.GONE); + }); + } + + @OnClick(R.id.active_call_paused_button_sircle) + void onResumeCall() { + mPresenter.resumeCall(); + } + + public boolean isBluetoothHeadsetConnected() { + return HeadphoneMonitoringService.isBluetoothHeadsetConnected(); + } + } diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/base/BaseActivity.java b/app/src/main/java/com/nynja/mobile/communicator/ui/base/BaseActivity.java index 7c1509748a..d5d20f1e2f 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/base/BaseActivity.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/base/BaseActivity.java @@ -116,7 +116,7 @@ public abstract class BaseActivity extends MvpAppCompatActivity implements BaseA mLayoutListenerWrapper = new OnGlobalLayoutListenerWrapper(this); wakeLockActivityIfNeeds(); - requestPermissions(); + //requestPermissions(); } protected void wakeLockActivityIfNeeds() { diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/CallTapToSpeakFragment.java b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/CallTapToSpeakFragment.java index e15e1d129e..77be42c95b 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/CallTapToSpeakFragment.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/CallTapToSpeakFragment.java @@ -20,8 +20,8 @@ import android.widget.Toast; import com.arellomobile.mvp.presenter.InjectPresenter; import com.nynja.mobile.communicator.R; -import com.nynja.mobile.communicator.data.conference.ActiveCallBase; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; import com.nynja.mobile.communicator.mvp.presenters.CallTapToSpeakPresenter; import com.nynja.mobile.communicator.mvp.view.CallTapToSpeakView; import com.nynja.mobile.communicator.ui.activities.calls.CallActivity; @@ -40,7 +40,7 @@ import static org.webrtc.ContextUtils.getApplicationContext; */ public class CallTapToSpeakFragment extends BaseFragment - implements CallTapToSpeakView, CallActivity.BluetoothConnectivityListener { + implements CallTapToSpeakView { @BindView(R.id.active_call_hold_to_speak_speaker) CheckableImageView speaker; @BindView(R.id.active_call_hold_to_speak_header_leave_text) TextView leave; @@ -177,7 +177,7 @@ public class CallTapToSpeakFragment extends BaseFragment @Override public void onSpeakerStateChanged(boolean isSpeakerOn) { if (isAdded() && isActive) { - getActivity().runOnUiThread(() -> updateSpeakerState(isSpeakerOn, ActiveCallBase.AudioRouteType.EARPIECE)); + getActivity().runOnUiThread(() -> updateSpeakerState(isSpeakerOn, CallStateData.AudioRouteType.EARPIECE)); } } @@ -201,15 +201,15 @@ public class CallTapToSpeakFragment extends BaseFragment DialogFactory.showActionSheetDialog(getContext(), itemPosition -> { switch (itemPosition) { case 0: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.SPEAKER); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.SPEAKER); break; case 1: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.EARPIECE); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.EARPIECE); break; case 2: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.BLUETOOTH); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.BLUETOOTH); break; } }, @@ -220,7 +220,7 @@ public class CallTapToSpeakFragment extends BaseFragment } @Override - public void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType) { + public void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType) { if (speaker == null) { return; } @@ -249,19 +249,25 @@ public class CallTapToSpeakFragment extends BaseFragment } @Override - public void onBluetoothDeviceConnected() { + public void onBluetoothConnectivityChanged(boolean connected) { + if (connected) { + onBluetoothDeviceConnected(); + } else { + onBluetoothDeviceDisconnected(); + } + } + + private void onBluetoothDeviceConnected() { if (getActivity() == null || !isAdded() || speaker == null) { return; } speaker.post(() -> { - speaker.setImageResource(R.drawable.ic_bluetooth_icon); speaker.setAutoToggle(false); }); } - @Override - public void onBluetoothDeviceDisconnected() { + private void onBluetoothDeviceDisconnected() { //mConferencePresenter.bluetoothDisconnected(); } @@ -279,7 +285,7 @@ public class CallTapToSpeakFragment extends BaseFragment if (isActive) { updateUI(); //save the mute state - mRestoreMuteTo = String.valueOf(mConferencePresenter.getActiveConference().isMuted); + mRestoreMuteTo = String.valueOf(mConferencePresenter.getActiveConference().mState.isMuted); mConferencePresenter.setMuteState(true); } else { // restore the mute @@ -321,8 +327,8 @@ public class CallTapToSpeakFragment extends BaseFragment private void updateUI() { ActiveConferenceCall activeConferenceCall = mConferencePresenter.getActiveConference(); if (activeConferenceCall != null) { - updateSpeakerState(activeConferenceCall.isSpeakerOn, activeConferenceCall.mAudioRouteType); - updateMicrophonState(activeConferenceCall.isMuted); + updateSpeakerState(activeConferenceCall.mState.isSpeakerOn, activeConferenceCall.mState.mAudioRouteType); + updateMicrophonState(activeConferenceCall.mState.isMuted); } } @@ -385,7 +391,7 @@ public class CallTapToSpeakFragment extends BaseFragment tapToSpeak.setSelected(!isMuted); } - private void updateSpeakerState(boolean isSpeakerOn, ActiveCallBase.AudioRouteType audioRouteType) { + private void updateSpeakerState(boolean isSpeakerOn, CallStateData.AudioRouteType audioRouteType) { if (speaker == null) { return; } diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceCallFragment.java b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceCallFragment.java index 3441886a6b..a790c4a1d7 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceCallFragment.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceCallFragment.java @@ -35,10 +35,12 @@ import android.widget.Toast; import com.arellomobile.mvp.presenter.InjectPresenter; import com.nynja.mobile.communicator.BuildConfig; import com.nynja.mobile.communicator.R; -import com.nynja.mobile.communicator.data.conference.ActiveCallBase; +import com.nynja.mobile.communicator.data.models.nynjamodels.ContactModel; import com.nynja.mobile.communicator.data.models.nynjamodels.ContactModel; import com.nynja.mobile.communicator.data.models.nynjamodels.RoomModel; import com.nynja.mobile.communicator.data.sdk.calls.ActiveConferenceCall; +import com.nynja.mobile.communicator.data.sdk.calls.BluetoothConnectivityListener; +import com.nynja.mobile.communicator.data.sdk.calls.CallStateData; import com.nynja.mobile.communicator.data.sdk.calls.ConferenceListItem; import com.nynja.mobile.communicator.interfaces.OnConferenceItemClickListener; import com.nynja.mobile.communicator.mvp.presenters.ConferenceCallPresenter; @@ -74,7 +76,7 @@ import timber.log.Timber; */ public class ConferenceCallFragment extends BaseFragment implements CallView, - OnConferenceItemClickListener, CallActivity.BluetoothConnectivityListener { + OnConferenceItemClickListener { private static final int FRONT_CAMERA = 1; private static final String PREFERENCE_NAME = "conference_calls"; @@ -241,7 +243,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, } if (mConferencePresenter.getActiveConference() != null) { - updateSpeakerState(mConferencePresenter.getActiveConference().isSpeakerOn); + updateSpeakerState(mConferencePresenter.getActiveConference().mState.isSpeakerOn); } } @@ -341,7 +343,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, void mute() { if (!audioMute.isEnabled()) return; if (muteMicHint.getVisibility() == View.VISIBLE) { - updateMicrophonState(mConferencePresenter.getActiveConference().isMuted); + updateMicrophonState(mConferencePresenter.getActiveConference().mState.isMuted); return; } showMuteMicHintIfNeed(); @@ -354,13 +356,11 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, if (isBluetoothHeadsetConnected()) { showAudioRoutActionSheet(); } else { - if (muteMicHint.getVisibility() == View.VISIBLE) { - updateSpeakerState(mConferencePresenter.getActiveConference().isSpeakerOn); - return; - } - if (getActivity() != null) { - callActivity.setIsSpeakerForced(true); - callActivity.setSpeakerState(!audioSpeaker.isChecked(), true); + if (audioSpeaker.isChecked()) { + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.EARPIECE); + } else { + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.SPEAKER); + } } } @@ -403,15 +403,15 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, DialogFactory.showActionSheetDialog(getContext(), itemPosition -> { switch (itemPosition) { case 0: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.SPEAKER); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.SPEAKER); break; case 1: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.EARPIECE); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.EARPIECE); break; case 2: - mConferencePresenter.setAudioRoute(ActiveCallBase.AudioRouteType.BLUETOOTH); + mConferencePresenter.setAudioRoute(CallStateData.AudioRouteType.BLUETOOTH); break; } }, @@ -565,7 +565,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, if (activeConferenceCall.isWaiting()) { waitingConference(activeConferenceCall); } else if ((activeConferenceCall.isVideoEnabled - || activeConferenceCall.mData.isOwnStreamActive) + || activeConferenceCall.mState.isOwnStreamActive) && !activeConferenceCall.isConference()){ videoConference(activeConferenceCall); //if (!activeConferenceCall.isSpeakerOn) @@ -933,9 +933,9 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, isActive = active; if (activeConferenceCall == null) return; if (active) { - updateMicrophonState(activeConferenceCall.isMuted); + updateMicrophonState(activeConferenceCall.mState.isMuted); if (activeConferenceCall.isVideoEnabled) { - if (activeConferenceCall.mData.isOwnStreamActive) { + if (activeConferenceCall.mState.isOwnStreamActive) { setLocalVideoRenderer(mConferencePresenter.getActiveConference()); mConferencePresenter.resumeCallVideoCapturer(); } @@ -946,7 +946,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, muteMicHint.setVisibility(View.GONE); mHandler.removeCallbacks(mShowMuteMicHintExpired); if (activeConferenceCall.isVideoEnabled) { - if (activeConferenceCall.mData.isOwnStreamActive) { + if (activeConferenceCall.mState.isOwnStreamActive) { //mConferencePresenter.pauseCallVideoCapturer(); removeLocalVideoRenderer(mConferencePresenter.getActiveConference()); } @@ -1172,7 +1172,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, private void requestPermissionIfNeeds(ActiveConferenceCall activeConferenceCall) { if (activeConferenceCall == null) return; - boolean enableVideo = (activeConferenceCall.mData.isOwnStreamActive + boolean enableVideo = (activeConferenceCall.mState.isOwnStreamActive && activeConferenceCall.mInitialStartCapturer); ArrayList permissions = getPermissionsForCall(enableVideo); @@ -1452,11 +1452,11 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, } private void initConference(ActiveConferenceCall activeConferenceCall) { - audioSpeaker.setChecked(activeConferenceCall.isSpeakerOn); - audioMute.setChecked(activeConferenceCall.isMuted); + audioSpeaker.setChecked(activeConferenceCall.mState.isSpeakerOn); + audioMute.setChecked(activeConferenceCall.mState.isMuted); videoOnOf.setChecked(mConferencePresenter.isCameraRunning()); //activeConferenceCall.isCameraRunning()); shareOnOf.setChecked(mConferencePresenter.isScreenSharing()); - setMuteText(activeConferenceCall.isMuted); + setMuteText(activeConferenceCall.mState.isMuted); videoRemotePhoto.setVisibility(View.GONE); videoRemote.setVisibility(View.GONE); videoLocal.setVisibility(View.GONE); @@ -1513,7 +1513,6 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, } } - private boolean isBluetoothHeadsetConnected() { if (getActivity() != null) { return ((CallActivity) getActivity()).isBluetoothHeadsetConnected(); @@ -1527,25 +1526,19 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, return; } - if (isBluetoothHeadsetConnected()) { - if (mConferencePresenter.getActiveConference() != null) { - onAudioRouteChange(mConferencePresenter.getActiveConference().mAudioRouteType); - } else { - audioSpeaker.setImageResource(R.drawable.ic_bluetooth_icon); - audioSpeakerLabel.setText(getString(R.string.bluetooth)); - } + if (mConferencePresenter.getActiveConference() != null) { + onAudioRouteChanged(mConferencePresenter.getActiveConference().mState.mAudioRouteType); } else { - audioSpeaker.setImageResource(R.drawable.speaker_selector); + audioSpeaker.setImageResource(R.drawable.ic_bluetooth_icon); audioSpeaker.setChecked(isSpeakerOn); - audioSpeakerLabel.setText(getString(R.string.speakerphone)); + audioSpeakerLabel.setText(getString(R.string.bluetooth)); } audioSpeaker.setAutoToggle(!isBluetoothHeadsetConnected()); } - @Override - public void onAudioRouteChange(ActiveCallBase.AudioRouteType audioRouteType) { - if (audioSpeaker == null) { + private void onAudioRouteChanged(CallStateData.AudioRouteType audioRouteType) { + if (audioSpeaker == null || audioSpeakerLabel == null) { return; } @@ -1576,17 +1569,14 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, } @Override - public void onBluetoothDeviceConnected() { - if (getActivity() == null || !isAdded() || audioSpeaker == null) { + public void onAudioRouteChange(CallStateData.AudioRouteType audioRouteType) { + if (audioSpeaker == null || audioSpeakerLabel == null) { return; } - audioSpeaker.post(() -> { - audioSpeaker.setImageResource(R.drawable.ic_bluetooth_icon); - audioSpeaker.setAutoToggle(false); + new Handler(Looper.getMainLooper()).post(() -> { + onAudioRouteChanged( audioRouteType); }); - - audioSpeakerLabel.setText(getString(R.string.bluetooth)); } @Override @@ -1636,6 +1626,15 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, getString(R.string.call_conference_alert_title), null); } + @Override + public void onBluetoothConnectivityChanged(boolean connected) { + if (connected) { + onBluetoothDeviceConnected(); + } else { + onBluetoothDeviceDisconnected(); + } + } + @Override public void continueWithScreenshare() { new Handler(Looper.getMainLooper()).postDelayed(() -> { @@ -1644,8 +1643,17 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, }, Consts.DELAY_300); } - @Override - public void onBluetoothDeviceDisconnected() { + private void onBluetoothDeviceConnected() { + if (getActivity() == null || !isAdded() || audioSpeaker == null) { + return; + } + + audioSpeaker.post(() -> { + audioSpeaker.setAutoToggle(false); + }); + } + + private void onBluetoothDeviceDisconnected() { //mConferencePresenter.bluetoothDisconnected(); } @@ -1657,7 +1665,7 @@ public class ConferenceCallFragment extends BaseFragment implements CallView, // check for 'GotIt' pressed before... if (isMuteMicHintGotIt()) return; if (mConferencePresenter.getActiveConference() != null - && !mConferencePresenter.getActiveConference().isMuted) { + && !mConferencePresenter.getActiveConference().mState.isMuted) { muteMicHint.setVisibility(View.VISIBLE); mHandler.postDelayed(mShowMuteMicHintExpired, MUTE_MIC_HINT_SHOWING_TIME); } diff --git a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceVideoFragment.java b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceVideoFragment.java index af28f6a56f..de7048d25d 100644 --- a/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceVideoFragment.java +++ b/app/src/main/java/com/nynja/mobile/communicator/ui/fragments/conference/ConferenceVideoFragment.java @@ -348,9 +348,9 @@ public class ConferenceVideoFragment extends BaseFragment implements ConferenceV isActive = active; if (activeConferenceCall == null) return; if (active) { - updateMicrophonState(activeConferenceCall.isMuted); + updateMicrophonState(activeConferenceCall.mState.isMuted); if (activeConferenceCall.isVideoEnabled) { - if (activeConferenceCall.mData.isOwnStreamActive) { + if (activeConferenceCall.mState.isOwnStreamActive) { setLocalVideoRenderer(mConferencePresenter.getActiveConference()); mConferencePresenter.resumeCallVideoCapturer(); } @@ -360,7 +360,7 @@ public class ConferenceVideoFragment extends BaseFragment implements ConferenceV scrollToMyFeedPosition(); } else { if (activeConferenceCall.isVideoEnabled) { - if (activeConferenceCall.mData.isOwnStreamActive) { + if (activeConferenceCall.mState.isOwnStreamActive) { mConferencePresenter.pauseCallVideoCapturer(); removeLocalVideoRenderer(mConferencePresenter.getActiveConference(), true); } diff --git a/app/src/main/res/layout/layout_call_paused.xml b/app/src/main/res/layout/layout_call_paused.xml new file mode 100644 index 0000000000..38b61cb349 --- /dev/null +++ b/app/src/main/res/layout/layout_call_paused.xml @@ -0,0 +1,52 @@ + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/layout/paged_activity_call.xml b/app/src/main/res/layout/paged_activity_call.xml index 566173356e..a4f952c255 100644 --- a/app/src/main/res/layout/paged_activity_call.xml +++ b/app/src/main/res/layout/paged_activity_call.xml @@ -3,6 +3,7 @@ xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" + android:background="@drawable/background" xmlns:app="http://schemas.android.com/apk/res-auto"> + + + diff --git a/app/src/main/res/values-en/strings.xml b/app/src/main/res/values-en/strings.xml index 4b8c7a2ef6..0957587f23 100644 --- a/app/src/main/res/values-en/strings.xml +++ b/app/src/main/res/values-en/strings.xml @@ -1340,5 +1340,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume diff --git a/app/src/main/res/values-es/strings.xml b/app/src/main/res/values-es/strings.xml index a93d6de9c0..44e9cd40c5 100644 --- a/app/src/main/res/values-es/strings.xml +++ b/app/src/main/res/values-es/strings.xml @@ -1339,5 +1339,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml index 3fb29a0c69..25a60f51e4 100644 --- a/app/src/main/res/values-ko/strings.xml +++ b/app/src/main/res/values-ko/strings.xml @@ -1339,5 +1339,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume diff --git a/app/src/main/res/values-zh-rCN/strings.xml b/app/src/main/res/values-zh-rCN/strings.xml index 4716478128..564ec7275f 100644 --- a/app/src/main/res/values-zh-rCN/strings.xml +++ b/app/src/main/res/values-zh-rCN/strings.xml @@ -1339,5 +1339,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume diff --git a/app/src/main/res/values-zh/strings.xml b/app/src/main/res/values-zh/strings.xml index 4716478128..564ec7275f 100644 --- a/app/src/main/res/values-zh/strings.xml +++ b/app/src/main/res/values-zh/strings.xml @@ -1339,5 +1339,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index d18544ed30..ff73bb5990 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1341,5 +1341,6 @@ To share your screen, you need to stop your camera first. Tap \"Continue\" below and we will stop your camera for you and start screen sharing. To start your camera, you need to stop screen sharing first. Continue + Resume -- GitLab From d028e5818bfe19b5219c22f277e2e08586c0100b Mon Sep 17 00:00:00 2001 From: Ergyun Syuleyman Date: Mon, 15 Jun 2020 11:26:46 +0300 Subject: [PATCH 2/2] -switched tyo use latest core SDK version - v.1.22.3 --- app/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/build.gradle b/app/build.gradle index 37883ecf7c..df102aa9bc 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -679,7 +679,7 @@ dependencies { implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version" // Conference, Calls mobile SDK - implementation 'com.nynja.sdk:NynjaSdk:1.22.2.1@aar' + implementation 'com.nynja.sdk:NynjaSdk:1.22.3@aar' //implementation(name: 'NynjaSdk-1.22.2', ext: 'aar') //ExoPlayer -- GitLab