mirror of
https://github.com/aljazceru/Android-nRF-Toolbox.git
synced 2025-12-18 06:54:24 +01:00
Migration to AGP and Commons Library (#142)
* Update dependencies * Migrated logger feature * Updated to be compatible with common library version 2.0.0 * Migration to Kotlin BLE 1.1.0 * Changed to Enum entries * Removed unnecessary ExperimentalMaterial3Api annotation * Migrated from SmallTopAppBar to TopAppBar * Changed to data object * Made nullable logger * Changed to nullable * Changed import
This commit is contained in:
@@ -66,7 +66,7 @@ dependencies {
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.blek.uiscanner)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
implementation(libs.nordic.permissions.ble)
|
||||
implementation(libs.nordic.analytics)
|
||||
|
||||
@@ -79,4 +79,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.runtime.compose)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -37,6 +37,7 @@ import no.nordicsemi.android.analytics.AppAnalytics
|
||||
import no.nordicsemi.android.analytics.AppOpenEvent
|
||||
import no.nordicsemi.android.gls.GLSServer
|
||||
import no.nordicsemi.android.uart.UartServer
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
|
||||
@HiltAndroidApp
|
||||
@@ -58,5 +59,7 @@ class NrfToolboxApplication : Application() {
|
||||
|
||||
uartServer.start(this)
|
||||
glsServer.start(this)
|
||||
|
||||
Timber.plant(Timber.DebugTree())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,21 +0,0 @@
|
||||
package no.nordicsemi.android.nrftoolbox
|
||||
|
||||
import android.content.Context
|
||||
import dagger.Module
|
||||
import dagger.Provides
|
||||
import dagger.hilt.InstallIn
|
||||
import dagger.hilt.android.qualifiers.ApplicationContext
|
||||
import dagger.hilt.components.SingletonComponent
|
||||
import no.nordicsemi.android.common.logger.BleLogger
|
||||
import no.nordicsemi.android.common.logger.DefaultConsoleLogger
|
||||
|
||||
@Suppress("unused")
|
||||
@Module
|
||||
@InstallIn(SingletonComponent::class)
|
||||
internal class AppModule {
|
||||
|
||||
@Provides
|
||||
fun provideNordicLogger(
|
||||
@ApplicationContext context: Context
|
||||
): BleLogger = DefaultConsoleLogger(context)
|
||||
}
|
||||
@@ -61,7 +61,6 @@ import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.unit.dp
|
||||
import no.nordicsemi.android.nrftoolbox.R
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun FeatureButton(
|
||||
@DrawableRes iconId: Int,
|
||||
|
||||
@@ -34,7 +34,6 @@ package no.nordicsemi.android.nrftoolbox.view
|
||||
import androidx.compose.foundation.layout.*
|
||||
import androidx.compose.foundation.rememberScrollState
|
||||
import androidx.compose.foundation.verticalScroll
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Scaffold
|
||||
import androidx.compose.material3.Text
|
||||
@@ -69,7 +68,6 @@ private const val DFU_LINK = "https://play.google.com/store/apps/details?id=no.n
|
||||
|
||||
private const val LOGGER_PACKAGE_NAME = "no.nordicsemi.android.log"
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun HomeScreen() {
|
||||
val viewModel: HomeViewModel = hiltViewModel()
|
||||
|
||||
@@ -33,8 +33,8 @@ package no.nordicsemi.android.nrftoolbox.view
|
||||
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.SmallTopAppBar
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.material3.TopAppBar
|
||||
import androidx.compose.material3.TopAppBarDefaults
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.res.colorResource
|
||||
@@ -44,9 +44,9 @@ import no.nordicsemi.android.nrftoolbox.R
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun TitleAppBar(text: String) {
|
||||
SmallTopAppBar(
|
||||
TopAppBar(
|
||||
title = { Text(text, maxLines = 2) },
|
||||
colors = TopAppBarDefaults.smallTopAppBarColors(
|
||||
colors = TopAppBarDefaults.topAppBarColors(
|
||||
scrolledContainerColor = MaterialTheme.colorScheme.primary,
|
||||
containerColor = colorResource(id = R.color.appBarColor),
|
||||
titleContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
|
||||
@@ -114,7 +114,7 @@ class HomeViewModel @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
LoggerLauncher.launch(context)
|
||||
LoggerLauncher.launch(context, null)
|
||||
}
|
||||
|
||||
fun logEvent(event: ProfileOpenEvent) {
|
||||
|
||||
@@ -47,5 +47,7 @@ class NrfToolboxApplication : Application() {
|
||||
super.onCreate()
|
||||
|
||||
analytics.logEvent(AppOpenEvent)
|
||||
|
||||
Timber.plant(Timber.DebugTree())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -32,20 +32,25 @@
|
||||
// Top-level build file where you can add configuration options common to all sub-projects/modules.
|
||||
plugins {
|
||||
alias(libs.plugins.android.application) apply false
|
||||
alias(libs.plugins.android.library) apply false
|
||||
alias(libs.plugins.compose.compiler) apply false
|
||||
alias(libs.plugins.kotlin.android) apply false
|
||||
alias(libs.plugins.kotlin.parcelize) apply false
|
||||
alias(libs.plugins.kotlin.serialization) apply false
|
||||
alias(libs.plugins.kotlin.jvm) apply false
|
||||
alias(libs.plugins.kotlin.kapt) apply false
|
||||
alias(libs.plugins.ksp) apply false
|
||||
alias(libs.plugins.kotlin.serialization) apply false
|
||||
alias(libs.plugins.kotlin.parcelize) apply false
|
||||
alias(libs.plugins.hilt) apply false
|
||||
alias(libs.plugins.secrets) apply false
|
||||
alias(libs.plugins.protobuf) apply false
|
||||
alias(libs.plugins.ksp) apply false
|
||||
alias(libs.plugins.google.services) apply false
|
||||
alias(libs.plugins.firebase.crashlytics) apply false
|
||||
|
||||
// Nordic plugins are defined in https://github.com/NordicSemiconductor/Android-Gradle-Plugins
|
||||
alias(libs.plugins.nordic.application) apply false
|
||||
alias(libs.plugins.nordic.application.compose) apply false
|
||||
alias(libs.plugins.nordic.library) apply false
|
||||
alias(libs.plugins.nordic.library.compose) apply false
|
||||
alias(libs.plugins.nordic.hilt) apply false
|
||||
alias(libs.plugins.nordic.feature) apply false
|
||||
alias(libs.plugins.google.services) apply false
|
||||
alias(libs.plugins.firebase.crashlytics) apply false
|
||||
}
|
||||
|
||||
@@ -50,3 +50,5 @@ android.useAndroidX=true
|
||||
kotlin.code.style=official
|
||||
|
||||
android.nonTransitiveRClass=false
|
||||
# https://github.com/google/ksp/issues/1942#issuecomment-2157733096
|
||||
ksp.useKSP2=true
|
||||
|
||||
2
gradle/wrapper/gradle-wrapper.properties
vendored
2
gradle/wrapper/gradle-wrapper.properties
vendored
@@ -31,7 +31,7 @@
|
||||
|
||||
#Mon Feb 14 14:46:55 CET 2022
|
||||
distributionBase=GRADLE_USER_HOME
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-8.8-bin.zip
|
||||
distributionPath=wrapper/dists
|
||||
zipStorePath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
|
||||
@@ -35,7 +35,7 @@ import android.os.Bundle
|
||||
|
||||
sealed class FirebaseEvent(val eventName: String, val params: Bundle?)
|
||||
|
||||
object AppOpenEvent : FirebaseEvent("APP_OPEN", null)
|
||||
data object AppOpenEvent : FirebaseEvent("APP_OPEN", null)
|
||||
|
||||
class ProfileOpenEvent : FirebaseEvent {
|
||||
|
||||
|
||||
@@ -42,7 +42,6 @@ android {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
@@ -52,4 +51,8 @@ dependencies {
|
||||
implementation(libs.androidx.compose.material.iconsExtended)
|
||||
implementation(libs.androidx.core.ktx)
|
||||
implementation(libs.androidx.activity.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -1,9 +0,0 @@
|
||||
package no.nordicsemi.android.ui.view
|
||||
|
||||
import android.content.Context
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
|
||||
interface NordicLoggerFactory {
|
||||
|
||||
fun createNordicLogger(context: Context, profile: String?, key: String, name: String?): BleLoggerAndLauncher
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
package no.nordicsemi.android.ui.view
|
||||
|
||||
import android.content.Context
|
||||
import dagger.Module
|
||||
import dagger.Provides
|
||||
import dagger.hilt.InstallIn
|
||||
import dagger.hilt.components.SingletonComponent
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
|
||||
@Module
|
||||
@InstallIn(SingletonComponent::class)
|
||||
class NordicLoggerFactoryHiltModule {
|
||||
|
||||
@Provides
|
||||
fun createLogger(): NordicLoggerFactory {
|
||||
return object : NordicLoggerFactory {
|
||||
override fun createNordicLogger(
|
||||
context: Context,
|
||||
profile: String?,
|
||||
key: String,
|
||||
name: String?,
|
||||
): BleLoggerAndLauncher {
|
||||
return DefaultBleLogger.create(context, profile, key, name)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -36,11 +36,18 @@ import androidx.compose.foundation.layout.size
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.filled.ArrowBack
|
||||
import androidx.compose.material.icons.filled.Close
|
||||
import androidx.compose.material3.*
|
||||
import androidx.compose.material3.ButtonDefaults
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.IconButton
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.material3.TextButton
|
||||
import androidx.compose.material3.TopAppBar
|
||||
import androidx.compose.material3.TopAppBarDefaults
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.res.colorResource
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.unit.dp
|
||||
@@ -51,11 +58,11 @@ import no.nordicsemi.android.ui.R
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun CloseIconAppBar(text: String, onClick: () -> Unit) {
|
||||
SmallTopAppBar(
|
||||
TopAppBar(
|
||||
title = { Text(text, maxLines = 2) },
|
||||
colors = TopAppBarDefaults.smallTopAppBarColors(
|
||||
colors = TopAppBarDefaults.topAppBarColors(
|
||||
scrolledContainerColor = MaterialTheme.colorScheme.primary,
|
||||
containerColor = colorResource(id = R.color.appBarColor),
|
||||
containerColor = MaterialTheme.colorScheme.primaryContainer,
|
||||
titleContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
actionIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
navigationIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
@@ -74,11 +81,11 @@ fun CloseIconAppBar(text: String, onClick: () -> Unit) {
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun LoggerBackIconAppBar(text: String, onClick: () -> Unit) {
|
||||
SmallTopAppBar(
|
||||
TopAppBar(
|
||||
title = { Text(text, maxLines = 2) },
|
||||
colors = TopAppBarDefaults.smallTopAppBarColors(
|
||||
colors = TopAppBarDefaults.topAppBarColors(
|
||||
scrolledContainerColor = MaterialTheme.colorScheme.primary,
|
||||
containerColor = colorResource(id = R.color.appBarColor),
|
||||
containerColor = MaterialTheme.colorScheme.primaryContainer,
|
||||
titleContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
actionIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
navigationIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
@@ -108,11 +115,11 @@ fun LoggerBackIconAppBar(text: String, onClick: () -> Unit) {
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun BackIconAppBar(text: String, onClick: () -> Unit) {
|
||||
SmallTopAppBar(
|
||||
TopAppBar(
|
||||
title = { Text(text, maxLines = 2) },
|
||||
colors = TopAppBarDefaults.smallTopAppBarColors(
|
||||
colors = TopAppBarDefaults.topAppBarColors(
|
||||
scrolledContainerColor = MaterialTheme.colorScheme.primary,
|
||||
containerColor = colorResource(id = R.color.appBarColor),
|
||||
containerColor = MaterialTheme.colorScheme.primaryContainer,
|
||||
titleContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
actionIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
navigationIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
@@ -131,12 +138,17 @@ fun BackIconAppBar(text: String, onClick: () -> Unit) {
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun LoggerIconAppBar(text: String, onClick: () -> Unit, onDisconnectClick: () -> Unit, onLoggerClick: () -> Unit) {
|
||||
SmallTopAppBar(
|
||||
fun LoggerIconAppBar(
|
||||
text: String,
|
||||
onClick: () -> Unit,
|
||||
onDisconnectClick: () -> Unit,
|
||||
onLoggerClick: () -> Unit
|
||||
) {
|
||||
TopAppBar(
|
||||
title = { Text(text, maxLines = 2) },
|
||||
colors = TopAppBarDefaults.smallTopAppBarColors(
|
||||
colors = TopAppBarDefaults.topAppBarColors(
|
||||
scrolledContainerColor = MaterialTheme.colorScheme.primary,
|
||||
containerColor = colorResource(id = R.color.appBarColor),
|
||||
containerColor = MaterialTheme.colorScheme.primaryContainer,
|
||||
titleContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
actionIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
navigationIconContentColor = MaterialTheme.colorScheme.onPrimary,
|
||||
|
||||
@@ -51,7 +51,7 @@ dependencies {
|
||||
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.androidx.compose.material3)
|
||||
implementation(libs.androidx.compose.material.iconsExtended)
|
||||
@@ -60,4 +60,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -53,8 +53,7 @@ import no.nordicsemi.android.bps.view.BPSViewEvent
|
||||
import no.nordicsemi.android.bps.view.BPSViewState
|
||||
import no.nordicsemi.android.bps.view.DisconnectEvent
|
||||
import no.nordicsemi.android.bps.view.OpenLoggerEvent
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.common.navigation.NavigationResult
|
||||
import no.nordicsemi.android.common.navigation.Navigator
|
||||
import no.nordicsemi.android.kotlin.ble.client.main.callback.ClientBleGatt
|
||||
@@ -67,8 +66,11 @@ import no.nordicsemi.android.kotlin.ble.profile.bps.BloodPressureMeasurementPars
|
||||
import no.nordicsemi.android.kotlin.ble.profile.bps.IntermediateCuffPressureParser
|
||||
import no.nordicsemi.android.kotlin.ble.profile.bps.data.BloodPressureMeasurementData
|
||||
import no.nordicsemi.android.kotlin.ble.profile.bps.data.IntermediateCuffPressureData
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.toolbox.scanner.ScannerDestinationId
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import java.util.UUID
|
||||
import javax.inject.Inject
|
||||
|
||||
@@ -93,7 +95,7 @@ internal class BPSViewModel @Inject constructor(
|
||||
val state = _state.asStateFlow()
|
||||
|
||||
private var client: ClientBleGatt? = null
|
||||
private lateinit var logger: BleLoggerAndLauncher
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
init {
|
||||
navigationManager.navigateTo(ScannerDestinationId, ParcelUuid(BPS_SERVICE_UUID))
|
||||
@@ -113,7 +115,7 @@ internal class BPSViewModel @Inject constructor(
|
||||
fun onEvent(event: BPSViewEvent) {
|
||||
when (event) {
|
||||
DisconnectEvent -> onDisconnectEvent()
|
||||
OpenLoggerEvent -> logger.launch()
|
||||
OpenLoggerEvent -> LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -122,12 +124,18 @@ internal class BPSViewModel @Inject constructor(
|
||||
navigationManager.navigateUp()
|
||||
}
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "BPS", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = viewModelScope.launch {
|
||||
_state.value = _state.value.copy(deviceName = device.name)
|
||||
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "BPS", device.address)
|
||||
initLogger(device)
|
||||
|
||||
val client = ClientBleGatt.connect(context, device, viewModelScope, logger = logger)
|
||||
val client = ClientBleGatt.connect(context, device, viewModelScope)
|
||||
this@BPSViewModel.client = client
|
||||
|
||||
client.connectionStateWithStatus
|
||||
|
||||
@@ -47,7 +47,7 @@ dependencies {
|
||||
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
implementation(libs.nordic.navigation)
|
||||
|
||||
implementation(libs.nordic.blek.uiscanner)
|
||||
@@ -61,4 +61,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation(libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -41,15 +41,17 @@ import no.nordicsemi.android.cgms.data.CGMRecordWithSequenceNumber
|
||||
import no.nordicsemi.android.cgms.data.CGMServiceCommand
|
||||
import no.nordicsemi.android.cgms.data.CGMServiceData
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.gls.data.RequestStatus
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -60,7 +62,7 @@ class CGMRepository @Inject constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(CGMServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -92,8 +94,14 @@ class CGMRepository @Inject constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "CGM", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "CGM", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(CGMService::class.java, device)
|
||||
}
|
||||
@@ -124,7 +132,7 @@ class CGMRepository @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -132,7 +132,7 @@ internal class CGMService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@CGMService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@CGMService, device, lifecycleScope)
|
||||
this@CGMService.client = client
|
||||
|
||||
client.connectionStateWithStatus
|
||||
|
||||
@@ -46,8 +46,9 @@ dependencies {
|
||||
implementation(project(":lib_utils"))
|
||||
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.ui)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
implementation(libs.nordic.navigation)
|
||||
|
||||
implementation(libs.nordic.blek.client)
|
||||
@@ -61,4 +62,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -38,8 +38,7 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.csc.data.CSCServiceData
|
||||
import no.nordicsemi.android.csc.data.SpeedUnit
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
@@ -48,9 +47,12 @@ import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.csc.data.CSCData
|
||||
import no.nordicsemi.android.kotlin.ble.profile.csc.data.WheelSize
|
||||
import no.nordicsemi.android.kotlin.ble.profile.csc.data.WheelSizes
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -61,7 +63,7 @@ class CSCRepository @Inject constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _wheelSize = MutableStateFlow(WheelSizes.default)
|
||||
internal val wheelSize = _wheelSize.asStateFlow()
|
||||
@@ -91,8 +93,14 @@ class CSCRepository @Inject constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "CSC", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "CSC", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(CSCService::class.java, device)
|
||||
}
|
||||
@@ -123,7 +131,7 @@ class CSCRepository @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -86,7 +86,7 @@ internal class CSCService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@CSCService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@CSCService, device, lifecycleScope)
|
||||
this@CSCService.client = client
|
||||
|
||||
client.connectionStateWithStatus
|
||||
|
||||
@@ -47,7 +47,7 @@ import androidx.compose.ui.res.stringArrayResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.unit.dp
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.csc.R
|
||||
import no.nordicsemi.android.csc.data.CSCServiceData
|
||||
import no.nordicsemi.android.csc.data.SpeedUnit
|
||||
@@ -107,8 +107,10 @@ private fun SettingsSection(
|
||||
Column(
|
||||
horizontalAlignment = Alignment.CenterHorizontally
|
||||
) {
|
||||
SectionTitle(icon = Icons.Default.Settings,
|
||||
title = stringResource(R.string.csc_settings))
|
||||
SectionTitle(
|
||||
icon = Icons.Default.Settings,
|
||||
title = stringResource(R.string.csc_settings)
|
||||
)
|
||||
|
||||
Spacer(modifier = Modifier.height(16.dp))
|
||||
|
||||
|
||||
@@ -31,8 +31,8 @@
|
||||
|
||||
package no.nordicsemi.android.csc.view
|
||||
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.theme.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.ui.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.csc.data.SpeedUnit
|
||||
import no.nordicsemi.android.kotlin.ble.profile.csc.data.CSCData
|
||||
import java.util.Locale
|
||||
@@ -52,29 +52,29 @@ internal fun CSCData.speedWithSpeedUnit(speedUnit: SpeedUnit): Float {
|
||||
internal fun CSCData.displaySpeed(speedUnit: SpeedUnit): String {
|
||||
val speedWithUnit = speedWithSpeedUnit(speedUnit)
|
||||
return when (speedUnit) {
|
||||
SpeedUnit.M_S -> String.format("%.1f m/s", speedWithUnit)
|
||||
SpeedUnit.KM_H -> String.format("%.1f km/h", speedWithUnit)
|
||||
SpeedUnit.MPH -> String.format("%.1f mph", speedWithUnit)
|
||||
SpeedUnit.M_S -> String.format(Locale.US, "%.1f m/s", speedWithUnit)
|
||||
SpeedUnit.KM_H -> String.format(Locale.US, "%.1f km/h", speedWithUnit)
|
||||
SpeedUnit.MPH -> String.format(Locale.US, "%.1f mph", speedWithUnit)
|
||||
}
|
||||
}
|
||||
|
||||
internal fun CSCData.displayCadence(): String {
|
||||
return String.format("%.0f RPM", cadence)
|
||||
return String.format(Locale.US, "%.0f RPM", cadence)
|
||||
}
|
||||
|
||||
internal fun CSCData.displayDistance(speedUnit: SpeedUnit): String {
|
||||
return when (speedUnit) {
|
||||
SpeedUnit.M_S -> String.format("%.0f m", distance)
|
||||
SpeedUnit.KM_H -> String.format("%.0f m", distance)
|
||||
SpeedUnit.MPH -> String.format("%.0f yd", distance.toYards())
|
||||
SpeedUnit.M_S -> String.format(Locale.US, "%.0f m", distance)
|
||||
SpeedUnit.KM_H -> String.format(Locale.US, "%.0f m", distance)
|
||||
SpeedUnit.MPH -> String.format(Locale.US, "%.0f yd", distance.toYards())
|
||||
}
|
||||
}
|
||||
|
||||
internal fun CSCData.displayTotalDistance(speedUnit: SpeedUnit): String {
|
||||
return when (speedUnit) {
|
||||
SpeedUnit.M_S -> String.format("%.2f m", totalDistance)
|
||||
SpeedUnit.KM_H -> String.format("%.2f km", totalDistance.toKilometers())
|
||||
SpeedUnit.MPH -> String.format("%.2f mile", totalDistance.toMiles())
|
||||
SpeedUnit.M_S -> String.format(Locale.US, "%.2f m", totalDistance)
|
||||
SpeedUnit.KM_H -> String.format(Locale.US, "%.2f km", totalDistance.toKilometers())
|
||||
SpeedUnit.MPH -> String.format(Locale.US, "%.2f mile", totalDistance.toMiles())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -93,7 +93,7 @@ internal fun String.toSpeedUnit(): SpeedUnit {
|
||||
|
||||
internal fun SpeedUnit.temperatureSettingsItems(): RadioGroupViewEntity {
|
||||
return RadioGroupViewEntity(
|
||||
SpeedUnit.values().map { createRadioButtonItem(it, this) }
|
||||
SpeedUnit.entries.toTypedArray().map { createRadioButtonItem(it, this) }
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
@@ -45,9 +45,10 @@ dependencies {
|
||||
implementation(project(":lib_ui"))
|
||||
implementation(project(":lib_utils"))
|
||||
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.nordic.blek.client)
|
||||
implementation(libs.nordic.blek.profile)
|
||||
@@ -65,6 +66,10 @@ dependencies {
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
|
||||
testImplementation(libs.hilt.android.testing)
|
||||
kaptTest(libs.hilt.compiler)
|
||||
testImplementation(libs.androidx.test.rules)
|
||||
@@ -73,7 +78,7 @@ dependencies {
|
||||
testImplementation(libs.test.mockk)
|
||||
testImplementation(libs.androidx.test.ext)
|
||||
testImplementation(libs.kotlinx.coroutines.test)
|
||||
testImplementation(libs.test.slf4j.simple)
|
||||
testImplementation(libs.slf4j.simple)
|
||||
testImplementation(libs.test.robolectric)
|
||||
testImplementation(libs.kotlin.junit)
|
||||
}
|
||||
|
||||
@@ -3,16 +3,12 @@ package no.nordicsemi.android.gls
|
||||
import android.annotation.SuppressLint
|
||||
import android.content.Context
|
||||
import android.os.ParcelUuid
|
||||
import dagger.hilt.android.qualifiers.ApplicationContext
|
||||
import kotlinx.coroutines.CoroutineScope
|
||||
import kotlinx.coroutines.delay
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.mapNotNull
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.launch
|
||||
import no.nordicsemi.android.common.core.DataByteArray
|
||||
import no.nordicsemi.android.common.logger.BleLogger
|
||||
import no.nordicsemi.android.common.logger.DefaultConsoleLogger
|
||||
import no.nordicsemi.android.gls.main.viewmodel.BATTERY_LEVEL_CHARACTERISTIC_UUID
|
||||
import no.nordicsemi.android.gls.main.viewmodel.BATTERY_SERVICE_UUID
|
||||
import no.nordicsemi.android.gls.main.viewmodel.GLS_SERVICE_UUID
|
||||
@@ -26,6 +22,7 @@ import no.nordicsemi.android.kotlin.ble.core.advertiser.BleAdvertisingData
|
||||
import no.nordicsemi.android.kotlin.ble.core.advertiser.BleAdvertisingSettings
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.BleGattPermission
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.BleGattProperty
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.util.DataByteArray
|
||||
import no.nordicsemi.android.kotlin.ble.profile.gls.RecordAccessControlPointInputParser
|
||||
import no.nordicsemi.android.kotlin.ble.server.main.ServerBleGatt
|
||||
import no.nordicsemi.android.kotlin.ble.server.main.service.ServerBleGattCharacteristic
|
||||
@@ -42,9 +39,6 @@ private const val STANDARD_DELAY = 1000L
|
||||
@Singleton
|
||||
class GLSServer @Inject constructor(
|
||||
private val scope: CoroutineScope,
|
||||
@ApplicationContext
|
||||
private val context: Context,
|
||||
private val logger: BleLogger = DefaultConsoleLogger(context),
|
||||
) {
|
||||
|
||||
private lateinit var server: ServerBleGatt
|
||||
@@ -197,7 +191,6 @@ class GLSServer @Inject constructor(
|
||||
config = arrayOf(serviceConfig, batteryService),
|
||||
mock = device,
|
||||
scope = scope,
|
||||
logger = { _, log -> println(log) }
|
||||
)
|
||||
|
||||
BleAdvertiser.create(context)
|
||||
|
||||
@@ -32,10 +32,9 @@
|
||||
package no.nordicsemi.android.gls.main.viewmodel
|
||||
|
||||
import android.annotation.SuppressLint
|
||||
import android.app.Application
|
||||
import android.content.Context
|
||||
import android.os.ParcelUuid
|
||||
import androidx.lifecycle.AndroidViewModel
|
||||
import androidx.lifecycle.ViewModel
|
||||
import androidx.lifecycle.viewModelScope
|
||||
import dagger.hilt.android.lifecycle.HiltViewModel
|
||||
import dagger.hilt.android.qualifiers.ApplicationContext
|
||||
@@ -50,7 +49,7 @@ import kotlinx.coroutines.launch
|
||||
import no.nordicsemi.android.analytics.AppAnalytics
|
||||
import no.nordicsemi.android.analytics.Profile
|
||||
import no.nordicsemi.android.analytics.ProfileConnectedEvent
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.common.navigation.NavigationResult
|
||||
import no.nordicsemi.android.common.navigation.Navigator
|
||||
import no.nordicsemi.android.gls.GlsDetailsDestinationId
|
||||
@@ -80,11 +79,13 @@ import no.nordicsemi.android.kotlin.ble.profile.gls.data.RequestStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.gls.data.ResponseData
|
||||
import no.nordicsemi.android.kotlin.ble.profile.racp.RACPOpCode
|
||||
import no.nordicsemi.android.kotlin.ble.profile.racp.RACPResponseCode
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.toolbox.scanner.ScannerDestinationId
|
||||
import no.nordicsemi.android.ui.view.NordicLoggerFactory
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import no.nordicsemi.android.utils.tryOrLog
|
||||
import java.util.*
|
||||
import timber.log.Timber
|
||||
import java.util.UUID
|
||||
import javax.inject.Inject
|
||||
|
||||
val GLS_SERVICE_UUID: UUID = UUID.fromString("00001808-0000-1000-8000-00805f9b34fb")
|
||||
@@ -100,15 +101,14 @@ val BATTERY_LEVEL_CHARACTERISTIC_UUID = UUID.fromString("00002A19-0000-1000-8000
|
||||
@SuppressLint("MissingPermission")
|
||||
@HiltViewModel
|
||||
internal class GLSViewModel @Inject constructor(
|
||||
@ApplicationContext context: Context,
|
||||
@ApplicationContext private val context: Context,
|
||||
private val navigationManager: Navigator,
|
||||
private val analytics: AppAnalytics,
|
||||
private val stringConst: StringConst,
|
||||
private val loggerFactory: NordicLoggerFactory
|
||||
) : AndroidViewModel(context as Application) {
|
||||
) : ViewModel() {
|
||||
|
||||
private var client: ClientBleGatt? = null
|
||||
private lateinit var logger: BleLoggerAndLauncher
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private lateinit var glucoseMeasurementCharacteristic: ClientBleGattCharacteristic
|
||||
private lateinit var recordAccessControlPointCharacteristic: ClientBleGattCharacteristic
|
||||
@@ -136,7 +136,7 @@ internal class GLSViewModel @Inject constructor(
|
||||
|
||||
fun onEvent(event: GLSScreenViewEvent) {
|
||||
when (event) {
|
||||
OpenLoggerEvent -> logger.launch()
|
||||
OpenLoggerEvent -> LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
is OnWorkingModeSelected -> onEvent(event)
|
||||
is OnGLSRecordClick -> navigateToDetails(event.record)
|
||||
DisconnectEvent -> onDisconnectEvent()
|
||||
@@ -167,10 +167,9 @@ internal class GLSViewModel @Inject constructor(
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = viewModelScope.launch {
|
||||
_state.value = _state.value.copy(deviceName = device.name)
|
||||
initLogger(device)
|
||||
|
||||
logger = loggerFactory.createNordicLogger(getApplication(), stringConst.APP_NAME, "GLS", device.address)
|
||||
|
||||
val client = ClientBleGatt.connect(getApplication(), device, viewModelScope, logger = logger)
|
||||
val client = ClientBleGatt.connect(context, device, viewModelScope)
|
||||
this@GLSViewModel.client = client
|
||||
|
||||
client.waitForBonding()
|
||||
@@ -333,4 +332,10 @@ internal class GLSViewModel @Inject constructor(
|
||||
_state.value = _state.value.copyWithNewRequestStatus(RequestStatus.FAILED)
|
||||
}
|
||||
}
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "GLS", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,7 +48,7 @@ dependencies {
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.nordic.blek.client)
|
||||
implementation(libs.nordic.blek.profile)
|
||||
@@ -63,4 +63,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -38,16 +38,18 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.hrs.data.HRSServiceData
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.hrs.data.HRSData
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -58,7 +60,7 @@ class HRSRepository @Inject constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(HRSServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -85,8 +87,14 @@ class HRSRepository @Inject constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "HRS", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "HRS", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(HRSService::class.java, device)
|
||||
}
|
||||
@@ -117,7 +125,7 @@ class HRSRepository @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -88,7 +88,7 @@ internal class HRSService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@HRSService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@HRSService, device, lifecycleScope)
|
||||
this@HRSService.client = client
|
||||
|
||||
client.waitForBonding()
|
||||
|
||||
@@ -50,9 +50,10 @@ dependencies {
|
||||
implementation(libs.nordic.blek.uiscanner)
|
||||
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.ui)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.androidx.compose.material3)
|
||||
implementation(libs.androidx.compose.material.iconsExtended)
|
||||
@@ -61,4 +62,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -38,17 +38,19 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.hts.data.HTSServiceData
|
||||
import no.nordicsemi.android.hts.view.TemperatureUnit
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.hts.data.HTSData
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -59,7 +61,7 @@ class HTSRepository @Inject constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(HTSServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -86,9 +88,15 @@ class HTSRepository @Inject constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "HTS", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "HTS", device.address)
|
||||
initLogger(device)
|
||||
serviceManager.startService(HTSService::class.java, device)
|
||||
}
|
||||
|
||||
@@ -109,7 +117,7 @@ class HTSRepository @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -86,7 +86,7 @@ internal class HTSService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@HTSService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@HTSService, device, lifecycleScope)
|
||||
this@HTSService.client = client
|
||||
|
||||
client.connectionStateWithStatus
|
||||
|
||||
@@ -43,7 +43,7 @@ import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.unit.dp
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.hts.R
|
||||
import no.nordicsemi.android.hts.data.HTSServiceData
|
||||
import no.nordicsemi.android.ui.view.BatteryLevelView
|
||||
|
||||
@@ -31,8 +31,9 @@
|
||||
|
||||
package no.nordicsemi.android.hts.view
|
||||
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.theme.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.ui.view.RadioGroupViewEntity
|
||||
import java.util.Locale
|
||||
|
||||
private const val DISPLAY_FAHRENHEIT = "°F"
|
||||
private const val DISPLAY_CELSIUS = "°C"
|
||||
@@ -40,9 +41,9 @@ private const val DISPLAY_KELVIN = "°K"
|
||||
|
||||
internal fun displayTemperature(value: Float, temperatureUnit: TemperatureUnit): String {
|
||||
return when (temperatureUnit) {
|
||||
TemperatureUnit.CELSIUS -> String.format("%.1f °C", value)
|
||||
TemperatureUnit.FAHRENHEIT -> String.format("%.1f °F", value * 1.8f + 32f)
|
||||
TemperatureUnit.KELVIN -> String.format("%.1f °K", value + 273.15f)
|
||||
TemperatureUnit.CELSIUS -> String.format(Locale.US, "%.1f °C", value)
|
||||
TemperatureUnit.FAHRENHEIT -> String.format(Locale.US, "%.1f °F", value * 1.8f + 32f)
|
||||
TemperatureUnit.KELVIN -> String.format(Locale.US, "%.1f °K", value + 273.15f)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -57,11 +58,14 @@ internal fun String.toTemperatureUnit(): TemperatureUnit {
|
||||
|
||||
internal fun TemperatureUnit.temperatureSettingsItems(): RadioGroupViewEntity {
|
||||
return RadioGroupViewEntity(
|
||||
TemperatureUnit.values().map { createRadioButtonItem(it, this) }
|
||||
TemperatureUnit.entries.map { createRadioButtonItem(it, this) }
|
||||
)
|
||||
}
|
||||
|
||||
private fun createRadioButtonItem(unit: TemperatureUnit, selectedTemperatureUnit: TemperatureUnit): RadioButtonItem {
|
||||
private fun createRadioButtonItem(
|
||||
unit: TemperatureUnit,
|
||||
selectedTemperatureUnit: TemperatureUnit
|
||||
): RadioButtonItem {
|
||||
return RadioButtonItem(displayTemperature(unit), unit == selectedTemperatureUnit)
|
||||
}
|
||||
|
||||
|
||||
@@ -53,7 +53,7 @@ dependencies {
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.androidx.compose.material3)
|
||||
implementation(libs.androidx.compose.material.iconsExtended)
|
||||
@@ -62,4 +62,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -38,16 +38,18 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.prx.AlarmLevel
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.prx.data.PRXServiceData
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -58,7 +60,7 @@ class PRXRepository @Inject internal constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(PRXServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -88,8 +90,14 @@ class PRXRepository @Inject internal constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "PRX", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "PRX", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(PRXService::class.java, device)
|
||||
}
|
||||
@@ -119,7 +127,7 @@ class PRXRepository @Inject internal constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -164,7 +164,6 @@ internal class PRXService : NotificationService() {
|
||||
this@PRXService,
|
||||
device,
|
||||
lifecycleScope,
|
||||
logger = { p, s -> repository.log(p, s) },
|
||||
options = BleGattConnectOptions(autoConnect = true)
|
||||
)
|
||||
this@PRXService.client = client
|
||||
|
||||
@@ -48,7 +48,7 @@ dependencies {
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.nordic.blek.client)
|
||||
implementation(libs.nordic.blek.profile)
|
||||
@@ -61,4 +61,8 @@ dependencies {
|
||||
implementation(libs.androidx.lifecycle.service)
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
}
|
||||
|
||||
@@ -38,16 +38,18 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.DefaultBleLogger
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.kotlin.ble.profile.rscs.data.RSCSData
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.rscs.data.RSCSServiceData
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -58,7 +60,7 @@ class RSCSRepository @Inject constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val stringConst: StringConst
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(RSCSServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -85,8 +87,14 @@ class RSCSRepository @Inject constructor(
|
||||
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
private fun initLogger(device: ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "RSCS", device.address)
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = DefaultBleLogger.create(context, stringConst.APP_NAME, "RSCS", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(RSCSService::class.java, device)
|
||||
}
|
||||
@@ -109,7 +117,7 @@ class RSCSRepository @Inject constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -86,7 +86,7 @@ internal class RSCSService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@RSCSService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@RSCSService, device, lifecycleScope)
|
||||
this@RSCSService.client = client
|
||||
|
||||
client.connectionStateWithStatus
|
||||
|
||||
@@ -52,8 +52,9 @@ dependencies {
|
||||
|
||||
implementation(libs.nordic.core)
|
||||
implementation(libs.nordic.theme)
|
||||
implementation(libs.nordic.ui)
|
||||
implementation(libs.nordic.navigation)
|
||||
implementation(libs.nordic.uilogger)
|
||||
implementation(libs.nordic.logger)
|
||||
|
||||
implementation(libs.nordic.blek.client)
|
||||
implementation(libs.nordic.blek.profile)
|
||||
@@ -66,12 +67,8 @@ dependencies {
|
||||
implementation(libs.room.ktx)
|
||||
ksp(libs.room.compiler)
|
||||
|
||||
implementation(libs.accompanist.pager)
|
||||
implementation(libs.accompanist.pagerindicators)
|
||||
|
||||
implementation(libs.androidx.dataStore.core)
|
||||
implementation(libs.androidx.dataStore.preferences)
|
||||
implementation(libs.androidx.compose.material3)
|
||||
implementation(libs.androidx.compose.material.iconsExtended)
|
||||
implementation(libs.androidx.core.ktx)
|
||||
implementation(libs.androidx.activity.compose)
|
||||
@@ -79,6 +76,11 @@ dependencies {
|
||||
|
||||
implementation(libs.androidx.hilt.navigation.compose)
|
||||
|
||||
|
||||
// Timber & SLF4J
|
||||
implementation (libs.slf4j.timber)
|
||||
implementation(libs.nordic.log.timber)
|
||||
|
||||
testImplementation(libs.hilt.android.testing)
|
||||
kaptTest(libs.hilt.compiler)
|
||||
testImplementation(libs.androidx.test.rules)
|
||||
@@ -87,7 +89,7 @@ dependencies {
|
||||
testImplementation(libs.test.mockk)
|
||||
testImplementation(libs.androidx.test.ext)
|
||||
testImplementation(libs.kotlinx.coroutines.test)
|
||||
testImplementation(libs.test.slf4j.simple)
|
||||
testImplementation(libs.slf4j.simple)
|
||||
testImplementation(libs.test.robolectric)
|
||||
testImplementation(libs.kotlin.junit)
|
||||
|
||||
|
||||
@@ -9,13 +9,13 @@ import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.mapNotNull
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.launch
|
||||
import no.nordicsemi.android.common.core.DataByteArray
|
||||
import no.nordicsemi.android.kotlin.ble.advertiser.BleAdvertiser
|
||||
import no.nordicsemi.android.kotlin.ble.core.MockServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.advertiser.BleAdvertisingConfig
|
||||
import no.nordicsemi.android.kotlin.ble.core.advertiser.BleAdvertisingData
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.BleGattPermission
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.BleGattProperty
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.util.DataByteArray
|
||||
import no.nordicsemi.android.kotlin.ble.server.main.ServerBleGatt
|
||||
import no.nordicsemi.android.kotlin.ble.server.main.service.ServerBleGattCharacteristic
|
||||
import no.nordicsemi.android.kotlin.ble.server.main.service.ServerBleGattCharacteristicConfig
|
||||
|
||||
@@ -55,7 +55,7 @@ enum class MacroIcon(public val index: Int) {
|
||||
|
||||
companion object {
|
||||
fun create(index: Int): MacroIcon {
|
||||
return values().firstOrNull { it.index == index }
|
||||
return entries.firstOrNull { it.index == index }
|
||||
?: throw IllegalArgumentException("Cannot create MacroIcon for index: $index")
|
||||
}
|
||||
}
|
||||
|
||||
@@ -51,7 +51,7 @@ internal class CommentVisitor : Visitor {
|
||||
val element = node.node
|
||||
val builder =
|
||||
StringBuilder("A configuration must have 9 commands, one for each button.\n Possible icons are:")
|
||||
for (icon in MacroIcon.values()) builder.append("\n - ")
|
||||
for (icon in MacroIcon.entries) builder.append("\n - ")
|
||||
.append(icon.toString())
|
||||
element.comment = builder.toString()
|
||||
}
|
||||
|
||||
@@ -38,10 +38,12 @@ import kotlinx.coroutines.flow.asSharedFlow
|
||||
import kotlinx.coroutines.flow.asStateFlow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import no.nordicsemi.android.common.core.simpleSharedFlow
|
||||
import no.nordicsemi.android.common.logger.BleLoggerAndLauncher
|
||||
import no.nordicsemi.android.common.logger.LoggerLauncher
|
||||
import no.nordicsemi.android.kotlin.ble.core.ServerDevice
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionStateWithStatus
|
||||
import no.nordicsemi.android.log.LogSession
|
||||
import no.nordicsemi.android.log.timber.nRFLoggerTree
|
||||
import no.nordicsemi.android.service.DisconnectAndStopEvent
|
||||
import no.nordicsemi.android.service.ServiceManager
|
||||
import no.nordicsemi.android.uart.data.ConfigurationDataSource
|
||||
@@ -51,8 +53,8 @@ import no.nordicsemi.android.uart.data.UARTRecord
|
||||
import no.nordicsemi.android.uart.data.UARTRecordType
|
||||
import no.nordicsemi.android.uart.data.UARTServiceData
|
||||
import no.nordicsemi.android.uart.data.parseWithNewLineChar
|
||||
import no.nordicsemi.android.ui.view.NordicLoggerFactory
|
||||
import no.nordicsemi.android.ui.view.StringConst
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@@ -63,9 +65,8 @@ class UARTRepository @Inject internal constructor(
|
||||
private val serviceManager: ServiceManager,
|
||||
private val configurationDataSource: ConfigurationDataSource,
|
||||
private val stringConst: StringConst,
|
||||
private val loggerFactory: NordicLoggerFactory
|
||||
) {
|
||||
private var logger: BleLoggerAndLauncher? = null
|
||||
private var logger: nRFLoggerTree? = null
|
||||
|
||||
private val _data = MutableStateFlow(UARTServiceData())
|
||||
internal val data = _data.asStateFlow()
|
||||
@@ -98,11 +99,17 @@ class UARTRepository @Inject internal constructor(
|
||||
private fun shouldClean() = !isOnScreen && !isServiceRunning
|
||||
|
||||
fun launch(device: ServerDevice) {
|
||||
logger = loggerFactory.createNordicLogger(context, stringConst.APP_NAME, "UART", device.address)
|
||||
initLogger(device)
|
||||
_data.value = _data.value.copy(deviceName = device.name)
|
||||
serviceManager.startService(UARTService::class.java, device)
|
||||
}
|
||||
|
||||
private fun initLogger(device : ServerDevice) {
|
||||
logger?.let { Timber.uproot(it) }
|
||||
logger = nRFLoggerTree(context, stringConst.APP_NAME, "UART", device.name ?: "Unknown")
|
||||
.also { Timber.plant(it) }
|
||||
}
|
||||
|
||||
fun onConnectionStateChanged(connectionState: GattConnectionStateWithStatus?) {
|
||||
_data.value = _data.value.copy(connectionState = connectionState)
|
||||
}
|
||||
@@ -135,7 +142,7 @@ class UARTRepository @Inject internal constructor(
|
||||
}
|
||||
|
||||
fun openLogger() {
|
||||
logger?.launch()
|
||||
LoggerLauncher.launch(context, logger?.session as? LogSession)
|
||||
}
|
||||
|
||||
fun log(priority: Int, message: String) {
|
||||
|
||||
@@ -43,7 +43,6 @@ import kotlinx.coroutines.flow.map
|
||||
import kotlinx.coroutines.flow.mapNotNull
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.launch
|
||||
import no.nordicsemi.android.common.core.DataByteArray
|
||||
import no.nordicsemi.android.kotlin.ble.client.main.callback.ClientBleGatt
|
||||
import no.nordicsemi.android.kotlin.ble.client.main.service.ClientBleGattCharacteristic
|
||||
import no.nordicsemi.android.kotlin.ble.client.main.service.ClientBleGattServices
|
||||
@@ -53,10 +52,11 @@ import no.nordicsemi.android.kotlin.ble.core.data.BleGattProperty
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.BleWriteType
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.Mtu
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.util.DataByteArray
|
||||
import no.nordicsemi.android.kotlin.ble.profile.battery.BatteryLevelParser
|
||||
import no.nordicsemi.android.service.DEVICE_DATA
|
||||
import no.nordicsemi.android.service.NotificationService
|
||||
import java.util.*
|
||||
import java.util.UUID
|
||||
import javax.inject.Inject
|
||||
|
||||
val UART_SERVICE_UUID: UUID = UUID.fromString("6E400001-B5A3-F393-E0A9-E50E24DCCA9E")
|
||||
@@ -92,7 +92,7 @@ internal class UARTService : NotificationService() {
|
||||
}
|
||||
|
||||
private fun startGattClient(device: ServerDevice) = lifecycleScope.launch {
|
||||
val client = ClientBleGatt.connect(this@UARTService, device, lifecycleScope, logger = { p, s -> repository.log(p, s) })
|
||||
val client = ClientBleGatt.connect(this@UARTService, device, lifecycleScope)
|
||||
this@UARTService.client = client
|
||||
|
||||
if (!client.isConnected) {
|
||||
|
||||
@@ -45,21 +45,20 @@ import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.unit.dp
|
||||
import kotlinx.coroutines.launch
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.theme.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.ui.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.uart.R
|
||||
import no.nordicsemi.android.uart.data.MacroEol
|
||||
import no.nordicsemi.android.ui.view.ScreenSection
|
||||
import no.nordicsemi.android.ui.view.SectionTitle
|
||||
import no.nordicsemi.android.utils.EMPTY
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
internal fun InputSection(onEvent: (UARTViewEvent) -> Unit) {
|
||||
val text = rememberSaveable { mutableStateOf(String.EMPTY) }
|
||||
val hint = stringResource(id = R.string.uart_input_hint)
|
||||
val checkedItem = rememberSaveable { mutableStateOf(MacroEol.values()[0]) }
|
||||
val checkedItem = rememberSaveable { mutableStateOf(MacroEol.entries[0]) }
|
||||
|
||||
Row(verticalAlignment = Alignment.CenterVertically) {
|
||||
Box(modifier = Modifier.weight(1f)) {
|
||||
@@ -99,9 +98,9 @@ internal fun InputSection(onEvent: (UARTViewEvent) -> Unit) {
|
||||
|
||||
@Composable
|
||||
internal fun EditInputSection(onEvent: (UARTViewEvent) -> Unit) {
|
||||
val checkedItem = rememberSaveable { mutableStateOf(MacroEol.values()[0]) }
|
||||
val checkedItem = rememberSaveable { mutableStateOf(MacroEol.entries[0]) }
|
||||
|
||||
val items = MacroEol.values().map {
|
||||
val items = MacroEol.entries.map {
|
||||
RadioButtonItem(it.toDisplayString(), it == checkedItem.value)
|
||||
}
|
||||
val viewEntity = RadioGroupViewEntity(items)
|
||||
|
||||
@@ -70,7 +70,6 @@ internal fun UARTAddConfigurationDialog(onEvent: (UARTViewEvent) -> Unit, onDism
|
||||
)
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
private fun NameInput(
|
||||
name: MutableState<String>,
|
||||
|
||||
@@ -34,12 +34,21 @@ package no.nordicsemi.android.uart.view
|
||||
import androidx.compose.foundation.Image
|
||||
import androidx.compose.foundation.background
|
||||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.*
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.Row
|
||||
import androidx.compose.foundation.layout.Spacer
|
||||
import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.layout.size
|
||||
import androidx.compose.foundation.layout.wrapContentHeight
|
||||
import androidx.compose.foundation.lazy.grid.GridCells
|
||||
import androidx.compose.foundation.lazy.grid.GridItemSpan
|
||||
import androidx.compose.foundation.lazy.grid.LazyVerticalGrid
|
||||
import androidx.compose.foundation.shape.RoundedCornerShape
|
||||
import androidx.compose.material3.*
|
||||
import androidx.compose.material3.AlertDialog
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.OutlinedTextField
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.material3.TextButton
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.MutableState
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
@@ -52,9 +61,9 @@ import androidx.compose.ui.graphics.ColorFilter
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.unit.dp
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.theme.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.theme.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonGroup
|
||||
import no.nordicsemi.android.common.ui.view.RadioButtonItem
|
||||
import no.nordicsemi.android.common.ui.view.RadioGroupViewEntity
|
||||
import no.nordicsemi.android.uart.R
|
||||
import no.nordicsemi.android.uart.data.MacroEol
|
||||
import no.nordicsemi.android.uart.data.MacroIcon
|
||||
@@ -67,7 +76,7 @@ private const val GRID_SIZE = 5
|
||||
internal fun UARTAddMacroDialog(macro: UARTMacro?, onEvent: (UARTViewEvent) -> Unit) {
|
||||
val newLineChar = rememberSaveable { mutableStateOf(macro?.newLineChar ?: MacroEol.LF) }
|
||||
val command = rememberSaveable { mutableStateOf(macro?.command ?: String.EMPTY) }
|
||||
val selectedIcon = rememberSaveable { mutableStateOf(macro?.icon ?: MacroIcon.values()[0]) }
|
||||
val selectedIcon = rememberSaveable { mutableStateOf(macro?.icon ?: MacroIcon.entries.toTypedArray()[0]) }
|
||||
|
||||
AlertDialog(
|
||||
onDismissRequest = { onEvent(OnEditFinish) },
|
||||
@@ -130,7 +139,6 @@ internal fun UARTAddMacroDialog(macro: UARTMacro?, onEvent: (UARTViewEvent) -> U
|
||||
)
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
private fun CommandInput(command: MutableState<String>) {
|
||||
Column {
|
||||
@@ -150,7 +158,7 @@ private fun CommandInput(command: MutableState<String>) {
|
||||
|
||||
@Composable
|
||||
private fun NewLineCharSection(checkedItem: MacroEol, onItemClick: (MacroEol) -> Unit) {
|
||||
val items = MacroEol.values().map {
|
||||
val items = MacroEol.entries.map {
|
||||
RadioButtonItem(it.toDisplayString(), it == checkedItem)
|
||||
}
|
||||
val viewEntity = RadioGroupViewEntity(items)
|
||||
|
||||
@@ -31,12 +31,10 @@
|
||||
|
||||
package no.nordicsemi.android.uart.view
|
||||
|
||||
import androidx.compose.foundation.ExperimentalFoundationApi
|
||||
import androidx.compose.foundation.layout.Box
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.fillMaxSize
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.Scaffold
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.collectAsState
|
||||
@@ -46,16 +44,16 @@ import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.unit.dp
|
||||
import androidx.hilt.navigation.compose.hiltViewModel
|
||||
import no.nordicsemi.android.common.theme.view.PagerView
|
||||
import no.nordicsemi.android.common.theme.view.PagerViewEntity
|
||||
import no.nordicsemi.android.common.theme.view.PagerViewItem
|
||||
import no.nordicsemi.android.common.ui.view.PagerView
|
||||
import no.nordicsemi.android.common.ui.view.PagerViewEntity
|
||||
import no.nordicsemi.android.common.ui.view.PagerViewItem
|
||||
import no.nordicsemi.android.kotlin.ble.core.data.GattConnectionState
|
||||
import no.nordicsemi.android.kotlin.ble.ui.scanner.view.DeviceConnectingView
|
||||
import no.nordicsemi.android.kotlin.ble.ui.scanner.view.DeviceDisconnectedView
|
||||
import no.nordicsemi.android.uart.R
|
||||
import no.nordicsemi.android.uart.viewmodel.UARTViewModel
|
||||
import no.nordicsemi.android.ui.view.NavigateUpButton
|
||||
import no.nordicsemi.android.ui.view.ProfileAppBar
|
||||
import no.nordicsemi.android.kotlin.ble.ui.scanner.view.DeviceConnectingView
|
||||
import no.nordicsemi.android.kotlin.ble.ui.scanner.view.DeviceDisconnectedView
|
||||
|
||||
@Composable
|
||||
fun UARTScreen() {
|
||||
@@ -99,7 +97,6 @@ private fun PaddingBox(content: @Composable () -> Unit) {
|
||||
}
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalFoundationApi::class)
|
||||
@Composable
|
||||
private fun SuccessScreen() {
|
||||
val input = stringResource(id = R.string.uart_input)
|
||||
|
||||
@@ -39,20 +39,20 @@ internal sealed class UARTViewEvent
|
||||
|
||||
internal data class OnEditMacro(val position: Int) : UARTViewEvent()
|
||||
internal data class OnCreateMacro(val macro: UARTMacro) : UARTViewEvent()
|
||||
internal object OnDeleteMacro : UARTViewEvent()
|
||||
internal object OnEditFinish : UARTViewEvent()
|
||||
internal data object OnDeleteMacro : UARTViewEvent()
|
||||
internal data object OnEditFinish : UARTViewEvent()
|
||||
|
||||
internal data class OnConfigurationSelected(val configuration: UARTConfiguration) : UARTViewEvent()
|
||||
internal data class OnAddConfiguration(val name: String) : UARTViewEvent()
|
||||
internal object OnEditConfiguration : UARTViewEvent()
|
||||
internal object OnDeleteConfiguration : UARTViewEvent()
|
||||
internal data object OnEditConfiguration : UARTViewEvent()
|
||||
internal data object OnDeleteConfiguration : UARTViewEvent()
|
||||
internal data class OnRunMacro(val macro: UARTMacro) : UARTViewEvent()
|
||||
internal data class OnRunInput(val text: String, val newLineChar: MacroEol) : UARTViewEvent()
|
||||
|
||||
internal object ClearOutputItems : UARTViewEvent()
|
||||
internal object DisconnectEvent : UARTViewEvent()
|
||||
internal data object ClearOutputItems : UARTViewEvent()
|
||||
internal data object DisconnectEvent : UARTViewEvent()
|
||||
|
||||
internal object NavigateUp : UARTViewEvent()
|
||||
internal object OpenLogger : UARTViewEvent()
|
||||
internal data object NavigateUp : UARTViewEvent()
|
||||
internal data object OpenLogger : UARTViewEvent()
|
||||
|
||||
internal object MacroInputSwitchClick : UARTViewEvent()
|
||||
internal data object MacroInputSwitchClick : UARTViewEvent()
|
||||
|
||||
@@ -77,7 +77,6 @@ import no.nordicsemi.android.uart.view.OnRunMacro
|
||||
import no.nordicsemi.android.uart.view.OpenLogger
|
||||
import no.nordicsemi.android.uart.view.UARTViewEvent
|
||||
import no.nordicsemi.android.uart.view.UARTViewState
|
||||
import no.nordicsemi.android.ui.view.NordicLoggerFactory
|
||||
import javax.inject.Inject
|
||||
|
||||
@HiltViewModel
|
||||
@@ -86,7 +85,6 @@ internal class UARTViewModel @Inject constructor(
|
||||
private val navigationManager: Navigator,
|
||||
private val dataSource: UARTPersistentDataSource,
|
||||
private val analytics: AppAnalytics,
|
||||
private val loggerFactory: NordicLoggerFactory
|
||||
) : ViewModel() {
|
||||
|
||||
private val _state = MutableStateFlow(UARTViewState())
|
||||
|
||||
@@ -50,7 +50,7 @@ dependencyResolutionManagement {
|
||||
}
|
||||
versionCatalogs {
|
||||
create("libs") {
|
||||
from("no.nordicsemi.android.gradle:version-catalog:1.11.1")
|
||||
from("no.nordicsemi.android.gradle:version-catalog:2.4")
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -79,6 +79,6 @@ include(":lib_utils")
|
||||
// includeBuild("../Android-Common-Libraries")
|
||||
//}
|
||||
//
|
||||
if (file("../Kotlin-BLE-Library").exists()) {
|
||||
includeBuild("../Kotlin-BLE-Library")
|
||||
}
|
||||
//if (file("../Kotlin-BLE-Library").exists()) {
|
||||
// includeBuild("../Kotlin-BLE-Library")
|
||||
//}
|
||||
|
||||
Reference in New Issue
Block a user