VideoHelp Forum




+ Reply to Thread
Results 1 to 12 of 12
  1. Member
    Join Date
    Aug 2009
    Location
    United States
    Search Comp PM
    Hi everyone,

    I have read a frame from a standard 176x144, YUV 4:2:0 sequence and performed Integer transform and Inverse Integer transform on it.

    But when i try to re-write the frame I get a lot of horizontal pink lines. When I compare the pixel values of the frame before and after the transform there is hardly a difference of 1 or 2.

    Why is this happening?



    test.yuv
    Quote Quote  
  2. Member
    Join Date
    Jul 2009
    Location
    Spain
    Search Comp PM
    Without more information, the best we can say is you must be doing it wrong.

    What software are you using to read, process and write the frame, and to do the pixel comparison?

    If you have written your own code, please post the relevant fragments here.
    Quote Quote  
  3. Member
    Join Date
    Aug 2009
    Location
    United States
    Search Comp PM
    Hi Gavino
    Thanks for your reply ....

    Ok..

    1. I am writing all my code in VC++ IDE but in C. (which I am more comfortable with).

    2. The sequence I am reading (and have posted in my earlier post) is FOREMAN sequence. (176*144)

    3. I am using fread and fwrite/fprintf to read and write the frame. I have posted my code below. I am also using Integer transform instead of DCT. This I read from the H.264 standar and with post and pre-scaling it works very well.

    The relevant parts of the code are pasted below.

    Reading a frame: after opening it in "rb" mode

    Code:
    		fread (sYUVRead.Y, 1, (nSize), pInpVideo);
    		fread (sYUVRead.U, 1, (nSize)/4, pInpVideo);
    		fread (sYUVRead.V, 1, (nSize)/4, pInpVideo);

    The pointers are of type "unsigned char"

    Then I use the pixel data to perform some float and int operations during the transform and scaling operations. I then write back the info using %c and fprintf to write a frame as follows.


    BLOCK_SIZE is 4 and I have written a loop to choose every 4x4 block and transmit it to the Integer transform. pOutput is a integer pointer.

    Code:
    	for(row=0; row < sFileInfo.nHeight/4; row++)
    	{
    		for(block_num=0; block_num < sFileInfo.nWidth/4; block_num++)
    		{
    				for(i=0;i<BLOCK_SIZE;i++)
    					for(j=0;j<BLOCK_SIZE;j++)
    						*(block[i]+j) = *(sYUVRead.Y + (4*row+i)*sFileInfo.nWidth + block_num*BLOCK_SIZE + j);
    					
    	
    				ForwardTrans(block,tblock);		
    				InverseTrans(tblock,block);		
    
    				
    		for(i=0;i<BLOCK_SIZE;i++)
    			for(j=0;j<BLOCK_SIZE;j++)
    				*(pOutput + j + (4*row+i)*(sFileInfo.nWidth) + (block_num*BLOCK_SIZE) ) = *(block[i]+j);		
    		}
    	}
    
    	
    	for(i=0;i<176*144;i++)
    		fprintf(pTrial,"%c",*(pOutput+i));
    To compare the pixel values I just print out the frames in a text file with one value per line and then compare them. I also took the PSNR value and it comes to 63dB.

    Any ideas what is going wrong?

    Then I do the same for U and V frames and use the same fprintf statement.

    This gives rise to the pink lines in the frame like the one i posted earlier.
    Quote Quote  
  4. Member
    Join Date
    Jul 2009
    Location
    Spain
    Search Comp PM
    The code you posted seems OK, but only shows the luma processing (Y plane)
    When processing the chroma (U, V) planes, have you changed the loop ranges to allow for the width and height being halved (two nested processing loops and the writing loop)?
    Quote Quote  
  5. Member
    Join Date
    Aug 2009
    Location
    United States
    Search Comp PM
    This is what I am doing for U and V frames. I think I have handled the loop counters correctly because the PSNR is really high.


    Code:
    	for(row=0; row < sFileInfo.nHeight/(8); row++)
    	{
    		for(block_num=0; block_num < sFileInfo.nWidth/(4*2); block_num++)
    		{
    			for(i=0;i<BLOCK_SIZE;i++)
    				for(j=0;j<BLOCK_SIZE;j++)
    					*(block[i]+j) = *(sYUVRead.U + (4*row+i)*sFileInfo.nWidth + block_num*BLOCK_SIZE + j);
    
    				ForwardTrans(block,tblock);		
    				InverseTrans(tblock,block);		
    
    
    		for(i=0;i<BLOCK_SIZE;i++)
    			for(j=0;j<BLOCK_SIZE;j++)
    				*(pOutput + j + (4*row+i)*(sFileInfo.nWidth) + (block_num*BLOCK_SIZE) ) = *(block[i]+j);		
    
    		}
    	}
    
    	for(i=0;i<176*144/4;i++)
    	{
    		fprintf(pTrial,"%c",*(pOutput+i));
    	}
    Quote Quote  
  6. Somewhere in there you overwrote every other scanline of the U and V planes with data from the Y plane.
    Quote Quote  
  7. Member
    Join Date
    Jul 2009
    Location
    Spain
    Search Comp PM
    Originally Posted by krao
    Code:
    	for(row=0; row < sFileInfo.nHeight/(8); row++)
    	{
    		for(block_num=0; block_num < sFileInfo.nWidth/(4*2); block_num++)
    		{
    			for(i=0;i<BLOCK_SIZE;i++)
    				for(j=0;j<BLOCK_SIZE;j++)
    					*(block[i]+j) = *(sYUVRead.U + (4*row+i)*sFileInfo.nWidth + block_num*BLOCK_SIZE + j);
                  ...
    I think this should be sFileInfo.nWidth/2.
    Similarly in the setting of the output pixel.
    Quote Quote  
  8. Member
    Join Date
    Aug 2009
    Location
    United States
    Search Comp PM
    Oh great ... that was the error. Thanks a lot !

    Btw .. is there any book which teaches a lot of this kind of programming? Or is the trial and error way? Also is there any freeware with which I can analyse the frame info? YUVtools is expensive and the trial is only for 30 days... any suggestions?
    Quote Quote  
  9. I recommend you use 2d arrays. It makes your code much clearer. array2d[y][x] is simpler than array[y*width + x];
    Quote Quote  
  10. Member
    Join Date
    Aug 2009
    Location
    United States
    Search Comp PM
    Oh? I must give that a shot too. I had a look at H.263 codec and formed an idea in my head that pointers are the way to go when I wrote my own codec. Hence the pointer heavy style.
    Quote Quote  
  11. In my opinion, everything you do to make your code more readable (and more easily understood by others or yourself in the future) will pay off in the long run.

    Here's a sample of runtime allocated 2d arrays including a YV12 allocator:

    readyuv.zip
    Quote Quote  



Similar Threads

Visit our sponsor! Try DVDFab and backup Blu-rays!