资源描述
试验三:图像直方图分析
一·实验目的
1. 掌握VC++6.0图像编程的基本操作
2. 应用VC++6.0编程绘制灰度直方图。
二·实验内容
1. 用VC++6.0绘制灰度直方图;
2. 对图像进行直方图分析。
三·实验步骤
(1) 启动VC++6.0,打开Dip工程。
(2)将Pointpro.h、Pointpro.cpp文件及Areapro.h、Areapro.cpp文件拷贝到当前工程目录文件里面。
(3)在Fileview-->Dipfilesà右键àSettingàLinkà添加Pointpro.h、Pointpro.cpp文件及Areapro.h、Areapro.cpp文件。
(4)在菜单栏àinsertàresouceàdialogànew,在对话框模版的非控制区点击鼠标右键,在弹出的对话框中选properties,设置为ID:IDD_DLG_Intensity,C标题:Histogram,关闭属性对话框,回到“建立类向导”(MFC classwizard),在弹出的对话框中选创建新类CDlgIntensity后确定。并且在FileView中修改DlgIntensity.cpp和DlgIntensity.h相应的代码;
(5) 在弹出的对话框中,添加如下的按钮等控件:
例如右键单击上面最大的静态文本,在弹出的对话框中选“属性”,在属性对话框中添加如下内容:
(6)在ResourceView栏中àMenuà选IDR_DIPTYPE ,如图在View菜单栏下空的一栏中,右键鼠标,在弹出的对话框中选属性properties,在弹出的对话框中,设置:ID:ID_VIEW_HIST,标题为Histogram,在建立的类向导中选类为CDlgIntensity,确定。
(7)在StdAfx.h中添加#include<math.h>
(8)在DipView.h中//{{AFX_MSG(CDipView)下添加 afx_msg void OnViewHist();
afx_msg void OnUpdateViewHist(CCmdUI* pCmdUI);
(9)DipView.cpp添加#include "PointPro.h"和#include "DlgIntensity.h",
在BEGIN_MESSAGE_MAP(CDipView, CScrollView)处添加:
ON_COMMAND(ID_VIEW_HIST, OnViewHist)
ON_UPDATE_COMMAND_UI(ID_VIEW_HIST, OnUpdateViewHist)
在// CDipView message handlers下面添加:
void CDipView::OnViewHist()
{
CDipDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
//判断当前是否有图像对象
if( pDoc->m_pDibObject == NULL ) return;
//在点处理CPointPro类中创建用来绘制直方图的数据
CPointPro PointOperation( pDoc->m_pDibObject );
int *pHistogram = PointOperation.GetHistogram();
//生成一个对话框CHistDlg类的实例
CDlgIntensity HistDlg;
//将绘制直方图的数据传递给CHistDlg对话框类的公有成员变量m_pnHistogram
if( pHistogram != NULL )
{
//设置直方图数据指针
HistDlg.m_pnHistogram = pHistogram;
//设置当前像素值为0的像素数
HistDlg.m_nCurrentPiexsNum = pHistogram[0];
//设置是否为256级灰度图像
HistDlg.m_bIsGray256 = PointOperation.IsGray256();
}
//显示对话框
if ( HistDlg.DoModal() != IDOK)
return;
delete [] pHistogram;
}
void CDipView::OnUpdateViewHist(CCmdUI* pCmdUI)
{
CDipDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
pCmdUI->Enable( pDoc->m_pDibObject->GetNumBits() >= 8);
}
(10)在DipDoc.h中添加:
protected:
long m_lHeight;
long m_lWidth;
(11)在DipDoc.cpp中添加菜单命令:#include "AreaPro.h",在CDipDoc::CDipDoc()下面添加{
m_pDibObject = NULL;
m_bImageLoaded = FALSE;
// TODO: add one-time construction code here
m_lHeight = 0;
m_lWidth = 0;
}
在最下面添加:
void CDipDoc::OnFileSaveAs()
{
// TODO: Add your command handler code here
static int nIndex = 1;
CFileDialog DialogSaveAs( FALSE, NULL, m_pDibObject->GetImageName(),
OFN_HIDEREADONLY, szFilter );
DialogSaveAs.m_ofn.nFilterIndex = (DWORD) nIndex;
if( DialogSaveAs.DoModal() == IDOK )
{
CMainFrame *pMainFrame = ( CMainFrame * )AfxGetMainWnd();
CChildFrame *pChildFrame = ( CChildFrame * )pMainFrame->MDIGetActive();
CDipView *pDipView = ( CDipView * )pChildFrame->GetActiveView();
nIndex = (int) DialogSaveAs.m_ofn.nFilterIndex;
if( nIndex == 5 )
{
if( m_pDibObject->GetNumBits() != 24 )
{
AfxMessageBox("必须是24位真彩色图像才能存为JPEG格式!");
return;
}
}
if( m_pDibObject != NULL )
{
CString strPathName = DialogSaveAs.GetPathName();
int nFindIndex = strPathName.Find(".");
if( nFindIndex != -1)
strPathName = strPathName.Left( nFindIndex );
strPathName += CDibObject::szExtensions[ nIndex - 1 ];
//m_pDibObject->ProcessImageHeader();
//m_pDibObject->ProcessPalette();
m_pDibObject->Save( strPathName );
CString strFileName = DialogSaveAs.GetFileName();
nFindIndex = strFileName.Find(".");
if ( nFindIndex != -1 )
strFileName = strFileName.Left( nFindIndex );
strFileName += CDibObject::szExtensions[ nIndex - 1 ];
pChildFrame->SetWindowText( strFileName );
SetPathName( strPathName );
if( nIndex == 5 )
{
m_pDibObject->Load( strPathName );
pDipView->InvalidateRect( NULL, FALSE );
pDipView->UpdateWindow();
}
}
}
}
(12)在ChildFrm.h中添加
public:
CChildFrame();
int m_nWidth, m_nHeight;
(13)在ChildFrm.cpp中添加
CChildFrame::CChildFrame()
{
m_nWidth = 300;
m_nHeight = 150;
}
在BOOL CChildFrame::PreCreateWindow(CREATESTRUCT& cs)添加:
{
// TODO: Modify the Window class or styles here by modifying
// the CREATESTRUCT cs
cs.cx = m_nWidth;
cs.cy = m_nHeight;
if( !CMDIChildWnd::PreCreateWindow(cs) )
return FALSE;
return TRUE;
}
一、 实验结果
二、 实验心得及体会
通过做这次实验,使我又学到了关于图像直方图的知识,进一步掌握了图像编程的基本操作:会应用VC++6.0编程绘制灰度直方图。
展开阅读全文