Add texture support to HardwareVideoEncoder.

HardwareVideoEncoderFactory can now take an EglBase.Context on creation.
When it does, it creates video encoders in texture mode.  It uses the
COLOR_FormatSurface colorFormat.  It passes the EglBase.Context to the
HardwareVideoEncoder.

The HardwareVideoEncoder sets up an input surface for its codec and handles
incoming frames by drawing them onto the input surface.

BUG=webrtc:7760
R=pthatcher@webrtc.org, sakal@webrtc.org

Review-Url: https://codereview.webrtc.org/2977153003 .
Cr-Commit-Position: refs/heads/master@{#19083}
This commit is contained in:
Bjorn Mellem
2017-07-18 13:19:26 -07:00
parent f80f344215
commit 0cf9a4a482
5 changed files with 293 additions and 37 deletions

View File

@ -55,14 +55,28 @@ public class HardwareVideoEncoderFactory implements VideoEncoderFactory {
private static final String H264_CONSTRAINED_HIGH_3_1 =
H264_PROFILE_CONSTRAINED_HIGH + H264_LEVEL_3_1;
private final EglBase14.Context sharedContext;
private final boolean enableIntelVp8Encoder;
private final boolean enableH264HighProfile;
public HardwareVideoEncoderFactory(boolean enableIntelVp8Encoder, boolean enableH264HighProfile) {
public HardwareVideoEncoderFactory(
EglBase.Context sharedContext, boolean enableIntelVp8Encoder, boolean enableH264HighProfile) {
// Texture mode requires EglBase14.
if (sharedContext instanceof EglBase14.Context) {
this.sharedContext = (EglBase14.Context) sharedContext;
} else {
Logging.w(TAG, "No shared EglBase.Context. Encoders will not use texture mode.");
this.sharedContext = null;
}
this.enableIntelVp8Encoder = enableIntelVp8Encoder;
this.enableH264HighProfile = enableH264HighProfile;
}
@Deprecated
public HardwareVideoEncoderFactory(boolean enableIntelVp8Encoder, boolean enableH264HighProfile) {
this(null, enableIntelVp8Encoder, enableH264HighProfile);
}
@Override
public VideoEncoder createEncoder(VideoCodecInfo input) {
VideoCodecType type = VideoCodecType.valueOf(input.name);
@ -74,11 +88,14 @@ public class HardwareVideoEncoderFactory implements VideoEncoderFactory {
String codecName = info.getName();
String mime = type.mimeType();
int colorFormat = MediaCodecUtils.selectColorFormat(
MediaCodecUtils.ENCODER_COLOR_FORMATS, info.getCapabilitiesForType(mime));
int colorFormat = MediaCodecUtils.selectColorFormat(sharedContext == null
? MediaCodecUtils.ENCODER_COLOR_FORMATS
: MediaCodecUtils.TEXTURE_COLOR_FORMATS,
info.getCapabilitiesForType(mime));
return new HardwareVideoEncoder(codecName, type, colorFormat, getKeyFrameIntervalSec(type),
getForcedKeyFrameIntervalMs(type, codecName), createBitrateAdjuster(type, codecName));
getForcedKeyFrameIntervalMs(type, codecName), createBitrateAdjuster(type, codecName),
sharedContext);
}
@Override
@ -127,8 +144,10 @@ public class HardwareVideoEncoderFactory implements VideoEncoderFactory {
return false;
}
// Check for a supported color format.
if (MediaCodecUtils.selectColorFormat(
MediaCodecUtils.ENCODER_COLOR_FORMATS, info.getCapabilitiesForType(type.mimeType()))
if (MediaCodecUtils.selectColorFormat(sharedContext == null
? MediaCodecUtils.ENCODER_COLOR_FORMATS
: MediaCodecUtils.TEXTURE_COLOR_FORMATS,
info.getCapabilitiesForType(type.mimeType()))
== null) {
return false;
}

View File

@ -273,6 +273,36 @@ public class RendererCommon {
return matrix;
}
/** Converts android.graphics.Matrix to a float[16] matrix array. */
public static float[] convertMatrixFromAndroidGraphicsMatrix(android.graphics.Matrix matrix) {
float[] values = new float[9];
matrix.getValues(values);
// The android.graphics.Matrix looks like this:
// [x1 y1 w1]
// [x2 y2 w2]
// [x3 y3 w3]
// We want to contruct a matrix that looks like this:
// [x1 y1 0 w1]
// [x2 y2 0 w2]
// [ 0 0 1 0]
// [x3 y3 0 w3]
// Since it is stored in column-major order, it looks like this:
// [x1 x2 0 x3
// y1 y2 0 y3
// 0 0 1 0
// w1 w2 0 w3]
// clang-format off
float[] matrix4x4 = {
values[0 * 3 + 0], values[1 * 3 + 0], 0, values[2 * 3 + 0],
values[0 * 3 + 1], values[1 * 3 + 1], 0, values[2 * 3 + 1],
0, 0, 1, 0,
values[0 * 3 + 2], values[1 * 3 + 2], 0, values[2 * 3 + 2],
};
// clang-format on
return matrix4x4;
}
/**
* Calculate display size based on scaling type, video aspect ratio, and maximum display size.
*/