mirror of
https://github.com/nextcloud/talk-android
synced 2025-06-21 20:49:36 +01:00
move SurfaceViewRenderer into WebRTCVideoView
Signed-off-by: Marcel Hibbe <dev@mhibbe.de>
This commit is contained in:
parent
aacc013485
commit
35c777e70d
@ -959,7 +959,8 @@ class CallActivity : CallBaseActivity() {
|
|||||||
binding!!.composeParticipantGrid.setContent {
|
binding!!.composeParticipantGrid.setContent {
|
||||||
MaterialTheme {
|
MaterialTheme {
|
||||||
ParticipantGrid(
|
ParticipantGrid(
|
||||||
participants = participantUiStates.toList()
|
participants = participantUiStates.toList(),
|
||||||
|
eglBase = rootEglBase!!
|
||||||
) {
|
) {
|
||||||
animateCallControls(true, 0)
|
animateCallControls(true, 0)
|
||||||
}
|
}
|
||||||
|
@ -148,7 +148,7 @@ class ParticipantDisplayItem(
|
|||||||
isStreamEnabled = isStreamEnabled,
|
isStreamEnabled = isStreamEnabled,
|
||||||
raisedHand = raisedHand?.state == true,
|
raisedHand = raisedHand?.state == true,
|
||||||
avatarUrl = urlForAvatar,
|
avatarUrl = urlForAvatar,
|
||||||
surfaceViewRenderer = surfaceViewRenderer
|
mediaStream = mediaStream,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -7,7 +7,7 @@
|
|||||||
|
|
||||||
package com.nextcloud.talk.call
|
package com.nextcloud.talk.call
|
||||||
|
|
||||||
import org.webrtc.SurfaceViewRenderer
|
import org.webrtc.MediaStream
|
||||||
|
|
||||||
data class ParticipantUiState(
|
data class ParticipantUiState(
|
||||||
val sessionKey: String,
|
val sessionKey: String,
|
||||||
@ -17,5 +17,5 @@ data class ParticipantUiState(
|
|||||||
val isStreamEnabled: Boolean,
|
val isStreamEnabled: Boolean,
|
||||||
val raisedHand: Boolean,
|
val raisedHand: Boolean,
|
||||||
val avatarUrl: String?,
|
val avatarUrl: String?,
|
||||||
val surfaceViewRenderer: SurfaceViewRenderer? = null
|
val mediaStream: MediaStream?
|
||||||
)
|
)
|
||||||
|
@ -27,9 +27,15 @@ import androidx.compose.ui.platform.LocalConfiguration
|
|||||||
import androidx.compose.ui.tooling.preview.Preview
|
import androidx.compose.ui.tooling.preview.Preview
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import com.nextcloud.talk.call.ParticipantUiState
|
import com.nextcloud.talk.call.ParticipantUiState
|
||||||
|
import org.webrtc.EglBase
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun ParticipantGrid(modifier: Modifier = Modifier, participants: List<ParticipantUiState>, onClick: () -> Unit) {
|
fun ParticipantGrid(
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
|
eglBase: EglBase?,
|
||||||
|
participants: List<ParticipantUiState>,
|
||||||
|
onClick: () -> Unit
|
||||||
|
) {
|
||||||
val configuration = LocalConfiguration.current
|
val configuration = LocalConfiguration.current
|
||||||
val isPortrait = configuration.orientation == Configuration.ORIENTATION_PORTRAIT
|
val isPortrait = configuration.orientation == Configuration.ORIENTATION_PORTRAIT
|
||||||
|
|
||||||
@ -44,7 +50,8 @@ fun ParticipantGrid(modifier: Modifier = Modifier, participants: List<Participan
|
|||||||
participant = participants[0],
|
participant = participants[0],
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxSize()
|
.fillMaxSize()
|
||||||
.clickable { onClick() }
|
.clickable { onClick() },
|
||||||
|
eglBase = eglBase
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -63,7 +70,8 @@ fun ParticipantGrid(modifier: Modifier = Modifier, participants: List<Participan
|
|||||||
participant = it,
|
participant = it,
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.weight(1f)
|
.weight(1f)
|
||||||
.fillMaxWidth()
|
.fillMaxWidth(),
|
||||||
|
eglBase = eglBase
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -80,7 +88,8 @@ fun ParticipantGrid(modifier: Modifier = Modifier, participants: List<Participan
|
|||||||
participant = it,
|
participant = it,
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.weight(1f)
|
.weight(1f)
|
||||||
.fillMaxHeight()
|
.fillMaxHeight(),
|
||||||
|
eglBase = eglBase
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -102,7 +111,8 @@ fun ParticipantGrid(modifier: Modifier = Modifier, participants: List<Participan
|
|||||||
participant = participant,
|
participant = participant,
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
.aspectRatio(1.5f)
|
.aspectRatio(1.5f),
|
||||||
|
eglBase = eglBase
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -118,7 +128,8 @@ const val numberOfParticipants = 4
|
|||||||
@Composable
|
@Composable
|
||||||
fun ParticipantGridPreview() {
|
fun ParticipantGridPreview() {
|
||||||
ParticipantGrid(
|
ParticipantGrid(
|
||||||
participants = getTestParticipants(numberOfParticipants)
|
participants = getTestParticipants(numberOfParticipants),
|
||||||
|
eglBase = null
|
||||||
) {}
|
) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -130,7 +141,8 @@ fun ParticipantGridPreview() {
|
|||||||
@Composable
|
@Composable
|
||||||
fun ParticipantGridPreviewPortrait2() {
|
fun ParticipantGridPreviewPortrait2() {
|
||||||
ParticipantGrid(
|
ParticipantGrid(
|
||||||
participants = getTestParticipants(numberOfParticipants)
|
participants = getTestParticipants(numberOfParticipants),
|
||||||
|
eglBase = null
|
||||||
) {}
|
) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -142,7 +154,8 @@ fun ParticipantGridPreviewPortrait2() {
|
|||||||
@Composable
|
@Composable
|
||||||
fun ParticipantGridPreviewLandscape1() {
|
fun ParticipantGridPreviewLandscape1() {
|
||||||
ParticipantGrid(
|
ParticipantGrid(
|
||||||
participants = getTestParticipants(numberOfParticipants)
|
participants = getTestParticipants(numberOfParticipants),
|
||||||
|
eglBase = null
|
||||||
) {}
|
) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -157,7 +170,7 @@ fun getTestParticipants(numberOfParticipants: Int): List<ParticipantUiState> {
|
|||||||
isStreamEnabled = true,
|
isStreamEnabled = true,
|
||||||
raisedHand = true,
|
raisedHand = true,
|
||||||
avatarUrl = "",
|
avatarUrl = "",
|
||||||
surfaceViewRenderer = null
|
mediaStream = null
|
||||||
)
|
)
|
||||||
participantList.add(participant)
|
participantList.add(participant)
|
||||||
}
|
}
|
||||||
|
@ -9,6 +9,7 @@ package com.nextcloud.talk.call.components
|
|||||||
|
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
import androidx.compose.foundation.layout.Box
|
import androidx.compose.foundation.layout.Box
|
||||||
|
import androidx.compose.foundation.layout.fillMaxSize
|
||||||
import androidx.compose.foundation.layout.fillMaxWidth
|
import androidx.compose.foundation.layout.fillMaxWidth
|
||||||
import androidx.compose.foundation.layout.padding
|
import androidx.compose.foundation.layout.padding
|
||||||
import androidx.compose.foundation.layout.size
|
import androidx.compose.foundation.layout.size
|
||||||
@ -25,18 +26,25 @@ import androidx.compose.ui.graphics.Color
|
|||||||
import androidx.compose.ui.res.painterResource
|
import androidx.compose.ui.res.painterResource
|
||||||
import androidx.compose.ui.tooling.preview.Preview
|
import androidx.compose.ui.tooling.preview.Preview
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
|
import androidx.compose.ui.viewinterop.AndroidView
|
||||||
import com.nextcloud.talk.R
|
import com.nextcloud.talk.R
|
||||||
import com.nextcloud.talk.call.ParticipantUiState
|
import com.nextcloud.talk.call.ParticipantUiState
|
||||||
|
import org.webrtc.EglBase
|
||||||
|
import org.webrtc.SurfaceViewRenderer
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun ParticipantTile(participant: ParticipantUiState, modifier: Modifier = Modifier) {
|
fun ParticipantTile(
|
||||||
|
participant: ParticipantUiState,
|
||||||
|
eglBase: EglBase?,
|
||||||
|
modifier: Modifier = Modifier
|
||||||
|
) {
|
||||||
Box(
|
Box(
|
||||||
modifier = modifier
|
modifier = modifier
|
||||||
.clip(RoundedCornerShape(12.dp))
|
.clip(RoundedCornerShape(12.dp))
|
||||||
.background(Color.DarkGray)
|
.background(Color.DarkGray)
|
||||||
) {
|
) {
|
||||||
if (participant.isStreamEnabled && participant.surfaceViewRenderer != null) {
|
if (participant.isStreamEnabled && participant.mediaStream != null) {
|
||||||
WebRTCVideoView(participant.surfaceViewRenderer)
|
WebRTCVideoView(participant, eglBase)
|
||||||
} else {
|
} else {
|
||||||
AvatarWithFallback(participant)
|
AvatarWithFallback(participant)
|
||||||
}
|
}
|
||||||
@ -94,11 +102,12 @@ fun ParticipantTilePreview() {
|
|||||||
isStreamEnabled = true,
|
isStreamEnabled = true,
|
||||||
raisedHand = true,
|
raisedHand = true,
|
||||||
avatarUrl = "",
|
avatarUrl = "",
|
||||||
surfaceViewRenderer = null
|
mediaStream = null,
|
||||||
)
|
)
|
||||||
ParticipantTile(
|
ParticipantTile(
|
||||||
participant = participant,
|
participant = participant,
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth(),
|
||||||
|
eglBase = null
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -11,13 +11,28 @@ import androidx.compose.foundation.layout.fillMaxSize
|
|||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.viewinterop.AndroidView
|
import androidx.compose.ui.viewinterop.AndroidView
|
||||||
|
import com.nextcloud.talk.call.ParticipantUiState
|
||||||
|
import org.webrtc.EglBase
|
||||||
import org.webrtc.SurfaceViewRenderer
|
import org.webrtc.SurfaceViewRenderer
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun WebRTCVideoView(surfaceViewRenderer: SurfaceViewRenderer) {
|
fun WebRTCVideoView(
|
||||||
|
participant: ParticipantUiState,
|
||||||
|
eglBase: EglBase?,
|
||||||
|
) {
|
||||||
AndroidView(
|
AndroidView(
|
||||||
factory = { surfaceViewRenderer },
|
factory = { context ->
|
||||||
update = { /* No-op, renderer is already initialized and reused */ },
|
SurfaceViewRenderer(context).apply {
|
||||||
modifier = Modifier.fillMaxSize()
|
init(eglBase?.eglBaseContext, null)
|
||||||
|
setEnableHardwareScaler(true)
|
||||||
|
setMirror(false)
|
||||||
|
participant.mediaStream?.videoTracks?.firstOrNull()?.addSink(this)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
modifier = Modifier.fillMaxSize(),
|
||||||
|
onRelease = {
|
||||||
|
participant.mediaStream?.videoTracks?.firstOrNull()?.removeSink(it)
|
||||||
|
it.release()
|
||||||
|
}
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user