Compare commits
3 Commits
70f2913989
...
83047648b4
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
83047648b4 | ||
|
|
1d132c481f | ||
|
|
c4f49bc440 |
1
.gitignore
vendored
1
.gitignore
vendored
@ -14,7 +14,6 @@
|
|||||||
.cxx
|
.cxx
|
||||||
local.properties
|
local.properties
|
||||||
/.idea
|
/.idea
|
||||||
/.idea
|
|
||||||
/sunmiui-lib
|
/sunmiui-lib
|
||||||
/paysdk-lib
|
/paysdk-lib
|
||||||
/app/uat
|
/app/uat
|
||||||
|
|||||||
3
.idea/.gitignore
vendored
3
.idea/.gitignore
vendored
@ -1,3 +0,0 @@
|
|||||||
# Default ignored files
|
|
||||||
/shelf/
|
|
||||||
/workspace.xml
|
|
||||||
@ -4,10 +4,10 @@
|
|||||||
<selectionStates>
|
<selectionStates>
|
||||||
<SelectionState runConfigName="app">
|
<SelectionState runConfigName="app">
|
||||||
<option name="selectionMode" value="DROPDOWN" />
|
<option name="selectionMode" value="DROPDOWN" />
|
||||||
<DropdownSelection timestamp="2026-05-07T16:25:07.233027800Z">
|
<DropdownSelection timestamp="2026-09-15T06:58:26.019801800Z">
|
||||||
<Target type="DEFAULT_BOOT">
|
<Target type="DEFAULT_BOOT">
|
||||||
<handle>
|
<handle>
|
||||||
<DeviceId pluginId="PhysicalDevice" identifier="serial=PB0219AQ60954" />
|
<DeviceId pluginId="PhysicalDevice" identifier="serial=PB13216J53652" />
|
||||||
</handle>
|
</handle>
|
||||||
</Target>
|
</Target>
|
||||||
</DropdownSelection>
|
</DropdownSelection>
|
||||||
|
|||||||
@ -1,62 +0,0 @@
|
|||||||
<component name="InspectionProjectProfileManager">
|
|
||||||
<profile version="1.0">
|
|
||||||
<option name="myName" value="Project Default" />
|
|
||||||
<inspection_tool class="ComposePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="ComposePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="ComposePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="ComposePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="GlancePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="GlancePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="GlancePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="GlancePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewAnnotationInFunctionWithParameters" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewApiLevelMustBeValid" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewDeviceShouldUseNewSpec" enabled="true" level="WEAK WARNING" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewFontScaleMustBeGreaterThanZero" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewMultipleParameterProviders" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewParameterProviderOnFirstParameter" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="PreviewPickerAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
|
|
||||||
<option name="composableFile" value="true" />
|
|
||||||
<option name="previewFile" value="true" />
|
|
||||||
</inspection_tool>
|
|
||||||
<inspection_tool class="UsePropertyAccessSyntax" enabled="true" level="WEAK WARNING" enabled_by_default="true" />
|
|
||||||
</profile>
|
|
||||||
</component>
|
|
||||||
@ -1,10 +1,5 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<project version="4">
|
<project version="4">
|
||||||
<component name="ExternalStorageConfigurationManager" enabled="true" />
|
<component name="ExternalStorageConfigurationManager" enabled="true" />
|
||||||
<component name="ProjectRootManager" version="2" languageLevel="JDK_21" default="true" project-jdk-name="temurin-21" project-jdk-type="JavaSDK">
|
<component name="ProjectRootManager" version="2" languageLevel="JDK_21" default="true" project-jdk-name="temurin-21" project-jdk-type="JavaSDK" />
|
||||||
<output url="file://$PROJECT_DIR$/build/classes" />
|
|
||||||
</component>
|
|
||||||
<component name="ProjectType">
|
|
||||||
<option name="id" value="Android" />
|
|
||||||
</component>
|
|
||||||
</project>
|
</project>
|
||||||
@ -39,7 +39,9 @@ class DashboardViewModel @Inject constructor(
|
|||||||
val isCurrentBusinessSettlement = latestSettlement?.isCurrentBusinessSettlement() == true
|
val isCurrentBusinessSettlement = latestSettlement?.isCurrentBusinessSettlement() == true
|
||||||
_uiState.update {
|
_uiState.update {
|
||||||
it.copy(
|
it.copy(
|
||||||
recentTransactions = payDetails.map { pd -> pd.toRecord() },
|
recentTransactions = payDetails
|
||||||
|
.filterNot { it.isSettlementTransaction() }
|
||||||
|
.map { pd -> pd.toRecord() },
|
||||||
totalSaleCount = payDetails.totalSaleCount(),
|
totalSaleCount = payDetails.totalSaleCount(),
|
||||||
totalSaleAmount = payDetails.totalSaleAmount(),
|
totalSaleAmount = payDetails.totalSaleAmount(),
|
||||||
settlementStatusText = if (isCurrentBusinessSettlement) {
|
settlementStatusText = if (isCurrentBusinessSettlement) {
|
||||||
@ -151,6 +153,11 @@ private fun PayDetail.isSaleTransaction(): Boolean {
|
|||||||
(transactionType == TransactionsType.WAVEPAY.value && qrTransStatus == 1)
|
(transactionType == TransactionsType.WAVEPAY.value && qrTransStatus == 1)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun PayDetail.isSettlementTransaction(): Boolean {
|
||||||
|
return transactionType == TransactionsType.SETTLEMENT.value ||
|
||||||
|
transType?.contains("SETTLEMENT", ignoreCase = true) == true
|
||||||
|
}
|
||||||
|
|
||||||
private fun formatTypeLabel(raw: String): String = when {
|
private fun formatTypeLabel(raw: String): String = when {
|
||||||
raw.equals("CASH_OUT", ignoreCase = true) -> "CASH_ADV"
|
raw.equals("CASH_OUT", ignoreCase = true) -> "CASH_ADV"
|
||||||
raw.contains("SALE", ignoreCase = true) -> "Sale"
|
raw.contains("SALE", ignoreCase = true) -> "Sale"
|
||||||
|
|||||||
@ -2,6 +2,7 @@ package com.mob.utsmyanmar.ui.navigation
|
|||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.os.Build
|
import android.os.Build
|
||||||
|
import android.widget.Toast
|
||||||
import androidx.activity.ComponentActivity
|
import androidx.activity.ComponentActivity
|
||||||
import androidx.annotation.RequiresApi
|
import androidx.annotation.RequiresApi
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
@ -167,6 +168,7 @@ fun AppNavGraph(
|
|||||||
|
|
||||||
LaunchedEffect(tmsSetupUiState.isTerminalDisabled) {
|
LaunchedEffect(tmsSetupUiState.isTerminalDisabled) {
|
||||||
if (tmsSetupUiState.isTerminalDisabled) {
|
if (tmsSetupUiState.isTerminalDisabled) {
|
||||||
|
tmsSetupViewModel.clearTerminalDisabledState()
|
||||||
navController.navigate(Routes.TmsSetup.route) {
|
navController.navigate(Routes.TmsSetup.route) {
|
||||||
popUpTo(Routes.Dashboard.route) {
|
popUpTo(Routes.Dashboard.route) {
|
||||||
inclusive = true
|
inclusive = true
|
||||||
@ -842,7 +844,9 @@ fun AppNavGraph(
|
|||||||
},
|
},
|
||||||
onShowError = {},
|
onShowError = {},
|
||||||
onShowSuccess = {},
|
onShowSuccess = {},
|
||||||
onShowPrinterDialog = {}
|
onShowPrinterDialog = { message ->
|
||||||
|
Toast.makeText(activity, message, Toast.LENGTH_LONG).show()
|
||||||
|
}
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -82,6 +82,7 @@ class SettlementViewModel @Inject constructor(
|
|||||||
|
|
||||||
private var flag = false
|
private var flag = false
|
||||||
private var errorFlag = false
|
private var errorFlag = false
|
||||||
|
private var settlementApproved = false
|
||||||
private var isSecondCall = false
|
private var isSecondCall = false
|
||||||
private var batchIndex = 0
|
private var batchIndex = 0
|
||||||
|
|
||||||
@ -239,6 +240,8 @@ class SettlementViewModel @Inject constructor(
|
|||||||
repository.deletePayDetail(pay)
|
repository.deletePayDetail(pay)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
repository.deleteReversalTransactions()
|
||||||
|
|
||||||
deleteTrans.forEach { pay ->
|
deleteTrans.forEach { pay ->
|
||||||
repository.deletePayDetail(pay)
|
repository.deletePayDetail(pay)
|
||||||
}
|
}
|
||||||
@ -269,6 +272,10 @@ class SettlementViewModel @Inject constructor(
|
|||||||
private fun requestOnlineProcessSettlement() {
|
private fun requestOnlineProcessSettlement() {
|
||||||
val state = _uiState.value
|
val state = _uiState.value
|
||||||
|
|
||||||
|
// Keep the local batch until this request receives an approved response.
|
||||||
|
settlementApproved = false
|
||||||
|
errorFlag = false
|
||||||
|
|
||||||
val hostName = HostName.MPU
|
val hostName = HostName.MPU
|
||||||
val field60 = SystemParamsOperation.getInstance().getCurrentBatchNum()
|
val field60 = SystemParamsOperation.getInstance().getCurrentBatchNum()
|
||||||
|
|
||||||
@ -407,15 +414,23 @@ class SettlementViewModel @Inject constructor(
|
|||||||
when {
|
when {
|
||||||
resultStr == Constant.ANSWER_CODE_ACCEPT ||
|
resultStr == Constant.ANSWER_CODE_ACCEPT ||
|
||||||
resultStr == Constant.ANSWER_CODE_APPROVED -> {
|
resultStr == Constant.ANSWER_CODE_APPROVED -> {
|
||||||
|
settlementApproved = true
|
||||||
currentPayDetail.isNeedReversal = false
|
currentPayDetail.isNeedReversal = false
|
||||||
}
|
}
|
||||||
|
|
||||||
resultStr == "95" || resultStr == "095" -> {
|
resultStr == "95" || resultStr == "095" -> {
|
||||||
|
settlementApproved = false
|
||||||
currentPayDetail.isNeedReversal = !flag
|
currentPayDetail.isNeedReversal = !flag
|
||||||
}
|
}
|
||||||
|
|
||||||
|
else -> {
|
||||||
|
settlementApproved = false
|
||||||
|
currentPayDetail.isNeedReversal = false
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
errorFlag = true
|
errorFlag = true
|
||||||
|
settlementApproved = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -447,13 +462,12 @@ class SettlementViewModel @Inject constructor(
|
|||||||
flag = false
|
flag = false
|
||||||
batchIndex = 0
|
batchIndex = 0
|
||||||
|
|
||||||
updateDB()
|
if (!errorFlag && settlementApproved) {
|
||||||
insertPayDetail(currentPayDetail)
|
updateDB()
|
||||||
|
insertPayDetail(currentPayDetail)
|
||||||
if (errorFlag) {
|
|
||||||
postStatus(TransactionStatus.ON_ERROR)
|
|
||||||
} else {
|
|
||||||
postStatus(TransactionStatus.ON_SUCCESS)
|
postStatus(TransactionStatus.ON_SUCCESS)
|
||||||
|
} else {
|
||||||
|
postStatus(TransactionStatus.ON_ERROR)
|
||||||
}
|
}
|
||||||
|
|
||||||
_uiState.update {
|
_uiState.update {
|
||||||
|
|||||||
@ -44,6 +44,10 @@ fun TmsSetupRoute(
|
|||||||
) {
|
) {
|
||||||
val state by viewModel.uiState.collectAsState()
|
val state by viewModel.uiState.collectAsState()
|
||||||
|
|
||||||
|
LaunchedEffect(viewModel) {
|
||||||
|
viewModel.initialize()
|
||||||
|
}
|
||||||
|
|
||||||
LaunchedEffect(viewModel) {
|
LaunchedEffect(viewModel) {
|
||||||
viewModel.navigateToDashboard.collect { onNavigateDashboard() }
|
viewModel.navigateToDashboard.collect { onNavigateDashboard() }
|
||||||
}
|
}
|
||||||
|
|||||||
@ -49,7 +49,7 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
private val emvParamOperation: EmvParamOperation,
|
private val emvParamOperation: EmvParamOperation,
|
||||||
@ApplicationContext private val context: Context
|
@ApplicationContext private val context: Context
|
||||||
) : ViewModel() {
|
) : ViewModel() {
|
||||||
private val TAG = TmsSetupViewModel::class.simpleName;
|
private val TAG = TmsSetupViewModel::class.simpleName
|
||||||
private val _uiState = MutableStateFlow(TmsSetupUiState())
|
private val _uiState = MutableStateFlow(TmsSetupUiState())
|
||||||
private val _dashboardUiState = MutableStateFlow(DashboardUiState())
|
private val _dashboardUiState = MutableStateFlow(DashboardUiState())
|
||||||
val uiState: StateFlow<TmsSetupUiState> = _uiState.asStateFlow()
|
val uiState: StateFlow<TmsSetupUiState> = _uiState.asStateFlow()
|
||||||
@ -65,8 +65,14 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
|
|
||||||
private val disposables = CompositeDisposable()
|
private val disposables = CompositeDisposable()
|
||||||
private val tmsSetups = TMSSetupsImpl()
|
private val tmsSetups = TMSSetupsImpl()
|
||||||
|
private var requestInProgress = false
|
||||||
|
|
||||||
|
private var initialized = false
|
||||||
|
|
||||||
|
fun initialize() {
|
||||||
|
if (initialized) return
|
||||||
|
initialized = true
|
||||||
|
|
||||||
init {
|
|
||||||
viewModelScope.launch {
|
viewModelScope.launch {
|
||||||
waitForHardware()
|
waitForHardware()
|
||||||
TMSUtil.getInstance().generateFinalVersion()
|
TMSUtil.getInstance().generateFinalVersion()
|
||||||
@ -75,20 +81,29 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun downloadConfigs(onSuccess: () -> Unit = {}) {
|
fun downloadConfigs(onSuccess: () -> Unit = {}) {
|
||||||
|
// Do not use isLoading here because it also covers the hardware startup phase.
|
||||||
|
if (requestInProgress) return
|
||||||
|
requestInProgress = true
|
||||||
|
|
||||||
_uiState.update {
|
_uiState.update {
|
||||||
it.copy(isLoading = true, isError = false, statusText = "Connecting to TMS server...")
|
it.copy(
|
||||||
|
isLoading = true,
|
||||||
|
isError = false,
|
||||||
|
isTerminalDisabled = false,
|
||||||
|
statusText = "Connecting to TMS server..."
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
val disposable = repository.getParams(buildRequest())
|
val disposable = repository.getParams(buildRequest())
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.doFinally { requestInProgress = false }
|
||||||
.subscribe(
|
.subscribe(
|
||||||
{ response ->
|
{ response ->
|
||||||
_uiState.update { it.copy(
|
_uiState.update { it.copy(
|
||||||
statusText = "Applying configuration...")
|
statusText = "Applying configuration...")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
val appResponse = SiriusResponse(
|
val appResponse = SiriusResponse(
|
||||||
serial = response.serial.orEmpty(),
|
serial = response.serial.orEmpty(),
|
||||||
ecrKey = response.ecrKey.orEmpty(),
|
ecrKey = response.ecrKey.orEmpty(),
|
||||||
@ -111,7 +126,6 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
"Empty error response (${error.code()})"
|
"Empty error response (${error.code()})"
|
||||||
}
|
}
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
// Server returned non-JSON (HTML 404 page, plain text, etc.)
|
|
||||||
"Server error: ${error.code()}"
|
"Server error: ${error.code()}"
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -138,7 +152,6 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
delay(500.milliseconds)
|
delay(500.milliseconds)
|
||||||
elapsed += 500
|
elapsed += 500
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun onConfigApplied(onSuccess: () -> Unit) {
|
private fun onConfigApplied(onSuccess: () -> Unit) {
|
||||||
@ -148,6 +161,7 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
LogUtil.d(TAG, "isActive ${ops.isActive}")
|
LogUtil.d(TAG, "isActive ${ops.isActive}")
|
||||||
val msg = ops.disabledMsg.takeIf { it.isNotEmpty() }
|
val msg = ops.disabledMsg.takeIf { it.isNotEmpty() }
|
||||||
?: "This terminal has been disabled. Please contact your administrator."
|
?: "This terminal has been disabled. Please contact your administrator."
|
||||||
|
|
||||||
_uiState.update {
|
_uiState.update {
|
||||||
it.copy(
|
it.copy(
|
||||||
isLoading = false,
|
isLoading = false,
|
||||||
@ -157,6 +171,11 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
errorMessage = msg
|
errorMessage = msg
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// FIX 2: Actually trigger the navigation event so the UI leaves this screen
|
||||||
|
viewModelScope.launch {
|
||||||
|
_navigateToDisable.emit(msg)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -188,6 +207,10 @@ class TmsSetupViewModel @Inject constructor(
|
|||||||
viewModelScope.launch { _navigateToDashboard.emit(Unit) }
|
viewModelScope.launch { _navigateToDashboard.emit(Unit) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun clearTerminalDisabledState() {
|
||||||
|
_uiState.update { it.copy(isTerminalDisabled = false) }
|
||||||
|
}
|
||||||
|
|
||||||
@SuppressLint("MissingPermission")
|
@SuppressLint("MissingPermission")
|
||||||
private fun buildRequest(): SiriusRequest {
|
private fun buildRequest(): SiriusRequest {
|
||||||
return try {
|
return try {
|
||||||
|
|||||||
@ -1,6 +1,7 @@
|
|||||||
package com.mob.utsmyanmar.ui.transaction_result
|
package com.mob.utsmyanmar.ui.transaction_result
|
||||||
|
|
||||||
import androidx.lifecycle.ViewModel
|
import androidx.lifecycle.ViewModel
|
||||||
|
import androidx.lifecycle.Observer
|
||||||
import androidx.lifecycle.viewModelScope
|
import androidx.lifecycle.viewModelScope
|
||||||
import com.mob.utsmyanmar.model.ecr.ECRResultStatus
|
import com.mob.utsmyanmar.model.ecr.ECRResultStatus
|
||||||
import com.mob.utsmyanmar.utils.CoreUtils
|
import com.mob.utsmyanmar.utils.CoreUtils
|
||||||
@ -47,6 +48,8 @@ class TransactionResultViewModel @Inject constructor(
|
|||||||
|
|
||||||
private var started = false
|
private var started = false
|
||||||
private var resultTimeoutJob: Job? = null
|
private var resultTimeoutJob: Job? = null
|
||||||
|
private var printStatusObserver: Observer<PrintStatus?>? = null
|
||||||
|
private var observedSharedViewModel: SharedViewModel? = null
|
||||||
|
|
||||||
fun onEvent(
|
fun onEvent(
|
||||||
event: TransactionResultEvent,
|
event: TransactionResultEvent,
|
||||||
@ -196,7 +199,11 @@ class TransactionResultViewModel @Inject constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun observePrintStatus(sharedViewModel: SharedViewModel) {
|
private fun observePrintStatus(sharedViewModel: SharedViewModel) {
|
||||||
sharedViewModel.printXStatus.observeForever { status ->
|
printStatusObserver?.let { observer ->
|
||||||
|
observedSharedViewModel?.printXStatus?.removeObserver(observer)
|
||||||
|
}
|
||||||
|
printStatusObserver = Observer<PrintStatus?> { status ->
|
||||||
|
status ?: return@Observer
|
||||||
when (status) {
|
when (status) {
|
||||||
PrintStatus.EMPTY_PAPER_ROLL -> {
|
PrintStatus.EMPTY_PAPER_ROLL -> {
|
||||||
startPrintProcess(sharedViewModel, false)
|
startPrintProcess(sharedViewModel, false)
|
||||||
@ -209,6 +216,18 @@ class TransactionResultViewModel @Inject constructor(
|
|||||||
else -> Unit
|
else -> Unit
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
observedSharedViewModel = sharedViewModel
|
||||||
|
sharedViewModel.printXStatus.observeForever(printStatusObserver!!)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onCleared() {
|
||||||
|
resultTimeoutJob?.cancel()
|
||||||
|
printStatusObserver?.let { observer ->
|
||||||
|
observedSharedViewModel?.printXStatus?.removeObserver(observer)
|
||||||
|
}
|
||||||
|
printStatusObserver = null
|
||||||
|
observedSharedViewModel = null
|
||||||
|
super.onCleared()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun startPrintProcess(
|
private fun startPrintProcess(
|
||||||
@ -220,7 +239,16 @@ class TransactionResultViewModel @Inject constructor(
|
|||||||
|
|
||||||
override fun paperRollIsReady() {
|
override fun paperRollIsReady() {
|
||||||
if (isSettlement) {
|
if (isSettlement) {
|
||||||
sharedViewModel.startPrintProcessSettlement()
|
sharedViewModel.startPrintProcessSettlement(
|
||||||
|
onSuccess = ::navigateMain,
|
||||||
|
onFailure = {
|
||||||
|
sendUiEvent(
|
||||||
|
TransactionResultUiEvent.ShowPrinterDialog(
|
||||||
|
"Settlement report printing failed"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
} else {
|
} else {
|
||||||
sharedViewModel.startPrintProcess()
|
sharedViewModel.startPrintProcess()
|
||||||
}
|
}
|
||||||
|
|||||||
@ -43,7 +43,7 @@ object MockData {
|
|||||||
cardNo="6244310039574344",
|
cardNo="6244310039574344",
|
||||||
expDate="3011",
|
expDate="3011",
|
||||||
cardScheme="MPU",
|
cardScheme="MPU",
|
||||||
cardHolderName="Htin Kyaw Win",
|
cardHolderName="Nay Nwe Ei Kyaw Phyo",
|
||||||
iccData="6244310039574344=30112011558125900000"
|
iccData="6244310039574344=30112011558125900000"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|||||||
@ -78,6 +78,8 @@ class SharedViewModel @Inject constructor(
|
|||||||
val isEmv = SingleLiveEvent<Boolean>()
|
val isEmv = SingleLiveEvent<Boolean>()
|
||||||
|
|
||||||
private val settlementStatus = MutableLiveData<Boolean>()
|
private val settlementStatus = MutableLiveData<Boolean>()
|
||||||
|
private var settlementPrintInProgress = false
|
||||||
|
private var settlementPrintCompletedKey: String? = null
|
||||||
|
|
||||||
private val wavePayStatus = MutableLiveData<Boolean>()
|
private val wavePayStatus = MutableLiveData<Boolean>()
|
||||||
|
|
||||||
@ -419,17 +421,46 @@ class SharedViewModel @Inject constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun startPrintProcessSettlement() {
|
fun startPrintProcessSettlement(
|
||||||
|
onSuccess: () -> Unit,
|
||||||
|
onFailure: () -> Unit
|
||||||
|
) {
|
||||||
|
|
||||||
val detail = payDetail.value ?: return
|
val detail = payDetail.value ?: run {
|
||||||
|
onFailure()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
val printKey = "${detail.batchNo}:${detail.voucherNo}"
|
||||||
|
|
||||||
|
synchronized(this) {
|
||||||
|
if (settlementPrintCompletedKey == printKey || settlementPrintInProgress) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
settlementPrintInProgress = true
|
||||||
|
}
|
||||||
|
|
||||||
PrintXReceipt.getInstance()
|
PrintXReceipt.getInstance()
|
||||||
.printSmileSettlementReport(detail, object : PrintXStatus {
|
.printSmileSettlementReport(detail, object : PrintXStatus {
|
||||||
|
|
||||||
|
private var callbackHandled = false
|
||||||
|
|
||||||
override fun onSuccess() {
|
override fun onSuccess() {
|
||||||
|
synchronized(this) {
|
||||||
|
if (callbackHandled) return
|
||||||
|
callbackHandled = true
|
||||||
|
settlementPrintInProgress = false
|
||||||
|
settlementPrintCompletedKey = printKey
|
||||||
|
}
|
||||||
|
onSuccess()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onFailure() {
|
override fun onFailure() {
|
||||||
|
synchronized(this) {
|
||||||
|
if (callbackHandled) return
|
||||||
|
callbackHandled = true
|
||||||
|
settlementPrintInProgress = false
|
||||||
|
}
|
||||||
|
onFailure()
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@ -37,6 +37,9 @@ public interface PayDetailDao {
|
|||||||
@Delete
|
@Delete
|
||||||
void deletePayDetail(PayDetail payDetail);
|
void deletePayDetail(PayDetail payDetail);
|
||||||
|
|
||||||
|
@Query("DELETE FROM paydetail WHERE transactionType = 10")
|
||||||
|
void deleteReversalTransactions();
|
||||||
|
|
||||||
// 13 = CASH DEPOSIT & 9 = CASH ADVANCE & 14 = FUND TRANSFER
|
// 13 = CASH DEPOSIT & 9 = CASH ADVANCE & 14 = FUND TRANSFER
|
||||||
@Query("SELECT * FROM paydetail WHERE isSettle = 0 AND transactionType = 13 OR transactionType = 9 AND isSettle = 0 OR transactionType = 14 AND isSettle = 0")
|
@Query("SELECT * FROM paydetail WHERE isSettle = 0 AND transactionType = 13 OR transactionType = 9 AND isSettle = 0 OR transactionType = 14 AND isSettle = 0")
|
||||||
LiveData<List<PayDetail>> getSettlement();
|
LiveData<List<PayDetail>> getSettlement();
|
||||||
|
|||||||
@ -209,5 +209,9 @@ public class Repository {
|
|||||||
payDetailDao.deletePayDetail(payDetail);
|
payDetailDao.deletePayDetail(payDetail);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void deleteReversalTransactions() {
|
||||||
|
payDetailDao.deleteReversalTransactions();
|
||||||
|
}
|
||||||
|
|
||||||
public LiveData<List<PayDetail>> getAllTrans() { return payDetailDao.getAllTrans(); }
|
public LiveData<List<PayDetail>> getAllTrans() { return payDetailDao.getAllTrans(); }
|
||||||
}
|
}
|
||||||
|
|||||||
@ -13,8 +13,6 @@ import java.text.DecimalFormat;
|
|||||||
import java.text.NumberFormat;
|
import java.text.NumberFormat;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
|
||||||
import sunmi.sunmiui.utils.LogUtil;
|
|
||||||
|
|
||||||
public class PrintUtils {
|
public class PrintUtils {
|
||||||
|
|
||||||
public static PrintUtils getInstance() {
|
public static PrintUtils getInstance() {
|
||||||
@ -265,18 +263,18 @@ public class PrintUtils {
|
|||||||
public String processNameSpaceSecondLine(String input) {
|
public String processNameSpaceSecondLine(String input) {
|
||||||
String[] words = input.split(" ");
|
String[] words = input.split(" ");
|
||||||
|
|
||||||
if (input.length() < 15) {
|
if (input.length() < 20) {
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
if (words.length == 3 && input.length() > 15) {
|
if (words.length == 3 && input.length() > 20) {
|
||||||
return words[2];
|
return words[2];
|
||||||
} else if (words.length == 2 && input.length() <= 15) {
|
} else if (words.length == 2 && input.length() <= 20) {
|
||||||
return "";
|
return "";
|
||||||
} else if (words.length == 2 && input.length() > 15) {
|
} else if (words.length == 2 && input.length() > 20) {
|
||||||
return words[1];
|
return words[1];
|
||||||
} else {
|
} else {
|
||||||
return input.substring(15);
|
return input.substring(20);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user