⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 main.c

📁 face recognition using hmm. first version.
💻 C
字号:
#ifdef _CH_
#define WIN32
#error "The file needs cvaux, which is not wrapped yet. Sorry"
#endif

#ifndef _EiC
#include "cv.h"
#include "highgui.h"

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <math.h>
#include <float.h>
#include <limits.h>
#include <time.h>
#include <ctype.h>
#include <direct.h>
#endif

#ifdef _EiC
#define WIN32
#endif

#define MARGIN 15			// add margin to the detect face window
int  imageCount=0;			// image index for storing clipped faces
char strImageDir[255];		// directory for face images to be clipped
char strPersonName[255];	// person name, used for locating the directory
char strFilePrefix[255];	// image prefix for the stored images
int startFrame=0;			//start frame number
int endFrame=50;			//end frame number
int  bSaveFaces;			// toggle for saving faces
int bFirstFace = 1;     // flag for first face

static CvMemStorage* storage = 0;
static CvHaarClassifierCascade* cascade = 0;

void FindFaces( IplImage* image );
void SaveFace(IplImage* src, int x, int y, int w, int h);

int bFindFromImageSeq = 0;

const char* cascade_name =
    "--cascade=../../data/haarcascades/haarcascade_frontalface_alt.xml";

char *ReadConfigLine(FILE *fp){
	char line[255];
	char c;
	int idx=0;

	line[0]='\0';
	while(!feof(fp)){
		if(fgetc(fp)=='=')break;
	}
	while(!feof(fp)&&(c=fgetc(fp))!='\n'){
		line[idx++]=c;
	}
	line[idx]='\0';
	return line;

}


void loadconfig(char *configFilename){
	FILE *fp;
	char strStartFrame[255];
	char strEndFrame[255];

	if(!(fp=fopen(configFilename,"r"))){
		printf("Cannot load config.ini!\nexiting.......\n");
		exit(0);
	}

	strcpy(strImageDir, ReadConfigLine(fp));
	printf("source dir:%s\n", strImageDir);
	strcpy(strPersonName, ReadConfigLine(fp));
	printf("source person:%s\n", strPersonName);
	strcpy(strFilePrefix, ReadConfigLine(fp));
	printf("source prefix:%s\n", strFilePrefix);
	strcpy(strStartFrame, ReadConfigLine(fp));
	startFrame=atoi(strStartFrame);
	printf("start frame:%d\n", startFrame);
	strcpy(strEndFrame, ReadConfigLine(fp));
	endFrame=atoi(strEndFrame);
	printf("end frame:%d\n", endFrame);
	printf("config loaded....\n");
	fclose(fp);
}

int main( int argc, char** argv )
{
    CvCapture* capture = 0;
    IplImage *frame, *frame_copy = 0;
    const char *pName;
	char input[255];
	const char *input_name;
	char filename[255];
	char dirname[255];
    int optlen = strlen("--cascade=");
	int c, i;

    pName = argc > 1 ? argv[1] : 0;
	if(argc>1){
		sprintf(input, "%s.avi", pName);
		input_name = input;
	}
	else
		input_name = 0;

	cascade_name = cascade_name+optlen;

    cascade = (CvHaarClassifierCascade*)cvLoad( cascade_name, 0, 0, 0 );
    
    if( !cascade )
    {
        fprintf( stderr, "ERROR: Could not load classifier cascade\n" );
        return -1;
    }

	loadconfig("config.ini");
	if(argc>1){
		sprintf(strPersonName, "%s", pName);
		//create directory
		sprintf(dirname, "%s\\%s", strImageDir, strPersonName);
		_mkdir(dirname);
	}

    storage = cvCreateMemStorage(0);
	
    cvNamedWindow( "Video", 1 );

	//check if find faces from a sequnce of images
	if(bFindFromImageSeq){
		for(i=0; i<200; i++){
			sprintf(filename, "%s\\%s\\%s%03d.jpg", strImageDir, strPersonName, strFilePrefix, i);
			printf(filename);
			printf("\n");
			frame = cvLoadImage(filename, 1);
			FindFaces( frame );

			c = cvWaitKey(10);
			switch( c )
			{
			case '\x1b':
				printf("Exiting ...\n");
				goto exit_main;
			case 's':
				bSaveFaces = !bSaveFaces;
				printf("face clipping: %d\n", bSaveFaces);
				break;
			}
		}
	}
    
	if( !input_name || (isdigit(input_name[0]) && input_name[1] == '\0') ){
        capture = cvCaptureFromCAM( !input_name ? 0 : input_name[0] - '0' );
		bSaveFaces = 0; //let user start the clipping face process
	}
	else{
        capture = cvCaptureFromAVI( input_name ); 
		bSaveFaces = 1; //auto start clipping face process
	}
	printf("press \'s\' to toggle the face clipping process...\n");
	printf("face clipping: %d\n", bSaveFaces);

    if( capture )
    {
        for(;;)
        {
            if( !cvGrabFrame( capture ))
                break;
            frame = cvRetrieveFrame( capture );
            if( !frame )
                break;
            if( !frame_copy )
                frame_copy = cvCreateImage( cvSize(frame->width,frame->height),
                                            IPL_DEPTH_8U, frame->nChannels );
            if( frame->origin == IPL_ORIGIN_TL )
                cvCopy( frame, frame_copy, 0 );
            else
                cvFlip( frame, frame_copy, 0 );
            
            FindFaces( frame_copy );

			c = cvWaitKey(10);
			switch( c )
			{
			case '\x1b':
				printf("Exiting ...\n");
				goto exit_main;
			case 's':
				bSaveFaces = !bSaveFaces;
				printf("face clipping: %d\n", bSaveFaces);
				break;
			}
        }

        cvReleaseImage( &frame_copy );
        cvReleaseCapture( &capture );
    }
    else
    {
		printf("FindFaces: extracts faces from live cams or avi videos.\n");
		printf("   syntax: FacesFaces [filename.avi]\n");
		printf("           neither live cams nor avi videos are found.\n");
		printf("           exiting.....\n");
    }
    
exit_main:
    cvDestroyWindow("Video");

    return 0;
}

