IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> C++知识库 -> QT 仿电子看板系统 DockWidget的使用 -> 正文阅读

[C++知识库]QT 仿电子看板系统 DockWidget的使用

前言

上文
书接上文 额额 上文已经把QChart 的 各个线的种类写了 然后这次就把布局加上

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

一 DockWidget的使用

首先这边个人的使用方式是分成3个类
一个是DockWidgetTitle 也就是DockWidgt的标题
因为标题要带有拖动的效果
所以我们这边需要自定义他都标题框

第二个是DockWidget
也就是自己继承的QDockWidget使用

第三个是DockWidgetList
一个管理DockWidget的一个列表类

1.DockWidgetTitle

class DockWidgetTitle : public QWidget
{
    Q_OBJECT
public:
    DockWidgetTitle(QLabel* lbl = nullptr,QWidget* parent = nullptr);
    DockWidgetTitle(QString text = "",QWidget* parent = nullptr);
    ~DockWidgetTitle();

protected:
    void mouseMoveEvent(QMouseEvent* e);
    void mousePressEvent(QMouseEvent* e);
    void mouseReleaseEvent(QMouseEvent* e);
private:
};

DockWidgetTitle::DockWidgetTitle(QLabel *lbl,QWidget *parent)
    :QWidget (parent)
{
    QHBoxLayout* mLayout = new QHBoxLayout();
    mLayout->setSpacing(0);
    mLayout->setContentsMargins(0,0,0,0);
    mLayout->addWidget(lbl);
    this->setLayout(mLayout);
}

DockWidgetTitle::DockWidgetTitle(QString text, QWidget *parent)
{
    QHBoxLayout* mLayout = new QHBoxLayout();
    mLayout->setSpacing(0);
    mLayout->setContentsMargins(0,0,0,0);

    QLabel* lbl = new QLabel();
    lbl->setAlignment(Qt::AlignCenter);
    lbl->setStyleSheet("background-color:rgb(41,43,77);"
                       "font : ""楷体"" 15pt;"
                       "color:rgb(240,240,240);");
    lbl->setText(text);
    lbl->setFixedHeight(30);
    mLayout->addWidget(lbl);
    this->setLayout(mLayout);
}

DockWidgetTitle::~DockWidgetTitle()
{

}

void DockWidgetTitle::mouseMoveEvent(QMouseEvent *event)
{
    QWidget::mouseMoveEvent(event);
}

void DockWidgetTitle::mousePressEvent(QMouseEvent *event)
{
    QWidget::mousePressEvent(event);
}

void DockWidgetTitle::mouseReleaseEvent(QMouseEvent *event)
{
    QWidget::mouseReleaseEvent(event);
}
这一步其实没有什么太大的改动
你自己整出自己想要的控件代入进去即可
鼠标事件继承父类的就好

2.DockWidget

class DockWidget : public QDockWidget
{
    Q_OBJECT
public:
    DockWidget(QString text = "",QWidget* parent = nullptr);
    DockWidget(QLabel* lbl = nullptr,QWidget* parent = nullptr);
    ~DockWidget();

    void SetDockWidget(QWidget* widget);
//    void Remove();
};

DockWidget::DockWidget(QString text, QWidget *parent)
    :QDockWidget (parent)
{
    DockWidgetTitle* mTitle = new DockWidgetTitle(text);
    this->setTitleBarWidget(mTitle);

    DockWidgetList::Get()->Push(this);
}

DockWidget::DockWidget(QLabel *lbl, QWidget *parent)
    :QDockWidget (parent)
{
    DockWidgetTitle* mTitle = new DockWidgetTitle(lbl);
    this->setTitleBarWidget(mTitle);

    DockWidgetList::Get()->Push(this);
}
DockWidget::~DockWidget()
{

}
void DockWidget::SetDockWidget(QWidget *widget)
{
    this->setWidget(widget);
}
这一步也没有太大的疑问把
就是简单的把Title跟DockWidget链接一下
然后在创建的时候通过List Push进去列表里面操作即可

3.DockWidgetList

class DockWidgetList : public QObject
{
    Q_OBJECT
public:
    static DockWidgetList* Get();

    void Push(DockWidget*);

	//删除所有
    void DeleteAll();
    //隐藏所有
    void HideAll();
    //隐藏某一项
    void HideIndex(int index);
    //显示所有
    void ShowAll();
    //显示某一项
    void ShowIndex(int index);
    //返回某一项
    DockWidget* GetDockWidgetIndex(int);
private:
    QList<DockWidget*> _list;
private:
    DockWidgetList(QObject* obj = nullptr);
    ~DockWidgetList();
};

DockWidgetList *DockWidgetList::Get()
{
    static DockWidgetList cx;
    return &cx;
}

void DockWidgetList::Push(DockWidget *wid)
{
    _list.push_back(wid);
}

void DockWidgetList::DeleteAll()
{
    for(auto & i : _list)
    {
        i->deleteLater();
        i = nullptr;
    }
}

void DockWidgetList::HideAll()
{
    for(auto & i : _list)
    {
        i->hide();
    }
}

