SegmentedButton#

New in version 1.2.0.

Segmented buttons help people select options, switch views, or sort elements.

https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-preview.png

Usage#

MDScreen:

    MDSegmentedButton:

        MDSegmentedButtonItem:
            icon: ...
            text: ...

        MDSegmentedButtonItem:
            icon: ...
            text: ...

        MDSegmentedButtonItem:
            icon: ...
            text: ...

Example#

from kivy.lang import Builder

from kivymd.app import MDApp

KV = '''
MDScreen:

    MDSegmentedButton:
        pos_hint: {"center_x": .5, "center_y": .5}

        MDSegmentedButtonItem:
            text: "Walking"

        MDSegmentedButtonItem:
            text: "Transit"

        MDSegmentedButtonItem:
            text: "Driving"
'''


class Example(MDApp):
    def build(self):
        self.theme_cls.theme_style = "Dark"
        return Builder.load_string(KV)


Example().run()

By default, segmented buttons support single marking of elements:

https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-multiselect-false.gif

For multiple marking of elements, use the kivymd.uix.segmentedbutton.segmentedbutton.MDSegmentedButton.multiselect parameter:

MDSegmentedButton:
    multiselect: True
https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-multiselect-true.gif

Control width#

The width of the panel of segmented buttons will be equal to the width of the texture of the widest button multiplied by the number of buttons:

https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-width-by-default.png

But you can use the size_hint_x parameter to specify the relative width:

MDSegmentedButton:
    size_hint_x: .9
https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-width-size-hint-x.png

Customization#

You can see below in the documentation from which classes the MDSegmentedButton and MDSegmentedButtonItem classes are inherited and use all their attributes such as md_bg_color, md_bg_color etc. for additional customization of segments.

Events#

  • on_marked

    The method is called when a segment is marked.

  • on_unmarked

    The method is called when a segment is unmarked.

MDSegmentedButton:
    on_marked: app.on_marked(*args)
def on_marked(
    self,
    segment_button: MDSegmentedButton,
    segment_item: MDSegmentedButtonItem,
    marked: bool,
) -> None:
    print(segment_button)
    print(segment_item)
    print(marked)

A practical example#

import os

from faker import Faker

from kivy.clock import Clock
from kivy.lang import Builder
from kivy.properties import StringProperty

from kivymd.app import MDApp
from kivymd.uix.boxlayout import MDBoxLayout
from kivymd.uix.segmentedbutton import MDSegmentedButton, MDSegmentedButtonItem
from kivymd.utils import asynckivy

KV = '''
<UserCard>
    adaptive_height: True
    md_bg_color: "#343930"
    radius: 16

    TwoLineAvatarListItem:
        id: item
        divider: None
        _no_ripple_effect: True
        text: root.name
        secondary_text: root.path_to_file
        theme_text_color: "Custom"
        text_color: "#8A8D79"
        secondary_theme_text_color: self.theme_text_color
        secondary_text_color: self.text_color
        on_size:
            self.ids._left_container.size = (item.height, item.height)
            self.ids._left_container.x = dp(6)
            self._txt_right_pad = item.height + dp(12)

        ImageLeftWidget:
            source: root.album
            radius: root.radius


MDScreen:
    md_bg_color: "#151514"

    MDBoxLayout:
        orientation: "vertical"
        padding: "12dp"
        spacing: "12dp"

        MDLabel:
            adaptive_height: True
            text: "Your downloads"
            font_style: "H5"
            theme_text_color: "Custom"
            text_color: "#8A8D79"

        MDSegmentedButton:
            size_hint_x: 1
            selected_color: "#303A29"
            line_color: "#343930"
            on_marked: app.on_marked(*args)

            MDSegmentedButtonItem:
                text: "Songs"
                active: True

            MDSegmentedButtonItem:
                text: "Albums"

            MDSegmentedButtonItem:
                text: "Podcasts"

        RecycleView:
            id: card_list
            viewclass: "UserCard"
            bar_width: 0

            RecycleBoxLayout:
                orientation: 'vertical'
                spacing: "16dp"
                padding: "16dp"
                default_size: None, dp(72)
                default_size_hint: 1, None
                size_hint_y: None
                height: self.minimum_height
'''


class UserCard(MDBoxLayout):
    name = StringProperty()
    path_to_file = StringProperty()
    album = StringProperty()


