www.pudn.com > hmmPlatform.rar > WaveDisplay.cpp
#include "StdAfx.h"
#include ".\wavedisplay.h"
//////////////////////////////////////////////////////////////////////////
// class CWaveDisplay
//
// 功能: 实现数据的在GUI上的显示
// 创建人: 陈文凯 (chwkai@gmail.com)
// 创建日期:2005年5月19日
// 修改人:
// 修改日期:
// 版本
CWaveDisplay::CWaveDisplay(HWND hOwner)
: m_nPrecision(0)
{
this->InitDefaultSetting();
// 设定父控件
this->m_hOwner = hOwner;
}
CWaveDisplay::~CWaveDisplay(void)
{
this->Dispose();
}
BEGIN_MESSAGE_MAP(CWaveDisplay, CStatic)
ON_WM_PAINT()
ON_WM_MOUSEWHEEL()
END_MESSAGE_MAP()
//////////////////////////////////////////////////////////////////////////
// 调用默认设置函数,初始化显示区域
void CWaveDisplay::InitDefaultSetting()
{
// 缓冲为空
this->m_pBuffer = NULL;
//// 设置显示参数
this->SetGridWidth();
this->SetCoordinateWidth();
this->SetCellSize();
this->SetLineWidth();
this->SetPrecision();
this->SetLineColor();
this->SetBkColor();
this->SetGridColor();
this->SetCoordinateColor();
this->SetXMetrics();
this->SetYMetrics();
this->SetZoomStep();
}
//////////////////////////////////////////////////////////////////////////
// 进行显示区域初始化,画出背景和网格
void CWaveDisplay::DrawTable(CPaintDC* pDc)
{
CSize size; // 显示区域大小
int curVPos = 0; // 绘制线条处的y
int curHPos = 0; // 绘制线条处的x
CPen linePen(0, this->m_nGridWidth, this->m_refGridColor); // 设置网格线条
CPen coPen(0, this->m_nCoordinateWidth, this->m_refCoordinateColor); // 设置坐标轴线条
CBrush bkBrush(this->m_refBkColor); // 用于设置背景色
// 获取显示区域大小,并设定区域原点位置
this->GetClientRect(&this->m_clientRect);
size = this->m_clientRect.Size();
this->m_ptOrigin.y = (this->m_clientRect.bottom - this->m_clientRect.top) / 2;
this->m_ptOrigin.x = 0;
this->m_ptCurPos = this->m_ptOrigin;
// 填充背景
pDc->FillRect(&this->m_clientRect, &bkBrush);
// 绘制X轴
pDc->SelectObject(coPen);
pDc->MoveTo(this->m_ptOrigin.x, this->m_ptOrigin.y);
pDc->LineTo(this->m_clientRect.right - this->m_clientRect.left, this->m_ptOrigin.y);
// 绘制网格线
pDc->SelectObject(linePen);
// 先绘制纵向线条
curHPos = this->m_ptOrigin.x;
while (curHPos < size.cx)
{
pDc->MoveTo(curHPos, 0);
pDc->LineTo(curHPos, size.cy);
curHPos += this->m_nCellSize;
}
// 再绘制横向线条,先绘制上半轴
curVPos = this->m_ptOrigin.y - this->m_nCellSize;
while (curVPos > 0)
{
pDc->MoveTo(this->m_ptOrigin.x, curVPos);
pDc->LineTo(size.cx, curVPos);
curVPos -= this->m_nCellSize;
}
// 再绘制下半轴
curVPos = this->m_ptOrigin.y + this->m_nCellSize;
while (curVPos < this->m_clientRect.bottom)
{
pDc->MoveTo(this->m_ptOrigin.x, curVPos);
pDc->LineTo(size.cx, curVPos);
curVPos += this->m_nCellSize;
}
}
//////////////////////////////////////////////////////////////////////////
// 按设定的显示精度,绘制数据
void CWaveDisplay::DrawData(CPaintDC* pDc)
{
CPen linePen(0, this->m_nLineWidth, this->m_refLineColor);
UINT nCount = 0;
// 读取缓冲数据
if (this->m_pBuffer != NULL)
{
pDc->SelectObject(linePen);
pDc->MoveTo(this->m_ptCurPos);
for (UINT nCount = 0;
nCount < this->m_pBuffer->nSize && this->m_ptCurPos.x < this->m_clientRect.right;
nCount += this->m_nPrecision)
{
// 计算纵坐标
this->m_ptCurPos.y = this->m_pBuffer->lpData[nCount] * this->m_fYMetrics;
this->m_ptCurPos.y = this->m_ptOrigin.y - this->m_ptCurPos.y;
// 对数值进行截取
this->m_ptCurPos.y =
(this->m_ptCurPos.y > this->m_clientRect.bottom ?
this->m_clientRect.bottom : this->m_ptCurPos.y);
this->m_ptCurPos.y =
(this->m_ptCurPos.y < this->m_clientRect.top ?
this->m_clientRect.top : this->m_ptCurPos.y);
pDc->LineTo(this->m_ptCurPos);
//pDc->MoveTo(this->m_ptCurPos);
this->m_ptCurPos.x += this->m_fXMetrics;
}
}
}
//////////////////////////////////////////////////////////////////////////
// 释放所占用的资源
void CWaveDisplay::Dispose()
{
PDisplayChunk lpTemp = NULL;
while (this->m_pBuffer != NULL)
{
lpTemp = this->m_pBuffer;
this->m_pBuffer = this->m_pBuffer->lpNext;
if (lpTemp->lpData != NULL)
{
delete[] lpTemp->lpData;
}
delete[] lpTemp;
}
this->m_pBuffer = NULL;
}
//////////////////////////////////////////////////////////////////////////
// 设定显示数据
void CWaveDisplay::LoadData(double* pData, unsigned int nSize)
{
BOOL bRet = false; // 设定样本是否成功
PDisplayChunk pChunk = NULL;
if (pData != NULL)
{
// 拷贝显示数据
pChunk = new DisplayChunk;
pChunk->lpData = new double[nSize];
pChunk->nDataReaded = 0;
pChunk->nSize = nSize;
pChunk->lpNext = NULL;
memcpy(pChunk->lpData, pData, sizeof(double) * nSize);
}
this->m_pBuffer = pChunk;
// 画出新数据
this->Invalidate();
}
//////////////////////////////////////////////////////////////////////////
// 加入新的显示缓冲块,维护缓冲块链表
//void CWaveDisplay::AppendBuffer(PDisplayChunk pChunk)
//{
// PDisplayChunk lpTemp = NULL;
//
// if (pChunk != NULL && pChunk->lpData != NULL)
// {
// // 若显示缓冲为空
// if (this->m_pBuffer == NULL)
// {
// this->m_pBuffer = pChunk;
// }
// // 把缓冲添加到链表最后
// else
// {
// lpTemp = this->m_pBuffer;
//
// while (lpTemp->lpNext != NULL)
// {
// lpTemp = lpTemp->lpNext;
// }
//
// lpTemp->lpNext = pChunk;
// }
//
// pChunk->lpNext = NULL;
// }
//}
//////////////////////////////////////////////////////////////////////////
// 设定波形颜色
void CWaveDisplay::SetLineColor( int nRed /* = 0 */, int nGreen /* = 128 */, int nBlack /* = 64 */)
{
this->m_refLineColor = RGB(nRed, nGreen, nBlack);
}
//////////////////////////////////////////////////////////////////////////
// 设定背景颜色
void CWaveDisplay::SetBkColor( int nRed /* = 0 */, int nGreen /* = 0 */, int nBlack /* = 0 */)
{
this->m_refBkColor = RGB(nRed, nGreen, nBlack);
}
//////////////////////////////////////////////////////////////////////////
// 设定坐标轴颜色
void CWaveDisplay::SetCoordinateColor( int nRed /* = 255 */, int nGreen /* = 255 */, int nBlack /* = 0 */)
{
this->m_refCoordinateColor = RGB(nRed, nGreen, nBlack);
}
//////////////////////////////////////////////////////////////////////////
// 设定网格颜色
void CWaveDisplay::SetGridColor( int nRed /* = 0 */, int nGreen /* = 128 */, int nBlack /* = 64s */)
{
this->m_refGridColor = RGB(nRed, nGreen, nBlack);
}
//////////////////////////////////////////////////////////////////////////
// 设定X轴逻辑单元宽度
void CWaveDisplay::SetXMetrics(float fValue /* = 1 */)
{
if (fValue > 0)
{
this->m_fXMetrics = fValue;
}
}
//////////////////////////////////////////////////////////////////////////
// 设定Y轴逻辑单元宽度
void CWaveDisplay::SetYMetrics(float fValue /* = 1 */)
{
if (fValue > 0)
{
this->m_fYMetrics = fValue;
}
}
//////////////////////////////////////////////////////////////////////////
// 设定显示单元格的宽(高)度,以象素为单位
void CWaveDisplay::SetCellSize(UINT nSize /* = 10 */)
{
this->m_nCellSize = nSize;
}
//////////////////////////////////////////////////////////////////////////
// 设定数据线条宽度
void CWaveDisplay::SetLineWidth(UINT nWidth /* = 1 */)
{
this->m_nLineWidth = nWidth;
}
//////////////////////////////////////////////////////////////////////////
// 设定坐标轴宽度
void CWaveDisplay::SetCoordinateWidth(UINT nWidth /* = 1 */)
{
this->m_nCoordinateWidth = nWidth;
}
//////////////////////////////////////////////////////////////////////////
// 设定网格线宽度
void CWaveDisplay::SetGridWidth(UINT nWidth /* = 1 */)
{
this->m_nGridWidth = nWidth;
}
//////////////////////////////////////////////////////////////////////////
// 重载CWnd::OnPaint,绘制波形数据
void CWaveDisplay::OnPaint()
{
CPaintDC dc(this);
this->DrawTable(&dc);
this->DrawData(&dc);
}
//////////////////////////////////////////////////////////////////////////
// 设定显示精度
void CWaveDisplay::SetPrecision(UINT nPrecision)
{
this->m_nPrecision = nPrecision;
}
//////////////////////////////////////////////////////////////////////////
// 用鼠标中键滚动,进行显示微调时的放大倍数
void CWaveDisplay::SetZoomStep(UINT nStep)
{
this->m_nZoomStep = nStep;
}
//////////////////////////////////////////////////////////////////////////
// 在鼠标中间滚动时,进行显示微调
BOOL CWaveDisplay::OnMouseWheel(UINT nFlags, short zDelta, CPoint pt)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
// 放大
if (zDelta > 0)
{
this->m_fYMetrics *= this->m_nZoomStep;
}
else
{
this->m_fYMetrics /= this->m_nZoomStep;
}
// 重绘数据
this->Invalidate();
return TRUE;
}
//////////////////////////////////////////////////////////////////////////
// 获取显示微调放大倍数
UINT CWaveDisplay::GetZoomSetp() const
{
return this->m_nZoomStep;
}
//////////////////////////////////////////////////////////////////////////
// 获取Y放大倍数
float CWaveDisplay::GetYMetrics() const
{
return this->m_fYMetrics;
}
//////////////////////////////////////////////////////////////////////////
// 获取X放大倍数
float CWaveDisplay::GetXMetrics() const
{
return this->m_fXMetrics;
}
//////////////////////////////////////////////////////////////////////////
// 获取显示精度
UINT CWaveDisplay::GetPrecision() const
{
return this->m_nPrecision;
}