Skip to content

Commit

Permalink
Merge pull request #4746 from nextcloud/refactorContactsActivityCompose
Browse files Browse the repository at this point in the history
ContactsScreen: extract Composables to files and simplify passed parameters
  • Loading branch information
mahibi authored Feb 20, 2025
2 parents 5c11a2e + 7615b92 commit d3a6532
Show file tree
Hide file tree
Showing 12 changed files with 690 additions and 478 deletions.

Large diffs are not rendered by default.

75 changes: 75 additions & 0 deletions app/src/main/java/com/nextcloud/talk/contacts/ContactsScreen.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
/*
* Nextcloud Talk - Android Client
*
* SPDX-FileCopyrightText: 2024 Sowjanya Kota <sowjanya.kch@gmail.com>
* SPDX-FileCopyrightText: 2025 Marcel Hibbe <dev@mhibbe.de>
* SPDX-License-Identifier: GPL-3.0-or-later
*/

package com.nextcloud.talk.contacts

import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Scaffold
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.colorResource
import androidx.compose.ui.res.stringResource
import androidx.lifecycle.compose.collectAsStateWithLifecycle
import com.nextcloud.talk.R
import com.nextcloud.talk.contacts.components.AppBar
import com.nextcloud.talk.contacts.components.ContactsList
import com.nextcloud.talk.contacts.components.ConversationCreationOptions

@Composable
fun ContactsScreen(contactsViewModel: ContactsViewModel, uiState: ContactsUiState) {
val context = LocalContext.current

val searchQuery by contactsViewModel.searchQuery.collectAsStateWithLifecycle()
val isSearchActive by contactsViewModel.isSearchActive.collectAsStateWithLifecycle()
val isAddParticipants by contactsViewModel.isAddParticipantsView.collectAsStateWithLifecycle()
val autocompleteUsers by contactsViewModel.selectedParticipantsList.collectAsStateWithLifecycle()

Scaffold(
topBar = {
AppBar(
title = stringResource(R.string.nc_app_product_name),
searchQuery = searchQuery,
isSearchActive = isSearchActive,
isAddParticipants = isAddParticipants,
autocompleteUsers = autocompleteUsers,
onEnableSearch = {
contactsViewModel.setSearchActive(true)
},
onDisableSearch = {
contactsViewModel.setSearchActive(false)
},
onUpdateSearchQuery = {
contactsViewModel.updateSearchQuery(query = it)
},
onUpdateAutocompleteUsers = {
contactsViewModel.getContactsFromSearchParams()
}
)
},
content = {
Column(
Modifier.padding(it)
.background(colorResource(id = R.color.bg_default))
) {
ConversationCreationOptions(
context = context,
contactsViewModel = contactsViewModel
)
ContactsList(
contactsUiState = uiState,
contactsViewModel = contactsViewModel,
context = context
)
}
}
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,8 @@ class ContactsViewModel @Inject constructor(
val searchQuery: StateFlow<String> = _searchQuery
private val shareTypes: MutableList<String> = mutableListOf(ShareType.User.shareType)
val shareTypeList: List<String> = shareTypes
private val _searchState = MutableStateFlow(false)
val searchState: StateFlow<Boolean> = _searchState
private val _isSearchActive = MutableStateFlow(false)
val isSearchActive: StateFlow<Boolean> = _isSearchActive
private val selectedParticipants = MutableStateFlow<List<AutocompleteUser>>(emptyList())
val selectedParticipantsList: StateFlow<List<AutocompleteUser>> = selectedParticipants.asStateFlow()
private val _isAddParticipantsView = MutableStateFlow(false)
Expand All @@ -57,8 +57,8 @@ class ContactsViewModel @Inject constructor(
fun updateSelectedParticipants(participants: List<AutocompleteUser>) {
selectedParticipants.value = participants
}
fun updateSearchState(searchState: Boolean) {
_searchState.value = searchState
fun setSearchActive(searchState: Boolean) {
_isSearchActive.value = searchState
}

fun updateShareTypes(value: List<String>) {
Expand Down
104 changes: 0 additions & 104 deletions app/src/main/java/com/nextcloud/talk/contacts/SearchComponent.kt

This file was deleted.

89 changes: 89 additions & 0 deletions app/src/main/java/com/nextcloud/talk/contacts/components/AppBar.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@
/*
* Nextcloud Talk - Android Client
*
* SPDX-FileCopyrightText: 2024 Sowjanya Kota <sowjanya.kch@gmail.com>
* SPDX-FileCopyrightText: 2025 Marcel Hibbe <dev@mhibbe.de>
* SPDX-License-Identifier: GPL-3.0-or-later
*/

package com.nextcloud.talk.contacts.components

import android.annotation.SuppressLint
import android.app.Activity
import android.content.Intent
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Row
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.automirrored.filled.ArrowBack
import androidx.compose.material.icons.filled.Search
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton
import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBar
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.stringResource
import com.nextcloud.talk.R
import com.nextcloud.talk.models.json.autocomplete.AutocompleteUser

@SuppressLint("UnrememberedMutableState")
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun AppBar(
title: String,
searchQuery: String,
isSearchActive: Boolean,
isAddParticipants: Boolean,
autocompleteUsers: List<AutocompleteUser>,
onEnableSearch: () -> Unit,
onDisableSearch: () -> Unit,
onUpdateSearchQuery: (String) -> Unit,
onUpdateAutocompleteUsers: () -> Unit
) {
val context = LocalContext.current

TopAppBar(
title = { Text(text = title) },
navigationIcon = {
IconButton(onClick = {
(context as? Activity)?.finish()
}) {
Icon(Icons.AutoMirrored.Filled.ArrowBack, contentDescription = stringResource(R.string.back_button))
}
},
actions = {
IconButton(onClick = onEnableSearch) {
Icon(Icons.Filled.Search, contentDescription = stringResource(R.string.search_icon))
}
if (isAddParticipants) {
Text(
text = stringResource(id = R.string.nc_contacts_done),
modifier = Modifier.clickable {
val resultIntent = Intent().apply {
putParcelableArrayListExtra(
"selectedParticipants",
ArrayList(autocompleteUsers)
)
}
(context as? Activity)?.setResult(Activity.RESULT_OK, resultIntent)
(context as? Activity)?.finish()
}
)
}
}
)
if (isSearchActive) {
Row {
SearchComponent(
text = searchQuery,
onTextChange = { searchQuery ->
onUpdateSearchQuery(searchQuery)
onUpdateAutocompleteUsers()
},
onDisableSearch = onDisableSearch
)
}
}
}
Loading

0 comments on commit d3a6532

Please sign in to comment.