现在的位置: 首页 > 综合 > 正文

例2-1……例2-10 OpenCV入门

2013年10月04日 ⁄ 综合 ⁄ 共 7997字 ⁄ 字号 评论关闭
/* 例 2.1 从磁盘加载并显示图像
1、打开Visual Studio 2005,文件->新建->项目->其他语言 ->Visual C++->控制台应用程序->命名2-1->全部默认
2、添加库文件。项目->属性->配置属性 ->链接器->输入->活动(win32)下的附加依赖项,
添加 cv200d.lib cvaux200d.lib  cxcore200d.lib  cxts200d.lib highgui200d.lib  ml200d.lib-> 确定
3、添加如下代码:
*/

#include "stdafx.h"
#include <highgui.h>

int main(int argc, char** argv)
{
	IplImage* img=cvLoadImage(argv[1]);
	cvNamedWindow("第一个例子2-1,0717",CV_WINDOW_AUTOSIZE);
	cvShowImage("显示图像",img);
	cvWaitKey(0);
	cvReleaseImage(&img);
	cvDestroyWindow("第一个例子2-1,0717");
	return 0;
}

/*4、生成解决方案,在...2-1/debug/下面放置一幅图片1.jpg。
开始->运行->cmd->cd 到目标工作文件夹...2-1/debug,敲入2-1.exe 1.JPG,即会运行程序。
若要结束,按esc。
*/

笔记:注意项目是C++的控制台应用程序修改main函数的名称和参数,
涉及到格式问题库文件要添加正确最后会出来两个窗体,
cvNamedWindow为主,cvShowImage为辅大小写关系到结构和构造函数,谨慎为好

// 例 2.2 播放磁盘上的视频文件

#include "stdafx.h"
#include <highgui.h>
int main(int argc, char** argv) 
{
	cvNamedWindow("example2",CV_WINDOW_AUTOSIZE);
	CvCapture* capture=cvCreateFileCapture(argv[1]); 
	//返回指向Cvcapture结构的指针 
	IplImage* frame;
	while(1) 
	{
		frame=cvQueryFrame(capture);		//将下一帧视频载入内存
		//cvLoadImage()为图像分配内存空间,	cvQueryFrame使用已经在cvCapture结构中分配好的内存
		if (!frame)
			break;
		cvShowImage("example2",frame);
		char c='/0'; 
		c=cvWaitKey(33);		//等待33ms。经实践,不起作用
		if (c==27) //esc 键 
			break;
	}
	cvReleaseCapture(&capture);	//释放结构,即释放内存 
	cvDestroyWindow("example2");
	cvWaitKey(0);
	return 0;
}

// 例 2.3 添加滚动条控制
#include "stdafx.h"
#include <stdlib.h>
#include <cv.h>
#include <highgui.h>

int g_slider_position=0;
CvCapture* g_capture=NULL;

void onTrackbarSlide(int pos) 
{
	cvSetCaptureProperty(g_capture,CV_CAP_PROP_POS_FRAMES,pos);
}

int main(int argc,char** argv) 
{
	cvNamedWindow("example3",CV_WINDOW_AUTOSIZE);
	g_capture=cvCreateFileCapture(argv[1]); 
	int frames=(int)cvGetCaptureProperty(g_capture,CV_CAP_PROP_FRAME_COUNT); 
	if (frames!=0)
	{
		cvCreateTrackbar("position","example3",& g_slider_position,frames,onTrackbarSlide);
	}
	IplImage* frame;while(1) 
	{
		frame=cvQueryFrame(g_capture);
		if (!frame) 
		{
			break;
		}
		cvShowImage("example3",frame);
		char c=cvWaitKey(0);
		if (c==27) 
		{
			break;
		}
	}
	cvReleaseImage(&frame);	//释放的语句放在这里,否则一闪而过 
	cvDestroyWindow("example3");
	return 0;
}

笔记:cmd中输入的参数第一个是由于程序的名字,第二个是avi格式视频的名字

// 例 2.4 对图像进行平滑处理
#include "stdafx.h"
#include <cv.h>
#include <highgui.h>
void example2_4(IplImage* Image) 
{
	cvNamedWindow("example2_4- in");
	cvNamedWindow("example2_4- out");
	cvShowImage("example2_4- in",Image);
	IplImage* out=cvCreateImage(cvGetSize(Image),IPL_DEPTH_8U,3); 
	cvSmooth(Image,out,CV_GAUSSIAN,3,3); 
	cvShowImage("example2_4- out",out);
	cvReleaseImage(&out);
	cvWaitKey(0);
	cvDestroyWindow("example2_4- in");
	cvDestroyWindow("example2_4-out");
}

