📄 mainframe.cpp
字号:
// MainFrame.cpp : implementation file
//
#include "stdafx.h"
#include "test1394show.h"
#include "MainFrame.h"
#include "DisplayDlg.h"
#include "DeviceDlg.h"
#include "Configure1394Dlg.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define WINDOW_WIDTH 640
#define WINDOW_HEIGHT 480
#define SCREEN_BPP 8
#define BLOCKSIZE 1024//2048 //当总线速度为400Kb/S,每个异步包的有效数据块大小
#define IMAGESIZE 101376//307200 //图像字节数
/////////////////////////////////////////////////////////////////////////////
// CMainFrame
IMPLEMENT_DYNCREATE(CMainFrame, CFrameWnd)
CMainFrame::CMainFrame()
{
LoadFrame(IDR_MAINFRAME);
m_bWindowed = TRUE;
m_nDisplayOrSave = 0;
m_bStop = FALSE;
m_bOpen = FALSE;
char cTemp[200];
::GetCurrentDirectory(200,cTemp);
m_strImagePath = cTemp;
m_strImagePath += "\\";
m_strImageName = "image";
m_strImageExt = "raw";
}
CMainFrame::~CMainFrame()
{
FreeDirectDraw();
}
BEGIN_MESSAGE_MAP(CMainFrame, CFrameWnd)
//{{AFX_MSG_MAP(CMainFrame)
ON_COMMAND(ID_START, OnStart)
ON_COMMAND(ID_STOP, OnStop)
ON_UPDATE_COMMAND_UI(ID_START, OnUpdateStart)
ON_UPDATE_COMMAND_UI(ID_STOP, OnUpdateStop)
ON_COMMAND(ID_CONFIGURE_1394, OnConfigure1394)
ON_COMMAND(ID_CONFIGURE_DISPLAY, OnConfigureDisplay)
ON_COMMAND(ID_GET_1394DEVICE, OnGet1394device)
ON_WM_CREATE()
ON_COMMAND(ID_FULL_SCREEN, OnFullScreen)
ON_WM_CHAR()
ON_WM_MOVE()
ON_WM_DESTROY()
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CMainFrame message handlers
//图像大小已经改为640*480,2004.2.11,王沛改
void CMainFrame::OnStart()
{
//显示已知的图像序列
if( m_nDisplayOrSave == 1 )
{
if( m_ImageNameExtList.IsEmpty() )
{
MessageBox("请设定需要显示的图像序列!");
return;
}
CString strAllName,str;
POSITION pos = m_ImageNameExtList.GetHeadPosition();
for (int i=0;i < m_ImageNameExtList.GetCount();i++)
{
if( TRUE == m_bStop )
break;
str = m_ImageNameExtList.GetNext(pos);
strAllName = m_strImagePath + str;
if(FAILED( m_pDisplay->CreateSurfaceFromFile(&m_pLogoSurface,strAllName.GetBuffer(strAllName.GetLength()),0,0,m_strImageExt)))
{
MessageBox("显示图像失败");
return;
}
DisplayFrame();
SAFE_DELETE( m_pLogoSurface );
}
}
//采集图像并显示、存储
//开始从1394设备读取数据并显示
//读取数据
//显示
if( m_nDisplayOrSave == 0 )
{
/*
time_t ltimeLa;
_tzset();
time( <imeLa );
*/
//先判断1394设备是否打开
if( !m_bOpen )
return;
//得到设定的将要保存的图像的路径、名称、扩展名(文件类型)
//设置循环,每次得到一帧图像,存储并显示
DWORD Status;
//定义ASYNC_READ
ASYNC_READ asyncRead;
//自动得到Generation次数
asyncRead.bGetGeneration = TRUE;
asyncRead.ulGeneration = 0;
//地址
asyncRead.DestinationAddress.IA_Destination_Offset.Off_High = 0;
asyncRead.DestinationAddress.IA_Destination_Offset.Off_Low = 0;
//读取的字节数
asyncRead.nNumberOfBytesToRead = BLOCKSIZE;
asyncRead.nBlockSize = 0;
asyncRead.fulFlags = 0;
/*
asyncRead.fulFlags |= ASYNC_FLAGS_NONINCREMENTING;
asyncRead.fulFlags |= ASYNC_FLAGS_PING;
*/
//开辟传给驱动的存储空间
ULONG ulBufferSize;
PASYNC_READ pAsyncRead = NULL;
ulBufferSize = sizeof(ASYNC_READ) + asyncRead.nNumberOfBytesToRead;//字节为单位
pAsyncRead = (PASYNC_READ)LocalAlloc(LPTR, ulBufferSize);
FillMemory(pAsyncRead, ulBufferSize, 0);//开辟的每一个字节都为零
*pAsyncRead = asyncRead;
int nFrame;nFrame = 0;
int nTime,nRow,nLine;
char byteFrame[IMAGESIZE];//存储采集的一帧图像
ZeroMemory(byteFrame,IMAGESIZE);
// ZeroMemory(byteFrame,35);
while( nFrame < m_nFrameNumber )//采集的帧数
{
if( TRUE == m_bStop )
break;
nRow = nLine = 0;
//采集一帧的数据,然后存储到文件,并将裸图转换为位图
for( nTime = 0;nTime < (IMAGESIZE/BLOCKSIZE-1);nTime++ )
//for( nTime = 0;nTime < IMAGESIZE/BLOCKSIZE;nTime++ )//640*480 = 2048*150 = 307200
{
Status = g_CurrentDev.AsyncRead(pAsyncRead,ulBufferSize);//调驱动,读BLOCKSIZE个字节
if ( Status == STATUS_SUCCESS )
{
//输出读入的数据到byteFrame
CopyMemory(&byteFrame[nTime*(BLOCKSIZE-4)],pAsyncRead->Data,(BLOCKSIZE-4));//hyb 改,为了去除黑点,只取前1020字节,04-11-08
//CopyMemory(&byteFrame[nTime*BLOCKSIZE],pAsyncRead->Data,BLOCKSIZE);//每次拷贝BLOCKSIZE字节,直到考完BLOCKSIZE*150字节
}
else
{
Status = GetLastError();
// PrintOut(NL"AsyncRead failed"NL);
// PrintError(Status);
MessageBox("AsyncRead failed");
break;
}
}
if( NULL != pAsyncRead )
LocalFree(pAsyncRead);
//保存byteFrame中的一帧数据到文件中
SaveImageToFile(byteFrame,nFrame);
//在内存中创建图像
if(FAILED( m_pDisplay->CreateSurfaceFromImage(&m_pLogoSurface,byteFrame,0,0) ))
{
MessageBox("显示图像失败");
return;
}
//显示内存中的一帧图像
DisplayFrame();
SAFE_DELETE( m_pLogoSurface );
nFrame++;
}
// close device
g_CurrentDev.Close();
// MessageBox("采集图像结束!");
}
}
void CMainFrame::OnStop()
{
//停止读取数据和显示
m_bStop = TRUE;
}
void CMainFrame::OnUpdateStart(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
}
void CMainFrame::OnUpdateStop(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
}
//对于1394设备的属性和显示属性,在程序启动时默认设置,用户可在Setting菜单下修改
void CMainFrame::OnConfigure1394()
{
//获得和设置1394设备的属性
CConfigure1394Dlg dlg;
if( IDOK != dlg.DoModal() )
return;
else
{
}
}
void CMainFrame::OnConfigureDisplay()
{
//获得和设置显示属性
CDisplayDlg DisplayDlg;
if( IDOK != DisplayDlg.DoModal() )
return;
else
{
m_nDisplayOrSave = DisplayDlg.m_nDisplayOrSave;//显示或存储
m_strImagePath = DisplayDlg.m_strImagePath;//路径
m_strImageName = DisplayDlg.m_strImageName;//图像名称
m_strImageExt = DisplayDlg.m_strImageExt;//扩展名
if( m_nDisplayOrSave == 1 )
{
//得到预显示的图像的名称
m_ImageNameExtList.RemoveAll();
CString str;
POSITION pos = DisplayDlg.m_FileNameExtList.GetHeadPosition();
for (int i=0;i < DisplayDlg.m_FileNameExtList.GetCount();i++)
{
str = DisplayDlg.m_FileNameExtList.GetNext(pos);
m_ImageNameExtList.AddTail(str);
}
}
}
}
HRESULT CMainFrame::InitDirectDraw()
{
LPDIRECTDRAWPALETTE pDDPal = NULL;
HRESULT hr;
// int iSprite;
//创建DirectDraw对象,窗口模式
m_pDisplay = new C1394Display();
HWND hWnd = m_hWnd;
if( m_bWindowed )
{
if( FAILED( hr = m_pDisplay->CreateWindowedDisplay( hWnd, WINDOW_WIDTH, WINDOW_HEIGHT ) ) )
{
MessageBox( "建立DirectDraw对象失败" );
return hr;
}
}
else if( FAILED( hr = m_pDisplay->CreateFullScreenDisplay( hWnd, WINDOW_WIDTH, WINDOW_HEIGHT, SCREEN_BPP ) ) )
{
MessageBox( "建立DirectDraw对象失败" );
return hr;
}
/* //创建调色板
// Create and set the palette when in palettized color
if( FAILED( hr = m_pDisplay->CreatePaletteFromBitmap( &pDDPal, MAKEINTRESOURCE( IDB_DIRECTX ) ) ) )
return hr;
m_pDisplay->SetPalette( pDDPal );
SAFE_RELEASE( pDDPal );
*/ //创建表面
// Create a surface, and draw a bitmap resource on it.
/* if( FAILED( hr = m_pDisplay->CreateSurfaceFromBitmap( &m_pLogoSurface, MAKEINTRESOURCE( IDB_DIRECTX ),
SPRITE_DIAMETER, SPRITE_DIAMETER ) ) )
return hr;
*/
// if (FAILED(hr = m_pDisplay->CreateSurfaceFromBitmap
// (&m_pLogoSurface,"F:\\wx\\Motion1.bmp",0,0)))
/*
// Create a surface, and draw text to it.
if( FAILED( hr = m_pDisplay->CreateSurfaceFromText( &m_pTextSurface, NULL, HELPTEXT,
RGB(0,0,0), RGB(255, 255, 0) ) ) )
return hr;
*/
// Set the color key for the logo sprite to black
// if( FAILED( hr = m_pLogoSurface->SetColorKey( 0 ) ) )
// return hr;
return S_OK;
}
void CMainFrame::FreeDirectDraw()
{
// SAFE_DELETE( m_pLogoSurface );
/* for( int i=0;i<10;i++ )
SAFE_DELETE( m_pLogoSurface );
*/
// SAFE_DELETE( m_pTextSurface );
SAFE_DELETE( m_pDisplay );
}
void CMainFrame::OnGet1394device()
{
// 查询所有的1394设备,并打开其中一个
CDeviceDlg dlg;
if( IDOK != dlg.DoModal() )
return;
else
{
m_nFrameNumber = dlg.m_nFrameNumber;
m_bOpen = dlg.m_bOpen;
}
}
int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
return -1;
InitDirectDraw();/*
//
CString strName = "F:\\wx\\计算机视觉图片资料1\\\\Motion";
CString strBack = ".bmp";
CString strNum,strAllName;
for( int i=0;i<10;i++ )
{
strNum.Empty();
strNum.Format("%d",i+1);
strAllName = strName + strNum + strBack;
if(FAILED( m_pDisplay->CreateSurfaceFromFile(&m_pLogoSurface[i],strAllName.GetBuffer(strAllName.GetLength()),0,0)))
{
MessageBox("显示图像失败");
return -1;
}
// DisplayFrame();
// SAFE_DELETE( m_pLogoSurface );
}
//*/
return 0;
}
HRESULT CMainFrame::DisplayFrame()
{
HRESULT hr;
// Fill the back buffer with black, ignoring errors until the flip
m_pDisplay->Clear( 0 );//清空 DisplaySurface
// Blt the help text on the backbuffer, ignoring errors until the flip
// m_pDisplay->Blt( 10, 10, m_pTextSurface, NULL );//用 Blt() 描绘图象
// Blt all the sprites onto the back buffer using color keying,
// ignoring errors until the last blt. Note that all of these sprites
// use the same DirectDraw surface.
m_pDisplay->Blt( 0, 0, m_pLogoSurface, NULL );
// We are in windowed mode so perform a blt from the backbuffer
// to the primary, returning any errors like DDERR_SURFACELOST
if( FAILED( hr = m_pDisplay->Present() ) )//用 Present() 换帧
return hr;
return S_OK;
}
HRESULT CMainFrame::DisplayFrame(int i)
{
HRESULT hr;
// Fill the back buffer with black, ignoring errors until the flip
// m_pDisplay->Clear( 0 );//清空 DisplaySurface
// Blt the help text on the backbuffer, ignoring errors until the flip
// m_pDisplay->Blt( 10, 10, m_pTextSurface, NULL );//用 Blt() 描绘图象
// Blt all the sprites onto the back buffer using color keying,
// ignoring errors until the last blt. Note that all of these sprites
// use the same DirectDraw surface.
m_pDisplay->Blt( 0, 0, m_pLogoSurfaceMul[i], NULL );
// We are in windowed mode so perform a blt from the backbuffer
// to the primary, returning any errors like DDERR_SURFACELOST
if( FAILED( hr = m_pDisplay->Present() ) )//用 Present() 换帧
return hr;
return S_OK;
}
void CMainFrame::OnFullScreen()
{
}
void CMainFrame::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
{
if( nChar== VK_ESCAPE ) //判断是否按下 Esc 键
PostMessage(WM_CLOSE ); //传送WM_CLOSE信息
if( nChar== VK_SPACE ) //判断是否按下 空格 键
OnStart();
CFrameWnd::OnChar(nChar, nRepCnt, nFlags);
}
void CMainFrame::OnMove(int x, int y)
{
CFrameWnd::OnMove(x, y);
m_pDisplay->UpdateBounds();
}
void CMainFrame::SaveImageToFile(char *byteFrame, int n)
{
//保存图像数据到裸图文件
//构造文件名为 *00.raw、*01.raw......
CString strFile,strTemp;
strTemp.Format("%d",n);
int nLen;
nLen = strTemp.GetLength();
if( 1== nLen )
strTemp = "00" + strTemp;
if( 2== nLen )
strTemp = "0" + strTemp;
strFile = m_strImagePath + m_strImageName + strTemp + ".raw";
HANDLE hf; // file handle
hf = CreateFile(strFile,
GENERIC_READ | GENERIC_WRITE,
(DWORD) 0,
NULL,
CREATE_ALWAYS,
FILE_ATTRIBUTE_NORMAL,
(HANDLE) NULL);
if (hf == INVALID_HANDLE_VALUE)
{
DWORD dw = GetLastError();
}
// Copy the BITMAPFILEHEADER into the .BMP file.
DWORD dwTmp;
//if (!WriteFile(hf, byteFrame, IMAGESIZE, (LPDWORD) &dwTmp, NULL))
if (!WriteFile(hf, byteFrame, 99960, (LPDWORD) &dwTmp, NULL))//1020*98=99960
{
DWORD dw = GetLastError();
}
// Close the .BMP file.
if (!CloseHandle(hf))
{
DWORD dw = GetLastError();
}
}
void CMainFrame::OnDestroy()
{
CFrameWnd::OnDestroy();
// close device
g_CurrentDev.Close();
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -