Migrate SearchResultsActivity to fragment

Signed-off-by: Aayush Gupta <aayushgupta219@gmail.com>
This commit is contained in:
Aayush Gupta
2023-06-22 23:13:47 +05:30
parent 43004cdf07
commit 0d7419f398
7 changed files with 95 additions and 95 deletions

View File

@@ -144,7 +144,6 @@
</intent-filter> </intent-filter>
</activity> </activity>
<activity android:name=".view.ui.search.SearchResultsActivity" />
<activity android:name=".view.ui.commons.StreamBrowseActivity" /> <activity android:name=".view.ui.commons.StreamBrowseActivity" />
<activity android:name=".view.ui.details.ScreenshotActivity" /> <activity android:name=".view.ui.details.ScreenshotActivity" />
<activity android:name=".view.ui.commons.CategoryBrowseActivity" /> <activity android:name=".view.ui.commons.CategoryBrowseActivity" />

View File

@@ -29,7 +29,6 @@ import com.aurora.store.data.model.Report
import com.aurora.store.view.ui.details.AppDetailsActivity import com.aurora.store.view.ui.details.AppDetailsActivity
import com.aurora.store.view.ui.details.DetailsExodusActivity import com.aurora.store.view.ui.details.DetailsExodusActivity
import com.aurora.store.view.ui.details.DevAppsActivity import com.aurora.store.view.ui.details.DevAppsActivity
import com.aurora.store.view.ui.search.SearchResultsActivity
import com.google.gson.Gson import com.google.gson.Gson
import com.google.gson.GsonBuilder import com.google.gson.GsonBuilder
import java.lang.reflect.Modifier import java.lang.reflect.Modifier
@@ -70,13 +69,4 @@ object NavigationUtil {
val options = ActivityOptions.makeSceneTransitionAnimation(context as AppCompatActivity) val options = ActivityOptions.makeSceneTransitionAnimation(context as AppCompatActivity)
context.startActivity(intent, options.toBundle()) context.startActivity(intent, options.toBundle())
} }
fun openSearchActivity(context: Context) {
val intent = Intent(
context,
SearchResultsActivity::class.java
)
val options = ActivityOptions.makeSceneTransitionAnimation(context as AppCompatActivity)
context.startActivity(intent, options.toBundle())
}
} }

View File

