C++ Qt 从布局中获取子项

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4065378/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 14:27:47  来源:igfitidea点击:

Qt get children from layout

c++qtqt4qt-designer

提问by Alex Ivasyuv

I try to hide all widgets in layout. But looks like findChildrendoesn't work for layout.

我尝试隐藏布局中的所有小部件。但看起来findChildren不适用于布局。

Here's my sample code:

这是我的示例代码:

QLayout * layout = widget -> findChild<QLayout *> (layoutName);
QList<QWidget *> list = layout -> findChildren<QWidget *> ();

cout << list.size() << endl;

sizeis 0, but inside this layout I have a few widgets. But the same code works fine if I try to get widgets from parent widget.

size是 0,但在这个布局中我有一些小部件。但是,如果我尝试从父小部件获取小部件,则相同的代码可以正常工作。

How I can get them from appropriate layout?

我如何从适当的布局中获取它们?

回答by Frank Osterfeld

The layout does not "inject" itself in the parent-child tree, so the widgets stay (direct) children of their parent widget.

布局不会在父子树中“注入”自身,因此小部件保持(直接)其父小部件的子代。

You could use QLayout::count()and QLayout::itemAt()instead.

你可以使用QLayout::count()andQLayout::itemAt()代替。

回答by braggPeaks

You can simply iterate over the layout's items, using itemAt(), then test whether the item is a widget:

您可以简单地迭代布局的项目,使用itemAt(),然后测试该项目是否是一个小部件:

for (int i = 0; i < gridLayout->count(); ++i)
{
  QWidget *widget = gridLayout->itemAt(i)->widget();
  if (widget != NULL)
  {
    widget->setVisible(false);
  }
  else
  {
    // You may want to recurse, or perform different actions on layouts.
    // See gridLayout->itemAt(i)->layout()
  }
}

回答by isamert

It's very late but if anyone finds here like me, here is my solution: I tried @braggPeaks answer(it's same as @Frank Osterfeld answer) but it failed. Then I modified like this and it works like a charm. (I have no idea why it works, because my layout has no null items but still I have to check if it has.)

很晚了,但如果有人像我一样在这里找到,这是我的解决方案:我尝试了@braggPeaks 答案(与@Frank Osterfeld 答案相同)但失败了。然后我像这样修改,它就像一个魅力。(我不知道它为什么起作用,因为我的布局没有空项目,但我仍然必须检查它是否有。)

for (int i = 0; i < this->layout->count(); ++i) {
    QWidget *w = this->layout->itemAt(i)->widget();
    if(w != NULL)
        w->setVisible(false);
}

回答by JCS

Since layout is not part of widget hierarchy, the widget has to be queried from parent but then indexOf can be used to see if it belongs and its location

由于布局不是小部件层次结构的一部分,因此必须从父级查询小部件,然后可以使用 indexOf 查看它是否属于及其位置

  QLayout * top_l= layout(); // The parent widgets layout
   // Find your layout that you want to search inside
   QHBoxLayout * hbox = top_l->findChild<QHBoxLayout*>(QString("horizontalLayout_2"));
    if (hbox != 0) {
        std::cout << "Found horizontalLayout_2!"<<std::endl;
        QPushButton * st = findChild<QPushButton*>(QString("startButton"));

        if (st != 0) {
            std::cout << "Found startButton in top level widget"<<std::endl;
            int idx = hbox->indexOf(st);
            if (idx >=0) {
                std::cout << "Found startButton in hbox layout at location : "
                          <<idx<<std::endl;
            }
        }
    };

回答by supaflav

Responding to an old post, but I wanted a simple way to disable all widgets contained in a layout or any child-layout. This worked for my purposes:

回复旧帖子,但我想要一种简单的方法来禁用布局或任何子布局中包含的所有小部件。这对我的目的有效:

void setEnabledWidgetsInLayout(QLayout *layout, bool enabled)
{
   if (layout == NULL)
      return;

   QWidget *pw = layout->parentWidget();
   if (pw == NULL)
      return;

   foreach(QWidget *w, pw->findChildren<QWidget*>())
   {
      if (isChildWidgetOfAnyLayout(layout,w))
         w->setEnabled(enabled);
   }
}

bool isChildWidgetOfAnyLayout(QLayout *layout, QWidget *widget)
{
   if (layout == NULL or widget == NULL)
      return false;

   if (layout->indexOf(widget) >= 0)
      return true;

   foreach(QObject *o, layout->children())
   {
      if (isChildWidgetOfAnyLayout((QLayout*)o,widget))
         return true;
   }

   return false;
}

回答by Andrew

Did you try children()method instead of findChildren()? Maybe you are getting a 'bad' layout from widget -> findChild<QLayout *> (layoutName)method. Try to find children right after creating the layout - so you are sure the layout is correct. Doing so you will be able do determine what function works wrong.

你有没有尝试children()方法而不是findChildren()?也许您从widget -> findChild<QLayout *> (layoutName)方法中得到了“糟糕”的布局。尝试在创建布局后立即找到孩子 - 这样您就可以确定布局是正确的。这样做您将能够确定哪些功能出错。