HapeLee hai 1 ano
pai
achega
58e0f51c3e
Modificáronse 26 ficheiros con 185 adicións e 532 borrados
  1. 2 2
      app/src/main/java/io/legato/kazusa/lib/prefs/Preference.kt
  2. 4 1
      app/src/main/java/io/legato/kazusa/lib/prefs/PreferenceCategory.kt
  3. 8 5
      app/src/main/java/io/legato/kazusa/ui/about/AppLogDialog.kt
  4. 4 4
      app/src/main/java/io/legato/kazusa/ui/association/ImportBookSourceDialog.kt
  5. 6 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportDictRuleDialog.kt
  6. 7 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportHttpTtsDialog.kt
  7. 6 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportReplaceRuleDialog.kt
  8. 6 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportRssSourceDialog.kt
  9. 7 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportThemeDialog.kt
  10. 7 6
      app/src/main/java/io/legato/kazusa/ui/association/ImportTxtTocRuleDialog.kt
  11. 1 1
      app/src/main/java/io/legato/kazusa/ui/main/explore/ExploreFragment.kt
  12. 78 0
      app/src/main/java/io/legato/kazusa/ui/widget/EmptyMessageView.kt
  13. 0 327
      app/src/main/java/io/legato/kazusa/ui/widget/checkbox/SmoothCheckBox.kt
  14. 3 3
      app/src/main/java/io/legato/kazusa/ui/widget/text/PrimaryTextView.kt
  15. 0 88
      app/src/main/java/io/legato/kazusa/ui/widget/text/StrokeTextView.kt
  16. 1 0
      app/src/main/res/layout/activity_import_book.xml
  17. 3 19
      app/src/main/res/layout/dialog_book_change_source.xml
  18. 6 5
      app/src/main/res/layout/dialog_recycler_view.xml
  19. 2 2
      app/src/main/res/layout/dialog_select_section_export.xml
  20. 6 19
      app/src/main/res/layout/fragment_books.xml
  21. 5 18
      app/src/main/res/layout/fragment_explore.xml
  22. 5 0
      app/src/main/res/values-zh/arrays.xml
  23. 2 2
      app/src/main/res/values-zh/strings.xml
  24. 6 0
      app/src/main/res/values/array_values.xml
  25. 6 0
      app/src/main/res/values/arrays.xml
  26. 4 0
      app/src/main/res/values/attrs.xml

+ 2 - 2
app/src/main/java/io/legato/kazusa/lib/prefs/Preference.kt

@@ -19,7 +19,7 @@ import io.legato.kazusa.R
 import splitties.views.onLongClick
 import splitties.views.onLongClick
 import kotlin.math.roundToInt
 import kotlin.math.roundToInt
 
 
