当前位置:首页 » 《我的小黑屋》 » 正文

QT开发:基于Qt实现的交通信号灯模拟器:实现一个带有倒计时功能的图形界面应用

7 人参与  2024年10月09日 16:40  分类 : 《我的小黑屋》  评论

点击全文阅读


介绍

        本文将介绍如何使用Qt框架实现一个简单的交通信号灯控制程序。本程序包括一个图形界面,显示红、黄、绿三色信号灯,并通过定时器控制信号灯的切换。同时,我们还将实现一个带有按钮的界面,用于展示信号灯的状态。

1. 安装Qt开发环境

        如果你还没有安装Qt开发环境,请前往Qt官网下载并安装最新的Qt版本。安装过程中请确保选择了Qt Creator和相应的Qt版本(如Qt 5或Qt 6)。本文所示例子基于Qt 5.12版本实现。

2. 创建新项目

2.1 打开Qt Creator

启动Qt Creator开发环境。

2.2 创建新项目

在Qt Creator主界面,点击File -> New File or Project。在弹出的窗口中,选择Application -> Qt Widgets Application,然后点击Choose...按钮。输入项目名称,例如trafficlightApp,选择项目保存路径,然后点击Next。选择合适的Qt版本和编译器配置,然后点击Next。确认类名设置,默认情况下,主窗口类名为MainWindow。你可以保留默认值或者修改,点击Next。点击Finish,Qt Creator会自动生成一个新的Qt Widgets项目。

3. 设置项目结构

3.1 添加必要文件

在项目创建完成后,你可以看到Qt Creator已经为你生成了基本的项目结构。接下来,我们需要手动添加一些文件。

在项目视图中右键点击项目名称(trafficlightApp),选择Add New...。选择C++ Class,然后点击Choose...。输入类名为TrafficLightWidget,基类选择QWidget,然后点击Next,再点击Finish。使用相同的方法,再添加一个类Widget,基类选择QWidget

我们的项目结构如下:

trafficlightApp/├── images/│   ├── green.png│   ├── red.png│   └── yellow.png├── trafficlightApp.pro├── main.cpp├── trafficlightwidget.cpp├── trafficlightwidget.h├── widget.cpp├── widget.h└── widget.ui

4. 编写代码

4.1 修改trafficlightApp.pro文件

        编辑项目文件trafficlightApp.pro,添加资源文件信息,若为windows系统上QT Creator创建的项目trafficlightApp.pro不要修改,会自动配置;在Ubuntu系统上需要手动在文件中添加源文件和头文件等。

QT       += core guigreaterThan(QT_MAJOR_VERSION, 4): QT += widgetsCONFIG += c++11# You can make your code fail to compile if it uses deprecated APIs.# In order to do so, uncomment the following line.#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0SOURCES += \    main.cpp \    trafficlightwidget.cpp \    widget.cppHEADERS += \    trafficlightwidget.h \    widget.hFORMS += \    widget.ui# Default rules for deployment.qnx: target.path = /tmp/$${TARGET}/binelse: unix:!android: target.path = /opt/$${TARGET}/bin!isEmpty(target.path): INSTALLS += targetDISTFILES += \    images/green.png \    images/red.png \    images/yellow.png

4.2 编写main.cpp

#include "trafficlightwidget.h"#include <QApplication>int main(int argc, char *argv[]){    QApplication a(argc, argv);    TrafficLightWidget w;    w.show();    return a.exec();}

4.3 编写trafficlightwidget.h

#ifndef TRAFFICLIGHTWIDGET_H#define TRAFFICLIGHTWIDGET_H#include <QWidget>#include <QTimer>class TrafficLightWidget : public QWidget{    Q_OBJECTpublic:    explicit TrafficLightWidget(QWidget *parent = nullptr);protected:    void paintEvent(QPaintEvent *event) override;private slots:    void updateLight();private:    QTimer *timer;    int lightIndex; // 0 for red, 1 for yellow, 2 for green    int redDuration; // Duration for red light in ms    int yellowDuration; // Duration for yellow light in ms    int greenDuration; // Duration for green light in ms    int elapsedTime; // Time elapsed since last change in ms    int remainingTime; // Remaining time for current light in seconds    int getLightDuration(int light) const; // Function to get the duration for the given light};#endif // TRAFFICLIGHTWIDGET_H

