Compare commits

..

2 Commits

Author SHA1 Message Date
vsuryakumar
b22de3cf8b Merge branch 'main' of https://github.com/surya-x/sickle-cell-updated into navigation-db
Updated to main.
2023-02-13 13:09:46 +05:30
vsuryakumar
0b6d78dfbb Added navigation Drawer. 2023-02-03 11:22:31 +05:30
232 changed files with 2196 additions and 19111 deletions

7
.gitignore vendored
View File

@@ -1,7 +1,12 @@
*.iml
.gradle
/local.properties
/.idea
/.idea/caches
/.idea/libraries
/.idea/modules.xml
/.idea/workspace.xml
/.idea/navEditor.xml
/.idea/assetWizardSettings.xml
.DS_Store
/build
/captures

2
.idea/compiler.xml generated
View File

@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<bytecodeTargetLevel target="17" />
<bytecodeTargetLevel target="11" />
</component>
</project>

3
.idea/gradle.xml generated
View File

@@ -5,15 +5,14 @@
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="testRunner" value="GRADLE" />
<option name="distributionType" value="DEFAULT_WRAPPED" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="gradleJvm" value="jbr-17" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" />
</set>
</option>
<option name="resolveExternalAnnotations" value="false" />
</GradleProjectSettings>
</option>
</component>

6
.idea/kotlinc.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="KotlinJpsPluginSettings">
<option name="version" value="1.8.21" />
</component>
</project>

40
.idea/misc.xml generated Normal file
View File

@@ -0,0 +1,40 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="DesignSurface">
<option name="filePathToZoomLevelMap">
<map>
<entry key="app/src/main/res/drawable/ic_baseline_cancel_24.xml" value="0.1965" />
<entry key="app/src/main/res/drawable/ic_baseline_check_circle_24.xml" value="0.243" />
<entry key="app/src/main/res/drawable/ic_baseline_dot_24.xml" value="0.1785" />
<entry key="app/src/main/res/drawable/ic_baseline_file_download_24.xml" value="0.243" />
<entry key="app/src/main/res/drawable/ic_baseline_home_24.xml" value="0.243" />
<entry key="app/src/main/res/drawable/ic_baseline_new_label_24.xml" value="0.243" />
<entry key="app/src/main/res/drawable/ic_baseline_usb_24.xml" value="0.157" />
<entry key="app/src/main/res/drawable/ic_baseline_usb_off_24.xml" value="0.157" />
<entry key="app/src/main/res/drawable/progressbar_drawable.xml" value="0.1885" />
<entry key="app/src/main/res/drawable/result_background_green.xml" value="0.243" />
<entry key="app/src/main/res/drawable/result_background_red.xml" value="0.1785" />
<entry key="app/src/main/res/drawable/result_background_tellow.xml" value="0.1785" />
<entry key="app/src/main/res/font/inter_bold.xml" value="0.33487179487179486" />
<entry key="app/src/main/res/layout/activity_main.xml" value="0.165" />
<entry key="app/src/main/res/layout/activity_splash.xml" value="0.24375" />
<entry key="app/src/main/res/layout/activity_test_right.xml" value="0.24375" />
<entry key="app/src/main/res/layout/fragment_test_right_exp_reference.xml" value="0.25" />
<entry key="app/src/main/res/layout/fragment_test_right_exp_sample.xml" value="0.25" />
<entry key="app/src/main/res/layout/fragment_test_right_process.xml" value="0.24375" />
<entry key="app/src/main/res/layout/fragment_test_right_results.xml" value="0.25" />
<entry key="app/src/main/res/layout/table_item.xml" value="0.22407407407407406" />
<entry key="app/src/main/res/menu/menu.xml" value="0.25" />
<entry key="app/src/main/res/menu/my_menu.xml" value="0.25" />
<entry key="app/src/main/res/mipmap-anydpi-v26/hpos_icon.xml" value="0.1505" />
<entry key="app/src/main/res/mipmap-anydpi-v26/hpos_icon_round.xml" value="0.1505" />
</map>
</option>
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_11" default="true" project-jdk-name="Android Studio default JDK" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
</project>

2
app/.gitignore vendored
View File

@@ -1,3 +1,3 @@
/build
/google-services*
/google-services.json
/idea

View File

@@ -2,25 +2,19 @@ plugins {
id 'com.android.application'
id 'org.jetbrains.kotlin.android'
id 'com.google.firebase.appdistribution'
id 'dagger.hilt.android.plugin'
id 'com.google.gms.google-services'
id 'androidx.navigation.safeargs.kotlin'
id 'kotlin-kapt'
id 'com.google.firebase.crashlytics'
}
//apply plugin: 'kotlin-android'
android {
compileSdk 34
namespace 'in.sminnovations.hpostesting'
compileSdk 32
// prod - production, preprod - preproduction, quality - qc
defaultConfig {
applicationId "in.sminnovations.hpostesting"
applicationId "com.example.hpos"
minSdk 21
targetSdk 34
versionCode 26
versionName "2.1.26"
targetSdk 32
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
@@ -32,113 +26,41 @@ android {
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_17
targetCompatibility JavaVersion.VERSION_17
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '17'
jvmTarget = '1.8'
}
dataBinding {
enabled = true
}
buildFeatures {
viewBinding true
buildConfig = true
}
lint {
abortOnError false
checkReleaseBuilds false
}
packagingOptions {
exclude 'mockito-extensions/org.mockito.plugins.MockMaker'
}
}
dependencies {
implementation "com.google.dagger:hilt-android:2.46"
kapt "com.google.dagger:hilt-android-compiler:2.46"
implementation 'androidx.core:core-ktx:1.12.0'
implementation 'androidx.appcompat:appcompat:1.6.1'
implementation 'com.google.android.material:material:1.11.0'
implementation 'androidx.core:core-ktx:1.7.0'
implementation 'androidx.appcompat:appcompat:1.5.1'
implementation 'com.google.android.material:material:1.7.0'
implementation 'androidx.constraintlayout:constraintlayout:2.1.4'
implementation 'androidx.lifecycle:lifecycle-livedata-ktx:2.6.2'
implementation 'androidx.fragment:fragment-ktx:1.6.2'
//firebase
implementation platform('com.google.firebase:firebase-bom:32.1.0')
implementation("com.google.firebase:firebase-perf-ktx")
implementation("com.google.firebase:firebase-crashlytics-ktx")
implementation("com.google.firebase:firebase-analytics-ktx")
implementation 'com.google.firebase:firebase-firestore-ktx'
implementation 'com.google.firebase:firebase-auth-ktx'
implementation 'com.google.firebase:firebase-storage-ktx'
implementation 'com.firebaseui:firebase-ui-firestore:8.0.2'
implementation 'com.google.android.gms:play-services-auth:20.7.0'
implementation 'com.google.android.gms:play-services-location:21.0.1'
implementation 'com.google.android.gms:play-services-ads-identifier:18.0.1'
implementation 'com.google.android.things:androidthings:1.0'
implementation 'com.google.firebase:firebase-appdistribution:16.0.0-beta11'
implementation("com.google.firebase:firebase-appdistribution-api-ktx:16.0.0-beta11")
implementation 'androidx.preference:preference-ktx:1.2.1'
implementation 'androidx.preference:preference-ktx:1.2.1'
implementation 'com.google.android.play:core:1.10.3'
implementation 'io.nats:jnats:2.11.2'
// Testing
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
// Mockito dependencies
testImplementation 'org.mockito:mockito-core:3.12.4'
androidTestImplementation 'org.mockito:mockito-android:3.12.4'
androidTestImplementation 'org.mockito:mockito-inline:3.12.4'
testImplementation "androidx.arch.core:core-testing:2.2.0"
testImplementation 'org.jetbrains.kotlinx:kotlinx-coroutines-test:1.7.1'
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:2.6.2"
implementation 'com.opencsv:opencsv:5.5'
implementation 'com.github.mik3y:usb-serial-for-android:3.5.1'
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:2.5.1"
implementation 'com.opencsv:opencsv:4.6'
implementation 'com.github.mik3y:usb-serial-for-android:3.4.6'
implementation "androidx.fragment:fragment-ktx:1.6.2"
implementation "androidx.fragment:fragment-ktx:1.5.5"
// CSV read, write
implementation 'com.opencsv:opencsv:5.5'
implementation 'com.opencsv:opencsv:4.6'
// Barcode scanner
implementation 'com.journeyapps:zxing-android-embedded:4.3.0'
// implementation 'androidx.appcompat:appcompat:1.1.0'
// implementation "androidx.core:core-ktx:+"
// implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
// Google ML Kit usign play services
implementation 'com.google.android.gms:play-services-code-scanner:16.1.0'
//Room
implementation "androidx.room:room-ktx:2.6.1"
implementation "androidx.room:room-runtime:2.6.1"
kapt ("androidx.room:room-compiler:2.6.1")
//image
implementation 'com.github.bumptech.glide:glide:4.13.2'
annotationProcessor 'com.github.bumptech.glide:compiler:4.13.2'
// Navigation Component
implementation "androidx.navigation:navigation-fragment-ktx:2.7.6"
implementation "androidx.navigation:navigation-ui-ktx:2.7.6"
//Dagger - Hilt
implementation "com.google.dagger:hilt-android:2.46"
kapt "com.google.dagger:hilt-android-compiler:2.46"
kapt "androidx.hilt:hilt-compiler:1.1.0"
// Retrofit + GSON
implementation "com.squareup.retrofit2:retrofit:2.9.0"
implementation "com.squareup.retrofit2:converter-gson:2.9.0"
implementation("com.squareup.okhttp3:okhttp:4.9.3")
implementation "androidx.preference:preference-ktx:1.2.1"
implementation 'io.nats:jnats:2.11.2'
implementation 'com.google.android.play:core:1.10.3'
}
}
//repositories {
// mavenCentral()
//}

Binary file not shown.

View File

@@ -1,20 +0,0 @@
{
"version": 3,
"artifactType": {
"type": "APK",
"kind": "Directory"
},
"applicationId": "com.example.hpos",
"variantName": "release",
"elements": [
{
"type": "SINGLE",
"filters": [],
"attributes": [],
"versionCode": 1,
"versionName": "1.0",
"outputFile": "app-release.apk"
}
],
"elementType": "File"
}

View File

@@ -1,11 +1,13 @@
package com.example.hpostesting
package com.example.hpos
import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.platform.app.InstrumentationRegistry
import org.junit.Assert.*
import androidx.test.ext.junit.runners.AndroidJUnit4
import org.junit.Test
import org.junit.runner.RunWith
import org.junit.Assert.*
/**
* Instrumented test, which will execute on an Android device.
*

View File

@@ -1,30 +1,13 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
xmlns:tools="http://schemas.android.com/tools"
package="com.example.hpos">
<uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
<uses-permission
android:name="android.permission.BATTERY_STATS"
tools:ignore="ProtectedPermissions" />
<uses-feature android:name="android.hardware.camera" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-feature android:name="android.hardware.usb.host" />
<uses-permission android:name="android.permission.USB_PERMISSION" />
<application
android:name="com.example.hpostesting.HPOSTestingApplication"
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules"
@@ -32,87 +15,43 @@
android:label="@string/app_name"
android:roundIcon="@mipmap/hpos_icon_round"
android:supportsRtl="true"
android:theme="@style/Theme.HPOSTesting"
android:theme="@style/Theme.HPOS"
tools:targetApi="31">
<activity
android:name="com.example.hpostesting.presentation.hemocube.DigitalCardActivity"
android:exported="false" />
<activity
android:name="com.example.hpostesting.presentation.diagnostics.DiagnosticsActivity"
android:exported="false" />
<activity
android:name="com.example.hpostesting.presentation.hemocube.HemocubeActivity"
android:exported="false"
android:noHistory="true"
android:parentActivityName="com.example.hpostesting.presentation.MainActivity"
android:theme="@style/Theme.HPOS.NoActionBar"
android:windowSoftInputMode="adjustPan" />
<activity
android:name="com.example.hpostesting.presentation.buffercheck.HemocubeBufferCheckActivity"
android:exported="false"
android:noHistory="true"
android:parentActivityName="com.example.hpostesting.presentation.MainActivity"
android:theme="@style/Theme.HPOS.NoActionBar"
android:windowSoftInputMode="adjustPan" />
<activity
android:name="com.example.hpostesting.presentation.KitScanActivity"
android:exported="false"
android:noHistory="true"
android:theme="@style/Theme.HPOS.NoActionBar" />
<activity
android:name="com.example.hpostesting.presentation.dashboard.DashboardActivity"
android:exported="false"
android:label="@string/title_activity_dashboard"
android:theme="@style/Theme.HPOS.NoActionBar"
tools:ignore="AppLinkUrlError,MissingClass">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="content" />
<data android:scheme="file" />
<data android:mimeType="application/vnd.android.package-archive" />
</intent-filter>
</activity>
<service
android:name="com.example.hpostesting.presentation.testRight.UsbService"
android:name="com.example.hpos.presentation.testRight.UsbService"
android:enabled="true"
android:exported="false" />
<activity
android:name="com.example.hpostesting.presentation.SplashActivity"
android:name="com.example.hpos.presentation.SplashActivity"
android:exported="true"
android:noHistory="true"
android:theme="@style/AppTheme.NoActionBar">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name="com.example.hpostesting.presentation.testRight.TestRightActivity"
android:name="com.example.hpos.presentation.testRight.TestRightActivity"
android:exported="false"
android:noHistory="true"
android:parentActivityName="com.example.hpostesting.presentation.MainActivity"
android:theme="@style/Theme.HPOS.NoActionBar"
android:windowSoftInputMode="adjustPan">
android:windowSoftInputMode="adjustPan"
android:parentActivityName="com.example.hpos.presentation.MainActivity">
<!-- <intent-filter>-->
<!-- <action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" />-->
<!-- </intent-filter>-->
<!-- <intent-filter> -->
<!-- <action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" /> -->
<!-- </intent-filter> -->
<!-- <meta-data-->
<!-- android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"-->
<!-- android:resource="@xml/device_filter" />-->
</activity>
<!-- <meta-data -->
<!-- android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" -->
<!-- android:resource="@xml/device_filter" /> -->
</activity> <!-- android:theme="@style/Theme.HPOS.ActionBar" -->
<!-- android:theme="@style/Theme.HPOS.ActionBar"-->
<activity
android:name="com.example.hpostesting.presentation.MainActivity"
android:exported="true"
android:theme="@style/AppTheme.NoActionBar">
android:name="com.example.hpos.presentation.MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" />
</intent-filter>
@@ -120,22 +59,8 @@
<meta-data
android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"
android:resource="@xml/device_filter" />
</activity>
<activity
android:name="com.journeyapps.barcodescanner.CaptureActivity"
android:screenOrientation="portrait"
android:stateNotNeeded="true"
tools:replace="android:screenOrientation" />
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="com.example.hpostesting.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths" />
</provider>
</activity>
</application>

View File

@@ -1 +0,0 @@
BASE_URL= https://datacollection.micropcr.com/api/

View File

@@ -0,0 +1,11 @@
package com.example.hpos
import android.app.Application
class MyApplication : Application() {
// private val sampleDetails = PatientDetails("Change it later");
// fun getSampleDetails() : PatientDetails = sampleDetails
// fun setSampleDetails(sample: SampleDetails) {sampleDetails = sample}
}

View File

@@ -0,0 +1,27 @@
package com.example.hpos.data
import androidx.lifecycle.MutableLiveData
import com.example.hpos.data.model.TestRightDeviceConstants
import com.example.hpos.data.model.TestType
object DataHolder {
var selectedTestType: TestType = TestType.SICKLECERT
val usbConnected = MutableLiveData(true)
var isStoragePermissionGranted = false
var isAppFolderCreated = false
var appFolderPath = ""
var isReferenceTaken = false
var sampleReadCounter = 0
var deviceConstant: TestRightDeviceConstants? = null
var deviceSerialNumber: String = "ABCD"
/* Contains wavelength -> pixel no.*/
val wavelengthToPixelArray = ArrayList<Double>()
/* (For reference/baseline) Contains pixel no. -> Intensity of light falling on that pixel */
val intensityReferenceArray = ArrayList<Double>()
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data
package com.example.hpos.data
import android.content.Context
import android.content.SharedPreferences

View File

@@ -0,0 +1,7 @@
package com.example.hpos.data
import com.example.hpos.data.model.TestInfo
interface Repository {
suspend fun saveToDatabase(info: TestInfo)
}

View File

@@ -0,0 +1,12 @@
package com.example.hpos.data
import com.example.hpos.data.model.TestInfo
class RepositoryImpl : Repository {
override suspend fun saveToDatabase(info: TestInfo) {
}
}

View File

