⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ecgtestdlg.cpp

📁 这是VISUAL C++ 6.0环境下编译的ECG测试程序
💻 CPP
字号:
// ECGTestDlg.cpp : implementation file
//

#include "stdafx.h"
#include "ECGTest.h"
#include "ECGTestDlg.h"

#include "math.h"

#include "ECGDATADlg.h"
#include "ECGDFTDlg.h"
#include "BIANYIDLG.h"
#include "STARTDLG.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

#define PI 3.1415926

CBIANYIDLG	EcgBianyiDlg;
CECGDATADlg EcgDataDlg;
CECGDFTDlg  EcgDFTDlg;

/////////////////////////////////////////////////////////////////////////////
// CAboutDlg dialog used for App About

class CAboutDlg : public CDialog
{
public:
	CAboutDlg();

// Dialog Data
	//{{AFX_DATA(CAboutDlg)
	enum { IDD = IDD_ABOUTBOX };
	//}}AFX_DATA

	// ClassWizard generated virtual function overrides
	//{{AFX_VIRTUAL(CAboutDlg)
	protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV support
	//}}AFX_VIRTUAL

// Implementation
protected:
	//{{AFX_MSG(CAboutDlg)
	//}}AFX_MSG
	DECLARE_MESSAGE_MAP()
};

CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
{
	//{{AFX_DATA_INIT(CAboutDlg)
	//}}AFX_DATA_INIT
}

void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialog::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CAboutDlg)
	//}}AFX_DATA_MAP
}

BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
	//{{AFX_MSG_MAP(CAboutDlg)
		// No message handlers
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CECGTestDlg dialog

CECGTestDlg::CECGTestDlg(CWnd* pParent /*=NULL*/)
	: CDialog(CECGTestDlg::IDD, pParent)
{
	//{{AFX_DATA_INIT(CECGTestDlg)
	m_Date = _T("");
	m_Time = _T("");
	//}}AFX_DATA_INIT
	// Note that LoadIcon does not require a subsequent DestroyIcon in Win32
	m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void CECGTestDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialog::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CECGTestDlg)
	DDX_Text(pDX, IDC_DATE, m_Date);
	DDX_Text(pDX, IDC_TIME, m_Time);
	//}}AFX_DATA_MAP
}

BEGIN_MESSAGE_MAP(CECGTestDlg, CDialog)
	//{{AFX_MSG_MAP(CECGTestDlg)
	ON_WM_SYSCOMMAND()
	ON_WM_PAINT()
	ON_WM_QUERYDRAGICON()
	ON_COMMAND(IDC_FILE_OPEN, OnFileOpen)
	ON_COMMAND(IDC_ABORT, OnAbort)
	ON_WM_TIMER()
	ON_BN_CLICKED(IDC_CHECK6, OnCheck6)
	ON_WM_CTLCOLOR()
	ON_COMMAND(IDC_EXIT, OnExit)
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CECGTestDlg message handlers

BOOL CECGTestDlg::OnInitDialog()
{
	CDialog::OnInitDialog();

	// Add "About..." menu item to system menu.

	// IDM_ABOUTBOX must be in the system command range.
	ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
	ASSERT(IDM_ABOUTBOX < 0xF000);

	CMenu* pSysMenu = GetSystemMenu(FALSE);
	if (pSysMenu != NULL)
	{
		CString strAboutMenu;
		strAboutMenu.LoadString(IDS_ABOUTBOX);
		if (!strAboutMenu.IsEmpty())
		{
			pSysMenu->AppendMenu(MF_SEPARATOR);
			pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
		}
	}

	// Set the icon for this dialog.  The framework does this automatically
	//  when the application's main window is not a dialog
	SetIcon(m_hIcon, TRUE);			// Set big icon
	SetIcon(m_hIcon, FALSE);		// Set small icon
	
	// TODO: Add extra initialization here
	
	startDlg.DoModal();
	EcgDataDlg.Create(IDD_FORMVIEW,this);
	EcgDataDlg.ShowWindow(SW_SHOW);
	EcgDFTDlg.Create(IDD_FORMVIEW1,this);
	EcgDFTDlg.ShowWindow(SW_SHOW);
	EcgBianyiDlg.Create(IDD_FORMVIEW2,this);
	EcgBianyiDlg.ShowWindow(SW_SHOW);
	SetTimer(1,100,NULL);

	

	return TRUE;  // return TRUE  unless you set the focus to a control
}

void CECGTestDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
	if ((nID & 0xFFF0) == IDM_ABOUTBOX)
	{
		CAboutDlg dlgAbout;
		dlgAbout.DoModal();
	}
	else
	{
		CDialog::OnSysCommand(nID, lParam);
	}
}

// If you add a minimize button to your dialog, you will need the code below
//  to draw the icon.  For MFC applications using the document/view model,
//  this is automatically done for you by the framework.

void CECGTestDlg::OnPaint() 
{
/*	if (IsIconic())
	{
		CPaintDC dc(this); // device context for painting
		
		SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);

		// Center icon in client rectangle
		int cxIcon = GetSystemMetrics(SM_CXICON);
		int cyIcon = GetSystemMetrics(SM_CYICON);
		CRect rect;
		GetClientRect(&rect);
		int x = (rect.Width() - cxIcon + 1) / 2;
		int y = (rect.Height() - cyIcon + 1) / 2;

		// Draw the icon
		dc.DrawIcon(x, y, m_hIcon);
	}
	else
	{
		CDialog::OnPaint();
	}*/
	CPaintDC dc(this); // device context for painting

	GetClientRect(rect);
	m_bitmap1.Detach();
	m_bitmap1.LoadBitmap(IDB_BITMAP11);
	CBrush brush(&m_bitmap1);
	dc.FillRect(rect,&brush);
}

// The system calls this to obtain the cursor to display while the user drags
//  the minimized window.
HCURSOR CECGTestDlg::OnQueryDragIcon()
{
	return (HCURSOR) m_hIcon;
}

void ReverseOrder(_complex A[],int N)
{
	int NV2=N/2;
	int NM1=N-1;
	int I,J,K=0;
	_complex T;//用于中介的复数变量T
	I=J=1;
	while(I<=NM1)
	{
		if(I<J)
		{
			T=A[J-1];//将A[J-1]的内容和A[I-1]的内容互换,借助于中间变量T
			A[J-1]=A[I-1];
			A[I-1]=T;
		}
		K=NV2;
		while(K<J)
		{
			J-=K;
			K/=2;
		}
	J+=K;
	I++;
	}
}

void four1(double data[1025], int nn, int isign)
{
	int n,j,i,m,mmax,istep;
	double tempr,tempi,theta,wpr,wpi,wr,wi,wtemp;
    n = 2 * nn;
    j = 1;
    for (i = 1; i<=n ; i=i+2)
	{
        if( j > i)
		{
            tempr = data[j];
            tempi = data[j + 1];
            data[j] = data[i];
            data[j + 1] = data[i + 1];
            data[i] = tempr;
            data[i + 1] = tempi;
        }
        m = n / 2;
        while (m >= 2 && j > m)
		{
            j = j - m;
            m = m / 2;
        }
        j = j + m;
    }
    mmax = 2;
    while( n > mmax )
	{
        istep = 2 * mmax;
        theta = 6.28318530717959 / (isign * mmax);
        wpr = -2.0 * sin(0.5 * theta)*sin(0.5 * theta);
        wpi = sin(theta);
        wr = 1.0;
        wi = 0.0;
        for( m = 1; m<=mmax; m=m+2)
		{
            for (i = m; i<=n; i=i+istep)
			{
                j = i + mmax;
                tempr = double(wr) * data[j] - double(wi) * data[j + 1];
                tempi = double(wr) * data[j + 1] + double(wi) * data[j];
                data[j] = data[i] - tempr;
                data[j + 1] = data[i + 1] - tempi;
                data[i] = data[i] + tempr;
                data[i + 1] = data[i + 1] + tempi;
            }
            wtemp = wr;
            wr = wr * wpr - wi * wpi + wr;
            wi = wi * wpr + wtemp * wpi + wi;
        }
        mmax = istep;
    }
}

