www.pudn.com > facedetectDLL_expressions.zip > classimage.cpp


/*************************************************************************** 
                          classimage.cpp 
 
  Base class for all images 
 
    begin                : Sat Nov 23 2002 
    copyright            : (C) 2002 by Bob Mottram 
    email                : fuzzgun@btinternet.com 
 ***************************************************************************/ 
 
/*************************************************************************** 
 *                                                                         * 
 *   This program is free software; you can redistribute it and/or modify  * 
 *   it under the terms of the GNU General Public License as published by  * 
 *   the Free Software Foundation; either version 2 of the License, or     * 
 *   (at your option) any later version.                                   * 
 *                                                                         * 
 ***************************************************************************/ 
 
#include  
#include  
#include  
#include  
#include "classimage.h" 
 
 
 
//--------------------------------------------------------------------------------------------- 
// constructor 
//--------------------------------------------------------------------------------------------- 
classimage::classimage() 
{ 
  initialised=0; 
  reductionFactor_x=1; 
  reductionFactor_y=1; 
  image=NULL; 
  width=0; 
  height=0; 
  rotationLookup=NULL; 
} 
 
//--------------------------------------------------------------------------------------------- 
// destructor 
//--------------------------------------------------------------------------------------------- 
classimage::~classimage() 
{ 
  int x,y; 
 
  if (image!=NULL) 
  { 
    for (x=0;x 0) v2 = image[x - 1][y][0]; else v2 = 0; 
      tVal = abs(v1 - v2); 
      if (y > 0) v2 = image[x][y - 1][0]; else v2 = 0; 
      tVal += abs(v1 - v2); 
      textureVal += tVal; 
       
      p += image[x][y][0]; 
      p2 += tVal; 
      if (y > 0) 
	  { 
        Integral[x][y][0] = p + Integral[x][y - 1][0]; 
        Integral[x][y][1] = p2 + Integral[x][y - 1][1]; 
	  } 
      else 
	  { 
        Integral[x][y][0] = p; 
        Integral[x][y][1] = p2; 
      } 
	 
	} 
  } 
  Texture = textureVal / (width * height); 
 
} 
 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//  get the total pixel value for the given area 
//------------------------------------------------------------------------------------------------------------------------ 
long classimage::getIntegral(int tx, int ty, int bx, int by, int index) 
{ 
  return(Integral[bx][by][index] + Integral[tx][ty][index] - (Integral[tx][by][index] + Integral[bx][ty][index])); 
} 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//  detect different types of feature 
//------------------------------------------------------------------------------------------------------------------------ 
long classimage::detectFeature(int x, int y, int wdth, int hght, int featureType) 
{ 
  long area[4]; 
  long v=0; 
   
  switch(featureType) 
  { 
    case 0:  //A 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght + hght, 0); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght + hght, 0); 
      v = abs(area[0] - area[1]); 
	  break; 
	} 
 
    case 1:  //B 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 0); 
      area[1] = getIntegral(x, y + hght, x + wdth, y + hght + hght, 0); 
      v = abs(area[0] - area[1]); 
	  break; 
	} 
 
    case 2:  //C 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 0); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght, 0); 
      area[2] = getIntegral(x + wdth + wdth, y, x + wdth + wdth + wdth, y + hght, 0); 
      v = abs((area[1] * 2) - (area[0] + area[2])); 
	  break; 
	} 
 
    case 3:  //D 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 0); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght, 0); 
      area[2] = getIntegral(x, y + hght, x + wdth, y + hght + hght, 0); 
      area[3] = getIntegral(x + wdth, y + hght, x + wdth + wdth, y + hght + hght, 0); 
      v = abs((area[1] + area[2]) - (area[0] + area[3])); 
	  break; 
	} 
 
	 
    case 4:  //A 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght + hght, 1); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght + hght, 1); 
      v = abs(area[0] - area[1]); 
	  break; 
	} 
 
    case 5:  //B 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 1); 
      area[1] = getIntegral(x, y + hght, x + wdth, y + hght + hght, 1); 
      v = abs(area[0] - area[1]); 
	  break; 
	} 
 
    case 6:  //C 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 1); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght, 1); 
      area[2] = getIntegral(x + wdth + wdth, y, x + wdth + wdth + wdth, y + hght, 1); 
      v = abs((area[1] * 2) - (area[0] + area[2])); 
	  break; 
	} 
 
    case 7:  //D 
	{ 
      area[0] = getIntegral(x, y, x + wdth, y + hght, 1); 
      area[1] = getIntegral(x + wdth, y, x + wdth + wdth, y + hght, 1); 
      area[2] = getIntegral(x, y + hght, x + wdth, y + hght + hght, 1); 
      area[3] = getIntegral(x + wdth, y + hght, x + wdth + wdth, y + hght + hght, 1); 
      v = abs((area[1] + area[2]) - (area[0] + area[3])); 
	  break; 
	} 
 
 
    case 8:   
	{ 
      v = getIntegral(x, y, x + wdth + wdth, y + hght + hght, 0); 
	  break; 
	} 
 
    case 9:   
	{ 
      v = getIntegral(x, y, x + wdth + wdth, y + hght + hght, 1); 
	  break; 
	} 
 
  } 
   
  return(v); 
} 
 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//  sample the given image within the given bounding box 
