user8506085
user8506085

Reputation:

Kivy Button in Popup not calling function

Here's the code that has the problem:

Class Screen1(Screen):
    def win(self):
        if win == True:
             Self.open_popup()

    def open_popup(self):
        content = BoxLayout()
        button = Button(text="restart", on_press=self.retry(), 
        on_release=self.dismiss() )
        content.add_widget(button)
        self.popup = Popup(title="Popup", content=content)

    def retry(self):
        #resets game

It gives me the error "none is not callable" and "Screen1 has no attribute dismiss" what am I doing wrong?

Also, I have had to call the popup like this and not in a .kv file because that for some reason didn't work with screen manager

Upvotes: 1

Views: 1754

Answers (2)

ikolim
ikolim

Reputation: 16011

Question It gives me the error "none is not callable" and "Screen1 has no attribute dismiss" what am I doing wrong?

Answer Popup has bindable functions such as open and dismiss.

Question Also, I have had to call the popup like this and not in a .kv file because that for some reason didn't work with screen manager

Answer You can create a class of Popup widget, and define all the widgets in the kv file. Please refer to the example below for details.

Example

main.py

from kivy.app import App
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.properties import BooleanProperty
from kivy.uix.popup import Popup


class MessageBox(Popup):
    def __init__(self, obj, **kwargs):
        super(MessageBox, self).__init__(**kwargs)
        self.obj = obj


class Screen1(Screen):
    win = BooleanProperty(True)

    def __init__(self, **kwargs):
        super(Screen1, self).__init__(**kwargs)
        self.name = "screen1"
        self.display_winner()

    def display_winner(self):
        if self.win:
            popup = MessageBox(self)    # pass screen1 object
            popup.open()

    def retry(self):
        print("Reset Game")


class ScreenManagement(ScreenManager):
    pass


class TestApp(App):
    title = "Kivy Screen Manager & Popup Demo"

    def build(self):
        return ScreenManagement()


if __name__ == "__main__":
    TestApp().run()

test.kv

#:kivy 1.10.0

<MessageBox>:
    title: "Popup"
    size_hint: None, None
    size: 400, 400
    auto_dismiss: False

    BoxLayout:
        orientation: "vertical"
        Label:
            text: "Player 1 is the winner!"
        Button:
            size_hint: 1, 0.2
            text: "restart"
            on_press: root.obj.retry()
            on_release: root.dismiss()

<ScreenManagement>:
    Screen1:

<Screen1>:
    name: "screen1"

Output

enter image description here enter image description here

Upvotes: 2

Mikhail Gerasimov
Mikhail Gerasimov

Reputation: 39536

1)

on_press=self.retry()

You're calling self.retry function here and pass it's result as on_press. You should pass function itself:

on_press=self.retry

2)

self.dismiss()

You're trying to call function self.dismiss on Screen object. Screen doesn't have this method, Popup does. You probably want something like this:

content = BoxLayout()
self.popup = Popup(
    title="Popup", 
    content=content
)
button = Button(
    text="restart",
    on_press=self.retry,
    on_release=self.popup.dismiss
)
content.add_widget(button)

Upvotes: 1

Related Questions