【问题标题】:Kivy - How to Size Embedded Anchor Layouts?Kivy - 如何调整嵌入式锚布局的大小?
【发布时间】:2019-06-26 19:31:11
【问题描述】:

我想在 .kv 文件中构建以下简单设计。

它由三部分组成:

  • 一个左上角的锚布局,由 3 列的网格布局组成。我希望它的宽度等于窗口宽度的 20%,高度等于窗口高度的 75%。
  • 一个右上角的锚布局,由垂直方向的框布局组成。我希望它的宽度等于窗口宽度的 80%,高度等于窗口高度的 75%。
  • 一个左下角的锚布局,目前是空的。我希望它的高度是窗口高度的 25%。

这三个部分本身包含在 AnchorLayout 中。

我尝试将这个设计翻译成 .kv 文件,如下所示。

#:kivy 1.11.1

<Example>:
    anchor_x: "center"
    anchor_y: "center"

    AnchorLayout:
        anchor_x: "left"
        anchor_y: "top"
        size_hint: (0.2, 0.75)

        GridLayout:
            cols: 3
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"

    AnchorLayout:
        anchor_x: "right"
        anchor_y: "top"
        size_hint: (0.8, 0.75)

        BoxLayout:
            orientation: "vertical"
            Label:
                text: "HELLO..."
            Label:
                text: "WORLD..."

    AnchorLayout:
        anchor_x: "left"
        anchor_y: "bottom"
        size_hint: (1, 0.25)

        Label:
            text: "FOOTER"

如果重要的话,这里也是我的 .py 文件的代码。

# Importing Kivy
import kivy
kivy.require("1.11.1")

# Importing kivy libraries
from kivy.app import App
from kivy.uix.anchorlayout import AnchorLayout
from kivy.lang import Builder


# Importing external libraries


# Import kv files
Builder.load_file("example.kv")


# Root widget of the application
class Example(AnchorLayout):
    pass


# Application class
class TestApp(App):
    def build(self, **kwargs):
        return Example()

# Launch the application
if __name__=="__main__":
    app = TestApp()
    app.run()

输出看起来不像我预期的那样,如下图所示:

我不明白。因为 AnchorLayout 是 Widget 类的子类,并且它本身包含在 Layout 中,所以它的 size_hint 属性应该可以让我定义它的大小。

我在这里缺少什么?提前致谢!

【问题讨论】:

  • AnchorLayoutanchor_xanchor_y 属性会影响AnchorLayout 的子代,因此您的Example 布局试图将其所有子代靠近中心。
  • 非常感谢,这完全合乎逻辑!

标签: python-3.x layout kivy kivy-language sizing


【解决方案1】:

问题 - 以设计为中心

设计放置在中心。

根本原因

对于anchor_xanchor_y,根是AnchorLayout,其值为'center'。因此,它的所有孩子(AnchorLayouts)都相对于根放置。

下面是您设计的不同颜色的可视化视图。

AnchorLayout

AnchorLayout 将其子元素与边框(上、下、左、右)或中心对齐。

解决方案

您的设计有三种可能的解决方案。首选方法1。

方法 1 - 否 AnchorLayouts

此方法将所有AnchorLayouts 替换为BoxLayouts。它少用了一个AnchorLayout 小部件,这使应用程序的资源效率更高,即使用更少的内存并且应用程序更小。

片段 - 方法 1

<Example>:
    orientation: 'vertical'

    BoxLayout:
        ...
        GridLayout:    # left box
            ...
        BoxLayout:    # right box
            ...
    BoxLayout:    # footer
        ...

方法 2 - BoxLayout 作为根

此方法用BoxLayout 替换根小部件并重新对齐左框。

片段 - 方法 2

<Example>:
    orientation: 'vertical'

    AnchorLayout:
        ...
        GridLayout:    # left box
            ...
        AnchorLayout:    # right box
            ...
    AnchorLayout:    # footer
        ...

方法3

此方法将BoxLayout 添加为根的子级,并将AnchorLayout 的其余部分添加为BoxLayout 的子级。

片段 - 方法 3

