entity, dao, db, viewmodel & factory

pull/7/head
Baptiiiiste 2 years ago
parent d97ad3724c
commit 74837038a4

@ -14,7 +14,6 @@ android {
targetSdk 33 targetSdk 33
versionCode 1 versionCode 1
versionName "1.0" versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
} }
@ -33,7 +32,17 @@ android {
} }
} }
apply plugin: 'kotlin-kapt'
dependencies { dependencies {
kapt "androidx.room:room-compiler:2.5.1"
annotationProcessor "androidx.room:room-compiler:2.5.1"
implementation "androidx.room:room-runtime:2.5.1"
implementation "androidx.room:room-ktx:2.5.1"
// implementation 'androidx.lifecycle:lifecycle-livedata:2.6.1'
// implementation 'androidx.lifecycle:lifecycle-livedata-ktx:2.6.1'
// implementation 'androidx.lifecycle:lifecycle-viewmodel-ktx:2.6.1'
implementation 'androidx.core:core-ktx:1.9.0' implementation 'androidx.core:core-ktx:1.9.0'
implementation 'androidx.appcompat:appcompat:1.6.1' implementation 'androidx.appcompat:appcompat:1.6.1'
@ -47,5 +56,6 @@ dependencies {
implementation "androidx.fragment:fragment-ktx:1.5.5" implementation "androidx.fragment:fragment-ktx:1.5.5"
implementation 'org.osmdroid:osmdroid-android:6.1.14' implementation 'org.osmdroid:osmdroid-android:6.1.14'
implementation 'com.github.MKergall:osmbonuspack:6.9.0' implementation 'com.github.MKergall:osmbonuspack:6.9.0'
implementation 'com.android.support:multidex:1.0.3'
} }

@ -0,0 +1,17 @@
package uca.baptistearthur.geocaching.application
import android.app.Application
import uca.baptistearthur.geocaching.data.Database
class RTApplication: Application() {
lateinit var db: Database
override fun onCreate() {
super.onCreate()
db = Database.getInstance(applicationContext) as Database
}
}

@ -0,0 +1,32 @@
package uca.baptistearthur.geocaching.converters
import androidx.room.TypeConverter
import java.util.Date
import com.google.gson.Gson
import com.google.gson.reflect.TypeToken
import uca.baptistearthur.geocaching.model.Place
class Converters {
@TypeConverter
fun toDate(timestamp: Long?): Date? {
return if (timestamp == null) null else Date(timestamp)
}
@TypeConverter
fun toLong(date: Date?): Long? {
return date?.time
}
@TypeConverter
fun toString(places: List<Place>): String {
return Gson().toJson(places)
}
@TypeConverter
fun toPlaces(value: String): List<Place> {
val listType = object : TypeToken<List<Place>>() {}.type
return Gson().fromJson(value, listType)
}
}

@ -0,0 +1,26 @@
package uca.baptistearthur.geocaching.data
import android.content.Context
import androidx.room.Room
import androidx.room.RoomDatabase
import androidx.room.TypeConverters
import uca.baptistearthur.geocaching.converters.Converters
import uca.baptistearthur.geocaching.model.RoadTripEntity
@androidx.room.Database(entities = arrayOf(RoadTripEntity::class), version=1)
@TypeConverters(Converters::class)
abstract class Database : RoomDatabase(){
abstract fun roadTripDAO(): RoadTripDAO
companion object{
private var INSTANCE: Database ?= null
fun getInstance(context: Context) =
INSTANCE ?: synchronized(this){
val db = Room.databaseBuilder(context, Database::class.java, "roadTripDB").build()
INSTANCE = db
}
}
}

@ -0,0 +1,24 @@
package uca.baptistearthur.geocaching.data
import androidx.annotation.RequiresPermission.Read
import androidx.room.Delete
import androidx.room.Insert
import androidx.room.Query
import kotlinx.coroutines.flow.Flow
import uca.baptistearthur.geocaching.model.RoadTripEntity
@androidx.room.Dao
interface RoadTripDAO {
@Insert
suspend fun insertRoadTrip(r: RoadTripEntity)
@Delete
suspend fun deleteRoadTrip(r: RoadTripEntity)
@Query("SELECT * FROM Roadtrip")
fun getAllRoadTrips(): Flow<MutableList<RoadTripEntity>>
@Query("SELECT * FROM Roadtrip WHERE id = :id")
fun getRoadTripById(id: Int): Flow<RoadTripEntity>
}

@ -1,28 +1,32 @@
package uca.baptistearthur.geocaching.data package uca.baptistearthur.geocaching.data
import uca.baptistearthur.geocaching.model.Place import uca.baptistearthur.geocaching.model.Place
import uca.baptistearthur.geocaching.model.RoadTrip import uca.baptistearthur.geocaching.model.RoadTripEntity
import java.util.Date import java.util.Date
class Stub { class Stub {
fun load(): MutableList<RoadTrip> { fun load(): MutableList<RoadTripEntity> {
val list = listOf( val list = listOf(
RoadTrip( RoadTripEntity(
1,
"France", "France",
Date(), Date(),
listOf(Place(49.3, 49.3)).toMutableList() listOf(Place(49.3, 49.3)).toMutableList()
), ),
RoadTrip( RoadTripEntity(
2,
"Italie", "Italie",
Date(), Date(),
listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList() listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList()
), ),
RoadTrip( RoadTripEntity(
3,
"Danemark", "Danemark",
Date(), Date(),
listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList() listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList()
), ),
RoadTrip( RoadTripEntity(
4,
"Islande", "Islande",
Date(), Date(),
listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList() listOf(Place(48.866667, 2.333333), Place(48.866667, 2.333333), Place(48.866667, 2.333333)).toMutableList()

@ -1,15 +0,0 @@
package uca.baptistearthur.geocaching.model
import java.util.Date
class RoadTrip(
val name: String,
val date: Date,
val places: MutableList<Place>
){
fun addPlaceToRoadTripList(place: Place) = places.add(place)
fun addPlaceToRoadTripList(latitude: Double, longitude: Double) = places.add(Place(latitude, longitude))
}

@ -0,0 +1,19 @@
package uca.baptistearthur.geocaching.model
import androidx.room.ColumnInfo
import androidx.room.Entity
import androidx.room.PrimaryKey
import java.util.Date
@Entity(tableName = "Roadtrip")
class RoadTripEntity(
@PrimaryKey(autoGenerate = true) val id: Int,
@ColumnInfo(name="name") val name: String,
@ColumnInfo(name="date") val date: Date,
@ColumnInfo(name="places") val places: MutableList<Place>
){
fun addPlaceToRoadTripList(place: Place) = places.add(place)
fun addPlaceToRoadTripList(latitude: Double, longitude: Double) = places.add(Place(latitude, longitude))
}

@ -6,7 +6,6 @@ import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import uca.baptistearthur.geocaching.R import uca.baptistearthur.geocaching.R
import uca.baptistearthur.geocaching.model.Place import uca.baptistearthur.geocaching.model.Place
import uca.baptistearthur.geocaching.model.RoadTrip
class PlacesAdapter (val places: List<Place>) : RecyclerView.Adapter<PlacesViewHolder>(){ class PlacesAdapter (val places: List<Place>) : RecyclerView.Adapter<PlacesViewHolder>(){

@ -6,10 +6,10 @@ import android.view.ViewGroup
import androidx.navigation.NavController import androidx.navigation.NavController
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import uca.baptistearthur.geocaching.R import uca.baptistearthur.geocaching.R
import uca.baptistearthur.geocaching.model.RoadTrip import uca.baptistearthur.geocaching.model.RoadTripEntity
class RoadTripAdapter(val voyages: List<RoadTrip>, val navController: NavController) : RecyclerView.Adapter<RoadTripViewHolder>(){ class RoadTripAdapter(val voyages: List<RoadTripEntity>, val navController: NavController) : RecyclerView.Adapter<RoadTripViewHolder>(){
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RoadTripViewHolder { override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RoadTripViewHolder {
return RoadTripViewHolder(LayoutInflater.from(parent.context).inflate(R.layout.cell_one_roadtrip, parent, false), navController) return RoadTripViewHolder(LayoutInflater.from(parent.context).inflate(R.layout.cell_one_roadtrip, parent, false), navController)

@ -8,9 +8,8 @@ import androidx.fragment.app.Fragment
import androidx.recyclerview.widget.LinearLayoutManager import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import uca.baptistearthur.geocaching.R import uca.baptistearthur.geocaching.R
import uca.baptistearthur.geocaching.model.RoadTrip import uca.baptistearthur.geocaching.model.RoadTripEntity
import uca.baptistearthur.geocaching.recyclerview.PlacesAdapter import uca.baptistearthur.geocaching.recyclerview.PlacesAdapter
import uca.baptistearthur.geocaching.recyclerview.RoadTripAdapter
// TODO: Rename parameter arguments, choose names that match // TODO: Rename parameter arguments, choose names that match
// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
@ -19,10 +18,10 @@ private const val ARG_PARAM2 = "param2"
/** /**
* A simple [Fragment] subclass. * A simple [Fragment] subclass.
* Use the [RoadTrip.newInstance] factory method to * Use the [RoadTripEntity.newInstance] factory method to
* create an instance of this fragment. * create an instance of this fragment.
*/ */
class DetailledRoadTripFragment(val roadTrip: RoadTrip): Fragment() { class DetailledRoadTripFragment(val roadTrip: RoadTripEntity): Fragment() {
// TODO: Rename and change types of parameters // TODO: Rename and change types of parameters
private var param1: String? = null private var param1: String? = null
private var param2: String? = null private var param2: String? = null

@ -13,7 +13,7 @@ import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import uca.baptistearthur.geocaching.R import uca.baptistearthur.geocaching.R
import uca.baptistearthur.geocaching.data.Stub import uca.baptistearthur.geocaching.data.Stub
import uca.baptistearthur.geocaching.model.RoadTrip import uca.baptistearthur.geocaching.model.RoadTripEntity
import uca.baptistearthur.geocaching.recyclerview.RoadTripAdapter import uca.baptistearthur.geocaching.recyclerview.RoadTripAdapter
import java.util.* import java.util.*
@ -24,7 +24,7 @@ private const val ARG_PARAM2 = "param2"
/** /**
* A simple [Fragment] subclass. * A simple [Fragment] subclass.
* Use the [RoadTrip.newInstance] factory method to * Use the [RoadTripEntity.newInstance] factory method to
* create an instance of this fragment. * create an instance of this fragment.
*/ */
class RoadTripFragment : Fragment() { class RoadTripFragment : Fragment() {
@ -33,8 +33,6 @@ class RoadTripFragment : Fragment() {
private var param2: String? = null private var param2: String? = null
private var model = Stub().load() private var model = Stub().load()
private var roadTripRecyclerView : RecyclerView? = null private var roadTripRecyclerView : RecyclerView? = null
private var editTextRoadTripName: EditText? = null
private var buttonAddNewRoadTrip: Button? = null
override fun onCreate(savedInstanceState: Bundle?) { override fun onCreate(savedInstanceState: Bundle?) {
@ -49,36 +47,13 @@ class RoadTripFragment : Fragment() {
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? { override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
val view = inflater.inflate(R.layout.fragment_roadtrip, container, false) val view = inflater.inflate(R.layout.fragment_roadtrip, container, false)
roadTripRecyclerView = view?.findViewById(R.id.recyclerViewRoadTripList) roadTripRecyclerView = view?.findViewById(R.id.recyclerViewRoadTripList)
roadTripRecyclerView?.adapter = RoadTripAdapter(model, findNavController()) roadTripRecyclerView?.adapter = RoadTripAdapter(model, findNavController())
roadTripRecyclerView?.layoutManager = LinearLayoutManager(context) roadTripRecyclerView?.layoutManager = LinearLayoutManager(context)
editTextRoadTripName = view?.findViewById(R.id.editTextRoadTripName)
buttonAddNewRoadTrip = view?.findViewById(R.id.buttonAddNewRoadTrip)
buttonAddNewRoadTrip?.setOnClickListener {
addRoadTrip(editTextRoadTripName!!, roadTripRecyclerView!!)
}
return view return view
} }
@SuppressLint("NotifyDataSetChanged")
fun addRoadTrip(editText: EditText, recyclerView: RecyclerView) {
val roadTripName = editText.text.toString().trim()
if(roadTripName.isNotEmpty() && roadTripName.length <= 20){
editText.text?.clear()
val roadTrip = RoadTrip(roadTripName, Date(), mutableListOf())
model.add(roadTrip)
recyclerView.adapter?.notifyDataSetChanged()
}else{
editText.error = "Le nom du voyage doit être compris entre 1 et 20 caractères."
}
}
companion object { companion object {
/** /**
* Use this factory method to create a new instance of * Use this factory method to create a new instance of

@ -0,0 +1,27 @@
package uca.baptistearthur.geocaching.viewModels
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.launch
import uca.baptistearthur.geocaching.data.RoadTripDAO
import uca.baptistearthur.geocaching.model.RoadTripEntity
class RoadTripViewModel(val dao: RoadTripDAO): ViewModel() {
fun getRoadTripById(id: Int) = dao.getRoadTripById(id) // .asLiveData() // ne marche pas -> impossible d'importer
fun getAllRoadTrips() = dao.getAllRoadTrips() // .asLiveData()
fun insertRoadTrip(r: RoadTripEntity){
viewModelScope.launch {
dao.insertRoadTrip(r)
}
}
fun deleteRoadTrip(r: RoadTripEntity){
viewModelScope.launch {
dao.deleteRoadTrip(r)
}
}
}

@ -0,0 +1,15 @@
package uca.baptistearthur.geocaching.viewModels
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelProvider
import uca.baptistearthur.geocaching.data.RoadTripDAO
class ViewModelFactory(private val dao: RoadTripDAO): ViewModelProvider.Factory{
override fun <T : ViewModel> create(modelClass: Class<T>): T {
if (modelClass.isAssignableFrom(RoadTripViewModel::class.java)){
return RoadTripViewModel(dao) as T
}
throw IllegalArgumentException("Unknown ViewModel class")
}
}

@ -15,30 +15,6 @@
android:padding="10dp" android:padding="10dp"
android:textSize="20sp"/> android:textSize="20sp"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
>
<EditText
android:id="@+id/editTextRoadTripName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="@string/textaddNewRoadTrip"
android:layout_weight="1"/>
<Button
android:id="@+id/buttonAddNewRoadTrip"
android:layout_width="50dp"
android:layout_height="wrap_content"
android:text="@string/add_roadtrip_button"
android:layout_gravity="center"
android:backgroundTint="@color/main_turquoise_200"
/>
</LinearLayout>
<androidx.recyclerview.widget.RecyclerView <androidx.recyclerview.widget.RecyclerView
android:id="@+id/recyclerViewRoadTripList" android:id="@+id/recyclerViewRoadTripList"
android:layout_width="match_parent" android:layout_width="match_parent"

Loading…
Cancel
Save