//------------------------------------------------------------------------------------------------------------------------ 
void classimage::sampleFromImage(classimage *example_img, int tx, int ty, int bx, int by) 
{ 
  int x,y,xx,yy,dx,dy,c; 
   
  dx = bx - tx; 
  dy = by - ty; 
   
  for (x = 0;ximage[xx][yy][c]; 
    } 
  } 
   
  updateIntegralImage(); 
} 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//  get image from a bitmap 
//------------------------------------------------------------------------------------------------------------------------ 
 
void classimage::updateFromBitmap(BYTE *bmp, int RGBformat, int wdth, int hght) 
{ 
  int x,y,xx,yy; 
  unsigned char r,g,b; 
  int p; 
 
  //create a new image array if necessary 
  if (width==0) createImage(wdth/reductionFactor_x,hght/reductionFactor_y); 
 
  //populate the image array from the bitmap 
  p=0; 
  for (y=0;ywidth-1) xx = width-1; 
		if (yy>height-1) yy = height-1; 
         
        r = image[xx][yy][0]; 
        g = image[xx][yy][1]; 
        b = image[xx][yy][2]; 
 
	   
  	    if (RGBformat==0)  //pixels in RGB order 
		{ 
	      bmp[p] = (BYTE)r; p++; 
	      bmp[p] = (BYTE)g; p++; 
	      bmp[p] = (BYTE)b; p++; 
		} 
	    else 
		{ //pixels in BGR order 
	      bmp[p] = (BYTE)b; p++; 
	      bmp[p] = (BYTE)g; p++; 
	      bmp[p] = (BYTE)r; p++; 
		} 
 
      } 
    } 
 
 
  //test pattern 
  /* 
  int pixels = width*height; 
  int p2; 
  for (p=0;p100) p2=0; 
  } 
  */ 
 
} 
 
 
 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//random number generator 
//------------------------------------------------------------------------------------------------------------------------ 
float classimage::Rnd() 
{ 
  return(rand()/(float)RAND_MAX); 
} 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//  update from another image object 
//------------------------------------------------------------------------------------------------------------------------ 
 
void classimage::updateFromImage(classimage *img) 
{ 
  int x,y,xx,yy,c; 
 
  if (!initialised) 
    { 
    createImage(img->width/reductionFactor_x,img->height/reductionFactor_y); 
    initialised=true; 
    } 
 
  xx=0; 
  for (x=0;xwidth;x+=reductionFactor_x) 
    { 
    yy=0; 
    for (y=0;yheight;y+=reductionFactor_y) 
      { 
      for (c=0;c<3;c++) image[xx][yy][c] = img->image[x][y][c]; 
      yy++; 
      } 
    xx++; 
    } 
 
  updateIntegralImage(); 
} 
 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//rotate the image 
//------------------------------------------------------------------------------------------------------------------------ 
void classimage::Rotate90() 
{ 
  int x,y,c; 
  unsigned char temp; 
   
  for (x=0;x-1) && (x-1) && (ywidth/2; 
    cy = sourceImage->height/2; 
 
    for (x=0;xwidth;x++) 
	{ 
      for (y=0;yheight;y++) 
	  { 
	    hyp = (float)sqrt(((x-cx)*(x-cx))+((y-cy)*(y-cy))); 
		if (hyp>0) 
		{ 
		  ang = (float)acos((y-cy)/hyp); 
		  if (x-cx>0) ang = (float)((2*3.1415927)-ang); 
	      xx = cx + (int)(hyp * sin(rot-ang)); 
	      yy = cy + (int)(hyp * cos(rot-ang)); 
		} 
		else 
		{ 
          xx=x; 
		  yy=y; 
        } 
 
     	if ((xx>=0) && (xx=0) && (yyimage[xx][yy][c]; 
		} 
	  } 
	} 
 
    //recalculate the integral image 
    updateIntegralImage(); 
  } 
 
} 
 
 
 
//------------------------------------------------------------------------------------------------------------------------ 
//returns the 'centre of gravity' for the given region relative to the given colour 
//------------------------------------------------------------------------------------------------------------------------ 
void classimage::CG(int tx, int ty, int bx, int by, unsigned char targ_r, unsigned char targ_g, unsigned char targ_b, int &cx, int &cy, int maxval) 
{ 
  int x,y,p[3],c; 
  long tot,tot_x,tot_y,dp; 
   
  tot = 1; 
  tot_x = 0; 
  tot_y = 0; 
  for (x=tx;xminrowhits) 
	{ 
      totrowhits+=rowhits; 
	  NoOfRows++; 
	} 
  } 
  totrowhits /= NoOfRows; 
  averageWidth = (((by-ty) - NoOfRows) + totrowhits)/2; 
   
  return((hits * 100) / pixels); 
}