在 Python/Kivy 中调整 .png 大小时如何避免出现颠簸

How to avoid bumps at my .png's when resizing them in Python/Kivy

我是 Kivy 的新手,我正在尝试为以后即将到来的程序部分建立一个模板。 现在我被卡住了,因为当我尝试调整它们的大小时,我美妙的圆形 .png 按钮都得到了 "edges/bumps" 的国王。

按钮应该是这样的...

...这就是实际发生的情况(请忽略白色背景)

我用其他多个 .png 尝试过,所以我非常确定问题不在 .png 本身。

这是我的代码(我把它缩短了以便于找到相关部分。如果你觉得你需要更多代码,我当然可以添加):

test.kv

#:kivy 1.0.9

<MainWindow>:
BoxLayout:
    #[shortened for readability reasons]
    BoxLayout:
        #[shortened for readability reasons]
    BoxLayout:
        #[shortened for readability reasons]
        AnchorLayout:
            #[shortened for readability reasons]
        FloatLayout:
            canvas:
                Rectangle:
                    pos: self.pos
                    size: self.size
            Button:
                id: leftButton
                background_normal: 'assets/graphics/buttons/dummy.png'
                background_down: 'assets/graphics/buttons/.png'
                size_hint: .15, .15
                pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}

也许这里有人知道问题出在哪里以及如何解决? 请记住,我想在 .kv 文件中修复它(如果可能),以便以后可以更轻松地重用它。

另一个小问题是其他一些按钮的位置。我想让它们与右侧对齐,但我找不到如何访问按钮本身的宽度,所以我可以从 self.width 中减去它(如果我得到的话,它应该是周围布局的宽度没错)

有什么建议吗?


同时我做了一些测试以确保文件类型不是这里的问题。据我所知,我尝试使用 .gif 和 .tif,这是支持透明度的其他最常见的文件类型。 结果与 .png

相同

为了阐明设计最终应该是什么样子,我将添加另一张图片:

所以我认为我必须使用 FloatLayout 来完成。我想像在 pyqt 中那样用网格来做,但是在 kivy 中,不可能定义应该放置小部件的单元格,也不能给它一个 colspan 或 rowspan。至少那是我读过的。如有错误请指正


好的,ikolim 的解决方案到目前为止有效,但产生了另一个问题:我不能再使用 background_normal 和 background_down,但我觉得我必须给用户一个视觉反馈 -例如 - 单击按钮并按住它。我想因为我使用 ButtonBehavier,所以我也可以使用背景素材。但事实似乎并非如此。有谁能给我一些解决方法的提示吗?


更新:我现在可以使用视觉反馈了。解决方案非常简单,直到上周五我才忽略它(直到现在我才能回到有互联网的计算机上)。 所以对于有类似问题的感兴趣的reader,这是我的解决方案: 我现在只使用 on_press 和 on_release 侦听器并将那里的图像源从 myPic.png 更改为 myPic_clicked.png,反之亦然。

所以问题解决了,我会在几天后写一个完整的答案并关闭这个问题。 但在那之前,我真的很想知道是否有人有想法,为什么我有这个颠簸。一方面为了对kivy有全面的了解,另一方面为了避免以后出现这个问题。

提前致谢!

  • 创建继承 ButtonBehavior 和 Image 的自定义按钮
  • 使用 GridLayout 将自定义按钮排成一行

示例

main.py

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

runTouchApp(Builder.load_string('''
#:kivy 1.11.0

<CustomButton@ButtonBehavior+Image>:

GridLayout:
    rows: 1
    canvas:
        Rectangle:
            pos: self.pos
            size: self.size

    CustomButton:
        id: Button0
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button1
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button2
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button3
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')
'''))

输出

好的,在没有其他人似乎知道原始问题是什么之后,这里至少有一个非常有效的解决方案。

ikolim 的回答几乎完全正确,我要对此表示敬意。但它也错过了一个——至少对我来说——重要的部分。这是他的代码。之后我将解释缺少的内容:

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

runTouchApp(Builder.load_string('''
#:kivy 1.11.0

<CustomButton@ButtonBehavior+Image>:
GridLayout:
    rows: 1
    canvas:
        Rectangle:
            pos: self.pos
            size: self.size

    CustomButton:
        id: Button0
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button1
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button2
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')

    CustomButton:
        id: Button3
        source: './dummy.png'
        size_hint: .15, .15
        pos_hint: {'x':root.size_hint_x/2, 'y':root.size_hint_y/2}
        on_release:
            print('CustomButton clicked')
'''))

问题是,如果我们这样做,带有颠簸的错误就消失了。但是 background_normal 和 background_down 也不再起作用了。解决方案是改用 on_pressed 和 on_release 并更改其中的源。