diff --git a/app/src/main/java/io/legado/app/data/entities/BookSource.kt b/app/src/main/java/io/legado/app/data/entities/BookSource.kt index c09a467dc..b9419c805 100644 --- a/app/src/main/java/io/legado/app/data/entities/BookSource.kt +++ b/app/src/main/java/io/legado/app/data/entities/BookSource.kt @@ -169,8 +169,31 @@ data class BookSource( return AppConst.SCRIPT_ENGINE.eval(jsStr, bindings) } - data class ExploreKind( - var title: String, - var url: String? = null - ) -} \ No newline at end of file + fun equal(source: BookSource?): Boolean { + if (source == null) { + return false + } + return bookSourceName == source.bookSourceName + && bookSourceUrl == source.bookSourceUrl + && bookSourceGroup == source.bookSourceGroup + && bookSourceType == source.bookSourceType + && bookUrlPattern == source.bookUrlPattern + && enabled == source.enabled + && enabledExplore == source.enabledExplore + && header == source.header + && loginUrl == source.loginUrl + && lastUpdateTime == source.lastUpdateTime + && exploreUrl == source.exploreUrl + && searchUrl == source.searchUrl + && ruleSearch == source.ruleSearch + && ruleExplore == source.ruleExplore + && ruleBookInfo == source.ruleBookInfo + && ruleToc == source.ruleToc + && ruleContent == source.ruleContent + } +} + +data class ExploreKind( + var title: String, + var url: String? = null +) \ No newline at end of file diff --git a/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditActivity.kt b/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditActivity.kt index a5d1e7676..c3f2d2231 100644 --- a/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditActivity.kt +++ b/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditActivity.kt @@ -12,7 +12,6 @@ import android.view.MenuItem import android.view.ViewTreeObserver import android.widget.EditText import android.widget.PopupWindow -import androidx.lifecycle.Observer import androidx.recyclerview.widget.LinearLayoutManager import com.google.android.material.tabs.TabLayout import io.legado.app.R @@ -21,10 +20,14 @@ import io.legado.app.constant.AppConst import io.legado.app.data.entities.BookSource import io.legado.app.data.entities.EditEntity import io.legado.app.data.entities.rule.* +import io.legado.app.lib.dialogs.alert +import io.legado.app.lib.dialogs.noButton +import io.legado.app.lib.dialogs.yesButton import io.legado.app.lib.theme.ATH import io.legado.app.ui.book.source.debug.BookSourceDebugActivity import io.legado.app.ui.widget.KeyboardToolPop import io.legado.app.utils.GSON +import io.legado.app.utils.applyTint import io.legado.app.utils.getViewModel import kotlinx.android.synthetic.main.activity_book_source_edit.* import org.jetbrains.anko.displayMetrics @@ -51,10 +54,9 @@ class BookSourceEditActivity : override fun onActivityCreated(savedInstanceState: Bundle?) { initView() - viewModel.sourceLiveData.observe(this, Observer { - upRecyclerView(it) - }) - viewModel.initData(intent) + viewModel.initData(intent) { + upRecyclerView() + } } override fun onCompatCreateOptionsMenu(menu: Menu): Boolean { @@ -65,14 +67,16 @@ class BookSourceEditActivity : override fun onCompatOptionsItemSelected(item: MenuItem): Boolean { when (item.itemId) { R.id.menu_save -> { - getSource()?.let { - viewModel.save(it) { setResult(Activity.RESULT_OK); finish() } + val source = getSource() + if (checkSource(source)) { + viewModel.save(source) { setResult(Activity.RESULT_OK); finish() } } } R.id.menu_debug_source -> { - getSource()?.let { - viewModel.save(it) { - startActivity(Pair("key", it.bookSourceUrl)) + val source = getSource() + if (checkSource(source)) { + viewModel.save(source) { + startActivity(Pair("key", source.bookSourceUrl)) } } } @@ -82,7 +86,7 @@ class BookSourceEditActivity : clipboard?.primaryClip = ClipData.newPlainText(null, sourceStr) } } - R.id.menu_paste_source -> viewModel.pasteSource() + R.id.menu_paste_source -> viewModel.pasteSource { upRecyclerView() } } return super.onCompatOptionsItemSelected(item) } @@ -109,7 +113,21 @@ class BookSourceEditActivity : } override fun finish() { - super.finish() + val source = getSource() + if (!source.equal(viewModel.bookSource)) { + alert(title = "是否保存") { + yesButton { + if (checkSource(source)) { + viewModel.save(source) { + super.finish() + } + } + } + noButton { } + }.show().applyTint() + } else { + super.finish() + } } override fun onDestroy() { @@ -129,33 +147,34 @@ class BookSourceEditActivity : recycler_view.scrollToPosition(0) } - private fun upRecyclerView(bookSource: BookSource?) { - bookSource?.let { + private fun upRecyclerView() { + val source = viewModel.bookSource + source?.let { cb_is_enable.isChecked = it.enabled cb_is_enable_find.isChecked = it.enabledExplore - sp_type.setSelection(bookSource.bookSourceType) + sp_type.setSelection(it.bookSourceType) } //基本信息 sourceEntities.clear() sourceEntities.apply { - add(EditEntity("bookSourceUrl", bookSource?.bookSourceUrl, R.string.book_source_url)) - add(EditEntity("bookSourceName", bookSource?.bookSourceName, R.string.book_source_name)) + add(EditEntity("bookSourceUrl", source?.bookSourceUrl, R.string.book_source_url)) + add(EditEntity("bookSourceName", source?.bookSourceName, R.string.book_source_name)) add( EditEntity( "bookSourceGroup", - bookSource?.bookSourceGroup, + source?.bookSourceGroup, R.string.book_source_group ) ) - add(EditEntity("loginUrl", bookSource?.loginUrl, R.string.book_source_login_url)) - add(EditEntity("bookUrlPattern", bookSource?.bookUrlPattern, R.string.book_url_pattern)) - add(EditEntity("header", bookSource?.header, R.string.source_http_header)) + add(EditEntity("loginUrl", source?.loginUrl, R.string.book_source_login_url)) + add(EditEntity("bookUrlPattern", source?.bookUrlPattern, R.string.book_url_pattern)) + add(EditEntity("header", source?.header, R.string.source_http_header)) } //搜索 - (bookSource?.getSearchRule()).let { searchRule -> + (source?.getSearchRule()).let { searchRule -> searchEntities.clear() searchEntities.apply { - add(EditEntity("searchUrl", bookSource?.searchUrl, R.string.rule_search_url)) + add(EditEntity("searchUrl", source?.searchUrl, R.string.rule_search_url)) add(EditEntity("bookList", searchRule?.bookList, R.string.rule_book_list)) add(EditEntity("name", searchRule?.name, R.string.rule_book_name)) add(EditEntity("author", searchRule?.author, R.string.rule_book_author)) @@ -168,7 +187,7 @@ class BookSourceEditActivity : } } //详情页 - (bookSource?.getBookInfoRule()).let { infoRule -> + (source?.getBookInfoRule()).let { infoRule -> infoEntities.clear() infoEntities.apply { add(EditEntity("init", infoRule?.init, R.string.rule_book_info_init)) @@ -183,7 +202,7 @@ class BookSourceEditActivity : } } //目录页 - (bookSource?.getTocRule()).let { tocRule -> + (source?.getTocRule()).let { tocRule -> tocEntities.clear() tocEntities.apply { add(EditEntity("chapterList", tocRule?.chapterList, R.string.rule_chapter_list)) @@ -193,7 +212,7 @@ class BookSourceEditActivity : } } //正文页 - (bookSource?.getContentRule()).let { contentRule -> + (source?.getContentRule()).let { contentRule -> contentEntities.clear() contentEntities.apply { add(EditEntity("content", contentRule?.content, R.string.rule_book_content)) @@ -208,10 +227,10 @@ class BookSourceEditActivity : } //发现 - (bookSource?.getExploreRule()).let { exploreRule -> + (source?.getExploreRule()).let { exploreRule -> findEntities.clear() findEntities.apply { - add(EditEntity("exploreUrl", bookSource?.exploreUrl, R.string.rule_find_url)) + add(EditEntity("exploreUrl", source?.exploreUrl, R.string.rule_find_url)) add(EditEntity("bookList", exploreRule?.bookList, R.string.rule_book_list)) add(EditEntity("name", exploreRule?.name, R.string.rule_book_name)) add(EditEntity("author", exploreRule?.author, R.string.rule_book_author)) @@ -226,15 +245,11 @@ class BookSourceEditActivity : setEditEntities(0) } - private fun getSource(): BookSource? { - val source = viewModel.sourceLiveData.value ?: BookSource() + private fun getSource(): BookSource { + val source = viewModel.bookSource?.copy() ?: BookSource() source.enabled = cb_is_enable.isChecked source.enabledExplore = cb_is_enable_find.isChecked source.bookSourceType = sp_type.selectedItemPosition - viewModel.sourceLiveData.value?.let { - source.customOrder = it.customOrder - source.weight = it.weight - } val searchRule = SearchRule() val exploreRule = ExploreRule() val bookInfoRule = BookInfoRule() @@ -250,10 +265,6 @@ class BookSourceEditActivity : "header" -> source.header = it.value } } - if (source.bookSourceUrl.isBlank() || source.bookSourceName.isBlank()) { - toast("书源名称和URL不能为空") - return null - } searchEntities.forEach { when (it.key) { "searchUrl" -> source.searchUrl = it.value @@ -320,6 +331,14 @@ class BookSourceEditActivity : return source } + private fun checkSource(source: BookSource): Boolean { + if (source.bookSourceUrl.isBlank() || source.bookSourceName.isBlank()) { + toast("书源名称和URL不能为空") + return false + } + return true + } + override fun sendText(text: String) { if (text.isBlank()) return val view = window.decorView.findFocus() diff --git a/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditViewModel.kt b/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditViewModel.kt index 5368c9650..db62afbce 100644 --- a/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditViewModel.kt +++ b/app/src/main/java/io/legado/app/ui/book/source/edit/BookSourceEditViewModel.kt @@ -4,7 +4,6 @@ import android.app.Application import android.content.ClipboardManager import android.content.Context import android.content.Intent -import androidx.lifecycle.MutableLiveData import io.legado.app.App import io.legado.app.base.BaseViewModel import io.legado.app.data.entities.BookSource @@ -12,10 +11,10 @@ import io.legado.app.help.storage.OldRule class BookSourceEditViewModel(application: Application) : BaseViewModel(application) { - val sourceLiveData: MutableLiveData = MutableLiveData() + var bookSource: BookSource? = null private var oldSourceUrl: String? = null - fun initData(intent: Intent) { + fun initData(intent: Intent, onFinally: () -> Unit) { execute { val key = intent.getStringExtra("data") var source: BookSource? = null @@ -24,12 +23,14 @@ class BookSourceEditViewModel(application: Application) : BaseViewModel(applicat } source?.let { oldSourceUrl = it.bookSourceUrl - sourceLiveData.postValue(it) + bookSource = it } ?: let { - sourceLiveData.postValue(BookSource().apply { + bookSource = BookSource().apply { customOrder = App.db.bookSourceDao().maxOrder + 1 - }) + } } + }.onFinally { + onFinally() } } @@ -50,19 +51,21 @@ class BookSourceEditViewModel(application: Application) : BaseViewModel(applicat } } - fun pasteSource() { + fun pasteSource(onSuccess: () -> Unit) { execute { val clipboard = context.getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager? clipboard?.primaryClip?.let { if (it.itemCount > 0) { val json = it.getItemAt(0).text.toString() OldRule.jsonToBookSource(json)?.let { source -> - sourceLiveData.postValue(source) + bookSource = source } ?: toast("格式不对") } } }.onError { toast(it.localizedMessage) + }.onSuccess { + onSuccess() } } } \ No newline at end of file