4.4 编写trafficlightwidget.cpp

#include "trafficlightwidget.h"#include <QPainter>TrafficLightWidget::TrafficLightWidget(QWidget *parent)    : QWidget(parent),      lightIndex(0), // Start with red light      redDuration(30000), // Red duration 30 seconds      yellowDuration(3000), // Yellow duration 3 seconds      greenDuration(30000), // Green duration 30 seconds      elapsedTime(0), // Reset elapsed time      remainingTime(redDuration / 1000) // Start with red light's duration{    setFixedSize(200, 660); // Set the size of the traffic light widget to include countdown    // Set up the timer to tick every second (1000 milliseconds)    timer = new QTimer(this);    connect(timer, &QTimer::timeout, this, &TrafficLightWidget::updateLight);    timer->start(1000); // Start the timer}void TrafficLightWidget::paintEvent(QPaintEvent *){    QPainter painter(this);    QColor lightRed(255, 0, 0, 255);    QColor lightYellow(255, 255, 0, 255);    QColor lightGreen(0, 255, 0, 255);    QColor lightOff(50, 50, 50, 255);    // Draw the traffic light frame    painter.setBrush(Qt::black);    painter.drawRect(10, 10, 180, 580);    // Draw the red light    painter.setBrush(lightIndex == 0 ? lightRed : lightOff);    painter.drawEllipse(40, 30, 120, 120);    // Draw the yellow light    painter.setBrush(lightIndex == 1 ? lightYellow : lightOff);    painter.drawEllipse(40, 180, 120, 120);    // Draw the green light    painter.setBrush(lightIndex == 2 ? lightGreen : lightOff);    painter.drawEllipse(40, 330, 120, 120);    // Draw the countdown timer    painter.setPen(Qt::white);    QFont font = painter.font();    font.setPointSize(24);    painter.setFont(font);    QString remainingTimeString = QString::number(remainingTime);    painter.drawText(QRect(40, 530, 120, 50), Qt::AlignCenter, remainingTimeString);}void TrafficLightWidget::updateLight(){    // Update remaining time for the current light    remainingTime = (getLightDuration(lightIndex) - elapsedTime) / 1000;    elapsedTime += 1000; // Add 1 second to elapsed time    // Check if the current light duration has passed    if (elapsedTime >= getLightDuration(lightIndex)) {        lightIndex = (lightIndex + 1) % 3; // Cycle through the lights        elapsedTime = 0; // Reset elapsed time        remainingTime = getLightDuration(lightIndex) / 1000; // Reset remaining time    }    update(); // Request a repaint}int TrafficLightWidget::getLightDuration(int light) const{    switch (light) {        case 0: return redDuration; // Red light duration        case 1: return yellowDuration; // Yellow light duration        case 2: return greenDuration; // Green light duration        default: return 0; // Default case (should not be reached)    }}

4.5 编写widget.h

#ifndef WIDGET_H#define WIDGET_H#include <QWidget>QT_BEGIN_NAMESPACEnamespace Ui { class Widget; }QT_END_NAMESPACEclass Widget : public QWidget{    Q_OBJECTpublic:    Widget(QWidget *parent = nullptr);    ~Widget();private slots:    void on_toolButton_clicked();    void on_pushButton_clicked();    void on_pushButton_2_clicked();private:    Ui::Widget *ui;};#endif // WIDGET_H

4.6 编写widget.cpp

#include "widget.h"#include "ui_widget.h"#include <QGraphicsEffect>#include<QMessageBox>Widget::Widget(QWidget *parent)    : QWidget(parent)    , ui(new Ui::Widget){    ui->setupUi(this);    // Set up button styles    ui->pushButton->setStyleSheet("border-radius: 50%; background-color: #ff0000;");    ui->pushButton_2->setStyleSheet("border-radius: 50%; background-color: rgb(85, 255, 0);");}Widget::~Widget(){    delete ui;}void Widget::on_toolButton_clicked(){    // Placeholder for tool button click event}void Widget::on_pushButton_clicked(){    QMessageBox::information(this,"提示:","红灯,请等待!");}void Widget::on_pushButton_2_clicked(){     QMessageBox::information(this,"提示:","绿灯,请通行!");}