<Example>:
    anchor_x: "center"
    anchor_y: "center"

    BoxLayout:
        orientation: 'vertical'

        AnchorLayout:
            ...
            GridLayout:    # left box
                ...
            AnchorLayout:    # right box
                ...
        AnchorLayout:    # footer
            ...

示例

方法 1 - 否 AnchorLayouts

main.py

from kivy.base import runTouchApp
from kivy.lang import Builder

runTouchApp(Builder.load_string("""

BoxLayout:
    orientation: 'vertical'

    BoxLayout:
        size_hint: 1, 0.75

        GridLayout:
            size_hint: 0.2, 1

            canvas.before:
                Color:
                    rgba: 1, 0, 0, 1
                Rectangle:
                    size: self.size
                    pos: self.pos

            cols: 3
            row_force_default: True
            row_default_height: 40

            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"            

        BoxLayout:
            orientation: 'vertical'

            canvas.before:
                Color:
                    rgba: 0, 1, 0, 1
                Rectangle:
                    size: self.size
                    pos: self.pos

            Label:
                text: "HELLO..."
            Label:
                text: "WORLD..."


    BoxLayout:
        size_hint: 1, 0.25

        canvas.before:
            Color:
                rgba: 0, 0, 1, 1
            Rectangle:
                size: self.size
                pos: self.pos

        Label:
            text: "FOOTER"

"""))

输出:方法 1 - 否 AnchorLayouts

方法 2 - BoxLayout 作为根

main.py

from kivy.base import runTouchApp
from kivy.lang import Builder

runTouchApp(Builder.load_string("""

BoxLayout:
    orientation: 'vertical'

    AnchorLayout:
        size_hint: 1, 0.75
        anchor_x: 'left'
        anchor_y: 'top'

        GridLayout:
            size_hint: 0.2, 1

            canvas.before:
                Color:
                    rgba: 1, 0, 0, 1
                Rectangle:
                    size: self.size
                    pos: self.pos

            cols: 3
            row_force_default: True
            row_default_height: 40

            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"            

        AnchorLayout:
            anchor_x: 'right'
            anchor_y: 'top'

            BoxLayout:
                orientation: 'vertical'
                size_hint: 0.8, 1

                canvas.before:
                    Color:
                        rgba: 0, 1, 0, 1
                    Rectangle:
                        size: self.size
                        pos: self.pos

                Label:
                    text: "HELLO..."
                Label:
                    text: "WORLD..."


    AnchorLayout:
        size_hint: 1, 0.25
        anchor_x: 'left'
        anchor_y: 'bottom'

        canvas.before:
            Color:
                rgba: 0, 0, 1, 1
            Rectangle:
                size: self.size
                pos: self.pos

        Label:
            text: "FOOTER"

"""))

输出:方法 2 - BoxLayout 作为 root

【讨论】:

  • 非常感谢这个非常详尽的答案,它有助于理解 Kivy 中的布局是如何工作的。没错,实际上不需要锚布局来产生目标设计。
【解决方案2】:

Example 类更改为扩展FloatLayout 而不是AnchorLayout 允许对其子级进行更多控制。随着对Example 的更改,这是一个看起来更像你想要的kv

<Example>:
    AnchorLayout:
        anchor_x: "center"
        anchor_y: "top"
        size_hint: (0.2, 0.75)
        pos_hint: {'x':0, 'top':1}

        GridLayout:
            cols: 3
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"
            Button:
                text: "X"

    AnchorLayout:
        anchor_x: "center"
        anchor_y: "top"
        size_hint: (0.8, 0.75)
        pos_hint: {'right':1, 'top':1}

        BoxLayout:
            orientation: "vertical"
            Label:
                text: "HELLO..."
            Label:
                text: "WORLD..."

    AnchorLayout:
        anchor_x: "center"
        anchor_y: "bottom"
        size_hint: (1, 0.25)
        pos_hint: {'x':0, 'y':0}

        Label:
            text: "FOOTER"

【讨论】:

  • 非常感谢。事实上,根锚布局是所有子锚布局的中心!
猜你喜欢
  • 1970-01-01
  • 2011-05-09
  • 1970-01-01
  • 1970-01-01
  • 2011-08-31
  • 2015-04-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多