mirror of
https://github.com/samsonjs/media.git
synced 2026-04-27 15:07:40 +00:00
Add nullness annotations to MediaCodecVideoRenderer
#fixit PiperOrigin-RevId: 562926813
This commit is contained in:
parent
8c0191d0cb
commit
8dcafa0398
1 changed files with 25 additions and 22 deletions
|
|
@ -88,6 +88,8 @@ import com.google.common.util.concurrent.MoreExecutors;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.concurrent.Executor;
|
import java.util.concurrent.Executor;
|
||||||
|
import org.checkerframework.checker.initialization.qual.Initialized;
|
||||||
|
import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Decodes and renders video using {@link MediaCodec}.
|
* Decodes and renders video using {@link MediaCodec}.
|
||||||
|
|
@ -151,7 +153,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
private final int maxDroppedFramesToNotify;
|
private final int maxDroppedFramesToNotify;
|
||||||
private final boolean deviceNeedsNoPostProcessWorkaround;
|
private final boolean deviceNeedsNoPostProcessWorkaround;
|
||||||
|
|
||||||
private CodecMaxValues codecMaxValues;
|
private @MonotonicNonNull CodecMaxValues codecMaxValues;
|
||||||
private boolean codecNeedsSetOutputSurfaceWorkaround;
|
private boolean codecNeedsSetOutputSurfaceWorkaround;
|
||||||
private boolean codecHandlesHdr10PlusOutOfBandMetadata;
|
private boolean codecHandlesHdr10PlusOutOfBandMetadata;
|
||||||
@Nullable private Surface displaySurface;
|
@Nullable private Surface displaySurface;
|
||||||
|
|
@ -396,16 +398,17 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
this.context = context.getApplicationContext();
|
this.context = context.getApplicationContext();
|
||||||
frameReleaseHelper = new VideoFrameReleaseHelper(this.context);
|
frameReleaseHelper = new VideoFrameReleaseHelper(this.context);
|
||||||
eventDispatcher = new EventDispatcher(eventHandler, eventListener);
|
eventDispatcher = new EventDispatcher(eventHandler, eventListener);
|
||||||
|
@SuppressWarnings("nullness:assignment")
|
||||||
|
VideoSink.@Initialized RenderControl renderControl = this;
|
||||||
videoSinkProvider =
|
videoSinkProvider =
|
||||||
new CompositingVideoSinkProvider(
|
new CompositingVideoSinkProvider(context, videoFrameProcessorFactory, renderControl);
|
||||||
context, videoFrameProcessorFactory, /* renderControl= */ this);
|
|
||||||
deviceNeedsNoPostProcessWorkaround = deviceNeedsNoPostProcessWorkaround();
|
deviceNeedsNoPostProcessWorkaround = deviceNeedsNoPostProcessWorkaround();
|
||||||
joiningDeadlineMs = C.TIME_UNSET;
|
joiningDeadlineMs = C.TIME_UNSET;
|
||||||
scalingMode = C.VIDEO_SCALING_MODE_DEFAULT;
|
scalingMode = C.VIDEO_SCALING_MODE_DEFAULT;
|
||||||
decodedVideoSize = VideoSize.UNKNOWN;
|
decodedVideoSize = VideoSize.UNKNOWN;
|
||||||
tunnelingAudioSessionId = C.AUDIO_SESSION_ID_UNSET;
|
tunnelingAudioSessionId = C.AUDIO_SESSION_ID_UNSET;
|
||||||
firstFrameState = C.FIRST_FRAME_NOT_RENDERED_ONLY_ALLOWED_IF_STARTED;
|
firstFrameState = C.FIRST_FRAME_NOT_RENDERED_ONLY_ALLOWED_IF_STARTED;
|
||||||
clearReportedVideoSize();
|
reportedVideoSize = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -725,7 +728,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onDisabled() {
|
protected void onDisabled() {
|
||||||
clearReportedVideoSize();
|
reportedVideoSize = null;
|
||||||
lowerFirstFrameState(C.FIRST_FRAME_NOT_RENDERED_ONLY_ALLOWED_IF_STARTED);
|
lowerFirstFrameState(C.FIRST_FRAME_NOT_RENDERED_ONLY_ALLOWED_IF_STARTED);
|
||||||
haveReportedFirstFrameRenderedForCurrentSurface = false;
|
haveReportedFirstFrameRenderedForCurrentSurface = false;
|
||||||
tunnelingOnFrameRenderedListener = null;
|
tunnelingOnFrameRenderedListener = null;
|
||||||
|
|
@ -766,21 +769,21 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
setOutput(message);
|
setOutput(message);
|
||||||
break;
|
break;
|
||||||
case MSG_SET_SCALING_MODE:
|
case MSG_SET_SCALING_MODE:
|
||||||
scalingMode = (Integer) message;
|
scalingMode = (int) checkNotNull(message);
|
||||||
@Nullable MediaCodecAdapter codec = getCodec();
|
@Nullable MediaCodecAdapter codec = getCodec();
|
||||||
if (codec != null) {
|
if (codec != null) {
|
||||||
codec.setVideoScalingMode(scalingMode);
|
codec.setVideoScalingMode(scalingMode);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case MSG_SET_CHANGE_FRAME_RATE_STRATEGY:
|
case MSG_SET_CHANGE_FRAME_RATE_STRATEGY:
|
||||||
frameReleaseHelper.setChangeFrameRateStrategy((int) message);
|
frameReleaseHelper.setChangeFrameRateStrategy((int) checkNotNull(message));
|
||||||
break;
|
break;
|
||||||
case MSG_SET_VIDEO_FRAME_METADATA_LISTENER:
|
case MSG_SET_VIDEO_FRAME_METADATA_LISTENER:
|
||||||
frameMetadataListener = (VideoFrameMetadataListener) message;
|
frameMetadataListener = (VideoFrameMetadataListener) checkNotNull(message);
|
||||||
videoSinkProvider.setVideoFrameMetadataListener(frameMetadataListener);
|
videoSinkProvider.setVideoFrameMetadataListener(frameMetadataListener);
|
||||||
break;
|
break;
|
||||||
case MSG_SET_AUDIO_SESSION_ID:
|
case MSG_SET_AUDIO_SESSION_ID:
|
||||||
int tunnelingAudioSessionId = (int) message;
|
int tunnelingAudioSessionId = (int) checkNotNull(message);
|
||||||
if (this.tunnelingAudioSessionId != tunnelingAudioSessionId) {
|
if (this.tunnelingAudioSessionId != tunnelingAudioSessionId) {
|
||||||
this.tunnelingAudioSessionId = tunnelingAudioSessionId;
|
this.tunnelingAudioSessionId = tunnelingAudioSessionId;
|
||||||
if (tunneling) {
|
if (tunneling) {
|
||||||
|
|
@ -865,7 +868,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// The display surface has been removed.
|
// The display surface has been removed.
|
||||||
clearReportedVideoSize();
|
reportedVideoSize = null;
|
||||||
lowerFirstFrameState(C.FIRST_FRAME_NOT_RENDERED);
|
lowerFirstFrameState(C.FIRST_FRAME_NOT_RENDERED);
|
||||||
if (videoSinkProvider.isInitialized()) {
|
if (videoSinkProvider.isInitialized()) {
|
||||||
videoSinkProvider.clearOutputSurfaceInfo();
|
videoSinkProvider.clearOutputSurfaceInfo();
|
||||||
|
|
@ -942,6 +945,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
DecoderReuseEvaluation evaluation = codecInfo.canReuseCodec(oldFormat, newFormat);
|
DecoderReuseEvaluation evaluation = codecInfo.canReuseCodec(oldFormat, newFormat);
|
||||||
|
|
||||||
@DecoderDiscardReasons int discardReasons = evaluation.discardReasons;
|
@DecoderDiscardReasons int discardReasons = evaluation.discardReasons;
|
||||||
|
CodecMaxValues codecMaxValues = checkNotNull(this.codecMaxValues);
|
||||||
if (newFormat.width > codecMaxValues.width || newFormat.height > codecMaxValues.height) {
|
if (newFormat.width > codecMaxValues.width || newFormat.height > codecMaxValues.height) {
|
||||||
discardReasons |= DISCARD_REASON_VIDEO_MAX_RESOLUTION_EXCEEDED;
|
discardReasons |= DISCARD_REASON_VIDEO_MAX_RESOLUTION_EXCEEDED;
|
||||||
}
|
}
|
||||||
|
|
@ -999,7 +1003,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
return Format.NO_VALUE;
|
return Format.NO_VALUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
String sampleMimeType = format.sampleMimeType;
|
String sampleMimeType = checkNotNull(format.sampleMimeType);
|
||||||
if (MimeTypes.VIDEO_DOLBY_VISION.equals(sampleMimeType)) {
|
if (MimeTypes.VIDEO_DOLBY_VISION.equals(sampleMimeType)) {
|
||||||
// Dolby vision can be a wrapper around H264 or H265. We assume it's wrapping H265 by default
|
// Dolby vision can be a wrapper around H264 or H265. We assume it's wrapping H265 by default
|
||||||
// because it's the common case, and because some devices may fail to allocate the codec when
|
// because it's the common case, and because some devices may fail to allocate the codec when
|
||||||
|
|
@ -1150,7 +1154,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
protected DecoderReuseEvaluation onInputFormatChanged(FormatHolder formatHolder)
|
protected DecoderReuseEvaluation onInputFormatChanged(FormatHolder formatHolder)
|
||||||
throws ExoPlaybackException {
|
throws ExoPlaybackException {
|
||||||
@Nullable DecoderReuseEvaluation evaluation = super.onInputFormatChanged(formatHolder);
|
@Nullable DecoderReuseEvaluation evaluation = super.onInputFormatChanged(formatHolder);
|
||||||
eventDispatcher.inputFormatChanged(formatHolder.format, evaluation);
|
eventDispatcher.inputFormatChanged(checkNotNull(formatHolder.format), evaluation);
|
||||||
return evaluation;
|
return evaluation;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1266,7 +1270,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
byte[] hdr10PlusInfo = new byte[data.remaining()];
|
byte[] hdr10PlusInfo = new byte[data.remaining()];
|
||||||
data.get(hdr10PlusInfo);
|
data.get(hdr10PlusInfo);
|
||||||
data.position(0);
|
data.position(0);
|
||||||
setHdr10PlusInfoV29(getCodec(), hdr10PlusInfo);
|
setHdr10PlusInfoV29(checkNotNull(getCodec()), hdr10PlusInfo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -1731,8 +1735,10 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
if (displaySurface == placeholderSurface) {
|
if (displaySurface == placeholderSurface) {
|
||||||
displaySurface = null;
|
displaySurface = null;
|
||||||
}
|
}
|
||||||
placeholderSurface.release();
|
if (placeholderSurface != null) {
|
||||||
placeholderSurface = null;
|
placeholderSurface.release();
|
||||||
|
placeholderSurface = null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void setJoiningDeadlineMs() {
|
private void setJoiningDeadlineMs() {
|
||||||
|
|
@ -1758,7 +1764,7 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
}
|
}
|
||||||
|
|
||||||
private void maybeNotifyRenderedFirstFrame() {
|
private void maybeNotifyRenderedFirstFrame() {
|
||||||
if (firstFrameState != C.FIRST_FRAME_RENDERED) {
|
if (displaySurface != null && firstFrameState != C.FIRST_FRAME_RENDERED) {
|
||||||
firstFrameState = C.FIRST_FRAME_RENDERED;
|
firstFrameState = C.FIRST_FRAME_RENDERED;
|
||||||
eventDispatcher.renderedFirstFrame(displaySurface);
|
eventDispatcher.renderedFirstFrame(displaySurface);
|
||||||
haveReportedFirstFrameRenderedForCurrentSurface = true;
|
haveReportedFirstFrameRenderedForCurrentSurface = true;
|
||||||
|
|
@ -1766,15 +1772,11 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
}
|
}
|
||||||
|
|
||||||
private void maybeRenotifyRenderedFirstFrame() {
|
private void maybeRenotifyRenderedFirstFrame() {
|
||||||
if (haveReportedFirstFrameRenderedForCurrentSurface) {
|
if (displaySurface != null && haveReportedFirstFrameRenderedForCurrentSurface) {
|
||||||
eventDispatcher.renderedFirstFrame(displaySurface);
|
eventDispatcher.renderedFirstFrame(displaySurface);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void clearReportedVideoSize() {
|
|
||||||
reportedVideoSize = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Notifies the new video size. */
|
/** Notifies the new video size. */
|
||||||
private void maybeNotifyVideoSizeChanged(VideoSize newOutputSize) {
|
private void maybeNotifyVideoSizeChanged(VideoSize newOutputSize) {
|
||||||
if (!newOutputSize.equals(VideoSize.UNKNOWN) && !newOutputSize.equals(reportedVideoSize)) {
|
if (!newOutputSize.equals(VideoSize.UNKNOWN) && !newOutputSize.equals(reportedVideoSize)) {
|
||||||
|
|
@ -2048,7 +2050,8 @@ public class MediaCodecVideoRenderer extends MediaCodecRenderer implements Video
|
||||||
isVerticalVideo ? shortEdgePx : longEdgePx,
|
isVerticalVideo ? shortEdgePx : longEdgePx,
|
||||||
isVerticalVideo ? longEdgePx : shortEdgePx);
|
isVerticalVideo ? longEdgePx : shortEdgePx);
|
||||||
float frameRate = format.frameRate;
|
float frameRate = format.frameRate;
|
||||||
if (codecInfo.isVideoSizeAndRateSupportedV21(alignedSize.x, alignedSize.y, frameRate)) {
|
if (alignedSize != null
|
||||||
|
&& codecInfo.isVideoSizeAndRateSupportedV21(alignedSize.x, alignedSize.y, frameRate)) {
|
||||||
return alignedSize;
|
return alignedSize;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue