[xiph-commits] r15539 - trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder

cristianadam at svn.xiph.org cristianadam at svn.xiph.org
Wed Nov 26 13:21:40 PST 2008


Author: cristianadam
Date: 2008-11-26 13:21:40 -0800 (Wed, 26 Nov 2008)
New Revision: 15539

Modified:
   trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.cpp
   trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.h
Log:
Fixed flipped recordings when a RGB source was used.

Modified: trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.cpp
===================================================================
--- trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.cpp	2008-11-26 14:33:26 UTC (rev 15538)
+++ trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.cpp	2008-11-26 21:21:40 UTC (rev 15539)
@@ -1,6 +1,8 @@
 //===========================================================================
 //Copyright (C) 2003, 2004 Zentaro Kavanagh
 //
+//Copyright (C) 2008 Cristian Adam
+//
 //Redistribution and use in source and binary forms, with or without
 //modification, are permitted provided that the following conditions
 //are met:
@@ -45,6 +47,7 @@
 	,	m_uptoFrame(0)
 	,	m_hasBegun(false)
 	,	m_numFrames(0)
+    ,   m_isImageFlipped(false)
 
 {
 	//debugLog.open("g:\\logs\\theoencfiltinput.log", ios_base::out);
@@ -549,16 +552,9 @@
 }
 //-------------------------------------------------------------------------
 
-long TheoraEncodeInputPin::encodeRGB24toYV12(unsigned char* inBuf, long inNumBytes) {
-	//Blue Green Red Blue Green Red.
-	unsigned long locNumPixels = (inNumBytes/3);
-	unsigned char* locAYUVBuf = new unsigned char[locNumPixels<<2];   //4 bytes per pixel
-
+long TheoraEncodeInputPin::encodeRGB24toYV12(unsigned char* inBuf, long inNumBytes) 
+{
 	/*
-
-
-
-
 	Conversion from RGB to YUV is defined by starting with the following:
 
 	L = Kr * R + Kb * B + (1 – Kr – Kb) * G
@@ -622,10 +618,15 @@
 	/*
 	Kr = 0.299
 	Kb = 0.114
+	*/
 
+    //Blue Green Red Blue Green Red.
+    unsigned long numPixels = inNumBytes / 3;
 
-	*/
+    static std::vector<unsigned char> ayuvBuf;
+    ayuvBuf.resize(numPixels * 4);
 
+
 	//Scaled by factor of 65536 to integerise.
 	const int KR = 19596;
 	const int KB = 7472;
@@ -640,88 +641,69 @@
 	int locB = 0;
 	int locR = 0;
 
-	//unsigned char* locSourcePtr = inBuf;
-	unsigned char* locDestPtr = locAYUVBuf;
+    //unsigned char* locSourcePtr = inBuf;
+    unsigned char* pDest = &*ayuvBuf.begin();
 
     //SOURCE: Blue Green Red Blue Green Red.
-	//DEST: v u y a
+    //DEST: v u y a
 
-	unsigned char* locSourceEnds = inBuf + (locNumPixels * 3);
+    unsigned char* pSourceEnds = inBuf + inNumBytes;
 
-	//Upside down... Upside down !
-	//for (unsigned char* locSourcePtr = inBuf; locSourcePtr < locSourceEnds; locSourcePtr += 3) {
-	//	locB = locSourcePtr[0];					//Blue
-	//	locL = KB * (locB);						//Blue
-	//	
-	//	locL += G_FACTOR * (locSourcePtr[1]);	//Green
+    unsigned char* pSource = 0;
+    unsigned char* pEnd = 0;
 
-	//	locR = locSourcePtr[2];					//Red
-	//	locL += KR * (locR);					//Red
+    long stride = 0;
 
-	//	
-	//	*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);			//V for Victor
-	//	*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);			//U for ugly
-	//	*(locDestPtr++) = CLIP3(0, 255, locL >> 16);												//Y for yellow
-	//	*(locDestPtr++) = 255;																		//A for alpha
-	//}
-	
+    if (m_isImageFlipped)
+    {
+        stride = m_width * 3;
+        pSource = inBuf;
+        pEnd = pSourceEnds;
+    }
+    else
+    {
+        // Negative stride
+        stride = 0 - m_width * 3;
+        pSource = pSourceEnds - std::abs(stride);
+        pEnd = inBuf - std::abs(stride);
+    }
 
-	unsigned char* locColSourcePtr = NULL;
-	unsigned char* locColEndPtr = NULL;
-	unsigned long locLineLength = m_width * 3;
-	unsigned long col = 0;
-	for (unsigned char* locSourcePtr = locSourceEnds - locLineLength; locSourcePtr >= inBuf; locSourcePtr -= locLineLength) {
-		//
-		//for(unsigned char* locColSourcePtr = locSourcePtr, int i = 0; i < m_width; i++, locColSourcePtr +=4) {
-		//
-		locColSourcePtr = locSourcePtr;
-		locColEndPtr = locColSourcePtr + locLineLength;
-		while (locColSourcePtr < locColEndPtr) {
-			locB = locColSourcePtr[0];					//Blue
-			locL = KB * (locB);							//Blue
-		
-			locL += G_FACTOR * (locColSourcePtr[1]);	//Green
+    for (; pSource != pEnd; pSource += stride) 
+    {
+        unsigned char* pColSource = pSource;
+        unsigned char* pColEnd = pColSource + std::abs(stride);
 
-			locR = locColSourcePtr[2];					//Red
-			locL += KR * (locR);						//Red
+        while (pColSource < pColEnd) 
+        {
+            locB = pColSource[0];					//Blue
+            locL = KB * (locB);						//Blue
 
-		
-			*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);			//V for Victor
-			*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);			//U for ugly
-			*(locDestPtr++) = CLIP3(0, 255, locL >> 16);												//Y for yellow
-			*(locDestPtr++) = 255;																		//A for alpha
+            locL += G_FACTOR * (pColSource[1]);	    //Green
 
-			//debugCount++;		
-			locColSourcePtr+=3;
+            locR = pColSource[2];					//Red
+            locL += KR * (locR);					//Red
 
-		}
+            *(pDest++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);	//V for Victor
+            *(pDest++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);	//U for ugly
+            *(pDest++) = CLIP3(0, 255, locL >> 16);											//Y for yellow
+            *(pDest++) = 255;														        //A for alpha
 
+            pColSource += 3;
+        }
+    }
 
-	}
+    encodeAYUVtoYV12(&*ayuvBuf.begin(), ayuvBuf.size());
 
