解释这个编码器如何处理 PPS 和 SPS?
Explain how this encoder deals with PPS and SPS?
我在网上找到这段代码,有人可以解释一下 PPS 和 SPS 部分吗?
if (sps != null && pps != null)
之后的所有内容我明白自从我们检查 if (spsPpsBuffer.getInt() == 0x00000001)
因为 NALU 以 0x00000001 开头但在那之后我真的不了解以下内容:
为什么ppsIndex
先设置为0然后设置为spsPpsBuffer.position()
?
为什么SPS缓冲区大小是ppsIndex - 8
?
为什么PPS缓冲区的大小是outData.length - ppsIndex
?
这是代码:
@Override
public void offerEncoder(byte[] input) {
try {
ByteBuffer[] inputBuffers = mediaCodec.getInputBuffers();
ByteBuffer[] outputBuffers = mediaCodec.getOutputBuffers();
int inputBufferIndex = mediaCodec.dequeueInputBuffer(-1);
if (inputBufferIndex >= 0) {
ByteBuffer inputBuffer = inputBuffers[inputBufferIndex];
inputBuffer.clear();
inputBuffer.put(input);
mediaCodec.queueInputBuffer(inputBufferIndex, 0, input.length, 0, 0);
}
MediaCodec.BufferInfo bufferInfo = new MediaCodec.BufferInfo();
int outputBufferIndex = mediaCodec.dequeueOutputBuffer(bufferInfo, 0);
while (outputBufferIndex >= 0) {
ByteBuffer outputBuffer = outputBuffers[outputBufferIndex];
byte[] outData = new byte[bufferInfo.size];
outputBuffer.get(outData);
if (sps != null && pps != null) {
ByteBuffer frameBuffer = ByteBuffer.wrap(outData);
frameBuffer.putInt(bufferInfo.size - 4);
frameListener.frameReceived(outData, 0, outData.length);
} else {
ByteBuffer spsPpsBuffer = ByteBuffer.wrap(outData);
if (spsPpsBuffer.getInt() == 0x00000001) {
System.out.println("parsing sps/pps");
} else {
System.out.println("something is amiss?");
}
int ppsIndex = 0;
while(!(spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x01)) {
}
ppsIndex = spsPpsBuffer.position();
sps = new byte[ppsIndex - 8];
System.arraycopy(outData, 4, sps, 0, sps.length);
pps = new byte[outData.length - ppsIndex];
System.arraycopy(outData, ppsIndex, pps, 0, pps.length);
if (null != parameterSetsListener) {
parameterSetsListener.avcParametersSetsEstablished(sps, pps);
}
}
mediaCodec.releaseOutputBuffer(outputBufferIndex, false);
outputBufferIndex = mediaCodec.dequeueOutputBuffer(bufferInfo, 0);
}
} catch (Throwable t) {
t.printStackTrace();
}
}
非常感谢。
您可以从之前的回答中大致了解 PPS/SPS:
H264 with multiple PPS and SPS
以上代码是高度专业化的,仅适用于一小部分 H.264 流。该代码假设一个固定长度的 SPS(8 字节)并做出了一些更无效的假设。
除非代码适用于一种特定的编码器 - 我可能不会使用它。
这似乎是一个不错的 H.264 解析器:https://github.com/aizvorski/h264bitstream
我在网上找到这段代码,有人可以解释一下 PPS 和 SPS 部分吗?
if (sps != null && pps != null)
之后的所有内容我明白自从我们检查 if (spsPpsBuffer.getInt() == 0x00000001)
因为 NALU 以 0x00000001 开头但在那之后我真的不了解以下内容:
为什么
ppsIndex
先设置为0然后设置为spsPpsBuffer.position()
?为什么SPS缓冲区大小是
ppsIndex - 8
?为什么PPS缓冲区的大小是
outData.length - ppsIndex
?
这是代码:
@Override
public void offerEncoder(byte[] input) {
try {
ByteBuffer[] inputBuffers = mediaCodec.getInputBuffers();
ByteBuffer[] outputBuffers = mediaCodec.getOutputBuffers();
int inputBufferIndex = mediaCodec.dequeueInputBuffer(-1);
if (inputBufferIndex >= 0) {
ByteBuffer inputBuffer = inputBuffers[inputBufferIndex];
inputBuffer.clear();
inputBuffer.put(input);
mediaCodec.queueInputBuffer(inputBufferIndex, 0, input.length, 0, 0);
}
MediaCodec.BufferInfo bufferInfo = new MediaCodec.BufferInfo();
int outputBufferIndex = mediaCodec.dequeueOutputBuffer(bufferInfo, 0);
while (outputBufferIndex >= 0) {
ByteBuffer outputBuffer = outputBuffers[outputBufferIndex];
byte[] outData = new byte[bufferInfo.size];
outputBuffer.get(outData);
if (sps != null && pps != null) {
ByteBuffer frameBuffer = ByteBuffer.wrap(outData);
frameBuffer.putInt(bufferInfo.size - 4);
frameListener.frameReceived(outData, 0, outData.length);
} else {
ByteBuffer spsPpsBuffer = ByteBuffer.wrap(outData);
if (spsPpsBuffer.getInt() == 0x00000001) {
System.out.println("parsing sps/pps");
} else {
System.out.println("something is amiss?");
}
int ppsIndex = 0;
while(!(spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x00 && spsPpsBuffer.get() == 0x01)) {
}
ppsIndex = spsPpsBuffer.position();
sps = new byte[ppsIndex - 8];
System.arraycopy(outData, 4, sps, 0, sps.length);
pps = new byte[outData.length - ppsIndex];
System.arraycopy(outData, ppsIndex, pps, 0, pps.length);
if (null != parameterSetsListener) {
parameterSetsListener.avcParametersSetsEstablished(sps, pps);
}
}
mediaCodec.releaseOutputBuffer(outputBufferIndex, false);
outputBufferIndex = mediaCodec.dequeueOutputBuffer(bufferInfo, 0);
}
} catch (Throwable t) {
t.printStackTrace();
}
}
非常感谢。
您可以从之前的回答中大致了解 PPS/SPS: H264 with multiple PPS and SPS
以上代码是高度专业化的,仅适用于一小部分 H.264 流。该代码假设一个固定长度的 SPS(8 字节)并做出了一些更无效的假设。 除非代码适用于一种特定的编码器 - 我可能不会使用它。
这似乎是一个不错的 H.264 解析器:https://github.com/aizvorski/h264bitstream