4.7 编辑widget.ui

在Qt Designer中打开widget.ui文件:

<?xml version="1.0" encoding="UTF-8"?><ui version="4.0"> <class>Widget</class> <widget class="QWidget" name="Widget">  <property name="geometry">   <rect>    <x>0</x>    <y>0</y>    <width>800</width>    <height>600</height>   </rect>  </property>  <property name="windowTitle">   <string>红绿灯模拟程序</string>  </property>  <widget class="QCheckBox" name="checkBox">   <property name="geometry">    <rect>     <x>10</x>     <y>10</y>     <width>81</width>     <height>31</height>    </rect>   </property>   <property name="text">    <string>CheckBox</string>   </property>  </widget>  <widget class="QToolButton" name="toolButton">   <property name="geometry">    <rect>     <x>710</x>     <y>0</y>     <width>71</width>     <height>31</height>    </rect>   </property>   <property name="styleSheet">    <string notr="true">border-color: rgb(0, 255, 255);border-left-color: qradialgradient(spread:pad, cx:0.5, cy:0.5, radius:0.5, fx:0.5, fy:0.5, stop:0 rgba(0, 0, 0, 0), stop:0.52 rgba(0, 0, 0, 0), stop:0.565 rgba(82, 121, 76, 33), stop:0.65 rgba(159, 235, 148, 64), stop:0.721925 rgba(255, 238, 150, 129), stop:0.77 rgba(255, 128, 128, 204), stop:0.89 rgba(191, 128, 255, 64), stop:1 rgba(0, 0, 0, 0));</string>   </property>   <property name="text">    <string>Click Me</string>   </property>  </widget>  <widget class="QPushButton" name="pushButton">   <property name="geometry">    <rect>     <x>30</x>     <y>100</y>     <width>100</width>     <height>100</height>    </rect>   </property>   <property name="styleSheet">    <string notr="true">background-color:white;border-radius:5px;border:1px solid  black;color:#587fba;</string>   </property>   <property name="text">    <string>MyButton</string>   </property>   <property name="flat">    <bool>false</bool>   </property>  </widget>  <widget class="QPushButton" name="pushButton_2">   <property name="geometry">    <rect>     <x>330</x>     <y>100</y>     <width>100</width>     <height>100</height>    </rect>   </property>   <property name="styleSheet">    <string notr="true">background-color:rgb(85, 255, 0);border-radius:5px;border:1px solid  black;color:#587fba;</string>   </property>   <property name="text">    <string>MyButton</string>   </property>   <property name="flat">    <bool>false</bool>   </property>  </widget> </widget> <resources/> <connections/></ui>

配置这些控件的属性,如位置、文本内容和样式表等,可以参考前面提供的widget.ui文件内容。

5. 构建和运行项目

点击Qt Creator中的Build按钮来构建项目。如果项目配置正确且代码无误,构建过程应能成功完成。

        点击Run按钮,运行程序。你将看到一个包含交通信号灯和两个按钮的窗口。红色、黄色、绿色信号灯会根据设定的时长自动切换。

运行结果展示:

4ec0e1f533f94a1b8a5cd0bbae78a090.png            091ad3c21227481f9e565a357e1cc5f2.png               cce42fb233b140eda43fc7030053a743.png

通过上述详细步骤,你已经完成了一个基于Qt的简单交通信号灯控制程序的实现。希望这些说明对你有所帮助。

 


点击全文阅读


本文链接:http://zhangshiyu.com/post/169606.html

<< 上一篇 下一篇 >>

  • 评论(0)
  • 赞助本站

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

关于我们 | 我要投稿 | 免责申明

Copyright © 2020-2022 ZhangShiYu.com Rights Reserved.豫ICP备2022013469号-1