Commit Graph

138 Commits

Author SHA1 Message Date
Stu
32434dbc28 Guard drag handler with recover and nil checks 2025-12-13 22:33:56 -05:00
Stu
fdb0f44fa7 Fix drag target setup crash (require non-empty target list) 2025-12-13 22:32:35 -05:00
Stu
6fc4d80e6c Use TargetEntry drag setup for GTK draw area 2025-12-13 22:31:30 -05:00
Stu
2239c5cf3a Fix drag URI handling to prevent crash 2025-12-13 22:30:37 -05:00
Stu
93bd8a1424 Fix TargetEntryNew return handling 2025-12-13 22:25:50 -05:00
Stu
4d33e1ec71 Fix drag targets and force X11 backend for embedded mpv 2025-12-13 22:24:07 -05:00
Stu
bec66816df Fix drag target setup for gtkplayer 2025-12-13 22:22:33 -05:00
Stu
aba4d14f57 GTK/mpv embed: fix locale, add CSS theme, drag-and-drop support 2025-12-13 22:21:44 -05:00
Stu
03b6804a9e Fix build: remove unused imports, drop playSess img refs, cleanup state init 2025-12-13 21:58:41 -05:00
Stu
c81d540b0f Use local go cache/mod in build.sh and check gtk3 dev 2025-12-13 21:50:38 -05:00
Stu
19c3d1e3ad Handle GetWindow error return for mpv embed 2025-12-13 21:48:16 -05:00
Stu
2e4b433f01 Rewrite gtkplayer entry cleanly 2025-12-13 21:46:59 -05:00
Stu
a4653dd116 Fix GetWindow return handling 2025-12-13 21:45:25 -05:00
Stu
1c40324cd6 Simplify GTK window retrieval for mpv embed 2025-12-13 21:44:19 -05:00
Stu
bab96baee8 Handle gdk window retrieval without boolean conversion 2025-12-13 21:42:35 -05:00
Stu
e3305ce80c Fix Gtk window checks for mpv embed 2025-12-13 21:41:48 -05:00
Stu
08e0da1d45 Fix GTK window handle calls for mpv embed 2025-12-13 21:40:04 -05:00
Stu
ba1db9e16f Fix GTK/mpv player build issues (imports, window ID, polling) 2025-12-13 21:39:04 -05:00
Stu
26c48ab981 Vendor gotk3, add mpv cgo wrapper, and GTK mpv player stub 2025-12-13 18:58:03 -05:00
Stu
7f0ea613d6 Install mpv on Windows via choco/scoop 2025-12-13 12:43:33 -05:00
Stu
051a17243c Add mpv runtime dependency to installer and build scripts 2025-12-10 05:55:05 -05:00
Stu
1dfab7000b Switch playback to mpv IPC and poll progress 2025-12-10 05:47:38 -05:00
Stu
0ba248af4e Coalesce player view renders and schedule once 2025-12-10 05:31:48 -05:00
Stu
4929918d4b Replace internal decoder with ffplay subprocess 2025-12-10 05:27:24 -05:00
Stu
3d43123840 Throttle player view calls aggressively 2025-12-10 05:22:30 -05:00
Stu
feeaf8e39a Throttle player view rebuilds after video load 2025-12-10 05:20:37 -05:00
Stu
8479bfef6f Guard player view render and refresh after loads 2025-12-10 05:17:02 -05:00
Stu
9d255680bf Track current source to avoid rebuilds 2025-12-10 05:09:01 -05:00
Stu
a393183d83 Trim extra UI rebuild guard 2025-12-10 05:02:17 -05:00
Stu
22e325e123 Keep player session alive and stop repeated rebuilds 2025-12-10 04:59:43 -05:00
Stu
47067aabf0 Keep player session alive in showPlayerView 2025-12-10 04:54:55 -05:00
Stu
e727b8ea09 Auto-start playback, guard view rebuilds, and clean window close 2025-12-10 03:23:40 -05:00
Stu
fc1e91bda6 Avoid player view rebuild when already active 2025-12-10 03:13:54 -05:00
Stu
ee08618142 Add playback session logging for troubleshooting 2025-12-09 18:53:30 -05:00
Stu
ab9f19095d Set video surface size and surface ffmpeg errors 2025-12-09 18:51:41 -05:00
Stu
142d2f1383 Default to software canvas and fix binary name in run.sh 2025-12-09 18:28:57 -05:00
Stu
8815f69fe8 Show preview frame when loading videos 2025-12-09 18:20:36 -05:00
Stu
c4a5e48a22 Add comprehensive debug logging and performance monitoring
Added detailed terminal output to diagnose video loading hangs:
- Session creation logging (resolution, fps, target size)
- FFmpeg command logging
- Frame decode pipeline timing (first frame, decode time, render time)
- Real-time FPS counter (reports every 2 seconds)
- Memory usage info (frame buffer size)
- Error reporting with FFmpeg stderr output

