Browse Source

Merge pull request #2027 from element-hq/feature/bma/openRoomAvatar

Feature/bma/open room avatar
pull/2030/head
Benoit Marty 9 months ago committed by GitHub
parent
commit
4d414989bb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 1
      changelog.d/1918.misc
  2. 9
      features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesFlowNode.kt
  3. 18
      features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsFlowNode.kt
  4. 6
      features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsNode.kt
  5. 20
      features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt
  6. 2
      features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/avatar/AvatarPreviewNode.kt
  7. 4
      libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomMember.kt

1
changelog.d/1918.misc

@ -0,0 +1 @@ @@ -0,0 +1 @@
Add ability to see the room avatar in the media viewer.

9
features/messages/impl/src/main/kotlin/io/element/android/features/messages/impl/MessagesFlowNode.kt

@ -242,7 +242,6 @@ class MessagesFlowNode @AssistedInject constructor( @@ -242,7 +242,6 @@ class MessagesFlowNode @AssistedInject constructor(
backstack.push(navTarget)
}
is TimelineItemVideoContent -> {
val mediaSource = event.content.videoSource
val navTarget = NavTarget.MediaViewer(
mediaInfo = MediaInfo(
name = event.content.body,
@ -250,13 +249,12 @@ class MessagesFlowNode @AssistedInject constructor( @@ -250,13 +249,12 @@ class MessagesFlowNode @AssistedInject constructor(
formattedFileSize = event.content.formattedFileSize,
fileExtension = event.content.fileExtension
),
mediaSource = mediaSource,
mediaSource = event.content.videoSource,
thumbnailSource = event.content.thumbnailSource,
)
backstack.push(navTarget)
}
is TimelineItemFileContent -> {
val mediaSource = event.content.fileSource
val navTarget = NavTarget.MediaViewer(
mediaInfo = MediaInfo(
name = event.content.body,
@ -264,13 +262,12 @@ class MessagesFlowNode @AssistedInject constructor( @@ -264,13 +262,12 @@ class MessagesFlowNode @AssistedInject constructor(
formattedFileSize = event.content.formattedFileSize,
fileExtension = event.content.fileExtension
),
mediaSource = mediaSource,
mediaSource = event.content.fileSource,
thumbnailSource = event.content.thumbnailSource,
)
backstack.push(navTarget)
}
is TimelineItemAudioContent -> {
val mediaSource = event.content.mediaSource
val navTarget = NavTarget.MediaViewer(
mediaInfo = MediaInfo(
name = event.content.body,
@ -278,7 +275,7 @@ class MessagesFlowNode @AssistedInject constructor( @@ -278,7 +275,7 @@ class MessagesFlowNode @AssistedInject constructor(
formattedFileSize = event.content.formattedFileSize,
fileExtension = event.content.fileExtension
),
mediaSource = mediaSource,
mediaSource = event.content.mediaSource,
thumbnailSource = null,
)
backstack.push(navTarget)

18
features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsFlowNode.kt

@ -34,7 +34,7 @@ import io.element.android.features.roomdetails.impl.edit.RoomDetailsEditNode @@ -34,7 +34,7 @@ import io.element.android.features.roomdetails.impl.edit.RoomDetailsEditNode
import io.element.android.features.roomdetails.impl.invite.RoomInviteMembersNode
import io.element.android.features.roomdetails.impl.members.RoomMemberListNode
import io.element.android.features.roomdetails.impl.members.details.RoomMemberDetailsNode
import io.element.android.features.roomdetails.impl.members.details.avatar.RoomMemberAvatarPreviewNode
import io.element.android.features.roomdetails.impl.members.details.avatar.AvatarPreviewNode
import io.element.android.features.roomdetails.impl.notificationsettings.RoomNotificationSettingsNode
import io.element.android.libraries.architecture.BackstackNode
import io.element.android.libraries.architecture.animation.rememberDefaultTransitionHandler
@ -87,7 +87,7 @@ class RoomDetailsFlowNode @AssistedInject constructor( @@ -87,7 +87,7 @@ class RoomDetailsFlowNode @AssistedInject constructor(
data class RoomMemberDetails(val roomMemberId: UserId) : NavTarget
@Parcelize
data class MemberAvatarPreview(val userName: String, val avatarUrl: String) : NavTarget
data class AvatarPreview(val name: String, val avatarUrl: String) : NavTarget
}
override fun resolve(navTarget: NavTarget, buildContext: BuildContext): Node {
@ -110,8 +110,8 @@ class RoomDetailsFlowNode @AssistedInject constructor( @@ -110,8 +110,8 @@ class RoomDetailsFlowNode @AssistedInject constructor(
backstack.push(NavTarget.RoomNotificationSettings(showUserDefinedSettingStyle = false))
}
override fun openAvatarPreview(username: String, url: String) {
backstack.push(NavTarget.MemberAvatarPreview(username, url))
override fun openAvatarPreview(name: String, url: String) {
backstack.push(NavTarget.AvatarPreview(name, url))
}
}
createNode<RoomDetailsNode>(buildContext, listOf(roomDetailsCallback))
@ -151,7 +151,7 @@ class RoomDetailsFlowNode @AssistedInject constructor( @@ -151,7 +151,7 @@ class RoomDetailsFlowNode @AssistedInject constructor(
is NavTarget.RoomMemberDetails -> {
val callback = object : RoomMemberDetailsNode.Callback {
override fun openAvatarPreview(username: String, avatarUrl: String) {
backstack.push(NavTarget.MemberAvatarPreview(username, avatarUrl))
backstack.push(NavTarget.AvatarPreview(username, avatarUrl))
}
override fun onStartDM(roomId: RoomId) {
@ -161,22 +161,22 @@ class RoomDetailsFlowNode @AssistedInject constructor( @@ -161,22 +161,22 @@ class RoomDetailsFlowNode @AssistedInject constructor(
val plugins = listOf(RoomMemberDetailsNode.RoomMemberDetailsInput(navTarget.roomMemberId), callback)
createNode<RoomMemberDetailsNode>(buildContext, plugins)
}
is NavTarget.MemberAvatarPreview -> {
is NavTarget.AvatarPreview -> {
// We need to fake the MimeType here for the viewer to work.
val mimeType = MimeTypes.Images
val input = MediaViewerNode.Inputs(
mediaInfo = MediaInfo(
name = navTarget.userName,
name = navTarget.name,
mimeType = mimeType,
formattedFileSize = "",
fileExtension = ""
),
mediaSource = MediaSource(url = navTarget.avatarUrl),
thumbnailSource = MediaSource(url = navTarget.avatarUrl),
thumbnailSource = null,
canDownload = false,
canShare = false,
)
createNode<RoomMemberAvatarPreviewNode>(buildContext, listOf(input))
createNode<AvatarPreviewNode>(buildContext, listOf(input))
}
}
}

6
features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsNode.kt

@ -52,7 +52,7 @@ class RoomDetailsNode @AssistedInject constructor( @@ -52,7 +52,7 @@ class RoomDetailsNode @AssistedInject constructor(
fun openInviteMembers()
fun editRoomDetails()
fun openRoomNotificationSettings()
fun openAvatarPreview(username: String, url: String)
fun openAvatarPreview(name: String, url: String)
}
private val callbacks = plugins<Callback>()
@ -111,8 +111,8 @@ class RoomDetailsNode @AssistedInject constructor( @@ -111,8 +111,8 @@ class RoomDetailsNode @AssistedInject constructor(
callbacks.forEach { it.editRoomDetails() }
}
private fun openAvatarPreview(username: String, url: String) {
callbacks.forEach { it.openAvatarPreview(username, url) }
private fun openAvatarPreview(name: String, url: String) {
callbacks.forEach { it.openAvatarPreview(name, url) }
}
@Composable

20
features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/RoomDetailsView.kt

@ -16,6 +16,7 @@ @@ -16,6 +16,7 @@
package io.element.android.features.roomdetails.impl
import androidx.compose.foundation.clickable
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
@ -77,6 +78,7 @@ import io.element.android.libraries.designsystem.theme.components.TopAppBar @@ -77,6 +78,7 @@ import io.element.android.libraries.designsystem.theme.components.TopAppBar
import io.element.android.libraries.designsystem.utils.CommonDrawables
import io.element.android.libraries.matrix.api.room.RoomMember
import io.element.android.libraries.matrix.api.room.RoomNotificationMode
import io.element.android.libraries.matrix.api.room.getBestName
import io.element.android.libraries.ui.strings.CommonStrings
@Composable
@ -89,7 +91,7 @@ fun RoomDetailsView( @@ -89,7 +91,7 @@ fun RoomDetailsView(
openRoomMemberList: () -> Unit,
openRoomNotificationSettings: () -> Unit,
invitePeople: () -> Unit,
openAvatarPreview: (username: String, url: String) -> Unit,
openAvatarPreview: (name: String, url: String) -> Unit,
modifier: Modifier = Modifier,
) {
fun onShareMember() {
@ -120,7 +122,10 @@ fun RoomDetailsView( @@ -120,7 +122,10 @@ fun RoomDetailsView(
avatarUrl = state.roomAvatarUrl,
roomId = state.roomId,
roomName = state.roomName,
roomAlias = state.roomAlias
roomAlias = state.roomAlias,
openAvatarPreview = { avatarUrl ->
openAvatarPreview(state.roomName, avatarUrl)
},
)
MainActionsSection(
state = state,
@ -134,10 +139,8 @@ fun RoomDetailsView( @@ -134,10 +139,8 @@ fun RoomDetailsView(
avatarUrl = state.roomAvatarUrl ?: member.avatarUrl,
userId = member.userId.value,
userName = state.roomName,
openAvatarPreview = {
if (member.avatarUrl != null) {
openAvatarPreview(member.displayName ?: member.userId.value, member.avatarUrl!!)
}
openAvatarPreview = { avatarUrl ->
openAvatarPreview(member.getBestName(), avatarUrl)
},
)
RoomMemberMainActionsSection(onShareUser = ::onShareMember)
@ -265,6 +268,7 @@ private fun RoomHeaderSection( @@ -265,6 +268,7 @@ private fun RoomHeaderSection(
roomId: String,
roomName: String,
roomAlias: String?,
openAvatarPreview: (url: String) -> Unit,
modifier: Modifier = Modifier
) {
Column(
@ -275,7 +279,9 @@ private fun RoomHeaderSection( @@ -275,7 +279,9 @@ private fun RoomHeaderSection(
) {
Avatar(
avatarData = AvatarData(roomId, roomName, avatarUrl, AvatarSize.RoomHeader),
modifier = Modifier.size(70.dp)
modifier = Modifier
.size(70.dp)
.clickable(enabled = avatarUrl != null) { openAvatarPreview(avatarUrl!!) }
)
Spacer(modifier = Modifier.height(24.dp))
Text(

2
features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/avatar/RoomMemberAvatarPreviewNode.kt → features/roomdetails/impl/src/main/kotlin/io/element/android/features/roomdetails/impl/members/details/avatar/AvatarPreviewNode.kt

@ -26,7 +26,7 @@ import io.element.android.libraries.mediaviewer.api.viewer.MediaViewerNode @@ -26,7 +26,7 @@ import io.element.android.libraries.mediaviewer.api.viewer.MediaViewerNode
import io.element.android.libraries.mediaviewer.api.viewer.MediaViewerPresenter
@ContributesNode(RoomScope::class)
class RoomMemberAvatarPreviewNode @AssistedInject constructor(
class AvatarPreviewNode @AssistedInject constructor(
@Assisted buildContext: BuildContext,
@Assisted plugins: List<Plugin>,
presenterFactory: MediaViewerPresenter.Factory,

4
libraries/matrix/api/src/main/kotlin/io/element/android/libraries/matrix/api/room/RoomMember.kt

@ -32,3 +32,7 @@ data class RoomMember( @@ -32,3 +32,7 @@ data class RoomMember(
enum class RoomMembershipState {
BAN, INVITE, JOIN, KNOCK, LEAVE
}
fun RoomMember.getBestName(): String {
return displayName?.takeIf { it.isNotEmpty() } ?: userId.value
}

Loading…
Cancel
Save