-
-	//Still need to pass through to the AYUV conversion.
-	encodeAYUVtoYV12(locAYUVBuf, locNumPixels<<2);
-	delete[] locAYUVBuf;
-	locAYUVBuf = NULL;
-
 	return 0;
 }
 
 
 
-long TheoraEncodeInputPin::encodeRGB32toYV12(unsigned char* inBuf, long inNumBytes) {
-	//Blue Green Red Alpha Blue Green Red Alpha
-	//debugLog<<"EncodeRGB32 To YV12 :"<<endl;
+long TheoraEncodeInputPin::encodeRGB32toYV12(unsigned char* inBuf, long inNumBytes) 
+{
+	static std::vector<unsigned char> ayuvBuf;
+    ayuvBuf.resize(inNumBytes);
 
-	unsigned long locNumPixels = (inNumBytes/4);
-	
-	//debugLog<<"EncodeRGB32 To YV12 : Num pixels = "<<locNumPixels<<endl;
-	//debugLog<<"EncodeRGB32 To YV12 : Num BYtes = "<<inNumBytes<<endl;
-	unsigned char* locAYUVBuf = new unsigned char[inNumBytes];   //4 bytes per pixel
-
-	//debugLog<<"EncodeRGB32 To YV12 :"<<endl;
-
 	//Scaled by factor of 65536 to integerise.
 	const int KR = 19596;
 	const int KB = 7472;
@@ -737,89 +719,63 @@
 	int locR = 0;
 
 	//unsigned char* locSourcePtr = inBuf;
-	unsigned char* locDestPtr = locAYUVBuf;
+	unsigned char* pDest = &*ayuvBuf.begin();
 
     //SOURCE: Blue Green Red Blue Green Red.
 	//DEST: v u y a
 
-	unsigned char* locSourceEnds = inBuf + (inNumBytes);
-	//debugLog<<"EncodeRGB32 To YV12 : Source Starts = "<<(int)inBuf<<endl;
-	//debugLog<<"EncodeRGB32 To YV12 : Source Ends = "<<(int)locSourceEnds<<endl;
+	unsigned char* pSourceEnds = inBuf + inNumBytes;
 
-	//Debugging only... all refs to debugCount remove later
-	//unsigned long debugCount = 0;
-	//
+    unsigned char* pSource = 0;
+    unsigned char* pEnd = 0;
 
-	//Upside down !!
-	//for (unsigned char* locSourcePtr = inBuf; locSourcePtr < locSourceEnds; locSourcePtr += 4) {
-	//	locB = locSourcePtr[0];					//Blue
-	//	locL = KB * (locB);						//Blue
-	//	
-	//	locL += G_FACTOR * (locSourcePtr[1]);	//Green
+    long stride = 0;
 
-	//	locR = locSourcePtr[2];					//Red
-	//	locL += KR * (locR);					//Red
+    if (m_isImageFlipped)
+    {
+        stride = m_width * 4;
+        pSource = inBuf;
+        pEnd = pSourceEnds;
+    }
+    else
+    {
+        // Negative stride
+	    stride = 0 - m_width * 4;
+        pSource = pSourceEnds - std::abs(stride);
+        pEnd = inBuf - std::abs(stride);
+    }
 
-	//	
-	//	*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);			//V for Victor
-	//	*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);			//U for ugly
-	//	*(locDestPtr++) = CLIP3(0, 255, locL >> 16);												//Y for yellow
-	//	*(locDestPtr++) = locSourcePtr[3];																		//A for alpha
+    for (; pSource != pEnd; pSource += stride) 
+    {
+        unsigned char* pColSource = pSource;
+        unsigned char* pColEnd = pColSource + std::abs(stride);
 
-	//	debugCount++;
-	//}
-	unsigned char* locColSourcePtr = NULL;
-	unsigned char* locColEndPtr = NULL;
-	unsigned long locLineLength = m_width * 4;
-	unsigned long col = 0;
-	for (unsigned char* locSourcePtr = locSourceEnds - locLineLength; locSourcePtr >= inBuf; locSourcePtr -= locLineLength) {
-		//
-		//for(unsigned char* locColSourcePtr = locSourcePtr, int i = 0; i < m_width; i++, locColSourcePtr +=4) {
-		//
-		locColSourcePtr = locSourcePtr;
-		locColEndPtr = locColSourcePtr + locLineLength;
-		while (locColSourcePtr < locColEndPtr) {
-			locB = locColSourcePtr[0];					//Blue
-			locL = KB * (locB);							//Blue
-		
-			locL += G_FACTOR * (locColSourcePtr[1]);	//Green
+        while (pColSource < pColEnd) 
+        {
+            locB = pColSource[0];					//Blue
+            locL = KB * (locB);						//Blue
 
-			locR = locColSourcePtr[2];					//Red
-			locL += KR * (locR);						//Red
+            locL += G_FACTOR * (pColSource[1]);	    //Green
 
-		
-			*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);			//V for Victor
-			*(locDestPtr++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);			//U for ugly
-			*(locDestPtr++) = CLIP3(0, 255, locL >> 16);												//Y for yellow
-			*(locDestPtr++) = locColSourcePtr[3];														//A for alpha
+            locR = pColSource[2];					//Red
+            locL += KR * (locR);					//Red
 
-			//debugCount++;		
-			locColSourcePtr+=4;
+            *(pDest++) = CLIP3(0, 255, ((112 * ( (locR<<16) - locL)) / V_FACTOR) + 128);	//V for Victor
+            *(pDest++) = CLIP3(0, 255, ((112 * ( (locB<<16) - locL)) / U_FACTOR) + 128);	//U for ugly
+            *(pDest++) = CLIP3(0, 255, locL >> 16);											//Y for yellow
+            *(pDest++) = pColSource[3];														//A for alpha
 
-		}
-
-
-	}
-
-	//debugLog<<"EncodeRGB32 To YV12 : debugCount = "<<debugCount<<endl;
-
-	//ASSERT(debugCount == locNumPixels);
+            pColSource += 4;
+        }
+    }
 	
-	ASSERT(locDestPtr == (locAYUVBuf + inNumBytes));
-
-	//debugLog<<"EncodeRGB32 To YV12 : Calling AYUV to YV12 conversion"<<endl;
-	//Still need to pass through to the AYUV conversion.
-
-	encodeAYUVtoYV12(locAYUVBuf, inNumBytes);
-	delete[] locAYUVBuf;
-	locAYUVBuf = NULL;
-
+	encodeAYUVtoYV12(&*ayuvBuf.begin(), ayuvBuf.size());
+	
 	return 0;
 }
 
 
 
