用Visual2019C++MFC生成一个交通信号灯类,使得交通信号灯对象有红灯、绿灯、黄灯三个状态。信号灯的尺寸、状态可以设定,并能显示到指定的可视窗口中。信号灯具有倒计时功能,能够设定三种状态的保持时间,启动后能够持续运行的项目文件
时间: 2024-02-25 07:55:21 浏览: 94
好的,我了解了你的问题。下面是一个简单的实现,可以生成一个交通信号灯类,实现红灯、绿灯、黄灯三个状态,具有倒计时功能,可以设定三种状态的保持时间,能够显示到指定的可视窗口中。
首先,创建一个 MFC 应用程序,选择“Dialog Based”类型,命名为 TrafficLight。在 Resource View 中添加一个 Picture Control 控件,命名为 IDC_LIGHT,大小为 100x200。
在 TrafficLightDlg.h 头文件中添加以下代码:
```cpp
#pragma once
class CTrafficLightDlg : public CDialogEx
{
public:
CTrafficLightDlg(CWnd* pParent = nullptr);
enum { IDD = IDD_TRAFFICLIGHT_DIALOG };
protected:
HICON m_hIcon;
CStatic m_ctlLight;
int m_nTimeLeft;
int m_nRedTime;
int m_nGreenTime;
int m_nYellowTime;
int m_nState;
virtual void DoDataExchange(CDataExchange* pDX);
DECLARE_MESSAGE_MAP()
public:
virtual BOOL OnInitDialog();
afx_msg void OnPaint();
afx_msg HCURSOR OnQueryDragIcon();
afx_msg void OnTimer(UINT_PTR nIDEvent);
void SetState(int nState);
};
```
在 TrafficLightDlg.cpp 实现文件中添加以下代码:
```cpp
#include "pch.h"
#include "TrafficLight.h"
#include "TrafficLightDlg.h"
#include "afxdialogex.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
CTrafficLightDlg::CTrafficLightDlg(CWnd* pParent /*=nullptr*/)
: CDialogEx(IDD_TRAFFICLIGHT_DIALOG, pParent)
, m_nTimeLeft(0)
, m_nRedTime(10)
, m_nGreenTime(20)
, m_nYellowTime(5)
, m_nState(0)
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void CTrafficLightDlg::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
DDX_Control(pDX, IDC_LIGHT, m_ctlLight);
}
BEGIN_MESSAGE_MAP(CTrafficLightDlg, CDialogEx)
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_WM_TIMER()
END_MESSAGE_MAP()
BOOL CTrafficLightDlg::OnInitDialog()
{
CDialogEx::OnInitDialog();
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
SetState(0);
SetTimer(1, 1000, nullptr);
return TRUE;
}
void CTrafficLightDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, reinterpret_cast<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
{
CDialogEx::OnPaint();
}
}
HCURSOR CTrafficLightDlg::OnQueryDragIcon()
{
return static_cast<HCURSOR>(m_hIcon);
}
void CTrafficLightDlg::OnTimer(UINT_PTR nIDEvent)
{
m_nTimeLeft--;
if (m_nTimeLeft <= 0)
{
switch (m_nState)
{
case 0:
SetState(1);
break;
case 1:
SetState(2);
break;
case 2:
SetState(0);
break;
}
}
CDialogEx::OnTimer(nIDEvent);
}
void CTrafficLightDlg::SetState(int nState)
{
m_nState = nState;
switch (nState)
{
case 0:
m_ctlLight.SetBitmap((HBITMAP)LoadImage(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_RED), IMAGE_BITMAP, 0, 0, LR_DEFAULTSIZE));
m_nTimeLeft = m_nRedTime;
break;
case 1:
m_ctlLight.SetBitmap((HBITMAP)LoadImage(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_GREEN), IMAGE_BITMAP, 0, 0, LR_DEFAULTSIZE));
m_nTimeLeft = m_nGreenTime;
break;
case 2:
m_ctlLight.SetBitmap((HBITMAP)LoadImage(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_YELLOW), IMAGE_BITMAP, 0, 0, LR_DEFAULTSIZE));
m_nTimeLeft = m_nYellowTime;
break;
}
}
```
这里使用了三个位图资源,分别为红灯、绿灯、黄灯,需要在资源文件中添加这三个位图资源。可以通过“Resource View”->“Resource.h”文件进行添加。
最后,在 TrafficLightDlg.cpp 文件中添加以下代码,启动对话框:
```cpp
#include "TrafficLight.h"
#include "TrafficLightDlg.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
BEGIN_MESSAGE_MAP(CTrafficLightApp, CWinApp)
ON_COMMAND(ID_HELP, &CWinApp::OnHelp)
END_MESSAGE_MAP()
CTrafficLightApp::CTrafficLightApp()
{
}
CTrafficLightApp theApp;
BOOL CTrafficLightApp::InitInstance()
{
CWinApp::InitInstance();
CTrafficLightDlg dlg;
m_pMainWnd = &dlg;
INT_PTR nResponse = dlg.DoModal();
return FALSE;
}
```
现在,可以编译并运行该程序,即可看到一个交通信号灯的窗口,交通信号灯对象有红灯、绿灯、黄灯三个状态,并且具有倒计时功能,能够设定三种状态的保持时间,能够显示到指定的可视窗口中。
阅读全文