Search code examples
pythonkivyattributeerrorgetattrgetattribute

AttributeError: 'super' object has no attribute '__getattr__' ( I searched, but to no avail)


I'm trying to make a code to calculate how much paint is needed to paint the whole room.

My coding:

# main.py

from kivy.app import App
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.properties import ObjectProperty
from kivy.uix.popup import Popup
from kivy.uix.label import Label
from database import DataBase
from kivy.properties import NumericProperty


class CreateAccountWindow(Screen):
    panjang = ObjectProperty(None)
    lebar = ObjectProperty(None)
    tinggi = ObjectProperty(None)

    def submit(self):
        if self.tinggi.text !="":
            try:
                if float(self.tinggi.text) and float(self.lebar.text) and float(self.panjang.text):

                    sm.current = "main"

            except:
                invalidForm()

        else:
            invalidForm()




class MainWindow(Screen):
    # Each screen has by default a property manager that gives 
    # you the instance of the ScreenManager used.

    # declare class attributes
    panjang = ObjectProperty(None)
    lebar = ObjectProperty(None)
    tingi = ObjectProperty(None)
    luas1 = ObjectProperty(None)
    luas2 = ObjectProperty(None)
    cat = ObjectProperty(None)

    def logOut(self):
        self.manager.current = "create"

    def volume(self):
        luas1 = float(self.manager.ids.create.panjang.text) * float(self.manager.ids.create.tinggi.text) / 10
        luas2 = float(self.manager.ids.create.lebar.text) * float(self.manager.ids.create.tinggi.text) / 10

        self.luas1.text = str(luas1)
        self.luas2.text = str(luas2)
        self.cat.text = str(luas1 * 2 + luas2 * 2)

    def on_enter(self, *args):
        self.volume()    # calculate volume
        self.panjang.text = "Panjang: " + self.manager.ids.create.panjang.text
        self.lebar.text = "Lebar: " + self.manager.ids.create.lebar.text
        self.tinggi.text = "Tinggi: " + self.manager.ids.create.tinggi.text
        self.luas1.text = "Luas:" + self.manager.ids.main.luas1.text
        self.luas2.text = "Luas:" + self.manager.ids.main.luas2.text
        self.cat.text = "Luas:" + self.manager.ids.main.cat.text




class WindowManager(ScreenManager):
    pass


def invalidLogin():
    pop = Popup(title='Invalid Login',
                  content=Label(text='Invalid username or password.'),
                  size_hint=(None, None), size=(400, 400))
    pop.open()


def invalidForm():
    pop = Popup(title='Invalid Form',
                  content=Label(text='Please fill in all inputs with valid information.'),
                  size_hint=(None, None), size=(400, 400))

    pop.open()


kv = Builder.load_file("banyaknyakerja.kv")

sm = ScreenManager()

screens = [CreateAccountWindow(name="create"),MainWindow(name="main")]
for screen in screens:
    sm.add_widget(screen)

sm.current = "create"


class MyMainApp(App):
    def build(self):
        return sm


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

KV file:

<WindowManager>:
    CreateWindow:
        id:create
        name: "create"

    MainWindow:
        id: main
        name: "main"

<CreateAccountWindow>:

    panjang: panjang
    lebar: lebar
    tinggi: tinggi

    FloatLayout:
        cols:1

        FloatLayout:
            size: root.width, root.height/2

            Label:
                text: "serfbgokmfor"
                size_hint: 0.8, 0.2
                pos_hint: {"x":0.1, "top":1}
                font_size: (root.width**2 + root.height**2) / 14**4

            Label:
                size_hint: 0.5,0.12
                pos_hint: {"x":0, "top":0.8}
                text: "Panjang: "
                font_size: (root.width**2 + root.height**2) / 14**4

            TextInput:
                pos_hint: {"x":0.5, "top":0.8}
                size_hint: 0.4, 0.12
                id: panjang
                multiline: False
                font_size: (root.width**2 + root.height**2) / 14**4

            Label:
                size_hint: 0.5,0.12
                pos_hint: {"x":0, "top":0.8-0.13}
                text: "Lebar: "
                font_size: (root.width**2 + root.height**2) / 14**4

            TextInput:
                pos_hint: {"x":0.5, "top":0.8-0.13}
                size_hint: 0.4, 0.12
                id: lebar
                multiline: False
                font_size: (root.width**2 + root.height**2) / 14**4

            Label:
                size_hint: 0.5,0.12
                pos_hint: {"x":0, "top":0.8-0.13*2}
                text: "Tinggi:"
                font_size: (root.width**2 + root.height**2) / 14**4

            TextInput:
                pos_hint: {"x":0.5, "top":0.8-0.13*2}
                size_hint: 0.4, 0.12
                id: tinggi
                multiline: False
                font_size: (root.width**2 + root.height**2) / 14**4

        Button:
            pos_hint:{"x":0.3,"y":0.25}
            size_hint: 0.4, 0.1
            font_size: (root.width**2 + root.height**2) / 17**4
            text: "Fefrkglt;mlfavsmdmcfr"
            on_release:
                root.manager.transition.direction = "left"
                root.login()

        Button:
            pos_hint:{"x":0.2,"y":0.05}
            size_hint: 0.6, 0.15
            text: "Kira"
            font_size: (root.width**2 + root.height**2) / 14**4
            on_release:
                root.manager.transition.direction = "left"
                root.submit()



