delete video notament

This commit is contained in:
Raphael
2025-03-13 12:25:56 +01:00
parent a373516f9c
commit 5da4c40bd8
7 changed files with 101 additions and 25 deletions

View File

@@ -89,7 +89,7 @@ class ProjectActivity : AppCompatActivity() {
fun fetchVideos(){
this.project?.let{
videoRepository.fetchVideosOfProject(it.id, onSuccess = { videos ->
val adapter = VideoAdapter(false, videos, null) //ImageAdapter(imageUrls)
val adapter = VideoAdapter(false, videos.toMutableList(), null) //ImageAdapter(imageUrls)
binding.videosList.layoutManager = GridLayoutManager(this.baseContext, 2, GridLayoutManager.HORIZONTAL, false)
binding.videosList.addItemDecoration(GridSpacingItemDecoration(16)) // 16px spacing
binding.videosList.adapter = adapter

View File

@@ -46,10 +46,11 @@ import java.io.FileOutputStream
class VideoAdapter(
public val withProjectNames : Boolean,
private val videos: List<Video>,
private val videos: MutableList<Video>,
private val listener: OnEmptyStateListener?
) : RecyclerView.Adapter<VideoAdapter.VideoViewHolder>() {
private var projectRepository: ProjectRepository;
private var videoRepository : VideoRepository;
init {
val retrofit = Retrofit.Builder()
.baseUrl("https://timelapse.kerboul.me/api/")
@@ -57,6 +58,7 @@ class VideoAdapter(
.build()
projectRepository = ProjectRepository(retrofit.create(ApiService::class.java))
videoRepository = VideoRepository(retrofit.create(ApiService::class.java))
listener?.onEmptyStateChanged(videos.isEmpty())
}
@@ -105,12 +107,12 @@ class VideoAdapter(
context.startActivity(intent)
}
holder.itemView.setOnLongClickListener {
showPopupMenu(it, url)
showPopupMenu(it, url, video.id)
true
}
}
private fun showPopupMenu(view: View, videoUrl: String) {
private fun showPopupMenu(view: View, videoUrl: String, id:Int) {
val popupMenu = PopupMenu(view.context, view)
popupMenu.menuInflater.inflate(R.menu.video_popup_menu, popupMenu.menu)
@@ -120,6 +122,22 @@ class VideoAdapter(
downloadVideo(view.context, videoUrl)
true
}
R.id.menu_delete -> {
videoRepository.deleteVideo(id, onSuccess = {
val v = videos.find {v -> v.id == id}
val i = videos.indexOf(v)
this.videos.removeAt(i)
Handler(Looper.getMainLooper()).post {
Toast.makeText(view.context, "Video supprimée", Toast.LENGTH_SHORT).show()
}
notifyItemRemoved(i)
}, onError = {s ->
Handler(Looper.getMainLooper()).post {
Toast.makeText(view.context, "Erreur lors de la suppression : $s", Toast.LENGTH_SHORT).show()
}
});
true
}
else -> false
}
}

View File

@@ -2,16 +2,13 @@ package com.dreamteam.timelapse
import android.os.Bundle
import android.util.Log
import android.util.TypedValue
import androidx.fragment.app.Fragment
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.recyclerview.widget.GridLayoutManager
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import com.dreamteam.timelapse.data.VideoRepository
import com.dreamteam.timelapse.databinding.FragmentProjetsBinding
import com.dreamteam.timelapse.data.ApiService
import com.dreamteam.timelapse.data.Video
import com.dreamteam.timelapse.databinding.FragmentVideosBinding
@@ -84,11 +81,11 @@ class VideoFrag : Fragment(), VideoAdapter.OnEmptyStateListener {
//binding.swipeRefreshLayout.dragDown()
Log.d("ProjetsFrag", "User has refreshed the videos list")
videoRepository.fetchVideos(
videoRepository.fetchRenderedVideos(
onSuccess = { videos ->
Log.d("ProjetsFrag", "Projets reçus : $videos")
this.videos = videos
this.videoAdapter = VideoAdapter(true, this.videos, this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
this.videoAdapter = VideoAdapter(true, this.videos.toMutableList(), this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
this.recyclerView.adapter = this.videoAdapter
// Mettre à jour le RecyclerView ou autre traitement
},
@@ -96,7 +93,7 @@ class VideoFrag : Fragment(), VideoAdapter.OnEmptyStateListener {
Log.e("ProjetsFrag prout", errorMessage)
//onEmptyStateChanged(true)
this.videos = listOf<Video>()
this.videoAdapter = VideoAdapter(true, this.videos, this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
this.videoAdapter = VideoAdapter(true, this.videos.toMutableList(), this) //TODO : Potentiel problème pour les refresh ici (update de l'adapter ou un truc du genre à voir)
this.recyclerView.adapter = this.videoAdapter
}

View File

@@ -17,6 +17,8 @@ interface ApiService {
fun getMeasurements(@Path("id") projectId: Int): Call<List<Measurement>>
@GET("videos")
fun getVideos(): Call<List<VideoDTO>>
@DELETE("videos/{id}")
fun deleteVideo(@Path("id") videoId : Int): Call<Void>
@POST("projects/")
fun createProject(@Body project: Project): Call<Confirmation>
@GET("projects/{id}/videos")

View File

@@ -3,16 +3,32 @@ package com.dreamteam.timelapse.data
import retrofit2.Call
import retrofit2.Callback
import retrofit2.Response
import java.util.Date
class VideoRepository(private val apiService: ApiService) {
fun fetchVideos(onSuccess: (List<Video>) -> Unit, onError: (String) -> Unit) {
fun fetchRenderedVideos(onSuccess: (List<Video>) -> Unit, onError: (String) -> Unit) {
apiService.getVideos().enqueue(object : Callback<List<VideoDTO>> {
override fun onResponse(call: Call<List<VideoDTO>>, response: Response<List<VideoDTO>>) {
if (response.isSuccessful) {
val videoDtos = response.body() ?: emptyList()
val videos = videoDtos.map { it.toVideo() } // Convert ugly data to clean Video objects
onSuccess(videos)
onSuccess(videos.filter { v -> v.video_file != null })
} else {
onError("Erreur serveur : ${response.code()}")
}
}
override fun onFailure(call: Call<List<VideoDTO>>, t: Throwable) {
onError("Erreur réseau : ${t.message}")
}
})
}
fun fetchUnrenderedVideos(onSuccess: (List<Video>) -> Unit, onError: (String) -> Unit) {
apiService.getVideos().enqueue(object : Callback<List<VideoDTO>> {
override fun onResponse(call: Call<List<VideoDTO>>, response: Response<List<VideoDTO>>) {
if (response.isSuccessful) {
val videoDtos = response.body() ?: emptyList()
val videos = videoDtos.map { it.toVideo() } // Convert ugly data to clean Video objects
onSuccess(videos.filter { v -> v.video_file == null })
} else {
onError("Erreur serveur : ${response.code()}")
}
@@ -40,4 +56,36 @@ class VideoRepository(private val apiService: ApiService) {
}
})
}
fun fetchUnrenderedVideosOfProject(id:Int, onSuccess: (List<Video>) -> Unit, onError: (String) -> Unit){
apiService.getVideosOfProject(id).enqueue(object : Callback<List<VideoDTO>> {
override fun onResponse(call: Call<List<VideoDTO>>, response: Response<List<VideoDTO>>) {
if (response.isSuccessful) {
val videoDtos = response.body() ?: emptyList()
val videos = videoDtos.map { it.toVideo() } // Convert ugly data to clean Video objects
onSuccess(videos.filter { v -> v.video_file == null })
} else {
onError("Erreur serveur : ${response.code()}")
}
}
override fun onFailure(call: Call<List<VideoDTO>>, t: Throwable) {
onError("Erreur réseau : ${t.message}")
}
})
}
fun deleteVideo(id:Int, onSuccess: () -> Unit, onError: (String) -> Unit){
apiService.deleteVideo(id).enqueue(object : Callback<Void> {
override fun onResponse(call: Call<Void>, response: Response<Void>) {
if (response.isSuccessful) {
onSuccess()
} else {
onError("Erreur serveur : ${response.code()}")
}
}
override fun onFailure(call: Call<Void>, t: Throwable) {
onError("Erreur réseau : ${t.message}")
}
})
}}

View File

@@ -18,18 +18,25 @@
tools:ignore="MissingConstraints"
app:layout_constraintEnd_toEndOf="parent"
>
<com.google.android.material.appbar.CollapsingToolbarLayout
android:id="@+id/collapsingToolbar"
android:layout_width="match_parent"
android:layout_height="100sp"
app:layout_scrollFlags="scroll|exitUntilCollapsed"
app:expandedTitleTextAppearance="@style/TextAppearance.AppCompat.Large"
app:collapsedTitleTextAppearance="@style/TextAppearance.AppCompat.Small">
<TextView
android:id="@+id/project_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:padding="10dp"
android:text="Nom du projet"
android:textSize="20sp"
android:textStyle="bold"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
android:textStyle="bold" />
</com.google.android.material.appbar.CollapsingToolbarLayout>
</com.google.android.material.appbar.AppBarLayout>

View File

@@ -6,4 +6,8 @@
android:id="@+id/menu_download"
android:title="Télécharger"
android:icon="@android:drawable/ic_menu_save" />
<item
android:id="@+id/menu_delete"
android:title="Supprimer"
android:icon="@android:drawable/ic_delete" />
</menu>