-open class Preference(context: Context, attrs: AttributeSet) :
+open class Preference(context: Context, attrs: AttributeSet?) :
     androidx.preference.Preference(context, attrs) {
     androidx.preference.Preference(context, attrs) {
 
 
     private var onLongClick: ((preference: Preference) -> Boolean)? = null
     private var onLongClick: ((preference: Preference) -> Boolean)? = null
@@ -68,7 +68,7 @@ open class Preference(context: Context, attrs: AttributeSet) :
             if (iconView is ImageView) {
             if (iconView is ImageView) {
                 iconView.isVisible = icon != null
                 iconView.isVisible = icon != null
                 iconView.setImageDrawable(icon)
                 iconView.setImageDrawable(icon)
-                //iconView.setColorFilter(context.accentColor)
+               // iconView.setColorFilter(context.primaryColor)
             }
             }
 
 
             if (weightLayoutRes != null && weightLayoutRes != 0 && viewId != null && viewId != 0) {
             if (weightLayoutRes != null && weightLayoutRes != 0 && viewId != null && viewId != 0) {

+ 4 - 1
app/src/main/java/io/legato/kazusa/lib/prefs/PreferenceCategory.kt

@@ -7,6 +7,9 @@ import androidx.core.view.isVisible
 import androidx.preference.PreferenceCategory
 import androidx.preference.PreferenceCategory
 import androidx.preference.PreferenceViewHolder
 import androidx.preference.PreferenceViewHolder
 import io.legato.kazusa.R
 import io.legato.kazusa.R
+import io.legato.kazusa.lib.theme.primaryColor
+import io.legato.kazusa.utils.themeColor
+
 //import io.legado.app.lib.theme.accentColor
 //import io.legado.app.lib.theme.accentColor
 //import io.legado.app.lib.theme.backgroundColor
 //import io.legado.app.lib.theme.backgroundColor
 
 
@@ -25,7 +28,7 @@ class PreferenceCategory(context: Context, attrs: AttributeSet) :
         if (view is TextView) {  //  && !view.isInEditMode
         if (view is TextView) {  //  && !view.isInEditMode
             view.text = title
             view.text = title
             if (view.isInEditMode) return
             if (view.isInEditMode) return
-            //view.setTextColor(context.accentColor)
+           // view.setTextColor(context.primaryColor)
             view.isVisible = !title.isNullOrEmpty()
             view.isVisible = !title.isNullOrEmpty()
 
 
 //            val da = holder.findViewById(R.id.preference_divider_above)
 //            val da = holder.findViewById(R.id.preference_divider_above)

+ 8 - 5
app/src/main/java/io/legato/kazusa/ui/about/AppLogDialog.kt

@@ -31,11 +31,6 @@ class AppLogDialog : BaseDialogFragment(R.layout.dialog_recycler_view),
         LogAdapter(requireContext())
         LogAdapter(requireContext())
     }
     }
 
 
-    override fun onStart() {
-        super.onStart()
-        setLayout(0.9f, ViewGroup.LayoutParams.WRAP_CONTENT)
-    }
-
     override fun onFragmentCreated(view: View, savedInstanceState: Bundle?) {
     override fun onFragmentCreated(view: View, savedInstanceState: Bundle?) {
         binding.run {
         binding.run {
             //toolBar.setBackgroundColor(primaryColor)
             //toolBar.setBackgroundColor(primaryColor)
@@ -46,13 +41,21 @@ class AppLogDialog : BaseDialogFragment(R.layout.dialog_recycler_view),
             recyclerView.adapter = adapter
             recyclerView.adapter = adapter
         }
         }
         adapter.setItems(AppLog.logs)
         adapter.setItems(AppLog.logs)
+        updateEmptyView()
     }
     }
 
 
+    private fun updateEmptyView() {
+        binding.emptyView.visibility =
+            if (adapter.itemCount == 0) View.VISIBLE else View.GONE
+    }
+
+
     override fun onMenuItemClick(item: MenuItem?): Boolean {
     override fun onMenuItemClick(item: MenuItem?): Boolean {
         when (item?.itemId) {
         when (item?.itemId) {
             R.id.menu_clear -> {
             R.id.menu_clear -> {
                 AppLog.clear()
                 AppLog.clear()
                 adapter.clearItems()
                 adapter.clearItems()
+                updateEmptyView()
             }
             }
         }
         }
         return true
         return true

+ 4 - 4
app/src/main/java/io/legato/kazusa/ui/association/ImportBookSourceDialog.kt

@@ -93,8 +93,8 @@ class ImportBookSourceDialog() : BaseBottomSheetDialogFragment(R.layout.dialog_r
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
             binding.rotateLoading.gone()
             binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
@@ -104,8 +104,8 @@ class ImportBookSourceDialog() : BaseBottomSheetDialogFragment(R.layout.dialog_r
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 6 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportDictRuleDialog.kt

@@ -80,20 +80,20 @@ class ImportDictRuleDialog() : BaseDialogFragment(R.layout.dialog_recycler_view)
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-            //binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 7 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportHttpTtsDialog.kt

@@ -19,6 +19,7 @@ import io.legato.kazusa.databinding.ItemSourceImportBinding
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.utils.GSON
 import io.legato.kazusa.utils.GSON
+import io.legato.kazusa.utils.gone
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
@@ -83,20 +84,20 @@ class ImportHttpTtsDialog() : BaseDialogFragment(R.layout.dialog_recycler_view),
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-            //binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 6 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportReplaceRuleDialog.kt

@@ -88,20 +88,20 @@ class ImportReplaceRuleDialog() : BaseDialogFragment(R.layout.dialog_recycler_vi
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-           // binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allRules)
                 adapter.setItems(viewModel.allRules)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 6 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportRssSourceDialog.kt

@@ -92,20 +92,20 @@ class ImportRssSourceDialog() : BaseDialogFragment(R.layout.dialog_recycler_view
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-            //binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 7 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportThemeDialog.kt

@@ -19,6 +19,7 @@ import io.legato.kazusa.help.config.ThemeConfig
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.utils.GSON
 import io.legato.kazusa.utils.GSON
+import io.legato.kazusa.utils.gone
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
@@ -82,20 +83,20 @@ class ImportThemeDialog() : BaseBottomSheetDialogFragment(R.layout.dialog_recycl
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-            //binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 7 - 6
app/src/main/java/io/legato/kazusa/ui/association/ImportTxtTocRuleDialog.kt

@@ -19,6 +19,7 @@ import io.legato.kazusa.databinding.ItemSourceImportBinding
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.CodeDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.ui.widget.dialog.WaitDialog
 import io.legato.kazusa.utils.GSON
 import io.legato.kazusa.utils.GSON
+import io.legato.kazusa.utils.gone
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.setLayout
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.showDialogFragment
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
 import io.legato.kazusa.utils.viewbindingdelegate.viewBinding
@@ -82,20 +83,20 @@ class ImportTxtTocRuleDialog() : BaseDialogFragment(R.layout.dialog_recycler_vie
             upSelectText()
             upSelectText()
         }
         }
         viewModel.errorLiveData.observe(this) {
         viewModel.errorLiveData.observe(this) {
-            //binding.rotateLoading.gone()
-            binding.tvMsg.apply {
-                text = it
+            binding.rotateLoading.gone()
+            binding.emptyView.apply {
+                setMessage(it)
                 visible()
                 visible()
             }
             }
         }
         }
         viewModel.successLiveData.observe(this) {
         viewModel.successLiveData.observe(this) {
-            //binding.rotateLoading.gone()
+            binding.rotateLoading.gone()
             if (it > 0) {
             if (it > 0) {
                 adapter.setItems(viewModel.allSources)
                 adapter.setItems(viewModel.allSources)
                 upSelectText()
                 upSelectText()
             } else {
             } else {
-                binding.tvMsg.apply {
-                    setText(R.string.wrong_format)
+                binding.emptyView.apply {
+                    setMessage(R.string.wrong_format)
                     visible()
                     visible()
                 }
                 }
             }
             }

+ 1 - 1
app/src/main/java/io/legato/kazusa/ui/main/explore/ExploreFragment.kt

@@ -179,7 +179,7 @@ class ExploreFragment() : VMBaseFragment<ExploreViewModel>(R.layout.fragment_exp
             ).catch {
             ).catch {
                 AppLog.put("发现界面更新数据出错", it)
                 AppLog.put("发现界面更新数据出错", it)
             }.conflate().flowOn(IO).collect {
             }.conflate().flowOn(IO).collect {
-                binding.tvEmptyMsg.isGone = it.isNotEmpty() || searchView.text.isNotEmpty() == true
+                binding.emptyView.isGone = it.isNotEmpty() || searchView.text.isNotEmpty() == true
                 adapter.setItems(it, diffItemCallBack)
                 adapter.setItems(it, diffItemCallBack)
                 delay(500)
                 delay(500)
             }
             }

+ 78 - 0
app/src/main/java/io/legato/kazusa/ui/widget/EmptyMessageView.kt

@@ -0,0 +1,78 @@
+package io.legato.kazusa.ui.widget
+
+import android.content.Context
+import android.util.AttributeSet
+import android.view.Gravity
+import android.widget.LinearLayout
+import android.widget.TextView
+import androidx.annotation.StringRes
+import io.legato.kazusa.R
+import io.legato.kazusa.utils.dpToPx
+import androidx.core.content.withStyledAttributes
+
+class EmptyMessageView @JvmOverloads constructor(
+    context: Context, attrs: AttributeSet? = null
+) : LinearLayout(context, attrs) {
+
+    private val faceTextView: TextView
+    private val messageTextView: TextView
+
+    private val faces = listOf(
+        "(๑`^´๑)", "(´・ᴗ・`)", "(•̀ᴗ•́)و", "(ᵔᴥᵔ)", "(¬‿¬)", "(ಥ﹏ಥ)", "(。•́︿•̀。)"
+    )
+
+    init {
+        orientation = VERTICAL
+        gravity = Gravity.CENTER
+        layoutParams = LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT)
+        setPadding(16.dpToPx(), 16.dpToPx(), 16.dpToPx(), 16.dpToPx())
+
+        post {
+            val faceWidth = faceTextView.width
+            if (faceWidth > 0) {
+                messageTextView.maxWidth = (faceWidth * 2f).toInt()
+            }
+        }
+
+        faceTextView = TextView(context).apply {
+            layoutParams = LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT)
+            gravity = Gravity.CENTER
+            textSize = 32f
+            text = faces.random()
+        }
+
+        messageTextView = TextView(context).apply {
+            layoutParams = LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT).apply {
+                topMargin = 8.dpToPx()
+            }
+            gravity = Gravity.CENTER
+            text = R.string.empty.toString()
+        }
+
+        addView(faceTextView)
+        addView(messageTextView)
+
+        attrs?.let {
+            context.withStyledAttributes(it, R.styleable.EmptyMessageView) {
+                val msg = getString(R.styleable.EmptyMessageView_messageText)
+                messageTextView.text = msg ?: ""
+                faceTextView.text = faces.random()
+            }
+        }
+    }
+
+    /** 设置文字消息 */
+    fun setMessage(@StringRes resId: Int) {
+        messageTextView.setText(resId)
+    }
+
+    fun setMessage(msg: String) {
+        messageTextView.text = msg
+    }
+
+
+    /** 可选:手动刷新随机颜文字 */
+    fun refreshFace() {
+        faceTextView.text = faces.random()
+    }
+}

+ 0 - 327
app/src/main/java/io/legato/kazusa/ui/widget/checkbox/SmoothCheckBox.kt

@@ -1,327 +0,0 @@
-package io.legato.kazusa.ui.widget.checkbox
-
-import android.animation.ValueAnimator
-import android.content.Context
-import android.graphics.*
-import android.util.AttributeSet
-import android.view.View
-import android.view.animation.LinearInterpolator
-import android.widget.Checkable
-import androidx.core.view.postDelayed
-import io.legato.kazusa.R
-import io.legato.kazusa.lib.theme.ThemeStore
-import io.legato.kazusa.utils.dpToPx
-import io.legato.kazusa.utils.getCompatColor
-import kotlin.math.min
-import kotlin.math.pow
-import kotlin.math.roundToInt
-import kotlin.math.sqrt
-
-class SmoothCheckBox @JvmOverloads constructor(
-    context: Context,
-    attrs: AttributeSet? = null
-) : View(context, attrs), Checkable {
-    private var mPaint: Paint
-    private var mTickPaint: Paint
-    private var mFloorPaint: Paint
-    private var mTickPoints: Array<Point>
-    private var mCenterPoint: Point
-    private var mTickPath: Path
-    private var mLeftLineDistance = 0f
-    private var mRightLineDistance = 0f
-    private var mDrewDistance = 0f
-    private var mScaleVal = 1.0f
-    private var mFloorScale = 1.0f
-    private var mWidth = 0
-    private var mAnimDuration = 0
-    private var mStrokeWidth = 0
-    private var mCheckedColor = 0
-    private var mUnCheckedColor = 0
-    private var mFloorColor = 0
-    private var mFloorUnCheckedColor = 0
-    private var mChecked = false
-    private var mTickDrawing = false
-    var onCheckedChangeListener: ((checkBox: SmoothCheckBox, isChecked: Boolean) -> Unit)? = null
-
-    init {
-        val ta = context.obtainStyledAttributes(attrs, R.styleable.SmoothCheckBox)
-        var tickColor = ThemeStore.accentColor(context)
-        //mCheckedColor = context.getCompatColor(R.color.background_menu)
-        //mUnCheckedColor = context.getCompatColor(R.color.background_menu)
-        mFloorColor = context.getCompatColor(R.color.transparent30)
-        tickColor = ta.getColor(R.styleable.SmoothCheckBox_color_tick, tickColor)
-        mAnimDuration = ta.getInt(R.styleable.SmoothCheckBox_duration, DEF_ANIM_DURATION)
-        mFloorColor = ta.getColor(R.styleable.SmoothCheckBox_color_unchecked_stroke, mFloorColor)
-        mCheckedColor = ta.getColor(R.styleable.SmoothCheckBox_color_checked, mCheckedColor)
-        mUnCheckedColor = ta.getColor(R.styleable.SmoothCheckBox_color_unchecked, mUnCheckedColor)
-        mStrokeWidth = ta.getDimensionPixelSize(R.styleable.SmoothCheckBox_stroke_width, 0)
-        ta.recycle()
-        mFloorUnCheckedColor = mFloorColor
-        mTickPaint = Paint(Paint.ANTI_ALIAS_FLAG)
-        mTickPaint.style = Paint.Style.STROKE
-        mTickPaint.strokeCap = Paint.Cap.ROUND
-        mTickPaint.color = tickColor
-        mFloorPaint = Paint(Paint.ANTI_ALIAS_FLAG)
-        mFloorPaint.style = Paint.Style.FILL
-        mFloorPaint.color = mFloorColor
-        mPaint = Paint(Paint.ANTI_ALIAS_FLAG)
-        mPaint.style = Paint.Style.FILL
-        mPaint.color = mCheckedColor
-        mTickPath = Path()
-        mCenterPoint = Point()
-        mTickPoints = arrayOf(Point(), Point(), Point())
-        setOnClickListener {
-            toggle()
-            mTickDrawing = false
-            mDrewDistance = 0f
-            if (isChecked) {
-                startCheckedAnimation()
-            } else {
-                startUnCheckedAnimation()
-            }
-        }
-    }
-
-    override fun isChecked(): Boolean {
-        return mChecked
-    }
-
-    override fun setChecked(checked: Boolean) {
-        mChecked = checked
-        reset()
-        invalidate()
-        onCheckedChangeListener?.invoke(this@SmoothCheckBox, mChecked)
-    }
-
-    override fun toggle() {
-        this.isChecked = !isChecked
-    }
-
-    /**
-     * checked with animation
-     *
-     * @param checked checked
-     * @param animate change with animation
-     */
-    fun setChecked(checked: Boolean, animate: Boolean) {
-        if (animate) {
-            mTickDrawing = false
-            mChecked = checked
-            mDrewDistance = 0f
-            if (checked) {
-                startCheckedAnimation()
-            } else {
-                startUnCheckedAnimation()
-            }
-            onCheckedChangeListener?.invoke(this@SmoothCheckBox, mChecked)
-        } else {
-            this.isChecked = checked
-        }
-    }
-
-    private fun reset() {
-        mTickDrawing = true
-        mFloorScale = 1.0f
-        mScaleVal = if (isChecked) 0f else 1.0f
-        mFloorColor = if (isChecked) mCheckedColor else mFloorUnCheckedColor
-        mDrewDistance = if (isChecked) mLeftLineDistance + mRightLineDistance else 0f
-    }
-
-    private fun measureSize(measureSpec: Int): Int {
-        val defSize: Int = DEF_DRAW_SIZE.dpToPx()
-        val specSize = MeasureSpec.getSize(measureSpec)
-        val specMode = MeasureSpec.getMode(measureSpec)
-        var result = 0
-        when (specMode) {
-            MeasureSpec.UNSPECIFIED, MeasureSpec.AT_MOST -> result = min(defSize, specSize)
-            MeasureSpec.EXACTLY -> result = specSize
-        }
-        return result
-    }
-
-    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
-        super.onMeasure(widthMeasureSpec, heightMeasureSpec)
-        setMeasuredDimension(measureSize(widthMeasureSpec), measureSize(heightMeasureSpec))
-    }
-
-    override fun onLayout(
-        changed: Boolean,
-        left: Int,
-        top: Int,
-        right: Int,
-        bottom: Int
-    ) {
-        mWidth = measuredWidth
-        mStrokeWidth = if (mStrokeWidth == 0) measuredWidth / 10 else mStrokeWidth
-        mStrokeWidth =
-            if (mStrokeWidth > measuredWidth / 5) measuredWidth / 5 else mStrokeWidth
-        mStrokeWidth = if (mStrokeWidth < 3) 3 else mStrokeWidth
-        mCenterPoint.x = mWidth / 2
-        mCenterPoint.y = measuredHeight / 2
-        mTickPoints[0].x = (measuredWidth.toFloat() / 30 * 7).roundToInt()
-        mTickPoints[0].y = (measuredHeight.toFloat() / 30 * 14).roundToInt()
-        mTickPoints[1].x = (measuredWidth.toFloat() / 30 * 13).roundToInt()
-        mTickPoints[1].y = (measuredHeight.toFloat() / 30 * 20).roundToInt()
-        mTickPoints[2].x = (measuredWidth.toFloat() / 30 * 22).roundToInt()
-        mTickPoints[2].y = (measuredHeight.toFloat() / 30 * 10).roundToInt()
-        mLeftLineDistance = sqrt(
-            (mTickPoints[1].x - mTickPoints[0].x.toDouble()).pow(2.0) +
-                    (mTickPoints[1].y - mTickPoints[0].y.toDouble()).pow(2.0)
-        ).toFloat()
-        mRightLineDistance = sqrt(
-            (mTickPoints[2].x - mTickPoints[1].x.toDouble()).pow(2.0) +
-                    (mTickPoints[2].y - mTickPoints[1].y.toDouble()).pow(2.0)
-        ).toFloat()
-        mTickPaint.strokeWidth = mStrokeWidth.toFloat()
-    }
-
-    override fun onDraw(canvas: Canvas) {
-        drawBorder(canvas)
-        drawCenter(canvas)
-        drawTick(canvas)
-    }
-
-    private fun drawCenter(canvas: Canvas) {
-        mPaint.color = mUnCheckedColor
-        val radius = (mCenterPoint.x - mStrokeWidth) * mScaleVal
-        canvas.drawCircle(mCenterPoint.x.toFloat(), mCenterPoint.y.toFloat(), radius, mPaint)
-    }
-
-    private fun drawBorder(canvas: Canvas) {
-        mFloorPaint.color = mFloorColor
-        val radius = mCenterPoint.x
-        canvas.drawCircle(
-            mCenterPoint.x.toFloat(),
-            mCenterPoint.y.toFloat(),
-            radius * mFloorScale,
-            mFloorPaint
-        )
-    }
-
-    private fun drawTick(canvas: Canvas) {
-        if (mTickDrawing && isChecked) {
-            drawTickPath(canvas)
-        }
-    }
-
-    private fun drawTickPath(canvas: Canvas) {
-        mTickPath.reset()
-        // draw left of the tick
-        if (mDrewDistance < mLeftLineDistance) {
-            val step: Float = if (mWidth / 20.0f < 3) 3f else mWidth / 20.0f
-            mDrewDistance += step
-            val stopX =
-                mTickPoints[0].x + (mTickPoints[1].x - mTickPoints[0].x) * mDrewDistance / mLeftLineDistance
-            val stopY =
-                mTickPoints[0].y + (mTickPoints[1].y - mTickPoints[0].y) * mDrewDistance / mLeftLineDistance
-            mTickPath.moveTo(mTickPoints[0].x.toFloat(), mTickPoints[0].y.toFloat())
-            mTickPath.lineTo(stopX, stopY)
-            canvas.drawPath(mTickPath, mTickPaint)
-            if (mDrewDistance > mLeftLineDistance) {
-                mDrewDistance = mLeftLineDistance
-            }
-        } else {
-            mTickPath.moveTo(mTickPoints[0].x.toFloat(), mTickPoints[0].y.toFloat())
-            mTickPath.lineTo(mTickPoints[1].x.toFloat(), mTickPoints[1].y.toFloat())
-            canvas.drawPath(mTickPath, mTickPaint)
-            // draw right of the tick
-            if (mDrewDistance < mLeftLineDistance + mRightLineDistance) {
-                val stopX =
-                    mTickPoints[1].x + (mTickPoints[2].x - mTickPoints[1].x) * (mDrewDistance - mLeftLineDistance) / mRightLineDistance
-                val stopY =
-                    mTickPoints[1].y - (mTickPoints[1].y - mTickPoints[2].y) * (mDrewDistance - mLeftLineDistance) / mRightLineDistance
-                mTickPath.reset()
-                mTickPath.moveTo(mTickPoints[1].x.toFloat(), mTickPoints[1].y.toFloat())
-                mTickPath.lineTo(stopX, stopY)
-                canvas.drawPath(mTickPath, mTickPaint)
-                val step: Float = if (mWidth / 20f < 3) 3f else mWidth / 20f
-                mDrewDistance += step
-            } else {
-                mTickPath.reset()
-                mTickPath.moveTo(mTickPoints[1].x.toFloat(), mTickPoints[1].y.toFloat())
-                mTickPath.lineTo(mTickPoints[2].x.toFloat(), mTickPoints[2].y.toFloat())
-                canvas.drawPath(mTickPath, mTickPaint)
-            }
-        }
-        // invalidate
-        if (mDrewDistance < mLeftLineDistance + mRightLineDistance) {
-            postDelayed(10) { this.postInvalidate() }
-        }
-    }
-
-    private fun startCheckedAnimation() {
-        val animator = ValueAnimator.ofFloat(1.0f, 0f)
-        animator.duration = mAnimDuration / 3 * 2.toLong()
-        animator.interpolator = LinearInterpolator()
-        animator.addUpdateListener { animation: ValueAnimator ->
-            mScaleVal = animation.animatedValue as Float
-            mFloorColor = getGradientColor(
-                mUnCheckedColor,
-                mCheckedColor,
-                1 - mScaleVal
-            )
-            postInvalidate()
-        }
-        animator.start()
-        val floorAnimator = ValueAnimator.ofFloat(1.0f, 0.8f, 1.0f)
-        floorAnimator.duration = mAnimDuration.toLong()
-        floorAnimator.interpolator = LinearInterpolator()
-        floorAnimator.addUpdateListener { animation: ValueAnimator ->
-            mFloorScale = animation.animatedValue as Float
-            postInvalidate()
-        }
-        floorAnimator.start()
-        drawTickDelayed()
-    }
-
-    private fun startUnCheckedAnimation() {
-        val animator = ValueAnimator.ofFloat(0f, 1.0f)
-        animator.duration = mAnimDuration.toLong()
-        animator.interpolator = LinearInterpolator()
-        animator.addUpdateListener { animation: ValueAnimator ->
-            mScaleVal = animation.animatedValue as Float
-            mFloorColor = getGradientColor(
-                mCheckedColor,
-                mFloorUnCheckedColor,
-                mScaleVal
-            )
-            postInvalidate()
-        }
-        animator.start()
-        val floorAnimator = ValueAnimator.ofFloat(1.0f, 0.8f, 1.0f)
-        floorAnimator.duration = mAnimDuration.toLong()
-        floorAnimator.interpolator = LinearInterpolator()
-        floorAnimator.addUpdateListener { animation: ValueAnimator ->
-            mFloorScale = animation.animatedValue as Float
-            postInvalidate()
-        }
-        floorAnimator.start()
-    }
-
-    private fun drawTickDelayed() {
-        postDelayed(mAnimDuration.toLong()) {
-            mTickDrawing = true
-            postInvalidate()
-        }
-    }
-
-    companion object {
-        private const val DEF_DRAW_SIZE = 25
-        private const val DEF_ANIM_DURATION = 300
-        private fun getGradientColor(startColor: Int, endColor: Int, percent: Float): Int {
-            val startA = Color.alpha(startColor)
-            val startR = Color.red(startColor)
-            val startG = Color.green(startColor)
-            val startB = Color.blue(startColor)
-            val endA = Color.alpha(endColor)
-            val endR = Color.red(endColor)
-            val endG = Color.green(endColor)
-            val endB = Color.blue(endColor)
-            val currentA = (startA * (1 - percent) + endA * percent).toInt()
-            val currentR = (startR * (1 - percent) + endR * percent).toInt()
-            val currentG = (startG * (1 - percent) + endG * percent).toInt()
-            val currentB = (startB * (1 - percent) + endB * percent).toInt()
-            return Color.argb(currentA, currentR, currentG, currentB)
-        }
-    }
-}

+ 3 - 3
app/src/main/java/io/legato/kazusa/ui/widget/text/PrimaryTextView.kt

@@ -12,7 +12,7 @@ import io.legato.kazusa.lib.theme.ThemeStore
 class PrimaryTextView(context: Context, attrs: AttributeSet) :
 class PrimaryTextView(context: Context, attrs: AttributeSet) :
     AppCompatTextView(context, attrs) {
     AppCompatTextView(context, attrs) {
 
 
-    init {
-        setTextColor(ThemeStore.textColorPrimary(context))
-    }
+//    init {
+//        setTextColor(ThemeStore.textColorPrimary(context))
+//    }
 }
 }

+ 0 - 88
app/src/main/java/io/legato/kazusa/ui/widget/text/StrokeTextView.kt

@@ -1,88 +0,0 @@
-package io.legato.kazusa.ui.widget.text
-
-import android.content.Context
-import android.util.AttributeSet
-import androidx.appcompat.widget.AppCompatTextView
-import io.legato.kazusa.R
-import io.legato.kazusa.lib.theme.*
-import io.legato.kazusa.utils.dpToPx
-import io.legato.kazusa.utils.getCompatColor
-
-@Suppress("unused")
-open class StrokeTextView(context: Context, attrs: AttributeSet?) :
-    AppCompatTextView(context, attrs) {
-
-    private var radius = 1.dpToPx()
-    private val isBottomBackground: Boolean
-
-    init {
-        val typedArray = context.obtainStyledAttributes(attrs, R.styleable.StrokeTextView)
-        radius = typedArray.getDimensionPixelOffset(R.styleable.StrokeTextView_radius, radius)
-        isBottomBackground =
-            typedArray.getBoolean(R.styleable.StrokeTextView_isBottomBackground, false)
-        typedArray.recycle()
-        upBackground()
-    }
-
-    fun setRadius(radius: Int) {
-        this.radius = radius.dpToPx()
-        upBackground()
-    }
-
-    private fun upBackground() {
-        when {
-            isInEditMode -> {
-                background = Selector.shapeBuild()
-                    .setCornerRadius(radius)
-                    .setStrokeWidth(1.dpToPx())
-                    .setDisabledStrokeColor(context.getCompatColor(R.color.md_grey_500))
-                    .setDefaultStrokeColor(context.getCompatColor(R.color.secondaryText))
-                    //.setSelectedStrokeColor(context.getCompatColor(R.color.accent))
-                    .setPressedBgColor(context.getCompatColor(R.color.transparent30))
-                    .create()
-                setTextColor(
-                    Selector.colorBuild()
-                        .setDefaultColor(context.getCompatColor(R.color.secondaryText))
-                        //.setSelectedColor(context.getCompatColor(R.color.accent))
-                        .setDisabledColor(context.getCompatColor(R.color.md_grey_500))
-                        .create()
-                )
-            }
-            isBottomBackground -> {
-                //val isLight = ColorUtils.isColorLight(context.bottomBackground)
-                background = Selector.shapeBuild()
-                    .setCornerRadius(radius)
-                    .setStrokeWidth(1.dpToPx())
-                    .setDisabledStrokeColor(context.getCompatColor(R.color.md_grey_500))
-//                    .setDefaultStrokeColor(context.getPrimaryTextColor(isLight))
-//                    .setSelectedStrokeColor(context.accentColor)
-                    .setPressedBgColor(context.getCompatColor(R.color.transparent30))
-                    .create()
-                setTextColor(
-                    Selector.colorBuild()
-//                        .setDefaultColor(context.getPrimaryTextColor(isLight))
-//                        .setSelectedColor(context.accentColor)
-                        .setDisabledColor(context.getCompatColor(R.color.md_grey_500))
-                        .create()
-                )
-            }
-            else -> {
-                background = Selector.shapeBuild()
-                    .setCornerRadius(radius)
-                    .setStrokeWidth(1.dpToPx())
-                    .setDisabledStrokeColor(context.getCompatColor(R.color.md_grey_500))
-                    .setDefaultStrokeColor(ThemeStore.textColorSecondary(context))
-                    .setSelectedStrokeColor(ThemeStore.accentColor(context))
-                    .setPressedBgColor(context.getCompatColor(R.color.transparent30))
-                    .create()
-                setTextColor(
-                    Selector.colorBuild()
-                        .setDefaultColor(ThemeStore.textColorSecondary(context))
-                        .setSelectedColor(ThemeStore.accentColor(context))
-                        .setDisabledColor(context.getCompatColor(R.color.md_grey_500))
-                        .create()
-                )
-            }
-        }
-    }
-}

+ 1 - 0
app/src/main/res/layout/activity_import_book.xml

@@ -49,6 +49,7 @@
         android:id="@+id/refresh_progress_bar"
         android:id="@+id/refresh_progress_bar"
         android:layout_width="match_parent"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:layout_height="wrap_content"
+        android:visibility="gone"
         android:indeterminate="true"
         android:indeterminate="true"
         app:layout_constraintTop_toBottomOf="@id/lay_top" />
         app:layout_constraintTop_toBottomOf="@id/lay_top" />
 
 

+ 3 - 19
app/src/main/res/layout/dialog_book_change_source.xml

@@ -79,29 +79,13 @@
 
 
     </LinearLayout>
     </LinearLayout>
 
 
-
-    <LinearLayout
+    <io.legato.kazusa.ui.widget.EmptyMessageView
         android:id="@+id/tv_empty_msg"
         android:id="@+id/tv_empty_msg"
         android:layout_width="wrap_content"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
         android:layout_height="wrap_content"
-        android:layout_margin="16dp"
-        android:gravity="center"
+        android:visibility="invisible"
         android:layout_gravity="center"
         android:layout_gravity="center"
-        android:orientation="vertical"
-        android:visibility="gone">
-
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:text="(๑`^´๑)"
-            android:textSize="24sp" />
-
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:layout_margin="8dp"
-            android:text="还没有源!" />
-    </LinearLayout>
+        app:messageText="还没有源!"/>
 
 
     <androidx.recyclerview.widget.RecyclerView
     <androidx.recyclerview.widget.RecyclerView
         android:id="@+id/recycler_view"
         android:id="@+id/recycler_view"

+ 6 - 5
app/src/main/res/layout/dialog_recycler_view.xml

@@ -28,16 +28,17 @@
             android:id="@+id/rotate_loading"
             android:id="@+id/rotate_loading"
             android:layout_width="wrap_content"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:layout_height="wrap_content"
+            android:visibility="gone"
             android:layout_margin="32dp"
             android:layout_margin="32dp"
             android:layout_gravity="center"/>
             android:layout_gravity="center"/>
 
 
-        <TextView
-            android:id="@+id/tv_msg"
-            android:layout_width="match_parent"
+        <io.legato.kazusa.ui.widget.EmptyMessageView
+            android:id="@+id/emptyView"
+            android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:layout_height="wrap_content"
-            android:padding="16dp"
+            android:visibility="invisible"
             android:layout_gravity="center"
             android:layout_gravity="center"
-            android:visibility="gone" />
+            app:messageText="@string/empty"/>
 
 
     </FrameLayout>
     </FrameLayout>
 
 

+ 2 - 2
app/src/main/res/layout/dialog_select_section_export.xml

@@ -17,7 +17,7 @@
             android:layout_marginTop="12dp"
             android:layout_marginTop="12dp"
             android:orientation="horizontal">
             android:orientation="horizontal">
 
 
-            <io.legato.kazusa.ui.widget.checkbox.SmoothCheckBox
+            <com.google.android.material.checkbox.MaterialCheckBox
                 android:id="@+id/cb_all_export"
                 android:id="@+id/cb_all_export"
                 android:layout_width="20dp"
                 android:layout_width="20dp"
                 android:layout_height="20dp"
                 android:layout_height="20dp"
@@ -40,7 +40,7 @@
             android:layout_marginTop="12dp"
             android:layout_marginTop="12dp"
             android:orientation="horizontal">
             android:orientation="horizontal">
 
 
-            <io.legato.kazusa.ui.widget.checkbox.SmoothCheckBox
+            <com.google.android.material.checkbox.MaterialCheckBox
                 android:id="@+id/cb_select_export"
                 android:id="@+id/cb_select_export"
                 android:layout_width="20dp"
                 android:layout_width="20dp"
                 android:layout_height="20dp"
                 android:layout_height="20dp"

+ 6 - 19
app/src/main/res/layout/fragment_books.xml

@@ -2,7 +2,8 @@
 <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
 <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:tools="http://schemas.android.com/tools"
     xmlns:tools="http://schemas.android.com/tools"
     android:layout_width="match_parent"
     android:layout_width="match_parent"
-    android:layout_height="match_parent">
+    android:layout_height="match_parent"
+    xmlns:app="http://schemas.android.com/apk/res-auto">
 
 
     <androidx.swiperefreshlayout.widget.SwipeRefreshLayout
     <androidx.swiperefreshlayout.widget.SwipeRefreshLayout
         android:id="@+id/refresh_layout"
         android:id="@+id/refresh_layout"
@@ -17,27 +18,13 @@
 
 
     </androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
     </androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
 
 
-    <LinearLayout
-        android:id="@+id/tv_empty_msg"
+    <io.legato.kazusa.ui.widget.EmptyMessageView
+        android:id="@+id/emptyView"
         android:layout_width="wrap_content"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
         android:layout_height="wrap_content"
-        android:visibility="gone"
-        android:orientation="vertical"
+        android:visibility="visible"
         android:layout_gravity="center"
         android:layout_gravity="center"
-        android:layout_margin="16dp"
-        android:gravity="center">
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:text="(๑`^´๑)"
-            android:textSize="32sp" />
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:layout_margin="8dp"
-            android:text="@string/bookshelf_empty" />
-    </LinearLayout>
-
+        app:messageText="@string/bookshelf_empty"/>
 
 
 </FrameLayout>
 </FrameLayout>
 
 

+ 5 - 18
app/src/main/res/layout/fragment_explore.xml

@@ -55,29 +55,16 @@
         tools:listitem="@layout/item_find_book"
         tools:listitem="@layout/item_find_book"
         app:layout_behavior="@string/appbar_scrolling_view_behavior"/>
         app:layout_behavior="@string/appbar_scrolling_view_behavior"/>
 
 
-    <LinearLayout
-        android:id="@+id/tv_empty_msg"
+    <io.legato.kazusa.ui.widget.EmptyMessageView
+        android:id="@+id/emptyView"
         android:layout_width="wrap_content"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
         android:layout_height="wrap_content"
-        app:layout_anchor="@id/app_bar"
+        app:layout_anchor="@id/rv_find"
         app:layout_anchorGravity="center"
         app:layout_anchorGravity="center"
-        app:layout_behavior="@string/appbar_scrolling_view_behavior"
         android:visibility="gone"
         android:visibility="gone"
         android:orientation="vertical"
         android:orientation="vertical"
         android:layout_gravity="center"
         android:layout_gravity="center"
-        android:layout_margin="16dp"
-        android:gravity="center">
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:text="(っ˘ω˘ς )"
-            android:textSize="32sp" />
-        <TextView
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:layout_margin="8dp"
-            android:gravity="center"
-            android:text="@string/explore_empty" />
-    </LinearLayout>
+        android:gravity="center"
+        app:messageText="@string/explore_empty"/>
 
 
 </androidx.coordinatorlayout.widget.CoordinatorLayout>
 </androidx.coordinatorlayout.widget.CoordinatorLayout>

+ 5 - 0
app/src/main/res/values-zh/arrays.xml

@@ -131,4 +131,9 @@
         <item>关闭</item>
         <item>关闭</item>
     </string-array>
     </string-array>
 
 
+    <string-array name="customMode">
+        <item>全局</item>
+        <item>仅强调色</item>
+    </string-array>
+
 </resources>
 </resources>

+ 2 - 2
app/src/main/res/values-zh/strings.xml

@@ -613,7 +613,7 @@
     <string name="dur_pos">当前位置:</string>
     <string name="dur_pos">当前位置:</string>
     <string name="precision_search">精准搜索</string>
     <string name="precision_search">精准搜索</string>
     <string name="service_starting">正在启动服务</string>
     <string name="service_starting">正在启动服务</string>
-    <string name="empty">空</string>
+    <string name="empty">内容为空</string>
     <string name="file_chooser">文件选择</string>
     <string name="file_chooser">文件选择</string>
     <string name="folder_chooser">文件夹选择</string>
     <string name="folder_chooser">文件夹选择</string>
     <string name="bottom_line">我是有底线的</string>
     <string name="bottom_line">我是有底线的</string>
@@ -786,7 +786,7 @@
     <string name="import_str">导入</string>
     <string name="import_str">导入</string>
     <string name="export_str">导出</string>
     <string name="export_str">导出</string>
     <string name="save_theme_config">保存主题配置</string>
     <string name="save_theme_config">保存主题配置</string>
-    <string name="save_day_theme_summary">保存白天主题配置以供调用和分享</string>
+    <string name="save_day_theme_summary">保存主题配置以供调用和分享</string>
     <string name="save_night_theme_summary">保存夜间主题配置以供调用和分享</string>
     <string name="save_night_theme_summary">保存夜间主题配置以供调用和分享</string>
     <string name="theme_list">主题列表</string>
     <string name="theme_list">主题列表</string>
     <string name="theme_list_summary">使用、保存、导入或分享主题</string>
     <string name="theme_list_summary">使用、保存、导入或分享主题</string>

+ 6 - 0
app/src/main/res/values/array_values.xml

@@ -39,6 +39,7 @@
         <item>9</item>
         <item>9</item>
         <item>10</item>
         <item>10</item>
         <item>11</item>
         <item>11</item>
+        <item>12</item>
     </string-array>
     </string-array>
 
 
     <string-array name="screen_direction_value">
     <string-array name="screen_direction_value">
@@ -75,4 +76,9 @@
         <item>off</item>
         <item>off</item>
     </string-array>
     </string-array>
 
 
+    <string-array name="customMode_value">
+        <item>global</item>
+        <item>accent</item>
+    </string-array>
+
 </resources>
 </resources>

+ 6 - 0
app/src/main/res/values/arrays.xml

@@ -66,6 +66,7 @@
         <item>千禧年</item>
         <item>千禧年</item>
         <item>隐海修会</item>
         <item>隐海修会</item>
         <item>乐队</item>
         <item>乐队</item>
+		<item>自定义</item>
         <item>透明</item>
         <item>透明</item>
 	</string-array>
 	</string-array>
 
 
@@ -163,6 +164,11 @@
 		<item>Off</item>
 		<item>Off</item>
 	</string-array>
 	</string-array>
 
 
+	<string-array name="customMode">
+		<item>Global</item>
+		<item>Accent</item>
+	</string-array>
+
 	<string-array name="rule_type">
 	<string-array name="rule_type">
 		<item>BookSource</item>
 		<item>BookSource</item>
 		<item>RssSource</item>
 		<item>RssSource</item>

+ 4 - 0
app/src/main/res/values/attrs.xml

@@ -254,4 +254,8 @@
         <attr name="tipText" format="string" />
         <attr name="tipText" format="string" />
     </declare-styleable>
     </declare-styleable>
 
 
+    <declare-styleable name="EmptyMessageView">
+        <attr name="messageText" format="string" />
+    </declare-styleable>
+
 </resources>
 </resources>