<MainWindow>:
    panjang: panjang
    lebar: lebar
    tinggi: tinggi
    luas1: luas1
    luas2: luas2
    cat: cat

    FloatLayout:
        Label:
            id: panjang
            pos_hint:{"x": 0.1, "top":0.9}
            size_hint:0.8, 0.2
            text: "Panjang: "

        Label:
            id: lebar
            pos_hint:{"x": 0.1, "top":0.8}
            size_hint:0.8, 0.2
            text: "Lebar: "

        Label:
            id: tinggi
            pos_hint:{"x": 0.1, "top":0.7}
            size_hint:0.8, 0.2
            text: "Tinggi:"

        Label:
            id: luas1
            pos_hint:{"x": 0.1, "top":0.6}
            size_hint:0.8, 0.2
            text: "Luas:"

        Label:
            id: luas2
            pos_hint:{"x": 0.1, "top":0.5}
            size_hint:0.8, 0.2
            text: "Luas:"

        Label:
            id: cat
            pos_hint:{"x": 0.1, "top":0.4}
            size_hint:0.8, 0.2
            text: "Cat:"

        Button:
            pos_hint:{"x":0.2, "y": 0.1}
            size_hint:0.6,0.2
            text: "Semula"
            on_release:
                app.root.current = "create"
                root.manager.transition.direction = "down"

(It told me to show the minimum amount of code but damn I really don't know the problem here)

The outputs I expected wasn't complete and an error message was displayed:

File "C:\Users\dekmeymey\.kivy\banyaknyekerja.py", line 60, in on_enter
     self.volume()    # calculate volume
   File "C:\Users\dekmeymey\.kivy\banyaknyekerja.py", line 52, in volume
     luas1 = float(self.manager.ids.create.panjang.text) * float(self.manager.ids.create.tinggi.text) / 10
   File "kivy\properties.pyx", line 863, in kivy.properties.ObservableDict.__getattr__
 AttributeError: 'super' object has no attribute '__getattr__'

(THere are tons other error messages above this but I think this part is the most important one.)

I expected it to be somewhat like this:

Panjang: 23
Lebar: 11
Tinggi: 12
luas1: blabla
luas2: blabla
cat yang diperlukan: blabla

You get the point.

(I don't know how to insert the picture, so I do this instead.)

BUt I only get this:

Panjang:
Lebar:
Tinggi:
luas1:
luas2:
cat yang diperlukan:

How can I fix this?


Solution

  • I think there are several problems with your code. First, you are trying to access an id that you are not actually creating. In your kv the lines:

    <WindowManager>:
        CreateWindow:
            id:create
            name: "create"
    
        MainWindow:
            id: main
            name: "main"
    

    will create some ids within the WindowManager instance, but you are not using WindowManager, so those ids do not get created. Also, the above kv code will try to create an instance of a CreateWindow class, but there is no definition of such a class. I suspect you meant to use your CreateAccountWindow, so I would change the above kv code to:

    <WindowManager>:
        CreateAccountWindow:
            id:create
            name: "create"
    
        MainWindow:
            id: main
            name: "main"
    

    Next, you need to actually use that kv code. So change the code where you create the ScreenManager from:

    sm = ScreenManager()
    
    screens = [CreateAccountWindow(name="create"),MainWindow(name="main")]
    for screen in screens:
        sm.add_widget(screen)
    
    sm.current = "create"
    

    to:

    sm = WindowManager()
    sm.current = "main"
    

    (Note: I changed "create" to "main" in the above code, only because otherwise I couldn't figure out how to get to the main Screen.)

    Lastly, you are calling float(self.manager.ids.create.panjang.text) to convert the text to a float, but if the text of the panjang has not yet been entered, this will throw an Exception. So, you should either insure that the call to float does not occur unless that TextInput has a valid number as text, or give it a default number. Same applies to the other TextInputs.