I'm pretty much a beginner in Kotlin, Room, Flows and viewmodels. The Flow data coming from the viewmodel seems to be working quite well as soon as I launch the app, updating the Jetpack Compose LazyColumn in my MainActivity with data coming from Room Database as I keep inserting or deleting data in the DB through Android Studio's App Inspector and until the device is rotated. After the device is rotated the LazyColumn just stops being receiving new data (but the list still remains populated with what it had up to before device rotation). At this stage, when I add data to the DB, the LazyColum just keeps displaying the old data, until I rotate the device again, triggering recomposition and updating the list with the fresh data.
This is my situation:
OrderDao.kt
@Dao
interface OrderDao {
//just grabbing what I got from the DB and returning a Flow
@Query("SELECT * FROM orders")
fun loadAllOrders(): Flow<List<Order>>
}
OrderRepository.kt
class OrderRepository (context: Context) {
private val db : OrderDatabase
val orderDao : OrderDao
init{
db = Room.databaseBuilder(
context.applicationContext,
OrderDatabase::class.java, "orders"
).fallbackToDestructiveMigration().build()
orderDao = db.orderDao()
}
fun getOrders(): Flow<List<Order>> {
return orderDao.loadAllOrders()
}
}
Also the Database gets initialized in the repository as you can see, which I believe is not a good practice and it's something I need to see to fix, but if there is a good soul that could give me a hint it would be much appreciated. Anyways..
MainActivityViewModel.kt
class MainActivityViewModel(activity : Activity) : ViewModel() {
private var repository = OrderRepository(activity)
val mainUiState: StateFlow<MainActivityUiState> = repository.getOrders().map { MainActivityUiState(it) }
.stateIn(
scope = viewModelScope,
started = SharingStarted.WhileSubscribed(5_000L),
initialValue = MainActivityUiState()
)
data class MainActivityUiState(val itemList: List<Ordine> = listOf())
}
And my MainActivity.kt which contains the LazyColumn
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
val viewModel= MainActivityViewModel(this@MainActivity)
val orders by viewModel.mainUiState.collectAsState()
OrdersTheme {
// A surface container using the 'background' color from the theme
Surface(
modifier = Modifier.fillMaxSize(),
color = MaterialTheme.colors.background
) {
Column() {
OrderList(activity = this@MainActivity, orders = orders)
}
}
}
}
}
}
@Composable
fun ElencoOrdini (modifier: Modifier = Modifier, activity: MainActivity, orders : MainActivityViewModel.MainActivityUiState) {
Column(){
LazyColumn(contentPadding = PaddingValues(50.dp)){
itemsIndexed(orders.itemList) { index, item ->
OrderItem(order = item)
}
}
}
}
@Composable
fun OrderItem (order : Order) {
Row(
Modifier
.fillMaxSize()
.background(Color.LightGray)){
Text(text = "Order #")
Text(text = "${order.id}")
}
}
Can someone please give a hint on how to fix it? Any tip on how to improve the code maybe? I need some guidance. Thank you very much