From fd134096c8b38c620e59f86758c3c5c28acbaf5a Mon Sep 17 00:00:00 2001 From: Aayush Gupta Date: Thu, 12 Dec 2024 18:53:29 +0700 Subject: [PATCH] view_toolbar_search: Switch to native toolbar for search Signed-off-by: Aayush Gupta --- .../store/view/ui/all/AppsGamesFragment.kt | 98 +++++-------- .../view/ui/commons/BlacklistFragment.kt | 130 +++++++----------- .../view/ui/search/SearchResultsFragment.kt | 87 +++++------- .../ui/search/SearchSuggestionFragment.kt | 48 +++---- app/src/main/res/drawable/ic_menu.xml | 9 -- .../layout/fragment_generic_with_search.xml | 27 +++- .../res/layout/fragment_search_result.xml | 26 +++- .../res/layout/fragment_search_suggestion.xml | 29 +++- .../main/res/layout/view_toolbar_search.xml | 77 ----------- app/src/main/res/menu/menu_search.xml | 15 ++ app/src/main/res/values-night/themes.xml | 1 - app/src/main/res/values/themes.xml | 7 - 12 files changed, 222 insertions(+), 332 deletions(-) delete mode 100644 app/src/main/res/drawable/ic_menu.xml delete mode 100644 app/src/main/res/layout/view_toolbar_search.xml create mode 100644 app/src/main/res/menu/menu_search.xml diff --git a/app/src/main/java/com/aurora/store/view/ui/all/AppsGamesFragment.kt b/app/src/main/java/com/aurora/store/view/ui/all/AppsGamesFragment.kt index db9d20e2e..1c4cb7bcf 100644 --- a/app/src/main/java/com/aurora/store/view/ui/all/AppsGamesFragment.kt +++ b/app/src/main/java/com/aurora/store/view/ui/all/AppsGamesFragment.kt @@ -23,13 +23,8 @@ import android.net.Uri import android.os.Bundle import android.text.Editable import android.text.TextWatcher -import android.view.ContextThemeWrapper -import android.view.MenuInflater -import android.view.MenuItem import android.view.View -import android.widget.PopupMenu import androidx.activity.result.contract.ActivityResultContracts -import androidx.appcompat.content.res.AppCompatResources import androidx.fragment.app.viewModels import androidx.lifecycle.lifecycleScope import androidx.navigation.fragment.findNavController @@ -83,71 +78,44 @@ class AppsGamesFragment : BaseFragment() { } // Toolbar - binding.layoutToolbarNative.apply { - imgActionPrimary.visibility = View.VISIBLE - imgActionSecondary.visibility = View.VISIBLE - - imgActionPrimary.setOnClickListener { findNavController().navigateUp() } - imgActionSecondary.apply { - setImageDrawable( - AppCompatResources.getDrawable(requireContext(), R.drawable.ic_menu) - ) - setOnClickListener { - showMenu(it) - } - } - - inputSearch.addTextChangedListener(object : TextWatcher { - override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) { - if (s.isNullOrEmpty()) { - updateController(viewModel.apps.value) - } else { - val filteredPackages = viewModel.apps.value?.filter { - it.displayName.contains(s, true) || it.packageName.contains(s, true) - } - updateController(filteredPackages) + binding.toolbar.apply { + inflateMenu(R.menu.menu_import_export) + setNavigationOnClickListener { findNavController().navigateUp() } + setOnMenuItemClickListener { + when (it.itemId) { + R.id.action_export -> { + startForDocumentExport.launch( + "aurora_store_apps_${Calendar.getInstance().time.time}.json" + ) + true } + + else -> false } - - override fun afterTextChanged(s: Editable?) {} - override fun beforeTextChanged( - s: CharSequence?, - start: Int, - count: Int, - after: Int - ) { - } - }) - } - } - - private fun showMenu(anchor: View) { - val popupMenu = PopupMenu( - ContextThemeWrapper( - requireContext(), - R.style.AppTheme_PopupMenu - ), anchor - ) - - val inflater: MenuInflater = popupMenu.menuInflater - inflater.inflate(R.menu.menu_import_export, popupMenu.menu) - - popupMenu.menu.removeItem(R.id.action_import) - - popupMenu.setOnMenuItemClickListener { menuItem: MenuItem -> - when (menuItem.itemId) { - R.id.action_export -> { - startForDocumentExport.launch( - "aurora_store_apps_${Calendar.getInstance().time.time}.json" - ) - true - } - - else -> false } } - popupMenu.show() + binding.searchBar.addTextChangedListener(object : TextWatcher { + override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) { + if (s.isNullOrEmpty()) { + updateController(viewModel.apps.value) + } else { + val filteredPackages = viewModel.apps.value?.filter { + it.displayName.contains(s, true) || it.packageName.contains(s, true) + } + updateController(filteredPackages) + } + } + + override fun afterTextChanged(s: Editable?) {} + override fun beforeTextChanged( + s: CharSequence?, + start: Int, + count: Int, + after: Int + ) { + } + }) } private fun updateController(packages: List?) { diff --git a/app/src/main/java/com/aurora/store/view/ui/commons/BlacklistFragment.kt b/app/src/main/java/com/aurora/store/view/ui/commons/BlacklistFragment.kt index df0758433..35a251b74 100644 --- a/app/src/main/java/com/aurora/store/view/ui/commons/BlacklistFragment.kt +++ b/app/src/main/java/com/aurora/store/view/ui/commons/BlacklistFragment.kt @@ -24,13 +24,8 @@ import android.net.Uri import android.os.Bundle import android.text.Editable import android.text.TextWatcher -import android.view.ContextThemeWrapper -import android.view.MenuInflater -import android.view.MenuItem import android.view.View -import android.widget.PopupMenu import androidx.activity.result.contract.ActivityResultContracts -import androidx.appcompat.content.res.AppCompatResources import androidx.fragment.app.viewModels import androidx.lifecycle.lifecycleScope import androidx.navigation.fragment.findNavController @@ -71,46 +66,62 @@ class BlacklistFragment : BaseFragment() { } // Toolbar - binding.layoutToolbarNative.apply { - imgActionPrimary.visibility = View.VISIBLE - imgActionSecondary.apply { - visibility = View.VISIBLE - setImageDrawable( - AppCompatResources.getDrawable(requireContext(), R.drawable.ic_menu) - ) - setOnClickListener { - showMenu(it) - } - } - - imgActionPrimary.setOnClickListener { + binding.toolbar.apply { + inflateMenu(R.menu.menu_blacklist) + setNavigationOnClickListener { viewModel.blacklistProvider.blacklist = viewModel.selected findNavController().navigateUp() } + setOnMenuItemClickListener { + when (it.itemId) { + R.id.action_import -> { + startForDocumentImport.launch(arrayOf(Constants.JSON_MIME_TYPE)) + } - inputSearch.addTextChangedListener(object : TextWatcher { - override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) { - if (s.isNullOrEmpty()) { - updateController(viewModel.packages.value) - } else { - val filteredPackages = viewModel.packages.value?.filter { - it.applicationInfo!!.loadLabel(requireContext().packageManager) - .contains(s, true) || it.packageName.contains(s, true) - } - updateController(filteredPackages) + R.id.action_export -> { + startForDocumentExport.launch( + "aurora_store_apps_${Calendar.getInstance().time.time}.json" + ) + } + + R.id.action_select_all -> { + viewModel.selectAll() + binding.recycler.requestModelBuild() + true + } + + R.id.action_remove_all -> { + viewModel.removeAll() + binding.recycler.requestModelBuild() + true } } - - override fun afterTextChanged(s: Editable?) {} - override fun beforeTextChanged( - s: CharSequence?, - start: Int, - count: Int, - after: Int - ) { - } - }) + true + } } + + binding.searchBar.addTextChangedListener(object : TextWatcher { + override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) { + if (s.isNullOrEmpty()) { + updateController(viewModel.packages.value) + } else { + val filteredPackages = viewModel.packages.value?.filter { + it.applicationInfo!!.loadLabel(requireContext().packageManager) + .contains(s, true) || it.packageName.contains(s, true) + } + updateController(filteredPackages) + } + } + + override fun afterTextChanged(s: Editable?) {} + override fun beforeTextChanged( + s: CharSequence?, + start: Int, + count: Int, + after: Int + ) { + } + }) } override fun onPause() { @@ -118,49 +129,6 @@ class BlacklistFragment : BaseFragment() { viewModel.blacklistProvider.blacklist = viewModel.selected } - private fun showMenu(anchor: View) { - val popupMenu = PopupMenu( - ContextThemeWrapper( - requireContext(), - R.style.AppTheme_PopupMenu - ), anchor - ) - - val inflater: MenuInflater = popupMenu.menuInflater - inflater.inflate(R.menu.menu_blacklist, popupMenu.menu) - - popupMenu.setOnMenuItemClickListener { menuItem: MenuItem -> - when (menuItem.itemId) { - R.id.action_import -> { - startForDocumentImport.launch(arrayOf(Constants.JSON_MIME_TYPE)) - true - } - - R.id.action_export -> { - startForDocumentExport.launch( - "aurora_store_blacklist_${Calendar.getInstance().time.time}.json" - ) - true - } - - R.id.action_select_all -> { - viewModel.selectAll() - binding.recycler.requestModelBuild() - true - } - - R.id.action_remove_all -> { - viewModel.removeAll() - binding.recycler.requestModelBuild() - true - } - - else -> false - } - } - popupMenu.show() - } - private fun updateController(packages: List?) { binding.recycler.withModels { setFilterDuplicates(true) diff --git a/app/src/main/java/com/aurora/store/view/ui/search/SearchResultsFragment.kt b/app/src/main/java/com/aurora/store/view/ui/search/SearchResultsFragment.kt index f14385df2..599541918 100644 --- a/app/src/main/java/com/aurora/store/view/ui/search/SearchResultsFragment.kt +++ b/app/src/main/java/com/aurora/store/view/ui/search/SearchResultsFragment.kt @@ -50,7 +50,6 @@ import com.aurora.store.view.epoxy.views.app.NoAppViewModel_ import com.aurora.store.view.epoxy.views.shimmer.AppListViewShimmerModel_ import com.aurora.store.view.ui.commons.BaseFragment import com.aurora.store.viewmodel.search.SearchResultViewModel -import com.google.android.material.textfield.TextInputEditText import dagger.hilt.android.AndroidEntryPoint @AndroidEntryPoint @@ -59,8 +58,6 @@ class SearchResultsFragment : BaseFragment(), private val viewModel: SearchResultViewModel by viewModels() - private lateinit var searchView: TextInputEditText - private lateinit var sharedPreferences: SharedPreferences private var query: String? = null @@ -84,20 +81,20 @@ class SearchResultsFragment : BaseFragment(), sharedPreferences.registerOnSharedPreferenceChangeListener(this) // Toolbar - binding.layoutViewToolbar.apply { - searchView = inputSearch - imgActionPrimary.setOnClickListener { + binding.toolbar.apply { + setNavigationOnClickListener { + binding.searchBar.hideKeyboard() findNavController().navigateUp() } - imgActionSecondary.setOnClickListener { - findNavController().navigate(R.id.downloadFragment) - } - clearButton.apply { - visibility = if (query.isNullOrBlank()) View.GONE else View.VISIBLE - setOnClickListener { - searchView.text?.clear() - searchView.showKeyboard() + setOnMenuItemClickListener { + when (it.itemId) { + R.id.action_clear -> { + binding.searchBar.text?.clear() + binding.searchBar.showKeyboard() + } + R.id.action_download -> findNavController().navigate(R.id.downloadFragment) } + true } } @@ -186,30 +183,29 @@ class SearchResultsFragment : BaseFragment(), } } } else { - binding.recycler - .withModels { - setFilterDuplicates(true) + binding.recycler.withModels { + setFilterDuplicates(true) - filteredAppList.forEach { app -> - add( - AppListViewModel_() - .id(app.id) - .app(app) - .click(View.OnClickListener { - searchView.hideKeyboard() - openDetailsFragment(app.packageName, app) - }) - ) - } - - if (searchBundle.subBundles.isNotEmpty()) { - add( - AppProgressViewModel_() - .id("progress") - ) - } + filteredAppList.forEach { app -> + add( + AppListViewModel_() + .id(app.id) + .app(app) + .click(View.OnClickListener { + binding.searchBar.hideKeyboard() + openDetailsFragment(app.packageName, app) + }) + ) } + if (searchBundle.subBundles.isNotEmpty()) { + add( + AppProgressViewModel_() + .id("progress") + ) + } + } + binding.recycler.adapter?.let { if (it.itemCount < 10) { viewModel.next(searchBundle.subBundles) @@ -219,28 +215,22 @@ class SearchResultsFragment : BaseFragment(), } private fun attachSearch() { - searchView.addTextChangedListener(object : TextWatcher { - override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) { - - } + binding.searchBar.addTextChangedListener(object : TextWatcher { + override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {} override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) { - if (s.isNotEmpty()) { - binding.layoutViewToolbar.clearButton.visibility = View.VISIBLE - } else { - binding.layoutViewToolbar.clearButton.visibility = View.GONE - } + binding.toolbar.menu.findItem(R.id.action_clear)?.isVisible = s.isNotBlank() } override fun afterTextChanged(s: Editable) {} }) - searchView.setOnEditorActionListener { _: TextView?, actionId: Int, _: KeyEvent? -> + binding.searchBar.setOnEditorActionListener { _: TextView?, actionId: Int, _: KeyEvent? -> if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == KeyEvent.ACTION_DOWN || actionId == KeyEvent.KEYCODE_ENTER ) { - query = searchView.text.toString() + query = binding.searchBar.text.toString() query?.let { requireArguments().putString("query", it) queryViewModel(it) @@ -252,8 +242,8 @@ class SearchResultsFragment : BaseFragment(), } private fun updateQuery(query: String) { - searchView.text = Editable.Factory.getInstance().newEditable(query) - searchView.setSelection(query.length) + binding.searchBar.text = Editable.Factory.getInstance().newEditable(query) + binding.searchBar.setSelection(query.length) queryViewModel(query) } @@ -277,7 +267,6 @@ class SearchResultsFragment : BaseFragment(), .toList() } - override fun onSharedPreferenceChanged(sharedPreferences: SharedPreferences?, key: String?) { if (key == PREFERENCE_FILTER) query?.let { queryViewModel(it) } } diff --git a/app/src/main/java/com/aurora/store/view/ui/search/SearchSuggestionFragment.kt b/app/src/main/java/com/aurora/store/view/ui/search/SearchSuggestionFragment.kt index 1cc4fb5b1..ebebe7013 100644 --- a/app/src/main/java/com/aurora/store/view/ui/search/SearchSuggestionFragment.kt +++ b/app/src/main/java/com/aurora/store/view/ui/search/SearchSuggestionFragment.kt @@ -37,7 +37,6 @@ import com.aurora.store.databinding.FragmentSearchSuggestionBinding import com.aurora.store.view.epoxy.views.SearchSuggestionViewModel_ import com.aurora.store.view.ui.commons.BaseFragment import com.aurora.store.viewmodel.search.SearchSuggestionViewModel -import com.google.android.material.textfield.TextInputEditText import dagger.hilt.android.AndroidEntryPoint import kotlinx.coroutines.flow.collectLatest import kotlinx.coroutines.launch @@ -47,26 +46,21 @@ class SearchSuggestionFragment : BaseFragment() private val viewModel: SearchSuggestionViewModel by viewModels() - private lateinit var searchView: TextInputEditText - - private var query: String = String() - override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) // Toolbar - binding.layoutToolbarSearch.apply { - searchView = inputSearch - imgActionPrimary.setOnClickListener { - searchView.hideKeyboard() + binding.toolbar.apply { + setNavigationOnClickListener { + binding.searchBar.hideKeyboard() findNavController().navigateUp() } - imgActionSecondary.setOnClickListener { - findNavController().navigate(R.id.downloadFragment) - } - clearButton.apply { - visibility = if (query.isBlank()) View.GONE else View.VISIBLE - setOnClickListener { searchView.text?.clear() } + setOnMenuItemClickListener { + when (it.itemId) { + R.id.action_clear -> binding.searchBar.text?.clear() + R.id.action_download -> findNavController().navigate(R.id.downloadFragment) + } + true } } @@ -81,9 +75,7 @@ class SearchSuggestionFragment : BaseFragment() override fun onResume() { super.onResume() - if (::searchView.isInitialized) { - searchView.showKeyboard() - } + binding.searchBar.showKeyboard() } private fun updateController(searchSuggestions: List) { @@ -98,7 +90,7 @@ class SearchSuggestionFragment : BaseFragment() updateQuery(it.title) } .click { _ -> - searchView.hideKeyboard() + binding.searchBar.hideKeyboard() search(it.title) } ) @@ -107,32 +99,30 @@ class SearchSuggestionFragment : BaseFragment() } private fun setupSearch() { - searchView.addTextChangedListener(object : TextWatcher { + binding.searchBar.addTextChangedListener(object : TextWatcher { override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {} override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) { if (s.isNotEmpty()) { - query = s.toString() + val query = s.toString() if (query.isNotEmpty()) { viewModel.observeStreamBundles(query) } - binding.layoutToolbarSearch.clearButton.visibility = View.VISIBLE - } else { - binding.layoutToolbarSearch.clearButton.visibility = View.GONE } + binding.toolbar.menu.findItem(R.id.action_clear)?.isVisible = s.isNotBlank() } override fun afterTextChanged(s: Editable) {} }) - searchView.setOnEditorActionListener { _: TextView?, actionId: Int, _: KeyEvent? -> + binding.searchBar.setOnEditorActionListener { _: TextView?, actionId: Int, _: KeyEvent? -> if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == KeyEvent.ACTION_DOWN || actionId == KeyEvent.KEYCODE_ENTER ) { - query = searchView.text.toString() + val query = binding.searchBar.text.toString() if (query.isNotEmpty()) { - searchView.hideKeyboard() + binding.searchBar.hideKeyboard() search(query) return@setOnEditorActionListener true } @@ -142,8 +132,8 @@ class SearchSuggestionFragment : BaseFragment() } private fun updateQuery(query: String) { - searchView.text = Editable.Factory.getInstance().newEditable(query) - searchView.setSelection(query.length) + binding.searchBar.text = Editable.Factory.getInstance().newEditable(query) + binding.searchBar.setSelection(query.length) } private fun search(query: String) { diff --git a/app/src/main/res/drawable/ic_menu.xml b/app/src/main/res/drawable/ic_menu.xml deleted file mode 100644 index 966e8e94b..000000000 --- a/app/src/main/res/drawable/ic_menu.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - diff --git a/app/src/main/res/layout/fragment_generic_with_search.xml b/app/src/main/res/layout/fragment_generic_with_search.xml index fdba04491..9289fbf15 100644 --- a/app/src/main/res/layout/fragment_generic_with_search.xml +++ b/app/src/main/res/layout/fragment_generic_with_search.xml @@ -24,18 +24,35 @@ android:layout_height="match_parent" android:orientation="vertical"> - + + + + - \ No newline at end of file + diff --git a/app/src/main/res/layout/fragment_search_result.xml b/app/src/main/res/layout/fragment_search_result.xml index 80cf9a3f1..6f96a2055 100644 --- a/app/src/main/res/layout/fragment_search_result.xml +++ b/app/src/main/res/layout/fragment_search_result.xml @@ -30,15 +30,33 @@ android:layout_height="match_parent" android:orientation="vertical"> - + + + + + android:layout_below="@id/toolbar" /> - + + + + + android:layout_below="@id/toolbar" /> - \ No newline at end of file + diff --git a/app/src/main/res/layout/view_toolbar_search.xml b/app/src/main/res/layout/view_toolbar_search.xml deleted file mode 100644 index 86d75ec3e..000000000 --- a/app/src/main/res/layout/view_toolbar_search.xml +++ /dev/null @@ -1,77 +0,0 @@ - - - - - - - - - - - - diff --git a/app/src/main/res/menu/menu_search.xml b/app/src/main/res/menu/menu_search.xml new file mode 100644 index 000000000..fd45127de --- /dev/null +++ b/app/src/main/res/menu/menu_search.xml @@ -0,0 +1,15 @@ + + + + + diff --git a/app/src/main/res/values-night/themes.xml b/app/src/main/res/values-night/themes.xml index b8ecd72e1..c70d8103a 100644 --- a/app/src/main/res/values-night/themes.xml +++ b/app/src/main/res/values-night/themes.xml @@ -5,6 +5,5 @@ @style/Chip.Filter @style/AppTheme.PreferenceThemeOverlay @color/colorTransparent - @style/AppTheme.PopupMenu diff --git a/app/src/main/res/values/themes.xml b/app/src/main/res/values/themes.xml index e4795a322..cb5ebd377 100644 --- a/app/src/main/res/values/themes.xml +++ b/app/src/main/res/values/themes.xml @@ -24,7 +24,6 @@ @style/AppTheme.PreferenceThemeOverlay @style/AppTheme.BottomSheetStyle @color/colorTransparent - @style/AppTheme.PopupMenu - -