diff --git a/TODO.md b/TODO.md index 372a72c..423015e 100644 --- a/TODO.md +++ b/TODO.md @@ -1,9 +1,33 @@ -# TODO: Convert Edit Video Page to Modal +# TODO: Add Delete and Edit options to channel video 3-dot menu -## Steps: -- [x] 1. Create edit-video-modal.blade.php partial with cute design -- [x] 2. Modify VideoController's edit() method to support AJAX -- [x] 3. Modify VideoController's update() method for AJAX response -- [x] 4. Add Edit button and modal include to video show page -- [x] 5. Test the modal functionality +## Task +In `https://video.innovator.bh/channel/2`, the 3-dot menu must have Delete and Edit options. +## Requirements +- `/videos` (public area) - NO edit/delete options +- `/channel/{id}` (user channel page) - Edit and Delete options for the channel owner only + +## Plan + +### Step 1: Modify app.blade.php +- Add include for edit-video-modal partial + +### Step 2: Modify channel.blade.php +- Add conditional check for video ownership +- Add Edit button that calls openEditVideoModal() +- Add Delete button with confirmation +- Add separator before owner-only options + +### Step 3: Add JavaScript for delete functionality +- Add deleteVideo() function with AJAX call + +### Step 4: Update VideoController +- Add ownership check to destroy method +- Return JSON for AJAX requests + +## Status: Completed + +## Files Modified +1. `resources/views/layouts/app.blade.php` - Added edit-video-modal include +2. `resources/views/user/channel.blade.php` - Added Edit/Delete in dropdown +3. `app/Http/Controllers/VideoController.php` - Updated destroy method diff --git a/app/Http/Controllers/VideoController.php b/app/Http/Controllers/VideoController.php index 26bd8dc..bd519c2 100644 --- a/app/Http/Controllers/VideoController.php +++ b/app/Http/Controllers/VideoController.php @@ -274,13 +274,29 @@ class VideoController extends Controller return redirect()->route('videos.show', $video)->with('success', 'Video updated!'); } - public function destroy(Video $video) + public function destroy(Request $request, Video $video) { + // Check if user owns the video + if (Auth::id() !== $video->user_id) { + abort(403, 'You do not have permission to delete this video.'); + } + + $videoTitle = $video->title; + Storage::delete('public/videos/' . $video->filename); if ($video->thumbnail) { Storage::delete('public/thumbnails/' . $video->thumbnail); } $video->delete(); + + // Return JSON for AJAX requests + if ($request->expectsJson() || $request->ajax()) { + return response()->json([ + 'success' => true, + 'message' => 'Video deleted successfully!', + ]); + } + return redirect()->route('videos.index')->with('success', 'Video deleted!'); } @@ -347,4 +363,22 @@ class VideoController extends Controller exit; } } + + public function download(Video $video) + { + // Check if user can view this video + if (!$video->canView(Auth::user())) { + abort(404, 'Video not found'); + } + + $path = storage_path('app/public/videos/' . $video->filename); + + if (!file_exists($path)) { + abort(404, 'Video file not found'); + } + + $filename = $video->title . '.' . pathinfo($video->filename, PATHINFO_EXTENSION); + + return response()->download($path, $filename); + } } diff --git a/resources/views/layouts/app.blade.php b/resources/views/layouts/app.blade.php index 6af5116..8720ba4 100644 --- a/resources/views/layouts/app.blade.php +++ b/resources/views/layouts/app.blade.php @@ -345,6 +345,7 @@ @auth @include('layouts.partials.upload-modal') + @include('layouts.partials.edit-video-modal') @endauth diff --git a/resources/views/user/channel.blade.php b/resources/views/user/channel.blade.php index 710464c..64a6e09 100644 --- a/resources/views/user/channel.blade.php +++ b/resources/views/user/channel.blade.php @@ -317,6 +317,41 @@
@@ -367,6 +409,32 @@ function stopVideo(card) { video.classList.remove('active'); } } + +function deleteVideo(videoId, videoTitle) { + if (confirm('Are you sure you want to delete "' + videoTitle + '"? This action cannot be undone.')) { + fetch(`/videos/${videoId}`, { + method: 'DELETE', + headers: { + 'X-CSRF-TOKEN': '{{ csrf_token() }}', + 'Accept': 'application/json', + 'X-Requested-With': 'XMLHttpRequest' + } + }) + .then(response => response.json()) + .then(data => { + if (data.success || data.redirect) { + // Reload the page to show updated video list + window.location.reload(); + } else { + alert('Failed to delete video. Please try again.'); + } + }) + .catch(error => { + console.error('Error:', error); + alert('Failed to delete video. Please try again.'); + }); + } +} @endsection diff --git a/resources/views/videos/index.blade.php b/resources/views/videos/index.blade.php index 956d818..8498e08 100644 --- a/resources/views/videos/index.blade.php +++ b/resources/views/videos/index.blade.php @@ -269,6 +269,26 @@ diff --git a/resources/views/videos/show.blade.php b/resources/views/videos/show.blade.php index f5f4818..74ca297 100644 --- a/resources/views/videos/show.blade.php +++ b/resources/views/videos/show.blade.php @@ -187,8 +187,8 @@