From 9183c97aef45d5cd3776fa02d17300b72f5130ae Mon Sep 17 00:00:00 2001 From: Pritimay Sarkar Date: Thu, 21 Dec 2023 16:14:29 +0530 Subject: [PATCH 1/5] add slope based class --- app/build.gradle | 6 +- .../hpostesting/data/constant/Constants.kt | 12 ++-- .../data/model/patient/HemoCubeTestData.kt | 3 + .../presentation/hemocube/HemoCubeFragment.kt | 66 ++++++++++++++++++- .../hemocube/HemoCubeViewModel.kt | 3 + 5 files changed, 80 insertions(+), 10 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 0a45e20..3fc030e 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -16,11 +16,11 @@ android { // prod - production, preprod - preproduction, quality - qc defaultConfig { - applicationId "in.sminnovations.hpostesting" + applicationId "in.sminnovations.hpostesting.preprod" minSdk 21 targetSdk 34 - versionCode 56 - versionName "2.1.56" + versionCode 60 + versionName "2.1.60" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" } diff --git a/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt b/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt index 891c3a5..5f65f52 100644 --- a/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt +++ b/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt @@ -128,21 +128,21 @@ object Constants { listOf(1.0, 0.0) // LED4 ), "HCV-000-3005" to listOf( - listOf(1.7272, -1.1977), // LED1, 435nm + listOf(1.3801, -0.372), // LED1, 435nm listOf(0.581462456, -0.58502), // LED2, 415nm - listOf(0.2304, -0.0145), // LED3, 555nm + listOf(0.4565, -0.0371), // LED3, 555nm listOf(1.0, 0.0) // LED4 ), "HCV-000-3006" to listOf( - listOf(1.7272, -1.1977), // LED1, 435nm + listOf(1.3801, -0.372), // LED1, 435nm listOf(0.581462456, -0.58502), // LED2, 415nm - listOf(0.2304, -0.0145), // LED3, 555nm + listOf(0.4565, -0.0371), // LED3, 555nm listOf(1.0, 0.0) // LED4 ), "HCV-000-3007" to listOf( - listOf(1.7272, -1.1977), // LED1, 435nm + listOf(1.8445, -0.8213), // LED1, 435nm listOf(0.581462456, -0.58502), // LED2, 415nm - listOf(0.2304, -0.0145), // LED3, 555nm + listOf(0.4613, -0.0831), // LED3, 555nm listOf(1.0, 0.0) // LED4 ), "HCV-000-3008" to listOf( diff --git a/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt b/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt index 5b22aee..64719fe 100644 --- a/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt +++ b/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt @@ -46,9 +46,12 @@ data class HemoCubeTestData( var deviceRatio: Double? = null, var calculatedRatio: Double? = null, var predictedDenovixRatio: Double? = null, + var slopeRatio: Double? = null, var coefficients: String? = "", var classificationResult: String = "", var prdClassification: String = "", + var deviceRatioClass: String = "", + var slopeRatioClass: String = "", var errorMessages: String = "", var batteryLevel: String = "", var batteryCapacity: String = "", diff --git a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt index 7128812..046e426 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt @@ -504,6 +504,9 @@ class HemoCubeFragment : Fragment() { _predictedDenovixRatio = fittedAbs3.div(fittedAbs1) + val _slopeRatio = (fittedAbs1 - fittedAbs2) / (435 - 415) + val slopeClass = slopeRatioClassification(_slopeRatio) + if (fittedAbs1 <= fittedAbs2) { validationError = true allErrorMessages += "Error: Invalid Test. Problem with de-oxygenation" + "\n" @@ -521,6 +524,14 @@ class HemoCubeFragment : Fragment() { } } + if ((led1Average < 0.7 || led2Average < 0.7 || led3Average < 0.7 || led4Average < 0.7) && _slopeRatio > 35.0) { + validationError = true + activity?.runOnUiThread { + binding.errorMessage.text = "Severely Low Hb. Repeat test with 12 ul in 2 ml Buffer" + binding.errorMessage.visibility = View.VISIBLE + } + } + if (fittedAbs3 < 0.1) { validationError = true allErrorMessages += "Error: Low Hb. Repeat test" + "\n" @@ -552,11 +563,14 @@ class HemoCubeFragment : Fragment() { this.deviceRatio = deviceRatio this.calculatedRatio = calculateRatio(deviceRatio) this.predictedDenovixRatio = _predictedDenovixRatio + this.slopeRatio = _slopeRatio this.coefficients = currentDeviceData?.coefficients?.get(0) .toString() + ", " + currentDeviceData?.coefficients?.get(1).toString() this.classificationResult = findResult(calculatedRatio) this.prdClassification = absorbanceBasedClassification(predictedDenovixRatio) - hemoCubeViewModel.messages.postValue(this.prdClassification) + this.deviceRatioClass = deviceRatioClassification(deviceRatio) + this.slopeRatioClass = slopeRatioClass + hemoCubeViewModel.messages.postValue("Pdr: ${this.prdClassification}\n, Slope: ${this.slopeRatioClass}\n, Device: ${this.deviceRatioClass}") this.errorMessages = allErrorMessages this.resultData = deviceLog this.batteryLevel = hemoCubeViewModel.getBatteryLevel().toString() @@ -626,6 +640,56 @@ class HemoCubeFragment : Fragment() { return getString(R.string.invalid) } + fun deviceRatioClassification(ratio: Double?): String { + try { + hemoCubeViewModel.messages.postValue("result classification") + if (ratio != null) { + if (ratio in 0.0..0.4) + return getString(R.string.normal) + if (ratio in 0.4..0.45) + return getString(R.string.negative_borderline) + if (ratio in 0.45..0.55) + return getString(R.string.sickle_cell_trait) + if (ratio in 0.55..0.575) + return getString(R.string.positive_for_sickle_cell) + if (ratio in 0.09..1.0) + return getString(R.string.sickle_cell_disease) + } else { + return getString(R.string.invalid) + } + } catch (e: Exception) { + showToast(R.string.error_classification) + Firebase.crashlytics.recordException(e) + return getString(R.string.error) + } + return getString(R.string.invalid) + } + + fun slopeRatioClassification(ratio: Double?): String { + try { + hemoCubeViewModel.messages.postValue("result classification") + if (ratio != null) { + if (ratio in 0.0..35.0) + return getString(R.string.normal) + if (ratio in 35.0..40.0) + return getString(R.string.negative_borderline) + if (ratio in 40.0..70.0) + return getString(R.string.sickle_cell_trait) + if (ratio in 70.0..75.0) + return getString(R.string.positive_for_sickle_cell) + if (ratio in 75.0..300.0) + return getString(R.string.sickle_cell_disease) + } else { + return getString(R.string.invalid) + } + } catch (e: Exception) { + showToast(R.string.error_classification) + Firebase.crashlytics.recordException(e) + return getString(R.string.error) + } + return getString(R.string.invalid) + } + private fun absorbanceBasedClassification(predictedDenovixRatio: Double?): String { try { hemoCubeViewModel.messages.postValue("result classification") diff --git a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt index f32fa04..bffd814 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt @@ -129,10 +129,13 @@ class HemoCubeViewModel @Inject constructor( testDetails?.deviceRatio = DataHolder.hemoCubeTestData?.deviceRatio testDetails?.predictedDenovixRatio = DataHolder.hemoCubeTestData?.predictedDenovixRatio testDetails?.calculatedRatio = DataHolder.hemoCubeTestData?.calculatedRatio + testDetails?.slopeRatio = DataHolder.hemoCubeTestData?.slopeRatio testDetails?.coefficients = DataHolder.hemoCubeTestData?.coefficients testDetails?.classificationResult = DataHolder.hemoCubeTestData?.classificationResult!! testDetails?.prdClassification = DataHolder.hemoCubeTestData?.prdClassification.toString() + testDetails?.deviceRatioClass = DataHolder.hemoCubeTestData?.deviceRatioClass!! + testDetails?.slopeRatioClass = DataHolder.hemoCubeTestData?.slopeRatioClass!! testDetails?.batteryLevel = DataHolder.hemoCubeTestData?.batteryLevel.toString() testDetails?.batteryCapacity = DataHolder.hemoCubeTestData?.batteryCapacity.toString() testDetails?.batteryMaxCapacity = From 7a4b68690d035040d751cc7822065f66dc125a7b Mon Sep 17 00:00:00 2001 From: Pritimay Sarkar Date: Sat, 23 Dec 2023 18:19:13 +0530 Subject: [PATCH 2/5] add new slope class thresholds --- app/build.gradle | 4 ++-- .../example/hpostesting/data/dao/MyDataBase.kt | 2 +- .../presentation/hemocube/HemoCubeFragment.kt | 18 ++++++++++-------- .../layout/fragment_hemo_cube_reference.xml | 2 +- 4 files changed, 14 insertions(+), 12 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 3fc030e..7b12f84 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -19,8 +19,8 @@ android { applicationId "in.sminnovations.hpostesting.preprod" minSdk 21 targetSdk 34 - versionCode 60 - versionName "2.1.60" + versionCode 62 + versionName "2.1.62" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" } diff --git a/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt b/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt index 49115b7..b291c72 100644 --- a/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt +++ b/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt @@ -11,7 +11,7 @@ import com.example.hpostesting.data.model.patient.HemoCubeTestData import com.google.android.datatransport.runtime.dagger.Provides import javax.inject.Singleton -@Database(entities = [UserData::class, HemoCubeTestData::class, DeviceData::class], version = 13, exportSchema = false) +@Database(entities = [UserData::class, HemoCubeTestData::class, DeviceData::class], version = 14, exportSchema = false) @TypeConverters(Converters::class) abstract class MyDatabase : RoomDatabase() { abstract fun userDao(): UserDao diff --git a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt index 046e426..0de8422 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt @@ -26,6 +26,7 @@ import com.google.firebase.ktx.Firebase import com.google.firebase.perf.ktx.performance import `in`.sminnovations.hpostesting.R import `in`.sminnovations.hpostesting.databinding.FragmentHemoCubeReferenceBinding +import kotlin.math.abs import kotlin.math.log10 class HemoCubeFragment : Fragment() { @@ -504,7 +505,8 @@ class HemoCubeFragment : Fragment() { _predictedDenovixRatio = fittedAbs3.div(fittedAbs1) - val _slopeRatio = (fittedAbs1 - fittedAbs2) / (435 - 415) + val slope = (led1Average - led2Average) / (435 - 415) + val _slopeRatio = abs(led3Average / slope) val slopeClass = slopeRatioClassification(_slopeRatio) if (fittedAbs1 <= fittedAbs2) { @@ -569,8 +571,8 @@ class HemoCubeFragment : Fragment() { this.classificationResult = findResult(calculatedRatio) this.prdClassification = absorbanceBasedClassification(predictedDenovixRatio) this.deviceRatioClass = deviceRatioClassification(deviceRatio) - this.slopeRatioClass = slopeRatioClass - hemoCubeViewModel.messages.postValue("Pdr: ${this.prdClassification}\n, Slope: ${this.slopeRatioClass}\n, Device: ${this.deviceRatioClass}") + this.slopeRatioClass = slopeClass + hemoCubeViewModel.messages.postValue("Slope Ratio: ${slopeRatio},\n Slope: ${this.slopeRatioClass}\n") this.errorMessages = allErrorMessages this.resultData = deviceLog this.batteryLevel = hemoCubeViewModel.getBatteryLevel().toString() @@ -669,15 +671,15 @@ class HemoCubeFragment : Fragment() { try { hemoCubeViewModel.messages.postValue("result classification") if (ratio != null) { - if (ratio in 0.0..35.0) + if (ratio in 0.0..30.0) return getString(R.string.normal) - if (ratio in 35.0..40.0) + if (ratio in 30.0..35.0) return getString(R.string.negative_borderline) - if (ratio in 40.0..70.0) + if (ratio in 35.0..50.0) return getString(R.string.sickle_cell_trait) - if (ratio in 70.0..75.0) + if (ratio in 50.0..60.0) return getString(R.string.positive_for_sickle_cell) - if (ratio in 75.0..300.0) + if (ratio > 60.0) return getString(R.string.sickle_cell_disease) } else { return getString(R.string.invalid) diff --git a/app/src/main/res/layout/fragment_hemo_cube_reference.xml b/app/src/main/res/layout/fragment_hemo_cube_reference.xml index 9b166f9..18300de 100644 --- a/app/src/main/res/layout/fragment_hemo_cube_reference.xml +++ b/app/src/main/res/layout/fragment_hemo_cube_reference.xml @@ -210,7 +210,7 @@ style="@style/title1_1" android:visibility="gone" android:layout_width="0dp" - android:layout_height="180dp" + android:layout_height="0dp" android:layout_marginHorizontal="24dp" android:layout_marginTop="72dp" android:gravity="center" From f6b1b83f24de406806e54a09cb94c28f1daed7ba Mon Sep 17 00:00:00 2001 From: Pritimay Sarkar Date: Tue, 2 Jan 2024 10:56:38 +0530 Subject: [PATCH 3/5] add gains commands and save gains data --- app/build.gradle | 2 +- .../hpostesting/data/constant/Constants.kt | 152 +++++++++++++++- .../data/constant/HemoCubeCommands.kt | 6 +- .../hpostesting/data/dao/MyDataBase.kt | 2 +- .../data/model/patient/HemoCubeTestData.kt | 16 ++ .../HemoCubeBufferCheckFragment.kt | 5 +- .../presentation/hemocube/HemoCubeFragment.kt | 171 ++++++++++++++++-- .../hemocube/HemoCubeViewModel.kt | 12 ++ .../layout/fragment_hemo_cube_reference.xml | 27 +-- 9 files changed, 357 insertions(+), 36 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 7b12f84..5a97234 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -16,7 +16,7 @@ android { // prod - production, preprod - preproduction, quality - qc defaultConfig { - applicationId "in.sminnovations.hpostesting.preprod" + applicationId "in.sminnovations.hpostesting" minSdk 21 targetSdk 34 versionCode 62 diff --git a/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt b/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt index 5f65f52..c02e665 100644 --- a/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt +++ b/app/src/main/java/com/example/hpostesting/data/constant/Constants.kt @@ -73,7 +73,17 @@ object Constants { "HCV-000-3007", "HCV-000-3008", "HCV-000-3009", - "HCV-000-3010" + "HCV-000-3010", + "HCV-000-3011", + "HCV-000-3012", + "HCV-000-3013", + "HCV-000-3014", + "HCV-000-3015", + "HCV-000-3016", + "HCV-000-3017", + "HCV-000-3018", + "HCV-000-3019", + "HCV-000-3020" ) const val password = "SMI@12345" @@ -100,7 +110,23 @@ object Constants { const val TEST_STATUS_CODE_SAMPLE_COMPLETED = 9.0 const val TEST_STATUS_CODE_SAMPLE_PRINT_STARTED = 10.0 const val TEST_STATUS_CODE_SAMPLE_PRINT_COMPLETED = 11.0 - const val TEST_STATUS_CODE_TEST_COMPLETED = 12.0 + const val TEST_STATUS_CODE_FIRST_GAIN_STARTED = 12.0 + const val TEST_STATUS_CODE_FIRST_GAIN_COMPLETED = 13.0 + const val TEST_STATUS_CODE_FIRST_GAIN_PRINT_STARTED = 14.0 + const val TEST_STATUS_CODE_FIRST_GAIN_PRINT_COMPLETED = 15.0 + const val TEST_STATUS_CODE_SECOND_GAIN_STARTED = 16.0 + const val TEST_STATUS_CODE_SECOND_GAIN_COMPLETED = 17.0 + const val TEST_STATUS_CODE_SECOND_GAIN_PRINT_STARTED = 18.0 + const val TEST_STATUS_CODE_SECOND_GAIN_PRINT_COMPLETED = 19.0 + const val TEST_STATUS_CODE_THIRD_GAIN_STARTED = 20.0 + const val TEST_STATUS_CODE_THIRD_GAIN_COMPLETED = 21.0 + const val TEST_STATUS_CODE_THIRD_GAIN_PRINT_STARTED = 22.0 + const val TEST_STATUS_CODE_THIRD_GAIN_PRINT_COMPLETED = 23.0 + const val TEST_STATUS_CODE_FORTH_GAIN_STARTED = 24.0 + const val TEST_STATUS_CODE_FORTH_GAIN_COMPLETED = 25.0 + const val TEST_STATUS_CODE_FORTH_GAIN_PRINT_STARTED = 26.0 + const val TEST_STATUS_CODE_FORTH_GAIN_PRINT_COMPLETED = 27.0 + const val TEST_STATUS_CODE_TEST_COMPLETED = 30.0 val DEVICE_CONFIGURATION: Map>> = mapOf>>( "HCV-000-3001" to listOf( @@ -163,6 +189,66 @@ object Constants { listOf(0.2304, -0.0145), // LED3, 555nm listOf(1.0, 0.0) // LED4 ), + "HCV-000-3011" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3012" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3013" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3014" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3015" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3016" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3017" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3018" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3019" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), + "HCV-000-3020" to listOf( + listOf(1.7272, -1.1977), // LED1, 435nm + listOf(0.581462456, -0.58502), // LED2, 415nm + listOf(0.2304, -0.0145), // LED3, 555nm + listOf(1.0, 0.0) // LED4 + ), ) const val INCUBATION_TIME_MIN = 0 @@ -229,6 +315,66 @@ object Constants { listOf(24500, 26250), listOf(24500, 26250), listOf(24500, 26250), - ) + ), + "HCV-000-3011" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3012" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3013" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3014" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3015" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3016" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3017" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3018" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3019" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), + "HCV-000-3020" to listOf( + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + listOf(24500, 26250), + ), ) } \ No newline at end of file diff --git a/app/src/main/java/com/example/hpostesting/data/constant/HemoCubeCommands.kt b/app/src/main/java/com/example/hpostesting/data/constant/HemoCubeCommands.kt index 1a806e2..4e06388 100644 --- a/app/src/main/java/com/example/hpostesting/data/constant/HemoCubeCommands.kt +++ b/app/src/main/java/com/example/hpostesting/data/constant/HemoCubeCommands.kt @@ -4,6 +4,10 @@ enum class HemoCubeCommands(val command: String) { startBuffer("B\r"), runDiagnostics("D\r"), startSample("S\r"), - getSample("P\r"), + PRINT_COMMAND("P\r"), getDeviceId("I\r"), + FIRST_GAIN_COMMAND("T\r"), + SECOND_GAIN_COMMAND("U\r"), + THIRD_GAIN_COMMAND("V\r"), + FORTH_GAIN_COMMAND("W\r"), } \ No newline at end of file diff --git a/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt b/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt index b291c72..9b44389 100644 --- a/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt +++ b/app/src/main/java/com/example/hpostesting/data/dao/MyDataBase.kt @@ -11,7 +11,7 @@ import com.example.hpostesting.data.model.patient.HemoCubeTestData import com.google.android.datatransport.runtime.dagger.Provides import javax.inject.Singleton -@Database(entities = [UserData::class, HemoCubeTestData::class, DeviceData::class], version = 14, exportSchema = false) +@Database(entities = [UserData::class, HemoCubeTestData::class, DeviceData::class], version = 17, exportSchema = false) @TypeConverters(Converters::class) abstract class MyDatabase : RoomDatabase() { abstract fun userDao(): UserDao diff --git a/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt b/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt index 64719fe..6426955 100644 --- a/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt +++ b/app/src/main/java/com/example/hpostesting/data/model/patient/HemoCubeTestData.kt @@ -43,6 +43,22 @@ data class HemoCubeTestData( var abs2: Double? = null, var abs3: Double? = null, var abs4: Double? = null, + var led1Gain1: Double? = null, + var led2Gain1: Double? = null, + var led3Gain1: Double? = null, + var led4Gain1: Double? = null, + var led1Gain2: Double? = null, + var led2Gain2: Double? = null, + var led3Gain2: Double? = null, + var led4Gain2: Double? = null, + var led1Gain3: Double? = null, + var led2Gain3: Double? = null, + var led3Gain3: Double? = null, + var led4Gain3: Double? = null, + var led1Gain4: Double? = null, + var led2Gain4: Double? = null, + var led3Gain4: Double? = null, + var led4Gain4: Double? = null, var deviceRatio: Double? = null, var calculatedRatio: Double? = null, var predictedDenovixRatio: Double? = null, diff --git a/app/src/main/java/com/example/hpostesting/presentation/buffercheck/HemoCubeBufferCheckFragment.kt b/app/src/main/java/com/example/hpostesting/presentation/buffercheck/HemoCubeBufferCheckFragment.kt index 96ace8c..3334585 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/buffercheck/HemoCubeBufferCheckFragment.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/buffercheck/HemoCubeBufferCheckFragment.kt @@ -1,15 +1,12 @@ package com.example.hpostesting.presentation.buffercheck import android.content.Context -import android.content.Intent import android.content.SharedPreferences import android.os.Bundle import android.view.LayoutInflater import android.view.View import android.view.ViewGroup -import android.view.inputmethod.InputMethodManager import android.widget.Toast -import androidx.core.content.ContextCompat import androidx.fragment.app.Fragment import androidx.fragment.app.activityViewModels import androidx.lifecycle.MutableLiveData @@ -305,7 +302,7 @@ class HemoCubeBufferCheckFragment : Fragment() { private fun fetchResult() { - (activity as HemocubeBufferCheckActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.getSample, + (activity as HemocubeBufferCheckActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.PRINT_COMMAND, object : UsbServiceListener { override fun onUsbRead(data: ByteArray?) {} diff --git a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt index 0de8422..889fada 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeFragment.kt @@ -28,6 +28,7 @@ import `in`.sminnovations.hpostesting.R import `in`.sminnovations.hpostesting.databinding.FragmentHemoCubeReferenceBinding import kotlin.math.abs import kotlin.math.log10 +import kotlin.math.round class HemoCubeFragment : Fragment() { @@ -38,6 +39,7 @@ class HemoCubeFragment : Fragment() { private var isOnline = false private var currentDeviceData: DeviceData? = null private var resultData: String = "" + private var currentResultData: String = "" private var isUsingExistingBuffer = false private var isTestOngoing = false private var startListening = MutableLiveData(false) @@ -262,7 +264,7 @@ class HemoCubeFragment : Fragment() { data?.let { val stringData = String(it) fullReadOutput.append(stringData) - handleUsbData(stringData, testStatusCode) + handleUsbData(stringData) } } @@ -295,13 +297,14 @@ class HemoCubeFragment : Fragment() { }) } - private fun handleUsbData(stringData: String, testStatusCode: Double) { + private fun handleUsbData(stringData: String) { if (stringData.contains("#")) { isTestOngoing = true } resultData += stringData - hemoCubeViewModel.deviceMessages.postValue(resultData) + currentResultData += stringData + hemoCubeViewModel.deviceMessages.postValue(currentResultData) when { resultData.contains("SNE") && this.testStatusCode < Constants.TEST_STATUS_CODE_CONFIG_COMPLETED -> { @@ -338,7 +341,7 @@ class HemoCubeFragment : Fragment() { } } - resultData.contains("#SS") && this.testStatusCode < Constants.TEST_STATUS_CODE_SAMPLE_STARTED -> { + resultData.contains("#SS1") && this.testStatusCode < Constants.TEST_STATUS_CODE_SAMPLE_STARTED -> { this.testStatusCode = Constants.TEST_STATUS_CODE_SAMPLE_STARTED activity?.runOnUiThread { binding.tvSubtitle4.text = getString(R.string.sample_started) @@ -346,14 +349,48 @@ class HemoCubeFragment : Fragment() { } } - resultData.contains("#SC") && this.testStatusCode < Constants.TEST_STATUS_CODE_SAMPLE_COMPLETED -> { + resultData.contains("#SC1") && this.testStatusCode < Constants.TEST_STATUS_CODE_SAMPLE_COMPLETED -> { this.testStatusCode = Constants.TEST_STATUS_CODE_SAMPLE_COMPLETED hemoCubeViewModel.messages.postValue( getString(R.string.sample_completed) + "\n" + getString(R.string.gathering_data)) fetchResult() + currentResultData = "" testingTrace.stop() } + currentResultData.contains("#SS2") && this.testStatusCode < Constants.TEST_STATUS_CODE_FIRST_GAIN_STARTED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FIRST_GAIN_STARTED + hemoCubeViewModel.messages.postValue("1.3X Gain Started") + } + + currentResultData.contains("#SC2") && this.testStatusCode < Constants.TEST_STATUS_CODE_FIRST_GAIN_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FIRST_GAIN_COMPLETED + hemoCubeViewModel.messages.postValue("1.3X Gain Completed") + fetchResult() + } + + currentResultData.contains("#SS3") && this.testStatusCode < Constants.TEST_STATUS_CODE_SECOND_GAIN_STARTED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_SECOND_GAIN_STARTED + hemoCubeViewModel.messages.postValue("2X Gain Started") + } + + currentResultData.contains("#SC3") && this.testStatusCode < Constants.TEST_STATUS_CODE_SECOND_GAIN_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_SECOND_GAIN_COMPLETED + hemoCubeViewModel.messages.postValue("2X Gain Completed") + fetchResult() + } + + currentResultData.contains("#SS5") && this.testStatusCode < Constants.TEST_STATUS_CODE_FORTH_GAIN_STARTED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FORTH_GAIN_STARTED + hemoCubeViewModel.messages.postValue("7.6X Gain Started") + } + + currentResultData.contains("#SC5") && this.testStatusCode < Constants.TEST_STATUS_CODE_FORTH_GAIN_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FORTH_GAIN_COMPLETED + hemoCubeViewModel.messages.postValue("7.6X Gain Completed") + fetchResult() + } + resultData.contains("REND") && this.testStatusCode < Constants.TEST_STATUS_CODE_SAMPLE_PRINT_COMPLETED -> { this.testStatusCode = Constants.TEST_STATUS_CODE_SAMPLE_PRINT_COMPLETED hemoCubeViewModel.messages.postValue( @@ -395,6 +432,60 @@ class HemoCubeFragment : Fragment() { led4SampleForDevice = resultLines[8].split(' ')[1].split('\r')[0].trim().toDoubleOrNull()!! processResult() + sendFirstGainCommand() + currentResultData = "" + } + + currentResultData.contains("REND") && this.testStatusCode >= Constants.TEST_STATUS_CODE_FIRST_GAIN_COMPLETED && this.testStatusCode < Constants.TEST_STATUS_CODE_FIRST_GAIN_PRINT_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FIRST_GAIN_PRINT_COMPLETED + hemoCubeViewModel.messages.postValue("1.3X gain data gathered") + + val resultLines = currentResultData.split("\\s+(?=LB|LS)".toRegex()) + DataHolder.hemoCubeTestData?.apply { + led1Gain1 = resultLines[5].split(' ')[1].trim().toDoubleOrNull()!! + led2Gain1 = resultLines[6].split(' ')[1].trim().toDoubleOrNull()!! + led3Gain1 = resultLines[7].split(' ')[1].trim().toDoubleOrNull()!! + led4Gain1 = resultLines[8].split(' ')[1].split('\r')[0].trim().toDoubleOrNull()!! + } + + sendSecondGainCommand() + currentResultData = "" + } + + currentResultData.contains("REND") && this.testStatusCode >= Constants.TEST_STATUS_CODE_FIRST_GAIN_PRINT_COMPLETED && this.testStatusCode < Constants.TEST_STATUS_CODE_SECOND_GAIN_PRINT_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_SECOND_GAIN_PRINT_COMPLETED + hemoCubeViewModel.messages.postValue("2X gain data gathered") + + val resultLines = currentResultData.split("\\s+(?=LB|LS)".toRegex()) + DataHolder.hemoCubeTestData?.apply { + led1Gain2 = resultLines[5].split(' ')[1].trim().toDoubleOrNull()!! + led2Gain2 = resultLines[6].split(' ')[1].trim().toDoubleOrNull()!! + led3Gain2 = resultLines[7].split(' ')[1].trim().toDoubleOrNull()!! + led4Gain2 = resultLines[8].split(' ')[1].split('\r')[0].trim().toDoubleOrNull()!! + } + + sendForthGainCommand() + currentResultData = "" + } + + currentResultData.contains("REND") && this.testStatusCode >= Constants.TEST_STATUS_CODE_SECOND_GAIN_PRINT_COMPLETED && this.testStatusCode < Constants.TEST_STATUS_CODE_FORTH_GAIN_PRINT_COMPLETED -> { + this.testStatusCode = Constants.TEST_STATUS_CODE_FORTH_GAIN_PRINT_COMPLETED + hemoCubeViewModel.messages.postValue("7.6X gain data gathered") + + val resultLines = currentResultData.split("\\s+(?=LB|LS)".toRegex()) + DataHolder.hemoCubeTestData?.apply { + led1Gain4 = resultLines[5].split(' ')[1].trim().toDoubleOrNull()!! + led2Gain4 = resultLines[6].split(' ')[1].trim().toDoubleOrNull()!! + led3Gain4 = resultLines[7].split(' ')[1].trim().toDoubleOrNull()!! + led4Gain4 = resultLines[8].split(' ')[1].split('\r')[0].trim().toDoubleOrNull()!! + } + + activity?.runOnUiThread { + binding.btnSubmit.visibility = View.VISIBLE + binding.btnSubmit.isEnabled = true + binding.btnSubmit.isClickable = true + binding.clParent.setBackgroundColor(Color.parseColor("#edfffd")) + } } } } @@ -482,8 +573,6 @@ class HemoCubeFragment : Fragment() { binding.errorMessage.text = getString(R.string.error_improper_buffer_high) binding.errorMessage.visibility = View.VISIBLE - binding.btnSubmit.isEnabled = true - binding.btnSubmit.isClickable = true } } @@ -572,7 +661,7 @@ class HemoCubeFragment : Fragment() { this.prdClassification = absorbanceBasedClassification(predictedDenovixRatio) this.deviceRatioClass = deviceRatioClassification(deviceRatio) this.slopeRatioClass = slopeClass - hemoCubeViewModel.messages.postValue("Slope Ratio: ${slopeRatio},\n Slope: ${this.slopeRatioClass}\n") + hemoCubeViewModel.messages.postValue("Slope Ratio: ${round(slopeRatio!!)},\n Slope Class: ${this.slopeRatioClass}\n") this.errorMessages = allErrorMessages this.resultData = deviceLog this.batteryLevel = hemoCubeViewModel.getBatteryLevel().toString() @@ -596,12 +685,12 @@ class HemoCubeFragment : Fragment() { } // if (!validationError) { - activity?.runOnUiThread { - binding.btnSubmit.visibility = View.VISIBLE - binding.btnSubmit.isEnabled = true - binding.btnSubmit.isClickable = true - binding.clParent.setBackgroundColor(Color.parseColor("#edfffd")) - } +// activity?.runOnUiThread { +// binding.btnSubmit.visibility = View.VISIBLE +// binding.btnSubmit.isEnabled = true +// binding.btnSubmit.isClickable = true +// binding.clParent.setBackgroundColor(Color.parseColor("#edfffd")) +// } // } } catch (e: Exception) { Toast.makeText( @@ -752,10 +841,62 @@ class HemoCubeFragment : Fragment() { }) } + private fun sendFirstGainCommand() { + hemoCubeViewModel.progressBar.postValue(true) + + (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.FIRST_GAIN_COMMAND, + object : UsbServiceListener { + override fun onUsbRead(data: ByteArray?) {} + + override fun onUsbError(e: Exception?) { + hemoCubeViewModel.progressBar.postValue(false) + } + }) + } + + private fun sendSecondGainCommand() { + hemoCubeViewModel.progressBar.postValue(true) + + (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.SECOND_GAIN_COMMAND, + object : UsbServiceListener { + override fun onUsbRead(data: ByteArray?) {} + + override fun onUsbError(e: Exception?) { + hemoCubeViewModel.progressBar.postValue(false) + } + }) + } + + private fun sendThirdGainCommand() { + hemoCubeViewModel.progressBar.postValue(true) + + (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.THIRD_GAIN_COMMAND, + object : UsbServiceListener { + override fun onUsbRead(data: ByteArray?) {} + + override fun onUsbError(e: Exception?) { + hemoCubeViewModel.progressBar.postValue(false) + } + }) + } + + private fun sendForthGainCommand() { + hemoCubeViewModel.progressBar.postValue(true) + + (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.FORTH_GAIN_COMMAND, + object : UsbServiceListener { + override fun onUsbRead(data: ByteArray?) {} + + override fun onUsbError(e: Exception?) { + hemoCubeViewModel.progressBar.postValue(false) + } + }) + } + private fun fetchResult() { hemoCubeViewModel.progressBar.postValue(true) - (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.getSample, + (activity as HemocubeActivity).mService.sendAndListenToHemoCube(HemoCubeCommands.PRINT_COMMAND, object : UsbServiceListener { override fun onUsbRead(data: ByteArray?) {} diff --git a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt index bffd814..855df7c 100644 --- a/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt +++ b/app/src/main/java/com/example/hpostesting/presentation/hemocube/HemoCubeViewModel.kt @@ -126,6 +126,18 @@ class HemoCubeViewModel @Inject constructor( testDetails?.abs2 = DataHolder.hemoCubeTestData?.abs2 testDetails?.abs3 = DataHolder.hemoCubeTestData?.abs3 testDetails?.abs4 = DataHolder.hemoCubeTestData?.abs4 + testDetails?.led1Gain1 = DataHolder.hemoCubeTestData?.led1Gain1 + testDetails?.led2Gain1 = DataHolder.hemoCubeTestData?.led2Gain1 + testDetails?.led3Gain1 = DataHolder.hemoCubeTestData?.led3Gain1 + testDetails?.led4Gain1 = DataHolder.hemoCubeTestData?.led4Gain1 + testDetails?.led1Gain2 = DataHolder.hemoCubeTestData?.led1Gain2 + testDetails?.led2Gain2 = DataHolder.hemoCubeTestData?.led2Gain2 + testDetails?.led3Gain2 = DataHolder.hemoCubeTestData?.led3Gain2 + testDetails?.led4Gain2 = DataHolder.hemoCubeTestData?.led4Gain2 + testDetails?.led1Gain4 = DataHolder.hemoCubeTestData?.led1Gain4 + testDetails?.led2Gain4 = DataHolder.hemoCubeTestData?.led2Gain4 + testDetails?.led3Gain4 = DataHolder.hemoCubeTestData?.led3Gain4 + testDetails?.led4Gain4 = DataHolder.hemoCubeTestData?.led4Gain4 testDetails?.deviceRatio = DataHolder.hemoCubeTestData?.deviceRatio testDetails?.predictedDenovixRatio = DataHolder.hemoCubeTestData?.predictedDenovixRatio testDetails?.calculatedRatio = DataHolder.hemoCubeTestData?.calculatedRatio diff --git a/app/src/main/res/layout/fragment_hemo_cube_reference.xml b/app/src/main/res/layout/fragment_hemo_cube_reference.xml index 18300de..31e59be 100644 --- a/app/src/main/res/layout/fragment_hemo_cube_reference.xml +++ b/app/src/main/res/layout/fragment_hemo_cube_reference.xml @@ -205,20 +205,25 @@ app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/btn_submit" /> - + app:layout_constraintTop_toBottomOf="@id/error_message"> + + +