Welcome 微信登录
编程资源 图片资源库 蚂蚁家优选 PDF转换器

首页 / 操作系统 / Linux / 【OpenCV】使用floodfill()实现PhotoShop魔棒功能

在OpenCV中看到一个很有意思的函数:floodfill()使用给定颜色填充一个联通的区域C++: int floodFill(InputOutputArray image, Point seedPoint, 
Scalar newVal, Rect* rect=0, Scalar loDiff=Scalar(), 
Scalar upDiff=Scalar(), int flags=4 )一个简单的例子:#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/highgui/highgui.hpp"#include <iostream>using namespace cv;
using namespace std;
//floodfill()
//Fills a connected component with the given color.static void help()
{
 cout << " This program demonstrated the floodFill() function "
  "Call: "
  "./ffilldemo [image_name -- Default: fruits.jpg] " << endl; cout << "Hot keys: "
  " ESC - quit the program "
  " c - switch color/grayscale mode "
  " m - switch mask mode "
  " r - restore the original image "
  " s - use null-range floodfill "
  " f - use gradient floodfill with fixed(absolute) range "
  " g - use gradient floodfill with floating(relative) range "
  " 4 - use 4-connectivity mode "
  " 8 - use 8-connectivity mode " << endl;
}Mat image0, image, gray, mask;
int ffillMode = 1;
int loDiff = 20, upDiff = 20;
int connectivity = 4;
int isColor = true;
bool useMask = false;
int newMaskVal = 255;static void onMouse( int event, int x, int y, int, void* )
{
 if( event != CV_EVENT_LBUTTONDOWN )
  return; Point seed = Point(x,y);
 int lo = ffillMode == 0 ? 0 : loDiff;
 int up = ffillMode == 0 ? 0 : upDiff;
 int flags = connectivity + (newMaskVal << 8) +
  (ffillMode == 1 ? CV_FLOODFILL_FIXED_RANGE : 0);
 int b = (unsigned)theRNG() & 255;
 int g = (unsigned)theRNG() & 255;
 int r = (unsigned)theRNG() & 255;
 Rect ccomp; Scalar newVal = isColor ? Scalar(b, g, r) : Scalar(r*0.299 + g*0.587 + b*0.114);
 Mat dst = isColor ? image : gray;
 int area; if( useMask )
 {
  threshold(mask, mask, 1, 128, CV_THRESH_BINARY);
  area = floodFill(dst, mask, seed, newVal, &ccomp, Scalar(lo, lo, lo),
   Scalar(up, up, up), flags);
  imshow( "mask", mask );
 }
 else
 {
  area = floodFill(dst, seed, newVal, &ccomp, Scalar(lo, lo, lo),
   Scalar(up, up, up), flags);
 } imshow("image", dst);
 cout << area << " pixels were repainted ";
}
int main( )
{
 char* filename="0.png";
 image0 = imread(filename, 1); if( image0.empty() )
 {
  cout << "Image empty. Usage: ffilldemo <image_name> ";
  return 0;
 }
 help();
 image0.copyTo(image);
 cvtColor(image0, gray, CV_BGR2GRAY);
 mask.create(image0.rows+2, image0.cols+2, CV_8UC1); namedWindow( "image", 0 );
 createTrackbar( "lo_diff", "image", &loDiff, 255, 0 );
 createTrackbar( "up_diff", "image", &upDiff, 255, 0 ); setMouseCallback( "image", onMouse, 0 ); for(;;)
 {
  imshow("image", isColor ? image : gray);  int c = waitKey(0);
  if( (c & 255) == 27 )
  {
   cout << "Exiting ... ";
   break;
  }
  switch( (char)c )
  {
  case "c":
   if( isColor )
   {
    cout << "Grayscale mode is set ";
    cvtColor(image0, gray, CV_BGR2GRAY);
    mask = Scalar::all(0);
    isColor = false;
   }
   else
   {
    cout << "Color mode is set ";
    image0.copyTo(image);
    mask = Scalar::all(0);
    isColor = true;
   }
   break;
  case "m":
   if( useMask )
   {
    destroyWindow( "mask" );
    useMask = false;
   }
   else
   {
    namedWindow( "mask", 0 );
    mask = Scalar::all(0);
    imshow("mask", mask);
    useMask = true;
   }
   break;
  case "r":
   cout << "Original image is restored ";
   image0.copyTo(image);
   cvtColor(image, gray, CV_BGR2GRAY);
   mask = Scalar::all(0);
   break;
  case "s":
   cout << "Simple floodfill mode is set ";
   ffillMode = 0;
   break;
  case "f":
   cout << "Fixed Range floodfill mode is set ";
   ffillMode = 1;
   break;
  case "g":
   cout << "Gradient (floating range) floodfill mode is set ";
   ffillMode = 2;
   break;
  case "4":
   cout << "4-connectivity mode is set ";
   connectivity = 4;
   break;
  case "8":
   cout << "8-connectivity mode is set ";
   connectivity = 8;
   break;
  }
 } return 0;
}点击图标改变图像中的连图区域的颜色: --------------------------------------分割线 --------------------------------------Ubuntu Linux下安装OpenCV2.4.1所需包 http://www.linuxidc.com/Linux/2012-08/68184.htmUbuntu 12.04 安装 OpenCV2.4.2 http://www.linuxidc.com/Linux/2012-09/70158.htmCentOS下OpenCV无法读取视频文件 http://www.linuxidc.com/Linux/2011-07/39295.htmUbuntu 12.04下安装OpenCV 2.4.5总结 http://www.linuxidc.com/Linux/2013-06/86704.htmUbuntu 10.04中安装OpenCv2.1九步曲 http://www.linuxidc.com/Linux/2010-09/28678.htm基于QT和OpenCV的人脸识别系统 http://www.linuxidc.com/Linux/2011-11/47806.htm[翻译]Ubuntu 14.04, 13.10 下安装 OpenCV 2.4.9  http://www.linuxidc.com/Linux/2014-12/110045.htm--------------------------------------分割线 --------------------------------------OpenCV的详细介绍:请点这里
OpenCV的下载地址:请点这里本文永久更新链接地址:http://www.linuxidc.com/Linux/2015-02/114165.htm