void DockWidgetList::HideIndex(int index)
{
    if(index > _list.size() - 1)
    {
        return;
    }
    _list.at(index)->hide();
}

void DockWidgetList::ShowAll()
{
    for(auto &i : _list)
    {
        i->show();
    }
}

void DockWidgetList::ShowIndex(int index)
{
    if(index > _list.size() - 1)
    {
        return;
    }
    _list.at(index)->show();
}

DockWidget *DockWidgetList::GetDockWidgetIndex(int index)
{
    DockWidget* dock = new DockWidget("11");
    if(index >= _list.size())
        return dock;
    DockWidget* widget = _list.at(index);
    ShowIndex(index);
    return widget;
}
DockWidgetList::DockWidgetList(QObject *obj)
    :QObject (obj)
{

}
DockWidgetList::~DockWidgetList()
{
}
这里也是简单的一些show hide操作
没有别的特殊性
使用了单例模式 封装了他的List
通过调用接口的方式调用List

二 MainWindow布局

1.创建并布局

void MainWindow::InitWidget()
{
    ModuleWidget* productionSumWidget = new ModuleWidget(PRODUCTIONSUM);
    ModuleWidget* planForTheMonthWidget = new ModuleWidget(PLANFORTHEMONTH);
    ModuleWidget* deviceMonitorRingWidget = new ModuleWidget(DEVICEMONITORING);
    ModuleWidget* MdloProgressWidget = new ModuleWidget(MOLDPROGRESS);
    ModuleWidget* LoadDistributionWidget = new ModuleWidget(LOADDISTRIBUTION);
    ModuleWidget* PassedTheInSpectionWidget = new ModuleWidget(PASSEDTHEINSPECTION);
    ModuleWidget* QualityManagementWidget = new ModuleWidget(QUALITYMANAGEMENT);
    ModuleWidget* MaterialManagementWidget = new ModuleWidget(MATERIALMANAGEMENT);
    ModuleWidget* VideoSurveillance = new ModuleWidget(VIDEOSURVEILLANCE);

    DockWidget* dockWidget1 = new DockWidget("随便吧");
    dockWidget1->SetDockWidget(productionSumWidget);
    dockWidget1->setObjectName("dockWidget1");

    DockWidget* dockWidget2 = new DockWidget("随便了");
    dockWidget2->SetDockWidget(planForTheMonthWidget);
    dockWidget2->setObjectName("dockWidget2");

    DockWidget* dockWidget3 = new DockWidget("随便吧");
    dockWidget3->SetDockWidget(deviceMonitorRingWidget);
    dockWidget3->setObjectName("dockWidget3");

    DockWidget* dockWidget4 = new DockWidget("随便了");
    dockWidget4->SetDockWidget(MdloProgressWidget);
    dockWidget4->setObjectName("dockWidget4");

    DockWidget* dockWidget5 = new DockWidget("随便吧");
    dockWidget5->SetDockWidget(LoadDistributionWidget);
    dockWidget5->setObjectName("dockWidget5");

    DockWidget* dockWidget6 = new DockWidget("随便了");
    dockWidget6->SetDockWidget(PassedTheInSpectionWidget);
    dockWidget6->setObjectName("dockWidget6");

    DockWidget* dockWidget7 = new DockWidget("随便吧");
    dockWidget7->SetDockWidget(QualityManagementWidget);
    dockWidget7->setObjectName("dockWidget7");

    DockWidget* dockWidget8 = new DockWidget("随便了");
    dockWidget8->SetDockWidget(MaterialManagementWidget);
    dockWidget8->setObjectName("dockWidget8");

    DockWidget* dockWidget9 = new DockWidget("随便了");
    dockWidget9->SetDockWidget(VideoSurveillance);
    dockWidget9->setObjectName("dockWidget9");

    this->addDockWidget(Qt::LeftDockWidgetArea,dockWidget1);
    this->splitDockWidget(dockWidget1,dockWidget2,Qt::Horizontal);
    this->splitDockWidget(dockWidget2,dockWidget3,Qt::Horizontal);
    this->splitDockWidget(dockWidget1,dockWidget4,Qt::Vertical);
    this->splitDockWidget(dockWidget2,dockWidget5,Qt::Vertical);
    this->splitDockWidget(dockWidget3,dockWidget6,Qt::Vertical);
}
这里没有什么值得重点说的
就是创建Widget 赋予DockWidget
然后通过addDockWidget 跟 splitDockWidget 去布局即可
布局的顺序我是寻从 从左到右的方式
addDockWidget()splitDockWidget();
去看看QT的帮助文档应该也不会很难理解

2.菜单