int main(int argc, char** argv) 
{ 
	CvCapture* capture=NULL;
	capture=cvCreateFileCapture(argv[1]);
	//实际上 cvCreateFileCapture只分配一帧图像的空间,每次调用时覆盖前面的帧
	IplImage* img;
	while(1) 
	{
		img=cvQueryFrame(capture);
		if (!img)
			break; 
		cvShowImage("showimage",img);
		example2_4(img);
		char c=cvWaitKey(33); 
		if(c==27)
			break;
	}
	cvWaitKey(0);
	return 0;
}
笔记:没见得平滑多少。。。
	   
/*** *使用OpenCV对图像进行平滑 *作者:于仕琪<shiqi.yu@gmail.com> *****/
#include "stdafx.h"
#include <stdio.h>
#include <cv.h>
#include <highgui.h>
int main(int argc, char ** argv) 
   {
	   char * filename = (argc> 1)? argv[1]:"baboon.jpg"; 
	   IplImage * pSrcImage = NULL; 
	   IplImage * pDstImage = NULL; 
	   // 装入图像,转换为单通道 
	   if(! (pSrcImage = cvLoadImage(filename, CV_LOAD_IMAGE_GRAYSCALE))) 
	   {     
		   fprintf(stderr, "Can not open file %s/n", pSrcImage);    
		   fprintf(stderr, "Usage: %s & lt;image file name>/n", argv[0]); 
		   return -1; 
	   }  
	   //创建输出图像
	   if(! (pDstImage = cvCloneImage(pSrcImage)))
	   {     
		   fprintf(stderr, "Can not create image./n");  
		   return -1;  
	   } 
	   // 高斯平滑图像 
	   cvSmooth(pSrcImage, pDstImage, CV_GAUSSIAN, 15, 0, 0, 0); 
	   //显示结果 
	   cvNamedWindow("Source", CV_WINDOW_AUTOSIZE );
	   cvNamedWindow("Result", CV_WINDOW_AUTOSIZE );
	   cvShowImage("Source", pSrcImage); 
	   cvShowImage("Result", pDstImage); 
	   cvWaitKey(0); 
	   // 释放图像并退出 
	   cvDestroyAllWindows(); 
	   cvReleaseImage(&pSrcImage); 
	   cvReleaseImage(&pDstImage); 
	   return 0;
   }

// 例 2.5 图像的宽度和高度缩小一半
#include "stdafx.h"
#include <cv.h>
#include <highgui.h>
   IplImage* doPyrDown(IplImage* in,int filter=IPL_GAUSSIAN_5x5) 
   {
	   //最好确保输入image分成两个
	   assert(in->width%2==0 && in->height%2==0);
	   IplImage* out=cvCreateImage(cvSize(in->width/2,in->height/2),in->depth,in->nChannels);
	   cvPyrDown(in,out);
	   return out;
   };
int main(int argc, char** argv) 
{
	IplImage* img_in=cvLoadImage(argv[1]); 
	cvNamedWindow("example5",CV_WINDOW_AUTOSIZE);
	cvShowImage("example5,img_in",img_in);
	IplImage* img_out=doPyrDown(img_in,IPL_GAUSSIAN_5x5);
	cvShowImage("example5,img_out",img_out);
	cvWaitKey(0);cvReleaseImage(&img_in);
	cvDestroyWindow("example5");
	return 0;
}
笔记:对于缩放2倍,正常运行,得到希望的结果。
但是缩放非2倍,程序抛出:OpenCV Error
经查,CV_Assert( std::abs(dsize.width*2 - ssize.width) <= 2 && std::abs(dsize.height*2 - ssize.height) <= 2 );触发了断言。
断言是一种机制:预防逻辑上不应该出现的情况。这种情况有可能通过编译,并且程序能够运行,但结果不是希望的。
断言能够在这种情况下精确地给出问题出现的位置。
进一步的缩放比例,可以再次调用doPyrDown。例如,25%需要调用两次,12.5%需要调用3次。

// 例 2.6 边缘检测
#include "stdafx.h"
#include <stdlib.h>
#include <cv.h>
#include<highgui.h>
IplImage* doCanny(IplImage* in,double lowThresh,double highThresh,double aperture)
{
	if (in->nChannels!=1)
	{
		return 0;
		//如果不是单通道图像,就返回0.即:只能处理单通道图像
	}
	IplImage* out=cvCreateImage(cvSize(in->width,in-> height),IPL_DEPTH_8U,1);
	//将单通道图像的通道数置为1,深度8位 
	cvCanny(in,out,lowThresh,highThresh,aperture);
	return out;
}
int main(int argc, char** argv) 
{
	cvNamedWindow("example6",CV_WINDOW_AUTOSIZE);
	IplImage* img_in=cvLoadImage(argv[1]);
	cvShowImage("example6_in_original",img_in);
	//    
	img_in=cvCreateImage(cvSize(img_in->width,img_in->height),IPL_DEPTH_16U,1);//将图像转换为1通道的
	// 
	cvShowImage("example6_in_转换为1通道之后",img_in);
	IplImage* img_out=doCanny(img_in,10,100,1); 
	cvShowImage("example6_out",img_out);
	cvWaitKey(0);
	cvReleaseImage(&img_in);
	cvReleaseImage(&img_out);
	cvDestroyWindow("example6");
	return 0;
}
笔记:doCanny()参数的范围大概是10,100;50,200。
aperture默认为3输入的图像的通道不是1,执行到doCanny里面if 条件判断的时候,直接返回了。
doCanny未执行。貌似改为通道为1的图像之后,就是灰灰一片了

