【问题标题】:Qt GUI Easiest way to access MainWindow from another classQt GUI 从另一个类访问 MainWindow 的最简单方法
【发布时间】:2017-02-18 00:44:55
【问题描述】:

我正在做一个二十一点程序,并且我在主窗口类之外的另一个类(“hand.h”)中跟踪玩家手中的牌。

在手牌类中,对于我收集的每张卡片,我还创建了一个 QLabel,它为卡片抓取正确的卡片图像,并设置卡片应出现在主窗口上的位置的坐标。

问题是我无法根据最初在 main 函数中创建的 MainWindows 对象创建 QLabel。有什么简单的方法可以让我很容易地获得这些信息吗?感谢您的帮助!

我曾尝试使用 QGuiApplication::topLevelWindows(),但使用它时运气不佳。这是我正在使用的函数。

    #include <QRect>
    #include <QApplication>
    #include <iostream>
    #include <QLabel>
    #include "mainwindow.h"
    #include <QMainWindow>
    #include <QWindowList>
    #include <QWidgetList>
    #include "ui_mainwindow.h"

    void Test() {

    QList<QWindow*> Main_Window = QGuiApplication::topLevelWindows();
     for (int i = 0; i < Main_Window.size(); ++i) {
        if(Main_Window.objectName() == "mainWindow") // name is OK
                break;
        }
    QMainWindow* mainWindow = static_cast<QMainWindow*>(Main_Window);


    QLabel* temp;
    temp = new QLabel(Main_Window);
    temp->setPixmap(QString("Ten of Clubs.png"));
    temp->setGeometry(290, 300, 350, 390);
    temp->show();

    }

这里是创建主窗口的 main.cpp 文件

    int main(int argc, char *argv[])
    {
      srand(time(NULL));
      QApplication a(argc, argv);
      MainWindow w;

      w.show();
      return a.exec();
    }

我在网上找到了迭代代码,但一直遇到问题。 我在尝试遍历列表时遇到问题,但我不知道如何识别列表并且错误表明没有 objectName() 函数。此外,在静态转换行中,有一个错误说我无法将 QList 转换为 QMainWindow 类型。任何帮助将不胜感激。

【问题讨论】:

  • 你能解释一下如何使用 QLabel 来使用 topLevelWindows() 吗?我曾多次尝试使用它,但没有任何运气。除了 main 函数中的预制窗口之外,我没有创建任何窗口。
  • 这应该进入你的问题(你应该编辑)。如果您的代码在 github 上,您可以在问题中提供指向它的链接。
  • 你是对的。我很抱歉。我已经用我的代码更新了它并尝试解决它。再次感谢您的帮助!
  • 我尝试迭代列表并没有成功。有什么建议吗?
  • 这不是 Qt 特有的问题:像对待任何其他需要引用其他对象的 C++ 类一样处理它。

标签: c++ qt qtgui


【解决方案1】:

一般来说不可能,因为某些应用程序可能有几个(顶级)QMainWindow-s(并且它们的列表可能会随着时间而改变)。因此,对于这种情况,您最好将指针(您要处理的特定QMainWindow)明确传递给它....

一种可能的方法是让您的特定子类QApplication(这是一个单例类,请参阅QCoreApplication::instance 以获取其唯一实例)并在您的应用程序子类中放置您想要的显式窗口作为字段处理(也许你甚至想在你的应用程序类中添加一些新的信号或槽)。

但是,您可以使用QGuiApplication::topLevelWindows()QGuiApplication::allWindows() 来获取所有此类窗口的列表。请注意,QWindowList 只是 QList&lt;QWindow *&gt;。因此,请参阅 QList 了解如何遍历或迭代该列表。

一旦你找到了你想要的QMainWindow,通常的做法是在其中添加QLabel(但同样,信号和插槽可能会有所帮助)。

顺便说一句,每个(显示的)小部件都有其窗口,请参阅QWidget::window()


关于您的代码:

你的Main_Window 的名字真的很糟糕(而且这个名字太混乱了,我不能用它)。它是一个列表,而不是一个窗口。所以先写代码:

QMainWindow* mainWindow = nullptr;
{
  QList<QWindow*> topwinlist = QGuiApplication::topLevelWindows();
  int nbtopwin = topwinlist.size();
  for (int ix=0; ix<nbtopwin; ix++) {
    QWindow*curwin = topwinlist.at(ix);
    if (curwin->objectName() == "mainWindow")
      mainWindow = dynamic_cast<QMainWindow*>(curwin);
  }
} 

我没有测试上面的代码,我不确定它是否正确甚至可以编译。但是你为什么不只是有一个指向你的主窗口的全局指针:

 MainWindow*mymainwinp = nullptr;

并在您的 main 正文中适当地初始化它:

int main(int argc, char *argv[]) {
  srand(time(NULL));
  QApplication a(argc, argv);
  MainWindow w;
  mymainwinp = &w;
  w.show();
  int r = a.exec();
  mymainwinp = nullptr;
  return r;
}

然后在其他地方使用mymainwinp(例如在您的Test 中)?如果您想要更优雅的代码,请定义您自己的 QApplication 子类并将 mymainwinp 作为其中的一个字段。

【讨论】:

    猜你喜欢
    • 2021-08-10
    • 1970-01-01
    • 2011-10-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多