Commit 2c84f016 by olly Committed by Oliver Woodman

Parse and expose proj and st3d/stereo_mode

As described in:
https://github.com/google/spatial-media/blob/master/docs/spherical-video-v2-rfc.md.

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=130776689
parent 1579b68c
...@@ -55,10 +55,12 @@ public final class FormatTest extends TestCase { ...@@ -55,10 +55,12 @@ public final class FormatTest extends TestCase {
DrmInitData.SchemeData DRM_DATA_2 = new DrmInitData.SchemeData(C.UUID_NIL, VIDEO_WEBM, DrmInitData.SchemeData DRM_DATA_2 = new DrmInitData.SchemeData(C.UUID_NIL, VIDEO_WEBM,
TestUtil.buildTestData(128, 1 /* data seed */)); TestUtil.buildTestData(128, 1 /* data seed */));
DrmInitData drmInitData = new DrmInitData(DRM_DATA_1, DRM_DATA_2); DrmInitData drmInitData = new DrmInitData(DRM_DATA_1, DRM_DATA_2);
byte[] projectionData = new byte[] {1, 2, 3};
Format formatToParcel = new Format("id", MimeTypes.VIDEO_MP4, MimeTypes.VIDEO_H264, null, Format formatToParcel = new Format("id", MimeTypes.VIDEO_MP4, MimeTypes.VIDEO_H264, null,
1024, 2048, 1920, 1080, 24, 90, 2, 6, 44100, C.ENCODING_PCM_24BIT, 1001, 1002, 0, "und", 1024, 2048, 1920, 1080, 24, 90, 2, projectionData, C.STEREO_MODE_TOP_BOTTOM, 6, 44100,
Format.OFFSET_SAMPLE_RELATIVE, INIT_DATA, drmInitData); C.ENCODING_PCM_24BIT, 1001, 1002, 0, "und", Format.OFFSET_SAMPLE_RELATIVE, INIT_DATA,
drmInitData);
Parcel parcel = Parcel.obtain(); Parcel parcel = Parcel.obtain();
formatToParcel.writeToParcel(parcel, 0); formatToParcel.writeToParcel(parcel, 0);
......
...@@ -364,6 +364,21 @@ public final class C { ...@@ -364,6 +364,21 @@ public final class C {
public static final int MSG_CUSTOM_BASE = 10000; public static final int MSG_CUSTOM_BASE = 10000;
/** /**
* Indicates Monoscopic stereo layout, used with 360/3D/VR videos.
*/
public static final int STEREO_MODE_MONO = 0;
/**
* Indicates Top-Bottom stereo layout, used with 360/3D/VR videos.
*/
public static final int STEREO_MODE_TOP_BOTTOM = 1;
/**
* Indicates Left-Right stereo layout, used with 360/3D/VR videos.
*/
public static final int STEREO_MODE_LEFT_RIGHT = 2;
/**
* Converts a time in microseconds to the corresponding time in milliseconds, preserving * Converts a time in microseconds to the corresponding time in milliseconds, preserving
* {@link #TIME_UNSET} values. * {@link #TIME_UNSET} values.
* *
......
...@@ -126,6 +126,9 @@ import java.util.List; ...@@ -126,6 +126,9 @@ import java.util.List;
public static final int TYPE_mean = Util.getIntegerCodeForString("mean"); public static final int TYPE_mean = Util.getIntegerCodeForString("mean");
public static final int TYPE_name = Util.getIntegerCodeForString("name"); public static final int TYPE_name = Util.getIntegerCodeForString("name");
public static final int TYPE_data = Util.getIntegerCodeForString("data"); public static final int TYPE_data = Util.getIntegerCodeForString("data");
public static final int TYPE_st3d = Util.getIntegerCodeForString("st3d");
public static final int TYPE_sv3d = Util.getIntegerCodeForString("sv3d");
public static final int TYPE_proj = Util.getIntegerCodeForString("proj");
public static final int TYPE_vp08 = Util.getIntegerCodeForString("vp08"); public static final int TYPE_vp08 = Util.getIntegerCodeForString("vp08");
public static final int TYPE_vp09 = Util.getIntegerCodeForString("vp09"); public static final int TYPE_vp09 = Util.getIntegerCodeForString("vp09");
public static final int TYPE_vpcC = Util.getIntegerCodeForString("vpcC"); public static final int TYPE_vpcC = Util.getIntegerCodeForString("vpcC");
......
...@@ -29,6 +29,7 @@ import com.google.android.exoplayer2.util.ParsableByteArray; ...@@ -29,6 +29,7 @@ import com.google.android.exoplayer2.util.ParsableByteArray;
import com.google.android.exoplayer2.util.Util; import com.google.android.exoplayer2.util.Util;
import com.google.android.exoplayer2.video.AvcConfig; import com.google.android.exoplayer2.video.AvcConfig;
import com.google.android.exoplayer2.video.HevcConfig; import com.google.android.exoplayer2.video.HevcConfig;
import java.util.Arrays;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
...@@ -663,6 +664,8 @@ import java.util.List; ...@@ -663,6 +664,8 @@ import java.util.List;
List<byte[]> initializationData = null; List<byte[]> initializationData = null;
String mimeType = null; String mimeType = null;
byte[] projectionData = null;
int stereoMode = Format.NO_VALUE;
while (childPosition - position < size) { while (childPosition - position < size) {
parent.setPosition(childPosition); parent.setPosition(childPosition);
int childStartPosition = parent.getPosition(); int childStartPosition = parent.getPosition();
...@@ -705,6 +708,27 @@ import java.util.List; ...@@ -705,6 +708,27 @@ import java.util.List;
} else if (childAtomType == Atom.TYPE_pasp) { } else if (childAtomType == Atom.TYPE_pasp) {
pixelWidthHeightRatio = parsePaspFromParent(parent, childStartPosition); pixelWidthHeightRatio = parsePaspFromParent(parent, childStartPosition);
pixelWidthHeightRatioFromPasp = true; pixelWidthHeightRatioFromPasp = true;
} else if (childAtomType == Atom.TYPE_sv3d) {
projectionData = parseProjFromParent(parent, childStartPosition, childAtomSize);
} else if (childAtomType == Atom.TYPE_st3d) {
int version = parent.readUnsignedByte();
parent.skipBytes(3); // Flags.
if (version == 0) {
int layout = parent.readUnsignedByte();
switch (layout) {
case 0:
stereoMode = C.STEREO_MODE_MONO;
break;
case 1:
stereoMode = C.STEREO_MODE_TOP_BOTTOM;
break;
case 2:
stereoMode = C.STEREO_MODE_LEFT_RIGHT;
break;
default:
break;
}
}
} }
childPosition += childAtomSize; childPosition += childAtomSize;
} }
...@@ -716,7 +740,7 @@ import java.util.List; ...@@ -716,7 +740,7 @@ import java.util.List;
out.format = Format.createVideoSampleFormat(Integer.toString(trackId), mimeType, null, out.format = Format.createVideoSampleFormat(Integer.toString(trackId), mimeType, null,
Format.NO_VALUE, Format.NO_VALUE, width, height, Format.NO_VALUE, initializationData, Format.NO_VALUE, Format.NO_VALUE, width, height, Format.NO_VALUE, initializationData,
rotationDegrees, pixelWidthHeightRatio, drmInitData); rotationDegrees, pixelWidthHeightRatio, projectionData, stereoMode, drmInitData);
} }
/** /**
...@@ -1041,6 +1065,23 @@ import java.util.List; ...@@ -1041,6 +1065,23 @@ import java.util.List;
} }
/** /**
* Parses the proj box from sv3d box, as specified by https://github.com/google/spatial-media
*/
private static byte[] parseProjFromParent(ParsableByteArray parent, int position, int size) {
int childPosition = position + Atom.HEADER_SIZE;
while (childPosition - position < size) {
parent.setPosition(childPosition);
int childAtomSize = parent.readInt();
int childAtomType = parent.readInt();
if (childAtomType == Atom.TYPE_proj) {
return Arrays.copyOfRange(parent.data, childPosition, childPosition + childAtomSize);
}
childPosition += childAtomSize;
}
return null;
}
/**
* Parses the size of an expandable class, as specified by ISO 14496-1 subsection 8.3.3. * Parses the size of an expandable class, as specified by ISO 14496-1 subsection 8.3.3.
*/ */
private static int parseExpandableClassSize(ParsableByteArray data) { private static int parseExpandableClassSize(ParsableByteArray data) {
......
...@@ -373,6 +373,13 @@ public final class ParsableByteArray { ...@@ -373,6 +373,13 @@ public final class ParsableByteArray {
} }
/** /**
* Reads the next four bytes as a 32-bit floating point value.
*/
public float readFloat() {
return Float.intBitsToFloat(readInt());
}
/**
* Reads the next eight bytes as a 64-bit floating point value. * Reads the next eight bytes as a 64-bit floating point value.
*/ */
public double readDouble() { public double readDouble() {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment