aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xpix_opencv_athreshold-help.pd122
-rw-r--r--pix_opencv_athreshold.cc258
-rw-r--r--pix_opencv_athreshold.h95
3 files changed, 475 insertions, 0 deletions
diff --git a/pix_opencv_athreshold-help.pd b/pix_opencv_athreshold-help.pd
new file mode 100755
index 0000000..7e40898
--- /dev/null
+++ b/pix_opencv_athreshold-help.pd
@@ -0,0 +1,122 @@
+#N canvas 355 82 925 684 10;
+#X obj 277 -24 gemhead;
+#X obj 183 555 pix_texture;
+#X obj 183 574 square 2;
+#X obj 554 196 cnv 15 220 70 empty empty empty 20 12 0 14 -195568 -66577
+0;
+#N canvas 0 22 454 304 gemwin 0;
+#X obj 67 89 outlet;
+#X obj 67 10 inlet;
+#X obj 65 41 route create;
+#X msg 67 70 set destroy;
+#X msg 182 68 set create;
+#N canvas 87 154 247 179 Gem.init 0;
+#X obj 118 46 loadbang;
+#X msg 118 81 reset;
+#X obj 118 113 outlet;
+#X connect 0 0 1 0;
+#X connect 1 0 2 0;
+#X restore 289 80 pd Gem.init;
+#X obj 162 241 gemwin;
+#X msg 161 188 create \, 1;
+#X msg 237 189 destroy;
+#X msg 283 161 frame 15;
+#X obj 164 126 t b b b;
+#X connect 1 0 2 0;
+#X connect 2 0 3 0;
+#X connect 2 0 10 0;
+#X connect 2 1 4 0;
+#X connect 2 1 8 0;
+#X connect 3 0 0 0;
+#X connect 4 0 0 0;
+#X connect 7 0 6 0;
+#X connect 8 0 6 0;
+#X connect 9 0 6 0;
+#X connect 10 0 7 0;
+#X connect 10 2 9 0;
+#X restore 564 240 pd gemwin;
+#X msg 564 222 destroy;
+#X obj 29 508 pix_texture;
+#X obj 29 536 square 2;
+#X obj 158 168 translateXYZ -2 0 0;
+#X obj 182 239 separator;
+#X obj 170 -57 bng 25 250 50 0 empty empty empty 0 -6 0 8 -262144 -1
+-1;
+#X obj 337 144 unpack 0 0 0;
+#X floatatom 327 167 5 0 0 3 length - -;
+#X floatatom 376 167 5 0 0 3 width - -;
+#X floatatom 426 167 5 0 0 3 height - -;
+#X obj 227 118 bng 15 250 50 0 empty empty end_reached 20 7 0 10 -262144
+-1 -1;
+#X floatatom 209 83 5 0 10000 1 frame# - -;
+#X obj 170 -28 openpanel;
+#X msg 170 -8 open \$1;
+#X obj 158 101 pix_film;
+#X msg 176 35 auto \$1;
+#X obj 176 17 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
+;
+#X obj 181 276 translateXYZ 4 0 0;
+#X obj 178 299 cnv 15 600 250 empty empty empty 20 12 0 14 -4034 -66577
+0;
+#X text 562 202 Create window and render;
+#X msg 187 58 colorspace Grey;
+#X obj 183 508 pix_opencv_athreshold;
+#X floatatom 360 498 5 0 0 0 - - -;
+#X msg 298 405 mode \$1;
+#X floatatom 318 472 5 0 0 0 - - -;
+#X text 318 458 Max value used in some modes;
+#X msg 333 364 0;
+#X msg 363 384 1;
+#X text 349 405 thresholding mode ( default 0 );
+#X text 365 362 CV_THRESH_BINARY : pixel >= threshold;
+#X text 393 384 CV_THRESH_BINARY_INV :pixel <= threshold;
+#X text 358 484 blocksize ( 1 \, 3 \, 5 \, 7 \, ... );
+#X text 393 498 ( default 3 );
+#X msg 273 308 0;
+#X msg 305 323 1;
+#X msg 240 345 method \$1;
+#X text 304 344 thresholding method ( default 0 );
+#X text 305 306 CV_ADAPTIVE_THRESH_MEAN_C : mean value;
+#X text 337 323 CV_ADAPTIVE_THRESH_GAUSSIAN_C : gaussian mask;
+#X msg 319 427 dim \$1;
+#X floatatom 370 430 5 0 0 0 - - -;
+#X text 410 428 value to correct the theshold;
+#X text 399 86 written by Yves Degoyon ( ydegoyon@gmail.com );
+#X text 399 51 use the average of pixels in the block of pixels to
+filter only the pixels above or below that threshold \, depending on
+the mode BINARY or BINARY:INVERTED;
+#X text 400 40 pix_opencv_threshold : adaptive thresholding;
+#X connect 0 0 19 0;
+#X connect 1 0 2 0;
+#X connect 4 0 5 0;
+#X connect 5 0 4 0;
+#X connect 6 0 7 0;
+#X connect 8 0 6 0;
+#X connect 8 0 9 0;
+#X connect 9 0 22 0;
+#X connect 10 0 17 0;
+#X connect 11 0 12 0;
+#X connect 11 1 13 0;
+#X connect 11 2 14 0;
+#X connect 15 0 16 0;
+#X connect 16 0 19 1;
+#X connect 17 0 18 0;
+#X connect 18 0 19 0;
+#X connect 19 0 8 0;
+#X connect 19 1 11 0;
+#X connect 19 2 15 0;
+#X connect 20 0 19 0;
+#X connect 21 0 20 0;
+#X connect 22 0 26 0;
+#X connect 25 0 19 0;
+#X connect 26 0 1 0;
+#X connect 27 0 26 2;
+#X connect 28 0 26 0;
+#X connect 29 0 26 1;
+#X connect 31 0 28 0;
+#X connect 32 0 28 0;
+#X connect 38 0 40 0;
+#X connect 39 0 40 0;
+#X connect 40 0 26 0;
+#X connect 44 0 26 0;
+#X connect 45 0 44 0;
diff --git a/pix_opencv_athreshold.cc b/pix_opencv_athreshold.cc
new file mode 100644
index 0000000..ee819b0
--- /dev/null
+++ b/pix_opencv_athreshold.cc
@@ -0,0 +1,258 @@
+////////////////////////////////////////////////////////
+//
+// GEM - Graphics Environment for Multimedia
+//
+// zmoelnig@iem.kug.ac.at
+//
+// Implementation file
+//
+// Copyright (c) 1997-2000 Mark Danks.
+// Copyright (c) Günther Geiger.
+// Copyright (c) 2001-2002 IOhannes m zmoelnig. forum::für::umläute. IEM
+// Copyright (c) 2002 James Tittle & Chris Clepper
+// For information on usage and redistribution, and for a DISCLAIMER OF ALL
+// WARRANTIES, see the file, "GEM.LICENSE.TERMS" in this distribution.
+//
+/////////////////////////////////////////////////////////
+
+#include "pix_opencv_athreshold.h"
+
+CPPEXTERN_NEW(pix_opencv_athreshold)
+
+/////////////////////////////////////////////////////////
+//
+// pix_opencv_athreshold
+//
+/////////////////////////////////////////////////////////
+// Constructor
+//
+/////////////////////////////////////////////////////////
+pix_opencv_athreshold :: pix_opencv_athreshold()
+{
+ inlet_new(this->x_obj, &this->x_obj->ob_pd, gensym("float"), gensym("max_value"));
+ inlet_new(this->x_obj, &this->x_obj->ob_pd, gensym("float"), gensym("blocksize"));
+
+ max_value = 255;
+ x_threshold_mode = 0;
+ x_threshold_method = CV_ADAPTIVE_THRESH_MEAN_C;
+ x_blocksize = 3;
+ x_dim = 0;
+
+ comp_xsize=320;
+ comp_ysize=240;
+
+ rgba = cvCreateImage(cvSize(comp_xsize,comp_ysize), IPL_DEPTH_8U, 4);
+ rgb = cvCreateImage(cvSize(comp_xsize,comp_ysize), IPL_DEPTH_8U, 3);
+ gray = cvCreateImage(cvSize(comp_xsize,comp_ysize), IPL_DEPTH_8U, 1);
+}
+
+/////////////////////////////////////////////////////////
+// Destructor
+//
+/////////////////////////////////////////////////////////
+pix_opencv_athreshold :: ~pix_opencv_athreshold()
+{
+ //Destroy cv_images to clean memory
+ cvReleaseImage(&rgba);
+ cvReleaseImage(&gray);
+ cvReleaseImage(&rgb);
+}
+
+/////////////////////////////////////////////////////////
+// processImage
+//
+/////////////////////////////////////////////////////////
+void pix_opencv_athreshold :: processRGBAImage(imageStruct &image)
+{
+ unsigned char *pixels = image.data;
+
+ if ((this->comp_xsize!=image.xsize)||(this->comp_ysize!=image.ysize)||(!rgba)) {
+
+ this->comp_xsize = image.xsize;
+ this->comp_ysize = image.ysize;
+
+ //Destroy cv_images to clean memory
+ if ( rgba )
+ {
+ cvReleaseImage(&rgba);
+ cvReleaseImage(&gray);
+ cvReleaseImage(&rgb);
+ }
+
+ //create the orig image with new size
+ rgba = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 4);
+ rgb = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 3);
+ gray = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 1);
+ }
+ memcpy( rgba->imageData, image.data, image.xsize*image.ysize*4 );
+ cvCvtColor(rgba, gray, CV_BGRA2GRAY);
+
+ // Applies fixed-level thresholding to single-channel array.
+ switch(x_threshold_mode) {
+ case 0:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY, x_blocksize, x_dim);
+ break;
+ case 1:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY_INV, x_blocksize, x_dim);
+ break;
+ }
+
+ cvCvtColor(gray, rgba, CV_GRAY2BGRA);
+ //copy back the processed frame to image
+ memcpy( image.data, rgba->imageData, image.xsize*image.ysize*4 );
+}
+
+void pix_opencv_athreshold :: processRGBImage(imageStruct &image)
+{
+ unsigned char *pixels = image.data;
+
+ if ((this->comp_xsize!=image.xsize)||(this->comp_ysize!=image.ysize)||(!rgb)) {
+
+ this->comp_xsize = image.xsize;
+ this->comp_ysize = image.ysize;
+
+ //Destroy cv_images to clean memory
+ if ( rgb )
+ {
+ cvReleaseImage(&rgba);
+ cvReleaseImage(&gray);
+ cvReleaseImage(&rgb);
+ }
+
+ //create the orig image with new size
+ rgba = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 4);
+ rgb = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 3);
+ gray = cvCreateImage(cvSize(rgb->width,rgb->height), IPL_DEPTH_8U, 1);
+
+ }
+ memcpy( rgb->imageData, image.data, image.xsize*image.ysize*3 );
+ cvCvtColor(rgb, gray, CV_RGB2GRAY);
+
+ // Applies fixed-level thresholding to single-channel array.
+ switch(x_threshold_mode) {
+ case 0:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY, x_blocksize, x_dim);
+ break;
+ case 1:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY_INV, x_blocksize, x_dim);
+ break;
+ }
+
+ cvCvtColor(gray, rgb, CV_GRAY2BGR);
+ memcpy( image.data, rgb->imageData, image.xsize*image.ysize*3 );
+}
+
+void pix_opencv_athreshold :: processYUVImage(imageStruct &image)
+{
+ post( "pix_opencv_athreshold : yuv format not supported" );
+}
+
+void pix_opencv_athreshold :: processGrayImage(imageStruct &image)
+{
+ unsigned char *pixels = image.data;
+
+ if ((this->comp_xsize!=image.xsize)||(this->comp_ysize!=image.ysize)||(!rgb)) {
+
+ this->comp_xsize = image.xsize;
+ this->comp_ysize = image.ysize;
+
+ //Destroy cv_images to clean memory
+ if ( rgb )
+ {
+ cvReleaseImage(&rgba);
+ cvReleaseImage(&gray);
+ cvReleaseImage(&rgb);
+ }
+
+ //create the orig image with new size
+ rgba = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 4);
+ rgb = cvCreateImage(cvSize(image.xsize,image.ysize), IPL_DEPTH_8U, 3);
+ gray = cvCreateImage(cvSize(rgb->width,rgb->height), IPL_DEPTH_8U, 1);
+
+ }
+ memcpy( gray->imageData, image.data, image.xsize*image.ysize );
+
+ // Applies fixed-level thresholding to single-channel array.
+ switch(x_threshold_mode) {
+ case 0:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY, x_blocksize, x_dim);
+ break;
+ case 1:
+ cvAdaptiveThreshold(gray, gray, (float)max_value, x_threshold_method, CV_THRESH_BINARY_INV, x_blocksize, x_dim);
+ break;
+ }
+
+ memcpy( image.data, gray->imageData, image.xsize*image.ysize );
+}
+
+void pix_opencv_athreshold :: floatMaxValueMess (float maxvalue)
+{
+ if ( (int)maxvalue>0 ) max_value = (int)maxvalue;
+}
+
+void pix_opencv_athreshold :: floatModeMess (float mode)
+{
+ if ( ( (int)mode==0 ) || ( (int)mode==1 ) ) x_threshold_mode = (int)mode;
+}
+
+void pix_opencv_athreshold :: floatMethodMess (float method)
+{
+ if ( (int)method==CV_ADAPTIVE_THRESH_MEAN_C ) x_threshold_method = CV_ADAPTIVE_THRESH_MEAN_C;
+ if ( (int)method==CV_ADAPTIVE_THRESH_GAUSSIAN_C ) x_threshold_method = CV_ADAPTIVE_THRESH_GAUSSIAN_C;
+}
+
+void pix_opencv_athreshold :: floatBlockSizeMess (float blocksize)
+{
+ if ( ( (int)blocksize>=3 ) && ( (int)(blocksize+1)%2 == 0 ) )
+ {
+ x_blocksize = (int)blocksize;
+ }
+}
+
+void pix_opencv_athreshold :: floatDimMess (float dim)
+{
+ if ( (int)dim>0 ) x_dim = (int)dim;
+}
+
+/////////////////////////////////////////////////////////
+// static member function
+//
+/////////////////////////////////////////////////////////
+void pix_opencv_athreshold :: obj_setupCallback(t_class *classPtr)
+{
+ class_addmethod(classPtr, (t_method)&pix_opencv_athreshold::floatModeMessCallback,
+ gensym("mode"), A_FLOAT, A_NULL);
+ class_addmethod(classPtr, (t_method)&pix_opencv_athreshold::floatMethodMessCallback,
+ gensym("method"), A_FLOAT, A_NULL);
+ class_addmethod(classPtr, (t_method)&pix_opencv_athreshold::floatMaxValueMessCallback,
+ gensym("max_value"), A_FLOAT, A_NULL);
+ class_addmethod(classPtr, (t_method)&pix_opencv_athreshold::floatBlockSizeMessCallback,
+ gensym("blocksize"), A_FLOAT, A_NULL);
+ class_addmethod(classPtr, (t_method)&pix_opencv_athreshold::floatDimMessCallback,
+ gensym("dim"), A_FLOAT, A_NULL);
+}
+
+void pix_opencv_athreshold :: floatModeMessCallback(void *data, t_floatarg mode)
+{
+ GetMyClass(data)->floatModeMess((float)mode);
+}
+
+void pix_opencv_athreshold :: floatMethodMessCallback(void *data, t_floatarg method)
+{
+ GetMyClass(data)->floatMethodMess((float)method);
+}
+
+void pix_opencv_athreshold :: floatMaxValueMessCallback(void *data, t_floatarg maxvalue)
+{
+ GetMyClass(data)->floatMaxValueMess((float)maxvalue);
+}
+
+void pix_opencv_athreshold :: floatBlockSizeMessCallback(void *data, t_floatarg blocksize)
+{
+ GetMyClass(data)->floatBlockSizeMess((float)blocksize);
+}
+
+void pix_opencv_athreshold :: floatDimMessCallback(void *data, t_floatarg dim)
+{
+ GetMyClass(data)->floatDimMess((float)dim);
+}
diff --git a/pix_opencv_athreshold.h b/pix_opencv_athreshold.h
new file mode 100644
index 0000000..87c8e40
--- /dev/null
+++ b/pix_opencv_athreshold.h
@@ -0,0 +1,95 @@
+/*-----------------------------------------------------------------
+LOG
+ GEM - Graphics Environment for Multimedia
+
+ Change pix to greyscale
+
+ Copyright (c) 1997-1999 Mark Danks. mark@danks.org
+ Copyright (c) Günther Geiger. geiger@epy.co.at
+ Copyright (c) 2001-2002 IOhannes m zmoelnig. forum::für::umläute. IEM. zmoelnig@iem.kug.ac.at
+ Copyright (c) 2002 James Tittle & Chris Clepper
+ For information on usage and redistribution, and for a DISCLAIMER OF ALL
+ WARRANTIES, see the file, "GEM.LICENSE.TERMS" in this distribution.
+
+-----------------------------------------------------------------*/
+
+#ifndef INCLUDE_PIX_OPENCV_EDGE_H_
+#define INCLUDE_PIX_OPENCV_EDGE_H_
+
+#include "Base/GemPixObj.h"
+
+#ifndef _EiC
+#include "cv.h"
+#endif
+
+/*-----------------------------------------------------------------
+-------------------------------------------------------------------
+CLASS
+ pix_opencv_athreshold
+
+ Adapative threshold object
+
+KEYWORDS
+ pix
+
+DESCRIPTION
+
+-----------------------------------------------------------------*/
+class GEM_EXTERN pix_opencv_athreshold : public GemPixObj
+{
+ CPPEXTERN_HEADER(pix_opencv_athreshold, GemPixObj)
+
+ public:
+
+ //////////
+ // Constructor
+ pix_opencv_athreshold();
+
+ protected:
+
+ //////////
+ // Destructor
+ virtual ~pix_opencv_athreshold();
+
+ //////////
+ // Do the processing
+ virtual void processRGBAImage(imageStruct &image);
+ virtual void processRGBImage(imageStruct &image);
+ virtual void processYUVImage(imageStruct &image);
+ virtual void processGrayImage(imageStruct &image);
+
+ //////////
+ // Set the new edge threshold
+ void floatMaxValueMess(float maxvalue);
+ void floatModeMess(float mode);
+ void floatMethodMess(float method);
+ void floatBlockSizeMess(float blocksize);
+ void floatDimMess(float dim);
+
+ // The new edge threshold
+ int max_value;
+ int x_threshold_mode;
+ int x_threshold_method;
+ int x_blocksize;
+ int x_dim;
+
+ // to detect changes in the image size
+ int comp_xsize;
+ int comp_ysize;
+
+ private:
+
+ //////////
+ // Static member functions
+ static void floatMaxValueMessCallback(void *data, float maxvalue);
+ static void floatModeMessCallback(void *data, float mode);
+ static void floatMethodMessCallback(void *data, float method);
+ static void floatBlockSizeMessCallback(void *data, float blocksize);
+ static void floatDimMessCallback(void *data, float dim);
+
+ /////////
+ // IplImage needed
+ IplImage *rgba, *rgb, *gray;
+};
+
+#endif // for header file