python-3.xkivykivymd

Cannot change Screen in KivyMD


I am a beginner and studying KivyFramework, and in the process of studying I had a problem. I have a kv-file:

<DrawerClickableItem@MDNavigationDrawerItem>

<DrawerLabelItem@MDNavigationDrawerItem>
    focus_behavior: False
    _no_ripple_effect: True

MDScreen:    

    MDNavigationLayout:

        MDTopAppBar:
            id: toolbar
            title: "MainScreen"
            elevation: 4
            pos_hint: {"top": 1}            
            left_action_items: [["menu", lambda x: nav_drawer.set_state("open")]]

        MDScreenManager:
            id: sm          

            MDScreen:                
                name: 'empty'
                Empty:

            MDScreen:
                name: 'messages'
                Messages:


        MDNavigationDrawer:
            id: nav_drawer
            radius: (0, 16, 16, 0)
            close_on_click: True     

            MDNavigationDrawerMenu:

                MDNavigationDrawerHeader:
                    title: 'Title'
                    text: "Text"
                    spacing: "4dp"
                    padding: "12dp", 0, 0, "56dp"
                     

                DrawerClickableItem:                    
                    text: "Notify"
                    icon: "message-outline"
                    on_release:
                        sm.current = 'messages'
                        toolbar.title = 'Notify'
                        nav_drawer.set_state('close')

<Empty>:
    name: 'empty'

    MDFloatLayout:
        MDLabel:
            text: 'Welcome!'
            text_color: 'black'
            text_size: self.width, None
            pos_hint: {'center_x': .5, 'center_y': .54}
            halign: "center"

<Messages>
    name: 'messages'    
    MDBoxLayout:
        padding: [0, 55, 0, 0]        

        MDScrollView:            

            MDList:           

                OneLineAvatarIconListItem:
                    text: 'Messages'
                    divider_color: 'grey'                    
                    on_press:
                        root.messages_click() 
                        # app.sm.current = 'empty'
                    IconRightWidget:
                        icon: "arrow-right-bold-circle-outline"

and py-code:

class Empty(Screen):
    pass

class Messages(Screen):

    def messages_click(self):
        MainApp().sm.current = 'empty'
        MainApp().sm.transition.direction = 'left'            

class MainApp(MDApp):
    sm = MDScreenManager()

    def build(self):
        return Builder.load_string(KV)

MainApp().run()

When i click on OneLineAvatarIconListItem named Messages I get an error No Screen with name "empty" How can i solve it? I've tre to use self.manager.current = 'empty' and self.manager.current_screen but it's not work

Environment

Win: 11

Python: 3.8

Kivy: 1.1.1

KivyMD: 1.2.0dev


Solution

  • In your code:

    def messages_click(self):
        MainApp().sm.current = 'empty'
        MainApp().sm.transition.direction = 'left'
    

    MainApp() creates a new instance of the MainApp class. That new instance is unrelated to the MainApp instance that is the currently running App. Since that code is in a Screen class, you can access its manager to change the Screen, like this:

    def messages_click(self):
        self.manager.current = 'empty'
        self.manager.transition.direction = 'left'
    

    However, that illuminates another issue with your code where your Screen classes are not the children of a ScreenManager. That can be corrected by slightly simplifying part of your kv:

        MDScreenManager:
            id: sm          
    
            Empty:
    
            Messages:
    

    Also, there is a line of code in your MainApp:

    sm = MDScreenManager()
    

    That is creating a new instance of MDScreenManager that is, again, not related to the MSCrennManager that is created by your kv. I suggest that line should just be deleted.