// 例 2.7 两次缩放处理和Canny边缘检测
#include "stdafx.h"
#include <cv.h>
#include <highgui.h>
IplImage* doPyrDown(IplImage* in,int filter=IPL_GAUSSIAN_5x5)
{
	// 最好确保输入image分成两个  
	assert(in->width%2==0&&in-> height%2==0); 
	IplImage* out=cvCreateImage(cvSize(in->width/2,in-> height/2),in->depth,in->nChannels); 
	cvPyrDown(in,out);
	return out; 
}
IplImage* doCanny(IplImage* in,double lowThresh,double highThresh,double aperture) 
{  
	if (in->nChannels!=1) 
	{  
		return 0; 
	}
	IplImage* out=cvCreateImage(cvSize(cvGetSize(in).width,cvGetSize(in).height),IPL_DEPTH_8U,1);
	cvCanny(in,out,lowThresh,highThresh,aperture); 
	return out;
} 
int main(int argc, char** argv) 
{
	IplImage* img_in=cvLoadImage(argv[1]);
	IplImage* img1=doPyrDown(img_in,IPL_GAUSSIAN_5x5);
	IplImage* img2=doPyrDown(img1,IPL_GAUSSIAN_5x5);
	IplImage* img3=doCanny(img2,10,100,3);
	cvNamedWindow("example7",CV_WINDOW_AUTOSIZE);
	cvShowImage("example7_in",img_in);
	cvShowImage("example7_img1",img1);
	cvShowImage("example7_img2",img2);
	cvShowImage("example7_img3",img3);
	cvWaitKey(0);cvReleaseImage(&img_in);
	cvReleaseImage(&img1);
	cvReleaseImage(&img2);
	cvReleaseImage(&img3);
	cvDestroyWindow("example7");
	return 0;
}
边缘检测还是未实现... 

// 例 2.8 通过独立的阶段释放内存
//代码省略笔记:释放的内存必须是我们自己显示分配的只需要释放自己显示分配的内存

// 例 2.9 capture结构初始化之后,从视频或摄像设备读入图像没有区别
#include "stdafx.h"
#include <cv.h>
#include <highgui.h>
int _tmain(int argc,  char** argv)
{
	CvCapture* capture;
	if (argc==1)
	{
		capture=cvCreateCameraCapture(0);
		//默认值为 -1,表示随机选择一个
	}
	else
	{
		capture=cvCreateFileCapture(argv[1]);
	}
	assert(capture!=NULL);
	IplImage* frame;
	while(1)
	{
		frame=cvQueryFrame(capture);
		if (!frame) 
		{
			break;
		}
		cvShowImage("lala",frame);
		char c=cvWaitKey(33);
		if (c==27) 
		{
			break;
		}
	}
	cvReleaseImage(&frame);
	cvReleaseCapture(&capture);
	return 0;
}
笔记:如果只有一个参数(程序名称),则从摄像设备读取视频;否则,从第二个参数(视频名称)加载视频


// 例 2.2 读入彩色视频文件并以灰度格式输出.
//convert a video to grayscale
//argv[1]:input video file
//argv[2]:name of new output file
#include "stdafx.h"
#include <cv.h>
#include <highgui.h>
int main(int argc, char** argv)
{
	CvCapture* capture=0;
	capture=cvCreateFileCapture(argv[1]);
	if (!capture)
	{
		return -1;
	}
	IplImage* bgr_frame=cvQueryFrame(capture);
	double fps=cvGetCaptureProperty(capture,CV_CAP_PROP_FPS);
	CvSize size=cvSize((int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_WIDTH),(int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_HEIGHT));
	CvVideoWriter* writer=cvCreateVideoWriter(argv[2],CV_FOURCC('M','J','P','G'),fps,size);
	IplImage* logpolar_frame=cvCreateImage(size,IPL_DEPTH_8U,3);
	while ((bgr_frame=cvQueryFrame(capture))!=NULL)
	{
		cvLogPolar(bgr_frame,logpolar_frame,cvPoint2D32f(bgr_frame->width/2,bgr_frame->height/2),40,CV_INTER_LINEAR+CV_WARP_FILL_OUTLIERS);
		cvWriteFrame(writer,logpolar_frame);
	}
	cvReleaseVideoWriter(&writer);
	cvReleaseImage(&logpolar_frame);
	cvReleaseCapture(&capture);
	return 0;
}
笔记:貌似没有实现  

抱歉!评论已关闭.