class Example(MDApp):
    def build(self):
        self.theme_cls.theme_style = "Dark"
        return Builder.load_string(KV)

    def on_marked(
        self,
        segment_button: MDSegmentedButton,
        segment_item: MDSegmentedButtonItem,
        marked: bool,
    ) -> None:
        self.generate_card()

    def generate_card(self):
        async def generate_card():
            for i in range(10):
                await asynckivy.sleep(0)
                self.root.ids.card_list.data.append(
                    {
                        "name": fake.name(),
                        "path_to_file": f"{os.path.splitext(fake.file_path())[0]}.mp3",
                        "album": fake.image_url(),
                    }
                )

        fake = Faker()
        self.root.ids.card_list.data = []
        Clock.schedule_once(lambda x: asynckivy.start(generate_card()))


Example().run()
https://github.com/HeaTTheatR/KivyMD-data/raw/master/gallery/kivymddoc/segmented-button-practical-example.gif

API - kivymd.uix.segmentedbutton.segmentedbutton#

class kivymd.uix.segmentedbutton.segmentedbutton.MDSegmentedButtonItem(**kwargs)#

Segment button item.

For more information, see in the RectangularRippleBehavior and ButtonBehavior and MDBoxLayout class documentation.

icon#

Icon segment.

icon is an StringProperty and defaults to ‘’.

text#

Text segment.

text is an StringProperty and defaults to ‘’.

active#

Background color of an disabled segment.

active is an BooleanProperty and defaults to False.

disabled_color#

Is active segment.

active is an ColorProperty and defaults to None.

on_disabled(self, instance, value: bool)#
on_icon(self, instance, icon_name: str)#
class kivymd.uix.segmentedbutton.segmentedbutton.MDSegmentedButton(*args, **kwargs)#

Segment button panel.

For more information, see in the MDBoxLayout class documentation.

Events:
on_marked

The method is called when a segment is marked.

on_unmarked

The method is called when a segment is unmarked.

radius#

Panel radius.

radius is an VariableListProperty and defaults to [20, 20, 20, 20].

multiselect#

Do I allow multiple segment selection.

multiselect is an BooleanProperty and defaults to False.

hiding_icon_transition#

Name of the transition hiding the current icon.

hiding_icon_transition is a StringProperty and defaults to ‘linear’.

hiding_icon_duration#

Duration of hiding the current icon.

hiding_icon_duration is a NumericProperty and defaults to 0.05.

opening_icon_transition#

The name of the transition that opens a new icon of the “marked” type.

opening_icon_transition is a StringProperty and defaults to ‘linear’.

opening_icon_duration#

The duration of opening a new icon of the “marked” type.

opening_icon_duration is a NumericProperty and defaults to 0.05.

selected_items#

The list of MDSegmentedButtonItem objects that are currently marked.

selected_items is a ListProperty and defaults to [].

selected_color#

Color of the marked segment.

selected_color is a ColorProperty and defaults to None.

mark_segment(self, *args)#

Programmatically marks a segment.

adjust_segment_radius(self, *args)#

Rounds off the first and last elements.

adjust_segment_panel_width(self, *args)#

Sets the width of all segments and the width of the panel by the widest segment.

shift_segment_text(self, segment_item: MDSegmentedButtonItem)#

Shifts the segment text to the right, thus freeing up space for the icon (when the segment is marked).

show_icon_marked_segment(self, segment_item: MDSegmentedButtonItem)#

Sets the icon for the marked segment and changes the icon scale to the normal scale.

hide_icon_marked_segment(self, segment_item: MDSegmentedButtonItem)#

Changes the scale of the icon of the marked segment to zero.

restore_bg_segment(self, segment_item)#
set_bg_marked_segment(self, segment_item)#
set_selected_segment_list(self, segment_item)#
mark_item(self, segment_item: MDSegmentedButtonItem)#
uncheck_item(self)#
add_widget(self, widget, *args, **kwargs)#

Add a new widget as a child of this widget.

Parameters:
widget: Widget

Widget to add to our list of children.

index: int, defaults to 0

Index to insert the widget in the list. Notice that the default of 0 means the widget is inserted at the beginning of the list and will thus be drawn on top of other sibling widgets. For a full discussion of the index and widget hierarchy, please see the Widgets Programming Guide.

New in version 1.0.5.

canvas: str, defaults to None

Canvas to add widget’s canvas to. Can be ‘before’, ‘after’ or None for the default canvas.

New in version 1.9.0.

>>> from kivy.uix.button import Button
>>> from kivy.uix.slider import Slider
>>> root = Widget()
>>> root.add_widget(Button())
>>> slider = Slider()
>>> root.add_widget(slider)
on_size(self, instance_segment_button, size: list)#

Called when the root screen is resized.

on_marked(self, *args)#

The method is called when a segment is marked.

on_unmarked(self, *args)#

The method is called when a segment is unmarked.