Updated on 2026-08-14
This commit is contained in:
commit
3c2a006fb9
331 changed files with 8261 additions and 1670 deletions
|
|
@ -0,0 +1,17 @@
|
|||
package com.tangem.core.ui.components.artwork
|
||||
|
||||
import androidx.compose.runtime.Immutable
|
||||
import kotlinx.collections.immutable.ImmutableList
|
||||
import kotlinx.collections.immutable.toImmutableList
|
||||
|
||||
@Immutable
|
||||
data class ArtworkUM(
|
||||
val verifiedArtwork: ImmutableList<Byte>? = null,
|
||||
val defaultUrl: String,
|
||||
) {
|
||||
|
||||
constructor(bytes: ByteArray?, defaultUrl: String) : this(
|
||||
verifiedArtwork = bytes?.toList()?.toImmutableList(),
|
||||
defaultUrl = defaultUrl,
|
||||
)
|
||||
}
|
||||
|
|
@ -0,0 +1,485 @@
|
|||
package com.tangem.core.ui.components.atoms.text
|
||||
|
||||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.BoxWithConstraints
|
||||
import androidx.compose.foundation.layout.PaddingValues
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.foundation.text.BasicText
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.runtime.Stable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.text.AnnotatedString
|
||||
import androidx.compose.ui.text.LinkAnnotation
|
||||
import androidx.compose.ui.text.SpanStyle
|
||||
import androidx.compose.ui.text.TextLayoutResult
|
||||
import androidx.compose.ui.text.TextMeasurer
|
||||
import androidx.compose.ui.text.TextStyle
|
||||
import androidx.compose.ui.text.buildAnnotatedString
|
||||
import androidx.compose.ui.text.rememberTextMeasurer
|
||||
import androidx.compose.ui.text.style.TextOverflow
|
||||
import androidx.compose.ui.text.withLink
|
||||
import androidx.compose.ui.text.withStyle
|
||||
import androidx.compose.ui.unit.Constraints
|
||||
import androidx.compose.ui.unit.dp
|
||||
|
||||
/**
|
||||
|
||||
*
|
||||
* 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
|
||||
*
|
||||
* https://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.
|
||||
**/
|
||||
|
||||
private const val READ_MORE_TAG = "read_more"
|
||||
private const val READ_LESS_TAG = "read_less"
|
||||
|
||||
/**
|
||||
* Basic element that displays text with read more.
|
||||
*
|
||||
* @param text The text to be displayed.
|
||||
* @param expanded whether this text is expanded or collapsed.
|
||||
* @param modifier [Modifier] to apply to this layout node.
|
||||
* @param onExpandRequested called when this text is clicked. If `null`, then this text will not be
|
||||
* interactable, unless something else handles its input events and updates its state.
|
||||
* @param contentPadding a padding around the text.
|
||||
* @param style Style configuration for the text such as color, font, line height etc.
|
||||
* @param onTextLayout Callback that is executed when a new text layout is calculated. A
|
||||
* [TextLayoutResult] object that callback provides contains paragraph information, size of the
|
||||
* text, baselines and other details. The callback can be used to add additional decoration or
|
||||
* functionality to the text. For example, to draw selection around the text.
|
||||
* @param softWrap Whether the text should break at soft line breaks. If false, the glyphs in the
|
||||
* text will be positioned as if there was unlimited horizontal space. If [softWrap] is false,
|
||||
* [readMoreOverflow] and TextAlign may have unexpected effects.
|
||||
* @param readMoreText The read more text to be displayed in the collapsed state.
|
||||
* @param readMoreMaxLines An optional maximum number of lines for the text to span, wrapping if
|
||||
* necessary. If the text exceeds the given number of lines, it will be truncated according to
|
||||
* [readMoreOverflow]. If it is not null, then it must be greater than zero.
|
||||
* @param readMoreOverflow How visual overflow should be handled in the collapsed state.
|
||||
* @param readMoreStyle Style configuration for the read more text such as color, font, line height
|
||||
* etc.
|
||||
* @param readLessText The read less text to be displayed in the expanded state.
|
||||
* @param readLessStyle Style configuration for the read less text such as color, font, line height
|
||||
* etc.
|
||||
* @param toggleArea A clickable area of text to toggle.
|
||||
*/
|
||||
@Composable
|
||||
fun ReadMoreText(
|
||||
text: String,
|
||||
expanded: Boolean,
|
||||
modifier: Modifier = Modifier,
|
||||
onExpandRequested: ((Boolean) -> Unit)? = null,
|
||||
contentPadding: PaddingValues = PaddingValues(0.dp),
|
||||
style: TextStyle = TextStyle.Default,
|
||||
onTextLayout: (TextLayoutResult) -> Unit = {},
|
||||
softWrap: Boolean = true,
|
||||
readMoreText: String = "",
|
||||
readMoreMaxLines: Int = 2,
|
||||
readMoreOverflow: ReadMoreTextOverflow = ReadMoreTextOverflow.Ellipsis,
|
||||
readMoreStyle: SpanStyle = style.toSpanStyle(),
|
||||
readLessText: String = "",
|
||||
readLessStyle: SpanStyle = readMoreStyle,
|
||||
toggleArea: ToggleArea = ToggleArea.All,
|
||||
) {
|
||||
ReadMoreTextInternal(
|
||||
text = AnnotatedString(text),
|
||||
expanded = expanded,
|
||||
modifier = modifier,
|
||||
onExpandRequested = onExpandRequested,
|
||||
contentPadding = contentPadding,
|
||||
style = style,
|
||||
onTextLayout = onTextLayout,
|
||||
softWrap = softWrap,
|
||||
readMoreText = readMoreText,
|
||||
readMoreMaxLines = readMoreMaxLines,
|
||||
readMoreOverflow = readMoreOverflow,
|
||||
readMoreStyle = readMoreStyle,
|
||||
readLessText = readLessText,
|
||||
readLessStyle = readLessStyle,
|
||||
toggleArea = toggleArea,
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Basic element that displays text with read more.
|
||||
*
|
||||
* @param text The text to be displayed.
|
||||
* @param expanded whether this text is expanded or collapsed.
|
||||
* @param modifier [Modifier] to apply to this layout node.
|
||||
* @param onExpandRequested called when this text is clicked. If `null`, then this text will not be
|
||||
* interactable, unless something else handles its input events and updates its state.
|
||||
* @param contentPadding a padding around the text.
|
||||
* @param style Style configuration for the text such as color, font, line height etc.
|
||||
* @param onTextLayout Callback that is executed when a new text layout is calculated. A
|
||||
* [TextLayoutResult] object that callback provides contains paragraph information, size of the
|
||||
* text, baselines and other details. The callback can be used to add additional decoration or
|
||||
* functionality to the text. For example, to draw selection around the text.
|
||||
* @param softWrap Whether the text should break at soft line breaks. If false, the glyphs in the
|
||||
* text will be positioned as if there was unlimited horizontal space. If [softWrap] is false,
|
||||
* [readMoreOverflow] and TextAlign may have unexpected effects.
|
||||
* @param readMoreText The read more text to be displayed in the collapsed state.
|
||||
* @param readMoreMaxLines An optional maximum number of lines for the text to span, wrapping if
|
||||
* necessary. If the text exceeds the given number of lines, it will be truncated according to
|
||||
* [readMoreOverflow]. If it is not null, then it must be greater than zero.
|
||||
* @param readMoreOverflow How visual overflow should be handled in the collapsed state.
|
||||
* @param readMoreStyle Style configuration for the read more text such as color, font, line height
|
||||
* etc.
|
||||
* @param readLessText The read less text to be displayed in the expanded state.
|
||||
* @param readLessStyle Style configuration for the read less text such as color, font, line height
|
||||
* etc.
|
||||
* @param toggleArea A clickable area of text to toggle.
|
||||
*/
|
||||
@Composable
|
||||
fun ReadMoreText(
|
||||
text: AnnotatedString,
|
||||
expanded: Boolean,
|
||||
modifier: Modifier = Modifier,
|
||||
onExpandRequested: ((Boolean) -> Unit)? = null,
|
||||
contentPadding: PaddingValues = PaddingValues(0.dp),
|
||||
style: TextStyle = TextStyle.Default,
|
||||
onTextLayout: (TextLayoutResult) -> Unit = {},
|
||||
softWrap: Boolean = true,
|
||||
readMoreText: String = "",
|
||||
readMoreMaxLines: Int = 2,
|
||||
readMoreOverflow: ReadMoreTextOverflow = ReadMoreTextOverflow.Ellipsis,
|
||||
readMoreStyle: SpanStyle = style.toSpanStyle(),
|
||||
readLessText: String = "",
|
||||
readLessStyle: SpanStyle = readMoreStyle,
|
||||
toggleArea: ToggleArea = ToggleArea.All,
|
||||
) {
|
||||
ReadMoreTextInternal(
|
||||
text = text,
|
||||
expanded = expanded,
|
||||
modifier = modifier,
|
||||
onExpandRequested = onExpandRequested,
|
||||
contentPadding = contentPadding,
|
||||
style = style,
|
||||
onTextLayout = onTextLayout,
|
||||
softWrap = softWrap,
|
||||
readMoreText = readMoreText,
|
||||
readMoreMaxLines = readMoreMaxLines,
|
||||
readMoreOverflow = readMoreOverflow,
|
||||
readMoreStyle = readMoreStyle,
|
||||
readLessText = readLessText,
|
||||
readLessStyle = readLessStyle,
|
||||
toggleArea = toggleArea,
|
||||
)
|
||||
}
|
||||
|
||||
@Suppress("LongMethod", "LongParameterList")
|
||||
@Composable
|
||||
private fun ReadMoreTextInternal(
|
||||
text: AnnotatedString,
|
||||
expanded: Boolean,
|
||||
modifier: Modifier = Modifier,
|
||||
onExpandRequested: ((Boolean) -> Unit)? = null,
|
||||
contentPadding: PaddingValues = PaddingValues(0.dp),
|
||||
style: TextStyle = TextStyle.Default,
|
||||
onTextLayout: (TextLayoutResult) -> Unit = {},
|
||||
softWrap: Boolean = true,
|
||||
readMoreText: String = "",
|
||||
readMoreMaxLines: Int = 2,
|
||||
readMoreOverflow: ReadMoreTextOverflow = ReadMoreTextOverflow.Ellipsis,
|
||||
readMoreStyle: SpanStyle = style.toSpanStyle(),
|
||||
readLessText: String = "",
|
||||
readLessStyle: SpanStyle = readMoreStyle,
|
||||
toggleArea: ToggleArea = ToggleArea.All,
|
||||
) {
|
||||
require(readMoreMaxLines > 0) { "readMoreMaxLines should be greater than 0" }
|
||||
|
||||
val overflowText: String = remember(readMoreOverflow) {
|
||||
buildString {
|
||||
when (readMoreOverflow) {
|
||||
ReadMoreTextOverflow.Clip -> {
|
||||
}
|
||||
ReadMoreTextOverflow.Ellipsis -> {
|
||||
append(Typography.ellipsis)
|
||||
}
|
||||
}
|
||||
if (readMoreText.isNotEmpty()) {
|
||||
append(Typography.nbsp)
|
||||
}
|
||||
}
|
||||
}
|
||||
val readMoreTextWithStyle: AnnotatedString = remember(readMoreText, readMoreStyle) {
|
||||
buildAnnotatedString {
|
||||
if (readMoreText.isNotEmpty()) {
|
||||
withStyle(readMoreStyle) {
|
||||
append(readMoreText.replace(' ', Typography.nbsp))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
val readLessTextWithStyle: AnnotatedString = remember(readLessText, readLessStyle) {
|
||||
buildAnnotatedString {
|
||||
if (readLessText.isNotEmpty()) {
|
||||
withStyle(readLessStyle) {
|
||||
append(readLessText)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
val textMeasurer = rememberTextMeasurer()
|
||||
val state = remember { ReadMoreState() }
|
||||
|
||||
val currentText = buildAnnotatedString {
|
||||
if (expanded) {
|
||||
append(text)
|
||||
if (readLessTextWithStyle.isNotEmpty()) {
|
||||
append(' ')
|
||||
if (toggleArea == ToggleArea.More) {
|
||||
withLink(
|
||||
LinkAnnotation.Clickable(tag = READ_LESS_TAG) {
|
||||
onExpandRequested?.invoke(false)
|
||||
},
|
||||
) {
|
||||
append(readLessTextWithStyle)
|
||||
}
|
||||
} else {
|
||||
append(readLessTextWithStyle)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
val collapsedText = state.collapsedText
|
||||
if (collapsedText.isNotEmpty()) {
|
||||
append(collapsedText)
|
||||
append(overflowText)
|
||||
|
||||
if (toggleArea == ToggleArea.More) {
|
||||
withLink(
|
||||
LinkAnnotation.Clickable(tag = READ_MORE_TAG) {
|
||||
onExpandRequested?.invoke(true)
|
||||
},
|
||||
) {
|
||||
append(readMoreTextWithStyle)
|
||||
}
|
||||
} else {
|
||||
append(readMoreTextWithStyle)
|
||||
}
|
||||
} else {
|
||||
append(text)
|
||||
}
|
||||
}
|
||||
}
|
||||
val toggleableModifier = if (onExpandRequested != null && toggleArea == ToggleArea.All) {
|
||||
Modifier.clickable(
|
||||
enabled = state.isCollapsible,
|
||||
onClick = { onExpandRequested(!expanded) },
|
||||
)
|
||||
} else {
|
||||
Modifier
|
||||
}
|
||||
BoxWithConstraints(
|
||||
modifier = modifier
|
||||
.then(toggleableModifier)
|
||||
.padding(contentPadding),
|
||||
) {
|
||||
BasicText(
|
||||
text = currentText,
|
||||
modifier = Modifier,
|
||||
style = style,
|
||||
onTextLayout = onTextLayout,
|
||||
overflow = TextOverflow.Ellipsis,
|
||||
softWrap = softWrap,
|
||||
maxLines = if (expanded) Int.MAX_VALUE else readMoreMaxLines,
|
||||
)
|
||||
|
||||
val constraints = Constraints(maxWidth = constraints.maxWidth)
|
||||
LaunchedEffect(
|
||||
textMeasurer,
|
||||
constraints,
|
||||
overflowText,
|
||||
readMoreTextWithStyle,
|
||||
style,
|
||||
readMoreStyle,
|
||||
text,
|
||||
readMoreMaxLines,
|
||||
softWrap,
|
||||
) {
|
||||
state.applyCollapsedText(
|
||||
textMeasurer = textMeasurer,
|
||||
constraints = constraints,
|
||||
overflowText = overflowText,
|
||||
readMoreTextWithStyle = readMoreTextWithStyle,
|
||||
style = style,
|
||||
readMoreStyle = readMoreStyle,
|
||||
text = text,
|
||||
readMoreMaxLines = readMoreMaxLines,
|
||||
softWrap = softWrap,
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Stable
|
||||
private class ReadMoreState {
|
||||
private var _collapsedText: AnnotatedString by mutableStateOf(AnnotatedString(""))
|
||||
|
||||
var collapsedText: AnnotatedString
|
||||
get() = _collapsedText
|
||||
internal set(value) {
|
||||
if (value != _collapsedText) {
|
||||
_collapsedText = value
|
||||
}
|
||||
}
|
||||
|
||||
val isCollapsible: Boolean
|
||||
get() = collapsedText.isNotEmpty()
|
||||
|
||||
@Suppress("LongParameterList")
|
||||
fun applyCollapsedText(
|
||||
textMeasurer: TextMeasurer,
|
||||
constraints: Constraints,
|
||||
overflowText: String,
|
||||
readMoreTextWithStyle: AnnotatedString,
|
||||
style: TextStyle,
|
||||
readMoreStyle: SpanStyle,
|
||||
text: AnnotatedString,
|
||||
readMoreMaxLines: Int,
|
||||
softWrap: Boolean,
|
||||
) {
|
||||
val overflowTextWidth = if (overflowText.isNotEmpty()) {
|
||||
textMeasurer.measure(
|
||||
text = overflowText,
|
||||
style = style,
|
||||
).size.width
|
||||
} else {
|
||||
0
|
||||
}
|
||||
val readMoreTextWidth = if (readMoreTextWithStyle.isNotEmpty()) {
|
||||
textMeasurer.measure(
|
||||
text = readMoreTextWithStyle,
|
||||
style = style.merge(readMoreStyle),
|
||||
).size.width
|
||||
} else {
|
||||
0
|
||||
}
|
||||
val textLayout = textMeasurer.measure(
|
||||
text = text,
|
||||
style = style,
|
||||
maxLines = readMoreMaxLines,
|
||||
overflow = TextOverflow.Clip,
|
||||
softWrap = softWrap,
|
||||
constraints = constraints,
|
||||
)
|
||||
|
||||
val clipTextCount = textLayout.getLineEnd(lineIndex = textLayout.lineCount - 1)
|
||||
val isLineClipped = text.count() > clipTextCount
|
||||
if (isLineClipped) {
|
||||
val countUntilMaxLine =
|
||||
textLayout.getLineEnd(readMoreMaxLines - 1, visibleEnd = true)
|
||||
|
||||
val decorationWidth = overflowTextWidth + readMoreTextWidth
|
||||
val replaceCount = text
|
||||
.substringOf(textLayout, line = readMoreMaxLines)
|
||||
.calculateReplaceCountToBeSingleLineWith(
|
||||
maximumTextWidth = constraints.maxWidth - decorationWidth,
|
||||
measureTextWidth = { subText ->
|
||||
textMeasurer.measure(
|
||||
text = subText,
|
||||
style = style,
|
||||
softWrap = softWrap,
|
||||
).size.width
|
||||
},
|
||||
)
|
||||
collapsedText = text.subSequence(0, countUntilMaxLine - replaceCount)
|
||||
} else {
|
||||
collapsedText = AnnotatedString("")
|
||||
}
|
||||
}
|
||||
|
||||
private fun AnnotatedString.substringOf(layout: TextLayoutResult, line: Int): AnnotatedString {
|
||||
val lastLineStartIndex = layout.getLineStart(line - 1)
|
||||
val lastLineEndIndex = layout.getLineEnd(line - 1, visibleEnd = true)
|
||||
return subSequence(lastLineStartIndex, lastLineEndIndex)
|
||||
}
|
||||
|
||||
private inline fun AnnotatedString.calculateReplaceCountToBeSingleLineWith(
|
||||
maximumTextWidth: Int,
|
||||
measureTextWidth: (subText: AnnotatedString) -> Int,
|
||||
): Int {
|
||||
var replacedTextWidth: Int
|
||||
var replacedCount = -1
|
||||
do {
|
||||
replacedCount++
|
||||
replacedTextWidth = measureTextWidth(
|
||||
subSequence(0, this.length - replacedCount),
|
||||
)
|
||||
} while (replacedCount < this.length && replacedTextWidth >= maximumTextWidth)
|
||||
|
||||
val lastVisibleChar: Char? = this.getOrNull(this.length - replacedCount - 1)
|
||||
val firstOverflowChar: Char? = this.getOrNull(this.length - replacedCount)
|
||||
if (lastVisibleChar?.isSurrogate() == true && firstOverflowChar?.isHighSurrogate() == false) {
|
||||
val subText = subSequence(0, this.length - replacedCount)
|
||||
if (subText.isNotEmpty()) {
|
||||
return length - subText.indexOfLast { it.isHighSurrogate() }
|
||||
}
|
||||
}
|
||||
return replacedCount
|
||||
}
|
||||
}
|
||||
|
||||
@JvmInline
|
||||
value class ToggleArea private constructor(internal val value: Int) {
|
||||
|
||||
override fun toString(): String {
|
||||
return when (this) {
|
||||
All -> "All"
|
||||
More -> "More"
|
||||
else -> "Invalid"
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
/**
|
||||
* All area of the text is clickable to toggle.
|
||||
*/
|
||||
@Stable
|
||||
val All: ToggleArea = ToggleArea(1)
|
||||
|
||||
/**
|
||||
* 'More' and 'Less' area of the text is clickable to toggle.
|
||||
*/
|
||||
@Stable
|
||||
val More: ToggleArea = ToggleArea(2)
|
||||
}
|
||||
}
|
||||
|
||||
@JvmInline
|
||||
value class ReadMoreTextOverflow private constructor(internal val value: Int) {
|
||||
|
||||
override fun toString(): String {
|
||||
return when (this) {
|
||||
Clip -> "Clip"
|
||||
Ellipsis -> "Ellipsis"
|
||||
else -> "Invalid"
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
/**
|
||||
* Clip the overflowing text to fix its container.
|
||||
*/
|
||||
@Stable
|
||||
val Clip: ReadMoreTextOverflow = ReadMoreTextOverflow(1)
|
||||
|
||||
/**
|
||||
* Use an ellipsis to indicate that the text has overflowed.
|
||||
*/
|
||||
@Stable
|
||||
val Ellipsis: ReadMoreTextOverflow = ReadMoreTextOverflow(2)
|
||||
}
|
||||
}
|
||||
|
|
@ -9,6 +9,7 @@ import androidx.compose.foundation.layout.size
|
|||
import androidx.compose.foundation.shape.CircleShape
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.graphics.ColorFilter
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import com.tangem.core.ui.res.TangemTheme
|
||||
|
|
@ -19,12 +20,13 @@ fun CurrencyIconTopBadge(
|
|||
alpha: Float,
|
||||
colorFilter: ColorFilter?,
|
||||
modifier: Modifier = Modifier,
|
||||
background: Color = TangemTheme.colors.background.primary,
|
||||
) {
|
||||
Box(
|
||||
modifier = modifier
|
||||
.size(TangemTheme.dimens.size18)
|
||||
.background(
|
||||
color = TangemTheme.colors.background.primary,
|
||||
color = background,
|
||||
shape = CircleShape,
|
||||
),
|
||||
) {
|
||||
|
|
|
|||
|
|
@ -95,6 +95,7 @@ data class TangemDimens internal constructor(
|
|||
val size142: Dp = 142.dp,
|
||||
val size158: Dp = 158.dp,
|
||||
val size164: Dp = 164.dp,
|
||||
val size180: Dp = 180.dp,
|
||||
val size200: Dp = 200.dp,
|
||||
val size248: Dp = 248.dp,
|
||||
val size350: Dp = 350.dp,
|
||||
|
|
|
|||
13
core/ui/src/main/res/drawable/ic_network_new_24.xml
Normal file
13
core/ui/src/main/res/drawable/ic_network_new_24.xml
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:autoMirrored="true"
|
||||
android:viewportWidth="24"
|
||||
android:viewportHeight="24">
|
||||
|
||||
<path
|
||||
android:fillColor="#0099FF"
|
||||
android:fillType="evenOdd"
|
||||
android:pathData="M6.532,6.791C6.532,5.272 7.763,4.041 9.282,4.041C10.801,4.041 12.032,5.272 12.032,6.791C12.032,7.766 11.525,8.622 10.76,9.111L11.04,9.85C11.292,9.773 11.559,9.732 11.836,9.732C12.655,9.732 13.39,10.09 13.894,10.658L14.119,10.418C13.92,10.038 13.808,9.605 13.808,9.146C13.808,7.627 15.039,6.396 16.558,6.396C18.076,6.396 19.308,7.627 19.308,9.146C19.308,10.664 18.076,11.896 16.558,11.896C16.044,11.896 15.563,11.755 15.152,11.509L14.564,12.135C14.579,12.249 14.586,12.365 14.586,12.482C14.586,13.038 14.421,13.556 14.137,13.989L16.034,15.229C16.533,14.724 17.226,14.41 17.992,14.41C19.511,14.41 20.742,15.641 20.742,17.16C20.742,18.679 19.511,19.91 17.992,19.91C16.473,19.91 15.242,18.679 15.242,17.16C15.242,16.95 15.266,16.745 15.311,16.548L12.943,15C12.605,15.149 12.23,15.232 11.836,15.232C11.269,15.232 10.742,15.061 10.304,14.766L8.465,16.455C8.603,16.783 8.68,17.144 8.68,17.522C8.68,19.041 7.448,20.272 5.93,20.272C4.411,20.272 3.18,19.041 3.18,17.522C3.18,16.004 4.411,14.773 5.93,14.773C6.524,14.773 7.074,14.961 7.524,15.282L9.33,13.624L9.337,13.632C9.176,13.283 9.086,12.893 9.086,12.482C9.086,11.796 9.337,11.169 9.753,10.687L9.319,9.541L9.282,9.541C7.763,9.541 6.532,8.31 6.532,6.791ZM9.282,5.541C8.592,5.541 8.032,6.101 8.032,6.791C8.032,7.481 8.592,8.041 9.282,8.041C9.973,8.041 10.532,7.481 10.532,6.791C10.532,6.101 9.973,5.541 9.282,5.541ZM16.558,7.896C15.867,7.896 15.308,8.455 15.308,9.146C15.308,9.836 15.867,10.396 16.558,10.396C17.248,10.396 17.808,9.836 17.808,9.146C17.808,8.455 17.248,7.896 16.558,7.896ZM11.836,11.232C11.146,11.232 10.586,11.792 10.586,12.482C10.586,13.173 11.146,13.732 11.836,13.732C12.526,13.732 13.086,13.173 13.086,12.482C13.086,11.792 12.526,11.232 11.836,11.232ZM4.68,17.522C4.68,16.832 5.239,16.272 5.93,16.272C6.62,16.272 7.18,16.832 7.18,17.522C7.18,18.213 6.62,18.772 5.93,18.772C5.239,18.772 4.68,18.213 4.68,17.522ZM16.742,17.16C16.742,16.47 17.302,15.91 17.992,15.91C18.683,15.91 19.242,16.47 19.242,17.16C19.242,17.851 18.683,18.41 17.992,18.41C17.302,18.41 16.742,17.851 16.742,17.16Z" />
|
||||
|
||||
</vector>
|
||||
18
core/ui/src/main/res/drawable/img_approvale2_20.xml
Normal file
18
core/ui/src/main/res/drawable/img_approvale2_20.xml
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="20dp"
|
||||
android:height="20dp"
|
||||
android:autoMirrored="true"
|
||||
android:viewportWidth="20"
|
||||
android:viewportHeight="20">
|
||||
|
||||
<path
|
||||
android:fillColor="#0099FF"
|
||||
android:fillType="evenOdd"
|
||||
android:pathData="M8.807,1.939C9.142,1.683 9.524,1.482 9.999,1.482C10.473,1.482 10.855,1.683 11.191,1.939C11.501,2.176 11.842,2.517 12.231,2.906L12.263,2.938C12.646,3.32 12.967,3.464 13.474,3.464C13.536,3.464 13.617,3.461 13.711,3.459C13.958,3.452 14.291,3.442 14.576,3.466C14.993,3.502 15.537,3.615 15.956,4.03C16.377,4.448 16.494,4.995 16.53,5.415C16.555,5.702 16.545,6.037 16.538,6.286C16.536,6.38 16.534,6.461 16.534,6.523C16.534,6.867 16.572,7.046 16.631,7.181C16.692,7.32 16.803,7.477 17.06,7.734L17.091,7.766C17.481,8.155 17.821,8.496 18.059,8.807C18.315,9.142 18.515,9.524 18.515,9.998C18.515,10.473 18.315,10.855 18.059,11.19C17.821,11.501 17.481,11.842 17.091,12.231L17.06,12.263C16.803,12.52 16.692,12.677 16.631,12.816C16.572,12.951 16.534,13.13 16.534,13.474C16.534,13.536 16.536,13.617 16.538,13.711C16.545,13.96 16.555,14.295 16.53,14.582C16.494,15.002 16.377,15.549 15.956,15.967C15.537,16.382 14.993,16.495 14.576,16.531C14.291,16.555 13.958,16.545 13.711,16.538C13.618,16.535 13.536,16.533 13.474,16.533C13.136,16.533 12.96,16.567 12.828,16.622C12.696,16.676 12.545,16.777 12.305,17.017C12.258,17.065 12.192,17.135 12.115,17.217C11.934,17.411 11.689,17.674 11.467,17.868C11.13,18.163 10.628,18.515 9.999,18.515C9.37,18.515 8.868,18.163 8.531,17.868C8.308,17.674 8.063,17.411 7.882,17.217C7.805,17.135 7.74,17.065 7.692,17.017C7.452,16.777 7.302,16.676 7.17,16.622C7.038,16.567 6.861,16.533 6.524,16.533C6.462,16.533 6.38,16.535 6.287,16.538C6.039,16.545 5.707,16.555 5.422,16.531C5.004,16.495 4.46,16.382 4.042,15.967C3.62,15.549 3.504,15.002 3.468,14.582C3.443,14.295 3.452,13.96 3.459,13.711C3.462,13.617 3.464,13.536 3.464,13.474C3.464,13.13 3.426,12.951 3.367,12.816C3.306,12.677 3.195,12.52 2.938,12.263L2.906,12.231C2.517,11.842 2.176,11.501 1.939,11.19C1.683,10.855 1.482,10.473 1.482,9.998C1.482,9.524 1.683,9.142 1.939,8.807C2.176,8.496 2.517,8.155 2.906,7.766L2.938,7.734C3.321,7.351 3.464,7.03 3.464,6.523C3.464,6.461 3.462,6.38 3.459,6.286C3.452,6.039 3.443,5.706 3.467,5.421C3.502,5.004 3.615,4.46 4.03,4.041C4.448,3.62 4.995,3.504 5.415,3.467C5.703,3.442 6.038,3.452 6.287,3.459C6.38,3.461 6.461,3.464 6.524,3.464C7.03,3.464 7.352,3.32 7.734,2.938L7.766,2.906C8.155,2.517 8.496,2.176 8.807,1.939Z" />
|
||||
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:fillType="evenOdd"
|
||||
android:pathData="M13.464,8.04C13.821,7.854 13.96,7.414 13.774,7.057C13.587,6.7 13.147,6.561 12.79,6.747C11.373,7.485 10.195,8.914 9.399,10.075C9.087,10.531 8.823,10.96 8.616,11.317C8.408,11.119 8.2,10.95 8.016,10.811C7.8,10.649 7.606,10.521 7.465,10.432C7.394,10.388 7.336,10.354 7.294,10.33C7.273,10.318 7.257,10.308 7.244,10.301L7.23,10.293L7.225,10.29L7.223,10.289L7.222,10.289C6.868,10.097 6.425,10.228 6.233,10.581C6.041,10.935 6.172,11.378 6.526,11.57L6.532,11.573C6.538,11.577 6.549,11.583 6.563,11.592C6.592,11.608 6.637,11.635 6.693,11.67C6.806,11.74 6.964,11.844 7.139,11.976C7.499,12.248 7.888,12.603 8.132,12.992C8.273,13.217 8.526,13.347 8.791,13.332C9.056,13.317 9.292,13.159 9.407,12.92L9.407,12.919L9.411,12.913L9.425,12.884C9.438,12.858 9.457,12.818 9.484,12.767C9.537,12.664 9.616,12.513 9.719,12.328C9.926,11.956 10.227,11.447 10.602,10.9C11.369,9.781 12.379,8.605 13.464,8.04Z" />
|
||||
|
||||
</vector>
|
||||
13
core/ui/src/main/res/drawable/img_knight_shield_32.xml
Normal file
13
core/ui/src/main/res/drawable/img_knight_shield_32.xml
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="32dp"
|
||||
android:height="32dp"
|
||||
android:autoMirrored="true"
|
||||
android:viewportWidth="32"
|
||||
android:viewportHeight="32">
|
||||
|
||||
<path
|
||||
android:fillColor="#FFB71B"
|
||||
android:fillType="evenOdd"
|
||||
android:pathData="M16.214,1.668C14.03,1.668 12.267,2.448 10.774,3.263C10.303,3.52 9.876,3.769 9.474,4.002C8.525,4.554 7.719,5.023 6.819,5.326C6.683,5.371 6.542,5.416 6.399,5.461C5.631,5.703 4.787,5.969 4.269,6.575C3.799,7.126 3.677,7.846 3.56,8.537L3.543,8.634C2.104,17.057 5.406,26.376 13.794,29.764C14.591,30.086 15.207,30.335 16.218,30.335C17.23,30.335 17.846,30.086 18.643,29.764C27.031,26.376 30.331,17.065 28.889,8.633L28.873,8.537C28.755,7.845 28.633,7.125 28.163,6.575C27.646,5.968 26.801,5.703 26.034,5.461L26.033,5.461C25.889,5.416 25.749,5.371 25.614,5.326C24.713,5.023 23.906,4.554 22.956,4.002C22.554,3.768 22.127,3.52 21.656,3.263C20.163,2.448 18.399,1.668 16.214,1.668ZM14.884,21.634C14.884,20.897 15.48,20.3 16.217,20.3H16.229C16.965,20.3 17.562,20.897 17.562,21.634C17.562,22.37 16.965,22.967 16.229,22.967H16.217C15.48,22.967 14.884,22.37 14.884,21.634ZM15.217,17.634C15.217,18.186 15.665,18.634 16.217,18.634C16.769,18.634 17.217,18.186 17.217,17.634V9.634C17.217,9.081 16.769,8.634 16.217,8.634C15.665,8.634 15.217,9.081 15.217,9.634V17.634Z" />
|
||||
|
||||
</vector>
|
||||
Loading…
Add table
Add a link
Reference in a new issue