diff --git a/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepository.kt b/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepository.kt index 9a1c59b9..db58c458 100644 --- a/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepository.kt +++ b/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepository.kt @@ -6,6 +6,7 @@ import dev.meloda.fast.model.api.domain.VkAttachment import dev.meloda.fast.model.api.domain.VkAttachmentHistoryMessage import dev.meloda.fast.model.api.domain.VkMessage import dev.meloda.fast.model.api.responses.MessagesGetConversationMembersResponse +import dev.meloda.fast.model.api.responses.MessagesGetReadPeersResponse import dev.meloda.fast.model.api.responses.MessagesSendResponse import dev.meloda.fast.network.RestApiErrorDomain @@ -110,4 +111,9 @@ interface MessagesRepository { chatId: Long, memberId: Long ): ApiResult + + suspend fun getMessageReadPeers( + peerId: Long, + cmId: Long + ): ApiResult } diff --git a/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepositoryImpl.kt b/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepositoryImpl.kt index bfe58c81..9d234732 100644 --- a/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepositoryImpl.kt +++ b/core/data/src/main/kotlin/dev/meloda/fast/data/api/messages/MessagesRepositoryImpl.kt @@ -37,6 +37,7 @@ import dev.meloda.fast.model.api.requests.MessagesRemoveChatUserRequest import dev.meloda.fast.model.api.requests.MessagesSendRequest import dev.meloda.fast.model.api.requests.MessagesUnpinMessageRequest import dev.meloda.fast.model.api.responses.MessagesGetConversationMembersResponse +import dev.meloda.fast.model.api.responses.MessagesGetReadPeersResponse import dev.meloda.fast.model.api.responses.MessagesSendResponse import dev.meloda.fast.network.RestApiErrorDomain import dev.meloda.fast.network.mapApiDefault @@ -419,4 +420,18 @@ class MessagesRepositoryImpl( messagesService.removeChatUser(requestModel.map).mapApiDefault() } + + override suspend fun getMessageReadPeers( + peerId: Long, + cmId: Long + ): ApiResult = withContext(Dispatchers.IO) { + messagesService.getMessageReadPeers( + mapOf( + "peer_id" to peerId.toString(), + "cmid" to cmId.toString(), + "extended" to "1", + "fields" to VkConstants.USER_FIELDS + ) + ).mapApiDefault() + } } diff --git a/core/domain/src/main/kotlin/dev/meloda/fast/domain/GetMessageReadPeersUseCase.kt b/core/domain/src/main/kotlin/dev/meloda/fast/domain/GetMessageReadPeersUseCase.kt new file mode 100644 index 00000000..ae9d5e04 --- /dev/null +++ b/core/domain/src/main/kotlin/dev/meloda/fast/domain/GetMessageReadPeersUseCase.kt @@ -0,0 +1,21 @@ +package dev.meloda.fast.domain + +import dev.meloda.fast.data.State +import dev.meloda.fast.data.api.messages.MessagesRepository +import dev.meloda.fast.data.mapToState +import kotlinx.coroutines.flow.Flow + +class GetMessageReadPeersUseCase( + private val repository: MessagesRepository +) : BaseUseCase { + + operator fun invoke( + peerId: Long, + cmId: Long + ): Flow> = flowNewState { + repository.getMessageReadPeers( + peerId = peerId, + cmId = cmId + ).mapToState(successMapper = { it.totalCount }) + } +} diff --git a/core/domain/src/main/kotlin/dev/meloda/fast/domain/di/DomainModule.kt b/core/domain/src/main/kotlin/dev/meloda/fast/domain/di/DomainModule.kt index 7a8579a7..de371265 100644 --- a/core/domain/src/main/kotlin/dev/meloda/fast/domain/di/DomainModule.kt +++ b/core/domain/src/main/kotlin/dev/meloda/fast/domain/di/DomainModule.kt @@ -6,6 +6,7 @@ import dev.meloda.fast.domain.AccountUseCaseImpl import dev.meloda.fast.domain.GetCurrentAccountUseCase import dev.meloda.fast.domain.GetLocalUserByIdUseCase import dev.meloda.fast.domain.GetLocalUsersByIdsUseCase +import dev.meloda.fast.domain.GetMessageReadPeersUseCase import dev.meloda.fast.domain.LoadConversationsByIdUseCase import dev.meloda.fast.domain.LoadUserByIdUseCase import dev.meloda.fast.domain.LoadUsersByIdsUseCase @@ -27,4 +28,6 @@ val domainModule = module { singleOf(::GetCurrentAccountUseCase) singleOf(::LoadConversationsByIdUseCase) + + singleOf(::GetMessageReadPeersUseCase) } diff --git a/core/model/src/main/kotlin/dev/meloda/fast/model/api/responses/MessagesResponse.kt b/core/model/src/main/kotlin/dev/meloda/fast/model/api/responses/MessagesResponse.kt index 884912dd..f60adcec 100644 --- a/core/model/src/main/kotlin/dev/meloda/fast/model/api/responses/MessagesResponse.kt +++ b/core/model/src/main/kotlin/dev/meloda/fast/model/api/responses/MessagesResponse.kt @@ -70,3 +70,10 @@ data class MessagesMarkAsImportantResponse( @Json(name = "peer_id") val peerId: Long ) } + +@JsonClass(generateAdapter = true) +data class MessagesGetReadPeersResponse( + @Json(name = "items") val items: List, + @Json(name = "total_count") val totalCount: Int, + @Json(name = "profiles") val profiles: List?, +) diff --git a/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesService.kt b/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesService.kt index 580b3fef..84d9bba5 100644 --- a/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesService.kt +++ b/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesService.kt @@ -9,6 +9,7 @@ import dev.meloda.fast.model.api.responses.MessagesGetByIdResponse import dev.meloda.fast.model.api.responses.MessagesGetConversationMembersResponse import dev.meloda.fast.model.api.responses.MessagesGetHistoryAttachmentsResponse import dev.meloda.fast.model.api.responses.MessagesGetHistoryResponse +import dev.meloda.fast.model.api.responses.MessagesGetReadPeersResponse import dev.meloda.fast.model.api.responses.MessagesMarkAsImportantResponse import dev.meloda.fast.model.api.responses.MessagesSendResponse import dev.meloda.fast.network.ApiResponse @@ -108,4 +109,10 @@ interface MessagesService { suspend fun removeChatUser( @FieldMap params: Map ): ApiResult, RestApiError> + + @FormUrlEncoded + @POST(MessagesUrls.GET_MESSAGE_READ_PEERS) + suspend fun getMessageReadPeers( + @FieldMap params: Map + ): ApiResult, RestApiError> } diff --git a/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesUrls.kt b/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesUrls.kt index b4f196d4..1cee7a88 100644 --- a/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesUrls.kt +++ b/core/network/src/main/kotlin/dev/meloda/fast/network/service/messages/MessagesUrls.kt @@ -22,4 +22,5 @@ object MessagesUrls { const val REMOVE_CHAT_USER = "$URL/messages.removeChatUser" const val GET_HISTORY_ATTACHMENTS = "$URL/messages.getHistoryAttachments" const val CREATE_CHAT = "$URL/messages.createChat" + const val GET_MESSAGE_READ_PEERS = "$URL/messages.getMessageReadPeers" } diff --git a/core/ui/src/main/res/drawable/round_visibility_24.xml b/core/ui/src/main/res/drawable/round_visibility_24.xml deleted file mode 100644 index 11319c64..00000000 --- a/core/ui/src/main/res/drawable/round_visibility_24.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - diff --git a/core/ui/src/main/res/drawable/round_visibility_24px.xml b/core/ui/src/main/res/drawable/round_visibility_24px.xml new file mode 100644 index 00000000..854becc2 --- /dev/null +++ b/core/ui/src/main/res/drawable/round_visibility_24px.xml @@ -0,0 +1,10 @@ + + + + diff --git a/feature/auth/src/main/kotlin/dev/meloda/fast/auth/login/presentation/LoginScreen.kt b/feature/auth/src/main/kotlin/dev/meloda/fast/auth/login/presentation/LoginScreen.kt index d13795af..dc9ba0fa 100644 --- a/feature/auth/src/main/kotlin/dev/meloda/fast/auth/login/presentation/LoginScreen.kt +++ b/feature/auth/src/main/kotlin/dev/meloda/fast/auth/login/presentation/LoginScreen.kt @@ -296,7 +296,7 @@ fun LoginScreen( trailingIcon = { val imagePainter = painterResource( id = if (screenState.passwordVisible) R.drawable.round_visibility_off_24 - else R.drawable.round_visibility_24 + else R.drawable.round_visibility_24px ) IconButton(onClick = onPasswordVisibilityButtonClicked) { diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModel.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModel.kt index 2d3813a8..3cc103ff 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModel.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModel.kt @@ -65,4 +65,6 @@ interface MessagesHistoryViewModel { fun onReplyCloseClicked() fun onRequestReplyToMessage(cmId: Long) + + suspend fun loadMessageReadPeers(peerId: Long, cmId: Long): Int } diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModelImpl.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModelImpl.kt index c30b5181..6b1c6fa3 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModelImpl.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/MessagesHistoryViewModelImpl.kt @@ -38,6 +38,7 @@ import dev.meloda.fast.data.processState import dev.meloda.fast.datastore.AppSettings import dev.meloda.fast.datastore.UserSettings import dev.meloda.fast.domain.ConversationsUseCase +import dev.meloda.fast.domain.GetMessageReadPeersUseCase import dev.meloda.fast.domain.LoadConversationsByIdUseCase import dev.meloda.fast.domain.LongPollUpdatesParser import dev.meloda.fast.domain.MessagesUseCase @@ -70,6 +71,8 @@ import kotlinx.serialization.json.buildJsonObject import kotlinx.serialization.json.put import java.io.File import java.io.FileOutputStream +import kotlin.coroutines.resume +import kotlin.coroutines.suspendCoroutine import kotlin.math.abs import kotlin.random.Random @@ -80,6 +83,7 @@ class MessagesHistoryViewModelImpl( private val resourceProvider: ResourceProvider, private val userSettings: UserSettings, private val loadConversationsByIdUseCase: LoadConversationsByIdUseCase, + private val getMessageReadPeersUseCase: GetMessageReadPeersUseCase, updatesParser: LongPollUpdatesParser, savedStateHandle: SavedStateHandle ) : MessagesHistoryViewModel, ViewModel() { @@ -575,6 +579,23 @@ class MessagesHistoryViewModelImpl( replyToMessage(cmId) } + override suspend fun loadMessageReadPeers(peerId: Long, cmId: Long): Int = suspendCoroutine { + viewModelScope.launch { + getMessageReadPeersUseCase + .invoke(peerId = peerId, cmId = cmId) + .listenValue(viewModelScope) { state -> + state.processState( + error = { error -> + it.resume(-1) + }, + success = { count -> + it.resume(count) + } + ) + } + } + } + private fun handleNewMessage(event: LongPollParsedEvent.NewMessage) { val message = event.message diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubble.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubble.kt index e6a8a5de..98d3c822 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubble.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubble.kt @@ -83,9 +83,7 @@ fun MessageBubble( MaterialTheme.colorScheme.onPrimaryContainer } - val shouldShowBubble by remember(text) { - derivedStateOf { text != null } - } + val shouldShowBubble = !text.isNullOrEmpty() var bubbleContainerWidth by remember { mutableIntStateOf(0) @@ -95,25 +93,21 @@ fun MessageBubble( mutableIntStateOf(0) } - val shouldFill by remember(bubbleContainerWidth, attachmentsContainerWidth) { - derivedStateOf { - attachmentsContainerWidth >= bubbleContainerWidth - } + val shouldFill by derivedStateOf { + attachmentsContainerWidth >= bubbleContainerWidth } var containerWidth by remember { mutableIntStateOf(0) } - val minDateContainerWidth by remember(isEdited, isOut, isPinned, isImportant) { - derivedStateOf { - val mainPart = if (isEdited) 50 else 30 - val readIndicatorPart = if (isOut) 14 else 0 - val pinnedIndicatorPart = if (isPinned) 14 else 0 - val importantIndicatorPart = if (isImportant) 14 else 0 + val minDateContainerWidth = remember(isEdited, isOut, isPinned, isImportant) { + val mainPart = if (isEdited) 50 else 30 + val readIndicatorPart = if (isOut) 14 else 0 + val pinnedIndicatorPart = if (isPinned) 14 else 0 + val importantIndicatorPart = if (isImportant) 14 else 0 - (mainPart + readIndicatorPart + pinnedIndicatorPart + importantIndicatorPart).dp - } + (mainPart + readIndicatorPart + pinnedIndicatorPart + importantIndicatorPart).dp } val dateContainerWidth by animateDpAsState( diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/IncomingMessageBubble.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubbleIncoming.kt similarity index 100% rename from feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/IncomingMessageBubble.kt rename to feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubbleIncoming.kt diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/OutgoingMessageBubble.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubbleOutgoing.kt similarity index 100% rename from feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/OutgoingMessageBubble.kt rename to feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessageBubbleOutgoing.kt diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryDialogs.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryDialogs.kt index e37d1cc4..c9da9897 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryDialogs.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryDialogs.kt @@ -14,11 +14,13 @@ import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Text import androidx.compose.material3.minimumInteractiveComponentSize import androidx.compose.runtime.Composable +import androidx.compose.runtime.LaunchedEffect import androidx.compose.runtime.getValue import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.dp @@ -38,6 +40,7 @@ import java.util.concurrent.TimeUnit fun HandleDialogs( screenState: MessagesHistoryScreenState, dialog: MessageDialog?, + messageReadPeersLoader: suspend (peerId: Long, cmId: Long) -> Int, onConfirmed: (MessageDialog, Bundle) -> Unit = { _, _ -> }, onDismissed: (MessageDialog) -> Unit = {}, onItemPicked: (MessageDialog, Bundle) -> Unit = { _, _ -> } @@ -49,6 +52,7 @@ fun HandleDialogs( MessageOptionsDialog( screenState = screenState, message = dialog.message, + messageReadPeersLoader = messageReadPeersLoader, onDismissed = { onDismissed(dialog) }, onItemPicked = { bundle -> onItemPicked(dialog, bundle) } ) @@ -102,9 +106,15 @@ fun HandleDialogs( fun MessageOptionsDialog( screenState: MessagesHistoryScreenState, message: VkMessage, + messageReadPeersLoader: suspend (peerId: Long, cmId: Long) -> Int, onDismissed: () -> Unit = {}, onItemPicked: (Bundle) -> Unit ) { + val primaryColor = MaterialTheme.colorScheme.primary + val errorColor = MaterialTheme.colorScheme.error + + val showReadPeers = message.isOut && message.isPeerChat() + val options = mutableListOf() if (message.isFailed()) { options += MessageOption.Retry @@ -142,41 +152,47 @@ fun MessageOptionsDialog( options += MessageOption.Delete - val messageOptions = options.map { option -> - Triple( - stringResource(option.titleResId), - painterResource(option.iconResId), - when { - option in listOf( - MessageOption.Delete, - MessageOption.MarkAsSpam - ) -> MaterialTheme.colorScheme.error + val messageOptions = remember(options) { + options.map { option -> + Triple( + option.titleResId, + option.iconResId, + when { + option in listOf( + MessageOption.Delete, + MessageOption.MarkAsSpam + ) -> errorColor - else -> MaterialTheme.colorScheme.primary - } - ) + else -> primaryColor + } + ) + } } MaterialDialog(onDismissRequest = onDismissed) { + if (showReadPeers) { + var viewCount by remember { + mutableStateOf(null) + } + + LaunchedEffect(Unit) { + viewCount = messageReadPeersLoader.invoke(message.peerId, message.cmId) + } + + MessageOptionItem( + title = viewCount?.let { "$it views" } ?: "...", + iconResId = R.drawable.round_visibility_24px, + tintColor = primaryColor, + onClick = {} + ) + } + messageOptions - .forEachIndexed { index, (title, painter, tintColor) -> - DropdownMenuItem( - text = { - Row { - Text(text = title) - Spacer(modifier = Modifier.width(8.dp)) - } - }, - leadingIcon = { - Row { - Spacer(modifier = Modifier.width(8.dp)) - Icon( - painter = painter, - contentDescription = null, - tint = tintColor - ) - } - }, + .forEachIndexed { index, (titleResId, iconResId, tintColor) -> + MessageOptionItem( + title = stringResource(titleResId), + iconResId = iconResId, + tintColor = tintColor, onClick = { onDismissed() val pickedOption = options[index] @@ -193,6 +209,34 @@ fun MessageOptionsDialog( } } +@Composable +private fun MessageOptionItem( + title: String, + iconResId: Int, + tintColor: Color, + onClick: () -> Unit +) { + DropdownMenuItem( + text = { + Row { + Text(text = title) + Spacer(modifier = Modifier.width(8.dp)) + } + }, + leadingIcon = { + Row { + Spacer(modifier = Modifier.width(8.dp)) + Icon( + painter = painterResource(iconResId), + contentDescription = null, + tint = tintColor + ) + } + }, + onClick = onClick + ) +} + @Composable fun MessageDeleteDialog( messages: List, diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryRoute.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryRoute.kt index 10224e81..48fa1acc 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryRoute.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesHistoryRoute.kt @@ -85,6 +85,7 @@ fun MessagesHistoryRoute( HandleDialogs( screenState = screenState, dialog = dialog, + messageReadPeersLoader = viewModel::loadMessageReadPeers, onConfirmed = viewModel::onDialogConfirmed, onDismissed = viewModel::onDialogDismissed, onItemPicked = viewModel::onDialogItemPicked diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesList.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesList.kt index 979e0d4e..03b545b8 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesList.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/MessagesList.kt @@ -78,22 +78,21 @@ fun MessagesList( val scope = rememberCoroutineScope() - val onAttachmentClick by rememberUpdatedState( - { message: UiItem.Message, attachment: VkAttachment -> - if (isSelectedAtLeastOne) { - onMessageClicked(message.id) - } else { - when (attachment) { - is VkPhotoDomain -> { - val photos = message.attachments - .orEmpty() - .filterIsInstance() - .mapNotNull { photo -> photo.getMaxSize()?.url } + val onAttachmentClick by rememberUpdatedState { message: UiItem.Message, attachment: VkAttachment -> + if (isSelectedAtLeastOne) { + onMessageClicked(message.id) + } else { + when (attachment) { + is VkPhotoDomain -> { + val photos = message.attachments + .orEmpty() + .filterIsInstance() + .mapNotNull { photo -> photo.getMaxSize()?.url } - onPhotoClicked( - photos, - photos.indexOfFirst { it == attachment.getMaxSize()?.url } - ) + onPhotoClicked( + photos, + photos.indexOfFirst { it == attachment.getMaxSize()?.url } + ) // val maxSize = attachment.getMaxSize() // maxSize?.let { @@ -101,39 +100,36 @@ fun MessagesList( // Intent(Intent.ACTION_VIEW, maxSize.url.toUri()) // ) // } - } + } - is VkFileDomain -> { - context.startActivity( - Intent(Intent.ACTION_VIEW, attachment.url.toUri()) - ) - } + is VkFileDomain -> { + context.startActivity( + Intent(Intent.ACTION_VIEW, attachment.url.toUri()) + ) + } - is VkLinkDomain -> { - context.startActivity( - Intent(Intent.ACTION_VIEW, attachment.url.toUri()) - ) - } + is VkLinkDomain -> { + context.startActivity( + Intent(Intent.ACTION_VIEW, attachment.url.toUri()) + ) } } } - ) + } - val onAttachmentLongClick by rememberUpdatedState( - { message: UiItem.Message, attachment: VkAttachment -> - if (isSelectedAtLeastOne) { - onMessageLongClicked(message.id) - uiMessages - } else { - when (attachment) { - is VkPhotoDomain -> { - val maxSize = attachment.getMaxSize() - Log.d("MessagesList", "onPhotoLongClicked. Max size: ${maxSize?.url}") - } + val onAttachmentLongClick by rememberUpdatedState { message: UiItem.Message, attachment: VkAttachment -> + if (isSelectedAtLeastOne) { + onMessageLongClicked(message.id) + uiMessages + } else { + when (attachment) { + is VkPhotoDomain -> { + val maxSize = attachment.getMaxSize() + Log.d("MessagesList", "onPhotoLongClicked. Max size: ${maxSize?.url}") } } } - ) + } LazyColumn( modifier = modifier @@ -207,7 +203,6 @@ fun MessagesList( if (offsetDistinct == -100f && AppSettings.General.enableHaptic) { view.performHapticFeedback(HapticFeedbackConstantsCompat.CONTEXT_CLICK) } - Log.d("MessagesList", "offsetDistinct: $offsetDistinct") } Surface( diff --git a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/attachments/Reply.kt b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/attachments/Reply.kt index f982dbc1..1c0a23fb 100644 --- a/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/attachments/Reply.kt +++ b/feature/messageshistory/src/main/kotlin/dev/meloda/fast/messageshistory/presentation/attachments/Reply.kt @@ -28,14 +28,14 @@ import androidx.compose.ui.unit.dp @Composable fun Reply( - modifier: Modifier = Modifier, + onClick: () -> Unit, bottomPadding: Dp, shape: Shape, - onClick: () -> Unit, backgroundColor: Color, innerBackgroundColor: Color, title: String, - summary: String? + summary: String?, + modifier: Modifier = Modifier ) { Box( modifier = modifier