norman's blog

Notes of an amnesiac.
Never stop thinking.
Find an aesthetic description.

Thursday, June 4, 2009

CvArr, CvMat and IplImage

Step, Width and Height

Both IplImage and CvMat have the above three elements, which make them compatible. For CvMat, the three element are named as step, cols and rows; while for IplImage, they are denoted as widthStep, width and height
The step element in the matrix array is the length in bytes of a row in the matrix. In that structure, cols or width alone is not enough to move between matrix rows because, for machine efficiency, matrix or image allocation is done to the nearest four-byte boundary. Thus for instance, a matrix of width three bytes would be allocated four bytes with the last one ignored. When using cvCreateMat() and cvCreateImage() to creates the header and allocates data of IplImage and CvMat, the cvCreateImage will align each row on four-byte boundaries while cvCreateMat align rows to minimal possible steps.
Codes for creating a CvMat object according to four-byte alignment rule manually:
CvMat* mat = cvCreateMatHeader(rows, cols, type);
mat->step = 4 * (mat->cols * CV_ELEM_SIZE1(mat->type) * CV_MAT_CN(mat->type) / 4 + 1);//critical
cvCreateData(mat);

Transform between IplImage and CvMat

cvGetMat and cvGetImage are used to perform transformation between IplImage and CvMat, in which there is no new memory allocated for block data. The new object just points to the data block of original object, inheriting the setup of alignment(including width, height and step).

To transform from IplImage to CvMat, Use function:

CvMat* cvGetMat( const CvArr* arr, CvMat* mat, int* coi = 0, int allowND );
The function cvGetMat returns matrix header for the input array that can be matrix - CvMat*, image - IplImage* or multi-dimensional dense array - CvMatND* (latter case is allowed only if allowND != 0) .
In the case of matrix the function simply returns the input pointer.
In the case of IplImage* or CvMatND* it initializes mat structure with parameters of the current image ROI and returns pointer to this temporary structure.
Usage:
CvMat stub, *dst_mat;
dst_mat = cvGetMat(src_img, &stub, 0, 0);

To transform from CvMat to IplImage, Use function:

IplImage* cvGetImage( const CvArr* arr, IplImage* image_header );  
The function cvGetImage returns image header for the input array that can be matrix - CvMat*, or image - IplImage*.
In the case of image the function simply returns the input pointer.
In the case of CvMat* it initializes image_header structure with parameters of the input matrix.
Usage:
IplImage stub, *dst_img;
dst_img = cvGetImage(src_mat, &stub);
Note that if we transform IplImage to CvMat and then transform CvMat back to IplImage, we can get different headers if the ROI is set, and thus some IPL functions that calculate image stride from its width and align may fail on the resultant image.
These two functions are error prone due to the directly pointing to the original data block and the different default alignment rules of CvMat and IplImage. A practical way to avoid conflicts is to align CvMat manually.

Labels:

Read more!

Tuesday, June 2, 2009

CvSeq Operation

The normal way:

  CvSeq *seq = cvCreateSeq( 0, sizeof(CvSeq), elem_size, storage );
  cvSeqPush(seq, &elem);

The faster way:

  CvSeq* seq = NULL;
  CvSeqWriter writer;
  cvStartWriteSeq( 0, sizeof(CvSeq), elem_size, storage, &writer );
  //...
  CV_WRITE_SEQ_ELEM( elem, writer );
  //...
  seq = cvEndWriteSeq( &writer );  

Labels:

Read more!

cvWaitKey

Waits for a pressed key
int cvWaitKey( int delay=0 );
delay
Delay in milliseconds.
Return
Maybe ASCII code
The function cvWaitKey waits for key event infinitely (delay<=0) or for "delay" milliseconds. Returns the code of the pressed key or -1 if no key were pressed until the specified timeout has elapsed.
Note: This function is the only method in HighGUI to fetch and handle events so it needs to be called periodically for normal event processing, unless HighGUI is used within some environment that takes care of event processing.

Labels:

Read more!

Video I/O Functions in OpenCV

Video Capture

CvCapture* capture = NULL;
IplImage *frame = NULL;
if(is_video_file(input))
  capture = cvCreateFileCapture( input );
else if ( isdigit(input[0]) )
  capture = cvCreateCameraCapture( atoi(input) );
//cvGetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH);
//cvGetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT);
if(capture)
{
   for(;;)
   {
     if(!frame = cvQueryFrame( capture ))
       continue;//break;
     process_frame(frame);
     if( cvWaitKey( 10 ) >= 0 )
       break;
   }
}
cvReleaseImage( &frame );
cvReleaseCapture( &capture );

Video Writing

CvVideoWriter *writer = cvCreateVideoWriter(
            const char* filename, int fourcc, double fps, CvSize frame_size, int is_color=1);
IplImage *frame = NULL;
if(writer)
{
  for(;;)
  {
    if(!frame = get_frame();
      continue;
    cvWriteFrame(writer, frame);
    if( cvWaitKey( 10 ) >= 0 )
      break;
  }
}
cvReleaseImage( &frame );
cvReleaseVideoWriter( &writer );

Labels:

Read more!

Sunday, May 3, 2009

OpenCV

Supported image formats of cvLoadImage: 
BMP, DIB, JPEG, JPG, JPE, PNG, PBM, PGM, PPM, SR, RAS, TIFF, TIF

install in ubuntu
http://dircweb.king.ac.uk/reason/opencv_cvs.php#Hardy
Installing OpenCV for Ubuntu 8.04 (Hardy) We have tried the officially supported version of this, i.e. runnning KDE 3.x instead of 4.x Note that installation on version 7.10 follows the same procedure, but I never got round documenting it Things seem to be getting easier! Thanks to Leeds University for their guide on using OpenCV 1. sudo apt-get install build-essential to get compiler, ld, make, .... 2. Install the other necessary packages: sudo apt-get install libgtk2.0-dev libavcodec-dev libavformat-dev libjpeg62-dev libtiff4-dev 3. Now download and untar version 1.0.0 of OpenCV from http://sourceforge.net/project/showfiles.php?group_id=22870&package_id=16948 4. Now do * ./configure --prefix=/opt/opencv --enable-apps --enable-shared --with-ffmpeg --with-gnu-ld --with-x --without-quicktime CXXFLAGS=-fno-strict-aliasing * Check that the above produces no error and that in particular it reports ffmpeg as yes. If this is not the case there is no point in continuing! * make (if you have tried making other configurations you could also do a make clean before make) * sudo make install * sudo vi /etc/ld.so.conf.d/opencv.conf and add the line /opt/opencv/lib. Then sudo ldconfig 5. sudo vi /etc/bash.bashrc and add the lines: PKG_CONFIG_PATH=$PKG_CONFIG_PATH:/opt/opencv/lib/pkgconfig export PKG_CONFIG_PATH (this setting will be activated if you launch a new console/terminal or if you re-login) 6. So far so good? Now try running some sample programs. Donwload and untar this. Then: ./build-all.sh edge fruits.jpg (it shows that you can open and display a jpg file) cvplayer-v2 SEQ-003-C5_X4.mpg (it shows you can open and display an mpg video file, with ffmpeg)

Labels:

Read more!