kivy неправильно добавляет / размещает виджеты при добавлении в цикл for - PullRequest
0 голосов
/ 13 апреля 2019

Я хочу разместить 6 блоков (виджетов) на экране.Сначала я обновляю атрибуты pos блоков, а затем пытаюсь добавить их один за другим на экран.Проблема в том, что последний блок вообще не размещается, а все остальные находятся в соседних позициях, а не в том, что им дали.

Я пробовал несколько вариантов, таких как установка позиций при инициализации с помощью kwarg, не сработало.Кажется, я чего-то не понимаю, поэтому прошу помощи.Может кто-нибудь сказать мне, почему это не работает?

class Block(Widget):

    def __init__(self, red, green, blue, **kwargs):
        super(Block, self).__init__(**kwargs)
        self.canvas.add(Color(red, green, blue, 1))


class GameEnvironment(Widget):

    def __init__(self, **kwargs):
        super(GameEnvironment, self).__init__(**kwargs)
        self.blocks = self.create_blocks()
        self.position_blocks()
        self.add_blocks()

    def create_blocks(self):
        red_block = Block(1, 0, 0)
        blue_block = Block(0, 0, 1)
        green_block = Block(0, 1, 0)
        black_block = Block(0, 0, 0)
        orange_block = Block(1, .55, 0)
        celeste_block = Block(.5, 1, .83)
        return [red_block, blue_block, green_block, black_block, orange_block, celeste_block]

    def position_blocks(self):
        x = 0
        for block in self.blocks:
            block.pos = [x, 0]
            print("position:", block.pos)
            x += 100


    def add_blocks(self):
        for block in self.blocks:
            print("drawing block")
            self.add_widget(block)

class BlocksGameApp(App):
    def build(self):
        game_environment = GameEnvironment()
        return game_environment


BlocksGameApp().run()

.kv:

<GameEnvironment>:
    canvas:
        Color:
            rgba: 1, 1, 1, 1
        Rectangle:
            pos: self.pos
            size: self.size

<Block>:
    width: 100
    height: self.width
    canvas:
        Rectangle:
            pos: self.pos
            size: self.size

Ожидаемое: 6 прямоугольников рядом друг с другом с красным цветом в левом нижнем углу.

Результат: 5 прямоугольников с первым напозиция 100, 0.

Ответы [ 2 ]

0 голосов
/ 13 апреля 2019

Вопрос 1

Таким образом, цвет добавляется после группы, но почему тогда все прямоугольники не являются белыми?

Примечания

word, group означает графические инструкции, такие как Цвет, Прямоугольники, Треугольники, Линии, Эллипс и т. д.

Ответ 1

Со ссылкой на это приложение процесс конструктора разбивается на два этапа.

Шаг 1: Создание экземпляра - Блок (...)

Когда создается каждый блок,у него есть шаблон с графической инструкцией Rectangle, который составляет группу.

Модальное представление
Block:
    width: 100
    height: self.width
    canvas:
        Rectangle:
            pos: self.pos
            size: self.size

Шаг 2: Добавить цвет (...)

После создания блока следующая графическая инструкция, добавленная в группу, - Color.Когда ключевое слово after или before опускается из canvas, применяется значение по умолчанию after.

Модальное представление
Block:
    width: 100
    height: self.width
    canvas:
        Rectangle:
            pos: self.pos
            size: self.size
        Color:
            rgba: 1, 0, 0, 1    # red colour

Сводка

Следовательно, все блокине белого цвета, потому что Color инструкция была добавлена ​​после группы, Rectangle.Первый блок имеет белый цвет, поскольку последняя выполненная инструкция Color поступила из корневого виджета GameEnvironment.Второй блок имеет красный цвет, потому что предыдущая инструкция Color была красной.Третий блок имеет синий цвет, потому что предыдущая выполненная инструкция Color была синей и т. Д.

Следующий пример иллюстрирует эквивалент вашей программы, за исключением того, что цвет фона черный, каждый блок добавляется вручную, иразмер виджета по умолчанию - 100 на 100 (size: 100, 100 или size_hint: 1, 1).

canvas.py

from kivy.base import runTouchApp
from kivy.lang import Builder

runTouchApp(Builder.load_string("""
Widget:
    canvas:
        Color:
            rgba: 0, 0, 0, 1    # black background colour 
        Rectangle:
            pos: self.pos
            size: self.size       

    Widget:
        pos: 0, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 1, 0, 0, 1    # red colour

    Widget:
        pos: 100, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 0, 0, 1, 1    # blue colour

    Widget:
        pos: 200, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 0, 1, 0, 1    # green colour

    Widget:
        pos: 300, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 0, 0, 0, 1    # black colour

    Widget:
        pos: 400, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 1, 0.55, 0, 1    # orange colour

    Widget:
        pos: 500, 0
        canvas:
            Rectangle:
                pos: self.pos
                size: self.size
            Color:
                rgba: 0.5, 1, 0.83, 1    # celeste colour

"""))

Ответ 1 Демо

canvas without before

Вопрос 2

Разве цвет не добавляется к каждому объекту блока?

Ответ 2

Графическая инструкция Color добавляется к каждому объекту блока, но цвет не применяется немедленно, поскольку ключевое слово before было опущено в canvas, применяется стандартное значение after.

Следовательно, цвет применяется к следующему экземпляру виджета, если и только если у этого виджета нет графической инструкции, Color указано.

Проблема

последний блок вообще не помещается, а все остальные находятся в соседних позициях вместо того, что им дано

Причина корня

Запуск приложения, действительно добавлено6 блоков.Но первый блок имеет белый цвет, потому что последняя выполненная инструкция Color поступила из корневого виджета GameEnvironment.Второй блок красный.Третий блок синий и так далее.Color добавляется after группа.

Решение

Добавьте ключевое слово before к self.canvas.add(Color(...))

Фрагменты

class Block(Widget):

    def __init__(self, red, green, blue, **kwargs):
        super(Block, self).__init__(**kwargs)
        self.canvas.before.add(Color(red, green, blue, 1))

Kivy Canvas »before

before

Свойство для получения группы« до ».

Output

Result

0 голосов
/ 13 апреля 2019

Добавление Color к Canvas добавляет его после Rectangle, поэтому оно не влияет на текущий Rectangle. Вместо этого добавьте Color к Block в kv как:

<Block>:
    width: 100
    height: self.width
    canvas:
        Color:
            rgba: self.r, self.g, self.b, 1
        Rectangle:
            pos: self.pos
            size: self.size

Затем добавьте свойства r, g и b к классу Block:

class Block(Widget):
    r = NumericProperty(1)
    g = NumericProperty(1)
    b = NumericProperty(1)

    def __init__(self, red, green, blue, **kwargs):
        super(Block, self).__init__(**kwargs)
        self.r = red
        self.g = green
        self.b = blue

Я думаю, что это исправит.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...