void realft(double data[], int &n, int &isign)
{
	int n2p3,i,i1,i2,i3,i4;
	double theta,c1,c2,wpr,wpi,wr,wi,wrs,wis,h1r,h1i,h2r,h2i,wtemp,wri;
	wri=0.0;
    theta = 6.28318530717959 / 2.0 / n;
    c1 = 0.5;
    if (isign == 1)
	{
        c2 = -0.5;
        four1(data, n, 1);
	}
    else
	{
        c2 = 0.5;
        theta = -theta;
	}
    wpr = -2.0 * sin(0.5 * theta)*sin(0.5 * theta);
    wpi = sin(theta);
    wr = 1.0 + wpr;
    wi = wpi;
    n2p3 = 2 * n + 3;
    for (i = 2; i<=n / 2 + 1; i++)
	{
        i1 = 2 * i - 1;
        i2 = i1 + 1;
        i3 = n2p3 - i2;
        i4 = i3 + 1;
        wrs = float(wr);
        wis = float(wi);
        h1r = c1 * (data[i1] + data[i3]);
        h1i = c1 * (data[i2] - data[i4]);
        h2r = -c2 * (data[i2] + data[i4]);
        h2i = c2 * (data[i1] - data[i3]);
        data[i1] = h1r + wrs * h2r - wis * h2i;
        data[i2] = h1i + wrs * h2i + wis * h2r;
        data[i3] = h1r - wrs * h2r + wis * h2i;
        data[i4] = -h1i + wrs * h2i + wis * h2r;
        wtemp = wr;
        wr = wr * wpr - wi * wri + wr;
        wi = wi * wpr + wtemp * wpi + wi;
    }
    if( isign == 1 )
	{
        h1r = data[1];
        data[1] = h1r + data[2];
        data[2] = h1r - data[2];
	}
    else
	{
        h1r = data[1];
        data[1] = c1 * (h1r + data[2]);
        data[2] = c1 * (h1r - data[2]);
        four1(data, n, -1);
    }
}

void Fourier(_complex A[],int M)
{
	_complex U,W,T;
	int LE,LE1,I,J,IP;
	int N=(int)pow(2,M);
	//在此采用的是时间抽选奇偶分解方式,所以在参加运算前首先要对时间序列进行倒序
	ReverseOrder(A,N);
	int L=1;
	while(L<=M)
	{
		LE=(int)pow(2,L);
		LE1=LE/2;
		U.x=1.0f;
		U.y=0.0f;
		W.x=(float)cos(PI/(1.0*LE1));//计算W算子的值
		W.y=(float)-1.0*sin(PI/(1.0*LE1));
		if(abs(W.x)<1.0e-12)
			W.x=0.0f;
		if(abs(W.y)<1.0e-12)
			W.y=0.0f;
		J=1;
		while(J<=LE1)
		{
			I=J;
			while(I<=N)
			{
				IP=I+LE1;
				T.x=(float)A[IP-1].x*U.x-A[IP-1].x*U.y;//计算复数运算A*U
				T.y=(float)A[IP-1].y*U.y+A[IP-1].y*U.x;
				A[IP-1].x=(float)A[I-1].x-T.x;//计算复数运算A-T
				A[IP-1].y=(float)A[I-1].y-T.y;
				A[I-1].x+=T.x;//计算复数运算A+T
				A[I-1].y+=T.y;
				I+=LE;
			}
		float temp=U.x;
		U.x=(float)U.x*W.x-U.y*W.y;//计算复数运算U*W
		U.y=(float)temp*W.y+U.y*W.x;
		J++;
		}
	L++;
	}
}

BOOL m_control=FALSE,m_DFTflag=TRUE,m_filer=FALSE;
CString m_pathName;
int ECGData[166];//心电数据缓冲
double ECGDFTData[1025],ECGDataTemp[1025];//构造复数,以进行傅立叶变换

