from kivy.app import App
from kivy.graphics import Color, Line
from kivy.uix.behaviors import ToggleButtonBehavior
from kivy.uix.togglebutton import ToggleButton
from kivy.uix.widget import Widget
from kivy.utils import get_color_from_hex


class FrameToggleButton(ToggleButton):
    """当前按钮添加边框"""
    def do_press(self):
        """点击改变状态"""
        if self.state == 'normal':
            ToggleButtonBehavior.do_press(self)


class DrawCanvasWidget(Widget):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        # 设置默认颜色
        self.change_color(get_color_from_hex('#19caad'))
        self.line_width = 2

    def on_touch_down(self, touch):
        """触摸显示轨迹"""
        if Widget.on_touch_down(self, touch):
            return
        with self.canvas:
            touch.ud['current_line'] = Line(points=(touch.x, touch.y), width=self.line_width)

    def on_touch_move(self, touch):
        """连线"""
        if 'current_line' in touch.ud:
            touch.ud['current_line'].points += (touch.x, touch.y)

    def change_color(self, new_color):
        """调色"""
        self.last_color = new_color
        self.canvas.add(Color(*new_color))

    def change_line_width(self, line_width='Normal'):
        """线宽"""
        self.line_width = {'Thin': 1, 'Normal': 2, 'Thick': 4}[line_width]

    def clear_canvas(self):
        """清空"""
        saved = self.children[:]
        self.clear_widgets()
        self.canvas.clear()
        for widget in saved:
            self.add_widget(widget)
        self.change_color(self.last_color)


class PaintApp(App):
    def build(self):
        self.canvas_widget = DrawCanvasWidget()
        return self.canvas_widget


if __name__ == '__main__':
    PaintApp().run()

from kivy.uix.behaviors import ToggleButtonBehavior
from kivy.uix.togglebutton import ToggleButton

ToggleButton   ToggleButtonBehavior 两者的关系,

在 Kivy 框架中,ToggleButton 和 ToggleButtonBehavior 是两个不同的组件,但它们之间存在密切的关系。为了理解这两者之间的关系,我们首先要了解它们各自的作用。

  1. ToggleButtonBehavior:
    • 这是一个混入(Mixin)类,提供了切换按钮的基本行为。
    • 它不直接提供任何具体的 UI 实现,而是定义了切换按钮应有的行为逻辑,如状态的改变、触发事件等。
    • 其他 UI 组件可以通过继承这个行为来添加切换功能。
  2. ToggleButton:
    • 这是一个具体的 UI 控件,它继承自 Button 控件,并混入了 ToggleButtonBehavior
    • 也就是说,ToggleButton 是一个具有特定外观和行为的按钮,这些行为由 ToggleButtonBehavior 定义。
    • 用户在使用时,看到的是一个具有切换功能的按钮,而这个功能是由 ToggleButtonBehavior 提供的。

简单来说,ToggleButtonBehavior 提供了切换按钮的核心行为逻辑,而 ToggleButton 是这个行为逻辑的一个具体实现,它结合了 Button 的外观和 ToggleButtonBehavior 的功能。

在你的代码中:

from kivy.uix.behaviors import ToggleButtonBehavior  
from kivy.uix.togglebutton import ToggleButton

第一行导入了 ToggleButtonBehavior,这个类本身不提供 UI,只提供行为逻辑。第二行导入了 ToggleButton,这是一个具体的、可视化的切换按钮控件,它内部已经使用了 ToggleButtonBehavior。如果你想要创建一个自定义的切换按钮控件,你可能会直接使用 ToggleButtonBehavior 并结合其他 UI 控件。但如果你只是想要一个简单的切换按钮,那么直接使用 ToggleButton 就可以了。

#:import C kivy.utils.get_color_from_hex

<BottomColorButton@FrameToggleButton>:
    group: 'color'
    background_normal: 'radio_background_normal.png'
    background_down: 'radio_background_down.png'
    border: (3, 3, 3, 3)
    on_release: app.canvas_widget.change_color(self.background_color)

<LineWidthButton@FrameToggleButton>:
    group: 'line_width'
    color: C('#2c3e50')
    background_color: C('#ecf0f1')
    background_normal: 'radio_background_normal.png'
    background_down: 'radio_background_down.png'
    border: (3, 3, 3, 3)
    on_release: app.canvas_widget.change_line_width(self.text)