@@ -33,6 +33,8 @@ import androidx.lifecycle.Lifecycle
import androidx.lifecycle.ViewModelProvider import androidx.lifecycle.ViewModelProvider
import androidx.lifecycle.lifecycleScope import androidx.lifecycle.lifecycleScope
import androidx.lifecycle.repeatOnLifecycle import androidx.lifecycle.repeatOnLifecycle
import androidx.navigation.fragment.findNavController
import androidx.navigation.fragment.navArgs
import com.aurora.Constants import com.aurora.Constants
import com.aurora.extensions.open import com.aurora.extensions.open
import com.aurora.gplayapi.data.models.App import com.aurora.gplayapi.data.models.App
@@ -40,14 +42,14 @@ import com.aurora.gplayapi.data.models.SearchBundle
import com.aurora.store.R import com.aurora.store.R
import com.aurora.store.data.Filter import com.aurora.store.data.Filter
import com.aurora.store.data.providers.FilterProvider import com.aurora.store.data.providers.FilterProvider
import com.aurora.store.databinding.ActivitySearchResultBinding import com.aurora.store.databinding.FragmentSearchResultBinding
import com.aurora.store.util.Preferences import com.aurora.store.util.Preferences
import com.aurora.store.view.custom.recycler.EndlessRecyclerOnScrollListener import com.aurora.store.view.custom.recycler.EndlessRecyclerOnScrollListener
import com.aurora.store.view.epoxy.views.AppProgressViewModel_ import com.aurora.store.view.epoxy.views.AppProgressViewModel_
import com.aurora.store.view.epoxy.views.app.AppListViewModel_ import com.aurora.store.view.epoxy.views.app.AppListViewModel_
import com.aurora.store.view.epoxy.views.app.NoAppViewModel_ import com.aurora.store.view.epoxy.views.app.NoAppViewModel_
import com.aurora.store.view.epoxy.views.shimmer.AppListViewShimmerModel_ import com.aurora.store.view.epoxy.views.shimmer.AppListViewShimmerModel_
import com.aurora.store.view.ui.commons.BaseActivity import com.aurora.store.view.ui.commons.BaseFragment
import com.aurora.store.view.ui.downloads.DownloadActivity import com.aurora.store.view.ui.downloads.DownloadActivity
import com.aurora.store.view.ui.sheets.FilterSheet import com.aurora.store.view.ui.sheets.FilterSheet
import com.aurora.store.viewmodel.search.SearchResultViewModel import com.aurora.store.viewmodel.search.SearchResultViewModel
@@ -56,9 +58,15 @@ import com.google.android.material.textfield.TextInputEditText
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener { class SearchResultsFragment : BaseFragment(R.layout.fragment_search_result),
OnSharedPreferenceChangeListener {
private var _binding: FragmentSearchResultBinding? = null
private val binding: FragmentSearchResultBinding
get() = _binding!!
private val args: SearchResultsFragmentArgs by navArgs()
lateinit var B: ActivitySearchResultBinding
lateinit var VM: SearchResultViewModel lateinit var VM: SearchResultViewModel
lateinit var endlessRecyclerOnScrollListener: EndlessRecyclerOnScrollListener lateinit var endlessRecyclerOnScrollListener: EndlessRecyclerOnScrollListener
@@ -69,51 +77,59 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
var query: String? = null var query: String? = null
var searchBundle: SearchBundle = SearchBundle() var searchBundle: SearchBundle = SearchBundle()
private var shimmerAnimationVisible = false private var shimmerAnimationVisible = false
private var snackbar: Snackbar? = null private var snackbar: Snackbar? = null
override fun onConnected() { override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
hideNetworkConnectivitySheet() super.onViewCreated(view, savedInstanceState)
}
override fun onDisconnected() { _binding = FragmentSearchResultBinding.bind(view)
showNetworkConnectivitySheet()
}
override fun onReconnected() {
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
B = ActivitySearchResultBinding.inflate(layoutInflater)
VM = ViewModelProvider(this)[SearchResultViewModel::class.java] VM = ViewModelProvider(this)[SearchResultViewModel::class.java]
sharedPreferences = Preferences.getPrefs(this) sharedPreferences = Preferences.getPrefs(view.context)
sharedPreferences.registerOnSharedPreferenceChangeListener(this) sharedPreferences.registerOnSharedPreferenceChangeListener(this)
filter = FilterProvider.with(this).getSavedFilter() filter = FilterProvider.with(view.context).getSavedFilter()
setContentView(B.root) // Toolbar
binding.layoutViewToolbar.apply {
searchView = inputSearch
imgActionPrimary.setOnClickListener {
findNavController().navigateUp()
}
imgActionSecondary.setOnClickListener {
activity?.open(DownloadActivity::class.java)
}
}
attachToolbar() // Search
attachSearch() attachSearch()
attachRecycler()
attachFilter()
VM.liveData.observe(this) { // RecyclerView
endlessRecyclerOnScrollListener = object : EndlessRecyclerOnScrollListener() {
override fun onLoadMore(currentPage: Int) {
VM.next(searchBundle.subBundles)
}
}
binding.recycler.addOnScrollListener(endlessRecyclerOnScrollListener)
// Filter
binding.filterFab.setOnClickListener {
FilterSheet.newInstance().show(childFragmentManager, FilterSheet.TAG)
}
VM.liveData.observe(viewLifecycleOwner) {
if (shimmerAnimationVisible) { if (shimmerAnimationVisible) {
endlessRecyclerOnScrollListener.resetPageCount() endlessRecyclerOnScrollListener.resetPageCount()
B.recycler.clear() binding.recycler.clear()
shimmerAnimationVisible = false shimmerAnimationVisible = false
} }
searchBundle = it searchBundle = it
updateController(searchBundle) updateController(searchBundle)
} }
query = intent.getStringExtra(Constants.STRING_EXTRA) query = args.query
query?.let { query?.let { updateQuery(it) }
updateQuery(it)
}
lifecycleScope.launch { lifecycleScope.launch {
repeatOnLifecycle(Lifecycle.State.STARTED) { repeatOnLifecycle(Lifecycle.State.STARTED) {
@@ -124,74 +140,52 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
attachErrorLayout(getString(R.string.rate_limited)) attachErrorLayout(getString(R.string.rate_limited))
} else { } else {
snackbar = Snackbar.make( snackbar = Snackbar.make(
B.root, binding.root,
getString(R.string.rate_limited), getString(R.string.rate_limited),
Snackbar.LENGTH_INDEFINITE Snackbar.LENGTH_INDEFINITE
) )
snackbar?.show() snackbar?.show()
} }
} }
else -> { else -> {
if (B.errorLayout.isVisible) detachErrorLayout() if (binding.errorLayout.isVisible) detachErrorLayout()
if (snackbar != null && snackbar?.isShown == true) snackbar?.dismiss() if (snackbar != null && snackbar?.isShown == true) snackbar?.dismiss()
} }
} }
} }
} }
} }
} }
override fun onDestroy() { override fun onDestroyView() {
sharedPreferences.unregisterOnSharedPreferenceChangeListener(this) context?.let {
if (Preferences.getBoolean(this, Preferences.PREFERENCE_FILTER_SEARCH)) sharedPreferences.unregisterOnSharedPreferenceChangeListener(this)
FilterProvider.with(this).saveFilter(Filter()) if (Preferences.getBoolean(it, Preferences.PREFERENCE_FILTER_SEARCH)) {
super.onDestroy() FilterProvider.with(it).saveFilter(Filter())
}
}
super.onDestroyView()
_binding = null
} }
private fun attachErrorLayout(message: String) { private fun attachErrorLayout(message: String) {
B.recycler.visibility = View.GONE binding.recycler.visibility = View.GONE
B.filterFab.visibility = View.GONE binding.filterFab.visibility = View.GONE
B.errorLayout.visibility = View.VISIBLE binding.errorLayout.visibility = View.VISIBLE
B.errorMessage.text = message binding.errorMessage.text = message
} }
private fun detachErrorLayout() { private fun detachErrorLayout() {
B.recycler.visibility = View.VISIBLE binding.recycler.visibility = View.VISIBLE
B.filterFab.visibility = View.VISIBLE binding.filterFab.visibility = View.VISIBLE
B.errorLayout.visibility = View.GONE binding.errorLayout.visibility = View.GONE
}
private fun attachToolbar() {
searchView = B.layoutViewToolbar.inputSearch
B.layoutViewToolbar.imgActionPrimary.setOnClickListener {
finishAfterTransition()
}
B.layoutViewToolbar.imgActionSecondary.setOnClickListener {
open(DownloadActivity::class.java)
}
}
private fun attachFilter() {
B.filterFab.setOnClickListener {
FilterSheet.newInstance().show(supportFragmentManager, FilterSheet.TAG)
}
}
private fun attachRecycler() {
endlessRecyclerOnScrollListener = object : EndlessRecyclerOnScrollListener() {
override fun onLoadMore(currentPage: Int) {
VM.next(searchBundle.subBundles)
}
}
B.recycler.addOnScrollListener(endlessRecyclerOnScrollListener)
} }
private fun updateController(searchBundle: SearchBundle?) { private fun updateController(searchBundle: SearchBundle?) {
if (searchBundle == null) { if (searchBundle == null) {
shimmerAnimationVisible = true shimmerAnimationVisible = true
B.recycler.withModels { binding.recycler.withModels {
for (i in 1..10) { for (i in 1..10) {
add(AppListViewShimmerModel_().id(i)) add(AppListViewShimmerModel_().id(i))
} }
@@ -204,7 +198,7 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
if (filteredAppList.isEmpty()) { if (filteredAppList.isEmpty()) {
if (searchBundle.subBundles.isNotEmpty()) { if (searchBundle.subBundles.isNotEmpty()) {
VM.next(searchBundle.subBundles) VM.next(searchBundle.subBundles)
B.recycler.withModels { binding.recycler.withModels {
setFilterDuplicates(true) setFilterDuplicates(true)
add( add(
AppProgressViewModel_() AppProgressViewModel_()
@@ -212,10 +206,10 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
) )
} }
} else { } else {
B.recycler.adapter?.let { binding.recycler.adapter?.let {
/*Show empty search list if nothing found or no app matches filter criterion*/ /*Show empty search list if nothing found or no app matches filter criterion*/
if (it.itemCount == 1 && searchBundle.subBundles.isEmpty()) { if (it.itemCount == 1 && searchBundle.subBundles.isEmpty()) {
B.recycler.withModels { binding.recycler.withModels {
add( add(
NoAppViewModel_() NoAppViewModel_()
.id("no_app") .id("no_app")
@@ -227,7 +221,7 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
} }
} }
} else { } else {
B.recycler binding.recycler
.withModels { .withModels {
setFilterDuplicates(true) setFilterDuplicates(true)
@@ -250,7 +244,7 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
} }
} }
B.recycler.adapter?.let { binding.recycler.adapter?.let {
if (it.itemCount < 10) { if (it.itemCount < 10) {
VM.next(searchBundle.subBundles) VM.next(searchBundle.subBundles)
} }
@@ -295,7 +289,7 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
} }
private fun filter(appList: MutableList<App>): List<App> { private fun filter(appList: MutableList<App>): List<App> {
filter = FilterProvider.with(this).getSavedFilter() filter = FilterProvider.with(requireContext()).getSavedFilter()
return appList return appList
.asSequence() .asSequence()
.filter { if (!filter.paidApps) it.isFree else true } .filter { if (!filter.paidApps) it.isFree else true }
@@ -308,7 +302,7 @@ class SearchResultsActivity : BaseActivity(), OnSharedPreferenceChangeListener {
override fun onSharedPreferenceChanged(sharedPreferences: SharedPreferences?, key: String?) { override fun onSharedPreferenceChanged(sharedPreferences: SharedPreferences?, key: String?) {
if (key == FilterProvider.PREFERENCE_FILTER) { if (key == FilterProvider.PREFERENCE_FILTER) {
filter = FilterProvider.with(this).getSavedFilter() filter = FilterProvider.with(requireContext()).getSavedFilter()
query?.let { query?.let {
queryViewModel(it) queryViewModel(it)
} }

View File

@@ -152,9 +152,10 @@ class SearchSuggestionFragment : Fragment(R.layout.fragment_search_suggestion) {
) { ) {
requireContext().browse("${Constants.PLAY_QUERY_URL}$query", true) requireContext().browse("${Constants.PLAY_QUERY_URL}$query", true)
} else { } else {
val intent = Intent(requireContext(), SearchResultsActivity::class.java) findNavController().navigate(
intent.putExtra(Constants.STRING_EXTRA, query) SearchSuggestionFragmentDirections
startActivity(intent, requireContext().getEmptyActivityBundle()) .actionSearchSuggestionFragmentToSearchResultsFragment(query)
)
} }
} }
} }

View File

@@ -19,9 +19,11 @@
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android" <androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/coordinator" android:id="@+id/coordinator"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="match_parent"> android:layout_height="match_parent"
tools:context=".view.ui.search.SearchResultsFragment">
<RelativeLayout <RelativeLayout
android:layout_width="match_parent" android:layout_width="match_parent"

View File

@@ -79,5 +79,18 @@
android:id="@+id/searchSuggestionFragment" android:id="@+id/searchSuggestionFragment"
android:name="com.aurora.store.view.ui.search.SearchSuggestionFragment" android:name="com.aurora.store.view.ui.search.SearchSuggestionFragment"
android:label="@string/title_search_suggestion" android:label="@string/title_search_suggestion"
tools:layout="@layout/fragment_search_suggestion" /> tools:layout="@layout/fragment_search_suggestion">
<action
android:id="@+id/action_searchSuggestionFragment_to_searchResultsFragment"
app:destination="@id/searchResultsFragment" />
</fragment>
<fragment
android:id="@+id/searchResultsFragment"
android:name="com.aurora.store.view.ui.search.SearchResultsFragment"
android:label="@string/title_search_results"
tools:layout="@layout/fragment_search_result">
<argument
android:name="query"
app:argType="string" />
</fragment>
</navigation> </navigation>

View File

@@ -306,6 +306,7 @@
<string name="title_settings">"Settings"</string> <string name="title_settings">"Settings"</string>
<string name="title_spoof_manager">"Spoof manager"</string> <string name="title_spoof_manager">"Spoof manager"</string>
<string name="title_search_suggestion">"Search suggestion"</string> <string name="title_search_suggestion">"Search suggestion"</string>
<string name="title_search_results">"Search results"</string>
<string name="title_updates">"Updates"</string> <string name="title_updates">"Updates"</string>
<string name="title_advanced">"Advanced"</string> <string name="title_advanced">"Advanced"</string>
<string name="title_manual_download">"Manual download"</string> <string name="title_manual_download">"Manual download"</string>