_menu = new QMenu();
    QAction* actionStyle = new QAction("样式");
    QAction* actionSaveLayout = new QAction("保存布局");
    QAction* actionLoadLayout = new QAction("使用布局");

    QMenu* StyleMenu = new QMenu();
    QAction* actionStyle1 = new QAction("样式1");
    QAction* actionStyle2 = new QAction("样式2");
    QAction* actionStyle3 = new QAction("样式3");
    QAction* actionStyle4 = new QAction("样式4");
    QAction* actionStyle5 = new QAction("样式5");
    QAction* actionStyle6 = new QAction("样式6");
    QAction* actionStyle7 = new QAction("样式7");
    StyleMenu->addAction(actionStyle1);
    StyleMenu->addAction(actionStyle2);
    StyleMenu->addAction(actionStyle3);
    StyleMenu->addAction(actionStyle4);
    StyleMenu->addAction(actionStyle5);
    StyleMenu->addAction(actionStyle6);
    StyleMenu->addAction(actionStyle7);
    actionStyle->setMenu(StyleMenu);

    _menu->addAction(actionStyle);
    _menu->addAction(actionSaveLayout);
    _menu->addAction(actionLoadLayout);

    this->connect(actionStyle1,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(1),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(2),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Vertical);
    });
    this->connect(actionStyle2,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(1));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(5),DockWidgetList::Get()->GetDockWidgetIndex(6),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(7),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(5),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(6),DockWidgetList::Get()->GetDockWidgetIndex(8),Qt::Vertical);
    });
    this->connect(actionStyle3,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(2),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(6),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(5),DockWidgetList::Get()->GetDockWidgetIndex(7),Qt::Vertical);
    });
    this->connect(actionStyle4,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(2),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(4),DockWidgetList::Get()->GetDockWidgetIndex(7),Qt::Vertical);
    });
    this->connect(actionStyle5,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(2),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(3),DockWidgetList::Get()->GetDockWidgetIndex(6),Qt::Vertical);
    });
    this->connect(actionStyle6,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(1),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(2),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(1),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(2),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Vertical);
    });
    this->connect(actionStyle7,&QAction::triggered,this,[=](){
        DockWidgetList::Get()->HideAll();
        this->addDockWidget(Qt::LeftDockWidgetArea,DockWidgetList::Get()->GetDockWidgetIndex(0));
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(3),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(3),DockWidgetList::Get()->GetDockWidgetIndex(4),Qt::Horizontal);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(0),DockWidgetList::Get()->GetDockWidgetIndex(5),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(3),DockWidgetList::Get()->GetDockWidgetIndex(6),Qt::Vertical);
        this->splitDockWidget(DockWidgetList::Get()->GetDockWidgetIndex(4),DockWidgetList::Get()->GetDockWidgetIndex(7),Qt::Vertical);
    });
    this->connect(actionSaveLayout,&QAction::triggered,this,[=](){
        SaveLayout();
    });
    this->connect(actionLoadLayout,&QAction::triggered,this,[=](){
        LoadLayout();
    });

void MainWindow::contextMenuEvent(QContextMenuEvent *event)
{
    _menu->exec(QCursor::pos());
    event->accept();
}
菜单这块基本就是QT的Qenu 跟 QAciton去执行
你想怎么做都可以通过 创建 添加 信号与槽处理即可 
contextMenuEvent是右键创建菜单的事件

3.保存布局跟读取布局

void MainWindow::SaveLayout()
{
    const QString fileName = QDir::currentPath() + "/Layout.txt";
    if (fileName.isEmpty())
        return;
    QFile file(fileName);
    if (!file.open(QFile::WriteOnly)) {
        QString msg = tr("Failed to open %1\n%2")
                        .arg(fileName)
                        .arg(file.errorString());
        QMessageBox::warning(nullptr, tr("Error"), msg);
        return;
    }
    QByteArray geo_data = saveGeometry();
    QByteArray layout_data = saveState();
    bool ok = file.putChar((uchar)geo_data.size());
    if (ok)
        ok = file.write(geo_data) == geo_data.size();
    if (ok)
        ok = file.write(layout_data) == layout_data.size();
    if (!ok) {
        QString msg = tr("Error writing to %1\n%2")
                        .arg(fileName)
                        .arg(file.errorString());
        QMessageBox::warning(this, tr("Error"), msg);
        return;
    }
}

void MainWindow::LoadLayout()
{
    const QString fileName = QDir::currentPath() + "/Layout.txt";
    if (fileName.isEmpty())
        return;
    QFile file(fileName);
    if (!file.open(QFile::ReadOnly)) {
        QString msg = tr("Failed to open %1\n%2")
                        .arg(fileName)
                        .arg(file.errorString());
        QMessageBox::warning(this, tr("Error"), msg);
        return;
    }
    uchar geo_size;
    QByteArray geo_data;
    QByteArray layout_data;
    bool ok = file.getChar((char*)&geo_size);
    if (ok) {
        geo_data = file.read(geo_size);
        ok = geo_data.size() == geo_size;
    }
    if (ok) {
        layout_data = file.readAll();
        ok = layout_data.size() > 0;
    }
    if (ok)
        ok = restoreGeometry(geo_data);
    if (ok)
        ok = restoreState(layout_data);
    if (!ok) {
        QString msg = tr("Error reading %1")
                        .arg(fileName);
        QMessageBox::warning(this, tr("Error"), msg);
        return;
    }
}

三.总结

这篇文章应该都比较容易理解
因为都是一些关于界面的一些操作

我永远喜欢慧慧

  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2022-03-21 20:30:30  更:2022-03-21 20:34:26 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 3:07:37-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码