aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--pdp_opencv_haarcascade-help.pd191
-rw-r--r--pdp_opencv_haarcascade.c68
2 files changed, 162 insertions, 97 deletions
diff --git a/pdp_opencv_haarcascade-help.pd b/pdp_opencv_haarcascade-help.pd
index 9016e5a..089df39 100644
--- a/pdp_opencv_haarcascade-help.pd
+++ b/pdp_opencv_haarcascade-help.pd
@@ -1,61 +1,134 @@
-#N canvas 0 25 1247 665 10;
-#X obj 157 -1 pdp_v4l2;
-#X msg 225 -36 open /dev/video0;
-#X obj 146 261 pdp_xv;
-#X floatatom 281 325 5 0 0 0 - - -;
-#X floatatom 343 324 5 0 0 0 - - -;
-#X floatatom 396 324 5 0 0 0 - - -;
-#X obj 278 245 route 0 1 2 3 4;
-#X obj 241 57 openpanel;
-#X msg 181 58 load \$1;
-#X text 331 59 Load a trained cascade classifier from XML file;
-#X obj 311 57 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144 -1
--1;
-#X floatatom 319 114 5 0 0 0 - - -;
-#X floatatom 291 179 5 0 0 0 - - -;
-#X msg 198 143 mode \$1;
-#X obj 259 143 tgl 15 0 empty empty empty 17 7 0 10 -262144 -1 -1 0
+#N canvas 15 49 1247 801 10;
+#X text -158 -9 Written by Lluis Gomez i Bigorda ( lluis@artefacte.org
+);
+#X obj -158 12 cnv 15 621 250 empty empty empty 20 12 0 14 -260097
+-66577 0;
+#X obj 82 52 tgl 15 0 empty empty empty 17 7 0 10 -262144 -1 -1 0 1
+;
+#X obj 82 79 metro 40;
+#X msg 172 106 close;
+#X obj 102 177 pdp_v4l;
+#X msg 159 74 open /dev/video0;
+#X obj 283 54 tgl 15 0 empty empty empty 17 7 0 10 -262144 -1 -1 1
1;
-#X msg 200 178 min_size \$1;
-#X msg 196 111 min_neighbors \$1;
-#X text 358 113 Minimum number (minus 1) of neighbor rectangles that
-makes up an object (default 2);
-#X text 331 179 Minimum window size (default 30);
-#X msg 195 84 scale_factor \$1;
-#X floatatom 313 84 5 0 0 0 - - -;
-#X text 357 83 The factor by which the search window is scaled between
-the subsequent scans (default 1.1);
-#X obj 154 208 pdp_opencv_haarcascade;
-#X text 284 145 Mode of operation. Currently the only flag that may
-be specified is CV_HAAR_DO_CANNY_PRUNING == 0;
-#X text 338 263 For each object detected;
-#X text 280 341 Xcenter Ycenter Radio;
-#X obj 278 296 unpack 0 0 0;
-#X floatatom 341 403 5 0 0 0 - - -;
-#X floatatom 403 402 5 0 0 0 - - -;
-#X floatatom 456 402 5 0 0 0 - - -;
-#X text 340 419 Xcenter Ycenter Radio;
-#X obj 338 374 unpack 0 0 0;
-#X connect 0 0 22 0;
-#X connect 1 0 0 0;
-#X connect 6 0 26 0;
-#X connect 6 1 31 0;
+#X obj 283 81 metro 40;
+#X msg 364 100 close;
+#X msg 360 76 open /dev/video0;
+#X obj 303 179 pdp_v4l2;
+#X msg 369 155 format \$1;
+#X obj 370 133 hradio 15 1 0 4 empty empty empty 0 -8 0 10 -262144
+-1 -1 0;
+#X obj -128 227 pdp_qt;
+#X obj -95 163 metro 40;
+#X msg -95 135 bang;
+#X msg -54 135 stop;
+#X obj -128 66 openpanel;
+#X msg -128 91 open \$1;
+#X msg -128 38 bang;
+#X msg -94 190 loop \$1;
+#X obj -14 190 tgl 15 0 empty empty empty 17 7 0 10 -262144 -1 -1 1
+1;
+#X obj -14 108 loadbang;
+#X text -85 41 playing a video file;
+#X text 112 50 Camera input;
+#X obj -156 266 cnv 15 621 300 empty empty empty 20 12 0 14 -258113
+-66577 0;
+#X obj -129 591 pdp_xv;
+#X floatatom 25 511 5 0 0 0 - - -;
+#X floatatom 74 512 5 0 0 0 - - -;
+#X floatatom 121 510 5 0 0 0 - - -;
+#X obj 21 465 route 0 1 2 3 4;
+#X obj -129 418 pdp_opencv_haarcascade;
+#X text 123 469 For each object detected;
+#X obj 24 489 unpack 0 0 0;
+#X floatatom 174 512 5 0 0 0 - - -;
+#X floatatom 213 512 5 0 0 0 - - -;
+#X floatatom 251 513 5 0 0 0 - - -;
+#X obj 172 491 unpack 0 0 0;
+#X text -158 -62 pdp_opencv_haarscasccade : object recognition based
+on Haar's algorithm ( decision tree algorithm );
+#X text -159 -37 used for face detection by default;
+#X floatatom -56 443 5 0 0 0 - - -;
+#X text -17 443 number of objects detected;
+#X msg 6 282 load \$1;
+#X obj 70 282 openpanel;
+#X obj 138 281 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144
+-1 -1;
+#X text -162 -25 ( load haarscascase_frontalface_alt.xml );
+#X text 161 292 ( default haarscascase_frontalface_alt.xml );
+#X text 470 288 don't forget this step;
+#X text 471 274 <-- WARNING : if you don't see any object detected
+;
+#X text 163 280 load an haar's decision tree;
+#X msg 25 311 mode \$1;
+#X obj 83 311 hradio 15 1 0 2 empty empty empty 0 -8 0 10 -262144 -1
+-1 0;
+#X msg 34 338 min_size \$1;
+#X floatatom 114 340 5 0 0 0 - - -;
+#X floatatom 317 512 5 0 0 0 - - -;
+#X floatatom 356 512 5 0 0 0 - - -;
+#X floatatom 394 513 5 0 0 0 - - -;
+#X obj 315 491 unpack 0 0 0;
+#X text 124 311 mode 0 or 1 ( default 0 );
+#X text 154 338 minimum size of object ( default 30 );
+#X floatatom 152 363 5 0 0 0 - - -;
+#X text 190 362 minimum neighbours of object ( default 2 );
+#X msg 46 362 min_neighbors \$1;
+#X floatatom 160 389 5 0 0 0 - - -;
+#X text 198 388 scale used for recognition ( default 1.1 );
+#X text 315 527 Xcenter Ycenter Radius;
+#X text 171 527 Xcenter Ycenter Radius;
+#X text 25 527 Xcenter Ycenter Radius;
+#X msg 54 388 scale_factor \$1;
+#X obj -68 228 hsl 128 15 0 500 0 0 empty empty empty -2 -8 0 10 -262144
+-1 -1 0 1;
+#X connect 2 0 3 0;
+#X connect 3 0 5 0;
+#X connect 4 0 5 0;
+#X connect 5 0 32 0;
+#X connect 6 0 5 0;
#X connect 7 0 8 0;
-#X connect 8 0 22 0;
-#X connect 10 0 7 0;
-#X connect 11 0 16 0;
-#X connect 12 0 15 0;
-#X connect 13 0 22 0;
-#X connect 14 0 13 0;
-#X connect 15 0 22 0;
-#X connect 16 0 22 0;
-#X connect 19 0 22 0;
-#X connect 20 0 19 0;
-#X connect 22 0 2 0;
-#X connect 22 1 6 0;
-#X connect 26 0 3 0;
-#X connect 26 1 4 0;
-#X connect 26 2 5 0;
-#X connect 31 0 27 0;
-#X connect 31 1 28 0;
-#X connect 31 2 29 0;
+#X connect 8 0 11 0;
+#X connect 9 0 11 0;
+#X connect 10 0 11 0;
+#X connect 11 0 32 0;
+#X connect 12 0 11 0;
+#X connect 13 0 12 0;
+#X connect 14 0 32 0;
+#X connect 15 0 14 0;
+#X connect 16 0 15 0;
+#X connect 17 0 15 0;
+#X connect 18 0 19 0;
+#X connect 19 0 14 0;
+#X connect 20 0 18 0;
+#X connect 21 0 14 0;
+#X connect 22 0 21 0;
+#X connect 23 0 22 0;
+#X connect 23 0 16 0;
+#X connect 31 0 34 0;
+#X connect 31 1 38 0;
+#X connect 31 2 58 0;
+#X connect 32 0 27 0;
+#X connect 32 1 41 0;
+#X connect 32 2 31 0;
+#X connect 34 0 28 0;
+#X connect 34 1 29 0;
+#X connect 34 2 30 0;
+#X connect 38 0 35 0;
+#X connect 38 1 36 0;
+#X connect 38 2 37 0;
+#X connect 43 0 32 0;
+#X connect 44 0 43 0;
+#X connect 45 0 44 0;
+#X connect 51 0 32 0;
+#X connect 52 0 51 0;
+#X connect 53 0 32 0;
+#X connect 54 0 53 0;
+#X connect 58 0 55 0;
+#X connect 58 1 56 0;
+#X connect 58 2 57 0;
+#X connect 61 0 63 0;
+#X connect 63 0 32 0;
+#X connect 64 0 69 0;
+#X connect 69 0 32 0;
+#X connect 70 0 14 1;
diff --git a/pdp_opencv_haarcascade.c b/pdp_opencv_haarcascade.c
index cee9547..48382a7 100644
--- a/pdp_opencv_haarcascade.c
+++ b/pdp_opencv_haarcascade.c
@@ -34,13 +34,8 @@
#include "cv.h"
#endif
-
-
-
-
const char* default_cascade ="./haarcascade_frontalface_alt.xml";
-
typedef struct pdp_opencv_haarcascade_struct
{
t_object x_obj;
@@ -49,6 +44,7 @@ typedef struct pdp_opencv_haarcascade_struct
t_outlet *x_outlet0;
t_outlet *x_outlet1;
t_outlet *x_dataout;
+ t_atom rlist[4];
int x_packet0;
int x_packet1;
int x_dropped;
@@ -68,6 +64,7 @@ typedef struct pdp_opencv_haarcascade_struct
IplImage *frame, *img;
CvMemStorage* storage;
CvHaarClassifierCascade* cascade;
+ CvFont font;
} t_pdp_opencv_haarcascade;
@@ -79,7 +76,7 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
short int *data = (short int *)pdp_packet_data(x->x_packet0);
t_pdp *newheader = pdp_packet_header(x->x_packet1);
short int *newdata = (short int *)pdp_packet_data(x->x_packet1);
-
+ int i;
if ((x->x_width != (t_int)header->info.image.width) ||
(x->x_height != (t_int)header->info.image.height))
@@ -109,15 +106,12 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
memcpy( newdata, data, x->x_size*3 );
- //cv_processframe(x, x->x_plugin, newdata);
-
- // FEM UNA COPIA DEL PACKET A image->imageData ... http://www.cs.iit.edu/~agam/cs512/lect-notes/opencv-intro/opencv-intro.html aqui veiem la estructura de IplImage
memcpy( x->frame->imageData, data, x->x_size*3 );
- if( x->frame->origin == IPL_ORIGIN_TL )
- cvCopy( x->frame, x->img, 0 );
- else
- cvFlip( x->frame, x->img, 0 );
+ if( x->frame->origin == IPL_ORIGIN_TL )
+ cvCopy( x->frame, x->img, 0 );
+ else
+ cvFlip( x->frame, x->img, 0 );
static CvScalar colors[] =
{
@@ -134,9 +128,7 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
double scale = 1.3;
IplImage* gray = cvCreateImage( cvSize(x->img->width,x->img->height), 8, 1 );
IplImage* small_img = cvCreateImage( cvSize( cvRound (x->img->width/scale),
- cvRound (x->img->height/scale)),
- 8, 1 );
- int i;
+ cvRound (x->img->height/scale)), 8, 1 );
cvCvtColor( x->img, gray, CV_BGR2GRAY );
cvResize( gray, small_img, CV_INTER_LINEAR );
@@ -150,7 +142,12 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
x->scale_factor, x->min_neighbors, x->mode, cvSize(x->min_size, x->min_size) );
//t = (double)cvGetTickCount() - t;
//printf( "detection time = %gms\n", t/((double)cvGetTickFrequency()*1000.) );
- outlet_float(x->x_outlet1, (float)faces->total);
+
+ if ( faces && (faces->total > 0 ) )
+ outlet_float(x->x_outlet1, (float)faces->total);
+ else
+ outlet_float(x->x_outlet1, 0.0);
+
for( i = 0; i < (faces ? faces->total : 0); i++ )
{
CvRect* r = (CvRect*)cvGetSeqElem( faces, i );
@@ -160,13 +157,15 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
center.y = cvRound((r->y + r->height*0.5)*scale);
radius = cvRound((r->width + r->height)*0.25*scale);
cvCircle( x->img, center, radius, colors[i%8], 3, 8, 0 );
-
- t_atom rlist[4];
- SETFLOAT(&rlist[0], i);
- SETFLOAT(&rlist[1], center.x);
- SETFLOAT(&rlist[2], center.y);
- SETFLOAT(&rlist[3], radius);
- outlet_list( x->x_dataout, 0, 4, rlist );
+ char tindex[4];
+ sprintf( tindex, "%d", i );
+ cvPutText( x->img, tindex, center, &x->font, CV_RGB(255,255,255));
+
+ SETFLOAT(&x->rlist[0], i);
+ SETFLOAT(&x->rlist[1], center.x);
+ SETFLOAT(&x->rlist[2], center.y);
+ SETFLOAT(&x->rlist[3], radius);
+ outlet_list( x->x_dataout, 0, 4, x->rlist );
}
}
@@ -175,17 +174,10 @@ static void pdp_opencv_haarcascade_process_rgb(t_pdp_opencv_haarcascade *x)
cvClearMemStorage( x->storage );
memcpy( newdata, x->img->imageData, x->x_size*3 );
-
-
return;
}
-static void pdp_opencv_haarcascade_param(t_pdp_opencv_haarcascade *x, t_floatarg f1, t_floatarg f2)
-{
-
-}
-
static void pdp_opencv_haarcascade_scale_factor(t_pdp_opencv_haarcascade *x, t_floatarg f)
{
if (f>1) x->scale_factor = f;
@@ -208,10 +200,10 @@ static void pdp_opencv_haarcascade_min_neighbors(t_pdp_opencv_haarcascade *x, t_
static void pdp_opencv_haarcascade_load(t_pdp_opencv_haarcascade *x, t_symbol *filename)
{
- x->cascade = (CvHaarClassifierCascade*)cvLoad( filename->s_name, 0, 0, 0 );
+ x->cascade = (CvHaarClassifierCascade*)cvLoad( filename->s_name, 0, 0, 0 );
if( !x->cascade )
{
- post( "ERROR: Could not load classifier cascade from %s\n", filename->s_name );
+ post( "pdp_opencv_haarcascade: ERROR: Could not load classifier cascade from %s\n", filename->s_name );
} else post( "pdp_opencv_haarcascade: Loaded classifier cascade from %s\n", filename->s_name );
}
@@ -313,18 +305,18 @@ void *pdp_opencv_haarcascade_new(t_floatarg f)
x->mode = 0;
x->min_size = 30;
-
x->cascade = (CvHaarClassifierCascade*)cvLoad( default_cascade, 0, 0, 0 );
if( !x->cascade )
{
- post( "ERROR: Could not load default classifier cascade\n" );
+ post( "pdp_opencv_haarcascade : ERROR : Could not load default classifier cascade\n" );
} else post( "pdp_opencv_haarcascade: Loaded default classifier cascade\n" );
x->storage = cvCreateMemStorage(0);
- x->frame = cvCreateImage(cvSize(x->x_width,x->x_height), IPL_DEPTH_8U, 3);
- x->img = cvCreateImage(cvSize(x->frame->width,x->frame->height), IPL_DEPTH_8U, 3);
-
+ x->frame = cvCreateImage(cvSize(x->x_width,x->x_height), IPL_DEPTH_8U, 3);
+ x->img = cvCreateImage(cvSize(x->frame->width,x->frame->height), IPL_DEPTH_8U, 3);
+ // initialize font
+ cvInitFont( &x->font, CV_FONT_HERSHEY_PLAIN, 1.0, 1.0, 0, 1, 8 );
return (void *)x;
}