summaryrefslogtreecommitdiffstats
path: root/media/libstagefright/MPEG4Writer.cpp
diff options
context:
space:
mode:
authorJames Dong <jdong@google.com>2010-08-16 18:39:28 -0700
committerJames Dong <jdong@google.com>2010-11-05 15:47:52 -0700
commitaca1fe35480ae76dd6bae167ade40adc955e2d0d (patch)
treeed1cb95800d38e5937ae59d01dc60cbdf3803a3a /media/libstagefright/MPEG4Writer.cpp
parentff5bfcf19da45e6bb0136ef818b7c4bf8fd8db3d (diff)
downloadframeworks_av-aca1fe35480ae76dd6bae167ade40adc955e2d0d.zip
frameworks_av-aca1fe35480ae76dd6bae167ade40adc955e2d0d.tar.gz
frameworks_av-aca1fe35480ae76dd6bae167ade40adc955e2d0d.tar.bz2
Rotation support
- We only support 0, 90, 180, and 270 degree clockwise rotation - Some players are known to ignore composition matrix in the MP4 file, although this is part of the MP4 file standard. Both QT and YT are supporting the rotation Change-Id: I1b7f66a801e9d9c49d889c9b06dd6173fa7e76c4
Diffstat (limited to 'media/libstagefright/MPEG4Writer.cpp')
-rw-r--r--media/libstagefright/MPEG4Writer.cpp81
1 files changed, 62 insertions, 19 deletions
diff --git a/media/libstagefright/MPEG4Writer.cpp b/media/libstagefright/MPEG4Writer.cpp
index a15c274..cbb1604 100644
--- a/media/libstagefright/MPEG4Writer.cpp
+++ b/media/libstagefright/MPEG4Writer.cpp
@@ -202,6 +202,7 @@ private:
// Simple validation on the codec specific data
status_t checkCodecSpecificData() const;
+ int32_t mRotation;
void updateTrackSizeEstimate();
void addOneStscTableEntry(size_t chunkId, size_t sampleId);
@@ -519,6 +520,58 @@ void MPEG4Writer::stopWriterThread() {
pthread_join(mThread, &dummy);
}
+/*
+ * MP4 file standard defines a composition matrix:
+ * | a b u |
+ * | c d v |
+ * | x y w |
+ *
+ * the element in the matrix is stored in the following
+ * order: {a, b, u, c, d, v, x, y, w},
+ * where a, b, c, d, x, and y is in 16.16 format, while
+ * u, v and w is in 2.30 format.
+ */
+void MPEG4Writer::writeCompositionMatrix(int degrees) {
+ LOGV("writeCompositionMatrix");
+ uint32_t a = 0x00010000;
+ uint32_t b = 0;
+ uint32_t c = 0;
+ uint32_t d = 0x00010000;
+ switch (degrees) {
+ case 0:
+ break;
+ case 90:
+ a = 0;
+ b = 0x00010000;
+ c = 0xFFFF0000;
+ d = 0;
+ break;
+ case 180:
+ a = 0xFFFF0000;
+ d = 0xFFFF0000;
+ break;
+ case 270:
+ a = 0;
+ b = 0xFFFF0000;
+ c = 0x00010000;
+ d = 0;
+ break;
+ default:
+ CHECK(!"Should never reach this unknown rotation");
+ break;
+ }
+
+ writeInt32(a); // a
+ writeInt32(b); // b
+ writeInt32(0); // u
+ writeInt32(c); // c
+ writeInt32(d); // d
+ writeInt32(0); // v
+ writeInt32(0); // x
+ writeInt32(0); // y
+ writeInt32(0x40000000); // w
+}
+
status_t MPEG4Writer::stop() {
if (mFile == NULL) {
return OK;
@@ -584,15 +637,7 @@ status_t MPEG4Writer::stop() {
writeInt16(0); // reserved
writeInt32(0); // reserved
writeInt32(0); // reserved
- writeInt32(0x10000); // matrix
- writeInt32(0);
- writeInt32(0);
- writeInt32(0);
- writeInt32(0x10000);
- writeInt32(0);
- writeInt32(0);
- writeInt32(0);
- writeInt32(0x40000000);
+ writeCompositionMatrix(0);
writeInt32(0); // predefined
writeInt32(0); // predefined
writeInt32(0); // predefined
@@ -885,7 +930,8 @@ MPEG4Writer::Track::Track(
mCodecSpecificData(NULL),
mCodecSpecificDataSize(0),
mGotAllCodecSpecificData(false),
- mReachedEOS(false) {
+ mReachedEOS(false),
+ mRotation(0) {
getCodecSpecificDataFromInputFormatIfPossible();
const char *mime;
@@ -1178,6 +1224,11 @@ status_t MPEG4Writer::Track::start(MetaData *params) {
startTimeUs = 0;
}
+ int32_t rotationDegrees;
+ if (!mIsAudio && params && params->findInt32(kKeyRotationDegree, &rotationDegrees)) {
+ mRotation = rotationDegrees;
+ }
+
mIsRealTimeRecording = true;
{
int32_t isNotRealTime;
@@ -2071,15 +2122,7 @@ void MPEG4Writer::Track::writeTrackHeader(
mOwner->writeInt16(mIsAudio ? 0x100 : 0); // volume
mOwner->writeInt16(0); // reserved
- mOwner->writeInt32(0x10000); // matrix
- mOwner->writeInt32(0);
- mOwner->writeInt32(0);
- mOwner->writeInt32(0);
- mOwner->writeInt32(0x10000);
- mOwner->writeInt32(0);
- mOwner->writeInt32(0);
- mOwner->writeInt32(0);
- mOwner->writeInt32(0x40000000);
+ mOwner->writeCompositionMatrix(mRotation);
if (mIsAudio) {
mOwner->writeInt32(0);