Ejemplo básico de arquitectura MVVM (model-view-viewmodel) en Android usando Kotlin y Jetpack Compose.
A la hora de organizar el código de nuestra aplicación móvil tenemos varias opciones, como MCV, MVP o MVVM. Esta última es la preferida por Google en Android. Por lo tanto, vamos a crear una aplicación sencilla de muestra usando este patrón.
Para seguir el post necesitas tener conocimientos básicos de programación en Android con Kotlin y el marco de interfaz de usuario Jetpack Compose.
Crear un proyecto en Android Studio
Empezamos creando un proyecto desde Android Studio seleccionando la plantilla de actividad vacía con Jetpack Compose.
A continuación escribimos el nombre del proyecto y del paquete. Además de seleccionar la localización de la aplicación, el sdk mínimo y el lenguaje de programación kotlin.
Arquitectura MVVM
Con el patrón MVVM organizamos el código en 3 capas: Modelo, Vista y Modelo de vista. Esta arquitectura fomenta una clara separación de tareas entre las diferentes capas.
Modelo
La capa modelo es la responsable de mantener los datos y es totalmente independiente de la vista.
Vista
La capa vista se encarga de mostrar los datos al usuario a través de diversos elementos visuales.
Modelo de vista
La capa modelo de vista es la intermediaria entre el modelo y la vista. También es responsable de mantener el estado de los datos.
Creando las capas MVVM en Android Studio
En Android Studio empezamos creando la capa modelo. Nos situamos encima del nombre de nuestro paquete y hacemos clic con el botón derecho del ratón. A continuación seleccionamos New -> Package y escribimos model. Repetimos los mismos pasos para crear los otros 2 paquetes: view y viewmodel.
Ahora deberíamos tener una jerarquía de directorios similar a lo siguiente:
Modelo
Comenzamos creando una data class dentro de nuestro directorio model. En mi caso le voy a llamar Car con las propiedades id, brand y power. Esta clase representará los datos de nuestra app.
data class Car( val id: Int, val brand: String, val power: String )
Ahora añadimos una interface a la que llamamos CarRepository con un solo método getCars().
interface CarRepository { fun getCars(): List<Car> }
Por último implementamos la interface anterior en la clase CarRepositoryIml. Esta clase sobrescribe el método getCars(), que retorna una lista de Cars.
class CarRepositoryIml: CarRepository { override fun getCars(): List<Car> { return listOf( Car(id = 1, brand = "BMW", power = "321hp" ), Car(id = 2, brand = "Mercedes", power = "350hp" ), Car(id = 3, brand = "Toyota", power = "280hp" ), Car(id = 4, brand = "Audi", power = "400hp" ), Car(id = 5, brand = "Renault", power = "300hp" ), ) } }
Con esto ya estamos preparados para seguir con la capa Modelo de vista.
Modelo de Vista
En el paquete viewmodel creamos la clase CarsViewModel. Esta clase extiende de ViewModel y permite que los datos persistan a través de los cambios de configuración. Además de intermediar entre las capas Modelo y Vista.
class CarsViewModel: ViewModel() { private val repository: CarRepository = CarRepositoryIml() fun getCars(): List<Car> { return repository.getCars() } }
Aquí la propiedad repository de tipo CarsRepository obtiene los datos del repositorio. Después desde el método getCars() se exponen los datos a la capa vista.
Vista
Finalmente en el paquete view creamos el archivo Cars.kt. En este caso utilizamos el composable LazyColumn de Jetpack Compose, que organiza la lista de Cars en forma de columna desplazable.
@Composable fun Cars(modifier: Modifier) { val carsViewModel: CarsViewModel = CarsViewModel() LazyColumn(modifier = modifier, horizontalAlignment = Alignment.CenterHorizontally) { items(carsViewModel.getCars()) { car -> Image( modifier = Modifier .width(300.dp) .height(300.dp) .padding(20.dp), painter = painterResource(id = R.drawable.car), contentDescription = stringResource(id = R.string.dog_content_description) ) Text(text = "${car.brand} : ${car.power}") } } }
Pasamos a items la lista de Cars con carsViewModel.getCars()y dentro de éste obtenemos cada uno de los objetos Car, con los que poblamos el composable Text. También tenemos un composable Imagen cuyo drawable lo creamos en el directorio recursos.
Resultado
Sumario
Hemos configurado un proyecto Android sencillo mediante el patrón MVVM.
Hemos organizado el código Kotlin en tres directorios: Model, View y ViewModel
Hemos usado Jetpack Compose en la capa View para mostrar la lista de datos con un LazyColumn composable.
0 comentarios