-
 long TheoraEncodeInputPin::encodeAYUVtoYV12(unsigned char* inBuf, long inNumBytes) {
 
 	//TODO::: This doesn't appear to do offsets.
@@ -1467,7 +1423,12 @@
 
 			m_averageTimePerFrame = videoFormat->AvgTimePerFrame;
 			m_width = videoFormat->bmiHeader.biWidth;
-			m_height = videoFormat->bmiHeader.biHeight;
+            m_height = std::abs(videoFormat->bmiHeader.biHeight);
+
+            if (videoFormat->bmiHeader.biHeight > 0)
+            {
+                m_isImageFlipped = true;
+            }
 		}
 		else if (inMediaType->formattype == FORMAT_VideoInfo)
 		{
@@ -1475,7 +1436,12 @@
 
 			m_averageTimePerFrame = videoFormat->AvgTimePerFrame;
 			m_width = videoFormat->bmiHeader.biWidth;
-			m_height = videoFormat->bmiHeader.biHeight;
+            m_height = std::abs(videoFormat->bmiHeader.biHeight);
+
+            if (videoFormat->bmiHeader.biHeight > 0)
+            {
+                m_isImageFlipped = true;
+            }
 		}
 
 		if (m_averageTimePerFrame == 0)
@@ -1499,4 +1465,4 @@
 theora_info* TheoraEncodeInputPin::theoraInfo() 
 {
 	return &m_theoraInfo;
-}
\ No newline at end of file
+}

Modified: trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.h
===================================================================
--- trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.h	2008-11-26 14:33:26 UTC (rev 15538)
+++ trunk/oggdsf/src/lib/codecs/theora/filters/dsfTheoraEncoder/TheoraEncodeInputPin.h	2008-11-26 21:21:40 UTC (rev 15539)
@@ -97,6 +97,8 @@
 
 	bool m_hasBegun;
 
+    bool m_isImageFlipped;
+
 	/* To adapt theora frame rate to variable directshow clock */
 	unsigned __int64 m_numFrames;
 



More information about the commits mailing list