MaskBlur.cpp
Go to the documentation of this file.
00001 #include <face_contour_detector/filters/MaskBlur.h>
00002 
00003 #include <limits>
00004 #include <ros/ros.h>
00005 #include <ros/assert.h>
00006 #include <cmath>
00007 
00008 namespace face_contour_detector {
00009 
00010         namespace filters {
00011 
00012                 MaskBlur::MaskBlur(int blurWidth, face_contour_detector::Bgr8 blurColor) : m_blurWidth(blurWidth), m_blurColor(blurColor), m_maskPtr(0) { }
00013                 void MaskBlur::SetMask(const cv::Mat& mask, unsigned char maskTrue, unsigned char maskFalse) {
00014                         ROS_ASSERT(mask.type() == CV_8UC1);
00015                         m_maskPtr = &mask;
00016                         m_maskTrue = maskTrue;
00017                         m_maskFalse = maskFalse;
00018                 }
00019                 void MaskBlur::Apply(const cv::Mat& input, cv::Mat& output) const {
00020                         ROS_ASSERT(m_maskPtr->cols == input.cols && m_maskPtr->rows == input.rows);
00021                         ROS_ASSERT(m_maskPtr->cols == output.cols && m_maskPtr->rows == output.rows);
00022                         ROS_ASSERT(input.type() == CV_8UC3);
00023                         ROS_ASSERT(output.type() == CV_8UC3);
00024                         ROS_ASSERT(m_maskPtr != 0);
00025                         for (int y = 0; y < input.rows; y++) {
00026                                 for (int x = 0; x < input.cols; x++) {
00027 
00028                                         if (m_maskPtr->at<unsigned char>(y,x) == m_maskFalse) {
00029                                                 //scan the surounding
00030                                                 double minDistance = std::numeric_limits<double>::infinity();
00031                                                 Bgr8 closestColor;
00032                                                 for (int dy = m_blurWidth*-1; dy <= m_blurWidth; dy++) {
00033                                                         for (int dx = m_blurWidth*-1; dx <= m_blurWidth; dx++) {
00034                                                                 int newY = y + dy;
00035                                                                 int newX = x + dx;
00036                                                                 if (newY >= 0 && newY < output.rows &&
00037                                                                                 newX >= 0 && newX < output.cols) {
00038 
00039                                                                         if (m_maskPtr->at<unsigned char>(newY,newX) == m_maskTrue) {
00040                                                                                 double distance = sqrt(double(dx*dx + dy*dy));
00041                                                                                 if (distance < minDistance) {
00042                                                                                         minDistance = distance;
00043                                                                                         closestColor = input.at<Bgr8>(newY,newX);
00044                                                                                 }
00045                                                                         }
00046                                                                 }
00047                                                         }
00048                                                 }
00049                                                 if (minDistance == std::numeric_limits<double>::infinity()) {
00050                                                         //out of range -> setting to new value
00051                                                         output.at<Bgr8>(y,x) = m_blurColor;
00052                                                 } else {
00053                                                         //weightet adding of the values
00054                                                         double maxDist = sqrt(double(m_blurWidth*m_blurWidth*2));
00055                                                         Bgr8 re;
00056                                                         re.b = 0;
00057                                                         re.g = 0;
00058                                                         re.r = 0;
00059                                                         //ROS_INFO("blurColor is (%u, %u, %u)", m_blurColor.b, m_blurColor.g, m_blurColor.r);
00060                                                         /*double reDoubleB = std::floor((double(input.at<Bgr8>(y,x).b)*(maxDist-minDistance) + double(m_blurColor.b)*minDistance)/maxDist);
00061                                                         double reDoubleG = std::floor((double(input.at<Bgr8>(y,x).g)*(maxDist-minDistance) + double(m_blurColor.g)*minDistance)/maxDist);
00062                                                         double reDoubleR = std::floor((double(input.at<Bgr8>(y,x).r)*(maxDist-minDistance) + double(m_blurColor.r)*minDistance)/maxDist);*/
00063                                                         double reDoubleB = std::floor((double(closestColor.b)*(maxDist-minDistance) + double(m_blurColor.b)*minDistance)/maxDist);
00064                                                         double reDoubleG = std::floor((double(closestColor.g)*(maxDist-minDistance) + double(m_blurColor.g)*minDistance)/maxDist);
00065                                                         double reDoubleR = std::floor((double(closestColor.r)*(maxDist-minDistance) + double(m_blurColor.r)*minDistance)/maxDist);
00066 
00067                                                         //this is super ineffective
00068                                                         ROS_ASSERT(reDoubleB >= 0.0 && reDoubleB <= 255.0);
00069                                                         ROS_ASSERT(reDoubleG >= 0.0 && reDoubleG <= 255.0);
00070                                                         ROS_ASSERT(reDoubleR >= 0.0 && reDoubleR <= 255.0);
00071                                                         unsigned char iC = 0;
00072                                                         for (int i = 0; i <= 255; i++) {
00073                                                                 if (reDoubleB == double(i)) {
00074                                                                         re.b = iC;
00075                                                                 }
00076                                                                 if (reDoubleG == double(i)) {
00077                                                                         re.g = iC;
00078                                                                 }
00079                                                                 if (reDoubleR == double(i)) {
00080                                                                         re.r = iC;
00081                                                                 }
00082                                                                 iC++;
00083                                                         }
00084                                                         output.at<Bgr8>(y,x) = re;
00085                                                 }
00086 
00087                                         } else if (m_maskPtr->at<unsigned char>(y,x) == m_maskTrue) {
00088                                                 output.at<Bgr8>(y,x) = input.at<Bgr8>(y,x);
00089                                         } else {
00090                                                 Bgr8 tmp;
00091                                                 tmp.b = 255;
00092                                                 tmp.g = 0;
00093                                                 tmp.r = 0;
00094                                                 output.at<Bgr8>(y,x) = tmp;
00095                                                 ROS_ERROR("The value in the mask(at x=%i,y=%i) in neither true (%u) or false (%u) it is %u",x,y,m_maskTrue,m_maskFalse,m_maskPtr->at<unsigned char>(y,x));
00096                                         }
00097 
00098                                 }
00099                         }
00100                 }
00101 
00102         } //namespace filters
00103 
00104 } //namespace face_contour_detector
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends


face_contour_detector
Author(s): Fabian Wenzelmann and Julian Schmid
autogenerated on Wed Dec 26 2012 16:18:17