@@ -0,0 +1,29 @@
package com.example.hpos.data.constant
object Constants {
const val ACTION_USB_PERMISSION = "shanmukha.in.sickle_cell.USB_PERMISSION"
const val WRITE_TIMEOUT_MILLIS = 30000 // 30 sec
const val READ_TIMEOUT_MILLIS = 60000 // 1 min
const val DELAY_BETWEEN_COMMANDS: Long = 1000
const val TEST_RIGHT_TOTAL_PIXEL = 3694
const val MAXIMUM_TEST_ALLOWED_BEFORE_REFERENCE = 9999
const val RANGE_IN_RESULT_CALCULATIONS = 10
const val WAVELENGTH_OF_INTEREST_ONE = 427
const val WAVELENGTH_OF_INTEREST_TWO = 555
const val MIN_WAVELENGTH_RANGE_TO_RECORD = 350
const val MAX_WAVELENGTH_RANGE_TO_RECORD = 750
const val DEVICE_PRODUCT_ID = 24597
const val DEVICE_VENDOR_ID = 1027
const val ERROR_NORMAL = 400
const val ERROR_CRITICAL = 401
const val NO_OF_TIMES_TO_RUN_SAMPLE = 1
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.constant
package com.example.hpos.data.constant
enum class TestRightCommands(val command: String) {
led2Set50("led2 50\r"),

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.model
package com.example.hpos.data.model
data class CalculationVariableForTest(
var pixelNo: Int,

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.model
package com.example.hpos.data.model
data class ErrorMessage (
val message: String,

View File

@@ -1,6 +1,4 @@
package com.example.hpostesting.data.model
import com.example.hpostesting.data.model.test.TestRightResultType
package com.example.hpos.data.model
data class PatientData(
val name: String,

View File

@@ -0,0 +1,11 @@
package com.example.hpos.data.model
data class TestInfo(
val value: String,
val number1: String,
val number2: String,
val result: String,
val resultConfirmatory: String,
val directoryPath: String,
val fullPath: String
)

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.model.test
package com.example.hpos.data.model
data class TestRightCalculationData(
var absorbanceOne: Double?,

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.model.test
package com.example.hpos.data.model
data class TestRightDeviceConstants(
var a: String,

View File

@@ -1,10 +1,8 @@
package com.example.hpostesting.data.model.test
package com.example.hpos.data.model
enum class TestRightResultType {
NORMAL,
SICKLECELLTRAIT,
SICKLECELLDISEASE,
POSITIVEBORDERLINE,
NEGATIVEBORDERLINE,
UNDEFINED
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.data.model.test
package com.example.hpos.data.model
enum class TestType {
SICKLECERT,

View File

@@ -0,0 +1,94 @@
package com.example.hpos.domain
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestRightCalculationData
import com.example.hpos.data.model.TestRightResultType
class ResultCalculationWithAvgImpl : TestRightResultCalculation {
private val testRightCalculationData = TestRightCalculationData()
override fun getResults(wavelengthToAbsorbance: ArrayList<ArrayList<Double>>): TestRightCalculationData {
val startWavelengthOne =
Constants.WAVELENGTH_OF_INTEREST_ONE - Constants.RANGE_IN_RESULT_CALCULATIONS
val endWavelengthOne =
Constants.WAVELENGTH_OF_INTEREST_ONE + Constants.RANGE_IN_RESULT_CALCULATIONS + 1
var sumOfAbsorbanceAtOne = 0.0
var noOfAbsorbanceRecordedOne = 0
val startWavelengthTwo =
Constants.WAVELENGTH_OF_INTEREST_TWO - Constants.RANGE_IN_RESULT_CALCULATIONS
val endWavelengthTwo =
Constants.WAVELENGTH_OF_INTEREST_TWO + Constants.RANGE_IN_RESULT_CALCULATIONS + 1
var sumOfAbsorbanceAtTwo = 0.0
var noOfAbsorbanceRecordedTwo = 0
for (each in wavelengthToAbsorbance) {
if (each[0] >= startWavelengthOne && each[0] < endWavelengthOne) {
sumOfAbsorbanceAtOne += each[1]
noOfAbsorbanceRecordedOne++
}
if (each[0] >= startWavelengthTwo && each[0] < endWavelengthTwo) {
sumOfAbsorbanceAtTwo += each[1]
noOfAbsorbanceRecordedTwo++
}
}
val avgAbsorbanceOne = (sumOfAbsorbanceAtOne / noOfAbsorbanceRecordedOne)
val avgAbsorbanceTwo = (sumOfAbsorbanceAtTwo / noOfAbsorbanceRecordedTwo)
testRightCalculationData.absorbanceOne = avgAbsorbanceOne
testRightCalculationData.absorbanceTwo = avgAbsorbanceTwo
testRightCalculationData.result = calculateResultsAndRatio(avgAbsorbanceOne, avgAbsorbanceTwo)
return testRightCalculationData
}
private fun calculateResultsAndRatio(
absorbanceAtWaveOne: Double,
absorbanceAtWaveTwo: Double
): TestRightResultType {
if (absorbanceAtWaveOne != Double.MIN_VALUE && absorbanceAtWaveTwo != Double.MIN_VALUE && absorbanceAtWaveOne != 0.0) {
val value = absorbanceAtWaveTwo / absorbanceAtWaveOne
testRightCalculationData.ratioValue = value
if (value < 0.24 || value == 0.0) {
testRightCalculationData.ratioMinRange = 0.0
testRightCalculationData.ratioMaxRange = 0.24
return TestRightResultType.NORMAL
} else if (value >= 0.24 && value < 0.30) {
testRightCalculationData.ratioMinRange = 0.24
testRightCalculationData.ratioMaxRange = 0.30
return TestRightResultType.SICKLECELLTRAIT
} else if (value >= 0.30) {
testRightCalculationData.ratioMinRange = 0.30
testRightCalculationData.ratioMaxRange = 999.0
return TestRightResultType.SICKLECELLDISEASE
}
}
return TestRightResultType.UNDEFINED
// if (absorbanceAtWaveOne != Double.MIN_VALUE && absorbanceAtWaveTwo != Double.MIN_VALUE && absorbanceAtWaveOne != 0.0) {
// val value = absorbanceAtWaveTwo / absorbanceAtWaveOne
//
// if (value < 0.24 || value == 0.0) {
// return TestRightResultType.NORMAL
// } else if (value >= 0.24 && value < 0.30) {
// return TestRightResultType.SICKLECELLTRAIT
// } else if (value >= 0.30) {
// return TestRightResultType.SICKLECELLDISEASE
// }
//
// }
// return TestRightResultType.UNDEFINED
// Log.d(TAG, "value = $value")
// println("value = $value")
}
}

View File

@@ -0,0 +1,101 @@
package com.example.hpos.domain
import android.util.Log
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestRightResultType
import kotlin.math.log10
class ResultCalculationWithFirstImpl {
private val TAG = "Testright"
fun getResults(
wavelengthToPixelArray: ArrayList<ArrayList<Double>>,
intensityReferenceArray: ArrayList<ArrayList<Double>>,
intensitySampleArray: ArrayList<ArrayList<Double>>
) : TestRightResultType {
var pixelNoWithWave_427 = 0
var pixelNoWithWave_555 = 0
Log.d(TAG, "wavelengthToPixelArray size = ${wavelengthToPixelArray.size}")
// println("wavelengthToPixelArray size = ${wavelengthToPixelArray.size}")
for (each in wavelengthToPixelArray) {
var diff = each[0] - 427
if (pixelNoWithWave_427 == 0 && diff >= 0 && diff < 1) {
pixelNoWithWave_427 = each[1].toInt()
}
diff = each[0] - 555
if (pixelNoWithWave_555 == 0 && diff >= 0 && diff < 1) {
pixelNoWithWave_555 = each[1].toInt()
}
if (pixelNoWithWave_427 != 0 && pixelNoWithWave_555 != 0) {
break
}
}
Log.d(TAG, "pixelOfInterest_427 = ${pixelNoWithWave_427}")
Log.d(TAG, "pixelOfInterest_555 = ${pixelNoWithWave_555}")
// println("pixelOfInterest_427 = ${pixelNoWithWave_427}")
// println("pixelOfInterest_555 = ${pixelNoWithWave_555}")
val invertedPixel_427 = (Constants.TEST_RIGHT_TOTAL_PIXEL + 1) - pixelNoWithWave_427
val invertedPixel_555 = (Constants.TEST_RIGHT_TOTAL_PIXEL + 1) - pixelNoWithWave_555
var io_427 = 0.0
var io_555 = 0.0
for (each in intensityReferenceArray) {
if (each[0].toInt() == invertedPixel_427) {
io_427 = each[1]
}
if (each[0].toInt() == invertedPixel_555) {
io_555 = each[1]
}
}
Log.d(TAG, "I0 values are I0_427 = $io_427 , IO_555 = $io_555")
// println("I0 values are I0_427 = $io_427 , IO_555 = $io_555")
var i_427 = 0.0
var i_555 = 0.0
for (each in intensitySampleArray) {
if (each[0].toInt() == invertedPixel_427) {
i_427 = each[1]
}
if (each[0].toInt() == invertedPixel_555) {
i_555 = each[1]
}
}
Log.d(TAG, "I values are I_427 = $i_427 , I_555 = $i_555")
// println("I values are I_427 = $i_427 , I_555 = $i_555")
val absorbanceAtPixelWithWave_427 = log10(io_427 / i_427)
val absorbanceAtPixelWithWave_555 = log10(io_555 / i_555)
Log.d(
TAG,
"absorbance values are for 427 = $absorbanceAtPixelWithWave_427 , for 555 = $absorbanceAtPixelWithWave_555"
)
// println("absorbance values are for 427 = $absorbanceAtPixelWithWave_427 , for 555 = $absorbanceAtPixelWithWave_555")
var value = 0.0
if (absorbanceAtPixelWithWave_427 != 0.0 && absorbanceAtPixelWithWave_555 != 0.0) {
value = absorbanceAtPixelWithWave_555 / absorbanceAtPixelWithWave_427
}
Log.d(TAG, "value = $value")
// println("value = $value")
if (value < 0.24 || value == 0.0) {
return TestRightResultType.NORMAL
} else if (value >= 0.24 && value < 0.30) {
return TestRightResultType.SICKLECELLTRAIT
} else if (value >= 0.30) {
return TestRightResultType.SICKLECELLDISEASE
}
return TestRightResultType.UNDEFINED
}
}

View File

@@ -1,8 +1,8 @@
package com.example.hpostesting.domain
package com.example.hpos.domain
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.model.test.TestRightCalculationData
import com.example.hpostesting.data.model.test.TestRightResultType
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestRightCalculationData
import com.example.hpos.data.model.TestRightResultType
class ResultCalculationWithMaxImpl : TestRightResultCalculation {
@@ -57,24 +57,24 @@ class ResultCalculationWithMaxImpl : TestRightResultCalculation {
val value = absorbanceAtWaveTwo / absorbanceAtWaveOne
testRightCalculationData.ratioValue = value
if (value <= 0.29) {
if (value < 0.28 || value == 0.0) {
testRightCalculationData.ratioMinRange = 0.0
testRightCalculationData.ratioMaxRange = 0.29
testRightCalculationData.ratioMaxRange = 0.28
return TestRightResultType.NORMAL
} else if (value > 0.29 && value <= 0.32) {
testRightCalculationData.ratioMinRange = 0.29
testRightCalculationData.ratioMaxRange = 0.32
return TestRightResultType.NEGATIVEBORDERLINE
} else if (value > 0.32 && value <= 0.50) {
testRightCalculationData.ratioMinRange = 0.32
testRightCalculationData.ratioMaxRange = 0.50
} else if (value >= 0.28 && value < 0.285) {
testRightCalculationData.ratioMinRange = 0.28
testRightCalculationData.ratioMaxRange = 0.285
return TestRightResultType.UNDEFINED
} else if (value >= 0.285 && value < 0.52) {
testRightCalculationData.ratioMinRange = 0.285
testRightCalculationData.ratioMaxRange = 0.52
return TestRightResultType.SICKLECELLTRAIT
} else if (value > 0.50 && value <= 0.55) {
testRightCalculationData.ratioMinRange = 0.50
testRightCalculationData.ratioMaxRange = 0.55
return TestRightResultType.POSITIVEBORDERLINE
}else if (value > 0.55) {
testRightCalculationData.ratioMinRange = 0.55
} else if (value >= 0.52 && value < 0.525) {
testRightCalculationData.ratioMinRange = 0.52
testRightCalculationData.ratioMaxRange = 0.525
return TestRightResultType.UNDEFINED
}else if (value >= 0.525) {
testRightCalculationData.ratioMinRange = 0.525
testRightCalculationData.ratioMaxRange = 999.0
return TestRightResultType.SICKLECELLDISEASE
}

View File

@@ -1,44 +1,45 @@
package com.example.hpostesting.domain
package com.example.hpos.domain
import android.util.Log
import com.example.hpostesting.data.repository.LocalFileRepository
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.model.patient.UserData
import com.example.hpostesting.data.model.test.TestRightCalculationData
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.PatientData
import com.example.hpos.data.model.TestRightCalculationData
import com.opencsv.CSVWriter
import java.io.File
import java.io.FileWriter
import java.util.Collections.sort
class SaveRawData(private val localFileRepository: LocalFileRepository) {
class SaveRawData {
private val TAG = "saverawdata"
fun saveCsv(folderPath: String, fileName: String, matrix: ArrayList<ArrayList<Double>>) {
// try {
val fullPath = "$folderPath/$fileName"
// val writer = CSVWriter(FileWriter(fullPath))
val fullPath = "$folderPath/$fileName"
val writer = CSVWriter(FileWriter(fullPath))
sort(matrix) { one: ArrayList<Double>, two: ArrayList<Double> ->
one[0].compareTo(two[0])
}
val content = ArrayList<Array<String>>()
content.add(arrayOf("NM", "CA"))
for (eachRow in matrix) {
if (eachRow[0] >= Constants.MIN_WAVELENGTH_RANGE_TO_RECORD && eachRow[0] < Constants.MAX_WAVELENGTH_RANGE_TO_RECORD + 1) {
// val rowContent = arrayOf(String.format("%.3f", eachRow[0]), String.format("%.3f", eachRow[1]))
val rowContent =
arrayOf(
String.format("%.10f", eachRow[0]),
String.format("%.10f", eachRow[1])
)
content.add(rowContent)
sort(matrix) { one: ArrayList<Double>, two: ArrayList<Double> ->
one[0].compareTo(two[0])
}
}
localFileRepository.saveCsvToDisk(fullPath, content)
// writer.writeAll(content) // data is adding to csv
// writer.close()
val content = ArrayList<Array<String>>()
content.add(arrayOf("NM", "CA"))
for (eachRow in matrix) {
if (eachRow[0] >= Constants.MIN_WAVELENGTH_RANGE_TO_RECORD && eachRow[0] < Constants.MAX_WAVELENGTH_RANGE_TO_RECORD + 1) {
// val rowContent = arrayOf(String.format("%.3f", eachRow[0]), String.format("%.3f", eachRow[1]))
val rowContent =
arrayOf(
String.format("%.10f", eachRow[0]),
String.format("%.10f", eachRow[1])
)
content.add(rowContent)
}
}
writer.writeAll(content) // data is adding to csv
writer.close()
// } catch (e: Exception) {
// Log.e(TAG, e.toString())
@@ -46,18 +47,15 @@ class SaveRawData(private val localFileRepository: LocalFileRepository) {
}
fun saveLog(folderPath: String, fileName: String, calculationData: TestRightCalculationData) {
// val fileObj = File(folderPath, fileName)
// val writer = FileWriter(fileObj)
val fileObj = File(folderPath, fileName)
val writer = FileWriter(fileObj)
// writer.append(getLogStringFromObj(calculationData))
// writer.flush()
// writer.close()
val fullPath = folderPath + fileName
localFileRepository.saveTextToDisk(fullPath, getLogStringFromObj(calculationData))
writer.append(getLogStringFromObj(calculationData))
writer.flush()
writer.close()
}
private fun getLogStringFromObj(calculationData: TestRightCalculationData): String {
fun getLogStringFromObj(calculationData: TestRightCalculationData): String {
var outputString = "Test calculation logs ==>\n"
outputString += "Absorbance one = ${
String.format(
@@ -98,30 +96,24 @@ class SaveRawData(private val localFileRepository: LocalFileRepository) {
folderPath: String,
fileName: String,
calculationData: TestRightCalculationData,
testDetails: UserData?
patientData: PatientData
) {
// val fileObj = File(folderPath, fileName)
// val writer = FileWriter(fileObj)
val fileObj = File(folderPath, fileName)
val writer = FileWriter(fileObj)
// writer.append(getLogStringFromObjWithPatientData(calculationData, patientData))
// writer.flush()
// writer.close()
val fullPath = folderPath + fileName
localFileRepository.saveTextToDisk(
fullPath,
getLogStringFromObjWithPatientData(calculationData, testDetails)
)
writer.append(getLogStringFromObjWithPatientData(calculationData, patientData))
writer.flush()
writer.close()
}
private fun getLogStringFromObjWithPatientData(
calculationData: TestRightCalculationData,
testDetails: UserData?
patientData: PatientData
): String {
var outputString = "Test calculation logs ==>\n"
outputString += "Name = ${testDetails?.name}\n"
outputString += "ID = ${testDetails?._id}\n"
// outputString += "Gender = ${patientData.gender}\n"
outputString += "Name = ${patientData.name}\n"
outputString += "Age = ${patientData.age}\n"
outputString += "Gender = ${patientData.gender}\n"
outputString += "Absorbance one = ${
String.format(
"%.3f",

View File

@@ -1,9 +1,13 @@
package com.example.hpostesting.domain
package com.example.hpos.domain
import com.example.hpostesting.data.repository.LocalFileRepository
import com.example.hpostesting.data.model.CalculationVariableForTest
import android.util.Log
import com.example.hpos.data.model.CalculationVariableForTest
import com.opencsv.CSVWriter
import java.io.File
import java.io.FileOutputStream
import java.io.FileWriter
class SaveRawDataTest(private val localFileRepository: LocalFileRepository) {
class SaveRawDataTest {
private val TAG = "SaveRawDataTest"
@@ -11,7 +15,7 @@ class SaveRawDataTest(private val localFileRepository: LocalFileRepository) {
// try {
val fullPath = "$folderPath/$fileName"
// val writer = CSVWriter(FileWriter(fullPath))
val writer = CSVWriter(FileWriter(fullPath))
val content = ArrayList<Array<String>>()
// Header
@@ -31,40 +35,27 @@ class SaveRawDataTest(private val localFileRepository: LocalFileRepository) {
content.add(rowContent)
}
localFileRepository.saveCsvToDisk(fullPath, content)
// writer.writeAll(content) // data is adding to csv
// writer.close()
writer.writeAll(content) // data is adding to csv
writer.close()
// } catch (e: Exception){
// Log.e(TAG, e.toString())
// }
}
fun saveLog(folderPath: String, fileName: String, isReference: Boolean, fullString: String) {
// val fileObj = File(folderPath, fileName)
val fileObj = File(folderPath, fileName)
// Log.d(TAG, "$folderPath --- $fileName")
// val writer = FileWriter(fileObj)
val writer = FileWriter(fileObj)
// if (isReference)
// writer.append("\nREFERENCE OUTPUT\n")
// else
// writer.append("\nSAMPLE OUTPUT\n")
//
// writer.append(fullString)
// writer.flush()
// writer.close()
val filePath = folderPath + fileName
var stringToWrite = ""
stringToWrite += if (isReference)
"\nREFERENCE OUTPUT\n"
if (isReference)
writer.append("\nREFERENCE OUTPUT\n")
else
"\nSAMPLE OUTPUT\n"
stringToWrite += fullString
localFileRepository.saveTextToDisk(filePath, stringToWrite)
writer.append("\nSAMPLE OUTPUT\n")
writer.append(fullString)
writer.flush()
writer.close()
}

View File

@@ -1,8 +1,8 @@
package com.example.hpostesting.domain
package com.example.hpos.domain
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.model.test.TestRightCalculationData
import com.example.hpostesting.data.model.test.TestRightResultType
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestRightCalculationData
import com.example.hpos.data.model.TestRightResultType
class SickleFindResultCaluculationWithMaxImpl : TestRightResultCalculation{

View File

@@ -1,6 +1,6 @@
package com.example.hpostesting.domain
package com.example.hpos.domain
import com.example.hpostesting.data.model.test.TestRightCalculationData
import com.example.hpos.data.model.TestRightCalculationData
interface TestRightResultCalculation {
fun getResults(

View File

@@ -0,0 +1,171 @@
package com.example.hpos.presentation
import android.content.BroadcastReceiver
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.hardware.usb.UsbDevice
import android.hardware.usb.UsbManager
import android.os.Bundle
import android.util.Log
import android.view.Gravity
import android.view.Menu
import android.view.MenuItem
import android.widget.Toast
import androidx.appcompat.app.ActionBarDrawerToggle
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat
import androidx.core.view.GravityCompat
import androidx.core.view.get
import androidx.lifecycle.ViewModelProvider
import com.example.hpos.R
import com.example.hpos.data.DataHolder
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestType
import com.example.hpos.databinding.ActivityMainBinding
import com.example.hpos.presentation.testRight.TestRightActivity
import com.example.hpos.util.MyViewModelFactory
import com.hoho.android.usbserial.driver.UsbSerialProber
class MainActivity : AppCompatActivity()
// , SerialInputOutputManager.Listener
{
private lateinit var binding: ActivityMainBinding
private lateinit var viewModel: MainViewModel
private var myMenu: Menu? = null
private val TAG = "MainActivity"
private var mUsbReceiver: BroadcastReceiver = object : BroadcastReceiver() {
override fun onReceive(context: Context?, intent: Intent) {
val action = intent.action
if (UsbManager.ACTION_USB_DEVICE_DETACHED == action) {
DataHolder.usbConnected.value = false
// Toast.makeText(context, "Detached", Toast.LENGTH_SHORT).show()
} else if (UsbManager.ACTION_USB_DEVICE_ATTACHED == action) {
DataHolder.usbConnected.value = true
// Toast.makeText(context, "Attached", Toast.LENGTH_SHORT).show()
}
}
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityMainBinding.inflate(layoutInflater)
setContentView(binding.root)
viewModel = ViewModelProvider(
this,
MyViewModelFactory(applicationContext)
)[MainViewModel::class.java]
setSupportActionBar(binding.myToolbar)
setupNavigationDrawer()
setupListeners()
val filter = IntentFilter()
filter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED)
filter.addAction(UsbManager.ACTION_USB_DEVICE_ATTACHED)
registerReceiver(mUsbReceiver, filter)
}
private fun setupNavigationDrawer() {
// Pass the ActionBarToggle action into the drawerListener
val actionBarToggle = ActionBarDrawerToggle(this, binding.drawerLayout, 0, 0)
binding.drawerLayout.addDrawerListener(actionBarToggle)
// For the Navigation drawer
supportActionBar?.setDisplayHomeAsUpEnabled(true)
// Call syncState() on the action bar so it'll automatically change to the back button when the drawer layout is open
actionBarToggle.syncState()
// Call setNavigationItemSelectedListener on the NavigationView to detect when items are clicked
binding.navView.setNavigationItemSelectedListener { menuItem: MenuItem ->
when (menuItem.itemId) {
R.id.about_us -> {
Toast.makeText(this, "Test clicked", Toast.LENGTH_SHORT).show()
true
}
R.id.download_report -> {
Toast.makeText(this, "Download clicked", Toast.LENGTH_SHORT).show()
true
}
R.id.settings -> {
Toast.makeText(this, "Settings clicked", Toast.LENGTH_SHORT).show()
true
}
else -> {
false
}
}
}
}
private fun checkAndUpdateUsbConnection() {
val availableDrivers = UsbSerialProber.getDefaultProber().findAllDrivers(getSystemService(Context.USB_SERVICE) as UsbManager)
if (availableDrivers.isNotEmpty() && availableDrivers[0].device.productId == Constants.DEVICE_PRODUCT_ID && availableDrivers[0].device.vendorId == Constants.DEVICE_VENDOR_ID){
Log.d(TAG, "Device matched -> product = ${availableDrivers[0].device.productId}, vendor = ${availableDrivers[0].device.vendorId}")
DataHolder.usbConnected.value = true
} else if (availableDrivers.isNotEmpty()) {
Log.d(TAG, "Device NOT matched -> product = ${availableDrivers[0].device.productId}, vendor = ${availableDrivers[0].device.vendorId}")
Toast.makeText(this, "Device Not Compatible", Toast.LENGTH_SHORT).show()
DataHolder.usbConnected.value = false
} else {
Log.d(TAG, "Device NOT Connected")
DataHolder.usbConnected.value = false
}
}
private fun setupListeners() {
binding.cvItem1.setOnClickListener {
DataHolder.selectedTestType = TestType.SICKLECERT
val i = Intent(applicationContext, TestRightActivity::class.java)
startActivity(i)
}
binding.cvItem2.setOnClickListener {
DataHolder.selectedTestType = TestType.SICKLEFIND
val i = Intent(applicationContext, TestRightActivity::class.java)
startActivity(i)
}
DataHolder.usbConnected.observe(this){
// Log.d(TAG, "usbConnected observer called with value -> $it")
if (it){
myMenu?.get(0)?.icon = ContextCompat.getDrawable(this, R.drawable.ic_baseline_usb_24)
} else {
// Log.d(TAG, "into no block -> $it")
myMenu?.get(0)?.icon = ContextCompat.getDrawable(this, R.drawable.ic_baseline_usb_off_24)
}
}
}
override fun onCreateOptionsMenu(menu: Menu?): Boolean {
menuInflater.inflate(R.menu.my_menu, menu)
myMenu = menu
checkAndUpdateUsbConnection()
return true
}
// override the onSupportNavigateUp() function to launch the Drawer when the hamburger icon is clicked
override fun onSupportNavigateUp(): Boolean {
binding.drawerLayout.openDrawer(binding.navView)
return true
}
// override the onBackPressed() function to close the Drawer when the back button is clicked
override fun onBackPressed() {
if (binding.drawerLayout.isDrawerOpen(GravityCompat.START)) {
binding.drawerLayout.closeDrawer(GravityCompat.START)
} else {
super.onBackPressed()
}
}
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.presentation
package com.example.hpos.presentation
import androidx.lifecycle.ViewModel

View File

@@ -0,0 +1,39 @@
package com.example.hpos.presentation
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView
import com.example.hpos.R
import com.example.hpos.data.model.PatientData
class RVAdapter : RecyclerView.Adapter<RVAdapter.ViewHolder>() {
private val dataset = ArrayList<PatientData>()
class ViewHolder(view: View) : RecyclerView.ViewHolder(view) {
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
return ViewHolder(
LayoutInflater.from(parent.context)
.inflate(R.layout.table_item, parent, false)
)
}
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
}
override fun getItemCount(): Int {
return dataset.size
}
fun updateDataSet(newDataSet: ArrayList<PatientData>) {
dataset.clear()
dataset.addAll(newDataSet)
notifyDataSetChanged()
}
}

View File

@@ -0,0 +1,118 @@
package com.example.hpos.presentation
import android.Manifest
import android.content.Intent
import android.content.pm.PackageManager
import android.net.Uri
import android.os.Build
import android.os.Bundle
import android.os.Environment
import android.provider.Settings
import android.widget.Toast
import androidx.activity.result.contract.ActivityResultContracts
import androidx.annotation.RequiresApi
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat
import com.example.hpos.data.DataHolder
import com.example.hpos.databinding.ActivitySplashBinding
import com.example.hpos.util.MyUtils
/**
* Splash Activity
* Used for preprocessing of data, permissions
*/
class SplashActivity : AppCompatActivity() {
private lateinit var binding: ActivitySplashBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivitySplashBinding.inflate(layoutInflater)
setContentView(binding.root)
checkForPermissions()
}
private fun checkForPermissions() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
getPermissionsAboveAndroidR()
} else {
getPermissionsBelowAndroidR()
}
}
@RequiresApi(Build.VERSION_CODES.R)
private fun getPermissionsAboveAndroidR() {
// Checking if permission is already granted or not.
if (!Environment.isExternalStorageManager()) {
val storagePermissionResultLauncher =
registerForActivityResult(ActivityResultContracts.StartActivityForResult()) {
if (Environment.isExternalStorageManager()) {
DataHolder.isStoragePermissionGranted = true
moveToLandingPage()
} else {
DataHolder.isStoragePermissionGranted = false
Toast.makeText(
this,
"You must grant permission to storage to use the app",
Toast.LENGTH_SHORT
).show()
}
}
val intent = Intent()
intent.action = Settings.ACTION_MANAGE_APP_ALL_FILES_ACCESS_PERMISSION
intent.data = Uri.fromParts("package", this.packageName, null)
storagePermissionResultLauncher.launch(intent)
} else {
DataHolder.isStoragePermissionGranted = true
moveToLandingPage()
}
}
private fun getPermissionsBelowAndroidR() {
val requestPermissionLauncher =
registerForActivityResult(ActivityResultContracts.RequestPermission()) { isGranted: Boolean ->
if (isGranted) {
DataHolder.isStoragePermissionGranted = true
moveToLandingPage()
} else {
DataHolder.isStoragePermissionGranted = false
Toast.makeText(
this,
"You must grant permission to storage to use the app",
Toast.LENGTH_SHORT
).show()
}
}
if (ContextCompat.checkSelfPermission(
this,
Manifest.permission.READ_EXTERNAL_STORAGE
) != PackageManager.PERMISSION_GRANTED || ContextCompat.checkSelfPermission(
this,
Manifest.permission.WRITE_EXTERNAL_STORAGE
) != PackageManager.PERMISSION_GRANTED
) {
requestPermissionLauncher.launch(Manifest.permission.WRITE_EXTERNAL_STORAGE)
} else {
DataHolder.isStoragePermissionGranted = true
moveToLandingPage()
}
}
private fun moveToLandingPage() {
createAppFolder()
val i = Intent(applicationContext, MainActivity::class.java)
startActivity(i)
}
private fun createAppFolder() {
val folderPath = MyUtils.createAppFolder(applicationContext)
if (folderPath != null){
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
}
}
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.presentation
package com.example.hpos.presentation
interface UsbServiceListener {
fun onUsbRead(data: ByteArray?)

View File

@@ -1,38 +1,32 @@
package com.example.hpostesting.presentation.testRight
package com.example.hpos.presentation.testRight
import android.app.PendingIntent
import android.content.BroadcastReceiver
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.content.ServiceConnection
import android.content.*
import android.hardware.usb.UsbDevice
import android.hardware.usb.UsbDeviceConnection
import android.hardware.usb.UsbManager
import android.os.Bundle
import android.os.IBinder
import android.util.Log
import android.view.Menu
import android.view.*
import android.widget.Toast
import androidx.activity.viewModels
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat
import androidx.core.view.get
import com.example.hpostesting.data.DataHolder
import com.example.hpostesting.data.constant.Constants
import androidx.lifecycle.ViewModelProvider
import com.example.hpos.R
import com.example.hpos.data.DataHolder
import com.example.hpos.data.constant.Constants
import com.example.hpos.databinding.ActivityTestRightBinding
import com.example.hpos.util.MyViewModelFactory
import com.hoho.android.usbserial.driver.UsbSerialDriver
import com.hoho.android.usbserial.driver.UsbSerialProber
import dagger.hilt.android.AndroidEntryPoint
import `in`.sminnovations.hpostesting.R
import `in`.sminnovations.hpostesting.databinding.ActivityTestRightBinding
@AndroidEntryPoint
class TestRightActivity : AppCompatActivity() {
private lateinit var binding: ActivityTestRightBinding
private val viewModel by viewModels<TestRightViewModel>()
private lateinit var viewModel: TestRightViewModel
private var myMenu: Menu? = null
private lateinit var mDriver: UsbSerialDriver
@@ -64,8 +58,6 @@ class TestRightActivity : AppCompatActivity() {
val binder = service as UsbService.UsbServiceBinder
mService = binder.getService()
viewModel.isServiceConnected = true
// Todo: Uncomment this
mConnection.let { mService.connect(mDriver, mConnection!!) }
moveToNext()
}
@@ -79,6 +71,10 @@ class TestRightActivity : AppCompatActivity() {
super.onCreate(savedInstanceState)
binding = ActivityTestRightBinding.inflate(layoutInflater)
setContentView(binding.root)
viewModel = ViewModelProvider(
this,
MyViewModelFactory(this.applicationContext)
)[TestRightViewModel::class.java]
setSupportActionBar(binding.myToolbar)
supportActionBar?.setDisplayHomeAsUpEnabled(true)
@@ -103,6 +99,11 @@ class TestRightActivity : AppCompatActivity() {
}
}
// private fun testing() {
// supportFragmentManager.beginTransaction()
// .replace(binding.flMain.id, TestRightExpSample()).commit()
// }
private fun connectUsb(permissionGranted: Boolean) {
Log.d(TAG, "connectUsb() called, permission variable = $permissionGranted")
val manager = getSystemService(Context.USB_SERVICE) as UsbManager
@@ -113,7 +114,11 @@ class TestRightActivity : AppCompatActivity() {
} else {
mDriver = availableDrivers[0]
viewModel.testDetails?.deviceId = mDriver.device.serialNumber.toString()
if (mDriver.device.productId != Constants.DEVICE_PRODUCT_ID || mDriver.device.vendorId != Constants.DEVICE_VENDOR_ID){
Toast.makeText(this, "Device Connected is not supported", Toast.LENGTH_SHORT).show()
onBackPressed()
return
}
DataHolder.deviceSerialNumber = mDriver.device.serialNumber.toString()
mConnection = manager.openDevice(mDriver.device)
@@ -125,7 +130,12 @@ class TestRightActivity : AppCompatActivity() {
}
}
/*
* Request user permission. The response will be received in the BroadcastReceiver
*/
private fun requestUserPermission(manager: UsbManager, device: UsbDevice) {
// Log.d(TAG, "requestUserPermissions() called -> vendor id = ${device.vendorId} & product id = ${device.productId}")
val mPendingIntent: PendingIntent
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.S) {
mPendingIntent = PendingIntent.getBroadcast(
@@ -139,7 +149,7 @@ class TestRightActivity : AppCompatActivity() {
this,
0,
Intent(Constants.ACTION_USB_PERMISSION),
PendingIntent.FLAG_ONE_SHOT or PendingIntent.FLAG_IMMUTABLE
PendingIntent.FLAG_ONE_SHOT
)
}
@@ -174,6 +184,11 @@ class TestRightActivity : AppCompatActivity() {
fun onErrorReported(msg: String) {
Toast.makeText(this, msg, Toast.LENGTH_SHORT).show()
// Snackbar.make(binding.clParent, msg, Snackbar.LENGTH_LONG)
// .setAction("CLOSE") { Toast.makeText(this, "Will soon", Toast.LENGTH_SHORT).show() }
// .setActionTextColor(resources.getColor(R.color.white))
// .show()
if (!isFinishing)
onBackPressed()
}
@@ -183,6 +198,16 @@ class TestRightActivity : AppCompatActivity() {
myMenu = menu
return true
}
// override fun onOptionsItemSelected(item: MenuItem) = when (item.itemId) {
// R.id.action_usb -> {
//// Toast.makeText(this, "USB Connected", Toast.LENGTH_SHORT).show()
//// myMenu?.get(0)?.icon = ContextCompat.getDrawable(this, R.drawable.ic_baseline_usb_off_24)
// true
// }
// else -> {super.onOptionsItemSelected(item)}
// }
override fun onDestroy() {
super.onDestroy()
if (viewModel.isServiceConnected) {
@@ -191,4 +216,10 @@ class TestRightActivity : AppCompatActivity() {
viewModel.isServiceConnected = false
}
}
// fun View.setAllEnabled(enabled: Boolean) {
// isEnabled = enabled
// if (this is ViewGroup) children.forEach { child -> child.setAllEnabled(enabled) }
// }
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.presentation.testRight
package com.example.hpos.presentation.testRight
import android.os.Bundle
import android.os.Handler
@@ -8,28 +8,32 @@ import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.Toast
import androidx.core.view.children
import androidx.fragment.app.Fragment
import androidx.fragment.app.activityViewModels
import com.example.hpostesting.data.DataHolder
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.constant.TestRightCommands
import com.example.hpostesting.data.model.ErrorMessage
import com.example.hpostesting.presentation.UsbServiceListener
import com.example.hpostesting.presentation.utils.MyDialogListener
import com.example.hpostesting.presentation.utils.UIUtils
import dagger.hilt.android.AndroidEntryPoint
import `in`.sminnovations.hpostesting.R
import `in`.sminnovations.hpostesting.databinding.FragmentTestRightExpReferenceBinding
import com.example.hpos.R
import com.example.hpos.data.DataHolder
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.constant.TestRightCommands
import com.example.hpos.data.model.ErrorMessage
import com.example.hpos.databinding.FragmentTestRightExpReferenceBinding
import com.example.hpos.presentation.UsbServiceListener
import com.example.hpos.presentation.utils.MyDialogListener
import com.example.hpos.presentation.utils.UIUtils
@AndroidEntryPoint
class TestRightExpReference : Fragment() {
private lateinit var binding: FragmentTestRightExpReferenceBinding
private val viewModel: TestRightViewModel by activityViewModels()
private val TAG = "TestRightExpReference"
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View {
// Inflate the layout for this fragment
binding = FragmentTestRightExpReferenceBinding.inflate(inflater, container, false)
return binding.root
}
@@ -37,26 +41,34 @@ class TestRightExpReference : Fragment() {
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
setupListeners()
// if (DataHolder.isReferenceTaken)
// moveToSamplePage()
//
// DataHolder.sampleReadCounter <= Constants.MAXIMUM_TEST_ALLOWED_BEFORE_REFERENCE
if (DataHolder.deviceConstant == null) {
viewModel.progressBar.postValue(true)
Handler(Looper.getMainLooper()).postDelayed(
{ sendCmdToFetchDeviceConstant() }, Constants.DELAY_BETWEEN_COMMANDS
{ sendCmdToFetchDeviceConstant() },
Constants.DELAY_BETWEEN_COMMANDS
)
}
}
private fun setupListeners() {
binding.btnSetReference.setOnClickListener {
UIUtils.createAlertDialog(requireContext(),
UIUtils.createAlertDialog(
requireContext(),
getString(R.string.have_you_placed),
getString(R.string.please_place),
getString(R.string.no),
getString(R.string.yes),
object : MyDialogListener {
override fun onClickNegativeButton() {
// Todo: Only for testing
// viewModel.progressBar.postValue(true)
}
override fun onClickPositiveButton() {
startTakingReference()
}
@@ -64,15 +76,16 @@ class TestRightExpReference : Fragment() {
}
viewModel.errorTriggered.observe(viewLifecycleOwner) {
if (it != null) {
if (it != null){
UIUtils.onShowErrorToast(requireContext(), it.message)
if (it.code == Constants.ERROR_CRITICAL) {
if (it.code == Constants.ERROR_CRITICAL){
activity?.onBackPressed()
}
}
}
viewModel.progressBar.observe(viewLifecycleOwner) {
// Log.d(TAG, "SURYA OBSERVER Activated outcome = $it")
if (it) {
binding.progressBar.visibility = View.VISIBLE
binding.clParent.alpha = 0.5f
@@ -83,6 +96,7 @@ class TestRightExpReference : Fragment() {
binding.btnSetReference.isEnabled = true
}
}
}
/**
@@ -93,17 +107,19 @@ class TestRightExpReference : Fragment() {
* 4. command print
*/
private fun startTakingReference() {
// requireActivity().runOnUiThread {
sendCmdToSetLed()
// }
}
// private fun sendCmdToFetchDeviceConstant(recursive: Boolean) {
private fun sendCmdToFetchDeviceConstant() {
Log.d(TAG, "sendCmdToFetchDeviceConstant() called")
viewModel.progressBar.postValue(true)
val fullReadOutput = StringBuilder()
(activity as TestRightActivity).mService.eventDrivenWrite(
TestRightCommands.read,
(activity as TestRightActivity).mService.eventDrivenWrite(TestRightCommands.read,
object : UsbServiceListener {
override fun onUsbRead(data: ByteArray?) {
data?.let {
@@ -113,7 +129,8 @@ class TestRightExpReference : Fragment() {
if (stringData.contains("OK", true)) {
Log.d(
TAG, "onUsbRead() called in sendCmdToFetchDeviceConstant() found OK"
TAG,
"onUsbRead() called in sendCmdToFetchDeviceConstant() found OK"
)
viewModel.mapDeviceConstants(fullReadOutput.toString())
viewModel.progressBar.postValue(false)
@@ -121,11 +138,7 @@ class TestRightExpReference : Fragment() {
Log.d(TAG, "results = FINE")
viewModel.progressBar.postValue(false)
viewModel.errorTriggered.postValue(
ErrorMessage(
"Please Try Again!!", Constants.ERROR_CRITICAL
)
)
viewModel.errorTriggered.postValue(ErrorMessage("Please Try Again!!", Constants.ERROR_CRITICAL))
}
}
@@ -133,11 +146,7 @@ class TestRightExpReference : Fragment() {
override fun onUsbError(e: Exception?) {
Log.e(TAG, "onUsbIoError() called in sendCmdToFetchDeviceConstant() -> $e")
viewModel.errorTriggered.postValue(
ErrorMessage(
"Please Try Again this step", Constants.ERROR_NORMAL
)
)
viewModel.errorTriggered.postValue(ErrorMessage("Please Try Again this step", Constants.ERROR_NORMAL))
viewModel.progressBar.postValue(false)
}
@@ -162,7 +171,8 @@ class TestRightExpReference : Fragment() {
Runnable {
viewModel.progressBar.postValue(false)
sendCmdToAutoset()
}, Constants.DELAY_BETWEEN_COMMANDS
},
Constants.DELAY_BETWEEN_COMMANDS
)
}
}
@@ -193,7 +203,8 @@ class TestRightExpReference : Fragment() {
Runnable {
viewModel.progressBar.postValue(false)
sendCmdToRun()
}, Constants.DELAY_BETWEEN_COMMANDS
},
Constants.DELAY_BETWEEN_COMMANDS
)
}
@@ -226,10 +237,12 @@ class TestRightExpReference : Fragment() {
Runnable {
viewModel.progressBar.postValue(false)
sendCmdToFetchLightIntensities()
}, Constants.DELAY_BETWEEN_COMMANDS
},
Constants.DELAY_BETWEEN_COMMANDS
)
}
}
// }
}
override fun onUsbError(e: Exception?) {
@@ -243,23 +256,24 @@ class TestRightExpReference : Fragment() {
Log.d(TAG, "sendCmdToFetchLightIntensities() called")
viewModel.progressBar.postValue(true)
val fullReadOutput = StringBuilder()
DataHolder.testExp = true
(activity as TestRightActivity).mService.eventDrivenWrite(TestRightCommands.printAll,
object : UsbServiceListener {
override fun onUsbRead(data: ByteArray?) {
data?.let {
val stringData = String(it)
fullReadOutput.append(stringData)
if (stringData.trim().isNotEmpty() && fullReadOutput.substring(
Math.max(
fullReadOutput.length - 15, 0
)
).contains("OK [0]", true)
) {
// Log.d(TAG, stringData)
// if (stringData.contains("OK", true)) {
// if (fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK", true)) {
if (stringData.trim().isNotEmpty() && fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK [0]", true)) {
Log.d(TAG, "onUsbRead() called in sendCmdToFetchLightIntensities()")
// Log.d(TAG, fullReadOutput.toString())
viewModel.mapIntensityValues(fullReadOutput.toString(), true)
// viewModel.saveLogTest(requireContext().applicationContext, true, fullReadOutput.toString())
DataHolder.isReferenceTaken = true
Handler(Looper.getMainLooper()).postDelayed(
@@ -274,11 +288,7 @@ class TestRightExpReference : Fragment() {
override fun onUsbError(e: Exception?) {
Log.e(TAG, "onUsbIoError() called in sendCmdToFetchLightIntensities() -> $e")
viewModel.errorTriggered.postValue(
ErrorMessage(
"Please Try Again this step", Constants.ERROR_NORMAL
)
)
viewModel.errorTriggered.postValue(ErrorMessage("Please Try Again this step", Constants.ERROR_NORMAL))
viewModel.progressBar.postValue(false)
}

View File

@@ -1,6 +1,5 @@
package com.example.hpostesting.presentation.testRight
package com.example.hpos.presentation.testRight
import android.content.Intent
import android.os.Bundle
import android.os.Handler
import android.os.Looper
@@ -10,20 +9,20 @@ import android.view.View
import android.view.ViewGroup
import androidx.fragment.app.Fragment
import androidx.fragment.app.activityViewModels
import com.example.hpostesting.data.DataHolder
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.constant.TestRightCommands
import com.example.hpostesting.data.model.ErrorMessage
import com.example.hpostesting.data.model.test.TestType
import com.example.hpostesting.presentation.MainActivity
import com.example.hpostesting.presentation.UsbServiceListener
import com.example.hpostesting.presentation.utils.MyDialogListener
import com.example.hpostesting.presentation.utils.UIUtils
import dagger.hilt.android.AndroidEntryPoint
import `in`.sminnovations.hpostesting.R
import `in`.sminnovations.hpostesting.databinding.FragmentTestRightExpSampleBinding
import com.example.hpos.R
import com.example.hpos.data.DataHolder
import com.example.hpos.data.PreferenceUtility
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.constant.TestRightCommands
import com.example.hpos.data.model.ErrorMessage
import com.example.hpos.data.model.PatientData
import com.example.hpos.data.model.TestRightResultType
import com.example.hpos.data.model.TestType
import com.example.hpos.databinding.FragmentTestRightExpSampleBinding
import com.example.hpos.presentation.UsbServiceListener
import com.example.hpos.presentation.utils.MyDialogListener
import com.example.hpos.presentation.utils.UIUtils
@AndroidEntryPoint
class TestRightExpSample : Fragment() {
private lateinit var binding: FragmentTestRightExpSampleBinding
@@ -35,7 +34,16 @@ class TestRightExpSample : Fragment() {
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View {
// Inflate the layout for this fragment
binding = FragmentTestRightExpSampleBinding.inflate(inflater, container, false)
// if (DataHolder.sampleReadCounter > Constants.MAXIMUM_TEST_ALLOWED_BEFORE_REFERENCE) {
// binding.btnUpdateReference.enable()
// binding.clInstructions.setAllEnabled(false)
// } else {
// binding.btnUpdateReference.disable()
// binding.clInstructions.setAllEnabled(false)
// }
return binding.root
}
@@ -66,45 +74,58 @@ class TestRightExpSample : Fragment() {
}
binding.btnSubmit.setOnClickListener {
UIUtils.createAlertDialog(
requireContext(),
"WARNING",
"Please check if you have placed the sample of this person ${viewModel.testDetails?._id}",
getString(R.string.no),
"Yes",
object : MyDialogListener {
override fun onClickNegativeButton() {}
override fun onClickPositiveButton() {
UIUtils.createAlertDialog(
requireContext(),
getString(R.string.have_you_placed_sample),
getString(R.string.please_place_sample),
getString(R.string.no),
getString(R.string.yes_and_run),
object : MyDialogListener {
override fun onClickNegativeButton() {}
override fun onClickPositiveButton() {
startAcquiring()
}
})
}
})
// }
}
val details = checkAndReturnPatientDetails()
if (details != null) {
viewModel.patientDetails = details
binding.tvSkip.setOnClickListener {
DataHolder.sampleReadCounter = 0
DataHolder.isReferenceTaken = false
val i = Intent(requireContext(), MainActivity::class.java)
startActivity(i)
UIUtils.createAlertDialog(
requireContext(),
getString(R.string.have_you_placed_sample),
getString(R.string.please_place_sample),
getString(R.string.no),
getString(R.string.yes_and_run),
object : MyDialogListener {
override fun onClickNegativeButton() {}
override fun onClickPositiveButton() {
startAcquiring()
}
})
}
}
binding.etNameBlock.setOnClickListener { binding.etName.isErrorEnabled = false }
binding.etAgeBlock.setOnClickListener { binding.etAge.isErrorEnabled = false }
binding.etGenderBlock.setOnClickListener { binding.ddGender.isErrorEnabled = false }
}
private fun checkAndReturnPatientDetails(): PatientData? {
val name = binding.etName.editText?.text?.trim()
if (name.isNullOrEmpty()) {
binding.etName.error = getString(R.string.name_error)
return null
}
val age = binding.etAge.editText?.text?.trim()
if (age.isNullOrEmpty()) {
binding.etAge.error = getString(R.string.age_error)
return null
} else if (age.toString().toInt() < 0 || age.toString().toInt() > 199) {
binding.etAge.error = getString(R.string.age_error_out_of_bound)
return null
}
val gender = binding.ddGender.editText?.text
if (gender.isNullOrEmpty()) {
binding.ddGender.error = getString(R.string.gender_error)
return null
}
return PatientData(name.toString(), age.toString().toInt(), gender.toString(), TestRightResultType.UNDEFINED)
}
/**
* Executing the commands sequentially each after successfully executing one.
* 1. command run
* 2. command print
*/
private fun startAcquiring() {
// binding.progressBar.visibility = View.VISIBLE
sendCmdToRun()
}
@@ -120,6 +141,9 @@ class TestRightExpSample : Fragment() {
val stringData = String(it)
fullReadOutput.append(stringData)
Log.d(TAG, stringData)
// if (stringData.contains("OK", true)) {
// if (stringData.contains("OK", true) || fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK", true)) {
// if (fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK", true)) {
if (fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK [0]", true)) {
Log.d(TAG, "onUsbRead() called in sendCmdToRun()")
Handler(Looper.getMainLooper()).postDelayed(
@@ -147,8 +171,6 @@ class TestRightExpSample : Fragment() {
Log.d(TAG, "sendCmdToFetchLightIntensities() called")
viewModel.progressBar.postValue(true)
val fullReadOutput = StringBuilder()
DataHolder.testExp = false
(activity as TestRightActivity).mService.eventDrivenWrite(TestRightCommands.printAll,
object : UsbServiceListener {
override fun onUsbRead(data: ByteArray?) {
@@ -156,10 +178,17 @@ class TestRightExpSample : Fragment() {
val stringData = String(it)
fullReadOutput.append(stringData)
Log.d(TAG, stringData)
// if (stringData.contains("OK", true)) {
// if (stringData.contains("OK", true) || stringData.contains("O", true) || stringData.contains("K", true)) {
// if (stringData.contains("OK", true) || fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK", true)) {
// if (fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK", true)) {
if (stringData.trim().isNotEmpty() && fullReadOutput.substring(Math.max(fullReadOutput.length - 15, 0)).contains("OK [0]", true)) {
Log.d(TAG, "onUsbRead() called in sendCmdToFetchLightIntensities()")
viewModel.mapIntensityValues(fullReadOutput.toString(), false)
// viewModel.saveLogTest(requireContext().applicationContext, false, fullReadOutput.toString())
// showResultsAfterAcquiring()
Handler(Looper.getMainLooper()).postDelayed(
{
checkIfToRunAgain()
@@ -185,11 +214,15 @@ class TestRightExpSample : Fragment() {
viewModel.mapWavelengthToAbsorbance()
// Todo: Save CSV + Test CSV
if (DataHolder.selectedTestType == TestType.SICKLECERT) {
viewModel.calculateResults()
} else {
viewModel.calculateResultsForSickleFind()
}
// Todo: Save Log
saveDataLocally()
if (viewModel.numberOfSampleRun < Constants.NO_OF_TIMES_TO_RUN_SAMPLE) {
@@ -206,14 +239,49 @@ class TestRightExpSample : Fragment() {
}
private fun showResultsAfterAcquiring() {
// viewModel.mapWavelengthToAbsorbance()
// viewModel.calculateResults()
viewModel.progressBar.postValue(false)
// binding.progressBar.visibility = View.GONE
parentFragmentManager.beginTransaction().replace(R.id.fl_main, TestRightResults())
.commit()
}
private fun saveDataLocally() {
viewModel.saveCsv(requireContext().applicationContext, viewModel.getCSVFileName())
viewModel.saveLogWithPatient(requireContext().applicationContext, viewModel.getLogFileName())
val patientName = viewModel.patientDetails.name
// if (patientName.length > 5){
// patientName = patientName.substring(0, 5)
// }
val id = PreferenceUtility.generateId(requireContext())
val prefixCsv: String = if (DataHolder.selectedTestType == TestType.SICKLECERT)
"HPOSSC_${DataHolder.deviceSerialNumber}_${patientName}_"
else
"HPOSSF_${DataHolder.deviceSerialNumber}_${patientName}_"
// val prefixCsv = "HPOSSC_${DataHolder.deviceSerialNumber}_${patientName}_"
val fileExtensionCsv = ".csv"
val fileNameCsv = prefixCsv + id + fileExtensionCsv
saveCsv(fileNameCsv)
val prefixTxt = "log_${DataHolder.deviceSerialNumber}_${patientName}_"
val fileExtensionTxt = ".txt"
val fileNameTxt = prefixTxt + id + fileExtensionTxt
saveLog(fileNameTxt)
}
private fun saveCsv(fileName: String) {
Log.d(TAG, "saveCsv() called")
viewModel.saveCsv(requireContext().applicationContext, fileName)
viewModel.saveCsvForTesting(requireContext().applicationContext, "detailed_$fileName")
}
private fun saveLog(fileName: String) {
Log.d(TAG, "saveLog() called")
viewModel.saveLogWithPatient(requireContext().applicationContext, fileName)
}
}

View File

@@ -0,0 +1,203 @@
package com.example.hpos.presentation.testRight
import android.content.Intent
import android.os.Bundle
import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.Toast
import androidx.fragment.app.Fragment
import androidx.fragment.app.activityViewModels
import com.example.hpos.R
import com.example.hpos.data.DataHolder
import com.example.hpos.data.PreferenceUtility
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.TestRightResultType
import com.example.hpos.data.model.TestType
import com.example.hpos.databinding.FragmentTestRightResultsBinding
import com.example.hpos.presentation.MainActivity
import com.example.hpos.util.MyUtils
import java.text.SimpleDateFormat
import java.util.*
class TestRightResults : Fragment() {
private lateinit var binding: FragmentTestRightResultsBinding
private val viewModel: TestRightViewModel by activityViewModels()
private val TAG = "TestRightResults"
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View {
// Inflate the layout for this fragment
binding = FragmentTestRightResultsBinding.inflate(inflater, container, false)
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
setupListeners()
updateResults()
// saveCsv()
// saveLog()
}
private fun setupListeners() {
binding.ivHome.setOnClickListener {
val i = Intent(requireContext().applicationContext, MainActivity::class.java)
startActivity(i)
}
binding.ivNext.setOnClickListener {
moveToSamplePage()
}
}
fun moveToSamplePage() {
if (DataHolder.sampleReadCounter > Constants.MAXIMUM_TEST_ALLOWED_BEFORE_REFERENCE) {
DataHolder.sampleReadCounter = 0
DataHolder.isReferenceTaken = false
parentFragmentManager.beginTransaction()
.replace(R.id.fl_main, TestRightExpReference())
.commit()
} else {
parentFragmentManager.beginTransaction().replace(R.id.fl_main, TestRightExpSample())
.commit()
}
}
private fun saveLog() {
Log.d(TAG, "saveLog() called")
val sdfDate = SimpleDateFormat("ddMMyyyy HHmmss")
val fileName: String = "log_" + sdfDate.format(Date()) + ".txt"
viewModel.saveLog(requireContext().applicationContext, fileName)
// if (!DataHolder.isAppFolderCreated) {
// val folderPath = MyUtils.createAppFolder(requireContext().applicationContext)
// if (folderPath != null) {
// DataHolder.isAppFolderCreated = true
// DataHolder.appFolderPath = folderPath
// viewModel.saveLog(DataHolder.appFolderPath, fileName)
// }
// } else {
// viewModel.saveLog(DataHolder.appFolderPath, fileName)
// }
}
// private fun saveCsv() {
// Log.d(TAG, "saveCsv() called")
//
// val sdfDate = SimpleDateFormat("ddMMyyyy HHmmss")
// val fileName: String = sdfDate.format(Date()) + ".csv"
//
// if (!DataHolder.isAppFolderCreated) {
// val folderPath = MyUtils.createAppFolder(requireContext().applicationContext)
// if (folderPath != null) {
// DataHolder.isAppFolderCreated = true
// DataHolder.appFolderPath = folderPath
// viewModel.saveCsv(DataHolder.appFolderPath, fileName)
//
// viewModel.saveCsvForTesting(DataHolder.appFolderPath, "testing$fileName")
// }
// } else {
// viewModel.saveCsv(DataHolder.appFolderPath, fileName)
//
// viewModel.saveCsvForTesting(DataHolder.appFolderPath, "testing$fileName")
// }
//
// }
private fun saveCsv() {
Log.d(TAG, "saveCsv() called")
// val sdfDate = SimpleDateFormat("ddMMyyyy HHmmss")
// val fileName: String = sdfDate.format(Date()) + ".csv"
val prefix = "HPOSSC_${DataHolder.deviceSerialNumber}_"
val fileExtension = ".csv"
val fileName = PreferenceUtility.generateId(requireContext(), prefix) + fileExtension
viewModel.saveCsv(requireContext().applicationContext, fileName)
viewModel.saveCsvForTesting(requireContext().applicationContext, "testing$fileName")
}
private fun updateResults() {
binding.tvName.text = getString(R.string.name_in_textview, viewModel.patientDetails.name)
binding.tvAge.text =
getString(R.string.age_in_textview, viewModel.patientDetails.age.toString())
binding.tvGender.text =
getString(R.string.gender_in_textview, viewModel.patientDetails.gender)
if (DataHolder.selectedTestType == TestType.SICKLECERT){
when (viewModel.patientDetails.results) {
TestRightResultType.NORMAL -> {
binding.resultNormal.visibility = View.VISIBLE
}
TestRightResultType.SICKLECELLDISEASE -> {
binding.resultDisease.visibility = View.VISIBLE
}
TestRightResultType.SICKLECELLTRAIT -> {
binding.resultTrait.visibility = View.VISIBLE
}
else -> {
// binding.resultUndefined.visibility = View.VISIBLE
Toast.makeText(requireContext().applicationContext, "Please Test Again", Toast.LENGTH_LONG).show()
moveToSamplePage()
// val i = Intent(requireContext().applicationContext, MainActivity::class.java)
// startActivity(i)
}
}
} else {
when (viewModel.patientDetails.results) {
TestRightResultType.SICKLECELLDISEASE -> {
binding.resultDisease.visibility = View.VISIBLE
binding.resultDisease.text = "Positive"
}
TestRightResultType.NORMAL -> {
binding.resultNormal.visibility = View.VISIBLE
binding.resultNormal.text = "Negative"
}
else -> {
Toast.makeText(requireContext().applicationContext, "Please Test Again", Toast.LENGTH_LONG).show()
moveToSamplePage()
// val i = Intent(requireContext().applicationContext, MainActivity::class.java)
// startActivity(i)
}
}
}
// when (viewModel.patientDetails.results) {
// TestRightResultType.NORMAL -> {
// binding.resultNormal.visibility = View.VISIBLE
// }
// TestRightResultType.SICKLECELLDISEASE -> {
// binding.resultDisease.visibility = View.VISIBLE
// }
// TestRightResultType.SICKLECELLTRAIT -> {
// binding.resultTrait.visibility = View.VISIBLE
// }
// else -> {
// binding.resultUndefined.visibility = View.VISIBLE
// }
// }
// Log.d(TAG, "\n\n\n\nFor intensity Reference array size = ${DataHolder.intensityReferenceArray.size}")
// for (each in DataHolder.intensityReferenceArray){
// Log.d(TAG, "${each}")
// }
//
// Log.d(TAG, "\n\n\n\nFor intensity Reference array size = ${viewModel.intensitySampleArray.size}")
// for (each in viewModel.intensitySampleArray){
// Log.d(TAG, "${each}")
// }
// Log.d(TAG,"")
}
}

View File

@@ -1,68 +1,38 @@
package com.example.hpostesting.presentation.testRight
package com.example.hpos.presentation.testRight
import android.content.Context
import android.net.Uri
import androidx.lifecycle.LiveData
import android.util.Log
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.example.hpostesting.data.DataHolder
import com.example.hpostesting.data.NetworkStatusLiveData
import com.example.hpostesting.data.constant.Constants
import com.example.hpostesting.data.dao.UserDao
import com.example.hpostesting.data.model.CalculationVariableForTest
import com.example.hpostesting.data.model.ErrorMessage
import com.example.hpostesting.data.model.Response
import com.example.hpostesting.data.model.patient.UserData
import com.example.hpostesting.data.model.test.TestRightCalculationData
import com.example.hpostesting.data.model.test.TestRightDeviceConstants
import com.example.hpostesting.data.model.test.TestType
import com.example.hpostesting.data.repository.DatabaseRepository
import com.example.hpostesting.domain.ResultCalculationWithMaxImpl
import com.example.hpostesting.domain.SaveRawData
import com.example.hpostesting.domain.SaveRawDataTest
import com.example.hpostesting.domain.SickleFindResultCaluculationWithMaxImpl
import com.example.hpostesting.domain.TestRightResultCalculation
import com.example.hpostesting.util.MyUtils
import com.google.firebase.storage.FirebaseStorage
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.launch
import kotlinx.coroutines.tasks.await
import java.io.File
import com.example.hpos.data.DataHolder
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.model.*
import com.example.hpos.domain.*
import com.example.hpos.util.MyUtils
import java.text.SimpleDateFormat
import java.util.Calendar
import java.util.Date
import java.util.Locale
import javax.inject.Inject
import java.util.*
import java.util.Collections.sort
import kotlin.collections.ArrayList
import kotlin.math.log10
import kotlin.math.pow
@HiltViewModel
class TestRightViewModel @Inject constructor(
private val saveRawData: SaveRawData,
private val saveRawDataTest: SaveRawDataTest,
private val repository: DatabaseRepository,
private val userDao: UserDao,
context: Context
) : ViewModel() {
class TestRightViewModel : ViewModel() {
private val TAG = "TestRightViewModel"
var isServiceConnected = false
val progressBar = MutableLiveData(false)
// val errorTriggered = MutableLiveData<String>("")
val errorTriggered = MutableLiveData<ErrorMessage>()
var numberOfSampleRun = 0
val fireBaseUpload = MutableLiveData<String>()
val testDetails = DataHolder.selectedTest
private val _networkStatusLiveData = NetworkStatusLiveData(context)
val networkStatusLiveData: LiveData<Boolean>
get() = _networkStatusLiveData
val allUserData = userDao.getAll()
lateinit var patientDetails: PatientData
// var deviceConstant: TestRightDeviceConstants? = null
private lateinit var calculationData: TestRightCalculationData
/* (For exp sample) Contains pixel no. -> Intensity of light falling on that pixel */
val intensitySampleArray = ArrayList<Double>()
val wavelengthToAbsorbance = ArrayList<ArrayList<Double>>()
@@ -70,6 +40,8 @@ class TestRightViewModel @Inject constructor(
val calculationVariableList = ArrayList<CalculationVariableForTest>()
fun mapDeviceConstants(string: String) {
// Log.d(TAG, "mapDeviceConstants() called")
// Log.d(TAG, "mapDeviceConstants() value -> $string")
if (string.isNotEmpty()) {
val listOfStrings = string.split(",")
if (listOfStrings.size >= 4) {
@@ -86,7 +58,8 @@ class TestRightViewModel @Inject constructor(
// "Error 201: In processing the data from device"
errorTriggered.postValue(
ErrorMessage(
"Error 201: In processing the data from device", Constants.ERROR_NORMAL
"Error 201: In processing the data from device",
Constants.ERROR_NORMAL
)
)
}
@@ -95,7 +68,8 @@ class TestRightViewModel @Inject constructor(
// "Error 202: Unable to fetch data from device."
errorTriggered.postValue(
ErrorMessage(
"Error 202: Unable to fetch data from device.", Constants.ERROR_NORMAL
"Error 202: Unable to fetch data from device.",
Constants.ERROR_NORMAL
)
)
}
@@ -108,9 +82,13 @@ class TestRightViewModel @Inject constructor(
if (DataHolder.deviceConstant != null) {
for (x in 1..Constants.TEST_RIGHT_TOTAL_PIXEL) {
// val index = x - 1
val wavelength: Double = (DataHolder.deviceConstant!!.a.toDouble() * (x.toDouble()
.pow((3).toDouble()))) + (DataHolder.deviceConstant!!.b.toDouble() * (x.toDouble()
.pow((2).toDouble()))) + (DataHolder.deviceConstant!!.c.toDouble() * x) + (DataHolder.deviceConstant!!.d.toDouble())
val wavelength: Double =
(DataHolder.deviceConstant!!.a.toDouble() * (x.toDouble()
.pow((3).toDouble()))) +
(DataHolder.deviceConstant!!.b.toDouble() * (x.toDouble()
.pow((2).toDouble()))) +
(DataHolder.deviceConstant!!.c.toDouble() * x) +
(DataHolder.deviceConstant!!.d.toDouble())
DataHolder.wavelengthToPixelArray.add(wavelength)
}
@@ -119,7 +97,8 @@ class TestRightViewModel @Inject constructor(
// "Error 203: Unable to fetch data from device."
errorTriggered.postValue(
ErrorMessage(
"Error 203: Unable to fetch data from device.", Constants.ERROR_NORMAL
"Error 203: Unable to fetch data from device.",
Constants.ERROR_NORMAL
)
)
@@ -132,20 +111,26 @@ class TestRightViewModel @Inject constructor(
if (isReference) DataHolder.intensityReferenceArray.clear()
else intensitySampleArray.clear()
Log.d("SURYAKUMAR", fullString)
val listOfString = fullString.split("\n")
for (line in listOfString) {
if ("Buf" in line) {/* Removing trailing spaces and "Buf" from the string then taking lhs & rhs of ':' */
val numbers = line.trim().substring(3).split(":")
if ("Buf" in line) {
/* Removing trailing spaces and "Buf" from the string then taking lhs & rhs of ':' */
val numbers = line.trim()
.substring(3).split(":")
if (numbers.size >= 2) {
if (isReference) DataHolder.intensityReferenceArray.add(numbers[1].toDouble())
else intensitySampleArray.add(numbers[1].toDouble())
if (isReference)
DataHolder.intensityReferenceArray.add(numbers[1].toDouble())
else
intensitySampleArray.add(numbers[1].toDouble())
} else {
// "Error 204: Unable to fetch data from device."
errorTriggered.postValue(
ErrorMessage(
"Error 204: Unable to fetch data from device.", Constants.ERROR_NORMAL
"Error 204: Unable to fetch data from device.",
Constants.ERROR_NORMAL
)
)
@@ -255,11 +240,7 @@ class TestRightViewModel @Inject constructor(
val resultCalculation: TestRightResultCalculation = ResultCalculationWithMaxImpl()
calculationData = resultCalculation.getResults(wavelengthToAbsorbance)
// patientDetails.results = resultCalculation.getResults(wavelengthToAbsorbance)
// patientDetails.results = calculationData.result
testDetails?.result = calculationData.result
testDetails?.resultRatio = calculationData.ratioValue
testDetails?.testStatus = true
patientDetails.results = calculationData.result
}
@@ -268,28 +249,25 @@ class TestRightViewModel @Inject constructor(
val resultCalculation: TestRightResultCalculation =
SickleFindResultCaluculationWithMaxImpl()
calculationData = resultCalculation.getResults(wavelengthToAbsorbance)
testDetails?.result = calculationData.result
testDetails?.testStatus = true
patientDetails.results = calculationData.result
}
fun saveCsv(appContext: Context, filename: String) {
// try {
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
// SaveRawData().saveCsv(folderPath!!, filename, wavelengthToAbsorbance)
saveRawData.saveCsv(folderPath!!, filename, wavelengthToAbsorbance)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
// SaveRawData().saveCsv(folderPath, filename, wavelengthToAbsorbance)
saveRawData.saveCsv(folderPath, filename, wavelengthToAbsorbance)
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
SaveRawData().saveCsv(folderPath!!, filename, wavelengthToAbsorbance)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
SaveRawData().saveCsv(folderPath, filename, wavelengthToAbsorbance)
} else {
// errorTriggered.postValue("Unable to save CSV, Please try again")
}
}
}
// } catch (e: java.io.FileNotFoundException) {
// errorTriggered.postValue(
// ErrorMessage(
@@ -302,22 +280,19 @@ class TestRightViewModel @Inject constructor(
fun saveCsvForTesting(appContext: Context, filename: String) {
// try {
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
// SaveRawDataTest().saveCsv(folderPath!!, filename, calculationVariableList)
saveRawDataTest.saveCsv(folderPath!!, filename, calculationVariableList)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
// SaveRawDataTest().saveCsv(folderPath, filename, calculationVariableList)
saveRawDataTest.saveCsv(folderPath, filename, calculationVariableList)
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
SaveRawDataTest().saveCsv(folderPath!!, filename, calculationVariableList)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
SaveRawDataTest().saveCsv(folderPath, filename, calculationVariableList)
} else {
// errorTriggered.postValue("Unable to save CSV, Please try again")
}
}
}
// } catch (e: java.io.FileNotFoundException) {
// errorTriggered.postValue(
// ErrorMessage(
@@ -330,22 +305,20 @@ class TestRightViewModel @Inject constructor(
fun saveLog(appContext: Context, fileName: String) {
// try {
var folderPath: String? = DataHolder.appFolderPath
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
// SaveRawData().saveLog(folderPath!!, fileName, calculationData)
saveRawData.saveLog(folderPath!!, fileName, calculationData)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
// SaveRawData().saveLog(folderPath, fileName, calculationData)
saveRawData.saveLog(folderPath, fileName, calculationData)
if (DataHolder.isAppFolderCreated) {
SaveRawData().saveLog(folderPath!!, fileName, calculationData)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
SaveRawData().saveLog(folderPath, fileName, calculationData)
} else {
// errorTriggered.postValue("Unable to save Log, Please try again")
}
}
}
// } catch (e: java.io.FileNotFoundException) {
// errorTriggered.postValue(
// ErrorMessage(
@@ -358,26 +331,30 @@ class TestRightViewModel @Inject constructor(
fun saveLogWithPatient(appContext: Context, fileName: String) {
// try {
var folderPath: String? = DataHolder.appFolderPath
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
// SaveRawData().saveLogWithPatientData(
saveRawData.saveLogWithPatientData(
folderPath!!, fileName, calculationData, testDetails
)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
// SaveRawData().saveLogWithPatientData(
saveRawData.saveLogWithPatientData(
folderPath, fileName, calculationData, testDetails
if (DataHolder.isAppFolderCreated) {
SaveRawData().saveLogWithPatientData(
folderPath!!,
fileName,
calculationData,
patientDetails
)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
SaveRawData().saveLogWithPatientData(
folderPath,
fileName,
calculationData,
patientDetails
)
} else {
// errorTriggered.postValue("Unable to save Log, Please try again")
}
}
}
// } catch (e: java.io.FileNotFoundException) {
// errorTriggered.postValue(
// ErrorMessage(
@@ -399,136 +376,17 @@ class TestRightViewModel @Inject constructor(
var folderPath: String? = DataHolder.appFolderPath
if (DataHolder.isAppFolderCreated) {
saveRawDataTest.saveLog(folderPath!!, fileName, isReference, fullString)
// SaveRawDataTest().saveLog(folderPath!!, fileName, isReference, fullString)
SaveRawDataTest().saveLog(folderPath!!, fileName, isReference, fullString)
} else {
folderPath = MyUtils.createAppFolder(appContext)
if (folderPath != null) {
DataHolder.isAppFolderCreated = true
DataHolder.appFolderPath = folderPath
saveRawDataTest.saveLog(folderPath, fileName, isReference, fullString)
// SaveRawDataTest().saveLog(folderPath, fileName, isReference, fullString)
SaveRawDataTest().saveLog(folderPath, fileName, isReference, fullString)
} else {
// errorTriggered.postValue("Unable to save Log, Please try again")
}
}
}
fun getCSVFileName(): String {
val prefixCsv: String =
if (DataHolder.selectedTestType == TestType.SICKLECERT) "HPOSSC_${testDetails?._id}"
else "HPOSSF_${testDetails?._id}"
val fileExtensionCsv = ".csv"
return prefixCsv + fileExtensionCsv
}
fun getLogFileName(): String {
val prefixTxt = "log_${testDetails?._id}"
val fileExtensionTxt = ".txt"
return prefixTxt + fileExtensionTxt
}
private fun addResultTestToDb() {
testDetails?.testTime = SimpleDateFormat(
"yyyy-MM-dd HH:mm:ss", Locale.getDefault()
).format(Calendar.getInstance().time)
viewModelScope.launch {
testDetails!!.reportUploadTime = SimpleDateFormat(
"yyyy-MM-dd HH:mm:ss", Locale.getDefault()
).format(Calendar.getInstance().time)
when (repository.addTestToDatabase(testDetails)) {
is Response.Success -> {
fireBaseUpload.postValue("Success")
}
else -> {}
}
}
}
fun uploadResultToDatabase(context: Context, isOnline: Boolean,deviceSerialNumber: String) = viewModelScope.launch {
val csvFilePath = MyUtils.getAppFolderPath(context) + getCSVFileName()
val logTxtFilePath = MyUtils.getAppFolderPath(context) + getLogFileName()
testDetails?.csvPath = csvFilePath
testDetails?.reportPath = logTxtFilePath
testDetails?.deviceSerialNumber = deviceSerialNumber
if (isOnline) {
val storageRef = FirebaseStorage.getInstance().reference
val storageTestDetailsRef = storageRef.child("${testDetails?._id}/")
try {
val csvFileUri = Uri.fromFile(File(csvFilePath))
val logTxtFileUri = Uri.fromFile(File(logTxtFilePath))
val csvUploadTask =
storageTestDetailsRef.child(csvFileUri.lastPathSegment!!).putFile(csvFileUri)
.await()
val logUploadTask = storageTestDetailsRef.child(logTxtFileUri.lastPathSegment!!)
.putFile(logTxtFileUri).await()
val csvUri = csvUploadTask.storage.downloadUrl.await().toString()
val logUri = logUploadTask.storage.downloadUrl.await().toString()
val serialNumber = Constants.STATICID.firstOrNull { it == deviceSerialNumber }
testDetails?.csvPath = csvUri
testDetails?.reportPath = logUri
addResultTestToDb()
} catch (exception: Exception) {
// Handle the exception appropriately (e.g., log the error, display an error message)
}
} else {
testDetails?.testTime = SimpleDateFormat(
"yyyy-MM-dd HH:mm:ss", Locale.getDefault()
).format(Calendar.getInstance().time)
userDao.insertAll(testDetails!!)
}
}
fun bulkUploadResultToDatabase(userData: UserData) = viewModelScope.launch {
val storageRef = FirebaseStorage.getInstance().reference
val storageTestDetailsRef = storageRef.child("${testDetails?._id}/")
try {
val csvFileUri = Uri.fromFile(File(userData.csvPath))
val logTxtFileUri = Uri.fromFile(File(userData.reportPath))
val csvUploadTask =
storageTestDetailsRef.child(csvFileUri.lastPathSegment!!).putFile(csvFileUri)
.await()
val logUploadTask =
storageTestDetailsRef.child(logTxtFileUri.lastPathSegment!!).putFile(logTxtFileUri)
.await()
val csvUri = csvUploadTask.storage.downloadUrl.await().toString()
val logUri = logUploadTask.storage.downloadUrl.await().toString()
userData.csvPath = csvUri
userData.reportPath = logUri
bulkAddResultTestToDb(userData)
} catch (exception: Exception) {
// Handle the exception appropriately (e.g., log the error, display an error message)
}
}
private fun bulkAddResultTestToDb(userData: UserData) {
viewModelScope.launch {
userData.reportUploadTime = SimpleDateFormat(
"yyyy-MM-dd HH:mm:ss", Locale.getDefault()
).format(Calendar.getInstance().time)
when (repository.addTestToDatabase(userData)) {
is Response.Success -> {
fireBaseUpload.postValue("Success")
}
else -> {}
}
}
}
fun deleteById(userId: String) = viewModelScope.launch {
userDao.deleteById(id = userId)
}
}

View File

@@ -0,0 +1,123 @@
package com.example.hpos.presentation.testRight
import android.app.Service
import android.content.Intent
import android.hardware.usb.UsbDeviceConnection
import android.os.Binder
import android.os.IBinder
import android.util.Log
import com.example.hpos.data.constant.Constants
import com.example.hpos.data.constant.TestRightCommands
import com.example.hpos.presentation.UsbServiceListener
import com.hoho.android.usbserial.driver.UsbSerialDriver
import com.hoho.android.usbserial.driver.UsbSerialPort
import com.hoho.android.usbserial.util.SerialInputOutputManager
import java.io.IOException
class UsbService : Service() {
// Binder to be given to clients
private val binder = UsbServiceBinder()
private lateinit var mPort: UsbSerialPort
private var isUsbConnected = false
private val TAG = "UsbService"
inner class UsbServiceBinder : Binder() {
// Return this instance of UsbService so clients can call public methods
fun getService(): UsbService = this@UsbService
}
override fun onBind(intent: Intent): IBinder {
Log.d("surya", "onBind() called")
return binder
}
// fun connect(driver: UsbSerialDriver, connection: UsbDeviceConnection) {
// mPort = driver.ports[0] // Most devices have just one port (port 0)
// mPort.open(connection)
// mPort.setParameters(115200, 8, UsbSerialPort.STOPBITS_1, UsbSerialPort.PARITY_NONE)
//
// isUsbConnected = true
// Log.d(TAG, "My Usb Connected ${mPort.driver}")
// }
var listener: UsbServiceListener? = null
fun connect(driver: UsbSerialDriver, connection: UsbDeviceConnection) {
mPort = driver.ports[0] // Most devices have just one port (port 0)
mPort.open(connection)
mPort.setParameters(115200, 8, UsbSerialPort.STOPBITS_1, UsbSerialPort.PARITY_NONE)
isUsbConnected = true
Log.d(TAG, "My Usb Connected ${mPort.driver}")
val usbIoManager = SerialInputOutputManager(mPort,
object : SerialInputOutputManager.Listener{
override fun onNewData(data: ByteArray?) {
// Log.e(TAG, "onNewData() called inside eventDrivenWrite()")
listener?.onUsbRead(data)
}
override fun onRunError(e: Exception?) {
Log.e(TAG, "onRunError() called inside eventDrivenWrite()")
listener?.onUsbError(e)
}
})
usbIoManager.start();
}
fun disconnect() {
if(isUsbConnected){
mPort.close()
isUsbConnected = false;
Log.d(TAG, "My Usb disconnected:: ${mPort.driver}")
}
}
// fun eventDrivenWrite(command: TestRightCommands, listener: UsbServiceListener) {
// val usbIoManager = SerialInputOutputManager(mPort,
// object : SerialInputOutputManager.Listener{
// override fun onNewData(data: ByteArray?) {
// Log.e(TAG, "onNewData() called inside eventDrivenWrite() :: command = ${command.command}")
// listener.onUsbRead(data)
// }
// override fun onRunError(e: Exception?) {
// Log.e(TAG, "onRunError() called inside eventDrivenWrite()")
// listener.onUsbError(e)
// }
//
// })
// usbIoManager.start();
//
// try {
// mPort.write(command.command.toByteArray(), Constants.WRITE_TIMEOUT_MILLIS)
// } catch (e: IOException) {
// listener.onUsbError(e)
// }
// }
fun eventDrivenWrite(command: TestRightCommands, listener: UsbServiceListener) {
this.listener = listener
try {
mPort.write(command.command.toByteArray(), Constants.WRITE_TIMEOUT_MILLIS)
} catch (e: IOException) {
listener.onUsbError(e)
}
}
// fun write(command: TestRightCommands){
// mPort.write(command.command.toByteArray(), Constants.WRITE_TIMEOUT_MILLIS)
// }
// fun read(){
// val byteArray = ByteArray(3700)
// val len = mPort.read(byteArray, Constants.READ_TIMEOUT_MILLIS)
//
// Log.d(TAG, "length is $len")
// val byteArrayCropped = ByteArray(len)
// System.arraycopy(byteArray, 0, byteArrayCropped, 0, len)
//
// listener?.onUsbRead(byteArrayCropped)
// }
}

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.presentation.utils
package com.example.hpos.presentation.utils
interface MyDialogListener {
fun onClickNegativeButton()

View File

@@ -1,4 +1,4 @@
package com.example.hpostesting.presentation.utils
package com.example.hpos.presentation.utils
import android.content.Context
import android.widget.Toast

View File

@@ -0,0 +1,25 @@
package com.example.hpos.util
import android.content.Context
import android.os.Environment
import com.example.hpos.R
import java.io.File
object MyUtils {
fun createAppFolder(context: Context) : String? {
val folderPath = Environment.getExternalStorageDirectory().absolutePath + "/" + context.resources.getString(R.string.app_name) + "/"
val file = File(folderPath)
return if (!file.exists()) {
if (!file.mkdirs()) {
null
} else {
folderPath
}
} else {
folderPath
}
}
}

View File

@@ -0,0 +1,19 @@
package com.example.hpos.util
import android.content.Context
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelProvider
import com.example.hpos.presentation.MainViewModel
import com.example.hpos.presentation.testRight.TestRightViewModel
class MyViewModelFactory(private val context: Context) : ViewModelProvider.Factory {
override fun <T : ViewModel> create(modelClass: Class<T>): T {
if (modelClass.isAssignableFrom(MainViewModel::class.java))
return MainViewModel() as T
else if (modelClass.isAssignableFrom(TestRightViewModel::class.java))
return TestRightViewModel() as T
else
throw IllegalArgumentException("Unknown ViewModel class");
}
}

View File

@@ -1,30 +0,0 @@
package com.example.hpostesting
import android.app.Application
import android.content.Context
import androidx.room.Room
import com.example.hpostesting.data.dao.MyDatabase
import com.google.android.datatransport.runtime.dagger.Provides
import com.google.firebase.firestore.FirebaseFirestore
import com.google.firebase.firestore.FirebaseFirestoreSettings
import dagger.hilt.android.HiltAndroidApp
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.SupervisorJob
import javax.inject.Singleton
@HiltAndroidApp
class HPOSTestingApplication: Application() {
val applicationScope = CoroutineScope(SupervisorJob() + Dispatchers.IO)
override fun onCreate() {
super.onCreate()
val applicationScope = CoroutineScope(SupervisorJob() + Dispatchers.IO)
val firestoreSettings = FirebaseFirestoreSettings.Builder()
.setPersistenceEnabled(true) // Enable offline persistence if needed
.build()
val firestore = FirebaseFirestore.getInstance()
firestore.firestoreSettings = firestoreSettings
}
}

View File

@@ -1,30 +0,0 @@
package com.example.hpostesting.data
import androidx.lifecycle.MutableLiveData
import com.example.hpostesting.data.model.patient.HemoCubeTestData
import com.example.hpostesting.data.model.patient.UserData
import com.example.hpostesting.data.model.test.TestRightDeviceConstants
import com.example.hpostesting.data.model.test.TestType
object DataHolder {
var selectedTestType: TestType = TestType.SICKLECERT
val usbConnected = MutableLiveData(true)
var mobileUniqueId: String? = null
var isAppFolderCreated = false
var appFolderPath = ""
var isReferenceTaken = false
var sampleReadCounter = 0
var deviceConstant: TestRightDeviceConstants? = null
var deviceSerialNumber: String = "ABCD"
val deviceType = MutableLiveData<String>()
val wavelengthToPixelArray = ArrayList<Double>()
val intensityReferenceArray = ArrayList<Double>()
var selectedTest: UserData? = null
var hemoCubeTestData: HemoCubeTestData? = null
var kitSerial: String = ""
var location: UserData.Location? = null
var testExp: Boolean = true
var hemocubeResult: Double? = null
}

View File

@@ -1,62 +0,0 @@
package com.example.hpostesting.data
import android.content.Context
import android.net.ConnectivityManager
import android.net.Network
import android.net.NetworkCapabilities
import android.net.NetworkRequest
import android.os.Build
import androidx.annotation.RequiresApi
import androidx.lifecycle.LiveData
class NetworkStatusLiveData(context: Context) : LiveData<Boolean>() {
private val connectivityManager: ConnectivityManager =
context.applicationContext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
private val networkCallback = object : ConnectivityManager.NetworkCallback() {
override fun onAvailable(network: Network) {
postValue(true)
}
override fun onLost(network: Network) {
postValue(false)
}
}
@RequiresApi(Build.VERSION_CODES.M)
override fun onActive() {
super.onActive()
postValue(isNetworkAvailable())
registerNetworkCallback()
}
override fun onInactive() {
super.onInactive()
unregisterNetworkCallback()
}
private fun registerNetworkCallback() {
val networkRequest = NetworkRequest.Builder()
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
.addTransportType(NetworkCapabilities.TRANSPORT_ETHERNET)
.build()
connectivityManager.registerNetworkCallback(networkRequest, networkCallback)
}
private fun unregisterNetworkCallback() {
connectivityManager.unregisterNetworkCallback(networkCallback)
}
@RequiresApi(Build.VERSION_CODES.M)
private fun isNetworkAvailable(): Boolean {
val network = connectivityManager.activeNetwork
val networkCapabilities = connectivityManager.getNetworkCapabilities(network)
return networkCapabilities != null &&
networkCapabilities.hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET) &&
networkCapabilities.hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED)
}
}

View File

@@ -1,7 +0,0 @@
package com.example.hpostesting.data
sealed class Result<out T : Any> {
data class Success<out T : Any>(val data: T) : Result<T>()
data class Error(val exception: Exception) : Result<Nothing>()
class Loading<T : Any> : Result<T>()
}

View File

@@ -1,21 +0,0 @@
package com.example.hpostesting.data.api
import com.example.hpostesting.data.model.deviceprovision.DeviceProvisionRequest
import com.example.hpostesting.data.model.deviceprovision.DeviceProvisionResponse
import com.example.hpostesting.data.model.login.LoginRequest
import com.example.hpostesting.data.model.login.LoginResponse
import retrofit2.http.Body
import retrofit2.http.POST
interface MolbioAuthApi {
@POST("deviceManagement/device/provision")
suspend fun deviceProvision(
@Body deviceProvisionRequest: DeviceProvisionRequest
): DeviceProvisionResponse
@POST("deviceService/device/login")
suspend fun login(
@Body loginRequest: LoginRequest
): LoginResponse
}

View File

@@ -1,39 +0,0 @@
package com.example.hpostesting.data.api
import com.example.hpostesting.data.model.log.UploadLogsResponse
import com.example.hpostesting.data.model.molbioresult.MolbioV2ResultRequest
import com.example.hpostesting.data.model.molbioresult.MolbioV2ResultResponse
import com.example.hpostesting.data.model.updates.CheckUpdateRequest
import com.example.hpostesting.data.model.updates.CheckUpdateResponse
import com.example.hpostesting.data.model.updates.DeviceUpdateRequest
import okhttp3.MultipartBody
import okhttp3.ResponseBody
import retrofit2.http.Body
import retrofit2.http.Multipart
import retrofit2.http.POST
import retrofit2.http.PUT
import retrofit2.http.Part
interface MolbioResultApi {
@PUT("deviceService/results/HPOS")
suspend fun uploadResults(
@Body molbioV2ResultRequest: MolbioV2ResultRequest
): MolbioV2ResultResponse
@POST("deviceService/device/checkUpdate")
suspend fun checkUpdate(
@Body checkUpdateRequest: CheckUpdateRequest
): CheckUpdateResponse
@POST("deviceService/device/getUpdate")
suspend fun deviceUpdate(
@Body deviceUpdateRequest: DeviceUpdateRequest
): ResponseBody
@Multipart
@POST("deviceService/device/uploadLogs")
suspend fun uploadLogs(
@Part logFile: MultipartBody.Part
): UploadLogsResponse
}

View File

@@ -1,6 +0,0 @@
package com.example.hpostesting.data.api
interface PropertyProvider {
fun getProperty(key: String): String
}

View File

@@ -1,247 +0,0 @@
package com.example.hpostesting.data.constant
object Constants {
const val ACTION_USB_PERMISSION = "shanmukha.in.sickle_cell.USB_PERMISSION"
const val HOMOCUBE_USB_PERMISSION = "shanmukha.in.sickle_cell_homocube.USB_PERMISSION"
const val BASE_URL = "www.google.com"
const val ABHA_APP_PACKAGE = "in.ndhm.phr"
const val serialNumber = "NKH5555AH"
const val deviceTypeName = "HPOS"
const val uid = "NKH5555AH"
const val deviceProvisionEmail = "HPOS_provisioner@bigtec.co.in"
const val deviceProvisionPassword = "f2ab0e7f9d69"
const val deviceID = "HCV-000-3001"
const val devicePassword = "810516d8f4c7"
const val ACCESS_TOKEN = "accessToken"
const val NATS_TOKEN = "natsToken"
const val WRITE_TIMEOUT_MILLIS = 30000 // 30 sec
const val READ_TIMEOUT_MILLIS = 60000 // 1 min
const val DELAY_BETWEEN_COMMANDS: Long = 1000
const val TEST_RIGHT_TOTAL_PIXEL = 3694
const val MAXIMUM_TEST_ALLOWED_BEFORE_REFERENCE = 40
const val RANGE_IN_RESULT_CALCULATIONS = 10
const val WAVELENGTH_OF_INTEREST_ONE = 427
const val WAVELENGTH_OF_INTEREST_TWO = 555
const val MIN_WAVELENGTH_RANGE_TO_RECORD = 350
const val MAX_WAVELENGTH_RANGE_TO_RECORD = 750
const val DEVICE_PRODUCT_ID = 24597
const val DEVICE_TYPE_HOMOCUBE = "HOMOCUBE"
const val DEVICE_TYPE_TEST_RIGHT = "TEST_RIGHT"
const val DEVICE_VENDOR_ID = 1027
const val HOMO_CUBE_ID = 29987
const val VENDOR_ID = 6790
const val HEMO_CUBE_V2_PRODUCT_ID = 24577
const val HEMO_CUBE_V2_VENDOR_ID = 1027
const val ERROR_NORMAL = 400
const val ERROR_CRITICAL = 401
const val NO_OF_TIMES_TO_RUN_SAMPLE = 1
const val USER_ID = "usernameId"
val STATICID = listOf(
"ADMIN",
"VIZ-1000-0004",
"VIZ-1000-0005",
"VIZ-1000-0006",
"HC-V1-001",
"HC-V1-002",
"HC-V1-003",
"HC-V1-004",
"HC-V1-005",
"HC-V1-006",
"HC-V1-007",
"HC-V1-008",
"HC-V1-009",
"HC-V1-010",
"HC-V1-011",
"HC-V1-012",
"HC-V1-013",
"HC-V1-014",
"HC-V1-015",
"HC-V1-016",
"HC-V1-017",
"HC-V1-018",
"HC-V1-019",
"HC-V1-020",
"HCV-000-3001",
"HCV-000-3002",
"HCV-000-3003",
"HCV-000-3004",
"HCV-000-3005",
"HCV-000-3006",
"HCV-000-3007",
"HCV-000-3008",
"HCV-000-3009",
"HCV-000-3010"
)
const val password = "SMI@12345"
const val KIT_NUMBER = "KitNumber"
const val KIT_COUNT = "KitCount"
const val BUFFER_VALUE_1 = "BufferValue1"
const val BUFFER_VALUE_2 = "BufferValue2"
const val BUFFER_VALUE_3 = "BufferValue3"
const val BUFFER_VALUE_4 = "BufferValue4"
const val DEVICE_ID = "DEVICE_ID"
const val BUFFER_LED_LOWER_BOUND = 21000
const val BUFFER_LED_UPPER_BOUND = 24500
const val TEST_STATUS_CODE_TEST_STARTED = 1.0
const val TEST_STATUS_CODE_CONFIG_STARTED = 2.0
const val TEST_STATUS_CODE_CONFIG_COMPLETED = 3.0
const val TEST_STATUS_CODE_BUFFER_STARTED = 4.0
const val TEST_STATUS_CODE_BUFFER_COMPLETED = 5.0
const val TEST_STATUS_CODE_BUFFER_PRINT_STARTED = 6.0
const val TEST_STATUS_CODE_BUFFER_PRINT_COMPLETED = 7.0
const val TEST_STATUS_CODE_SAMPLE_STARTED = 8.0
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
val DEVICE_CONFIGURATION: Map<String, List<List<Double>>> = mapOf<String, List<List<Double>>>(
"HCV-000-3001" to listOf(
listOf(1.313, -0.89), // LED1, 435nm
listOf(0.581462456, -0.58502), // LED2, 415nm
listOf(0.2012, 0.0092), // LED3, 555nm
listOf(1.0, 0.0) // LED4
),
"HCV-000-3002" to listOf(
listOf(0.723142, -0.09135), // LED1, 435nm
listOf(0.581462456, -0.58502), // LED2, 415nm
listOf(0.1964, 0.011565), // LED3, 555nm
listOf(1.0, 0.0) // LED4
),
"HCV-000-3003" to listOf(
listOf(0.723142, -0.09135), // LED1, 435nm
listOf(0.581462456, -0.58502), // LED2, 415nm
listOf(0.1964, 0.011565), // LED3, 555nm
listOf(1.0, 0.0) // LED4
),
"HCV-000-3004" 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-3005" 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-3006" 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-3007" 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-3008" 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-3009" 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-3010" 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
const val INCUBATION_TIME_MAX = 1400
const val BATTERY_LEVEL_MIN = 0
val BUFFER_INTENSITY_THRESHOLDS: Map<String, List<List<Int>>> = mapOf<String, List<List<Int>>>(
"HCV-000-3001" to listOf(
listOf(20000, 25074),
listOf(20000, 24596),
listOf(20000, 26065),
listOf(20000, 27093),
),
"HCV-000-3002" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3003" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3004" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3005" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3006" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3007" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3008" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3009" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
),
"HCV-000-3010" to listOf(
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
listOf(24500, 26250),
)
)
}

View File

@@ -1,9 +0,0 @@
package com.example.hpostesting.data.constant
enum class HemoCubeCommands(val command: String) {
startBuffer("B\r"),
runDiagnostics("D\r"),
startSample("S\r"),
getSample("P\r"),
getDeviceId("I\r"),
}

View File

@@ -1,30 +0,0 @@
package com.example.hpostesting.data.constant
import android.content.Context
import android.content.SharedPreferences
import java.util.Locale
object LanguageManager {
private const val LANGUAGE_PREF_KEY = "language_pref"
fun setLocale(context: Context, languageCode: String) {
val locale = Locale(languageCode)
Locale.setDefault(locale)
val resources = context.resources
val configuration = resources.configuration
configuration.setLocale(locale)
context.createConfigurationContext(configuration)
}
fun persistLanguagePreference(context: Context, languageCode: String) {
val prefs: SharedPreferences = context.getSharedPreferences("AppPrefs", Context.MODE_PRIVATE)
prefs.edit().putString(LANGUAGE_PREF_KEY, languageCode).apply()
}
fun getSavedLanguage(context: Context): String {
val prefs: SharedPreferences = context.getSharedPreferences("AppPrefs", Context.MODE_PRIVATE)
return prefs.getString(LANGUAGE_PREF_KEY, "en") ?: "en"
}
}

View File

@@ -1,38 +0,0 @@
package com.example.hpostesting.data.dao
import androidx.room.TypeConverter
import com.example.hpostesting.data.model.patient.UserData
import com.google.common.reflect.TypeToken
import com.google.gson.Gson
class Converters {
private val gson = Gson()
@TypeConverter
fun fromString(value: String?): UserData.Location? {
return if (value != null) {
gson.fromJson(value, UserData.Location::class.java)
} else {
null
}
}
@TypeConverter
fun toString(location: UserData.Location?): String? {
return if (location != null) {
gson.toJson(location)
} else {
null
}
}
@TypeConverter
fun fromList(list: List<Double>): String {
return Gson().toJson(list)
}
@TypeConverter
fun toList(json: String): List<Double> {
val type = object : TypeToken<List<Double>>() {}.type
return Gson().fromJson(json, type)
}
}

View File

@@ -1,24 +0,0 @@
package com.example.hpostesting.data.dao
import androidx.lifecycle.LiveData
import androidx.room.Dao
import androidx.room.Insert
import androidx.room.OnConflictStrategy
import androidx.room.Query
import com.example.hpostesting.data.model.patient.DeviceData
import com.example.hpostesting.data.model.patient.HemoCubeTestData
import com.example.hpostesting.data.model.patient.UserData
@Dao
interface DeviceDao {
@Query("SELECT * from device_table")
fun getAll(): LiveData<List<HemoCubeTestData>>
@Insert(onConflict = OnConflictStrategy.REPLACE)
suspend fun insertAll(deviceData: DeviceData)
@Query("SELECT * FROM device_table WHERE deviceId = :id")
suspend fun getUserByID(id: String): HemoCubeTestData
@Query("DELETE FROM device_table WHERE deviceId = :id")
suspend fun deleteById(id: String)
}

View File

@@ -1,26 +0,0 @@
package com.example.hpostesting.data.dao
import androidx.lifecycle.LiveData
import androidx.room.Dao
import androidx.room.Insert
import androidx.room.OnConflictStrategy
import androidx.room.Query
import com.example.hpostesting.data.model.patient.HemoCubeTestData
import com.example.hpostesting.data.model.patient.UserData
@Dao
interface HemoCubeDao {
@Query("SELECT * from hemo_cube_test_table")
fun getAll(): LiveData<List<HemoCubeTestData>>
@Insert(onConflict = OnConflictStrategy.REPLACE)
suspend fun insertAll(hemoCubeTestData: HemoCubeTestData)
@Query("SELECT * FROM hemo_cube_test_table WHERE _id = :id")
suspend fun getUserByID(id: String): HemoCubeTestData
@Query("DELETE FROM hemo_cube_test_table WHERE _id = :id")
suspend fun deleteById(id: String)
@Query("UPDATE hemo_cube_test_table SET localFlag = :newValue WHERE _id = :id")
suspend fun updateFieldById(id: String, newValue: Boolean)
}

View File

@@ -1,19 +0,0 @@
package com.example.hpostesting.data.dao
import android.content.Context
import androidx.room.Database
import androidx.room.Room
import androidx.room.RoomDatabase
import androidx.room.TypeConverters
import com.example.hpostesting.data.model.patient.DeviceData
import com.example.hpostesting.data.model.patient.UserData
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)
@TypeConverters(Converters::class)
abstract class MyDatabase : RoomDatabase() {
abstract fun userDao(): UserDao
abstract fun hemoCubeDao(): HemoCubeDao
}

View File

@@ -1,23 +0,0 @@
package com.example.hpostesting.data.dao
import androidx.lifecycle.LiveData
import androidx.room.Dao
import androidx.room.Insert
import androidx.room.OnConflictStrategy
import androidx.room.Query
import com.example.hpostesting.data.model.patient.UserData
@Dao
interface UserDao {
@Query("SELECT * from user_table")
fun getAll(): LiveData<List<UserData>>
@Insert(onConflict = OnConflictStrategy.REPLACE)
suspend fun insertAll(userData: UserData)
@Query("SELECT * FROM user_table WHERE _id = :id")
suspend fun getUserByID(id: String): UserData
@Query("DELETE FROM user_table WHERE _id = :id")
suspend fun deleteById(id: String)
}

View File

@@ -1,23 +0,0 @@
package com.example.hpostesting.data.datasource
import com.opencsv.CSVWriter
import java.io.File
import java.io.FileWriter
class LocalFileDataSource {
fun saveCsvToDisk(filepath: String, contents: ArrayList<Array<String>>){
val writer = CSVWriter(FileWriter(filepath))
writer.writeAll(contents) // data is adding to csv
writer.close()
}
fun saveTextToDisk(filepath: String, contents: String){
val writer = FileWriter(File(filepath))
writer.append(contents)
writer.flush()
writer.close()
}
}

View File

@@ -1,21 +0,0 @@
package com.example.hpostesting.data.model
class AadharCard {
var name = ""
var dateOfBirth = ""
var gender = ""
var careOf = ""
var district = ""
var landmark = ""
var house = ""
var location = ""
var pinCode = ""
var postOffice = ""
var state = ""
var street = ""
var subDistrict = ""
var vtc = ""
var mobile = ""
}

View File

@@ -1,8 +0,0 @@
package com.example.hpostesting.data.model
data class Location(
var latitude: Double?,
var longitude: Double?
) {
constructor() : this(null, null)
}

View File

@@ -1,15 +0,0 @@
package com.example.hpostesting.data.model
import java.util.Calendar
import java.util.Date
data class PendingUploads(
// Filename
val pendingId: String,
val mobileId: String,
val patientId: String,
val filePath: String,
val timeAdded: Date
) {
constructor(): this("", "", "", "", Calendar.getInstance().time)
}

View File

@@ -1,7 +0,0 @@
package com.example.hpostesting.data.model
sealed class Response<out R> {
data class Success<out T>(val data: T) : Response<T>()
data class Error(val exception: Exception) : Response<Nothing>()
// object Loading : Response<Nothing>()
}

View File

@@ -1,6 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class Credentials(
val password: String? = "",
val username: String? = ""
)

View File

@@ -1,17 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class Device(
val assigned: Boolean? = false,
val createdAt: String? = "",
val createdBy: Int? = 0,
val deviceType: DeviceType? = DeviceType(),
val deviceTypeId: Int? = 0,
val deviceUser: DeviceUser? = DeviceUser(),
val enabled: Boolean? = false,
val id: Int? = 0,
val name: String? = "",
val serialNumber: String? = "",
val uid: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0
)

View File

@@ -1,6 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class DeviceProvisionData(
val credentials: Credentials? = Credentials(),
val device: Device? = Device()
)

View File

@@ -1,9 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class DeviceProvisionRequest(
val deviceTypeName: String? = "",
val email: String? = "",
val password: String? = "",
val serialNumber: String? = "",
val uid: String? = ""
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
import com.google.gson.annotations.SerializedName
data class DeviceProvisionResponse(
@SerializedName("Data")
val data: DeviceProvisionData? = DeviceProvisionData(),
@SerializedName("Message")
val message: String? = "",
@SerializedName("Result")
val result: String? = ""
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class DeviceType(
val createdAt: String? = "",
val createdBy: Int? = 0,
val description: String? = "",
val enabled: Boolean? = false,
val id: Int? = 0,
val name: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0
)

View File

@@ -1,15 +0,0 @@
package com.example.hpostesting.data.model.deviceprovision
data class DeviceUser(
val createdAt: String? = "",
val createdBy: Int? = 0,
val deviceId: Int? = 0,
val enabled: Boolean? = false,
val id: Int? = 0,
val lastLogin: Any? = Any(),
val natsToken: String? = "",
val natsTokenExpiry: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0,
val username: String? = ""
)

View File

@@ -1,9 +0,0 @@
package com.example.hpostesting.data.model.diagnostics
data class DiagnosticsData (
var deviceId: String = "",
var appVersion: String? = "",
var deviceType: String = "HEMOCUBE",
var deviceData: String = "",
var runTime: String = ""
)

View File

@@ -1,5 +0,0 @@
package com.example.hpostesting.data.model.log
data class UploadLogsData(
val filename: String? = ""
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.log
import com.google.gson.annotations.SerializedName
data class UploadLogsResponse(
@SerializedName("Data")
val data: UploadLogsData? = UploadLogsData(),
@SerializedName("Message")
val message: String? = "",
@SerializedName("Result")
val result: String? = ""
)

View File

@@ -1,16 +0,0 @@
package com.example.hpostesting.data.model.login
data class Device(
val assigned: Boolean? = false,
val createdAt: String? = "",
val createdBy: Int? = 0,
val deviceType: DeviceType? = DeviceType(),
val deviceTypeId: Int? = 0,
val enabled: Boolean? = false,
val id: Int? = 0,
val name: String? = "",
val serialNumber: String? = "",
val uid: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.login
data class DeviceType(
val createdAt: String? = "",
val createdBy: Int? = 0,
val description: String? = "",
val enabled: Boolean? = false,
val id: Int? = 0,
val name: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0
)

View File

@@ -1,16 +0,0 @@
package com.example.hpostesting.data.model.login
data class DeviceUser(
val createdAt: String? = "",
val createdBy: Int? = 0,
val device: Device? = Device(),
val deviceId: Int? = 0,
val enabled: Boolean? = false,
val id: Int? = 0,
val lastLogin: String? = "",
val natsToken: String? = "",
val natsTokenExpiry: String? = "",
val updatedAt: String? = "",
val updatedBy: Int? = 0,
val username: String? = ""
)

View File

@@ -1,6 +0,0 @@
package com.example.hpostesting.data.model.login
data class LoginData(
val accessToken: String? = "",
val deviceUser: DeviceUser? = DeviceUser()
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.login
data class LoginRequest(
val lab: String? = "",
val latitude: String? = "",
val location: String? = "",
val longitude: String? = "",
val mode: String? = "",
val password: String? = "",
val serialNumber: String? = "",
val username: String? = ""
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.login
import com.google.gson.annotations.SerializedName
data class LoginResponse(
@SerializedName("Data")
val data: LoginData? = LoginData(),
@SerializedName("Message")
val message: String? = "",
@SerializedName("Result")
val result: String? = ""
)

View File

@@ -1,38 +0,0 @@
package com.example.hpostesting.data.model.molbioresult
import com.example.hpostesting.data.model.patient.HemoCubeTestData
data class MolbioV2Result(
val age: Int? = 0,
val analysisDate: String? = "",
val analysisId: String? = "",
val analysisStatus: String? = "",
val analysisType: String? = "",
val analysisTypeMethod: String? = "",
val bloodGroup: String? = "",
val coefficients: List<Int>? = listOf(),
val collectionLocation: List<Any>? = listOf(),
val collectionTime: String? = "",
val collector: String? = "",
val curveFitting: String? = "",
val deviceName: String? = "",
val expiryTime: String? = "",
val gender: String? = "",
val interpretation: String? = "",
val `operator`: String? = "",
val patientId: Int? = 0,
val pregnancy: Boolean? = false,
val rawData: HemoCubeTestData? = HemoCubeTestData(),
val recommendation: String? = "",
val sampleId: String? = "",
val sampleType: String? = "",
val sickleCellHistory: Boolean? = false,
val testId: String? = "",
val testResult: String? = "",
val testStatus: String? = "",
val testTime: String? = "",
val testType: String? = "",
val thresholds: String? = "",
val underMedication: Boolean? = false,
val volume: Int? = 0
)

View File

@@ -1,42 +0,0 @@
package com.example.hpostesting.data.model.molbioresult
import com.example.hpostesting.data.model.patient.HemoCubeTestData
data class MolbioV2ResultData(
val age: Int? = 0,
val analysisDate: String? = "",
val analysisStatus: String? = "",
val analysisType: String? = "",
val analysisTypeMethod: String? = "",
val bloodGroup: String? = "",
val coefficients: List<Int>? = listOf(),
val collectionLocation: List<Any>? = listOf(),
val collectionTime: String? = "",
val collector: String? = "",
val createdAt: String? = "",
val createdBy: Int? = 0,
val curveFitting: String? = "",
val deviceId: Int? = 0,
val expiryTime: String? = "",
val gender: String? = "",
val id: Int? = 0,
val interpretation: String? = "",
val `operator`: String? = "",
val patientId: Int? = 0,
val pregnancy: Boolean? = false,
val rawData: HemoCubeTestData? = HemoCubeTestData(),
val recommendation: String? = "",
val sampleId: String? = "",
val sampleType: String? = "",
val sickleCellHistory: Boolean? = false,
val testId: String? = "",
val testResult: String? = "",
val testStatus: String? = "",
val testTime: String? = "",
val testType: String? = "",
val thresholds: String? = "",
val underMedication: Boolean? = false,
val updatedAt: String? = "",
val updatedBy: Int? = 0,
val volume: Int? = 0
)

View File

@@ -1,5 +0,0 @@
package com.example.hpostesting.data.model.molbioresult
data class MolbioV2ResultRequest(
val results: List<MolbioV2Result>? = listOf()
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.molbioresult
import com.google.gson.annotations.SerializedName
data class MolbioV2ResultResponse(
@SerializedName("Data")
val data: List<MolbioV2ResultData>? = listOf(),
@SerializedName("Message")
val message: String? = "",
@SerializedName("Result")
val result: String? = ""
)

View File

@@ -1,55 +0,0 @@
package com.example.hpostesting.data.model.molbioresult
import com.example.hpostesting.data.model.patient.UserData
data class RawData(
var _id: String = "",
var name: String = "",
var incubationTime: String = "",
var bloodGroup: String = "",
var birthYear: String = "",
var state: String = "",
var abhaId: String = "",
var userImageURL: String = "",
var location: UserData.Location? = null,
var reportUploadTime: String? = "",
var testType: String? = "HEMOCUBE",
var testTime: String? = "",
var testStatus: Boolean? = false,
var gender: String = "",
var localFlag: Boolean = false,
var deviceId: String? = "",
var appVersion:String? = "",
var deviceSerialNumber: String = "",
var deviceType: String = "HEMOCUBE",
var kitSerial: String = "",
var resultData: String = "",
var led1Buffer: Double? = null,
var led2Buffer: Double? = null,
var led3Buffer: Double? = null,
var led4Buffer: Double? = null,
var led1Sample: Double? = null,
var led2Sample: Double? = null,
var led3Sample: Double? = null,
var led4Sample: Double? = null,
var led1Average: Double? = null,
var led2Average: Double? = null,
var led3Average: Double? = null,
var led4Average: Double? = null,
var abs1: Double? = null,
var abs2: Double? = null,
var abs3: Double? = null,
var abs4: Double? = null,
var deviceRatio: Double? = null,
var calculatedRatio: Double? = null,
var predictedDenovixRatio: Double? = null,
var coefficients: String? = "",
var classificationResult: String = "",
var prdClassification: String = "",
var errorMessages: String = "",
var batteryLevel: String = "",
var batteryCapacity: String = "",
var batteryMaxCapacity: String = "",
var batteryTemperature: String = "",
var batteryVoltage: String = "",
)

View File

@@ -1,21 +0,0 @@
package com.example.hpostesting.data.model.patient
data class BufferCheckData(
var kitno: String = "",
var deviceId: String? = "",
var appVersion:String? = "",
var deviceSerialNumber: String = "",
var deviceType: String = "HEMOCUBE",
var resultData: String = "",
var led1Buffer: Double? = null,
var led2Buffer: Double? = null,
var led1Sample: Double? = null,
var led2Sample: Double? = null,
var led1Average: Double? = null,
var led2Average: Double? = null,
var deviceRatio: Double? = null,
var calculatedRatio: Double? = null,
var coefficients: String? = "",
var classificationResult: String = "",
var testTime: String = ""
)

View File

@@ -1,19 +0,0 @@
package com.example.hpostesting.data.model.patient
import androidx.room.Entity
import androidx.room.PrimaryKey
import com.google.firebase.firestore.PropertyName
@Entity(tableName = "device_table")
data class DeviceData(
@PrimaryKey
var _id: String = "",
@get:PropertyName("deviceId") @set:PropertyName("deviceId")
var deviceId: String = "",
@get:PropertyName("deviceType") @set:PropertyName("deviceType")
var deviceType: String = "",
@get:PropertyName("coefficients") @set:PropertyName("coefficients")
var coefficients: List<Double> = emptyList(),
@get:PropertyName("calibratedAt") @set:PropertyName("calibratedAt")
var calibratedAt: String = ""
)

View File

@@ -1,59 +0,0 @@
package com.example.hpostesting.data.model.patient
import androidx.room.Entity
import androidx.room.PrimaryKey
@Entity(tableName = "hemo_cube_test_table")
data class HemoCubeTestData(
@PrimaryKey
var _id: String = "",
var name: String = "",
var incubationTime: String = "",
var bloodGroup: String = "",
var birthYear: String = "",
var state: String = "",
var abhaId: String = "",
var userImageURL: String = "",
var location: UserData.Location? = null,
var reportUploadTime: String? = "",
var testType: String? = "HEMOCUBE",
var testTime: String? = "",
var testStatus: Boolean? = false,
var gender: String = "",
var localFlag: Boolean = false,
var deviceId: String? = "",
var appVersion:String? = "",
var deviceSerialNumber: String = "",
var deviceType: String = "HEMOCUBE",
var kitSerial: String = "",
var resultData: String = "",
var led1Buffer: Double? = null,
var led2Buffer: Double? = null,
var led3Buffer: Double? = null,
var led4Buffer: Double? = null,
var led1Sample: Double? = null,
var led2Sample: Double? = null,
var led3Sample: Double? = null,
var led4Sample: Double? = null,
var led1Average: Double? = null,
var led2Average: Double? = null,
var led3Average: Double? = null,
var led4Average: Double? = null,
var abs1: Double? = null,
var abs2: Double? = null,
var abs3: Double? = null,
var abs4: Double? = null,
var deviceRatio: Double? = null,
var calculatedRatio: Double? = null,
var predictedDenovixRatio: Double? = null,
var coefficients: String? = "",
var classificationResult: String = "",
var prdClassification: String = "",
var errorMessages: String = "",
var batteryLevel: String = "",
var batteryCapacity: String = "",
var batteryMaxCapacity: String = "",
var batteryTemperature: String = "",
var batteryVoltage: String = "",
var molbioFlag: Boolean = false
)

View File

@@ -1,70 +0,0 @@
package com.example.hpostesting.data.model.patient
import java.util.Date
data class PatientDetails(
var id: String,
var isIdABHA: Boolean,
var name: String?,
var yob: Int?,
var gender: Gender?,
var mobile: String?,
var isUnderMedication: Boolean?,
var isUnderTransfusion: Boolean?,
val photoUrl: String?,
var careOf: String?,
var isMarried: Boolean?,
var bloodGroup: String?,
var address: Address?,
var category: Category?,
var registerDate: Date?,
var uploadDate: Date?
) {
constructor() : this(
"",
false,
null,
null,
null,
null,
null,
null,
null,
null,
null,
null,
null,
null,
null,
null
)
enum class Gender {
MALE,
FEMALE,
OTHER
}
data class Address(
var house: String?,
val street: String?,
var city: String?,
val landMark: String?,
var postOffice: String?,
var district: String?,
val subDistrict: String?,
var state: String?,
val vtc: String?,
var pinCode: Int?,
) {
constructor() : this(null, null, null, null, null, null, null, null, null, null)
}
enum class Category {
GENERAL,
OBC,
SC,
ST,
}
}

View File

@@ -1,59 +0,0 @@
package com.example.hpostesting.data.model.patient
import androidx.room.Entity
import androidx.room.PrimaryKey
import com.example.hpostesting.data.model.test.TestRightResultType
@Entity(tableName = "user_table")
data class UserData(
@PrimaryKey
var _id: String = "",
var name: String = "",
var incubationTime: String = "",
var birthYear: String = "",
var abhaId: String = "",
var bloodGroup: String = "",
var userImageURL: String = "",
var gender: String ="",
var location: Location? = null,
var createdBy: String? = "",
var reportUploadTime: String? = "",
var testTime: String? = "",
var testStatus: Boolean? = false,
var mobileId: String = "",
var deviceId: String = "",
var state: String = "",
var deviceSerialNumber: String = "",
var kitSerial: String = "",
var csvPath: String = "",
var reportPath: String = "",
var result: TestRightResultType? = null,
var resultRatio: Double? = null,
var prdClassification: String = ""
) {
enum class Gender {
MALE,
FEMALE,
OTHER
}
data class Location(
var latitude: Double? = null,
var longitude: Double? = null
)
}
fun UserData.toHemoCubeTestData() = HemoCubeTestData(
_id = _id,
name = name,
birthYear = birthYear,
userImageURL = userImageURL,
testStatus = testStatus,
location = location,
gender = gender,
state = state,
abhaId = abhaId,
bloodGroup = bloodGroup,
prdClassification = prdClassification,
testTime = testTime
)

View File

@@ -1,5 +0,0 @@
package com.example.hpostesting.data.model.updates
data class CheckUpdateData(
val version: String? = ""
)

View File

@@ -1,5 +0,0 @@
package com.example.hpostesting.data.model.updates
data class CheckUpdateRequest(
val currentVersion: String? = ""
)

View File

@@ -1,12 +0,0 @@
package com.example.hpostesting.data.model.updates
import com.google.gson.annotations.SerializedName
data class CheckUpdateResponse(
@SerializedName("Data")
val data: CheckUpdateData? = CheckUpdateData(),
@SerializedName("Message")
val message: String? = "",
@SerializedName("Result")
val result: String? = ""
)

View File

@@ -1,5 +0,0 @@
package com.example.hpostesting.data.model.updates
data class DeviceUpdateRequest(
val serial_no: String? = ""
)

View File

@@ -1,205 +0,0 @@
package com.example.hpostesting.data.repository
import android.net.Uri
import com.example.hpostesting.data.Result
import com.example.hpostesting.data.api.MolbioAuthApi
import com.example.hpostesting.data.api.MolbioResultApi
import com.example.hpostesting.data.model.PendingUploads
import com.example.hpostesting.data.model.Response
import com.example.hpostesting.data.model.deviceprovision.DeviceProvisionRequest
import com.example.hpostesting.data.model.deviceprovision.DeviceProvisionResponse
import com.example.hpostesting.data.model.diagnostics.DiagnosticsData
import com.example.hpostesting.data.model.log.UploadLogsResponse
import com.example.hpostesting.data.model.login.LoginRequest
import com.example.hpostesting.data.model.login.LoginResponse
import com.example.hpostesting.data.model.molbioresult.MolbioV2ResultRequest
import com.example.hpostesting.data.model.molbioresult.MolbioV2ResultResponse
import com.example.hpostesting.data.model.patient.BufferCheckData
import com.example.hpostesting.data.model.patient.DeviceData
import com.example.hpostesting.data.model.patient.HemoCubeTestData
import com.example.hpostesting.data.model.patient.UserData
import com.example.hpostesting.data.model.updates.CheckUpdateRequest
import com.example.hpostesting.data.model.updates.CheckUpdateResponse
import com.example.hpostesting.data.model.updates.DeviceUpdateRequest
import com.google.firebase.crashlytics.ktx.crashlytics
import com.google.firebase.firestore.FirebaseFirestore
import com.google.firebase.firestore.ktx.firestore
import com.google.firebase.ktx.Firebase
import com.google.firebase.storage.ktx.storage
import kotlinx.coroutines.tasks.await
import okhttp3.MultipartBody
import okhttp3.ResponseBody
import java.io.File
import java.net.ConnectException
import java.net.SocketTimeoutException
import javax.inject.Inject
import javax.inject.Named
class NetworkException(message: String, cause: Throwable) : Exception(message, cause)
class DatabaseRepository @Inject constructor(
@Named("Auth")private val molbioAuthApi: MolbioAuthApi,
private val molbioResultApi: MolbioResultApi
) : Repository {
private val db: FirebaseFirestore = Firebase.firestore
private val storage = Firebase.storage
private suspend fun <T : Any> safeApiCall(apiCall: suspend () -> T): Result<T> {
return try {
val response = apiCall.invoke()
Result.Success(response)
} catch (e: SocketTimeoutException) {
Result.Error(NetworkException("Network timeout", e))
} catch (e: ConnectException) {
Result.Error(NetworkException("Network connection failed", e))
} catch (e: Exception) {
Result.Error(e)
}
}
suspend fun deviceProvision(deviceProvisionRequest: DeviceProvisionRequest): Result<DeviceProvisionResponse> {
return safeApiCall { molbioAuthApi.deviceProvision(deviceProvisionRequest) }
}
suspend fun login(loginRequest: LoginRequest): Result<LoginResponse> {
return safeApiCall { molbioAuthApi.login(loginRequest) }
}
suspend fun uploadResults(molbioV2ResultRequest: MolbioV2ResultRequest): Result<MolbioV2ResultResponse> {
return safeApiCall { molbioResultApi.uploadResults(molbioV2ResultRequest) }
}
suspend fun checkUpdate(checkUpdateRequest: CheckUpdateRequest): Result<CheckUpdateResponse> {
return safeApiCall { molbioResultApi.checkUpdate(checkUpdateRequest) }
}
suspend fun deviceUpdate(deviceUpdateRequest: DeviceUpdateRequest): Result<ResponseBody> {
return safeApiCall { molbioResultApi.deviceUpdate(deviceUpdateRequest) }
}
suspend fun uploadLogs(logFile: MultipartBody.Part): Result<UploadLogsResponse> {
return safeApiCall { molbioResultApi.uploadLogs(logFile) }
}
override suspend fun addTestToDatabase(data: HemoCubeTestData?): Response<String> {
return try {
val userdata =
db.collection("patientData").whereEqualTo("_id", data!!._id).get().await()
if (userdata.documents.isNotEmpty()) {
userdata.documents.forEach {
db.collection("patientData").document(it.id).update("testStatus", true)
}
}
db.collection("testData").add(data).await()
Response.Success(data._id)
} catch (e: Exception) {
Response.Error(e)
}
}
override suspend fun addTestToDatabase(data: UserData?): Response<String> {
return try {
val userdata =
db.collection("patientData").whereEqualTo("_id", data!!._id).get().await()
if (userdata.documents.isNotEmpty()) {
userdata.documents.forEach {
db.collection("patientData").document(it.id).update("testStatus", true)
}
}
db.collection("testData").add(data).await()
Response.Success(data._id)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
Response.Error(e)
}
}
override suspend fun addTestToDatabaseforBufferCheck(data: BufferCheckData?): Response<String> {
return try {
db.collection("buffers").add(data!!).await()
Response.Success(data.kitno)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
Response.Error(e)
}
}
override suspend fun addDiagnostics(data: DiagnosticsData?): Response<String> {
return try {
db.collection("diagnostics").add(data!!).await()
Response.Success(data.deviceId)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
Response.Error(e)
}
}
override suspend fun uploadFileToStorage(
patientID: String, filePath: String
): Response<Boolean> {
try {
val file = Uri.fromFile(File(filePath))
val riversRef = storage.reference.child("$patientID/${file.lastPathSegment}")
riversRef.putFile(file).await()
return Response.Success(true)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
return Response.Error(e)
}
}
suspend fun addToPendingQueue(pendingUploads: PendingUploads): Response<Boolean> {
return try {
db.collection("pendingUploads").document(pendingUploads.pendingId).set(pendingUploads)
.await()
Response.Success(true)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
Response.Error(e)
}
}
suspend fun getAllFromPendingQueue(): List<PendingUploads> {
val pendingList = mutableListOf<PendingUploads>()
return try {
val querySnapshot = db.collection("pendingUploads").orderBy("timeAdded").get().await()
for (doc in querySnapshot.documents) {
val pendingFile = doc.toObject(PendingUploads::class.java)
pendingFile?.let {
pendingList.add(it)
}
}
pendingList
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
pendingList
}
}
suspend fun removeFromPendingQueue(fileName: String): Response<Boolean> {
return try {
db.collection("pendingUploads").document(fileName).delete().await()
Response.Success(true)
} catch (e: Exception) {
Firebase.crashlytics.recordException(e)
Response.Error(e)
}
}
suspend fun getDeviceData(): List<DeviceData> {
return db.collection("devices").get().await().toObjects(DeviceData::class.java)
}
override suspend fun getDeviceDataById(deviceId: String): DeviceData? {
val querySnapshot = db.collection("devices").get().await()
val allDeviceDataList = querySnapshot.toObjects(DeviceData::class.java)
// Find the DeviceData object with the specified deviceId
return allDeviceDataList.find { it.deviceId == deviceId }
}
}

Some files were not shown because too many files have changed in this diff Show More