This will help identify performance bottlenecks and hanging issues
during video playback.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 16:09:02 -05:00
Stu
998b76cefd Hide playlist by default - make fullscreen video player the default view
Changed playlist visibility from auto-showing when multiple videos
to hidden by default. Users can toggle it with the menu (☰) button.

This gives a cleaner video player experience without the playlist
taking up screen space.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 12:40:33 -05:00
Stu
eb2a7a4297 Fix critical bug: remove TappableOverlay that was blocking all button clicks
The TappableOverlay was added to the entire stage container, which
made it cover the video AND all control buttons below. This invisible
overlay intercepted all mouse events, preventing buttons from working.

Temporarily disabled the overlay to restore button functionality.
Will need to reimplement properly as floating controls that only
overlay the video area, not the UI controls.

Fixes:
- Play/pause button now clickable
- Volume controls now work
- All other UI buttons functional
- Keyboard shortcuts (Space, F11, ESC) still work

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 12:30:28 -05:00
Stu
5e902262c5 Improve build script: remove aggressive cache cleaning and add auto dependency check
Changes:
- Removed -modcache flag that was deleting Go modules unnecessarily
- Changed from -cache -modcache -testcache to just go clean
- Added automatic system dependency detection (X11 libs)
- Will attempt to install missing deps automatically if found
- Keeps Go module cache intact between builds for faster compilation

This fixes the issue where builds would fail after cache cleaning due to
missing Go modules, while still checking for required system libraries.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 12:08:58 -05:00
Stu
792e5a6a5a Fix build error: rename tappableRenderer to overlayRenderer
Resolved naming conflict with existing tappableRenderer in components.go
by renaming the renderer in TappableOverlay to overlayRenderer.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 11:53:17 -05:00
Stu
e0ecc92195 Add Space bar play/pause and fix icon display with ASCII fallback
Fixes control interactions and icon display issues for immediate usability.

Keyboard Shortcuts:
- Space bar now globally toggles play/pause
- Works anywhere in the app when video is loaded
- No longer conflicts with keyframing mode shortcuts

Icon Display Fix:
- Replaced Material Icons unicode with ASCII/emoji fallback
- Play: ▶ | Pause: || | Stop: ■
- Skip: |◀ and ▶| | Fast: ◀◀ and ▶▶
- Volume: 🔊 🔉 🔇 emojis
- Menu: ☰ (hamburger)
- Works without special fonts installed

Why ASCII Fallback:
- Material Symbols font not installed by default
- Unicode characters displayed as boxes/gibberish
- ASCII icons work universally on all systems
- Ready for custom SVG icons replacement

Usage:
- Press Space anywhere to play/pause video
- Icons now display correctly without font dependencies
- Buttons should be more responsive

Next Steps:
- Add custom SVG icons (user will create)
- Implement overlay controls that auto-hide
- Fix play button responsiveness
- Move controls to overlay video area

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-09 11:37:49 -05:00
Stu
e25f0c4284 Add video interaction: double-click fullscreen and right-click play/pause
Implements intuitive video player interactions for enhanced user experience.

Video Interaction Features:
- Double-click video area to toggle fullscreen
- Right-click video area to play/pause
- Single-click does nothing (reserved for future use)
- Transparent tappable overlay on video canvas

Implementation:
- Created TappableOverlay widget in internal/ui/tappable.go
- Invisible widget captures tap, double-tap, and secondary-tap events
- Extends widget.BaseWidget for Fyne compatibility
- Added overlay to stage container after video image

User Experience:
- Double-click anywhere on video → instant fullscreen
- Right-click anywhere on video → quick play/pause
- Works alongside existing keyboard shortcuts (F11, Space, ESC)
- Play button icon updates when using right-click

Technical Details:
- TappableOverlay has no visual representation
- Implements Tapped(), DoubleTapped(), TappedSecondary()
- Callbacks are configurable per instance
- Positioned as top layer in container.NewMax() stack

