Skip to content

Commit 3a377f6

Browse files
authored
Merge branch 'master' into feat/hero-animation-header
2 parents 5a6eb4c + a246edc commit 3a377f6

1 file changed

Lines changed: 45 additions & 1 deletion

File tree

app/src/main/java/to/bitkit/ui/components/NumberPad.kt

Lines changed: 45 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package to.bitkit.ui.components
22

33
import androidx.annotation.DrawableRes
4+
import androidx.compose.foundation.focusable
45
import androidx.compose.foundation.layout.Box
56
import androidx.compose.foundation.layout.BoxScope
67
import androidx.compose.foundation.layout.BoxWithConstraints
@@ -12,10 +13,19 @@ import androidx.compose.foundation.lazy.grid.items
1213
import androidx.compose.material3.Icon
1314
import androidx.compose.material3.Text
1415
import androidx.compose.runtime.Composable
16+
import androidx.compose.runtime.LaunchedEffect
1517
import androidx.compose.runtime.getValue
18+
import androidx.compose.runtime.remember
1619
import androidx.compose.ui.Alignment
1720
import androidx.compose.ui.Modifier
21+
import androidx.compose.ui.focus.FocusRequester
22+
import androidx.compose.ui.focus.focusRequester
1823
import androidx.compose.ui.hapticfeedback.HapticFeedbackType
24+
import androidx.compose.ui.input.key.Key
25+
import androidx.compose.ui.input.key.KeyEventType
26+
import androidx.compose.ui.input.key.key
27+
import androidx.compose.ui.input.key.onPreviewKeyEvent
28+
import androidx.compose.ui.input.key.type
1929
import androidx.compose.ui.platform.LocalHapticFeedback
2030
import androidx.compose.ui.platform.testTag
2131
import androidx.compose.ui.res.painterResource
@@ -63,7 +73,20 @@ fun NumberPad(
6373
availableHeight: Dp = defaultHeight,
6474
errorKey: String? = null,
6575
) {
66-
BoxWithConstraints(modifier = modifier) {
76+
val focusRequester = remember { FocusRequester() }
77+
LaunchedEffect(Unit) { focusRequester.requestFocus() }
78+
79+
BoxWithConstraints(
80+
modifier = modifier
81+
.focusRequester(focusRequester)
82+
.onPreviewKeyEvent { keyEvent ->
83+
if (keyEvent.type != KeyEventType.KeyDown) return@onPreviewKeyEvent false
84+
val mapped = mapHardwareKey(keyEvent.key, type) ?: return@onPreviewKeyEvent false
85+
onPress(mapped)
86+
true
87+
}
88+
.focusable()
89+
) {
6790
val buttonHeight = when {
6891
constraints.hasFixedHeight -> maxHeight / ROWS
6992
else -> (availableHeight / ROWS).coerceIn(minButtonHeight, idealButtonHeight)
@@ -151,6 +174,27 @@ fun NumberPad(
151174

152175
enum class NumberPadType { SIMPLE, INTEGER, DECIMAL }
153176

177+
private val hardwareKeyMap = mapOf(
178+
Key.Zero to "0", Key.NumPad0 to "0",
179+
Key.One to "1", Key.NumPad1 to "1",
180+
Key.Two to "2", Key.NumPad2 to "2",
181+
Key.Three to "3", Key.NumPad3 to "3",
182+
Key.Four to "4", Key.NumPad4 to "4",
183+
Key.Five to "5", Key.NumPad5 to "5",
184+
Key.Six to "6", Key.NumPad6 to "6",
185+
Key.Seven to "7", Key.NumPad7 to "7",
186+
Key.Eight to "8", Key.NumPad8 to "8",
187+
Key.Nine to "9", Key.NumPad9 to "9",
188+
Key.Backspace to KEY_DELETE, Key.Delete to KEY_DELETE,
189+
Key.Period to KEY_DECIMAL, Key.NumPadDot to KEY_DECIMAL,
190+
)
191+
192+
private fun mapHardwareKey(key: Key, type: NumberPadType): String? {
193+
val mapped = hardwareKeyMap[key] ?: return null
194+
if (mapped == KEY_DECIMAL && type != NumberPadType.DECIMAL) return null
195+
return mapped
196+
}
197+
154198
@Composable
155199
fun NumberPadKeyButton(
156200
text: String,

0 commit comments

Comments
 (0)