UINT mThreadTest(LPVOID pParam)//心电数据动态显示线程
{
	CStdioFile hFile;
	CString fileContent,strtemp;
	int pos;
	hFile.Open(m_pathName,CFile::modeRead  | CFile::typeText);
	char str1[10],str2[10];
	if(hFile.GetLength()!=0)
	{
		hFile.ReadString(fileContent);
			while(!fileContent.IsEmpty()&& m_control)
			{
				pos=fileContent.Find('-');
				if(pos!=-1)
					fileContent=fileContent.Left(pos);
				ECGData[0]=atoi(fileContent);
				for(int j=165;j>0;j--)
				{
					ECGData[j]=ECGData[j-1];	
				}
				for(int i=0;i<165;i++)
				{
					_itoa(ECGData[i],str1,10);
					EcgDataDlg.DrawWave(str1);		
				}		

				ECGDFTData[0]=atoi(fileContent);//傅立叶变换
				for(int m=1024;m>0;m--)
				{
					ECGDFTData[m]=ECGDFTData[m-1];
				}
				for(int p=1024;p>0;p--)
				{
					ECGDataTemp[p]=ECGDFTData[p];
				}
/*				Fourier(ECGDFTData,10);
				for(int n=0;n<1024;n++)
				{
					_itoa(ECGDFTData[n].x,str2,10);
					EcgDFTDlg.DrawDFTWave(str2);		
				}*/
				int h=512,temp=1;
				realft(ECGDataTemp, h, temp);
				char str[10];
				for(int n=1;n<1025;n++)
				{
					//float ftemp = _cabs(ECGDataTemp[n]);
					//_itoa(ftemp,str,10);
					_itoa(labs(ECGDataTemp[n]),str,10);
					EcgDFTDlg.DrawDFTWave(str);		
				}
//				m_DFTflag=TRUE;
				hFile.ReadString(fileContent);
			}
	}

	//Sleep(100);
	AfxMessageBox("数据读取完毕!");
	return 0;
}

UINT mThreadAnaly(LPVOID pParam)//心电数据动态分析线程
{
	char str[10];
	while(m_DFTflag)
	{
	//			Fourier(ECGDataTemp,10);
				int h=512,temp=1;
				realft(ECGDataTemp, h, temp);
				for(int n=1;n<1025;n++)
				{
					//float ftemp = _cabs(ECGDataTemp[n]);
					//_itoa(ftemp,str,10);
					_itoa(ECGDataTemp[n],str,10);
					EcgDFTDlg.DrawDFTWave(str);		
				}
			m_DFTflag = FALSE;
	}
	return 0;
}

void CECGTestDlg::OnFileOpen() 
{

	 	// TODO: Add your command handler code here
	 	CFileDialog opendlg(TRUE,_T("BMP"),_T("*.txt"),OFN_HIDEREADONLY,_T("心电数据文件(*.txt)|*.txt|"));
	 	opendlg.m_ofn.lpstrTitle="打开心电数据文件";
	 	if(opendlg.DoModal()==IDOK)
	 	{
	 		m_pathName=opendlg.GetPathName();
			m_control=TRUE;
		//	AfxBeginThread(mThreadAnaly,this,THREAD_PRIORITY_NORMAL,0,0,NULL);
	 		AfxBeginThread(mThreadTest,this,THREAD_PRIORITY_NORMAL,0,0,NULL);
	 	}
	 		
		
}

void CECGTestDlg::OnAbort() 
{
	// TODO: Add your command handler code here
	CAboutDlg abortDlg;
	abortDlg.DoModal();
}

void CECGTestDlg::OnTimer(UINT nIDEvent) 
{
	// TODO: Add your message handler code here and/or call default

	CString timestr;
	CTime time = CTime::GetCurrentTime();
	timestr = time.Format("%Y-%m-%d");
	m_Date = timestr;
	m_Time = time.Format("%H:%M:%S");
	UpdateData(FALSE);
	
	CDialog::OnTimer(nIDEvent);
}

void CECGTestDlg::OnCheck6() 
{
	// TODO: Add your control notification handler code here
	/*if(m_filter=FALSE)
		m_filter = TRUE;
	else
		m_filter = FALSE;*/
}

HBRUSH CECGTestDlg::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor) 
{
	HBRUSH hbr = CDialog::OnCtlColor(pDC, pWnd, nCtlColor);
	
	// TODO: Change any attributes of the DC here
	if(nCtlColor==CTLCOLOR_BTN)
	{
		pDC->SetTextColor(RGB(100,0,200));
	}
	if(nCtlColor==CTLCOLOR_STATIC)
	{
		pDC->SetTextColor(RGB(200,0,200));
	}
	// TODO: Return a different brush if the default is not desired
	return hbr;
}


void CECGTestDlg::OnExit() 
{
	// TODO: Add your command handler code here
	OnOK();
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -