Update default favicon drawable

This commit is contained in:
Koitharu
2023-07-01 17:44:16 +03:00
parent a726b4f499
commit 55fdd6b7b1
7 changed files with 87 additions and 21 deletions

View File

@@ -5,45 +5,67 @@ import android.graphics.Canvas
import android.graphics.Color
import android.graphics.ColorFilter
import android.graphics.Paint
import android.graphics.Path
import android.graphics.PixelFormat
import android.graphics.Rect
import android.graphics.RectF
import android.graphics.drawable.Drawable
import androidx.annotation.StyleRes
import androidx.core.content.withStyledAttributes
import androidx.core.graphics.ColorUtils
import androidx.core.graphics.withClip
import com.google.android.material.color.MaterialColors
import org.koitharu.kotatsu.R
import kotlin.math.absoluteValue
class FaviconFallbackDrawable(
class FaviconDrawable(
context: Context,
@StyleRes styleResId: Int,
name: String,
) : Drawable() {
private val paint = Paint(Paint.ANTI_ALIAS_FLAG)
private var colorBackground = Color.WHITE
private var colorStroke = Color.LTGRAY
private val letter = name.take(1).uppercase()
private val color = MaterialColors.harmonizeWithPrimary(context, colorOfString(name))
private var cornerSize = 0f
private var colorForeground = Color.DKGRAY
private val textBounds = Rect()
private val tempRect = Rect()
private val boundsF = RectF()
private val clipPath = Path()
init {
paint.style = Paint.Style.FILL
context.withStyledAttributes(styleResId, R.styleable.FaviconFallbackDrawable) {
colorBackground = getColor(R.styleable.FaviconFallbackDrawable_backgroundColor, colorBackground)
colorStroke = getColor(R.styleable.FaviconFallbackDrawable_strokeColor, colorStroke)
cornerSize = getDimension(R.styleable.FaviconFallbackDrawable_cornerSize, cornerSize)
paint.strokeWidth = getDimension(R.styleable.FaviconFallbackDrawable_strokeWidth, 0f) * 2f
}
paint.textAlign = Paint.Align.CENTER
paint.isFakeBoldText = true
colorForeground = MaterialColors.harmonize(colorOfString(name), colorBackground)
}
override fun draw(canvas: Canvas) {
val cx = bounds.exactCenterX()
paint.color = color
canvas.drawPaint(paint)
paint.color = Color.WHITE
val ty = bounds.height() / 2f + textBounds.height() / 2f - textBounds.bottom
canvas.drawText(letter, cx, ty, paint)
if (cornerSize > 0f) {
canvas.withClip(clipPath) {
doDraw(canvas)
}
} else {
doDraw(canvas)
}
}
override fun onBoundsChange(bounds: Rect) {
super.onBoundsChange(bounds)
boundsF.set(bounds)
val innerWidth = bounds.width() - (paint.strokeWidth * 2f)
paint.textSize = getTextSizeForWidth(innerWidth, letter) * 0.5f
paint.getTextBounds(letter, 0, letter.length, textBounds)
invalidateSelf()
clipPath.reset()
clipPath.addRoundRect(boundsF, cornerSize, cornerSize, Path.Direction.CW)
clipPath.close()
}
override fun setAlpha(alpha: Int) {
@@ -58,6 +80,24 @@ class FaviconFallbackDrawable(
@Deprecated("Deprecated in Java")
override fun getOpacity() = PixelFormat.TRANSPARENT
private fun doDraw(canvas: Canvas) {
// background
paint.color = colorBackground
paint.style = Paint.Style.FILL
canvas.drawPaint(paint)
// letter
paint.color = colorForeground
val cx = (boundsF.left + boundsF.right) * 0.6f
val ty = boundsF.bottom * 0.7f + textBounds.height() * 0.5f - textBounds.bottom
canvas.drawText(letter, cx, ty, paint)
if (paint.strokeWidth > 0f) {
// stroke
paint.color = colorStroke
paint.style = Paint.Style.STROKE
canvas.drawPath(clipPath, paint)
}
}
private fun getTextSizeForWidth(width: Float, text: String): Float {
val testTextSize = 48f
paint.textSize = testTextSize

View File

@@ -8,7 +8,7 @@ import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegate
import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegateViewBinding
import org.koitharu.kotatsu.R
import org.koitharu.kotatsu.core.parser.favicon.faviconUri
import org.koitharu.kotatsu.core.ui.image.FaviconFallbackDrawable
import org.koitharu.kotatsu.core.ui.image.FaviconDrawable
import org.koitharu.kotatsu.core.ui.list.AdapterDelegateClickListenerAdapter
import org.koitharu.kotatsu.core.ui.list.OnListItemClickListener
import org.koitharu.kotatsu.core.util.ext.disposeImageRequest
@@ -76,7 +76,7 @@ fun exploreSourceListItemAD(
bind {
binding.textViewTitle.text = item.source.title
val fallbackIcon = FaviconFallbackDrawable(context, item.source.name)
val fallbackIcon = FaviconDrawable(context, R.style.FaviconDrawable_Small, item.source.name)
binding.imageViewIcon.newImageRequest(lifecycleOwner, item.source.faviconUri())?.run {
fallback(fallbackIcon)
placeholder(fallbackIcon)
@@ -107,7 +107,7 @@ fun exploreSourceGridItemAD(
bind {
binding.textViewTitle.text = item.source.title
val fallbackIcon = FaviconFallbackDrawable(context, item.source.name)
val fallbackIcon = FaviconDrawable(context, R.style.FaviconDrawable_Large, item.source.name)
binding.imageViewIcon.newImageRequest(lifecycleOwner, item.source.faviconUri())?.run {
fallback(fallbackIcon)
placeholder(fallbackIcon)

View File

@@ -3,8 +3,9 @@ package org.koitharu.kotatsu.search.ui.suggestion.adapter
import androidx.lifecycle.LifecycleOwner
import coil.ImageLoader
import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegateViewBinding
import org.koitharu.kotatsu.R
import org.koitharu.kotatsu.core.parser.favicon.faviconUri
import org.koitharu.kotatsu.core.ui.image.FaviconFallbackDrawable
import org.koitharu.kotatsu.core.ui.image.FaviconDrawable
import org.koitharu.kotatsu.core.util.ext.disposeImageRequest
import org.koitharu.kotatsu.core.util.ext.enqueueWith
import org.koitharu.kotatsu.core.util.ext.newImageRequest
@@ -31,7 +32,7 @@ fun searchSuggestionSourceAD(
bind {
binding.textViewTitle.text = item.source.title
binding.switchLocal.isChecked = item.isEnabled
val fallbackIcon = FaviconFallbackDrawable(context, item.source.name)
val fallbackIcon = FaviconDrawable(context, R.style.FaviconDrawable_Small, item.source.name)
binding.imageViewCover.newImageRequest(lifecycleOwner, item.source.faviconUri())?.run {
fallback(fallbackIcon)
placeholder(fallbackIcon)

View File

@@ -9,7 +9,7 @@ import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegate
import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegateViewBinding
import org.koitharu.kotatsu.R
import org.koitharu.kotatsu.core.parser.favicon.faviconUri
import org.koitharu.kotatsu.core.ui.image.FaviconFallbackDrawable
import org.koitharu.kotatsu.core.ui.image.FaviconDrawable
import org.koitharu.kotatsu.core.ui.list.OnTipCloseListener
import org.koitharu.kotatsu.core.util.ext.crossfade
import org.koitharu.kotatsu.core.util.ext.disposeImageRequest
@@ -66,7 +66,7 @@ fun sourceConfigItemCheckableDelegate(
binding.textViewTitle.text = item.source.title
binding.switchToggle.isChecked = item.isEnabled
binding.textViewDescription.textAndVisible = item.summary
val fallbackIcon = FaviconFallbackDrawable(context, item.source.name)
val fallbackIcon = FaviconDrawable(context, R.style.FaviconDrawable_Small, item.source.name)
binding.imageViewIcon.newImageRequest(lifecycleOwner, item.source.faviconUri())?.run {
crossfade(context)
error(fallbackIcon)
@@ -107,7 +107,7 @@ fun sourceConfigItemDelegate2(
binding.imageViewRemove.isVisible = item.isEnabled
binding.imageViewConfig.isVisible = item.isEnabled
binding.textViewDescription.textAndVisible = item.summary
val fallbackIcon = FaviconFallbackDrawable(context, item.source.name)
val fallbackIcon = FaviconDrawable(context, R.style.FaviconDrawable_Small, item.source.name)
binding.imageViewIcon.newImageRequest(lifecycleOwner, item.source.faviconUri())?.run {
crossfade(context)
error(fallbackIcon)

View File

@@ -18,8 +18,11 @@
android:layout_height="72dp"
android:background="?colorControlHighlight"
android:labelFor="@id/textView_title"
android:padding="1dp"
android:scaleType="fitCenter"
app:shapeAppearance="?shapeAppearanceCornerMedium"
app:strokeColor="?colorOutline"
app:strokeWidth="1dp"
tools:src="@tools:sample/avatars" />
<TextView

View File

@@ -116,9 +116,16 @@
<attr name="shapeAppearance" />
<attr name="shapeAppearanceOverlay" />
<attr name="cardBackgroundColor" />
<attr name="strokeWidth"/>
<attr name="strokeWidth" />
<attr name="strokeColor" />
<attr name="elevation" />
</declare-styleable>
</declare-styleable>
<declare-styleable name="FaviconFallbackDrawable">
<attr name="backgroundColor" />
<attr name="strokeColor" />
<attr name="strokeWidth" />
<attr name="cornerSize" />
</declare-styleable>
</resources>

View File

@@ -287,7 +287,7 @@
<item name="android:selectable">false</item>
</style>
<!-- Progress drawable -->
<!-- Drawable -->
<style name="ProgressDrawable">
<item name="android:fillAlpha">1</item>
@@ -299,4 +299,19 @@
<item name="autoFitTextSize">true</item>
</style>
<style name="FaviconDrawable">
<item name="backgroundColor">?colorBackgroundFloating</item>
<item name="strokeColor">?colorOutline</item>
</style>
<style name="FaviconDrawable.Small">
<item name="strokeWidth">1dp</item>
<item name="cornerSize">8dp</item>
</style>
<style name="FaviconDrawable.Large">
<item name="strokeWidth">1dp</item>
<item name="cornerSize">12dp</item>
</style>
</resources>