supression projet
This commit is contained in:
@@ -1,5 +1,6 @@
|
|||||||
package com.dreamteam.timelapse
|
package com.dreamteam.timelapse
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.util.Log
|
import android.util.Log
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
@@ -7,14 +8,28 @@ import android.view.View
|
|||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.ImageView
|
import android.widget.ImageView
|
||||||
import android.widget.TextView
|
import android.widget.TextView
|
||||||
|
import android.widget.Toast
|
||||||
|
import androidx.appcompat.app.AlertDialog
|
||||||
import androidx.core.content.ContextCompat
|
import androidx.core.content.ContextCompat
|
||||||
import androidx.core.graphics.drawable.DrawableCompat
|
import androidx.core.graphics.drawable.DrawableCompat
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.bumptech.glide.Glide
|
import com.bumptech.glide.Glide
|
||||||
|
import com.dreamteam.timelapse.data.ApiService
|
||||||
import com.dreamteam.timelapse.data.Project
|
import com.dreamteam.timelapse.data.Project
|
||||||
|
import com.dreamteam.timelapse.data.ProjectRepository
|
||||||
|
import com.google.android.material.snackbar.Snackbar
|
||||||
|
import retrofit2.Retrofit
|
||||||
|
import retrofit2.converter.gson.GsonConverterFactory
|
||||||
|
|
||||||
class ProjectAdapter(private val projects: List<Project>, private val listener: OnEmptyStateListener) : RecyclerView.Adapter<ProjectAdapter.ProjectViewHolder>() {
|
class ProjectAdapter(private val projects: MutableList<Project>, private val listener: OnEmptyStateListener) : RecyclerView.Adapter<ProjectAdapter.ProjectViewHolder>() {
|
||||||
|
val projectRepository : ProjectRepository;
|
||||||
init{
|
init{
|
||||||
|
val retrofit = Retrofit.Builder()
|
||||||
|
.baseUrl("https://timelapse.kerboul.me/api/")
|
||||||
|
.addConverterFactory(GsonConverterFactory.create())
|
||||||
|
.build()
|
||||||
|
|
||||||
|
projectRepository = ProjectRepository(retrofit.create(ApiService::class.java))
|
||||||
listener.onEmptyStateChanged(projects.isEmpty())
|
listener.onEmptyStateChanged(projects.isEmpty())
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -57,7 +72,32 @@ class ProjectAdapter(private val projects: List<Project>, private val listener:
|
|||||||
context.startActivity(intent)
|
context.startActivity(intent)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
fun removeItem(position: Int, context: Context, v : View) {
|
||||||
|
val builder = AlertDialog.Builder(context)
|
||||||
|
val dialog = builder.setTitle("Confirm Deletion")
|
||||||
|
.setMessage("Voulez vous supprimer ce projet ?")
|
||||||
|
.setPositiveButton("Supprimer") { dialog, _ ->
|
||||||
|
projectRepository.deleteProject(projects[position].id, onSuccess = {
|
||||||
|
val name = projects[position].name
|
||||||
|
projects.removeAt(position)
|
||||||
|
notifyItemRemoved(position)
|
||||||
|
Snackbar.make(v.rootView, "$name supprimé avec succès !", Snackbar.LENGTH_SHORT).show()
|
||||||
|
}, onError = {s ->
|
||||||
|
dialog.dismiss()
|
||||||
|
notifyItemChanged(position)
|
||||||
|
Snackbar.make(v.rootView, "Error while trying to delete ${projects[position].name} : $s", Snackbar.LENGTH_SHORT).show()
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
.setNegativeButton("Annuler") { dialog, _ ->
|
||||||
|
dialog.dismiss()
|
||||||
|
notifyItemChanged(position) // Reset swipe animation
|
||||||
|
}
|
||||||
|
.show()
|
||||||
|
dialog.setOnDismissListener {
|
||||||
|
notifyItemChanged(position) // Ensure the card resets when dialog closes
|
||||||
|
}
|
||||||
|
}
|
||||||
override fun getItemCount(): Int {
|
override fun getItemCount(): Int {
|
||||||
return projects.size
|
return projects.size
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,8 @@
|
|||||||
package com.dreamteam.timelapse
|
package com.dreamteam.timelapse
|
||||||
|
|
||||||
|
import android.graphics.Canvas
|
||||||
|
import android.graphics.Color
|
||||||
|
import android.graphics.drawable.ColorDrawable
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.util.Log
|
import android.util.Log
|
||||||
import android.util.TypedValue
|
import android.util.TypedValue
|
||||||
@@ -8,7 +11,9 @@ import android.view.LayoutInflater
|
|||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.GridLayout
|
import android.widget.GridLayout
|
||||||
|
import androidx.core.content.ContextCompat
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
import androidx.recyclerview.widget.GridLayoutManager
|
||||||
|
import androidx.recyclerview.widget.ItemTouchHelper
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.dreamteam.timelapse.data.ProjectRepository
|
import com.dreamteam.timelapse.data.ProjectRepository
|
||||||
@@ -72,6 +77,48 @@ class ProjetsFrag : Fragment(), ProjectAdapter.OnEmptyStateListener {
|
|||||||
recyclerView = binding.recyclerView // view.findViewById(R.id.recyclerView)
|
recyclerView = binding.recyclerView // view.findViewById(R.id.recyclerView)
|
||||||
recyclerView.layoutManager = LinearLayoutManager(context)
|
recyclerView.layoutManager = LinearLayoutManager(context)
|
||||||
|
|
||||||
|
val itemTouchHelper = ItemTouchHelper(object : ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.RIGHT) {
|
||||||
|
private val background = ColorDrawable(Color.RED) // Red background
|
||||||
|
private val deleteIcon = context?.let { ContextCompat.getDrawable(it, R.drawable.ic_delete) }
|
||||||
|
override fun onMove(recyclerView: RecyclerView, viewHolder: RecyclerView.ViewHolder, target: RecyclerView.ViewHolder): Boolean {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onSwiped(viewHolder: RecyclerView.ViewHolder, direction: Int) {
|
||||||
|
val position = viewHolder.adapterPosition
|
||||||
|
context?.let { (recyclerView.adapter as ProjectAdapter).removeItem(position, it, viewHolder.itemView) }
|
||||||
|
}
|
||||||
|
override fun onChildDraw(
|
||||||
|
c: Canvas, recyclerView: RecyclerView, viewHolder: RecyclerView.ViewHolder,
|
||||||
|
dX: Float, dY: Float, actionState: Int, isCurrentlyActive: Boolean
|
||||||
|
) {
|
||||||
|
val itemView = viewHolder.itemView
|
||||||
|
val backgroundCornerOffset = 20 // Slight offset for smooth animation
|
||||||
|
|
||||||
|
background.setBounds(
|
||||||
|
itemView.left,
|
||||||
|
itemView.top,
|
||||||
|
itemView.left + dX.toInt() - backgroundCornerOffset,
|
||||||
|
itemView.bottom
|
||||||
|
)
|
||||||
|
//background.draw(c)
|
||||||
|
|
||||||
|
// Position the delete icon
|
||||||
|
val iconMargin = (itemView.height - deleteIcon!!.intrinsicHeight) / 2
|
||||||
|
val iconRight = itemView.left + iconMargin + deleteIcon.intrinsicWidth
|
||||||
|
val iconLeft = itemView.left + iconMargin
|
||||||
|
val iconTop = itemView.top + (itemView.height - deleteIcon.intrinsicHeight) / 2
|
||||||
|
val iconBottom = iconTop + deleteIcon.intrinsicHeight
|
||||||
|
|
||||||
|
deleteIcon.setBounds(iconLeft, iconTop, iconRight, iconBottom)
|
||||||
|
deleteIcon.draw(c)
|
||||||
|
|
||||||
|
|
||||||
|
super.onChildDraw(c, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
itemTouchHelper.attachToRecyclerView(recyclerView)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun fetchProjects() {
|
private fun fetchProjects() {
|
||||||
@@ -86,7 +133,7 @@ class ProjetsFrag : Fragment(), ProjectAdapter.OnEmptyStateListener {
|
|||||||
onSuccess = { projects ->
|
onSuccess = { projects ->
|
||||||
Log.d("ProjetsFrag", "Projets reçus : $projects")
|
Log.d("ProjetsFrag", "Projets reçus : $projects")
|
||||||
this.projects = projects
|
this.projects = projects
|
||||||
this.projectAdapter = ProjectAdapter(this.projects, this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
|
this.projectAdapter = ProjectAdapter(this.projects.toMutableList(), this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
|
||||||
this.recyclerView.adapter = this.projectAdapter
|
this.recyclerView.adapter = this.projectAdapter
|
||||||
// Mettre à jour le RecyclerView ou autre traitement
|
// Mettre à jour le RecyclerView ou autre traitement
|
||||||
},
|
},
|
||||||
@@ -94,7 +141,7 @@ class ProjetsFrag : Fragment(), ProjectAdapter.OnEmptyStateListener {
|
|||||||
Log.e("ProjetsFrag prout", errorMessage)
|
Log.e("ProjetsFrag prout", errorMessage)
|
||||||
//onEmptyStateChanged(true)
|
//onEmptyStateChanged(true)
|
||||||
this.projects = listOf<Project>()
|
this.projects = listOf<Project>()
|
||||||
this.projectAdapter = ProjectAdapter(this.projects, this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
|
this.projectAdapter = ProjectAdapter(this.projects.toMutableList(), this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
|
||||||
this.recyclerView.adapter = this.projectAdapter
|
this.recyclerView.adapter = this.projectAdapter
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package com.dreamteam.timelapse.data
|
package com.dreamteam.timelapse.data
|
||||||
import retrofit2.Call
|
import retrofit2.Call
|
||||||
import retrofit2.http.Body
|
import retrofit2.http.Body
|
||||||
|
import retrofit2.http.DELETE
|
||||||
import retrofit2.http.Field
|
import retrofit2.http.Field
|
||||||
import retrofit2.http.FormUrlEncoded
|
import retrofit2.http.FormUrlEncoded
|
||||||
import retrofit2.http.GET
|
import retrofit2.http.GET
|
||||||
@@ -20,4 +21,6 @@ interface ApiService {
|
|||||||
fun createProject(@Body project: Project): Call<Confirmation>
|
fun createProject(@Body project: Project): Call<Confirmation>
|
||||||
@GET("projects/{id}/videos")
|
@GET("projects/{id}/videos")
|
||||||
fun getVideosOfProject(@Path("id") projectId:Int): Call<List<VideoDTO>>
|
fun getVideosOfProject(@Path("id") projectId:Int): Call<List<VideoDTO>>
|
||||||
|
@DELETE("projects/{id}")
|
||||||
|
fun deleteProject(@Path("id") projectId:Int) : Call<Void>
|
||||||
}
|
}
|
||||||
@@ -82,4 +82,21 @@ class ProjectRepository(private val apiService: ApiService) {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun deleteProject(id : Int, onSuccess: ()->Unit, onError: (String) -> Unit){
|
||||||
|
val call = apiService.deleteProject(id)
|
||||||
|
call.enqueue(object : Callback<Void> {
|
||||||
|
override fun onResponse(call: Call<Void>, response: Response<Void>) {
|
||||||
|
if (response.isSuccessful) {
|
||||||
|
onSuccess()
|
||||||
|
} else {
|
||||||
|
onError("Erreur : ${response.code()}")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onFailure(call: Call<Void>, t: Throwable) {
|
||||||
|
onError("Échec de l'appel API : ${t.message}")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
11
app/src/main/res/drawable/ic_delete.xml
Normal file
11
app/src/main/res/drawable/ic_delete.xml
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:width="24dp"
|
||||||
|
android:height="24dp"
|
||||||
|
android:viewportWidth="24"
|
||||||
|
android:viewportHeight="24">
|
||||||
|
|
||||||
|
<path
|
||||||
|
android:fillColor="@android:color/white"
|
||||||
|
android:pathData="M6,19c0,1.1 0.9,2 2,2h8c1.1,0 2,-0.9 2,-2V7H6v12M19,4h-3.5l-1,-1h-5l-1,1H5v2h14V4z" />
|
||||||
|
</vector>
|
||||||
@@ -22,6 +22,10 @@
|
|||||||
android:clipChildren="false"
|
android:clipChildren="false"
|
||||||
android:clipToPadding="false">
|
android:clipToPadding="false">
|
||||||
|
|
||||||
|
<RelativeLayout
|
||||||
|
android:id="@+id/relativeLayout"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent">
|
||||||
|
|
||||||
<androidx.constraintlayout.widget.ConstraintLayout
|
<androidx.constraintlayout.widget.ConstraintLayout
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
@@ -67,6 +71,7 @@
|
|||||||
<!-- Ajouter d'autres vues comme une image ou une description -->
|
<!-- Ajouter d'autres vues comme une image ou une description -->
|
||||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||||
|
|
||||||
|
</RelativeLayout>
|
||||||
</androidx.cardview.widget.CardView>
|
</androidx.cardview.widget.CardView>
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user