Search code examples
kivykivy-language

Reusing code in kivy


how can I reuse such code in kv lang?

<Search_type_panel>:
    max1_optn: max1
    max2_optn: max2
    both_optn: both
    BoxLayout:
        padding: "10dp"
        orientation: 'vertical'
        BoxLayout:
            orientation: 'horizontal'
            CheckBox:
                id: max1
                active: True
                group: 'search_type'
            Label:
                text: "[ref=max1]max1[/ref]"
                size_hint_x: "10"
                markup: True
                on_ref_press: root.setstatus(max1)

            CheckBox:
                id: max2
                active: False
                group: 'search_type'
            Label:
                text: "[ref=max2]max2[/ref]"
                size_hint_x: "10"
                markup: True
                on_ref_press: root.setstatus(max2)
            CheckBox:
                id: both
                active: False
                group: 'search_type'
            Label:
                text: "[ref=both]both[/both]"
                size_hint_x: "10"
                markup: True
                on_ref_press: root.setstatus(max2)

As you can see Label and Checkbox can be a grouped composite panel and I have to just supply different parameters to each one, so on the long run maintenance is simple enough, but How do I pass new parameters to these guys? While I know I can group them as:

  <custom>:
            CheckBox:
                id: both
                active: False
                group: 'search_type'
            Label:
                text: "[ref=both]both[/both]"
                size_hint_x: "10"
                markup: True
                on_ref_press: root.setstatus(max2)  

I don't really know how to pass new parameters to the widgets and reuse the kv lang code.


Solution

  • Reuse code in kv File

    Dynamic Classes

    Since each CheckBox has a different active value (True or False), it is not recommended to create a dynamic class containing both CheckBox and Label because it is difficult to reference the CheckBox and assign different id and active value to each of them when it is instantiated as a children.

    Snippets

    <Custom>:
        CheckBox:
            active: False
            group: 'search_type'
    
        Label:
            size_hint_x: "10"
            markup: True
            on_ref_press: app.root.setstatus(self)
    

    Example

    The example below creates two dynamice classes for CheckBox and Label respectively.

    main.py

    from kivy.app import App
    from kivy.uix.boxlayout import BoxLayout
    from kivy.properties import ObjectProperty
    
    
    class Search_type_panel(BoxLayout):
        max1_optn = ObjectProperty(None)
        max2_optn = ObjectProperty(None)
        both_optn = ObjectProperty(None)
    
        def setstatus(self, label):
            print("\nsetstatus:")
            for key in label.refs:
                print("\tUser clicked on refs =", key)
    
    
    class TestApp(App):
        def build(self):
            return Search_type_panel()
    
    
    if __name__ == "__main__":
        TestApp().run()
    

    test.kv

    #:kivy 1.10.0
    
    <CustomCheckBox@CheckBox>:
        active: False
        group: 'search_type'
    
    <CustomLabel@Label>:
        size_hint_x: "10"
        markup: True
        on_ref_press: app.root.setstatus(self)
    
    <Search_type_panel>:
        max1_optn: max1
        max2_optn: max2
        both_optn: both
    
        BoxLayout:
            padding: "10dp"
            orientation: 'vertical'
    
            BoxLayout:
                orientation: 'horizontal'
                CustomCheckBox:
                    id: max1
                    active: True
                CustomLabel:
                    text: "[ref=max1]max1[/ref]"
    
                CustomCheckBox:
                    id: max2
                CustomLabel:
                    text: "[ref=max2]max2[/ref]"
    
                CustomCheckBox:
                    id: both
                CustomLabel:
                    text: "[ref=both]both[/ref]"
    

    Output

    Img01 - App Startup Img02 - max2 refs clicked