diff --git a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/Badge.kt b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/Badge.kt
index 09fd8206..184415d7 100644
--- a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/Badge.kt
+++ b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/Badge.kt
@@ -18,6 +18,7 @@ import co.electriccoin.zcash.ui.design.util.StringResource
import co.electriccoin.zcash.ui.design.util.getValue
import co.electriccoin.zcash.ui.design.util.stringRes
+@Suppress("MagicNumber")
@Composable
fun Badge(
text: StringResource,
diff --git a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/RadioButton.kt b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/RadioButton.kt
index 8f54d38a..e9b139b7 100644
--- a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/RadioButton.kt
+++ b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/RadioButton.kt
@@ -97,7 +97,7 @@ fun RadioButton(
text = state.subtitle.getValue(),
style = ZcashTheme.extendedTypography.radioButton,
fontWeight = FontWeight.Normal,
- color = Color(0xFF838385),
+ color = ZcashTheme.zashiColors.textTertiary,
modifier =
Modifier.padding(
bottom = 6.dp,
diff --git a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/TextField.kt b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/TextField.kt
index bf2b44a3..e52f64ac 100644
--- a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/TextField.kt
+++ b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/component/TextField.kt
@@ -27,7 +27,6 @@ import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
import co.electriccoin.zcash.ui.design.theme.ZcashTheme
import co.electriccoin.zcash.ui.design.util.StringResource
-import co.electriccoin.zcash.ui.design.util.getValue
import kotlinx.coroutines.launch
@OptIn(ExperimentalFoundationApi::class)
@@ -133,59 +132,9 @@ fun FormTextField(
}
}
-@Suppress("LongParameterList")
-@OptIn(ExperimentalFoundationApi::class)
-@Composable
-fun FormTextField(
- state: TextFieldState,
- modifier: Modifier = Modifier,
- textStyle: TextStyle = ZcashTheme.extendedTypography.textFieldValue,
- placeholder: @Composable (() -> Unit)? = null,
- leadingIcon: @Composable (() -> Unit)? = null,
- trailingIcon: @Composable (() -> Unit)? = null,
- keyboardOptions: KeyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Text),
- colors: TextFieldColors =
- TextFieldDefaults.colors(
- cursorColor = ZcashTheme.colors.textPrimary,
- focusedContainerColor = Color.Transparent,
- unfocusedContainerColor = Color.Transparent,
- disabledContainerColor = Color.Transparent,
- errorContainerColor = Color.Transparent,
- focusedIndicatorColor = Color.Transparent,
- unfocusedIndicatorColor = Color.Transparent,
- disabledIndicatorColor = Color.Transparent
- ),
- keyboardActions: KeyboardActions = KeyboardActions.Default,
- shape: Shape = TextFieldDefaults.shape,
- withBorder: Boolean = true,
- bringIntoViewRequester: BringIntoViewRequester? = null,
- minHeight: Dp = ZcashTheme.dimens.textFieldDefaultHeight,
- testTag: String? = null
-) {
- FormTextField(
- value = state.value.getValue(),
- error = state.error?.getValue(),
- enabled = state.isEnabled,
- onValueChange = state.onValueChange,
- modifier = modifier,
- textStyle = textStyle,
- placeholder = placeholder,
- leadingIcon = leadingIcon,
- trailingIcon = trailingIcon,
- keyboardOptions = keyboardOptions,
- colors = colors,
- keyboardActions = keyboardActions,
- shape = shape,
- withBorder = withBorder,
- bringIntoViewRequester = bringIntoViewRequester,
- minHeight = minHeight,
- testTag = testTag,
- )
-}
-
data class TextFieldState(
val value: StringResource,
- val isEnabled: Boolean = true,
val error: StringResource? = null,
+ val isEnabled: Boolean = true,
val onValueChange: (String) -> Unit,
)
diff --git a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/theme/ZashiColors.kt b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/theme/ZashiColors.kt
index a36797e1..4d66d2a2 100644
--- a/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/theme/ZashiColors.kt
+++ b/ui-design-lib/src/main/java/co/electriccoin/zcash/ui/design/theme/ZashiColors.kt
@@ -17,6 +17,7 @@ data class ZashiColors(
val textLightSupport: Color,
val surfacePrimary: Color,
val bgPrimary: Color,
+ val bgSecondary: Color,
val defaultFg: Color,
val textTertiary: Color,
val textPrimary: Color,
@@ -28,7 +29,10 @@ data class ZashiColors(
val btnPrimaryFg: Color,
val btnPrimaryFgDisabled: Color,
val btnTextFg: Color,
- val exchangeRateColors: ExchangeRateColors
+ val exchangeRateColors: ExchangeRateColors,
+ val textSupport: Color,
+ val stroke: Color,
+ val divider: Color,
)
internal val LightZashiColorPalette =
@@ -37,6 +41,7 @@ internal val LightZashiColorPalette =
textLightSupport = Color(0xFFD9D8CF),
surfacePrimary = Color(0xFF282622),
bgPrimary = Color(0xFFFFFFFF),
+ bgSecondary = Color(0xFFF4F4F4),
defaultFg = Color(0xFFD9D8CF),
textPrimary = Color(0xFF231F20),
textTertiary = Color(0xFF716C5D),
@@ -48,7 +53,10 @@ internal val LightZashiColorPalette =
btnPrimaryFg = Color(0xFFFFFFFF),
btnPrimaryFgDisabled = Color(0xFF94907B),
btnTextFg = Color(0xFF231F20),
- exchangeRateColors = LightExchangeRateColorPalette
+ exchangeRateColors = LightExchangeRateColorPalette,
+ textSupport = Color(0xFF94907B),
+ stroke = Color(0xFFD9D8CF),
+ divider = Color(0xFFF7F7F5)
)
internal val DarkZashiColorPalette =
@@ -57,6 +65,7 @@ internal val DarkZashiColorPalette =
textLightSupport = Color(0xFFBDBBBC),
surfacePrimary = Color(0xFF454243),
bgPrimary = Color(0xFF231F20),
+ bgSecondary = Color(0xFF3B3839),
defaultFg = Color(0xFFBDBBBC),
textPrimary = Color(0xFFE8E8E8),
textTertiary = Color(0xFFBDBBBC),
@@ -68,7 +77,10 @@ internal val DarkZashiColorPalette =
btnPrimaryFg = Color(0xFF231F20),
btnPrimaryFgDisabled = Color(0xFF7E7C7C),
btnTextFg = Color(0xFFE8E8E8),
- exchangeRateColors = DarkExchangeRateColorPalette
+ exchangeRateColors = DarkExchangeRateColorPalette,
+ textSupport = Color(0xFF7E7C7C),
+ stroke = Color(0xFFA7A5A6),
+ divider = Color(0xFF343031)
)
@Suppress("CompositionLocalAllowlist")
diff --git a/ui-design-lib/src/main/res/ui/common/drawable/ic_radio_button_checked_variant_dark.xml b/ui-design-lib/src/main/res/ui/common/drawable/ic_radio_button_checked_variant_dark.xml
new file mode 100644
index 00000000..f36ff8d9
--- /dev/null
+++ b/ui-design-lib/src/main/res/ui/common/drawable/ic_radio_button_checked_variant_dark.xml
@@ -0,0 +1,21 @@
+
+
+
+
+
diff --git a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerView.kt b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerView.kt
index b2893521..bfb52ece 100644
--- a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerView.kt
+++ b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerView.kt
@@ -4,9 +4,9 @@ package co.electriccoin.zcash.ui.screen.chooseserver
import androidx.compose.animation.AnimatedVisibility
import androidx.compose.animation.core.animateFloatAsState
-import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.Image
import androidx.compose.foundation.background
+import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.Row
@@ -54,7 +54,6 @@ import co.electriccoin.zcash.ui.design.component.Badge
import co.electriccoin.zcash.ui.design.component.BlankBgScaffold
import co.electriccoin.zcash.ui.design.component.ButtonState
import co.electriccoin.zcash.ui.design.component.CircularScreenProgressIndicator
-import co.electriccoin.zcash.ui.design.component.FormTextField
import co.electriccoin.zcash.ui.design.component.LottieProgress
import co.electriccoin.zcash.ui.design.component.RadioButton
import co.electriccoin.zcash.ui.design.component.RadioButtonCheckedContent
@@ -62,13 +61,14 @@ import co.electriccoin.zcash.ui.design.component.RadioButtonState
import co.electriccoin.zcash.ui.design.component.SmallTopAppBar
import co.electriccoin.zcash.ui.design.component.TextFieldState
import co.electriccoin.zcash.ui.design.component.TopAppBarBackNavigation
+import co.electriccoin.zcash.ui.design.newcomponent.PreviewScreens
import co.electriccoin.zcash.ui.design.theme.ZcashTheme
import co.electriccoin.zcash.ui.design.util.StringResource
import co.electriccoin.zcash.ui.design.util.getValue
import co.electriccoin.zcash.ui.design.util.stringRes
import co.electriccoin.zcash.ui.screen.exchangerate.BottomBar
import co.electriccoin.zcash.ui.screen.exchangerate.ZashiButton
-import co.electriccoin.zcash.ui.design.newcomponent.PreviewScreens
+import co.electriccoin.zcash.ui.screen.exchangerate.ZashiTextField
@Composable
fun ChooseServerView(
@@ -145,7 +145,7 @@ private fun ServerLoading() {
Text(
text = stringResource(id = R.string.choose_server_loading_subtitle),
fontSize = 14.sp,
- color = Color(0xFF646464)
+ color = ZcashTheme.zashiColors.textTertiary
)
Spacer(modifier = Modifier.height(24.dp))
}
@@ -244,7 +244,7 @@ private fun LazyListScope.serverListItems(state: ServerListState) {
.padding(start = 4.dp, end = 4.dp)
.then(
if (item.radioButtonState.isChecked) {
- Modifier.background(Color(0xFFF4F4F6), RoundedCornerShape(12.dp))
+ Modifier.background(ZcashTheme.zashiColors.bgSecondary, RoundedCornerShape(12.dp))
} else {
Modifier
}
@@ -261,7 +261,7 @@ private fun LazyListScope.serverListItems(state: ServerListState) {
.padding(horizontal = 4.dp)
.then(
if (item.radioButtonState.isChecked && item.badge == null) {
- Modifier.background(Color(0xFFF4F4F6), RoundedCornerShape(12.dp))
+ Modifier.background(ZcashTheme.zashiColors.bgSecondary, RoundedCornerShape(12.dp))
} else {
Modifier
}
@@ -271,7 +271,13 @@ private fun LazyListScope.serverListItems(state: ServerListState) {
RadioButtonCheckedContent(item.radioButtonState)
} else {
Image(
- painter = painterResource(id = drawable.ic_radio_button_checked_variant),
+ painter = painterResource(
+ id = if (isSystemInDarkTheme()) {
+ drawable.ic_radio_button_checked_variant_dark
+ } else {
+ drawable.ic_radio_button_checked_variant
+ }
+ ),
contentDescription = item.radioButtonState.text.getValue(),
)
}
@@ -287,8 +293,7 @@ private fun LazyListScope.serverListItems(state: ServerListState) {
if (index != state.servers.lastIndex) {
Spacer(modifier = Modifier.height(4.dp))
HorizontalDivider(
- modifier = Modifier.padding(horizontal = 24.dp),
- color = Color(0xFFF7F7F5),
+ color = ZcashTheme.zashiColors.divider,
)
Spacer(modifier = Modifier.height(4.dp))
}
@@ -347,7 +352,6 @@ private fun ServerHeader(text: StringResource) {
)
}
-@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun CustomServerRadioButton(
state: ServerState.Custom,
@@ -374,7 +378,7 @@ private fun CustomServerRadioButton(
AnimatedVisibility(visible = state.radioButtonState.isChecked) {
val focusManager = LocalFocusManager.current
Spacer(modifier = Modifier.height(ZcashTheme.dimens.spacingSmall))
- FormTextField(
+ ZashiTextField(
state = state.newServerTextFieldState,
placeholder = {
Text(text = stringResource(R.string.choose_server_textfield_hint))
diff --git a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerViewModel.kt b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerViewModel.kt
index 9f8b79c5..0f2648fe 100644
--- a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerViewModel.kt
+++ b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/chooseserver/ChooseServerViewModel.kt
@@ -204,16 +204,18 @@ class ChooseServerViewModel(
private fun onSaveButtonClicked() =
viewModelScope.launch {
- if (isSaveInProgress.value) return@launch
-
- isSaveInProgress.update { true }
- val selection = getUserEndpointSelectionOrShowError() ?: return@launch
try {
- persistEndpoint(selection)
- } catch (e: PersistEndpointException) {
- showValidationErrorDialog(e.message)
+ if (isSaveInProgress.value) return@launch
+ isSaveInProgress.update { true }
+ val selection = getUserEndpointSelectionOrShowError() ?: return@launch
+ try {
+ persistEndpoint(selection)
+ } catch (e: PersistEndpointException) {
+ showValidationErrorDialog(e.message)
+ }
+ } finally {
+ isSaveInProgress.update { false }
}
- isSaveInProgress.update { false }
}
private fun onConfirmDialogButtonClicked() {
diff --git a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiButton.kt b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiButton.kt
index 99c51ad7..fc514bda 100644
--- a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiButton.kt
+++ b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiButton.kt
@@ -1,8 +1,8 @@
package co.electriccoin.zcash.ui.screen.exchangerate
+import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.foundation.layout.RowScope
import androidx.compose.foundation.layout.Spacer
-import androidx.compose.foundation.layout.displayCutoutPadding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.Button
@@ -10,7 +10,6 @@ import androidx.compose.material3.ButtonColors
import androidx.compose.material3.ButtonDefaults
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
-import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.unit.dp
@@ -58,7 +57,13 @@ internal fun ZashiButton(
@Composable
override fun Loading() {
if (enabled && isLoading) {
- LottieProgress(loadingRes = R.raw.lottie_loading_white)
+ LottieProgress(
+ loadingRes = if (isSystemInDarkTheme()) {
+ R.raw.lottie_loading
+ } else {
+ R.raw.lottie_loading_white
+ }
+ )
}
}
}
diff --git a/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiTextField.kt b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiTextField.kt
new file mode 100644
index 00000000..0d325d06
--- /dev/null
+++ b/ui-lib/src/main/java/co/electriccoin/zcash/ui/screen/exchangerate/ZashiTextField.kt
@@ -0,0 +1,316 @@
+package co.electriccoin.zcash.ui.screen.exchangerate
+
+import androidx.compose.foundation.border
+import androidx.compose.foundation.interaction.InteractionSource
+import androidx.compose.foundation.interaction.MutableInteractionSource
+import androidx.compose.foundation.interaction.collectIsFocusedAsState
+import androidx.compose.foundation.isSystemInDarkTheme
+import androidx.compose.foundation.layout.PaddingValues
+import androidx.compose.foundation.layout.defaultMinSize
+import androidx.compose.foundation.shape.RoundedCornerShape
+import androidx.compose.foundation.text.BasicTextField
+import androidx.compose.foundation.text.KeyboardActions
+import androidx.compose.foundation.text.KeyboardOptions
+import androidx.compose.foundation.text.selection.LocalTextSelectionColors
+import androidx.compose.foundation.text.selection.TextSelectionColors
+import androidx.compose.material3.ExperimentalMaterial3Api
+import androidx.compose.material3.LocalTextStyle
+import androidx.compose.material3.TextFieldColors
+import androidx.compose.material3.TextFieldDefaults
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.CompositionLocalProvider
+import androidx.compose.runtime.State
+import androidx.compose.runtime.getValue
+import androidx.compose.runtime.remember
+import androidx.compose.runtime.rememberUpdatedState
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.graphics.Shape
+import androidx.compose.ui.graphics.SolidColor
+import androidx.compose.ui.graphics.takeOrElse
+import androidx.compose.ui.text.TextStyle
+import androidx.compose.ui.text.input.VisualTransformation
+import androidx.compose.ui.unit.dp
+import co.electriccoin.zcash.ui.design.component.TextFieldState
+import co.electriccoin.zcash.ui.design.newcomponent.PreviewScreens
+import co.electriccoin.zcash.ui.design.theme.ZcashTheme
+import co.electriccoin.zcash.ui.design.util.getValue
+import co.electriccoin.zcash.ui.design.util.stringRes
+
+@Suppress("LongParameterList")
+@Composable
+fun ZashiTextField(
+ state: TextFieldState,
+ modifier: Modifier = Modifier,
+ readOnly: Boolean = false,
+ textStyle: TextStyle = LocalTextStyle.current,
+ label: @Composable (() -> Unit)? = null,
+ placeholder: @Composable (() -> Unit)? = null,
+ leadingIcon: @Composable (() -> Unit)? = null,
+ trailingIcon: @Composable (() -> Unit)? = null,
+ prefix: @Composable (() -> Unit)? = null,
+ suffix: @Composable (() -> Unit)? = null,
+ supportingText: @Composable (() -> Unit)? = null,
+ visualTransformation: VisualTransformation = VisualTransformation.None,
+ keyboardOptions: KeyboardOptions = KeyboardOptions.Default,
+ keyboardActions: KeyboardActions = KeyboardActions.Default,
+ singleLine: Boolean = false,
+ maxLines: Int = if (singleLine) 1 else Int.MAX_VALUE,
+ minLines: Int = 1,
+ interactionSource: MutableInteractionSource = remember { MutableInteractionSource() },
+ shape: Shape = ZashiTextFieldDefaults.shape,
+ colors: TextFieldColors = ZashiTextFieldDefaults.colors()
+) {
+ TextFieldInternal(
+ value = state.value.getValue(),
+ onValueChange = state.onValueChange,
+ modifier = modifier then Modifier.border(
+ width = 1.dp,
+ color = ZcashTheme.zashiColors.stroke,
+ shape = ZashiTextFieldDefaults.shape
+ ),
+ enabled = state.isEnabled,
+ readOnly = readOnly,
+ textStyle = textStyle,
+ label = label,
+ placeholder = placeholder,
+ leadingIcon = leadingIcon,
+ trailingIcon = trailingIcon,
+ prefix = prefix,
+ suffix = suffix,
+ supportingText = supportingText,
+ isError = state.error != null,
+ visualTransformation = visualTransformation,
+ keyboardOptions = keyboardOptions,
+ keyboardActions = keyboardActions,
+ singleLine = singleLine,
+ maxLines = maxLines,
+ minLines = minLines,
+ interactionSource = interactionSource,
+ shape = shape,
+ colors = colors,
+ )
+}
+
+@Suppress("LongParameterList")
+@OptIn(ExperimentalMaterial3Api::class)
+@Composable
+private fun TextFieldInternal(
+ value: String,
+ onValueChange: (String) -> Unit,
+ enabled: Boolean,
+ readOnly: Boolean,
+ textStyle: TextStyle,
+ label: @Composable (() -> Unit)?,
+ placeholder: @Composable (() -> Unit)?,
+ leadingIcon: @Composable (() -> Unit)?,
+ trailingIcon: @Composable (() -> Unit)?,
+ prefix: @Composable (() -> Unit)?,
+ suffix: @Composable (() -> Unit)?,
+ supportingText: @Composable (() -> Unit)?,
+ isError: Boolean,
+ visualTransformation: VisualTransformation,
+ keyboardOptions: KeyboardOptions,
+ keyboardActions: KeyboardActions,
+ singleLine: Boolean,
+ maxLines: Int,
+ minLines: Int,
+ interactionSource: MutableInteractionSource,
+ shape: Shape,
+ colors: TextFieldColors,
+ modifier: Modifier = Modifier,
+) {
+ // If color is not provided via the text style, use content color as a default
+ val textColor = textStyle.color.takeOrElse {
+ colors.textColor(enabled, isError, interactionSource).value
+ }
+ val mergedTextStyle = textStyle.merge(TextStyle(color = textColor))
+
+ CompositionLocalProvider(LocalTextSelectionColors provides colors.selectionColors) {
+ BasicTextField(
+ value = value,
+ modifier = modifier
+ .defaultMinSize(minWidth = TextFieldDefaults.MinWidth),
+ onValueChange = onValueChange,
+ enabled = enabled,
+ readOnly = readOnly,
+ textStyle = mergedTextStyle,
+ cursorBrush = SolidColor(colors.cursorColor(isError).value),
+ visualTransformation = visualTransformation,
+ keyboardOptions = keyboardOptions,
+ keyboardActions = keyboardActions,
+ interactionSource = interactionSource,
+ singleLine = singleLine,
+ maxLines = maxLines,
+ minLines = minLines,
+ decorationBox = @Composable { innerTextField ->
+ // places leading icon, text field with label and placeholder, trailing icon
+ TextFieldDefaults.DecorationBox(
+ value = value,
+ visualTransformation = visualTransformation,
+ innerTextField = innerTextField,
+ placeholder = placeholder,
+ label = label,
+ leadingIcon = leadingIcon,
+ trailingIcon = trailingIcon,
+ prefix = prefix,
+ suffix = suffix,
+ supportingText = supportingText,
+ shape = shape,
+ singleLine = singleLine,
+ enabled = enabled,
+ isError = isError,
+ interactionSource = interactionSource,
+ colors = colors,
+ contentPadding = PaddingValues(horizontal = 12.dp, vertical = 8.dp)
+ )
+ }
+ )
+ }
+}
+
+@Composable
+private fun TextFieldColors.textColor(
+ enabled: Boolean,
+ isError: Boolean,
+ interactionSource: InteractionSource
+): State {
+ val focused by interactionSource.collectIsFocusedAsState()
+
+ val targetValue = when {
+ !enabled -> disabledTextColor
+ isError -> errorTextColor
+ focused -> focusedTextColor
+ else -> unfocusedTextColor
+ }
+ return rememberUpdatedState(targetValue)
+}
+
+private val TextFieldColors.selectionColors: TextSelectionColors
+ @Composable get() = textSelectionColors
+
+@Composable
+internal fun TextFieldColors.cursorColor(isError: Boolean): State {
+ return rememberUpdatedState(if (isError) errorCursorColor else cursorColor)
+}
+
+object ZashiTextFieldDefaults {
+
+ val shape: Shape
+ get() = RoundedCornerShape(8.dp)
+
+ @Suppress("LongParameterList")
+ @Composable
+ fun colors(
+ focusedTextColor: Color = ZcashTheme.zashiColors.textPrimary,
+ unfocusedTextColor: Color = ZcashTheme.zashiColors.textPrimary,
+ disabledTextColor: Color = ZcashTheme.zashiColors.textPrimary,
+ errorTextColor: Color = Color.Unspecified,
+ focusedContainerColor: Color = if (isSystemInDarkTheme()) {
+ ZcashTheme.zashiColors.bgSecondary
+ } else {
+ ZcashTheme.zashiColors.bgPrimary
+ },
+ unfocusedContainerColor: Color = if (isSystemInDarkTheme()) {
+ ZcashTheme.zashiColors.bgSecondary
+ } else {
+ ZcashTheme.zashiColors.bgPrimary
+ },
+ disabledContainerColor: Color = if (isSystemInDarkTheme()) {
+ ZcashTheme.zashiColors.bgSecondary
+ } else {
+ ZcashTheme.zashiColors.bgPrimary
+ },
+ errorContainerColor: Color = Color.Unspecified,
+ cursorColor: Color = Color.Unspecified,
+ errorCursorColor: Color = Color.Unspecified,
+ selectionColors: TextSelectionColors? = null,
+ focusedIndicatorColor: Color = Color.Transparent,
+ unfocusedIndicatorColor: Color = Color.Transparent,
+ disabledIndicatorColor: Color = Color.Transparent,
+ errorIndicatorColor: Color = Color.Unspecified,
+ focusedLeadingIconColor: Color = Color.Unspecified,
+ unfocusedLeadingIconColor: Color = Color.Unspecified,
+ disabledLeadingIconColor: Color = Color.Unspecified,
+ errorLeadingIconColor: Color = Color.Unspecified,
+ focusedTrailingIconColor: Color = Color.Unspecified,
+ unfocusedTrailingIconColor: Color = Color.Unspecified,
+ disabledTrailingIconColor: Color = Color.Unspecified,
+ errorTrailingIconColor: Color = Color.Unspecified,
+ focusedLabelColor: Color = Color.Unspecified,
+ unfocusedLabelColor: Color = Color.Unspecified,
+ disabledLabelColor: Color = Color.Unspecified,
+ errorLabelColor: Color = Color.Unspecified,
+ focusedPlaceholderColor: Color = ZcashTheme.zashiColors.textSupport,
+ unfocusedPlaceholderColor: Color = ZcashTheme.zashiColors.textSupport,
+ disabledPlaceholderColor: Color = ZcashTheme.zashiColors.textSupport,
+ errorPlaceholderColor: Color = Color.Unspecified,
+ focusedSupportingTextColor: Color = ZcashTheme.zashiColors.textSupport,
+ unfocusedSupportingTextColor: Color = ZcashTheme.zashiColors.textSupport,
+ disabledSupportingTextColor: Color = ZcashTheme.zashiColors.textSupport,
+ errorSupportingTextColor: Color = Color.Unspecified,
+ focusedPrefixColor: Color = Color.Unspecified,
+ unfocusedPrefixColor: Color = Color.Unspecified,
+ disabledPrefixColor: Color = Color.Unspecified,
+ errorPrefixColor: Color = Color.Unspecified,
+ focusedSuffixColor: Color = Color.Unspecified,
+ unfocusedSuffixColor: Color = Color.Unspecified,
+ disabledSuffixColor: Color = Color.Unspecified,
+ errorSuffixColor: Color = Color.Unspecified,
+ ): TextFieldColors = TextFieldDefaults.colors(
+ focusedTextColor = focusedTextColor,
+ unfocusedTextColor = unfocusedTextColor,
+ disabledTextColor = disabledTextColor,
+ errorTextColor = errorTextColor,
+ focusedContainerColor = focusedContainerColor,
+ unfocusedContainerColor = unfocusedContainerColor,
+ disabledContainerColor = disabledContainerColor,
+ errorContainerColor = errorContainerColor,
+ cursorColor = cursorColor,
+ errorCursorColor = errorCursorColor,
+ selectionColors = selectionColors,
+ focusedIndicatorColor = focusedIndicatorColor,
+ unfocusedIndicatorColor = unfocusedIndicatorColor,
+ disabledIndicatorColor = disabledIndicatorColor,
+ errorIndicatorColor = errorIndicatorColor,
+ focusedLeadingIconColor = focusedLeadingIconColor,
+ unfocusedLeadingIconColor = unfocusedLeadingIconColor,
+ disabledLeadingIconColor = disabledLeadingIconColor,
+ errorLeadingIconColor = errorLeadingIconColor,
+ focusedTrailingIconColor = focusedTrailingIconColor,
+ unfocusedTrailingIconColor = unfocusedTrailingIconColor,
+ disabledTrailingIconColor = disabledTrailingIconColor,
+ errorTrailingIconColor = errorTrailingIconColor,
+ focusedLabelColor = focusedLabelColor,
+ unfocusedLabelColor = unfocusedLabelColor,
+ disabledLabelColor = disabledLabelColor,
+ errorLabelColor = errorLabelColor,
+ focusedPlaceholderColor = focusedPlaceholderColor,
+ unfocusedPlaceholderColor = unfocusedPlaceholderColor,
+ disabledPlaceholderColor = disabledPlaceholderColor,
+ errorPlaceholderColor = errorPlaceholderColor,
+ focusedSupportingTextColor = focusedSupportingTextColor,
+ unfocusedSupportingTextColor = unfocusedSupportingTextColor,
+ disabledSupportingTextColor = disabledSupportingTextColor,
+ errorSupportingTextColor = errorSupportingTextColor,
+ focusedPrefixColor = focusedPrefixColor,
+ unfocusedPrefixColor = unfocusedPrefixColor,
+ disabledPrefixColor = disabledPrefixColor,
+ errorPrefixColor = errorPrefixColor,
+ focusedSuffixColor = focusedSuffixColor,
+ unfocusedSuffixColor = unfocusedSuffixColor,
+ disabledSuffixColor = disabledSuffixColor,
+ errorSuffixColor = errorSuffixColor,
+ )
+}
+
+@Suppress("UnusedPrivateMember")
+@PreviewScreens
+@Composable
+private fun ZashiTextFieldPreview() = ZcashTheme {
+ ZashiTextField(
+ state = TextFieldState(
+ value = stringRes("Text")
+ ) {}
+ )
+}