GTK3 не перерисовывается после настройки сетки

У меня есть простой пример, который я пытаюсь проработать с GTK3, где я хочу простую сетку, которая повторно регулирует размер:

#!/usr/bin/python3

from gi.repository import Gtk, Gdk

class Window(Gtk.Window):
    def __init__(self):
        Gtk.Window.__init__(self, title='Grid Test')

        self.scroll = Gtk.ScrolledWindow()
        self.scroll.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
        self.add(self.scroll)

        self.grid = Gtk.Grid()
        self.scroll.add(self.grid)

        self.create_items()

        # quit on ctrl-w
        accel = Gtk.AccelGroup()
        accel.connect(Gdk.keyval_from_name('W'), Gdk.ModifierType.CONTROL_MASK, 0, self.exit)
        self.add_accel_group(accel)

        style_provider = Gtk.CssProvider()
        style_provider.load_from_data(bytes('''
        .button {
            background: none;
            border: none;
        }
        '''.encode()))
        Gtk.StyleContext.add_provider_for_screen(
            Gdk.Screen.get_default(),
            style_provider,
            Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION
        )

        self.width = self.scroll.get_allocated_width()
        self.scroll.connect("size-allocate", self.on_resize, self.scroll, self.grid)

    def create_items(self):
        # remove existing
        for wid in self.grid.get_children():
            self.grid.remove(wid)

        col, row = 0, 0
        cols = self.scroll.get_allocated_width() / (40 + self.grid.get_column_spacing())
        for i in range(10):
            button = Gtk.Button(label='foo{}'.format(i))
            button.connect('clicked', self.on_click)
            self.grid.attach(button, col, row, 1, 1)

            if col >= cols:
                col = 0
                row += 1
            else:
                col += 1

    def on_click(self, widget):
        print('clicked')

    def exit(self, *args):
        Gtk.main_quit()

    def on_resize(self, a, b, c, grid):
        new_width = self.scroll.get_allocated_width()
        if new_width != self.width:
            self.create_items()
            self.width = new_width

if __name__ == '__main__':
    win = Window()
    win.connect('delete-event', Gtk.main_quit)
    win.show_all()
    Gtk.main()

Это всегда приводит к пустому окну. Если я удаляю size-allocateобработчик, то элементы отображаются, но, конечно, не настраиваются при изменении размера окна.

Я пытался заставить перерисовывать self.queue_draw()окно и вид прокрутки, но это, похоже, не помогло.

1 ответ

  1. Кнопки по-прежнему скрыты после create_items()выполнения; вы должны добавить visible=Trueв Gtk.Buttonконструктор там, или повторно запустить win.show_all()в конце create_items().