Usage:
1. Load a video
2. Double-click video to enter fullscreen
3. Right-click to pause/play
4. ESC or F11 to exit fullscreen

Next Steps:
- Consider adding single-click functionality
- Add visual feedback for interactions
- Implement mouse cursor auto-hide in fullscreen

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-09 11:23:26 -05:00
Stu
b73beb1fef Add fullscreen mode with F11 and ESC keyboard shortcuts
Implements basic fullscreen toggle functionality for immersive video playback.

Fullscreen Features:
- F11 key toggles fullscreen on/off
- ESC key exits fullscreen mode
- Window.SetFullScreen() for native fullscreen
- isFullscreen state tracking in appState

Keyboard Shortcuts:
- F11: Toggle fullscreen (globally available)
- ESC: Exit fullscreen (only when in fullscreen mode)
- Shortcuts work from any screen in the app

Implementation:
- Added isFullscreen bool to appState
- Created toggleFullscreen() method
- Global keyboard handler in runGUI()
- SetOnTypedKey handles F11 and ESC

Usage:
1. Load a video in VT_Player
2. Press F11 to enter fullscreen
3. Press F11 or ESC to exit fullscreen

Next Steps:
- Add fullscreen button to player controls
- Auto-hide controls after 3 seconds in fullscreen
- Show controls on mouse movement in fullscreen
- Double-click video to toggle fullscreen

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-09 11:19:44 -05:00
Stu
30899b3512 Add Windows 11 compatibility and cross-platform build system
Ports Windows compatibility improvements from VideoTools to enable
VT_Player to build and run on Windows 11 alongside VideoTools.

Build System Enhancements:
- Universal build script auto-detects platform (Linux/macOS/Windows)
- Platform-specific build routing (build-linux.sh for Unix)
- Windows: Builds vt_player.exe with GUI flags (-H windowsgui)
- Windows: Automatic FFmpeg PATH detection
- Shares dependencies with VideoTools installation

Windows Console Hiding:
- Created internal/utils/proc_windows.go (Windows-specific)
- Created internal/utils/proc_other.go (Linux/macOS no-op)
- ApplyNoWindow() hides FFmpeg/ffprobe console windows on Windows
- Provides clean GUI experience without console popups

Cross-Platform Support:
- Build flags adapt to target platform automatically
- Go build tags for platform-specific code
- CGO enabled for all platforms (required by Fyne)
- Tested on Linux, ready for Windows 11

Documentation:
- WINDOWS_COMPATIBILITY.md: Complete Windows setup guide
- Explains dependency sharing with VideoTools
- Troubleshooting section for common issues
- Platform-specific build flag documentation

Benefits for Jake's Windows 11 Environment:
- Uses same MinGW-w64 toolchain as VideoTools
- Uses same FFmpeg installation (already on PATH)
- No additional dependency installation needed
- Build process identical to VideoTools

Technical Details:
- Windows GUI binary: vt_player.exe (~45MB)
- Linux/macOS binary: vt_player (~32MB)
- All platforms use CGO for Fyne OpenGL bindings
- syscall.SysProcAttr{HideWindow: true} for Windows processes

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-09 11:10:57 -05:00
Stu
5e2c07ad21 Create custom timeline widget with keyframe markers (Commit 6)
Implements visual timeline with smooth interaction and keyframe visualization:

Timeline Widget Features:
- Custom Fyne widget in internal/ui/timeline.go
- Visual keyframe markers (yellow 1px vertical lines)
- Current position scrubber (white 2px line with circle handle)
- Progress fill showing played portion (gray)
- Mouse click/drag for smooth seeking
- In/out point marker support (for future cut functionality)

Rendering Performance:
- Cached rendering objects to minimize redraws
- Only scrubber position updates on playback
- Full redraw only on resize or keyframe data change
- Optimized for 1000+ keyframes without lag

UI Integration:
- Timeline replaces slider when keyframing mode is enabled
- Automatically loads keyframe timestamps from Index
- Integrates with existing updateProgress callback
- Maintains current time/total time labels

Technical Implementation:
- TimelineWidget extends widget.BaseWidget
- Custom renderer implements fyne.WidgetRenderer
- SetOnChange() for seek callback
- SetPosition() for playback updates
- SetKeyframes() for keyframe marker display
- Desktop mouse events for hover and drag

