Horis 1 an în urmă
părinte
comite
c0399abd5b

+ 4 - 2
app/src/main/java/io/legado/app/model/webBook/SearchModel.kt

@@ -73,6 +73,7 @@ class SearchModel(private val scope: CoroutineScope, private val callBack: CallB
 
     private fun startSearch() {
         val precision = appCtx.getPrefBoolean(PreferKey.precisionSearch)
+        var hasMore = false
         searchJob = scope.launch(searchPool!!) {
             flow {
                 for (bs in bookSourceParts) {
@@ -90,12 +91,13 @@ class SearchModel(private val scope: CoroutineScope, private val callBack: CallB
                 for (book in items) {
                     book.releaseHtmlData()
                 }
+                hasMore = hasMore || items.isNotEmpty()
                 appDb.searchBookDao.insert(*items.toTypedArray())
                 mergeItems(items, precision)
                 currentCoroutineContext().ensureActive()
                 callBack.onSearchSuccess(searchBooks)
             }.onCompletion {
-                if (it == null) callBack.onSearchFinish(searchBooks.isEmpty())
+                if (it == null) callBack.onSearchFinish(searchBooks.isEmpty(), hasMore)
             }.catch {
                 AppLog.put("书源搜索出错\n${it.localizedMessage}", it)
             }.collect()
@@ -185,7 +187,7 @@ class SearchModel(private val scope: CoroutineScope, private val callBack: CallB
         fun getSearchScope(): SearchScope
         fun onSearchStart()
         fun onSearchSuccess(searchBooks: List<SearchBook>)
-        fun onSearchFinish(isEmpty: Boolean)
+        fun onSearchFinish(isEmpty: Boolean, hasMore: Boolean)
         fun onSearchCancel(exception: Throwable? = null)
     }
 

+ 5 - 17
app/src/main/java/io/legado/app/ui/book/search/SearchActivity.kt

@@ -54,7 +54,6 @@ import kotlinx.coroutines.flow.flowOn
 import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 import splitties.init.appCtx
-import kotlin.math.abs
 
 class SearchActivity : VMBaseActivity<ActivityBookSearchBinding, SearchViewModel>(),
     BookAdapter.CallBack,
@@ -240,20 +239,7 @@ class SearchActivity : VMBaseActivity<ActivityBookSearchBinding, SearchViewModel
             override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
                 super.onScrolled(recyclerView, dx, dy)
                 if (!recyclerView.canScrollVertically(1)) {
-                    val layoutManager = recyclerView.layoutManager as LinearLayoutManager
-                    val lastPosition = layoutManager.findLastCompletelyVisibleItemPosition()
-                    if (lastPosition == RecyclerView.NO_POSITION) {
-                        return
-                    }
-                    val lastView = layoutManager.findViewByPosition(lastPosition)
-                    if (lastView == null) {
-                        scrollToBottom()
-                        return
-                    }
-                    val bottom = abs(lastView.bottom - recyclerView.height)
-                    if (bottom <= 1) {
-                        scrollToBottom()
-                    }
+                    scrollToBottom()
                 }
             }
         })
@@ -324,6 +310,7 @@ class SearchActivity : VMBaseActivity<ActivityBookSearchBinding, SearchViewModel
         }
         if (viewModel.isSearchLiveData.value == false
             && viewModel.searchKey.isNotEmpty()
+            && viewModel.hasMore
         ) {
             viewModel.search("")
         }
@@ -407,8 +394,9 @@ class SearchActivity : VMBaseActivity<ActivityBookSearchBinding, SearchViewModel
             if (!isEmpty || viewModel.searchScope.isAll()) return@observe
             alert("搜索结果为空") {
                 val precisionSearch = appCtx.getPrefBoolean(PreferKey.precisionSearch)
+                val displayScope = viewModel.searchScope.display
                 if (precisionSearch) {
-                    setMessage("${viewModel.searchScope.display}分组搜索结果为空,是否关闭精准搜索?")
+                    setMessage("${displayScope}分组搜索结果为空,是否关闭精准搜索?")
                     yesButton {
                         appCtx.putPrefBoolean(PreferKey.precisionSearch, false)
                         precisionSearchMenuItem?.isChecked = false
@@ -416,7 +404,7 @@ class SearchActivity : VMBaseActivity<ActivityBookSearchBinding, SearchViewModel
                         viewModel.search(searchView.query.toString())
                     }
                 } else {
-                    setMessage("${viewModel.searchScope.display}分组搜索结果为空,是否切换到全部分组?")
+                    setMessage("${displayScope}分组搜索结果为空,是否切换到全部分组?")
                     yesButton {
                         viewModel.searchScope.update("")
                     }

+ 4 - 1
app/src/main/java/io/legado/app/ui/book/search/SearchViewModel.kt

@@ -30,6 +30,7 @@ class SearchViewModel(application: Application) : BaseViewModel(application) {
     var searchFinishLiveData = MutableLiveData<Boolean>()
     var isSearchLiveData = MutableLiveData<Boolean>()
     var searchKey: String = ""
+    var hasMore = true
     private var searchID = 0L
     private val searchModel = SearchModel(viewModelScope, object : SearchModel.CallBack {
 
@@ -45,9 +46,10 @@ class SearchViewModel(application: Application) : BaseViewModel(application) {
             searchBookLiveData.postValue(searchBooks)
         }
 
-        override fun onSearchFinish(isEmpty: Boolean) {
+        override fun onSearchFinish(isEmpty: Boolean, hasMore: Boolean) {
             isSearchLiveData.postValue(false)
             searchFinishLiveData.postValue(isEmpty)
+            this@SearchViewModel.hasMore = hasMore
         }
 
         override fun onSearchCancel(exception: Throwable?) {
@@ -99,6 +101,7 @@ class SearchViewModel(application: Application) : BaseViewModel(application) {
                 searchID = System.currentTimeMillis()
                 searchBookLiveData.postValue(emptyList())
                 searchKey = key
+                hasMore = true
             }
             if (searchKey.isEmpty()) {
                 return@execute

+ 7 - 0
app/src/main/java/io/legado/app/ui/widget/text/MultilineTextView.kt

@@ -1,12 +1,19 @@
 package io.legado.app.ui.widget.text
 
 import android.content.Context
+import android.os.Build
 import android.util.AttributeSet
 import androidx.appcompat.widget.AppCompatTextView
 
 class MultilineTextView(context: Context, attrs: AttributeSet?) :
     AppCompatTextView(context, attrs) {
 
+    init {
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
+            isFallbackLineSpacing = false
+        }
+    }
+
     override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
         val heightSize = MeasureSpec.getSize(heightMeasureSpec)
         calculateLines(heightSize)

+ 1 - 1
app/src/main/java/io/legado/app/web/socket/BookSearchWebSocket.kt

@@ -90,7 +90,7 @@ class BookSearchWebSocket(handshakeRequest: NanoHTTPD.IHTTPSession) :
         send(GSON.toJson(searchBooks))
     }
 
-    override fun onSearchFinish(isEmpty: Boolean) = close(normalClosure, SEARCH_FINISH, false)
+    override fun onSearchFinish(isEmpty: Boolean, hasMore: Boolean) = close(normalClosure, SEARCH_FINISH, false)
 
     override fun onSearchCancel(exception: Throwable?) = close(normalClosure, exception?.toString() ?: SEARCH_FINISH, false)