Browse Source

Fix mentions font weight and horizontal padding (#2025)

* Fix mentions font weight and horizontal padding

---------

Co-authored-by: ElementBot <benoitm+elementbot@element.io>
pull/2029/head
Jorge Martin Espinosa 9 months ago committed by GitHub
parent
commit
80408a807c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 1
      changelog.d/1449.bugfix
  2. 42
      libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/TextSyleToTypeface.kt
  3. 12
      libraries/textcomposer/impl/src/main/kotlin/io/element/android/libraries/textcomposer/mentions/MentionSpan.kt
  4. 30
      libraries/textcomposer/impl/src/main/kotlin/io/element/android/libraries/textcomposer/mentions/MentionSpanProvider.kt
  5. BIN
      tests/uitests/src/test/snapshots/images/ui_S_t[l.textcomposer.mentions_MentionSpan_null_MentionSpan-Day-18_19_null,NEXUS_5,1.0,en].png
  6. BIN
      tests/uitests/src/test/snapshots/images/ui_S_t[l.textcomposer.mentions_MentionSpan_null_MentionSpan-Night-18_20_null,NEXUS_5,1.0,en].png

1
changelog.d/1449.bugfix

@ -0,0 +1 @@ @@ -0,0 +1 @@
Adjust mention pills font weight and horizontal padding

42
libraries/designsystem/src/main/kotlin/io/element/android/libraries/designsystem/text/TextSyleToTypeface.kt

@ -0,0 +1,42 @@ @@ -0,0 +1,42 @@
/*
* Copyright (c) 2023 New Vector Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.element.android.libraries.designsystem.text
import android.graphics.Typeface
import androidx.compose.runtime.Composable
import androidx.compose.runtime.State
import androidx.compose.runtime.remember
import androidx.compose.ui.platform.LocalFontFamilyResolver
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.font.FontFamily
import androidx.compose.ui.text.font.FontStyle
import androidx.compose.ui.text.font.FontSynthesis
import androidx.compose.ui.text.font.FontWeight
@Composable
fun TextStyle.rememberTypeface(): State<Typeface> {
val resolver: FontFamily.Resolver = LocalFontFamilyResolver.current
@Suppress("UNCHECKED_CAST")
return remember(resolver, this) {
resolver.resolve(
fontFamily = fontFamily,
fontWeight = fontWeight ?: FontWeight.Normal,
fontStyle = fontStyle ?: FontStyle.Normal,
fontSynthesis = fontSynthesis ?: FontSynthesis.All,
)
} as State<Typeface>
}

12
libraries/textcomposer/impl/src/main/kotlin/io/element/android/libraries/textcomposer/mentions/MentionSpan.kt

@ -19,6 +19,7 @@ package io.element.android.libraries.textcomposer.mentions @@ -19,6 +19,7 @@ package io.element.android.libraries.textcomposer.mentions
import android.graphics.Canvas
import android.graphics.Paint
import android.graphics.RectF
import android.graphics.Typeface
import android.text.style.ReplacementSpan
import kotlin.math.roundToInt
@ -26,6 +27,9 @@ class MentionSpan( @@ -26,6 +27,9 @@ class MentionSpan(
val type: Type,
val backgroundColor: Int,
val textColor: Int,
val startPadding: Int,
val endPadding: Int,
val typeface: Typeface = Typeface.DEFAULT,
) : ReplacementSpan() {
override fun getSize(paint: Paint, text: CharSequence?, start: Int, end: Int, fm: Paint.FontMetricsInt?): Int {
@ -34,7 +38,8 @@ class MentionSpan( @@ -34,7 +38,8 @@ class MentionSpan(
if (mentionText != text.toString()) {
actualEnd = end + 1
}
return paint.measureText(mentionText, start, actualEnd).roundToInt() + 40
paint.typeface = typeface
return paint.measureText(mentionText, start, actualEnd).roundToInt() + startPadding + endPadding
}
override fun draw(canvas: Canvas, text: CharSequence?, start: Int, end: Int, x: Float, top: Int, y: Int, bottom: Int, paint: Paint) {
@ -46,11 +51,12 @@ class MentionSpan( @@ -46,11 +51,12 @@ class MentionSpan(
val textWidth = paint.measureText(mentionText, start, actualEnd)
// Extra vertical space to add below the baseline (y). This helps us center the span vertically
val extraVerticalSpace = y + paint.ascent() + paint.descent() - top
val rect = RectF(x, top.toFloat(), x + textWidth + 40, y.toFloat() + extraVerticalSpace)
val rect = RectF(x, top.toFloat(), x + textWidth + startPadding + endPadding, y.toFloat() + extraVerticalSpace)
paint.color = backgroundColor
canvas.drawRoundRect(rect, rect.height() / 2, rect.height() / 2, paint)
paint.color = textColor
canvas.drawText(mentionText, start, actualEnd, x + 20, y.toFloat(), paint)
paint.typeface = typeface
canvas.drawText(mentionText, start, actualEnd, x + startPadding, y.toFloat(), paint)
}
private fun getActualText(text: CharSequence?, start: Int): String {

30
libraries/textcomposer/impl/src/main/kotlin/io/element/android/libraries/textcomposer/mentions/MentionSpanProvider.kt

@ -17,16 +17,24 @@ @@ -17,16 +17,24 @@
package io.element.android.libraries.textcomposer.mentions
import android.graphics.Color
import android.graphics.Typeface
import android.view.ViewGroup
import android.widget.TextView
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.runtime.Composable
import androidx.compose.runtime.Stable
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.ui.graphics.toArgb
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.unit.dp
import androidx.compose.ui.viewinterop.AndroidView
import androidx.core.text.buildSpannedString
import io.element.android.compound.theme.ElementTheme
import io.element.android.libraries.designsystem.preview.ElementPreview
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.text.rememberTypeface
import io.element.android.libraries.designsystem.theme.currentUserMentionPillBackground
import io.element.android.libraries.designsystem.theme.currentUserMentionPillText
import io.element.android.libraries.designsystem.theme.mentionPillBackground
@ -34,7 +42,6 @@ import io.element.android.libraries.designsystem.theme.mentionPillText @@ -34,7 +42,6 @@ import io.element.android.libraries.designsystem.theme.mentionPillText
import io.element.android.libraries.matrix.api.core.SessionId
import io.element.android.libraries.matrix.api.permalink.PermalinkData
import io.element.android.libraries.matrix.api.permalink.PermalinkParser
import io.element.android.compound.theme.ElementTheme
@Stable
class MentionSpanProvider(
@ -44,6 +51,10 @@ class MentionSpanProvider( @@ -44,6 +51,10 @@ class MentionSpanProvider(
private var otherTextColor: Int = 0,
private var otherBackgroundColor: Int = Color.WHITE,
) {
private val paddingValues = PaddingValues(start = 4.dp, end = 6.dp)
private val paddingValuesPx = mutableStateOf(0 to 0)
private val typeface = mutableStateOf(Typeface.DEFAULT)
@Suppress("ComposableNaming")
@Composable
@ -52,10 +63,18 @@ class MentionSpanProvider( @@ -52,10 +63,18 @@ class MentionSpanProvider(
currentUserBackgroundColor = ElementTheme.colors.currentUserMentionPillBackground.toArgb()
otherTextColor = ElementTheme.colors.mentionPillText.toArgb()
otherBackgroundColor = ElementTheme.colors.mentionPillBackground.toArgb()
typeface.value = ElementTheme.typography.fontBodyLgMedium.rememberTypeface().value
with(LocalDensity.current) {
val leftPadding = paddingValues.calculateLeftPadding(LocalLayoutDirection.current).roundToPx()
val rightPadding = paddingValues.calculateRightPadding(LocalLayoutDirection.current).roundToPx()
paddingValuesPx.value = leftPadding to rightPadding
}
}
fun getMentionSpanFor(text: String, url: String): MentionSpan {
val permalinkData = PermalinkParser.parse(url)
val (startPaddingPx, endPaddingPx) = paddingValuesPx.value
return when {
permalinkData is PermalinkData.UserLink -> {
val isCurrentUser = permalinkData.userId == currentSessionId.value
@ -63,6 +82,9 @@ class MentionSpanProvider( @@ -63,6 +82,9 @@ class MentionSpanProvider(
type = MentionSpan.Type.USER,
backgroundColor = if (isCurrentUser) currentUserBackgroundColor else otherBackgroundColor,
textColor = if (isCurrentUser) currentUserTextColor else otherTextColor,
startPadding = startPaddingPx,
endPadding = endPaddingPx,
typeface = typeface.value,
)
}
text == "@room" && permalinkData is PermalinkData.FallbackLink -> {
@ -70,6 +92,9 @@ class MentionSpanProvider( @@ -70,6 +92,9 @@ class MentionSpanProvider(
type = MentionSpan.Type.USER,
backgroundColor = otherBackgroundColor,
textColor = otherTextColor,
startPadding = startPaddingPx,
endPadding = endPaddingPx,
typeface = typeface.value,
)
}
else -> {
@ -77,6 +102,9 @@ class MentionSpanProvider( @@ -77,6 +102,9 @@ class MentionSpanProvider(
type = MentionSpan.Type.ROOM,
backgroundColor = otherBackgroundColor,
textColor = otherTextColor,
startPadding = startPaddingPx,
endPadding = endPaddingPx,
typeface = typeface.value,
)
}
}

BIN
tests/uitests/src/test/snapshots/images/ui_S_t[l.textcomposer.mentions_MentionSpan_null_MentionSpan-Day-18_19_null,NEXUS_5,1.0,en].png (Stored with Git LFS)

Binary file not shown.

BIN
tests/uitests/src/test/snapshots/images/ui_S_t[l.textcomposer.mentions_MentionSpan_null_MentionSpan-Night-18_20_null,NEXUS_5,1.0,en].png (Stored with Git LFS)

Binary file not shown.
Loading…
Cancel
Save