【问题标题】:QDockWidget with a QGridLayout - Widget within the Layout do not align to the top带有 QGridLayout 的 QDockWidget - 布局内的小部件不与顶部对齐
【发布时间】:2012-02-27 15:38:21
【问题描述】:

我正在尝试创建一个可停靠的工具栏(类似于您在 Photoshop 中使用的工具),它将容纳 2 x (n) 网格的按钮。我的想法是使用一个 QGridLayout 父级到一个空白 QWidget,它被添加到一个 QDockWidget,并添加按钮到 QGridLayout。除了对齐之外,这似乎有效。

我已经为按钮设置了对齐方式...

myLayout->addWidget(button1,0,0,1,1,Qt::AlignTop);
myLayout->addWidget(button2,0,1,1,1,Qt::AlignTop);
myLayout->addWidget(button3,1,0,1,1,Qt::AlignTop);
myLayout->addWidget(button4,1,1,1,1,Qt::AlignTop);

...但是网格正在扩展到 QDockWidget 的完整高度,如下所示:

按钮也在水平扩展,以填满整个空间。我想我可以限制水平调整大小的能力(如果可能的话?)。

我在文档中忽略了一个函数来更好地控制 GridLayout 以限制它填充父小部件的整个宽度/高度?作为一个附带问题,有没有办法防止 QDOckWidget 被重新调整到某个方向?

【问题讨论】:

    标签: qt toolbar dock qdockwidget qgridlayout


    【解决方案1】:

    来自the documentation

    QGridLayout 占用提供给它的空间(通过它的父布局 或通过 parentWidget()),将其分成行和列,并且 将其管理的每个小部件放入正确的单元格中。

    列和行的行为相同;我们将讨论列,但是 行有等效的功能。

    每一列都有一个最小宽度和一个拉伸因子。最小值 宽度是使用 setColumnMinimumWidth() 和 该列中每个小部件的最小宽度。拉伸因子为 使用 setColumnStretch() 设置并确定有多少可用 列的空间将超过其必要的最小值。

    所以最简单的方法是使用固定大小的可停靠小部件QWidget::setFixedSize。一般来说,我不会推荐它(管理布局),但它非常适合您的情况,原因如下:

    • 所有按钮的大小都相同,因此您大致了解工具栏的大小,具体取决于按钮的数量。
    • 您不需要管理布局行为。
    • 您可以使用任一维度,也可以同时使用两者

    例如添加按钮时

      void addButton(QWidget* w,QGridLayout* wl, QButton* button, posParams...){
           // w is the widget inside the QDockWidget (edit)
           //wl is w layout
           //break the constraints, the widget can be resized
           w->setFixedSize(QSize(QWIDGETSIZE_MAX,QWIDGETSIZE_MAX));
           // only line to change if you want to hide, remove widget
           wl->addWidget(button, params);
           //fit to contents 
           w->adjustSize();
           // can be swapped to w->setFixedHeight, setFixedWidth
           w->setFixedSize(w->size());
      }
    

    尝试一下,并验证在修改后停靠和取消停靠小部件时事情不会出错。您应该注意,打破约束也会打破 布局。

    一般QLayout::SizeConstraintQWidget::minimumSizeHintQWidget::minimumSize之间存在层次结构,您可以在文档中找到。

    • QWidget::minimumSize 默认未设置。当它存在时,它占了上风 QWidget::minimumSizeHint
    • QWidget::minimumSizeHint 如果小部件不在布局中则无效(意味着可以用鼠标将其大小调整为 0),否则使用布局定义的那个。
    • QLayout::SizeConstraint 保存它*直接*管理的小部件的默认布局行为。如果您将布局A 嵌套在布局B 中,则添加到A 的所有小部件都将使用其属性。此外,如果 B 中的小部件 W 定义了自己的布局,则此布局约束将应用于小部件 W

    【讨论】:

    • 哇,感谢您的解释。因此,如果我理解正确,我可以设置 QWidget::setFixedSize (基于按钮的数量,根据您的示例动态,或者如果按钮数量恒定,则一次),然后将该 QWidget 添加到我的QDockWidget(处理停靠功能)。如果是这样,那就完美了!至于取消停靠/重新停靠 - QDockWidget 将如何反应?我敢肯定我可以自己测试一下,只是好奇。我假设在停靠时,大小会扩展到整个窗口 - 取消停靠会保持固定大小吗?
    • 你是对的,你需要在 QDockWidget 中修复小部件的大小。我更新我的答案。 QdockWidget 的样式是浮动的还是不浮动的,如果它在一个选项卡中,等等......你需要看看它在你改变这些属性时的行为,并使用上面的 3 条规则来调整它的行为。
    【解决方案2】:

    使用 QVBoxLayout,您首先添加 QGridLayout,然后添加这样的拉伸:

    my_vboxlayout->addLayout( my_gridlayout );
    my_vboxlayout->addStretch( 1 );
    

    或者,您可以告诉您的 QGridLayout 最后一行应该扩展到最大尺寸,这将推动按钮。
    在您的情况下,它将是:

    mygridlayout->setRowStretch( 2, 1 ); // give 3rd row maximum space
    

    文档链接:
    QBoxLayout
    QGridLayout

    【讨论】:

    • 刚刚尝试了第二个选项 - 设置第二行(或者我的最后一行),效果很好。谢谢!
    【解决方案3】:

    在下方插入一个垂直分隔符。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-09-28
      • 1970-01-01
      • 2020-10-08
      • 1970-01-01
      • 1970-01-01
      • 2020-11-16
      • 1970-01-01
      相关资源
      最近更新 更多