简体   繁体   中英

Checking for an id as child of an instance class gives error

So I have to get the id of the image existing inside the instance (button) so I have stored all the ids of the imgs in an array. There are 64 buttons and only 16 contain images so there is a total of 16 images in which all are different. Below is my half of my.kv code and my.py code.

<Game>:
name: "ChessBoard"

GridLayout:
    id: chess_board
    cols: 8
    rows: 8
    padding: ("60dp", "60dp", "60dp", "60dp")
    orientation: 'tb-lr'
    
    Button:
        id: button_1
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_1
            source: 'imgs/WhiteCastle.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_2
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_2
            source: 'imgs/WhiteKnight.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_3
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_3
            source: 'imgs/WhiteBishop.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_4
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
        AsyncImage:
            id: white_4
            source: 'imgs/WhiteQueen.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
        

    Button:
        id: button_5
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_5
            source: 'imgs/WhiteKing.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
        
    Button:
        id: button_6
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_6
            source: 'imgs/WhiteBishop.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
        
    Button:
        id: button_7
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_7
            source: 'imgs/WhiteKnight.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_8
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_8
            source: 'imgs/WhiteCastle.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y  #8
        
    Button:
        id: button_9
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_9
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_10
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_10
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_11
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_11
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
    
    Button:
        id: button_12
        background_normal: ''
        background_color: (1,1,1,1)
        on_press:root.moves(self, root)

        AsyncImage:
            id: white_12
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_13
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
        AsyncImage:
            id: white_13
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
    
    Button:
        id: button_14
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_14
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y

    Button:
        id: button_15
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_15
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y
    
    Button:
        id: button_16
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

        AsyncImage:
            id: white_16
            source: 'imgs/WhitePawn.png'
            center_x: self.parent.center_x
            center_y: self.parent.center_y  #16
   
    Button:
        id: button_17
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

    Button:
        id: button_18
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_19
        background_normal: ''
        background_color: (1,1,1,1)
        on_press:root.moves(self, root)

    Button:
        id: button_20
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_21
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

    Button:
        id: button_22
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_23
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)
    Button:
        id: button_24
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_25
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_26
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)
    Button:
        id: button_27
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    Button:
        id: button_28
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)
    Button:
        id: button_29
        background_color: (0, 0, 0, 1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_30
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)
    
    Button:
        id: button_31
        background_color: (0, 0, 0, 1) 
        on_press: root.moves(self, root)

    Button:
        id: button_32
        background_normal: ''
        background_color: (1,1,1,1)
        on_press: root.moves(self, root)

Now.py:

class Game(Screen):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)

def img_list(self):
    img_ids_list = []

    for x in range(1, 17):
        img_ids_list.append(f"white_{x}")

    for y in range(1, 17):
        img_ids_list.append(f"black_{y}")

    return img_ids_list

def moves(self, instance, root):
    all_ids = root.ids
    id_of_button = self.get_id(instance)
    img_id = self.check_if_img_exists(instance, root)

def check_if_img_exists(self, instance, root):
    img_ids = self.img_list()

    if img_ids[0] in root.ids:
        print("Ready for launch!")
        for x in range(1, 32):
            asyncImage = root.ids.img_ids[x]
            if asyncImage in instance.children:
                print("Button contains an AsyncImage")
                return asyncImage

    print("Button does not contain an AsyncImage")

def get_id(self, instance):
    for id, widget in instance.parent.parent.ids.items():
        if widget.__self__ == instance:
            return id

The error I get is

Traceback (most recent call last):
File "kivy\properties.pyx", line 961, in kivy.properties.ObservableDict.__getattr__
KeyError: 'img_ids'

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
File "C:\Users\Zaviyar Zahid\kivy-thelab\venv\main.py", line 98, in <module>
 ChessApp().run()
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\app.py", 
line 955, in run    
 runTouchApp()
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\base.py", line 574, in runTouchApp
 EventLoop.mainloop()
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\base.py", line 339, in mainloop
 self.idle()
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\base.py", line 383, in idle  
 self.dispatch_input()
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\base.py", line 334, in dispatch_input
 post_dispatch_input(*pop(0))
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\base.py", line 263, in post_dispatch_input
 listener.dispatch('on_motion', etype, me)
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\core\window\__init__.py", line 1660, in on_motion
 self.dispatch('on_touch_down', me)
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\core\window\__init__.py", line 1677, in on_touch_down
  if w.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\uix\screenmanager.py", line 1210, in on_touch_down
  return super(ScreenManager, self).on_touch_down(touch)
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\uix\widget.py", line 589, in on_touch_down
 if child.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\uix\relativelayout.py", line 306, in on_touch_down
 ret = super(RelativeLayout, self).on_touch_down(touch)
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\uix\widget.py", line 589, in on_touch_down
  if child.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\uix\widget.py", line 589, in on_touch_down
 if child.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 731, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
 packages\kivy\uix\behaviors\button.py", line 151, in on_touch_down
 self.dispatch('on_press')
 File "kivy\_event.pyx", line 727, in kivy._event.EventDispatcher.dispatch
File "kivy\_event.pyx", line 1307, in kivy._event.EventObservers.dispatch
File "kivy\_event.pyx", line 1191, in kivy._event.EventObservers._dispatch
File "C:\Users\Zaviyar Zahid\AppData\Roaming\Python\Python310\site- 
packages\kivy\lang\builder.py", line 55, in custom_callback
  exec(__kvlang__.co_value, idmap)
File "C:\Users\Zaviyar Zahid\kivy-thelab\venv\chess.kv", line 122, in <module>
 on_press: root.moves(self, root)
File "C:\Users\Zaviyar Zahid\kivy-thelab\venv\main.py", line 49, in moves
 img_id = self.check_if_img_exists(instance, root)
File "C:\Users\Zaviyar Zahid\kivy-thelab\venv\main.py", line 57, in check_if_img_exists
 asyncImage = root.ids.img_ids[x]
File "kivy\properties.pyx", line 964, in kivy.properties.ObservableDict.__getattr__
AttributeError: 'super' object has no attribute '__getattr__'

If you look at the error message, it is complaining about the line:

asyncImage = root.ids.img_ids[x]

Since root is your Game instance, that code is trying to access an id named img_ids in the Game instance. But you have not defined an img_ids in your kv . I suspect that you actually intended to use the img_ids variable that you created in the check_if_img_exists() method. Try changing the above line to:

asyncImage = img_ids[x]

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM