fix(android): add subtitleStyle.subtitlesFollowVideo prop to control subtitles positionning (#4133)
* fix(android): add subtitleStyle.subtitlesFollowVideo prop to control subtitles positionning * docs: add new prop description * docs: add supported platform for subtitleStyle * chore: use constructor instead of parse
This commit is contained in:
parent
688d98d68f
commit
2fa6c43615
@ -6,7 +6,7 @@ import com.facebook.react.bridge.ReadableMap
|
||||
/**
|
||||
* Helper file to parse SubtitleStyle prop and build a dedicated class
|
||||
*/
|
||||
class SubtitleStyle private constructor() {
|
||||
class SubtitleStyle public constructor() {
|
||||
var fontSize = -1
|
||||
private set
|
||||
var paddingLeft = 0
|
||||
@ -19,6 +19,8 @@ class SubtitleStyle private constructor() {
|
||||
private set
|
||||
var opacity = 1f
|
||||
private set
|
||||
var subtitlesFollowVideo = true
|
||||
private set
|
||||
|
||||
companion object {
|
||||
private const val PROP_FONT_SIZE_TRACK = "fontSize"
|
||||
@ -27,6 +29,7 @@ class SubtitleStyle private constructor() {
|
||||
private const val PROP_PADDING_LEFT = "paddingLeft"
|
||||
private const val PROP_PADDING_RIGHT = "paddingRight"
|
||||
private const val PROP_OPACITY = "opacity"
|
||||
private const val PROP_SUBTITLES_FOLLOW_VIDEO = "subtitlesFollowVideo"
|
||||
|
||||
@JvmStatic
|
||||
fun parse(src: ReadableMap?): SubtitleStyle {
|
||||
@ -37,6 +40,7 @@ class SubtitleStyle private constructor() {
|
||||
subtitleStyle.paddingLeft = ReactBridgeUtils.safeGetInt(src, PROP_PADDING_LEFT, 0)
|
||||
subtitleStyle.paddingRight = ReactBridgeUtils.safeGetInt(src, PROP_PADDING_RIGHT, 0)
|
||||
subtitleStyle.opacity = ReactBridgeUtils.safeGetFloat(src, PROP_OPACITY, 1f)
|
||||
subtitleStyle.subtitlesFollowVideo = ReactBridgeUtils.safeGetBool(src, PROP_SUBTITLES_FOLLOW_VIDEO, true)
|
||||
return subtitleStyle
|
||||
}
|
||||
}
|
||||
|
@ -48,6 +48,8 @@ public final class ExoPlayerView extends FrameLayout implements AdViewProvider {
|
||||
private @ViewType.ViewType int viewType = ViewType.VIEW_TYPE_SURFACE;
|
||||
private boolean hideShutterView = false;
|
||||
|
||||
private SubtitleStyle localStyle = new SubtitleStyle();
|
||||
|
||||
public ExoPlayerView(Context context) {
|
||||
super(context, null, 0);
|
||||
|
||||
@ -80,11 +82,16 @@ public final class ExoPlayerView extends FrameLayout implements AdViewProvider {
|
||||
adOverlayFrameLayout = new FrameLayout(context);
|
||||
|
||||
layout.addView(shutterView, 1, layoutParams);
|
||||
layout.addView(adOverlayFrameLayout, 2, layoutParams);
|
||||
if (localStyle.getSubtitlesFollowVideo()) {
|
||||
layout.addView(subtitleLayout, layoutParams);
|
||||
layout.addView(adOverlayFrameLayout, layoutParams);
|
||||
}
|
||||
|
||||
addViewInLayout(layout, 0, aspectRatioParams);
|
||||
if (!localStyle.getSubtitlesFollowVideo()) {
|
||||
addViewInLayout(subtitleLayout, 1, layoutParams);
|
||||
}
|
||||
}
|
||||
|
||||
private void clearVideoView() {
|
||||
if (surfaceView instanceof TextureView) {
|
||||
@ -107,7 +114,7 @@ public final class ExoPlayerView extends FrameLayout implements AdViewProvider {
|
||||
}
|
||||
|
||||
public void setSubtitleStyle(SubtitleStyle style) {
|
||||
// ensure we reset subtile style before reapplying it
|
||||
// ensure we reset subtitle style before reapplying it
|
||||
subtitleLayout.setUserDefaultStyle();
|
||||
subtitleLayout.setUserDefaultTextSize();
|
||||
|
||||
@ -121,7 +128,18 @@ public final class ExoPlayerView extends FrameLayout implements AdViewProvider {
|
||||
} else {
|
||||
subtitleLayout.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (localStyle.getSubtitlesFollowVideo() != style.getSubtitlesFollowVideo()) {
|
||||
// No need to manipulate layout if value didn't change
|
||||
if (style.getSubtitlesFollowVideo()) {
|
||||
removeViewInLayout(subtitleLayout);
|
||||
layout.addView(subtitleLayout, layoutParams);
|
||||
} else {
|
||||
layout.removeViewInLayout(subtitleLayout);
|
||||
addViewInLayout(subtitleLayout, 1, layoutParams, false);
|
||||
}
|
||||
requestLayout();
|
||||
}
|
||||
localStyle = style;
|
||||
}
|
||||
|
||||
public void setShutterColor(Integer color) {
|
||||
|
@ -846,14 +846,18 @@ source={{
|
||||
|
||||
### `subtitleStyle`
|
||||
|
||||
| Property | Description | Platforms |
|
||||
| ------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------ |
|
||||
| fontSize | Adjust the font size of the subtitles. Default: font size of the device | Android |
|
||||
| paddingTop | Adjust the top padding of the subtitles. Default: 0 | Android |
|
||||
| paddingBottom | Adjust the bottom padding of the subtitles. Default: 0 | Android |
|
||||
| paddingLeft | Adjust the left padding of the subtitles. Default: 0 | Android |
|
||||
| paddingRight | Adjust the right padding of the subtitles. Default: 0 | Android |
|
||||
| opacity | Adjust the visibility of subtitles with 0 hiding and 1 fully showing them. Android supports float values between 0 and 1 for varying opacity levels, whereas iOS supports only 0 or 1. Default: 1. | Android, iOS |
|
||||
<PlatformsList types={['Android', 'iOS']} />
|
||||
|
||||
| Property | Platform | Description | Platforms |
|
||||
| ------------- | -------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------ |
|
||||
| fontSize | Android | Adjust the font size of the subtitles. Default: font size of the device | Android |
|
||||
| paddingTop | Android | Adjust the top padding of the subtitles. Default: 0 | Android |
|
||||
| paddingBottom | Android | Adjust the bottom padding of the subtitles. Default: 0 | Android |
|
||||
| paddingLeft | Android | Adjust the left padding of the subtitles. Default: 0 | Android |
|
||||
| paddingRight | Android | Adjust the right padding of the subtitles. Default: 0 | Android |
|
||||
| opacity | Android, iOS | Adjust the visibility of subtitles with 0 hiding and 1 fully showing them. Android supports float values between 0 and 1 for varying opacity levels, whereas iOS supports only 0 or 1. Default: 1. | Android, iOS |
|
||||
| subtitlesFollowVideo | Android | Boolean to adjust position of subtitles. Default: true |
|
||||
|
||||
|
||||
Example:
|
||||
|
||||
@ -861,6 +865,27 @@ Example:
|
||||
subtitleStyle={{ paddingBottom: 50, fontSize: 20, opacity: 0 }}
|
||||
```
|
||||
|
||||
Note for `subtitlesFollowVideo`
|
||||
|
||||
`subtitlesFollowVideo` helps to determine how the subtitles are positionned.
|
||||
To understand this prop you need to understand how views management works.
|
||||
The main View style passed to react native video is the position reserved to display the video component.
|
||||
It may not match exactly the real video size.
|
||||
For exemple, you can pass a 4:3 video view and render a 16:9 video inside.
|
||||
So there is a second view, the video view.
|
||||
|
||||
Subtitles are managed in a third view.
|
||||
|
||||
First react-native-video resize the video to keep aspect ratio (depending on `resizeMode` property) and put it in main view.
|
||||
|
||||
* When putting subtitlesFollowVideo to true, the subtitle view will be adapt to the video view.
|
||||
It means that if the video is displayed out of screen, the subtitles may also be displayed out of screen.
|
||||
|
||||
* When putting subtitlesFollowVideo to false, the subtitle view will keep adapting to the main view.
|
||||
It means that if the video is displayed out of screen, the subtitles may also be displayed out of screen.
|
||||
|
||||
This prop can be changed on runtime.
|
||||
|
||||
### `textTracks`
|
||||
|
||||
<PlatformsList types={['Android', 'iOS', 'visionOS']} />
|
||||
|
@ -268,6 +268,7 @@ const VideoPlayer: FC<Props> = ({}) => {
|
||||
onPlaybackStateChanged={onPlaybackStateChanged}
|
||||
bufferingStrategy={BufferingStrategyType.DEFAULT}
|
||||
debug={{enable: true, thread: true}}
|
||||
subtitleStyle={{subtitlesFollowVideo: true}}
|
||||
/>
|
||||
</TouchableOpacity>
|
||||
)}
|
||||
|
@ -131,6 +131,7 @@ type SubtitleStyle = Readonly<{
|
||||
paddingLeft?: WithDefault<Float, 0>;
|
||||
paddingRight?: WithDefault<Float, 0>;
|
||||
opacity?: WithDefault<Float, 1>;
|
||||
subtitlesFollowVideo?: WithDefault<boolean, true>;
|
||||
}>;
|
||||
|
||||
type OnLoadData = Readonly<{
|
||||
|
@ -168,6 +168,7 @@ export type SubtitleStyle = {
|
||||
paddingLeft?: number;
|
||||
paddingRight?: number;
|
||||
opacity?: number;
|
||||
subtitlesFollowVideo?: boolean;
|
||||
};
|
||||
|
||||
export enum TextTrackType {
|
||||
|
Loading…
Reference in New Issue
Block a user