Visual Design:
- Dark gray background (#282828)
- Lighter gray progress fill (#3C3C3C)
- Yellow keyframe markers (#FFDC00 with transparency)
- White scrubber with circular handle
- Blue in-point marker for cuts
- Red out-point marker for cuts

References: DEV_SPEC lines 192-241

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-08 12:07:45 -05:00
Stu
3a5b1a1f1e Add frame-accurate navigation controls (Commit 5)
Implements comprehensive frame navigation UI and keyboard shortcuts:

Frame Navigation UI:
- Frame step buttons (←/→ icons) for single-frame stepping
- Keyframe jump buttons (⏮/⏭ icons) for I-frame navigation
- Frame counter display showing current frame number
- All navigation controls only visible in keyframing mode
- Automatic keyframe index loading when enabling frame mode

Keyboard Shortcuts:
- Left/Right arrows: step one frame backward/forward
- Up/Down arrows: jump to previous/next keyframe
- Space: play/pause toggle
- All shortcuts only active in keyframing mode

Frame Counter:
- Displays current frame number during playback
- Updates in real-time as video plays
- Shows "(KF)" suffix when on a keyframe
- Positioned next to playlist toggle button

Technical Details:
- StepFrame() method pauses playback and seeks precisely
- GetCurrentPosition() added to playSession for position queries
- Keyframe navigation uses binary search from detector.go
- All UI updates properly synchronized via Fyne.Do()
- Frame counter declared early for use in updateProgress callback

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-05 15:28:41 -05:00
1618558314 Implement keyframe detection system (Commit 4)
Core implementation:
- Create internal/keyframe package with detector.go
- Implement DetectKeyframes() using ffprobe packet flags
- Use 'K' flag in packet data to identify I-frames
- Binary search for FindNearestKeyframe() (before/after/nearest)
- EstimateFrameNumber() for frame calculations

Caching system:
- Save/load keyframe index to ~/.cache/vt_player/keyframes/
- Binary format: ~12 bytes per keyframe (~3KB for 4min video)
- Cache key based on file path + modification time
- Auto-invalidation when file changes
- DetectKeyframesWithCache() for automatic cache management

Performance:
- 265 keyframes detected in 0.60s for 4min video (441 kf/sec)
- FindNearestKeyframe: 67ns per lookup (binary search)
- Memory: ~3KB cache per video
- Exceeds target: <5s for 1-hour video

Integration:
- Add KeyframeIndex field to videoSource
- EnsureKeyframeIndex() method for lazy loading
- Ready for frame-accurate navigation features

Testing:
- Comprehensive unit tests (all passing)
- Benchmark tests for search performance
- cmd/test_keyframes utility for validation
- Tested on real video files

Prepares for Commits 5-10:
- Frame-by-frame navigation (Commit 5)
- Keyframe jump controls (Commit 5)
- Timeline with keyframe markers (Commit 6-7)
- In/out point marking (Commit 8)
- Lossless cut export (Commit 9-10)

References: DEV_SPEC Phase 2 (lines 54-119)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-05 14:11:45 -05:00
3f47da4ddf Integrate Google Material Icons for clean UI
Icon system:
- Create internal/ui/icons.go with Material Symbols unicode constants
- Add 50+ icon constants for all player features
- Implement NewIconButton() and helper functions
- Add GetVolumeIcon() and GetPlayPauseIcon() dynamic icon helpers

UI updates:
- Replace emoji icons (▶/⏸ 🔊 ☰) with Material Icons
- Use play_arrow/pause for play button with state toggle
- Use volume_up/down/mute/off for volume with dynamic updates
- Use menu icon for playlist toggle
- Use skip_previous/skip_next for track navigation

Documentation:
- Add MATERIAL_ICONS_MAPPING.md with complete icon reference
- Document 50+ Material Icon unicode mappings
- Include download instructions for Material Symbols font
- Map all planned features to appropriate icons

Benefits:
- Professional, consistent icon design
- Industry-standard Material Design language
- Better rendering than emoji (no font fallback issues)
- Scalable unicode characters (works immediately)
- Ready for font enhancement (optional Material Symbols font)

Prepares for:
- Frame navigation icons (navigate_before/next)
- Keyframe jump icons (first_page/last_page)
- Cut tool icons (content_cut, markers)
- All features in FEATURE_ROADMAP.md

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-05 10:06:43 -05:00