Custom Player View
Purpose
The custom player view encapsulates the video display surface, subtitle rendering, and user interaction controls into a single reusable component. It addresses the need for a flexible, adaptable media playback UI that integrates tightly with ExoPlayer, supporting a consistent playback experience across different devices including TVs. This view simplifies the management of video surface types, subtitle styling, and control overlays that are essential for rich media playback but are not covered in the generic parent topic of media playback and UI controls.
Functionality
Video Surface Management
The view dynamically creates and manages either aSurfaceVieworTextureViewdepending on configuration, encapsulating the video output surface that ExoPlayer renders to. This abstraction allows for device-specific optimizations and different rendering strategies.Aspect Ratio and Layout
It uses anAspectRatioFrameLayoutcontainer to maintain the correct aspect ratio of video content, adjusting dynamically as video dimensions change via ExoPlayer callbacks.Subtitle Rendering
The embeddedSubtitleViewdisplays timed text subtitles with custom styling optimized for TV devices, including font, size, and background color. Subtitles are updated in sync with video playback cues received from the ExoPlayer.User Interaction Controls Integration
The view allows an external user interaction component (e.g., playback buttons, seek bar) to be injected and managed transparently within its layout. This supports modular UI design where control logic and visuals are separated but visually integrated.Player Attachment and Event Listening
When aSimpleExoPlayerinstance is assigned, the view registers internal listeners to receive video size changes, text cues, playback events, and error notifications. It manages clearing and setting these listeners to avoid leaks and ensure correct event propagation.Media Model Binding
Provides a method to bind media metadata to the embedded user controller, enabling the UI controls to reflect current media state like title, duration, and ad availability.
Key Workflows and Methods
setPlayer(SimpleExoPlayer player, PlaybackActionCallback callback)
Attaches the ExoPlayer instance, sets the video surface (surface or texture view), and registers listeners for video and text events.addUserInteractionView(View controlView)
Inserts a custom playback control view into a designated placeholder within the layout, allowing flexible UI composition.ComponentListener(inner class)
Implements callbacks for video size changes (onVideoSizeChanged), subtitle cues (onCues), first frame rendered, and other player events. It updates UI elements like subtitle view and aspect ratio container accordingly.setMediaModel(MediaModel mediaModel)
Passes media metadata to theUserController, which updates UI observables bound to the control views.
Integration with Parent Topic and Other Subtopics
This custom player view complements the broader media playback and UI controls by acting as the unified container that hosts video output, subtitles, and user interaction elements. While the parent topic covers general playback and control logic, this view concretely implements the display layer and visual integration:
It works closely with the Player UI Controller and User Interaction Controller subtopics by hosting their views and binding to their logic through the
UserControllerinstance.It integrates with the Playback Activity Base by exposing methods to set the player and user controls, enabling activities to assemble the playback UI modularly.
By handling subtitle rendering internally, it offloads subtitle synchronization and styling concerns from higher-level controllers.
The view’s abstraction over video surfaces supports adaptive rendering strategies suitable for different device types, bridging the gap between playback logic and device-specific UI requirements.
This subtopic introduces a reusable, self-contained view component that encapsulates multiple playback UI concerns, providing a consistent foundation for building rich media players across the app.
Code Snippets Illustrating Key Interactions
Attaching the Player and Setting Surfaces
public void setPlayer(SimpleExoPlayer player, @NonNull PlaybackActionCallback callback) {
if (this.player != null) {
this.player.removeListener(componentListener);
this.player.clearTextOutput(componentListener);
this.player.clearVideoListener(componentListener);
if (surfaceView instanceof TextureView) {
this.player.clearVideoTextureView((TextureView) surfaceView);
} else if (surfaceView instanceof SurfaceView) {
this.player.clearVideoSurfaceView((SurfaceView) surfaceView);
}
}
this.player = player;
if (userController != null) {
userController.setPlayer(player, callback, this);
}
if (player != null) {
if (surfaceView instanceof TextureView) {
player.setVideoTextureView((TextureView) surfaceView);
} else if (surfaceView instanceof SurfaceView) {
player.setVideoSurfaceView((SurfaceView) surfaceView);
}
player.setVideoListener(componentListener);
player.setTextOutput(componentListener);
player.addListener(componentListener);
}
}
Handling Video Size Changes to Adjust Aspect Ratio
@Override
public void onVideoSizeChanged(int width, int height, int unappliedRotationDegrees,
float pixelWidthHeightRatio) {
if (contentFrame != null) {
float aspectRatio = height == 0 ? 1 : (width * pixelWidthHeightRatio) / height;
contentFrame.setAspectRatio(aspectRatio);
}
}
Receiving Subtitle Cues for Display
@Override
public void onCues(List<Cue> cues) {
if (subtitleView != null) {
subtitleView.onCues(cues);
}
}
Diagram
classDiagram
class TubiExoPlayerView {
-AspectRatioFrameLayout contentFrame
-View shutterView
-View surfaceView
-SubtitleView subtitleView
-View mUserInteractionView
-SimpleExoPlayer player
-UserController userController
+setPlayer(player, callback)
+addUserInteractionView(view)
+setMediaModel(mediaModel)
+getSubtitleView()
}
TubiExoPlayerView o-- "1" SimpleExoPlayer : attaches
TubiExoPlayerView o-- "1" AspectRatioFrameLayout : manages layout
TubiExoPlayerView o-- "1" SubtitleView : displays subtitles
TubiExoPlayerView o-- "0..1" View : user interaction controls
TubiExoPlayerView --> UserController : binds media state and controls
This class diagram visualizes the main structural elements of the custom player view and its relationships to ExoPlayer, subtitle rendering, user controls, and layout management. It highlights the view’s role as an integration point for video playback surfaces and interactive UI components.