<DrawCanvasWidget>:
    canvas.before:
        Color:
            rgba:[1, 1, 1, 1]
        Rectangle:
            pos: self.pos
            size: self.size

    BoxLayout:
        orientation: 'horizontal'
        padding: 2
        spacing: 2
        x: 0
        top: root.top
        size_hint: None, None
        size: 280, 44

        LineWidthButton:
            text: 'Thin'
        LineWidthButton:
            text: 'Normal'
            state: 'down'
        LineWidthButton:
            text: 'Thick'
        Button:
            text: 'Clear'
            on_release: root.clear_canvas()

    BoxLayout:
        id: bottom_box
        orientation: 'horizontal'
        padding: 2
        spacing: 2
        size: root.width, 40

        BottomColorButton:
            background_color: C('#19caad')
            state: 'down'

        BottomColorButton:
            background_color: C('#8cc7b5')

        BottomColorButton:
            background_color: C('#a0eee1')

        BottomColorButton:
            background_color: C('#bee7e9')

        BottomColorButton:
            background_color: C('#beedc7')

        BottomColorButton:
            background_color: C('#d6d5b7')

        BottomColorButton:
            background_color: C('#d1ba74')

        BottomColorButton:
            background_color: C('#e6ceac')

        BottomColorButton:
            background_color: C('#ecad9e')

        BottomColorButton:
            background_color: C('#f4606c')

        BottomColorButton:
            background_color: C('#3498db')

        BottomColorButton:
            background_color: C('#1abc9c')

        BottomColorButton:
            background_color: C('#2ecc71')

        BottomColorButton:
            background_color: C('#f1c40f')

        BottomColorButton:
            background_color: C('#e67e22')

        BottomColorButton:
            background_color: C('#e74c3c')

        BottomColorButton:
            background_color: C('#9b59b6')

        BottomColorButton:
            background_color: C('#ecf0f1')

        BottomColorButton:
            background_color: C('#95a5a6')

        BottomColorButton:
            background_color: C('#000000')

字典选值  键值对应
    def change_line_width(self, line_width='Normal'):
        """线宽"""
        self.line_width = {'Thin': 1, 'Normal': 2, 'Thick': 4}[line_width]

* 这行代码执行了以下操作:

1. 它创建了一个字典,该字典将字符串键 `'Thin'`、`'Normal'` 和 `'Thick'` 分别映射到整数值 `1`、`2` 和 `4`。

2. 使用 `line_width` 参数的值作为键来从该字典中获取对应的值。例如,如果 `line_width` 是 `'Thin'`,则字典将返回 `1`。

3. 将从字典中获取的值赋给 `self.line_width`。这意味着对象的 `line_width` 属性现在将存储与 `line_width` 参数对应的整数值。

python中 字典中{}[]

在Python中,字典(dictionary)是一种可变的数据结构,它存储键值对(key-value pairs),其中键(key)是唯一的,并且用于查找对应的值(value)。字典用大括号 {} 来定义,而方括号 [] 则通常用于列表(list)的索引和切片操作,或者在某些上下文中用于字典的键访问。

字典的定义和访问

字典的定义使用大括号 {},键和值之间用冒号 : 分隔,键值对之间用逗号 , 分隔。

# 定义一个字典  
my_dict = {'key1': 'value1', 'key2': 'value2', 'key3': 'value3'}  
  
# 访问字典中的值  
value1 = my_dict['key1']  # 通过键来访问值  
print(value1)  # 输出: value1
列表的索引和切片

列表(list)的定义使用方括号 [],元素之间用逗号 , 分隔。

# 定义一个列表  
my_list = [1, 2, 3, 4, 5]  
  
# 访问列表中的元素(索引)  
element1 = my_list[0]  # 列表索引从0开始  
print(element1)  # 输出: 1  
  
# 使用切片访问列表的一部分  
subset = my_list[1:4]  # 切片从索引1开始到索引4(不包括4)  
print(subset)  # 输出: [2, 3, 4]
字典的键访问与列表的索引之间的区别

虽然字典的键访问和列表的索引都使用方括号 [],但它们在语义和用途上有很大的不同:

  • 字典的键访问使用方括号是为了查找与给定键相关联的值。
  • 列表的索引使用方括号是为了访问列表中的特定元素(基于其位置)。

此外,尝试访问字典中不存在的键会抛出一个 KeyError 异常,而尝试访问列表的越界索引会抛出一个 IndexError 异常。

字典的键访问也可以使用 .get() 方法

为了避免 KeyError,你可以使用字典的 .get() 方法来访问键,如果键不存在,它会返回 None 或你提供的默认值。

value = my_dict.get('key4', 'default_value')  # 如果'key4'不存在,则返回'default_value'  
print(value)  # 输出: default_value(如果'key4'不在字典中)

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部