void SavePgm(IplImage *gray, char *filename){
	FILE *fp;
	int i, j;

	if(!(fp=fopen(filename, "wb"))){
		printf("Cannot write to file\n");
		exit(0);
	}
	fprintf(fp, "P5\n%d %d\n255\n", gray->height, gray->width);
	for(j=0;j<gray->height; j++){
		for(i=0; i<gray->width; i++){
			fputc((gray->imageData[j*gray->widthStep+i])&255,fp);
		}
	}

	fclose(fp);
}

void SaveFace( IplImage* src, int x, int y, int w, int h){
    IplImage *target, *gray;
	char filename[255];
	int i,j,x2,y2;

	if(!w || !h) return;

	//adjust window size to include more of the face
	x2=x+w; y2=y+h;
	if(x-MARGIN>=0)
		x=x-MARGIN;
	else
		x=0;
	if(y-MARGIN>=0)
		y=y-MARGIN;
	else
		y=0;
	if(x2+MARGIN<src->width)
		x2=x2+MARGIN;
	else
		x2=src->width-1;
	if(y2+MARGIN<src->height)
		y2=y2+MARGIN;
	else
		y2=src->height-1;
	w = x2-x;
	h = y2-y;

	// create target image
	target = cvCreateImage( cvSize(w,h), 8, 3 );
	gray = cvCreateImage(cvSize(w,h), 8, 1);

	for (i=y; i<y+h; i++){
		for (j=x; j<x+w; j++){
			target->imageData[(i-y)*target->widthStep+(j-x)*3]=
				src->imageData[i*src->widthStep+j*3];
			target->imageData[(i-y)*target->widthStep+(j-x)*3+1]=
				src->imageData[i*src->widthStep+j*3+1];
			target->imageData[(i-y)*target->widthStep+(j-x)*3+2]=
				src->imageData[i*src->widthStep+j*3+2];
		}
	}
	sprintf(filename, "%s\\%s\\%s%03d.pgm", strImageDir, strPersonName, strPersonName, imageCount++);
	
	cvCvtColor(target, gray, CV_BGR2GRAY);
	/*
	if(!(fp=fopen(filename, "wb"))){
		printf("Cannot write to file\n");
		exit(0);
	}
	fprintf(fp, "P5\n%d %d\n255\n", gray->height, gray->width);
	//for(j=0;j<gray->widthStep*gray->height; j++){
	fwrite(gray->imageData, gray->widthStep*gray->height, 1, fp);
		
	fclose(fp);
	*/
	SavePgm(gray, filename);

	if(bFirstFace){
		sprintf(filename, "%s\\%s\\%s.jpg", strImageDir, strPersonName, strPersonName);
		cvSaveImage(filename, target);
		bFirstFace = 0;
	}
}

void FindFaces( IplImage* img )
{
    int scale = 1;
    CvPoint pt1, pt2;
    int i;

    cvClearMemStorage( storage );

    if( cascade )
    {
        CvSeq* faces = cvHaarDetectObjects( img, cascade, storage,
                                            1.1, 2, CV_HAAR_DO_CANNY_PRUNING,
                                            cvSize(40, 40) );
        for( i = 0; i < (faces ? faces->total : 0); i++ )
        {
            CvRect* r = (CvRect*)cvGetSeqElem( faces, i );
			if(r->width>85 && r->height>85){
				pt1.x = r->x*scale;
				pt2.x = (r->x+r->width)*scale;
				pt1.y = r->y*scale;
				pt2.y = (r->y+r->height)*scale;
				if(bSaveFaces)
					SaveFace(img, pt1.x, pt1.y, r->width, r->height);
				cvRectangle( img, pt1, pt2, CV_RGB(255,0,0), 3, 8, 0 );
				//just handle one face per frame,ignore the others
				break;
			}
		}
	}

    cvShowImage( "Video", img);
}

#ifdef _EiC
main(1,"main.c");
#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -