mirror of
https://github.com/SchildiChat/SchildiChat-android.git
synced 2024-11-23 01:45:52 +03:00
Call: make PiP works with 2 calls
This commit is contained in:
parent
d3e4a3c010
commit
799cd99176
5 changed files with 100 additions and 74 deletions
|
@ -93,7 +93,6 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
}
|
||||
|
||||
private val callViewModel: VectorCallViewModel by viewModel()
|
||||
private lateinit var callArgs: CallArgs
|
||||
|
||||
@Inject lateinit var callManager: WebRtcCallManager
|
||||
@Inject lateinit var viewModelFactory: VectorCallViewModel.Factory
|
||||
|
@ -123,13 +122,6 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
window.navigationBarColor = Color.BLACK
|
||||
super.onCreate(savedInstanceState)
|
||||
|
||||
if (intent.hasExtra(MvRx.KEY_ARG)) {
|
||||
callArgs = intent.getParcelableExtra(MvRx.KEY_ARG)!!
|
||||
} else {
|
||||
Timber.tag(loggerTag.value).e("missing callArgs for VectorCall Activity")
|
||||
finish()
|
||||
}
|
||||
|
||||
Timber.tag(loggerTag.value).v("EXTRA_MODE is ${intent.getStringExtra(EXTRA_MODE)}")
|
||||
if (intent.getStringExtra(EXTRA_MODE) == INCOMING_RINGING) {
|
||||
turnScreenOnAndKeyguardOff()
|
||||
|
@ -152,16 +144,27 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
}
|
||||
.disposeOnDestroy()
|
||||
|
||||
if (callArgs.isVideoCall) {
|
||||
callViewModel.selectSubscribe(this, VectorCallViewState::callId, VectorCallViewState::isVideoCall) { _, isVideoCall ->
|
||||
if (isVideoCall) {
|
||||
if (checkPermissions(PERMISSIONS_FOR_VIDEO_IP_CALL, this, permissionCameraLauncher, R.string.permissions_rationale_msg_camera_and_audio)) {
|
||||
start()
|
||||
setupRenderersIfNeeded()
|
||||
}
|
||||
} else {
|
||||
if (checkPermissions(PERMISSIONS_FOR_AUDIO_IP_CALL, this, permissionCameraLauncher, R.string.permissions_rationale_msg_record_audio)) {
|
||||
start()
|
||||
setupRenderersIfNeeded()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onNewIntent(intent: Intent?) {
|
||||
super.onNewIntent(intent)
|
||||
intent?.takeIf { it.hasExtra(MvRx.KEY_ARG) }
|
||||
?.let { intent.getParcelableExtra<CallArgs>(MvRx.KEY_ARG) }
|
||||
?.let {
|
||||
callViewModel.handle(VectorCallViewActions.SwitchCall(it))
|
||||
}
|
||||
}
|
||||
|
||||
override fun getMenuRes() = R.menu.vector_call
|
||||
|
||||
|
@ -211,13 +214,19 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
}
|
||||
|
||||
override fun onDestroy() {
|
||||
callManager.getCallById(callArgs.callId)?.detachRenderers(listOf(views.pipRenderer, views.fullscreenRenderer))
|
||||
detachRenderersIfNeeded()
|
||||
turnScreenOffAndKeyguardOn()
|
||||
super.onDestroy()
|
||||
}
|
||||
|
||||
private fun detachRenderersIfNeeded() {
|
||||
val callId = withState(callViewModel) { it.callId }
|
||||
callManager.getCallById(callId)?.detachRenderers(listOf(views.pipRenderer, views.fullscreenRenderer))
|
||||
if (surfaceRenderersAreInitialized) {
|
||||
views.pipRenderer.release()
|
||||
views.fullscreenRenderer.release()
|
||||
surfaceRenderersAreInitialized = false
|
||||
}
|
||||
turnScreenOffAndKeyguardOn()
|
||||
super.onDestroy()
|
||||
}
|
||||
|
||||
private fun renderState(state: VectorCallViewState) {
|
||||
|
@ -291,7 +300,7 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
configureCallInfo(state)
|
||||
} else {
|
||||
configureCallInfo(state)
|
||||
if (callArgs.isVideoCall) {
|
||||
if (state.isVideoCall) {
|
||||
views.fullscreenRenderer.isVisible = true
|
||||
views.pipRendererWrapper.isVisible = true
|
||||
views.callInfoGroup.isVisible = false
|
||||
|
@ -403,10 +412,13 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
views.otherKnownCallLayout.setOnClickListener {
|
||||
withState(callViewModel) {
|
||||
val otherCall = callManager.getCallById(it.otherKnownCallInfo?.callId ?: "") ?: return@withState
|
||||
startActivity(newIntent(this, otherCall, null))
|
||||
finish()
|
||||
val callArgs = CallArgs(otherCall.nativeRoomId, otherCall.callId, otherCall.mxCall.opponentUserId, !otherCall.mxCall.isOutgoing, otherCall.mxCall.isVideoCall)
|
||||
callViewModel.handle(VectorCallViewActions.SwitchCall(callArgs))
|
||||
}
|
||||
}
|
||||
views.pipRendererWrapper.setOnClickListener {
|
||||
callViewModel.handle(VectorCallViewActions.ToggleCamera)
|
||||
}
|
||||
pipDraggrableView = views.pipRendererWrapper.setupDraggable()
|
||||
.setStickyMode(DraggableView.Mode.STICKY_XY)
|
||||
.build()
|
||||
|
@ -418,14 +430,15 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
|
||||
private val permissionCameraLauncher = registerForPermissionsResult { allGranted, _ ->
|
||||
if (allGranted) {
|
||||
start()
|
||||
setupRenderersIfNeeded()
|
||||
} else {
|
||||
// TODO display something
|
||||
finish()
|
||||
}
|
||||
}
|
||||
|
||||
private fun start() {
|
||||
private fun setupRenderersIfNeeded() {
|
||||
detachRenderersIfNeeded()
|
||||
rootEglBase = EglUtils.rootEglBase ?: return Unit.also {
|
||||
Timber.tag(loggerTag.value).v("rootEglBase is null")
|
||||
finish()
|
||||
|
@ -443,11 +456,10 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
views.fullscreenRenderer.setScalingType(RendererCommon.ScalingType.SCALE_ASPECT_FILL)
|
||||
views.fullscreenRenderer.setEnableHardwareScaler(true /* enabled */)
|
||||
|
||||
callManager.getCallById(callArgs.callId)?.attachViewRenderers(views.pipRenderer, views.fullscreenRenderer,
|
||||
intent.getStringExtra(EXTRA_MODE)?.takeIf { isFirstCreation() })
|
||||
|
||||
views.pipRendererWrapper.setOnClickListener {
|
||||
callViewModel.handle(VectorCallViewActions.ToggleCamera)
|
||||
val callId = withState(callViewModel) { it.callId }
|
||||
callManager.getCallById(callId)?.also { webRtcCall ->
|
||||
webRtcCall.attachViewRenderers(views.pipRenderer, views.fullscreenRenderer, intent.getStringExtra(EXTRA_MODE))
|
||||
intent.removeExtra(EXTRA_MODE)
|
||||
}
|
||||
surfaceRenderersAreInitialized = true
|
||||
}
|
||||
|
@ -467,7 +479,8 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
}.show(supportFragmentManager, FRAGMENT_DIAL_PAD_TAG)
|
||||
}
|
||||
is VectorCallViewEvents.ShowCallTransferScreen -> {
|
||||
navigator.openCallTransfer(this, callArgs.callId)
|
||||
val callId = withState(callViewModel) { it.callId }
|
||||
navigator.openCallTransfer(this, callId)
|
||||
}
|
||||
null -> {
|
||||
}
|
||||
|
@ -486,39 +499,6 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
.show()
|
||||
}
|
||||
|
||||
companion object {
|
||||
private const val EXTRA_MODE = "EXTRA_MODE"
|
||||
private const val FRAGMENT_DIAL_PAD_TAG = "FRAGMENT_DIAL_PAD_TAG"
|
||||
|
||||
const val OUTGOING_CREATED = "OUTGOING_CREATED"
|
||||
const val INCOMING_RINGING = "INCOMING_RINGING"
|
||||
const val INCOMING_ACCEPT = "INCOMING_ACCEPT"
|
||||
|
||||
fun newIntent(context: Context, call: WebRtcCall, mode: String?): Intent {
|
||||
return Intent(context, VectorCallActivity::class.java).apply {
|
||||
// what could be the best flags?
|
||||
flags = Intent.FLAG_ACTIVITY_NEW_TASK
|
||||
putExtra(MvRx.KEY_ARG, CallArgs(call.nativeRoomId, call.callId, call.mxCall.opponentUserId, !call.mxCall.isOutgoing, call.mxCall.isVideoCall))
|
||||
putExtra(EXTRA_MODE, mode)
|
||||
}
|
||||
}
|
||||
|
||||
fun newIntent(context: Context,
|
||||
callId: String,
|
||||
signalingRoomId: String,
|
||||
otherUserId: String,
|
||||
isIncomingCall: Boolean,
|
||||
isVideoCall: Boolean,
|
||||
mode: String?): Intent {
|
||||
return Intent(context, VectorCallActivity::class.java).apply {
|
||||
// what could be the best flags?
|
||||
flags = FLAG_ACTIVITY_CLEAR_TOP
|
||||
putExtra(MvRx.KEY_ARG, CallArgs(signalingRoomId, callId, otherUserId, isIncomingCall, isVideoCall))
|
||||
putExtra(EXTRA_MODE, mode)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun didTapAudioSettings() {
|
||||
CallSoundDeviceChooserBottomSheet().show(supportFragmentManager, "SoundDeviceChooser")
|
||||
}
|
||||
|
@ -544,7 +524,8 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
}
|
||||
|
||||
private fun returnToChat() {
|
||||
val args = RoomDetailArgs(callArgs.signalingRoomId)
|
||||
val roomId = withState(callViewModel) { it.roomId }
|
||||
val args = RoomDetailArgs(roomId)
|
||||
val intent = RoomDetailActivity.newIntent(this, args).apply {
|
||||
flags = FLAG_ACTIVITY_CLEAR_TOP
|
||||
}
|
||||
|
@ -592,4 +573,37 @@ class VectorCallActivity : VectorBaseActivity<ActivityCallBinding>(), CallContro
|
|||
)
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
private const val EXTRA_MODE = "EXTRA_MODE"
|
||||
private const val FRAGMENT_DIAL_PAD_TAG = "FRAGMENT_DIAL_PAD_TAG"
|
||||
|
||||
const val OUTGOING_CREATED = "OUTGOING_CREATED"
|
||||
const val INCOMING_RINGING = "INCOMING_RINGING"
|
||||
const val INCOMING_ACCEPT = "INCOMING_ACCEPT"
|
||||
|
||||
fun newIntent(context: Context, call: WebRtcCall, mode: String?): Intent {
|
||||
return Intent(context, VectorCallActivity::class.java).apply {
|
||||
// what could be the best flags?
|
||||
flags = Intent.FLAG_ACTIVITY_NEW_TASK
|
||||
putExtra(MvRx.KEY_ARG, CallArgs(call.nativeRoomId, call.callId, call.mxCall.opponentUserId, !call.mxCall.isOutgoing, call.mxCall.isVideoCall))
|
||||
putExtra(EXTRA_MODE, mode)
|
||||
}
|
||||
}
|
||||
|
||||
fun newIntent(context: Context,
|
||||
callId: String,
|
||||
signalingRoomId: String,
|
||||
otherUserId: String,
|
||||
isIncomingCall: Boolean,
|
||||
isVideoCall: Boolean,
|
||||
mode: String?): Intent {
|
||||
return Intent(context, VectorCallActivity::class.java).apply {
|
||||
// what could be the best flags?
|
||||
flags = Intent.FLAG_ACTIVITY_NEW_TASK
|
||||
putExtra(MvRx.KEY_ARG, CallArgs(signalingRoomId, callId, otherUserId, isIncomingCall, isVideoCall))
|
||||
putExtra(EXTRA_MODE, mode)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -29,6 +29,8 @@ sealed class VectorCallViewActions : VectorViewModelAction {
|
|||
data class ChangeAudioDevice(val device: CallAudioManager.Device) : VectorCallViewActions()
|
||||
object OpenDialPad: VectorCallViewActions()
|
||||
data class SendDtmfDigit(val digit: String) : VectorCallViewActions()
|
||||
data class SwitchCall(val callArgs: CallArgs) : VectorCallViewActions()
|
||||
|
||||
object SwitchSoundDevice : VectorCallViewActions()
|
||||
object HeadSetButtonPressed : VectorCallViewActions()
|
||||
object ToggleCamera : VectorCallViewActions()
|
||||
|
|
|
@ -174,7 +174,12 @@ class VectorCallViewModel @AssistedInject constructor(
|
|||
}
|
||||
|
||||
init {
|
||||
val webRtcCall = callManager.getCallById(initialState.callId)
|
||||
setupCallWithCurrentState()
|
||||
}
|
||||
|
||||
private fun setupCallWithCurrentState() = withState { state ->
|
||||
call?.removeListener(callListener)
|
||||
val webRtcCall = callManager.getCallById(state.callId)
|
||||
if (webRtcCall == null) {
|
||||
setState {
|
||||
copy(callState = Fail(IllegalArgumentException("No call")))
|
||||
|
@ -229,6 +234,7 @@ class VectorCallViewModel @AssistedInject constructor(
|
|||
override fun onCleared() {
|
||||
callManager.removeCurrentCallListener(currentCallListener)
|
||||
call?.removeListener(callListener)
|
||||
call = null
|
||||
proximityManager.stop()
|
||||
super.onCleared()
|
||||
}
|
||||
|
@ -309,6 +315,10 @@ class VectorCallViewModel @AssistedInject constructor(
|
|||
VectorCallViewActions.TransferCall -> {
|
||||
handleCallTransfer()
|
||||
}
|
||||
is VectorCallViewActions.SwitchCall -> {
|
||||
setState { VectorCallViewState(action.callArgs) }
|
||||
setupCallWithCurrentState()
|
||||
}
|
||||
}.exhaustive
|
||||
}
|
||||
|
||||
|
|
|
@ -348,7 +348,7 @@ class WebRtcCall(
|
|||
|
||||
fun attachViewRenderers(localViewRenderer: SurfaceViewRenderer?, remoteViewRenderer: SurfaceViewRenderer, mode: String?) {
|
||||
sessionScope?.launch(dispatcher) {
|
||||
Timber.tag(loggerTag.value).v("attachViewRenderers localRendeder $localViewRenderer / $remoteViewRenderer")
|
||||
Timber.tag(loggerTag.value).v("attachViewRenderers localRenderer $localViewRenderer / $remoteViewRenderer")
|
||||
localSurfaceRenderers.addIfNeeded(localViewRenderer)
|
||||
remoteSurfaceRenderers.addIfNeeded(remoteViewRenderer)
|
||||
when (mode) {
|
||||
|
|
|
@ -358,7 +358,7 @@ class NoticeEventFormatter @Inject constructor(
|
|||
}
|
||||
EventType.CALL_REJECT ->
|
||||
if (event.isSentByCurrentUser()) {
|
||||
sp.getString(R.string.call_tile_you_declined)
|
||||
sp.getString(R.string.call_tile_you_declined,"")
|
||||
} else {
|
||||
sp.getString(R.string.call_tile_other_declined, senderName)
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue