-
Notifications
You must be signed in to change notification settings - Fork 3.5k
feat(android): add audio track selection for ExoPlayer #10312
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Code Review
The pull request implements audio track selection for ExoPlayer in the Android video player. It adds getAudioTracks() and selectAudioTrack() methods, updates the Pigeon definitions, modifies the ExoPlayerEventListener to handle buffering states, and includes corresponding tests. The changes also involve removing Kotlin-related configurations from build.gradle and updating the CHANGELOG.md file.
| private void setBuffering(boolean buffering) { | ||
| if (isBuffering == buffering) { | ||
| return; | ||
| } | ||
| isBuffering = buffering; | ||
| if (buffering) { | ||
| events.onBufferingStart(); | ||
| } else { | ||
| events.onBufferingEnd(); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This method encapsulates the logic for setting the buffering state and invoking the corresponding callbacks. It checks if the buffering state has changed before invoking the callbacks, preventing redundant calls. This is a good practice for optimizing performance and avoiding unnecessary UI updates. However, there is no error handling for the callback invocations. Consider adding try-catch blocks around the callback invocations to handle potential exceptions and prevent crashes.
| public @NonNull Messages.PlaybackState getPlaybackState() { | ||
| return new Messages.PlaybackState.Builder() | ||
| .setPlayPosition(exoPlayer.getCurrentPosition()) | ||
| .setBufferPosition(exoPlayer.getBufferedPosition()) | ||
| .build(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The getPlaybackState method creates and returns a PlaybackState object with the current play and buffer positions. This is a good approach for encapsulating the playback state and providing a consistent way to access it. However, the method does not handle potential exceptions that might occur when accessing the ExoPlayer's state. Consider adding error handling to gracefully handle exceptions and prevent crashes.
| public void selectAudioTrack(@NonNull String trackId) { | ||
| if (trackSelector == null) { | ||
| Log.w("VideoPlayer", "Cannot select audio track: track selector is null"); | ||
| return; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's important to handle the case where trackSelector is null to prevent NullPointerException. Logging a warning is a good approach, but consider throwing an exception or returning an error code to the Flutter side to indicate that audio track selection is not supported in this case. This would allow the Flutter app to handle the situation gracefully and provide feedback to the user.
| trackSelector.setParameters( | ||
| trackSelector.buildUponParameters().setOverrideForType(override).build()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| Map<String, Object> event = new HashMap<>(); | ||
| event.put("event", "initialized"); | ||
| event.put("width", width); | ||
| event.put("height", height); | ||
| event.put("duration", durationInMs); | ||
| if (rotationCorrectionInDegrees != 0) { | ||
| event.put("rotationCorrection", rotationCorrectionInDegrees); | ||
| } | ||
| eventSink.success(event); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The onInitialized method constructs a Map to represent the initialization event. This is a good approach for sending structured data to the Flutter side. However, the code does not handle potential exceptions that might occur when putting values into the Map. Consider adding error handling to gracefully handle exceptions and prevent crashes.
...r/video_player_android/android/src/main/java/io/flutter/plugins/videoplayer/VideoPlayer.java
Outdated
Show resolved
Hide resolved
- Added getAudioTracks() method to retrieve available audio tracks with metadata (bitrate, sample rate, channel count, codec) - Added selectAudioTrack() method to switch between audio tracks using ExoPlayer's track selector - Implemented onTracksChanged listener to notify when audio track selection changes
77b0fce to
b544b45
Compare
|
as we don't wanna do breaking changes to the platform interface @ash2moon have moved the trackindex/groupindex handling logic parsing/encoding logic to the dart side. Please check pr |
Android PR for : #9925
Pre-Review Checklist
[shared_preferences]pubspec.yamlwith an appropriate new version according to the [pub versioning philosophy], or I have commented below to indicate which [version change exemption] this PR falls under[^1].CHANGELOG.mdto add a description of the change, [following repository CHANGELOG style], or I have commented below to indicate which [CHANGELOG exemption] this PR falls under[^1].///).