Skip to content

Commit

Permalink
[feat]: search apps in ChooseAppFragment
Browse files Browse the repository at this point in the history
  • Loading branch information
F0x1d committed Oct 29, 2023
1 parent 6a22c70 commit 2534a1c
Show file tree
Hide file tree
Showing 17 changed files with 114 additions and 28 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ class LogsFragment: BaseViewModelFragment<LogsViewModel, FragmentLogsBinding>(),
}
private var changingState = false

private val clearSelectionBackPressedCallback = object : OnBackPressedCallback(false) {
private val clearSelectionOnBackPressedCallback = object : OnBackPressedCallback(false) {
override fun handleOnBackPressed() {
viewModel.selectedItems.update {
emptyList()
Expand Down Expand Up @@ -70,7 +70,6 @@ class LogsFragment: BaseViewModelFragment<LogsViewModel, FragmentLogsBinding>(),
}
}

binding.toolbar.inflateMenu(R.menu.logs_menu)
binding.toolbar.menu.apply {
setClickListenerOn(R.id.pause_item) {
viewModel.switchState()
Expand Down Expand Up @@ -136,7 +135,7 @@ class LogsFragment: BaseViewModelFragment<LogsViewModel, FragmentLogsBinding>(),
viewModel.selectedItems.asLiveData().observe(viewLifecycleOwner) {
val selecting = it.isNotEmpty()

clearSelectionBackPressedCallback.isEnabled = selecting
clearSelectionOnBackPressedCallback.isEnabled = selecting

adapter.selectedItems = it
setupToolbarForSelection(selecting, it.size)
Expand Down Expand Up @@ -171,7 +170,7 @@ class LogsFragment: BaseViewModelFragment<LogsViewModel, FragmentLogsBinding>(),
}

requireActivity().onBackPressedDispatcher.apply {
addCallback(viewLifecycleOwner, clearSelectionBackPressedCallback)
addCallback(viewLifecycleOwner, clearSelectionOnBackPressedCallback)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,6 @@ class RecordingsFragment: BaseViewModelFragment<RecordingsViewModel, FragmentRec
}
}

binding.toolbar.inflateMenu(R.menu.recordings_menu)
binding.toolbar.menu.setClickListenerOn(R.id.clear_item) {
showAreYouSureClearDialog {
viewModel.clearRecordings()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,6 @@ class CrashDetailsFragment: BaseViewModelFragment<CrashDetailsViewModel, Activit
}
}

binding.toolbar.inflateMenu(R.menu.crash_details_menu)
binding.toolbar.setupBackButtonForNavController()

binding.copyLayout.replaceAccessibilityDelegateClassNameWithButton()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ class CrashesFragment: BaseViewModelFragment<CrashesViewModel, FragmentCrashesBi
}
}

binding.toolbar.inflateMenu(R.menu.crashes_menu)
binding.toolbar.menu.setClickListenerOn(R.id.clear_item) {
showAreYouSureClearDialog {
viewModel.clearCrashes()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.activity.OnBackPressedCallback
import androidx.core.widget.doAfterTextChanged
import androidx.fragment.app.viewModels
import androidx.hilt.navigation.fragment.hiltNavGraphViewModels
import androidx.lifecycle.asLiveData
Expand All @@ -13,13 +15,17 @@ import com.f0x1d.logfox.R
import com.f0x1d.logfox.adapter.AppsAdapter
import com.f0x1d.logfox.databinding.FragmentChooseAppBinding
import com.f0x1d.logfox.extensions.dpToPx
import com.f0x1d.logfox.extensions.views.widgets.setClickListenerOn
import com.f0x1d.logfox.extensions.views.widgets.setupBackButtonForNavController
import com.f0x1d.logfox.model.InstalledApp
import com.f0x1d.logfox.ui.fragment.base.BaseViewModelFragment
import com.f0x1d.logfox.viewmodel.filters.ChooseAppViewModel
import com.f0x1d.logfox.viewmodel.filters.EditFilterViewModel
import com.google.android.material.divider.MaterialDividerItemDecoration
import com.google.android.material.search.SearchView
import dagger.hilt.android.AndroidEntryPoint
import dev.chrisbanes.insetter.applyInsetter
import kotlinx.coroutines.flow.update

@AndroidEntryPoint
class ChooseAppFragment: BaseViewModelFragment<ChooseAppViewModel, FragmentChooseAppBinding>() {
Expand All @@ -28,10 +34,18 @@ class ChooseAppFragment: BaseViewModelFragment<ChooseAppViewModel, FragmentChoos

private val editFilterViewModel by hiltNavGraphViewModels<EditFilterViewModel>(R.id.editFilterFragment)

private val adapter = AppsAdapter {
private val onAppClicked: (InstalledApp) -> Unit = {
editFilterViewModel.selectApp(it)
findNavController().popBackStack()
}
private val appsAdapter = AppsAdapter(onAppClicked)
private val searchedAppsAdapter = AppsAdapter(onAppClicked)

private val closeSearchOnBackPressedCallback = object : OnBackPressedCallback(false) {
override fun handleOnBackPressed() {
binding.searchView.hide()
}
}

override fun inflateBinding(
inflater: LayoutInflater,
Expand All @@ -47,18 +61,47 @@ class ChooseAppFragment: BaseViewModelFragment<ChooseAppViewModel, FragmentChoos
}
}

binding.toolbar.setupBackButtonForNavController()
binding.searchBar.apply {
setupBackButtonForNavController()
menu.setClickListenerOn(R.id.search_item) {
binding.searchView.show()
}
}
binding.searchView.editText.doAfterTextChanged { editable ->
viewModel.query.update {
editable.toString()
}
}
binding.searchView.addTransitionListener { searchView, previousState, newState ->
closeSearchOnBackPressedCallback.isEnabled = newState == SearchView.TransitionState.SHOWN
}

listOf(
binding.appsRecycler,
binding.searchedAppsRecycler
).forEach {
it.apply {
layoutManager = LinearLayoutManager(requireContext())
addItemDecoration(MaterialDividerItemDecoration(requireContext(), LinearLayoutManager.VERTICAL).apply {
dividerInsetStart = 80.dpToPx.toInt()
dividerInsetEnd = 10.dpToPx.toInt()
isLastItemDecorated = false
})
}
}

binding.appsRecycler.layoutManager = LinearLayoutManager(requireContext())
binding.appsRecycler.addItemDecoration(MaterialDividerItemDecoration(requireContext(), LinearLayoutManager.VERTICAL).apply {
dividerInsetStart = 80.dpToPx.toInt()
dividerInsetEnd = 10.dpToPx.toInt()
isLastItemDecorated = false
})
binding.appsRecycler.adapter = adapter
binding.appsRecycler.adapter = appsAdapter
binding.searchedAppsRecycler.adapter = searchedAppsAdapter

viewModel.apps.asLiveData().observe(viewLifecycleOwner) {
adapter.submitList(it)
appsAdapter.submitList(it)
}
viewModel.searchedApps.observe(viewLifecycleOwner) {
searchedAppsAdapter.submitList(it)
}

requireActivity().onBackPressedDispatcher.apply {
addCallback(viewLifecycleOwner, closeSearchOnBackPressedCallback)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -95,9 +95,11 @@ class EditFilterFragment: BaseViewModelFragment<EditFilterViewModel, FragmentEdi

if (it == null) return@observe

binding.toolbar.inflateMenu(R.menu.edit_filter_menu)
binding.toolbar.menu.setClickListenerOn(R.id.export_item) {
exportFilterLauncher.launch("filter.json")
binding.toolbar.menu.apply {
findItem(R.id.export_item).isVisible = true
setClickListenerOn(R.id.export_item) {
exportFilterLauncher.launch("filter.json")
}
}

binding.saveFab.setOnClickListener { view ->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,6 @@ class FiltersFragment: BaseViewModelFragment<FiltersViewModel, FragmentFiltersBi
}

binding.toolbar.setupBackButtonForNavController()
binding.toolbar.inflateMenu(R.menu.filters_menu)
binding.toolbar.menu.apply {
setClickListenerOn(R.id.clear_item) {
showAreYouSureClearDialog {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,19 +1,36 @@
package com.f0x1d.logfox.viewmodel.filters

import android.app.Application
import androidx.lifecycle.asLiveData
import com.f0x1d.logfox.model.InstalledApp
import com.f0x1d.logfox.viewmodel.base.BaseViewModel
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.combine
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.flowOn
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.update
import javax.inject.Inject

@HiltViewModel
class ChooseAppViewModel @Inject constructor(
application: Application
): BaseViewModel(application) {

val apps = MutableStateFlow(emptyList<InstalledApp>())
val query = MutableStateFlow("")

val searchedApps = combine(apps, query) { apps, query ->
apps to query
}.map {
it.first.filter { app ->
app.title.toString().contains(it.second) || app.packageName.contains(it.second)
}
}.flowOn(
Dispatchers.IO
).distinctUntilChanged().asLiveData()

init {
load()
Expand Down
1 change: 1 addition & 0 deletions app/src/main/res/layout/activity_crash_details.xml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
app:titleCentered="true"
app:menu="@menu/crash_details_menu"
app:navigationIcon="@drawable/ic_arrow_back"
app:navigationIconTint="?colorOnSurface" />
</com.google.android.material.appbar.AppBarLayout>
Expand Down
26 changes: 20 additions & 6 deletions app/src/main/res/layout/fragment_choose_app.xml
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,30 @@
android:fitsSystemWindows="true"
app:liftOnScroll="true">

<com.google.android.material.appbar.MaterialToolbar
android:id="@+id/toolbar"
<com.google.android.material.search.SearchBar
android:id="@+id/search_bar"
android:layout_width="match_parent"
android:layout_height="?actionBarSize"
app:title="@string/apps"
app:titleCentered="true"
android:layout_height="wrap_content"
app:menu="@menu/choose_app_menu"
app:navigationIcon="@drawable/ic_arrow_back"
app:navigationIconTint="?colorOnSurface"/>
app:navigationIconTint="?colorOnSurface"
android:hint="@string/apps" />
</com.google.android.material.appbar.AppBarLayout>

<com.google.android.material.search.SearchView
android:id="@+id/search_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:hint="@string/apps"
app:layout_anchor="@id/search_bar">

<androidx.recyclerview.widget.RecyclerView
android:id="@+id/searched_apps_recycler"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:clipToPadding="false" />
</com.google.android.material.search.SearchView>

<androidx.recyclerview.widget.RecyclerView
android:id="@+id/apps_recycler"
android:layout_width="match_parent"
Expand Down
1 change: 1 addition & 0 deletions app/src/main/res/layout/fragment_crashes.xml
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?actionBarSize"
app:menu="@menu/crashes_menu"
app:title="@string/crashes"
app:titleCentered="true" />
</com.google.android.material.appbar.AppBarLayout>
Expand Down
1 change: 1 addition & 0 deletions app/src/main/res/layout/fragment_edit_filter.xml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
android:layout_height="?actionBarSize"
app:title="@string/filter"
app:titleCentered="true"
app:menu="@menu/edit_filter_menu"
app:navigationIcon="@drawable/ic_arrow_back"
app:navigationIconTint="?colorOnSurface" />
</com.google.android.material.appbar.AppBarLayout>
Expand Down
1 change: 1 addition & 0 deletions app/src/main/res/layout/fragment_filters.xml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
android:layout_height="?actionBarSize"
app:title="@string/filters"
app:titleCentered="true"
app:menu="@menu/filters_menu"
app:navigationIcon="@drawable/ic_arrow_back"
app:navigationIconTint="?colorOnSurface" />
</com.google.android.material.appbar.AppBarLayout>
Expand Down
1 change: 1 addition & 0 deletions app/src/main/res/layout/fragment_logs.xml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
android:layout_height="?actionBarSize"
app:title="@string/app_name"
app:titleCentered="true"
app:menu="@menu/logs_menu"
app:navigationIconTint="?colorOnSurface"/>
</com.google.android.material.appbar.AppBarLayout>

Expand Down
3 changes: 2 additions & 1 deletion app/src/main/res/layout/fragment_recordings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,8 @@
android:layout_width="match_parent"
android:layout_height="?actionBarSize"
app:title="@string/recordings"
app:titleCentered="true" />
app:titleCentered="true"
app:menu="@menu/recordings_menu" />
</com.google.android.material.appbar.AppBarLayout>

<androidx.recyclerview.widget.RecyclerView
Expand Down
8 changes: 8 additions & 0 deletions app/src/main/res/menu/choose_app_menu.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item android:id="@+id/search_item"
android:title="@string/search"
android:icon="@drawable/ic_search"
app:showAsAction="always" />
</menu>
1 change: 1 addition & 0 deletions app/src/main/res/menu/edit_filter_menu.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
android:id="@+id/export_item"
android:title="@string/export"
android:icon="@drawable/ic_export"
android:visible="false"
app:showAsAction="always" />

</menu>

0 comments on commit 2534a1c

Please sign in to comment.