'Hevc video stream Media Codec Half of video is broken when receive 2 I frame in a row
I'm trying to decode packages from Hevc Stream raw, then I receive 2 I Frames in a row because NaluType returns value 19 twice. Then half of the video is broken. I'm using Media Codec. How can I split the packages the hevc live video to render video without broken image? I've concatenated 2 I Frame but half of the video still broken.
private static final byte[] NALUStartCode = {0x00,0x00,0x00,0x01};
private boolean gotVPS = false;
private boolean gotPPS = false;
private boolean gotSPS = false;
private byte[] vspSet;
int temp;
private byte[] idrSet;
public DataStruct(byte[] data, long mTimeNum, boolean isParams) {
this.mVideoData = data;
this.mTimeNum = mTimeNum;
this.isParams = isParams;
}
private void splitRtpPackage(DataStruct hevcStruct) {
if (hevcStruct == null) {
return;
}
byte[] totalBytes = hevcStruct.getVideoData();
int payloadSize = totalBytes.length;
if (payloadSize > 8) {
byte[] hevcRaw = Arrays.copyOfRange(totalBytes, 12, totalBytes.length);
long timestamp = bytesToInt(Arrays.copyOfRange(totalBytes, 2, 10));
int check = totalBytes[1];
if (check != 2) {
stopSplitter();
return;
}
// extract the bit 2nd -> 6th from byte 1st
int nalType = (hevcRaw[0] >> 1) & 0x3f;
if ((9 < nalType && nalType < 16) || (21 < nalType && nalType < 32) || nalType > 40) {
return;
}
switch (nalType) {
case 32: //vps
this.vspSet = null;
this.vspSet = concatenateByteArrays(NALUStartCode, hevcRaw);
this.gotVPS = true;
this.gotSPS = false;
this.gotPPS = false;
break;
case 33: //sps
if (this.gotVPS) {
this.vspSet = concatenateByteArrays(this.vspSet, concatenateByteArrays(NALUStartCode, hevcRaw));
this.gotSPS = true;
}
break;
case 34: //pps
if (this.gotSPS) {
this.vspSet = concatenateByteArrays(this.vspSet, concatenateByteArrays(NALUStartCode, hevcRaw));
this.gotPPS = true;
this.gotVPS = false;
this.gotSPS = false;
onHevcPackageReceived(new DataStruct(this.vspSet, timestamp, true));
}
break;
case 19: //I Frame
case 20:
if (this.gotPPS) {
if (this.temp != 19 && this.temp != 20) {
this.idrSet = null;
this.idrSet = concatenateByteArrays(NALUStartCode, hevcRaw);
} else {
this.idrSet = concatenateByteArrays(this.idrSet, concatenateByteArrays(NALUStartCode, hevcRaw));
// concatened 2 I Frame
}
}
break;
case 0: // P Frame
case 1:
if (this.gotPPS) {
if (this.temp == 19 || this.temp == 20) {
onHevcPackageReceived(new DataStruct(this.idrSet, timestamp, false));
} else {
onHevcPackageReceived(new DataStruct(concatenateByteArrays(NALUStartCode, hevcRaw), timestamp, false));
}
}
break;
default:
if (this.gotPPS) {
onHevcPackageReceived(new DataStruct(concatenateByteArrays(NALUStartCode, hevcRaw), timestamp, false));
}
break;
}
this.temp = nalType;
}
}
private void onHevcPackageReceived(DataStruct dataStruct) {
this.Player.getDataQueue().enqueue(dataStruct); // enqueue to list to decode
}
private static byte[] concatenateByteArrays(byte[] a, byte[] b) {
byte[] result = new byte[(a.length + b.length)];
System.arraycopy(a, 0, result, 0, a.length);
System.arraycopy(b, 0, result, a.length, b.length);
return result;
}
private int bytesToInt(byte[] range) {
return ByteBuffer.wrap(range).getInt();
}
Solution 1:[1]
I fixed this.
I had to remove some packages with dpkg
sudo dpkg --remove --force-remove-reinstreq libgtk-3-dev
sudo dpkg --remove --force-remove-reinstreq mesa-common-dev
sudo dpkg --remove --force-remove-reinstreq libegl1-mesa-dev
sudo dpkg --remove libgles2-mesa-dev
Then I ran sudo apt --fix-broken install
I had to also run all updates and upgrades to fix everything.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 |
