添加格式化目录规则,只能写js,不用@js:标志,提供变量index和title,index从1开始

This commit is contained in:
kunfei
2023-05-16 21:06:17 +08:00
parent 41ef806c3c
commit 29bab84470
15 changed files with 1945 additions and 18 deletions
File diff suppressed because it is too large Load Diff
@@ -18,6 +18,7 @@ object AppPattern {
val authorRegex = Regex("^\\s*作\\s*者[:\\s]+|\\s+著") val authorRegex = Regex("^\\s*作\\s*者[:\\s]+|\\s+著")
val fileNameRegex = Regex("[\\\\/:*?\"<>|.]") val fileNameRegex = Regex("[\\\\/:*?\"<>|.]")
val splitGroupRegex = Regex("[,;,;]") val splitGroupRegex = Regex("[,;,;]")
val titleNumPattern = Pattern.compile("(第)(.+?)(章)")
//书源调试信息中的各种符号 //书源调试信息中的各种符号
val debugMessageSymbolRegex = Regex("[⇒◇┌└≡]") val debugMessageSymbolRegex = Regex("[⇒◇┌└≡]")
@@ -21,7 +21,7 @@ val appDb by lazy {
} }
@Database( @Database(
version = 68, version = 69,
exportSchema = true, exportSchema = true,
entities = [Book::class, BookGroup::class, BookSource::class, BookChapter::class, entities = [Book::class, BookGroup::class, BookSource::class, BookChapter::class,
ReplaceRule::class, SearchBook::class, SearchKeyword::class, Cookie::class, ReplaceRule::class, SearchBook::class, SearchKeyword::class, Cookie::class,
@@ -53,7 +53,8 @@ val appDb by lazy {
AutoMigration(from = 64, to = 65, spec = DatabaseMigrations.Migration_64_65::class), AutoMigration(from = 64, to = 65, spec = DatabaseMigrations.Migration_64_65::class),
AutoMigration(from = 65, to = 66), AutoMigration(from = 65, to = 66),
AutoMigration(from = 66, to = 67), AutoMigration(from = 66, to = 67),
AutoMigration(from = 67, to = 68) AutoMigration(from = 67, to = 68),
AutoMigration(from = 68, to = 69)
] ]
) )
abstract class AppDatabase : RoomDatabase() { abstract class AppDatabase : RoomDatabase() {
@@ -11,6 +11,7 @@ data class TocRule(
var chapterList: String? = null, var chapterList: String? = null,
var chapterName: String? = null, var chapterName: String? = null,
var chapterUrl: String? = null, var chapterUrl: String? = null,
var formatJs: String? = null,
var isVolume: String? = null, var isVolume: String? = null,
var isVip: String? = null, var isVip: String? = null,
var isPay: String? = null, var isPay: String? = null,
@@ -10,10 +10,10 @@ import com.github.liuyueyi.quick.transfer.ChineseUtils
import io.legado.app.constant.AppConst import io.legado.app.constant.AppConst
import io.legado.app.constant.AppConst.dateFormat import io.legado.app.constant.AppConst.dateFormat
import io.legado.app.constant.AppLog import io.legado.app.constant.AppLog
import io.legado.app.constant.AppPattern
import io.legado.app.data.entities.BaseSource import io.legado.app.data.entities.BaseSource
import io.legado.app.exception.NoStackTraceException import io.legado.app.exception.NoStackTraceException
import io.legado.app.help.http.BackstageWebView import io.legado.app.help.http.BackstageWebView
import io.legado.app.help.http.CookieManager
import io.legado.app.help.http.CookieManager.cookieJarHeader import io.legado.app.help.http.CookieManager.cookieJarHeader
import io.legado.app.help.http.CookieStore import io.legado.app.help.http.CookieStore
import io.legado.app.help.http.SSLHelper import io.legado.app.help.http.SSLHelper
@@ -777,6 +777,19 @@ interface JsExtensions : JsEncodeUtils {
return contentArray.joinToString("") return contentArray.joinToString("")
} }
/**
* 章节数转数字
*/
fun toNumChapter(s: String?): String? {
s ?: return null
val matcher = AppPattern.titleNumPattern.matcher(s)
if (matcher.find()) {
return "${matcher.group(1)}${StringUtils.stringToInt(matcher.group(2))}${matcher.group(3)}"
}
return s
}
/** /**
* 弹窗提示 * 弹窗提示
*/ */
@@ -743,18 +743,6 @@ class AnalyzeRule(
} }
} }
/**
* 章节数转数字
*/
fun toNumChapter(s: String?): String? {
s ?: return null
val matcher = titleNumPattern.matcher(s)
if (matcher.find()) {
return "${matcher.group(1)}${StringUtils.stringToInt(matcher.group(2))}${matcher.group(3)}"
}
return s
}
/** /**
* 重新获取book * 重新获取book
*/ */
@@ -809,7 +797,6 @@ class AnalyzeRule(
private val evalPattern = private val evalPattern =
Pattern.compile("@get:\\{[^}]+?\\}|\\{\\{[\\w\\W]*?\\}\\}", Pattern.CASE_INSENSITIVE) Pattern.compile("@get:\\{[^}]+?\\}|\\{\\{[\\w\\W]*?\\}\\}", Pattern.CASE_INSENSITIVE)
private val regexPattern = Pattern.compile("\\$\\d{1,2}") private val regexPattern = Pattern.compile("\\$\\d{1,2}")
private val titleNumPattern = Pattern.compile("(第)(.+?)(章)")
} }
} }
@@ -1,6 +1,8 @@
package io.legado.app.model.webBook package io.legado.app.model.webBook
import android.text.TextUtils import android.text.TextUtils
import com.script.SimpleBindings
import com.script.rhino.RhinoScriptEngine
import io.legado.app.R import io.legado.app.R
import io.legado.app.data.entities.Book import io.legado.app.data.entities.Book
import io.legado.app.data.entities.BookChapter import io.legado.app.data.entities.BookChapter
@@ -117,8 +119,21 @@ object BookChapterList {
} }
Debug.log(book.origin, "◇目录总数:${list.size}") Debug.log(book.origin, "◇目录总数:${list.size}")
coroutineContext.ensureActive() coroutineContext.ensureActive()
val formatJs = tocRule.formatJs
val bindings = SimpleBindings()
list.forEachIndexed { index, bookChapter -> list.forEachIndexed { index, bookChapter ->
bookChapter.index = index bookChapter.index = index
if (!formatJs.isNullOrBlank()) {
bindings["index"] = index + 1
bindings["title"] = bookChapter.title
RhinoScriptEngine.runCatching {
eval(formatJs, bindings)?.toString()?.let {
bookChapter.title = it
}
}.onFailure {
Debug.log(book.origin, "格式化标题出错, ${it.localizedMessage}")
}
}
} }
val replaceRules = ContentProcessor.get(book.name, book.origin).getTitleReplaceRules() val replaceRules = ContentProcessor.get(book.name, book.origin).getTitleReplaceRules()
book.latestChapterTitle = list.last().getDisplayTitle(replaceRules) book.latestChapterTitle = list.last().getDisplayTitle(replaceRules)
@@ -14,7 +14,12 @@ import io.legado.app.base.VMBaseActivity
import io.legado.app.constant.BookSourceType import io.legado.app.constant.BookSourceType
import io.legado.app.data.appDb import io.legado.app.data.appDb
import io.legado.app.data.entities.BookSource import io.legado.app.data.entities.BookSource
import io.legado.app.data.entities.rule.* import io.legado.app.data.entities.rule.BookInfoRule
import io.legado.app.data.entities.rule.ContentRule
import io.legado.app.data.entities.rule.ExploreRule
import io.legado.app.data.entities.rule.ReviewRule
import io.legado.app.data.entities.rule.SearchRule
import io.legado.app.data.entities.rule.TocRule
import io.legado.app.databinding.ActivityBookSourceEditBinding import io.legado.app.databinding.ActivityBookSourceEditBinding
import io.legado.app.help.config.LocalConfig import io.legado.app.help.config.LocalConfig
import io.legado.app.lib.dialogs.SelectItem import io.legado.app.lib.dialogs.SelectItem
@@ -32,7 +37,15 @@ import io.legado.app.ui.widget.dialog.UrlOptionDialog
import io.legado.app.ui.widget.dialog.VariableDialog import io.legado.app.ui.widget.dialog.VariableDialog
import io.legado.app.ui.widget.keyboard.KeyboardToolPop import io.legado.app.ui.widget.keyboard.KeyboardToolPop
import io.legado.app.ui.widget.text.EditEntity import io.legado.app.ui.widget.text.EditEntity
import io.legado.app.utils.* import io.legado.app.utils.GSON
import io.legado.app.utils.isContentScheme
import io.legado.app.utils.launch
import io.legado.app.utils.sendToClip
import io.legado.app.utils.setEdgeEffectColor
import io.legado.app.utils.share
import io.legado.app.utils.shareWithQr
import io.legado.app.utils.showDialogFragment
import io.legado.app.utils.startActivity
import io.legado.app.utils.viewbindingdelegate.viewBinding import io.legado.app.utils.viewbindingdelegate.viewBinding
import kotlinx.coroutines.Dispatchers.IO import kotlinx.coroutines.Dispatchers.IO
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
@@ -295,6 +308,7 @@ class BookSourceEditActivity :
add(EditEntity("chapterList", tr.chapterList, R.string.rule_chapter_list)) add(EditEntity("chapterList", tr.chapterList, R.string.rule_chapter_list))
add(EditEntity("chapterName", tr.chapterName, R.string.rule_chapter_name)) add(EditEntity("chapterName", tr.chapterName, R.string.rule_chapter_name))
add(EditEntity("chapterUrl", tr.chapterUrl, R.string.rule_chapter_url)) add(EditEntity("chapterUrl", tr.chapterUrl, R.string.rule_chapter_url))
add(EditEntity("formatJs", tr.formatJs, R.string.format_js_rule))
add(EditEntity("isVolume", tr.isVolume, R.string.rule_is_volume)) add(EditEntity("isVolume", tr.isVolume, R.string.rule_is_volume))
add(EditEntity("updateTime", tr.updateTime, R.string.rule_update_time)) add(EditEntity("updateTime", tr.updateTime, R.string.rule_update_time))
add(EditEntity("isVip", tr.isVip, R.string.rule_is_vip)) add(EditEntity("isVip", tr.isVip, R.string.rule_is_vip))
@@ -447,8 +461,11 @@ class BookSourceEditActivity :
"chapterList" -> tocRule.chapterList = it.value "chapterList" -> tocRule.chapterList = it.value
"chapterName" -> tocRule.chapterName = "chapterName" -> tocRule.chapterName =
viewModel.ruleComplete(it.value, tocRule.chapterList) viewModel.ruleComplete(it.value, tocRule.chapterList)
"chapterUrl" -> tocRule.chapterUrl = "chapterUrl" -> tocRule.chapterUrl =
viewModel.ruleComplete(it.value, tocRule.chapterList, 2) viewModel.ruleComplete(it.value, tocRule.chapterList, 2)
"formatJs" -> tocRule.formatJs = it.value
"isVolume" -> tocRule.isVolume = it.value "isVolume" -> tocRule.isVolume = it.value
"updateTime" -> tocRule.updateTime = it.value "updateTime" -> tocRule.updateTime = it.value
"isVip" -> tocRule.isVip = it.value "isVip" -> tocRule.isVip = it.value
@@ -1102,4 +1102,5 @@
<string name="webdav_application_authorization_error">Fail to authorize WebDav application</string> <string name="webdav_application_authorization_error">Fail to authorize WebDav application</string>
<string name="load_word_count">Cargar palabras del libro</string> <string name="load_word_count">Cargar palabras del libro</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
@@ -1105,4 +1105,5 @@
<string name="webdav_application_authorization_error">Fail to authorize WebDav application</string> <string name="webdav_application_authorization_error">Fail to authorize WebDav application</string>
<string name="load_word_count">Load word count</string> <string name="load_word_count">Load word count</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
@@ -1105,4 +1105,5 @@
<string name="webdav_application_authorization_error">Fail to authorize WebDav application</string> <string name="webdav_application_authorization_error">Fail to authorize WebDav application</string>
<string name="load_word_count">Carregar os palavras do livro</string> <string name="load_word_count">Carregar os palavras do livro</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
@@ -1102,4 +1102,5 @@
<string name="webdav_application_authorization_error">webDav应用验证失败</string> <string name="webdav_application_authorization_error">webDav应用验证失败</string>
<string name="load_word_count">加載字數</string> <string name="load_word_count">加載字數</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
@@ -1104,4 +1104,5 @@
<string name="webdav_application_authorization_error">webDav应用验证失败</string> <string name="webdav_application_authorization_error">webDav应用验证失败</string>
<string name="load_word_count">加載字數</string> <string name="load_word_count">加載字數</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
+1
View File
@@ -1104,4 +1104,5 @@
<string name="webdav_application_authorization_error">webDav应用验证失败</string> <string name="webdav_application_authorization_error">webDav应用验证失败</string>
<string name="load_word_count">加载字数</string> <string name="load_word_count">加载字数</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>
+1
View File
@@ -1105,4 +1105,5 @@
<string name="respondTime">respondTime: %1$d ms</string> <string name="respondTime">respondTime: %1$d ms</string>
<string name="load_word_count">Load word count</string> <string name="load_word_count">Load word count</string>
<string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string> <string name="replace_exclude_scope">排除范围,选填书名或者书源 URL</string>
<string name="format_js_rule">格式化规则(formatJs)</string>
</resources> </resources>