package com.vgmlr.wedge
// import kotlinx.coroutines.flow.first
import android.content.Context
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.font.FontFamily
import androidx.compose.ui.unit.sp
import androidx.core.content.edit
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.SharingStarted
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.stateIn
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
class MainViewModel(
val dao: NoteDao,
val prefs: PreferenceManager,
context: Context
) : ViewModel() {
private val appContext = context.applicationContext
private val syncPrefs = appContext.getSharedPreferences("sync_prefs", Context.MODE_PRIVATE)
private val _syncStatus = MutableStateFlow("Disconnected")
val syncStatus = _syncStatus.asStateFlow()
private val _isServerRunning = MutableStateFlow(false)
val isServerRunning = _isServerRunning.asStateFlow()
private var currentPassKey = ""
init {
viewModelScope.launch {
prefs.passKey.collect { currentPassKey = it }
}
}
fun updatePassKey(newKey: String) {
viewModelScope.launch {
prefs.setPassKey(newKey)
}
}
private val usbServerManager = UsbServerManager(
getLocalPassKey = { currentPassKey },
onMessageReceived = { cleanMessage ->
viewModelScope.launch(Dispatchers.IO) {
dao.save(NoteEntity(id = 1, content = cleanMessage, lastModified = System.currentTimeMillis()))
NoteWidgetProvider.triggerUpdate(appContext)
syncPrefs.edit {
putLong("sync_last_stamp", System.currentTimeMillis())
}
withContext(Dispatchers.Main) {
_syncStatus.value = "Received"
}
}
},
onStatusChanged = { status, isConnected ->
viewModelScope.launch {
_syncStatus.value = status
if (status.contains("Stopped") || status == "Disconnected") {
_isServerRunning.value = false
} else if (status.contains("Connecting") || status == "Connected") {
_isServerRunning.value = true
}
}
}
)
fun startUsbServer() {
usbServerManager.startServer()
}
fun stopUsbServer() {
usbServerManager.stopServer()
}
fun sendNoteText() {
viewModelScope.launch(Dispatchers.IO) {
val note = dao.getNoteSync()
val text = note?.content ?: ""
usbServerManager.sendTextMessage(text, currentPassKey, onSuccess = {
_syncStatus.value = "Sent"
})
}
}
/* fun runAutomatedSyncSequence() {
viewModelScope.launch(Dispatchers.IO) {
try {
startUsbServer()
syncStatus.first { status: String ->
status == "Connected"
}
val note = dao.getNoteSync()
val text = note?.content ?: ""
usbServerManager.sendTextMessage(text)
syncPrefs.edit {
putLong("sync_last_stamp", System.currentTimeMillis())
}
kotlinx.coroutines.delay(300)
} catch (e: Exception) {
e.printStackTrace()
} finally {
stopUsbServer()
}
}
} */
val editorStyle = prefs.settings.map { settings ->
TextStyle(
fontSize = settings.editorFontSize.sp,
fontFamily = FontFamily.Monospace,
lineHeight = (settings.editorFontSize * settings.lineHeight).sp,
color = parseColor(settings.textColor)
)
}.stateIn(
viewModelScope,
SharingStarted.Eagerly,
TextStyle(
fontSize = WedgeConfig.FONT_SIZE_DEFAULT.sp,
fontFamily = FontFamily.Monospace,
lineHeight = (WedgeConfig.FONT_SIZE_DEFAULT * WedgeConfig.LINE_HEIGHT_DEFAULT).sp,
color = parseColor(WedgeConfig.TEXT_COLOR_DEFAULT)
)
)
override fun onCleared() {
super.onCleared()
usbServerManager.stopServer()
}
}
class MainViewModelFactory(
private val dao: NoteDao,
private val prefs: PreferenceManager,
private val context: Context
) : androidx.lifecycle.ViewModelProvider.Factory {
@Suppress("UNCHECKED_CAST")
override fun <T : ViewModel> create(modelClass: Class<T>): T {
return MainViewModel(dao, prefs, context) as T
}
}