diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryLocation.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryLocation.kt index 3e0ec3ea911f726355e3afef50eb4aa90f16bbe5..78ff94aa01a3af64f4036d54b4e8daeb14cc1321 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryLocation.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryLocation.kt @@ -2,6 +2,8 @@ package de.rki.coronawarnapp.contactdiary.model data class DefaultContactDiaryLocation( override val locationId: Long = 0L, - override var locationName: String, - override val stableId: Long = locationId -) : ContactDiaryLocation + override var locationName: String +) : ContactDiaryLocation { + override val stableId: Long + get() = locationId +} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryPerson.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryPerson.kt index 1d0188925b5baef305ba5aeccc702971cfa4ac01..911bd939bfc14b4fbdebc634d6ccdaf11bf68d7e 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryPerson.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/model/DefaultContactDiaryPerson.kt @@ -2,6 +2,8 @@ package de.rki.coronawarnapp.contactdiary.model data class DefaultContactDiaryPerson( override val personId: Long = 0L, - override var fullName: String, - override val stableId: Long = personId -) : ContactDiaryPerson + override var fullName: String +) : ContactDiaryPerson { + override val stableId: Long + get() = personId +} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/ContactDiaryDayFragment.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/ContactDiaryDayFragment.kt index ae4dd4fc0ddd33175b5b532bb5980d9c07475c88..2301d5682a6ac8ad115851d100dad35ab47c1f2e 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/ContactDiaryDayFragment.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/ContactDiaryDayFragment.kt @@ -62,9 +62,11 @@ class ContactDiaryDayFragment : Fragment(R.layout.contact_diary_day_fragment), A } } - viewModel.uiState.observe2(this) { - binding.contactDiaryDayHeader.title = it.dayText(requireContext()) - binding.contactDiaryDayHeader.contentDescription = it.dayTextContentDescription(requireContext()) + viewModel.uiState.observe2(this) { uiState -> + binding.contactDiaryDayHeader.apply { + title = uiState.dayText(context) + contentDescription = uiState.dayTextContentDescription(context) + } } viewModel.routeToScreen.observe2(this) { diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/location/ContactDiaryLocationListAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/location/ContactDiaryLocationListAdapter.kt index 53ad1fa2d41f1b8a20164d6fa8531dc1727f420b..0e1dbfd1a8eeff1a8d3e3966d9351238d906485b 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/location/ContactDiaryLocationListAdapter.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/location/ContactDiaryLocationListAdapter.kt @@ -4,25 +4,19 @@ import android.view.ViewGroup import android.view.accessibility.AccessibilityEvent import de.rki.coronawarnapp.R import de.rki.coronawarnapp.contactdiary.model.ContactDiaryLocation +import de.rki.coronawarnapp.contactdiary.util.AbstractAdapter import de.rki.coronawarnapp.contactdiary.util.SelectableItem import de.rki.coronawarnapp.contactdiary.util.setClickLabel import de.rki.coronawarnapp.databinding.ContactDiaryLocationListItemBinding import de.rki.coronawarnapp.ui.lists.BaseAdapter import de.rki.coronawarnapp.util.lists.BindableVH import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffUtilAdapter -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffer -class ContactDiaryLocationListAdapter( +internal class ContactDiaryLocationListAdapter( private val onTappedCallback: (item: SelectableItem<ContactDiaryLocation>) -> Unit -) : BaseAdapter<ContactDiaryLocationListAdapter.CachedLocationViewHolder>(), +) : AbstractAdapter<SelectableItem<ContactDiaryLocation>, ContactDiaryLocationListAdapter.CachedLocationViewHolder>(), AsyncDiffUtilAdapter<SelectableItem<ContactDiaryLocation>> { - override val asyncDiffer: AsyncDiffer<SelectableItem<ContactDiaryLocation>> = AsyncDiffer(this) - - override fun getItemCount(): Int = data.size - - override fun getItemId(position: Int): Long = data[position].stableId - override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): CachedLocationViewHolder = CachedLocationViewHolder(parent) diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/person/ContactDiaryPersonListAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/person/ContactDiaryPersonListAdapter.kt index f8142cb31790c510697b750316d50e77c200de9c..d45e619471ab3b4f4513ac93c16b6ea7120be981 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/person/ContactDiaryPersonListAdapter.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/day/tabs/person/ContactDiaryPersonListAdapter.kt @@ -4,25 +4,19 @@ import android.view.ViewGroup import android.view.accessibility.AccessibilityEvent import de.rki.coronawarnapp.R import de.rki.coronawarnapp.contactdiary.model.ContactDiaryPerson +import de.rki.coronawarnapp.contactdiary.util.AbstractAdapter import de.rki.coronawarnapp.contactdiary.util.SelectableItem import de.rki.coronawarnapp.contactdiary.util.setClickLabel import de.rki.coronawarnapp.databinding.ContactDiaryPersonListItemBinding import de.rki.coronawarnapp.ui.lists.BaseAdapter import de.rki.coronawarnapp.util.lists.BindableVH import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffUtilAdapter -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffer -class ContactDiaryPersonListAdapter( +internal class ContactDiaryPersonListAdapter( private val onTappedCallback: (item: SelectableItem<ContactDiaryPerson>) -> Unit -) : BaseAdapter<ContactDiaryPersonListAdapter.CachedPersonViewHolder>(), +) : AbstractAdapter<SelectableItem<ContactDiaryPerson>, ContactDiaryPersonListAdapter.CachedPersonViewHolder>(), AsyncDiffUtilAdapter<SelectableItem<ContactDiaryPerson>> { - override val asyncDiffer: AsyncDiffer<SelectableItem<ContactDiaryPerson>> = AsyncDiffer(this) - - override fun getItemCount(): Int = data.size - - override fun getItemId(position: Int): Long = data[position].stableId - override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): CachedPersonViewHolder = CachedPersonViewHolder(parent) diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsFragment.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsFragment.kt index e9c77914fabb5e74f02964cc10a5a1fe2762614f..5a226c1139680e183acad1ee8307828b1a8fc347 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsFragment.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsFragment.kt @@ -1,24 +1,17 @@ package de.rki.coronawarnapp.contactdiary.ui.edit import android.os.Bundle -import android.view.LayoutInflater import android.view.View -import android.view.ViewGroup import android.view.accessibility.AccessibilityEvent -import android.widget.TextView import androidx.core.view.isGone import androidx.fragment.app.Fragment -import androidx.recyclerview.widget.RecyclerView import de.rki.coronawarnapp.R -import de.rki.coronawarnapp.contactdiary.model.ContactDiaryLocation import de.rki.coronawarnapp.contactdiary.ui.edit.ContactDiaryEditLocationsViewModel.NavigationEvent.ShowDeletionConfirmationDialog import de.rki.coronawarnapp.contactdiary.ui.edit.ContactDiaryEditLocationsViewModel.NavigationEvent.ShowLocationDetailSheet -import de.rki.coronawarnapp.contactdiary.util.setClickLabel +import de.rki.coronawarnapp.contactdiary.ui.edit.adapter.LocationEditAdapter import de.rki.coronawarnapp.databinding.ContactDiaryEditLocationsFragmentBinding import de.rki.coronawarnapp.util.DialogHelper import de.rki.coronawarnapp.util.di.AutoInject -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffUtilAdapter -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffer import de.rki.coronawarnapp.util.lists.diffutil.update import de.rki.coronawarnapp.util.ui.doNavigate import de.rki.coronawarnapp.util.ui.observe2 @@ -34,7 +27,7 @@ class ContactDiaryEditLocationsFragment : Fragment(R.layout.contact_diary_edit_l private val viewModel: ContactDiaryEditLocationsViewModel by cwaViewModels { viewModelFactory } private val binding: ContactDiaryEditLocationsFragmentBinding by viewBindingLazy() - private lateinit var listAdapter: ListAdapter + private lateinit var listAdapter: LocationEditAdapter override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) @@ -81,9 +74,11 @@ class ContactDiaryEditLocationsFragment : Fragment(R.layout.contact_diary_edit_l } private fun setupRecyclerView() { - listAdapter = ListAdapter(getString(R.string.accessibility_edit)) { - getString(R.string.accessibility_location, it.locationName) - } + listAdapter = LocationEditAdapter( + clickLabelString = getString(R.string.accessibility_edit), + getContentDescriptionString = { getString(R.string.accessibility_location, it.locationName) }, + onItemClicked = { viewModel.onEditLocationClick(it) } + ) binding.locationsRecyclerView.adapter = listAdapter } @@ -99,43 +94,4 @@ class ContactDiaryEditLocationsFragment : Fragment(R.layout.contact_diary_edit_l } ) } - - inner class ListAdapter( - private val clickLabelString: String, - private val getContentDescriptionString: (ContactDiaryLocation) -> String - ) : RecyclerView.Adapter<ListAdapter.ViewHolder>(), - AsyncDiffUtilAdapter<ContactDiaryLocation> { - - override val asyncDiffer: AsyncDiffer<ContactDiaryLocation> = AsyncDiffer(this) - - inner class ViewHolder(listItemView: View) : RecyclerView.ViewHolder(listItemView) { - val nameTextView = itemView.findViewById<TextView>(R.id.name) - val itemContainerView = itemView.findViewById<View>(R.id.item_container) - } - - override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ListAdapter.ViewHolder { - val view = LayoutInflater.from(parent.context).inflate(R.layout.contact_diary_edit_list_item, parent, false) - return ViewHolder(view) - } - - override fun onBindViewHolder(viewHolder: ListAdapter.ViewHolder, position: Int) { - val location = data[position] - with(viewHolder) { - nameTextView.text = location.locationName - itemContainerView.setOnClickListener { - viewModel.onEditLocationClick(location) - } - itemContainerView.contentDescription = getContentDescriptionString(location) - itemContainerView.setClickLabel(clickLabelString) - } - } - - override fun getItemCount(): Int { - return data.size - } - - override fun getItemId(position: Int): Long { - return data[position].locationId - } - } } diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsViewModel.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsViewModel.kt index 3ef030e2cb7a656271e2e7f3efe88d19da273f20..c4a5dd4e1555d3af1399ca77f501bfe8d41d32a5 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsViewModel.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditLocationsViewModel.kt @@ -28,10 +28,10 @@ class ContactDiaryEditLocationsViewModel @AssistedInject constructor( val navigationEvent = SingleLiveEvent<NavigationEvent>() - val isButtonEnabled = contactDiaryRepository.locations.map { !it.isNullOrEmpty() } + val isButtonEnabled = contactDiaryRepository.locations.map { it.isNotEmpty() } .asLiveData(dispatcherProvider.IO) - val isListVisible = contactDiaryRepository.locations.map { !it.isNullOrEmpty() } + val isListVisible = contactDiaryRepository.locations.map { it.isNotEmpty() } .asLiveData(dispatcherProvider.IO) fun onDeleteAllLocationsClick() { diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsFragment.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsFragment.kt index eaeace7dd4329e2179d3803652d29d0b86f55332..bd46ac7977fcb952ecb6a172ed22f49935327ff5 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsFragment.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsFragment.kt @@ -1,24 +1,17 @@ package de.rki.coronawarnapp.contactdiary.ui.edit import android.os.Bundle -import android.view.LayoutInflater import android.view.View -import android.view.ViewGroup import android.view.accessibility.AccessibilityEvent -import android.widget.TextView import androidx.core.view.isGone import androidx.fragment.app.Fragment -import androidx.recyclerview.widget.RecyclerView import de.rki.coronawarnapp.R -import de.rki.coronawarnapp.contactdiary.model.ContactDiaryPerson import de.rki.coronawarnapp.contactdiary.ui.edit.ContactDiaryEditPersonsViewModel.NavigationEvent.ShowDeletionConfirmationDialog import de.rki.coronawarnapp.contactdiary.ui.edit.ContactDiaryEditPersonsViewModel.NavigationEvent.ShowPersonDetailSheet -import de.rki.coronawarnapp.contactdiary.util.setClickLabel +import de.rki.coronawarnapp.contactdiary.ui.edit.adapter.PersonEditAdapter import de.rki.coronawarnapp.databinding.ContactDiaryEditPersonsFragmentBinding import de.rki.coronawarnapp.util.DialogHelper import de.rki.coronawarnapp.util.di.AutoInject -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffUtilAdapter -import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffer import de.rki.coronawarnapp.util.lists.diffutil.update import de.rki.coronawarnapp.util.ui.doNavigate import de.rki.coronawarnapp.util.ui.observe2 @@ -34,7 +27,7 @@ class ContactDiaryEditPersonsFragment : Fragment(R.layout.contact_diary_edit_per private val viewModel: ContactDiaryEditPersonsViewModel by cwaViewModels { viewModelFactory } private val binding: ContactDiaryEditPersonsFragmentBinding by viewBindingLazy() - private lateinit var listAdapter: ListAdapter + private lateinit var listAdapter: PersonEditAdapter override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) @@ -83,9 +76,11 @@ class ContactDiaryEditPersonsFragment : Fragment(R.layout.contact_diary_edit_per } private fun setupRecyclerView() { - listAdapter = ListAdapter(getString(R.string.accessibility_edit)) { - getString(R.string.accessibility_person, it.fullName) - } + listAdapter = PersonEditAdapter( + clickLabelString = getString(R.string.accessibility_edit), + getContentDescriptionString = { getString(R.string.accessibility_person, it.fullName) }, + onItemClicked = { viewModel.onEditPersonClick(it) } + ) binding.personsRecyclerView.adapter = listAdapter } @@ -101,43 +96,4 @@ class ContactDiaryEditPersonsFragment : Fragment(R.layout.contact_diary_edit_per } ) } - - inner class ListAdapter( - private val clickLabelString: String, - private val getContentDescriptionString: (ContactDiaryPerson) -> String - ) : RecyclerView.Adapter<ListAdapter.ViewHolder>(), - AsyncDiffUtilAdapter<ContactDiaryPerson> { - - override val asyncDiffer: AsyncDiffer<ContactDiaryPerson> = AsyncDiffer(this) - - inner class ViewHolder(listItemView: View) : RecyclerView.ViewHolder(listItemView) { - val nameTextView = itemView.findViewById<TextView>(R.id.name) - val itemContainerView = itemView.findViewById<View>(R.id.item_container) - } - - override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ListAdapter.ViewHolder { - val view = LayoutInflater.from(parent.context).inflate(R.layout.contact_diary_edit_list_item, parent, false) - return ViewHolder(view) - } - - override fun onBindViewHolder(viewHolder: ListAdapter.ViewHolder, position: Int) { - val person = data[position] - with(viewHolder) { - nameTextView.text = person.fullName - itemContainerView.setOnClickListener { - viewModel.onEditPersonClick(person) - } - itemContainerView.contentDescription = getContentDescriptionString(person) - itemContainerView.setClickLabel(clickLabelString) - } - } - - override fun getItemCount(): Int { - return data.size - } - - override fun getItemId(position: Int): Long { - return data[position].personId - } - } } diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsViewModel.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsViewModel.kt index 2fa6a23e7591d2984509a6aed59f34e182368906..d418c003a4c83a64fbd4a0644bbe1c96b842df69 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsViewModel.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/ContactDiaryEditPersonsViewModel.kt @@ -25,10 +25,10 @@ class ContactDiaryEditPersonsViewModel @AssistedInject constructor( val personsLiveData = contactDiaryRepository.people .asLiveData() - val isButtonEnabled = contactDiaryRepository.people.map { !it.isNullOrEmpty() } + val isButtonEnabled = contactDiaryRepository.people.map { it.isNotEmpty() } .asLiveData(dispatcherProvider.IO) - val isListVisible = contactDiaryRepository.people.map { !it.isNullOrEmpty() } + val isListVisible = contactDiaryRepository.people.map { it.isNotEmpty() } .asLiveData(dispatcherProvider.IO) private val coroutineExceptionHandler = CoroutineExceptionHandler { coroutineContext, ex -> diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/LocationEditAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/LocationEditAdapter.kt new file mode 100644 index 0000000000000000000000000000000000000000..54b560ab31cd084c2d3fe6208f30a1651de540c1 --- /dev/null +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/LocationEditAdapter.kt @@ -0,0 +1,40 @@ +package de.rki.coronawarnapp.contactdiary.ui.edit.adapter + +import android.view.ViewGroup +import de.rki.coronawarnapp.R +import de.rki.coronawarnapp.contactdiary.model.ContactDiaryLocation +import de.rki.coronawarnapp.contactdiary.util.AbstractAdapter +import de.rki.coronawarnapp.contactdiary.util.setClickLabel +import de.rki.coronawarnapp.databinding.ContactDiaryEditListItemBinding +import de.rki.coronawarnapp.ui.lists.BaseAdapter +import de.rki.coronawarnapp.util.lists.BindableVH + +internal class LocationEditAdapter( + private val clickLabelString: String, + private val getContentDescriptionString: (ContactDiaryLocation) -> String, + private val onItemClicked: (item: ContactDiaryLocation) -> Unit +) : AbstractAdapter<ContactDiaryLocation, LocationEditAdapter.ViewHolder>() { + + override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): ViewHolder = ViewHolder(parent) + + override fun onBindBaseVH(holder: ViewHolder, position: Int, payloads: MutableList<Any>) = + holder.bind(data[position], payloads) + + inner class ViewHolder(parent: ViewGroup) : BaseAdapter.VH(R.layout.contact_diary_edit_list_item, parent), + BindableVH<ContactDiaryLocation, ContactDiaryEditListItemBinding> { + override val viewBinding: + Lazy<ContactDiaryEditListItemBinding> = + lazy { ContactDiaryEditListItemBinding.bind(itemView) } + + override val onBindData: + ContactDiaryEditListItemBinding.(item: ContactDiaryLocation, payloads: List<Any>) -> Unit = + { location, _ -> + name.text = location.locationName + itemContainer.apply { + setOnClickListener { onItemClicked(location) } + contentDescription = getContentDescriptionString(location) + setClickLabel(clickLabelString) + } + } + } +} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/PersonEditAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/PersonEditAdapter.kt new file mode 100644 index 0000000000000000000000000000000000000000..c241ecef2fb03586ec4d16a135d9e58f30aa3c18 --- /dev/null +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/edit/adapter/PersonEditAdapter.kt @@ -0,0 +1,40 @@ +package de.rki.coronawarnapp.contactdiary.ui.edit.adapter + +import android.view.ViewGroup +import de.rki.coronawarnapp.R +import de.rki.coronawarnapp.contactdiary.model.ContactDiaryPerson +import de.rki.coronawarnapp.contactdiary.util.AbstractAdapter +import de.rki.coronawarnapp.contactdiary.util.setClickLabel +import de.rki.coronawarnapp.databinding.ContactDiaryEditListItemBinding +import de.rki.coronawarnapp.ui.lists.BaseAdapter +import de.rki.coronawarnapp.util.lists.BindableVH + +internal class PersonEditAdapter( + private val clickLabelString: String, + private val getContentDescriptionString: (ContactDiaryPerson) -> String, + private val onItemClicked: (item: ContactDiaryPerson) -> Unit +) : AbstractAdapter<ContactDiaryPerson, PersonEditAdapter.ViewHolder>() { + + override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): ViewHolder = ViewHolder(parent) + + override fun onBindBaseVH(holder: ViewHolder, position: Int, payloads: MutableList<Any>) = + holder.bind(data[position], payloads) + + inner class ViewHolder(parent: ViewGroup) : BaseAdapter.VH(R.layout.contact_diary_edit_list_item, parent), + BindableVH<ContactDiaryPerson, ContactDiaryEditListItemBinding> { + override val viewBinding: + Lazy<ContactDiaryEditListItemBinding> = + lazy { ContactDiaryEditListItemBinding.bind(itemView) } + + override val onBindData: + ContactDiaryEditListItemBinding.(item: ContactDiaryPerson, payloads: List<Any>) -> Unit = + { person, _ -> + name.text = person.fullName + itemContainer.apply { + setOnClickListener { onItemClicked(person) } + contentDescription = getContentDescriptionString(person) + setClickLabel(clickLabelString) + } + } + } +} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewFragment.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewFragment.kt index dc4624cdab362a923686a3304da8b921af3b629c..4cef4c67c8851503d535c67b39320b5cd6523a82 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewFragment.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewFragment.kt @@ -3,6 +3,7 @@ package de.rki.coronawarnapp.contactdiary.ui.overview import android.os.Bundle import android.view.View import android.view.accessibility.AccessibilityEvent +import androidx.appcompat.widget.Toolbar import androidx.core.app.ShareCompat import androidx.fragment.app.Fragment import de.rki.coronawarnapp.R @@ -23,7 +24,6 @@ import javax.inject.Inject class ContactDiaryOverviewFragment : Fragment(R.layout.contact_diary_overview_fragment), AutoInject { @Inject lateinit var viewModelFactory: CWAViewModelFactoryProvider.Factory - @Inject lateinit var contactDiaryOverviewMenu: ContactDiaryOverviewMenu private val vm: ContactDiaryOverviewViewModel by cwaViewModels { viewModelFactory } private val binding: ContactDiaryOverviewFragmentBinding by viewBindingLazy() @@ -35,7 +35,7 @@ class ContactDiaryOverviewFragment : Fragment(R.layout.contact_diary_overview_fr { vm.onItemPress(it) } ) - setupToolbar() + setupMenu(binding.toolbar) binding.apply { contactDiaryOverviewRecyclerview.adapter = adapter @@ -89,7 +89,37 @@ class ContactDiaryOverviewFragment : Fragment(R.layout.contact_diary_overview_fr } } - private fun setupToolbar() { - contactDiaryOverviewMenu.setupMenu(binding.toolbar) + private fun setupMenu(toolbar: Toolbar) = toolbar.apply { + inflateMenu(R.menu.menu_contact_diary_overview) + setOnMenuItemClickListener { + when (it.itemId) { + R.id.menu_contact_diary_information -> { + doNavigate( + ContactDiaryOverviewFragmentDirections + .actionContactDiaryOverviewFragmentToContactDiaryOnboardingFragment() + ) + true + } + R.id.menu_contact_diary_export_entries -> { + vm.onExportPress(context) + true + } + R.id.menu_contact_diary_edit_persons -> { + doNavigate( + ContactDiaryOverviewFragmentDirections + .actionContactDiaryOverviewFragmentToContactDiaryEditPersonsFragment() + ) + true + } + R.id.menu_contact_diary_edit_locations -> { + doNavigate( + ContactDiaryOverviewFragmentDirections + .actionContactDiaryOverviewFragmentToContactDiaryEditLocationsFragment() + ) + true + } + else -> onOptionsItemSelected(it) + } + } } } diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewMenu.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewMenu.kt deleted file mode 100644 index 048c25a9f2de0dc6f7b82ccee8b40415c5677a13..0000000000000000000000000000000000000000 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewMenu.kt +++ /dev/null @@ -1,52 +0,0 @@ -package de.rki.coronawarnapp.contactdiary.ui.overview - -import androidx.appcompat.widget.Toolbar -import androidx.navigation.NavController -import androidx.navigation.fragment.findNavController -import de.rki.coronawarnapp.R -import de.rki.coronawarnapp.ui.doNavigate -import de.rki.coronawarnapp.util.viewmodel.cwaViewModels -import javax.inject.Inject - -// TODO(Remove this useless class) -class ContactDiaryOverviewMenu @Inject constructor( - private val contactDiaryOverviewFragment: ContactDiaryOverviewFragment -) { - - private val navController: NavController - get() = contactDiaryOverviewFragment.findNavController() - private val vm: ContactDiaryOverviewViewModel by contactDiaryOverviewFragment.cwaViewModels { - contactDiaryOverviewFragment.viewModelFactory - } - - fun setupMenu(toolbar: Toolbar) = toolbar.apply { - inflateMenu(R.menu.menu_contact_diary_overview) - setOnMenuItemClickListener { - when (it.itemId) { - R.id.menu_contact_diary_information -> { - navController.doNavigate( - ContactDiaryOverviewFragmentDirections - .actionContactDiaryOverviewFragmentToContactDiaryOnboardingFragment() - ) - true - } - R.id.menu_contact_diary_export_entries -> { - vm.onExportPress(context) - true } - R.id.menu_contact_diary_edit_persons -> { - navController.doNavigate( - ContactDiaryOverviewFragmentDirections - .actionContactDiaryOverviewFragmentToContactDiaryEditPersonsFragment()) - true - } - R.id.menu_contact_diary_edit_locations -> { - navController.doNavigate( - ContactDiaryOverviewFragmentDirections - .actionContactDiaryOverviewFragmentToContactDiaryEditLocationsFragment()) - true - } - else -> contactDiaryOverviewFragment.onOptionsItemSelected(it) - } - } - } -} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewViewModel.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewViewModel.kt index 554bf6d88ccd8dac7ac5c3f110df500b931e0402..a0dbcbfaeff4060b8994d3903e953ddc1667cd86 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewViewModel.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/ContactDiaryOverviewViewModel.kt @@ -139,7 +139,9 @@ class ContactDiaryOverviewViewModel @AssistedInject constructor( } } - private fun List<String>.addToStringBuilder(sb: StringBuilder, dateString: String) = sorted() + private fun List<String>.addToStringBuilder(sb: StringBuilder, dateString: String) = sortedBy { + it.toLowerCase(Locale.ROOT) + } .forEach { sb.appendLine("$dateString $it") } // According to tech spec german locale only diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewAdapter.kt index 05a3a950db4b7cb8613ab4b168bc76e26f031450..3e3c3a730f25006b120c4930900c60bf1bd83b9e 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewAdapter.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewAdapter.kt @@ -1,67 +1,54 @@ package de.rki.coronawarnapp.contactdiary.ui.overview.adapter -import android.view.LayoutInflater import android.view.ViewGroup import androidx.core.view.isGone -import androidx.recyclerview.widget.RecyclerView +import de.rki.coronawarnapp.R +import de.rki.coronawarnapp.contactdiary.util.clearAndAddAll import de.rki.coronawarnapp.databinding.ContactDiaryOverviewListItemBinding +import de.rki.coronawarnapp.ui.lists.BaseAdapter +import de.rki.coronawarnapp.util.lists.BindableVH import org.joda.time.LocalDate class ContactDiaryOverviewAdapter( private val dateFormatter: (LocalDate) -> String, private val dateFormatterForAccessibility: (LocalDate) -> String, private val onItemSelectionListener: (ListItem) -> Unit -) : - RecyclerView.Adapter<ContactDiaryOverviewAdapter.OverviewElementHolder>() { +) : BaseAdapter<ContactDiaryOverviewAdapter.OverviewElementHolder>() { + private val elements: MutableList<ListItem> = mutableListOf() fun setItems(elements: List<ListItem>) { - this.elements.clear() - this.elements += elements + this.elements.clearAndAddAll(elements) notifyDataSetChanged() } - override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): OverviewElementHolder { - val inflater = LayoutInflater.from(parent.context) - return OverviewElementHolder( - ContactDiaryOverviewListItemBinding.inflate( - inflater, - parent, - false - ) - ) - } - override fun getItemCount() = elements.size - override fun onBindViewHolder(holder: OverviewElementHolder, position: Int) { - holder.bind(elements[position], dateFormatter, dateFormatterForAccessibility, onItemSelectionListener) - } - - class OverviewElementHolder(private val viewDataBinding: ContactDiaryOverviewListItemBinding) : - RecyclerView.ViewHolder(viewDataBinding.root) { - private val nestedItemAdapter = ContactDiaryOverviewNestedAdapter() - - init { - viewDataBinding.contactDiaryOverviewNestedRecyclerView.adapter = nestedItemAdapter - } + override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): OverviewElementHolder = OverviewElementHolder(parent) - fun bind( - item: ListItem, - dateFormatter: (LocalDate) -> String, - dateFormatterForAccessibility: (LocalDate) -> String, - onElementSelectionListener: (ListItem) -> Unit - ) { - viewDataBinding.contactDiaryOverviewElementName.text = dateFormatter(item.date) + override fun onBindBaseVH(holder: OverviewElementHolder, position: Int, payloads: MutableList<Any>) = + holder.bind(elements[position], payloads) - viewDataBinding.contactDiaryOverviewElementName.contentDescription = - dateFormatterForAccessibility(item.date) + inner class OverviewElementHolder(parent: ViewGroup) : + BaseAdapter.VH(R.layout.contact_diary_overview_list_item, parent), + BindableVH<ListItem, ContactDiaryOverviewListItemBinding> { - viewDataBinding.contactDiaryOverviewElementBody.setOnClickListener { onElementSelectionListener(item) } + override val viewBinding: Lazy<ContactDiaryOverviewListItemBinding> = + lazy { ContactDiaryOverviewListItemBinding.bind(itemView) } - viewDataBinding.contactDiaryOverviewNestedElementGroup.isGone = item.data.isEmpty() + private val nestedItemAdapter = ContactDiaryOverviewNestedAdapter() - nestedItemAdapter.setItems(item.data) + init { + viewBinding.value.contactDiaryOverviewNestedRecyclerView.adapter = nestedItemAdapter } + + override val onBindData: ContactDiaryOverviewListItemBinding.(item: ListItem, payloads: List<Any>) -> Unit = + { item, _ -> + contactDiaryOverviewElementName.text = dateFormatter(item.date) + contactDiaryOverviewElementName.contentDescription = dateFormatterForAccessibility(item.date) + contactDiaryOverviewElementBody.setOnClickListener { onItemSelectionListener(item) } + contactDiaryOverviewNestedElementGroup.isGone = item.data.isEmpty() + nestedItemAdapter.setItems(item.data) + } } } diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewNestedAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewNestedAdapter.kt index b8cd8b56d3baac8b681e20664790d1467af5a78d..e7835cb12fd5efa22917f93f221e2fca51bbf74b 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewNestedAdapter.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/overview/adapter/ContactDiaryOverviewNestedAdapter.kt @@ -1,37 +1,41 @@ package de.rki.coronawarnapp.contactdiary.ui.overview.adapter -import android.view.LayoutInflater import android.view.ViewGroup -import androidx.recyclerview.widget.RecyclerView +import de.rki.coronawarnapp.R +import de.rki.coronawarnapp.contactdiary.util.clearAndAddAll import de.rki.coronawarnapp.databinding.ContactDiaryOverviewNestedListItemBinding +import de.rki.coronawarnapp.ui.lists.BaseAdapter +import de.rki.coronawarnapp.util.lists.BindableVH class ContactDiaryOverviewNestedAdapter : - RecyclerView.Adapter<ContactDiaryOverviewNestedAdapter.NestedItemViewHolder>() { + BaseAdapter<ContactDiaryOverviewNestedAdapter.NestedItemViewHolder>() { private val dataList: MutableList<ListItem.Data> = mutableListOf() fun setItems(dataList: List<ListItem.Data>) { - this.dataList.clear() - this.dataList += dataList + this.dataList.clearAndAddAll(dataList) notifyDataSetChanged() } - override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): NestedItemViewHolder { - val inflater = LayoutInflater.from(parent.context) - return NestedItemViewHolder(ContactDiaryOverviewNestedListItemBinding.inflate(inflater, parent, false)) - } + override fun onCreateBaseVH(parent: ViewGroup, viewType: Int): NestedItemViewHolder = NestedItemViewHolder(parent) - override fun onBindViewHolder(holder: NestedItemViewHolder, position: Int) { - holder.bind(dataList[position]) - } + override fun onBindBaseVH(holder: NestedItemViewHolder, position: Int, payloads: MutableList<Any>) = + holder.bind(dataList[position], payloads) override fun getItemCount(): Int = dataList.size - class NestedItemViewHolder(private val viewBinding: ContactDiaryOverviewNestedListItemBinding) : - RecyclerView.ViewHolder(viewBinding.root) { - fun bind(data: ListItem.Data) { - viewBinding.contactDiaryOverviewElementImage.setImageResource(data.drawableId) - viewBinding.contactDiaryOverviewElementName.text = data.text - } + class NestedItemViewHolder(parent: ViewGroup) : + BaseAdapter.VH(R.layout.contact_diary_overview_nested_list_item, parent), + BindableVH<ListItem.Data, ContactDiaryOverviewNestedListItemBinding> { + override val viewBinding: + Lazy<ContactDiaryOverviewNestedListItemBinding> = + lazy { ContactDiaryOverviewNestedListItemBinding.bind(itemView) } + + override val onBindData: + ContactDiaryOverviewNestedListItemBinding.(item: ListItem.Data, payloads: List<Any>) -> Unit = + { key, _ -> + contactDiaryOverviewElementImage.setImageResource(key.drawableId) + contactDiaryOverviewElementName.text = key.text + } } } diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/location/ContactDiaryLocationBottomSheetDialogViewModel.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/location/ContactDiaryLocationBottomSheetDialogViewModel.kt index c59fb7368daf83c9949e2f72dd404d168fcc2a7b..7e639168a24a0b7d32d3c84daa383cbb88c43a09 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/location/ContactDiaryLocationBottomSheetDialogViewModel.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/location/ContactDiaryLocationBottomSheetDialogViewModel.kt @@ -97,5 +97,3 @@ class ContactDiaryLocationBottomSheetDialogViewModel @AssistedInject constructor fun create(addedAt: String?): ContactDiaryLocationBottomSheetDialogViewModel } } - -private const val MAX_LOCATION_NAME_LENGTH = 250 diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/person/ContactDiaryPersonBottomSheetDialogViewModel.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/person/ContactDiaryPersonBottomSheetDialogViewModel.kt index 82c42dd13f76a0399a4033560741744324f7a22c..eff32df76a4896a7429461d55ca31470b4b00a53 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/person/ContactDiaryPersonBottomSheetDialogViewModel.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/ui/sheets/person/ContactDiaryPersonBottomSheetDialogViewModel.kt @@ -97,5 +97,3 @@ class ContactDiaryPersonBottomSheetDialogViewModel @AssistedInject constructor( fun create(addedAt: String?): ContactDiaryPersonBottomSheetDialogViewModel } } - -private const val MAX_PERSON_NAME_LENGTH = 250 diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/AbstractAdapter.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/AbstractAdapter.kt new file mode 100644 index 0000000000000000000000000000000000000000..567c2c549d76bb7205144608b3e769e42ece7060 --- /dev/null +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/AbstractAdapter.kt @@ -0,0 +1,15 @@ +package de.rki.coronawarnapp.contactdiary.util + +import de.rki.coronawarnapp.ui.lists.BaseAdapter +import de.rki.coronawarnapp.util.lists.HasStableId +import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffUtilAdapter +import de.rki.coronawarnapp.util.lists.diffutil.AsyncDiffer + +internal abstract class AbstractAdapter<T : HasStableId, U : BaseAdapter.VH> : BaseAdapter<U>(), + AsyncDiffUtilAdapter<T> { + override val asyncDiffer: AsyncDiffer<T> = AsyncDiffer(this) + + override fun getItemCount(): Int = data.size + + override fun getItemId(position: Int): Long = data[position].stableId +} diff --git a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/ContactDiaryExtensions.kt b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/ContactDiaryExtensions.kt index 8149e4cf9d4c76715224d91a76d446f21279682f..6348145c6833c9a85aa064e517e8a154fb2e2f77 100644 --- a/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/ContactDiaryExtensions.kt +++ b/Corona-Warn-App/src/main/java/de/rki/coronawarnapp/contactdiary/util/ContactDiaryExtensions.kt @@ -97,3 +97,8 @@ fun View.setClickLabel(label: String) { } }) } + +fun <T> MutableList<T>.clearAndAddAll(newItems: List<T>) { + clear() + addAll(newItems) +}