From 79515f1205989ab9954980130adeb712dc4b1c2a Mon Sep 17 00:00:00 2001 From: Ighor Moura Date: Wed, 23 Jul 2025 17:42:10 -0400 Subject: [PATCH] melhorando tela de testes --- .../example/mypos/models/PaymentViewModel.kt | 10 +- .../com/example/mypos/screen/PaymentScreen.kt | 125 ++++++++++++------ .../mypos/services/AditumSdkService.kt | 2 +- .../mypos/services/PaymentApplication.kt | 2 +- 4 files changed, 93 insertions(+), 46 deletions(-) diff --git a/app/src/main/java/com/example/mypos/models/PaymentViewModel.kt b/app/src/main/java/com/example/mypos/models/PaymentViewModel.kt index f50980a..a24cfcd 100644 --- a/app/src/main/java/com/example/mypos/models/PaymentViewModel.kt +++ b/app/src/main/java/com/example/mypos/models/PaymentViewModel.kt @@ -1,6 +1,8 @@ package com.example.mypos.models import android.content.Context +import android.nfc.Tag +import android.util.Log import androidx.lifecycle.ViewModel import androidx.lifecycle.ViewModelProvider import androidx.lifecycle.viewModelScope @@ -20,6 +22,7 @@ class PaymentViewModel( private val aditumSdkService: AditumSdkService ) : ViewModel() { private val paymentApplication = application + private val TAG = "PaymentViewModel" private val _isServiceConnected = MutableStateFlow(false) val isServiceConnected: StateFlow = _isServiceConnected.asStateFlow() @@ -35,7 +38,12 @@ class PaymentViewModel( transactionStatus: TransactionStatus?, command: AbecsCommands? ) { - TODO("Not yet implemented") + val notificationMessage = when (command) { + AbecsCommands.Display -> "Exibindo mensagem: $message" + AbecsCommands.GetPin -> "Aguardando digitação do PIN" + else -> message ?: "Processando..." + } + Log.d(TAG, notificationMessage) } } ) diff --git a/app/src/main/java/com/example/mypos/screen/PaymentScreen.kt b/app/src/main/java/com/example/mypos/screen/PaymentScreen.kt index 721af53..f731b08 100644 --- a/app/src/main/java/com/example/mypos/screen/PaymentScreen.kt +++ b/app/src/main/java/com/example/mypos/screen/PaymentScreen.kt @@ -1,8 +1,10 @@ package com.example.mypos.screen - -import androidx.compose.foundation.text.KeyboardOptions +import android.os.Handler +import android.os.Looper import android.widget.Toast +import androidx.compose.foundation.background import androidx.compose.foundation.layout.* +import androidx.compose.foundation.text.KeyboardOptions import androidx.compose.material3.* import androidx.compose.runtime.* import androidx.compose.ui.Alignment @@ -14,39 +16,28 @@ import br.com.aditum.data.v2.enums.PaymentType import com.example.mypos.BuildConfig import com.example.mypos.models.PaymentViewModel import com.example.mypos.services.AditumSdkService -import com.example.mypos.services.PaymentApplication import kotlinx.coroutines.flow.collectLatest @Composable fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkService) { val context = LocalContext.current var amount by remember { mutableStateOf("") } + var installments by remember { mutableStateOf("1") } var paymentType by remember { mutableStateOf(PaymentType.Credit) } - var isServiceConnected by remember { mutableStateOf(false) } - var message by remember { mutableStateOf("") } - var pinLength by remember { mutableStateOf(0) } + val isServiceConnected by viewModel.isServiceConnected.collectAsState() + val message by aditumSdkService.messageFlow.collectAsState() + val pinLength by aditumSdkService.pinLengthFlow.collectAsState() var isInitializing by remember { mutableStateOf(false) } var isPaying by remember { mutableStateOf(false) } + var showLoading by remember { mutableStateOf(false) } - - LaunchedEffect(Unit) { - viewModel.isServiceConnected.collectLatest { connected -> - isServiceConnected = connected - } - } + val handler = remember { Handler(Looper.getMainLooper()) } - - LaunchedEffect(Unit) { - aditumSdkService.messageFlow.collectLatest { msg -> - message = msg - } - } - - - LaunchedEffect(Unit) { - aditumSdkService.pinLengthFlow.collectLatest { length -> - pinLength = length - } + if (showLoading) { + LoadingScreen( + message = message, + onDismiss = { showLoading = false } + ) } Column( @@ -61,37 +52,44 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic style = MaterialTheme.typography.headlineMedium ) - Text( text = if (isServiceConnected) "Serviço Conectado" else "Serviço Desconectado", color = if (isServiceConnected) MaterialTheme.colorScheme.primary else MaterialTheme.colorScheme.error ) - Button( onClick = { if (!isServiceConnected) { viewModel.startService() - Toast.makeText(context, "Tentando conectar ao serviço...", Toast.LENGTH_SHORT).show() + handler.post { + Toast.makeText(context, "Tentando conectar ao serviço...", Toast.LENGTH_SHORT).show() + } return@Button } if (!isInitializing) { isInitializing = true + showLoading = true aditumSdkService.initAditumSdk( applicationName = "MyPOS", applicationVersion = "1.0.0", activationCode = BuildConfig.ACTIVATION_CODE, resolve = { success -> isInitializing = false - Toast.makeText( - context, - if (success) "SDK inicializado com sucesso!" else "Falha na inicialização.", - Toast.LENGTH_LONG - ).show() + showLoading = false + handler.post { + Toast.makeText( + context, + if (success) "SDK inicializado com sucesso!" else "Falha na inicialização.", + Toast.LENGTH_LONG + ).show() + } }, reject = { errorCode, errorMessage -> isInitializing = false - Toast.makeText(context, "Erro: $errorMessage", Toast.LENGTH_LONG).show() + showLoading = false + handler.post { + Toast.makeText(context, "Erro: $errorMessage", Toast.LENGTH_LONG).show() + } } ) } @@ -102,7 +100,6 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic Text(if (isInitializing) "Inicializando..." else "Inicializar SDK") } - OutlinedTextField( value = amount, onValueChange = { amount = it.filter { char -> char.isDigit() || char == '.' } }, @@ -111,7 +108,15 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic modifier = Modifier.fillMaxWidth() ) - + OutlinedTextField( + value = installments, + onValueChange = { installments = it.filter { char -> char.isDigit() } }, + label = { Text("Quantidade de Parcelas") }, + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number), + modifier = Modifier.fillMaxWidth(), + enabled = paymentType == PaymentType.Credit + ) + Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.SpaceEvenly @@ -132,31 +137,43 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic } } - Button( onClick = { val amountValue = amount.toDoubleOrNull()?.times(100)?.toLong() + val installmentCount = installments.toIntOrNull() ?: 1 if (amountValue == null || amountValue <= 0) { - Toast.makeText(context, "Insira um valor válido", Toast.LENGTH_SHORT).show() + handler.post { + Toast.makeText(context, "Insira um valor válido", Toast.LENGTH_SHORT).show() + } return@Button } if (!isServiceConnected) { - Toast.makeText(context, "Serviço não conectado", Toast.LENGTH_SHORT).show() + handler.post { + Toast.makeText(context, "Serviço não conectado", Toast.LENGTH_SHORT).show() + } return@Button } if (!isPaying) { isPaying = true + showLoading = true aditumSdkService.pay( amount = amountValue, + installments = if (paymentType == PaymentType.Credit) installmentCount else null, paymentType = paymentType, allowContactless = true, resolve = { response -> isPaying = false - Toast.makeText(context, "Pagamento realizado com sucesso!", Toast.LENGTH_LONG).show() + showLoading = false + handler.post { + Toast.makeText(context, "Pagamento realizado com sucesso!", Toast.LENGTH_LONG).show() + } }, reject = { errorCode, errorMessage -> isPaying = false - Toast.makeText(context, "Erro no pagamento: $errorMessage", Toast.LENGTH_LONG).show() + showLoading = false + handler.post { + Toast.makeText(context, "Erro no pagamento: $errorMessage", Toast.LENGTH_LONG).show() + } } ) } @@ -167,15 +184,13 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic Text(if (isPaying) "Processando Pagamento..." else "Realizar Pagamento") } - - if (message.isNotEmpty()) { + if (message.isNotEmpty() && !showLoading) { Text( text = "Mensagem do PIN pad: $message", style = MaterialTheme.typography.bodyMedium ) } - if (pinLength > 0) { Text( text = "Comprimento do PIN: $pinLength", @@ -183,4 +198,28 @@ fun PaymentScreen(viewModel: PaymentViewModel, aditumSdkService: AditumSdkServic ) } } +} + +@Composable +fun LoadingScreen(message: String, onDismiss: () -> Unit) { + Box( + modifier = Modifier + .fillMaxSize() + .background(MaterialTheme.colorScheme.background.copy(alpha = 0.8f)), + contentAlignment = Alignment.Center + ) { + Column( + horizontalAlignment = Alignment.CenterHorizontally, + verticalArrangement = Arrangement.spacedBy(16.dp), + modifier = Modifier + .background(MaterialTheme.colorScheme.surface) + .padding(16.dp) + ) { + CircularProgressIndicator() + Text( + text = message.ifEmpty { "Processando..." }, + style = MaterialTheme.typography.bodyLarge + ) + } + } } \ No newline at end of file diff --git a/app/src/main/java/com/example/mypos/services/AditumSdkService.kt b/app/src/main/java/com/example/mypos/services/AditumSdkService.kt index 821aa21..3c56bd6 100644 --- a/app/src/main/java/com/example/mypos/services/AditumSdkService.kt +++ b/app/src/main/java/com/example/mypos/services/AditumSdkService.kt @@ -207,7 +207,7 @@ class AditumSdkService(private val paymentApplication: PaymentApplication) { override fun onResponse(paymentResponse: PaymentResponse?) { if (paymentResponse != null) { val json = gson.toJson(paymentResponse) - Log.e(TAG, "onResponse - $json") + Log.d(TAG, "onResponse - $json") resolve(paymentResponse) } else { Log.e(TAG, "onResponse - paymentResponse is null") diff --git a/app/src/main/java/com/example/mypos/services/PaymentApplication.kt b/app/src/main/java/com/example/mypos/services/PaymentApplication.kt index baa7002..063bb88 100644 --- a/app/src/main/java/com/example/mypos/services/PaymentApplication.kt +++ b/app/src/main/java/com/example/mypos/services/PaymentApplication.kt @@ -19,11 +19,11 @@ import kotlinx.coroutines.withContext class PaymentApplication : Application() { companion object { - private const val TAG = "PaymentApplication" private const val PACKAGE_BASE_NAME = "br.com.aditum" const val PACKAGE_NAME = "$PACKAGE_BASE_NAME.smartpostef" const val ACTION_COMMUNICATION_SERVICE = "$PACKAGE_BASE_NAME.AditumSdkService" } + private val TAG = "PaymentApplication" private val _isServiceConnectedFlow = MutableStateFlow(false) val isServiceConnectedFlow: StateFlow = _isServiceConnectedFlow.asStateFlow()