python-vlc не будет вставлять виджет gtk в окно, но вместо этого откроет новое окно
Я работаю над gtk3
передний конец для libvlc
написано на Python с использованием python-vlc
, Я следую за gtk3
Пример со страницы Python-VLC GitHub, но я испытываю странное поведение. У меня есть виджет, который выглядит так:
import gi
import sys
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk
class PlayerWidget(Gtk.DrawingArea):
__gtype_name__ = 'VLCWidget'
def __init__(self, instance):
Gtk.DrawingArea.__init__(self)
self.player = instance.media_player_new()
def handle_embed(*args):
if sys.platform == 'win32':
self.player.set_hwnd(self.get_window().get_handle())
else:
self.player.set_xwindow(self.get_window().get_xid())
return True
self.connect("realize", handle_embed)
self.set_size_request(320, 200)
Я вставил это здесь:
import vlc
import sys
from widgets.player import PlayerWidget
import gi
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk
class VideoPlayer(Gtk.Window):
CONST_APP_NAME = "video player"
def __init__(self):
Gtk.Window.__init__(self)
if 'linux' in sys.platform:
self.instance = vlc.Instance("--no-xlib")
else:
self.instance = vlc.Instance()
self.set_default_size(800, 600)
header = Gtk.HeaderBar(title=self.CONST_APP_NAME)
header.set_subtitle("Filename.mp4")
header.set_show_close_button(True) # this one is the troublemaker
self.set_titlebar(header)
self.connect("destroy", Gtk.main_quit)
self.player_widget = PlayerWidget(self.instance)
self.add(self.player_widget)
def show_window(self):
self.show_all()
Gtk.main()
def set_media(self, fname):
self.player_widget.player.set_media(self.instance.media_new(fname))
def play(self):
self.player_widget.play()
if not len(sys.argv) > 0:
print('Please provide a filename')
sys.exit(1)
p = VideoPlayer()
p.set_media(sys.argv[1])
p.play()
p.show_window()
p.instance.release()
Это работает нормально, если я вставлю его в пустое окно Gtk.window. Однако, если я добавлю HeaderBar
в это окно, а затем добавить кнопку закрытия к этому HeaderBar
с помощью set_show_close_button(True)
он перестает работать, как ожидалось. PlayerWidget
больше не будет отображаться встроенным, но вместо этого будет открыто новое (второе) окно, в котором воспроизводится видео. Если я не добавлю кнопку закрытия в HeaderBar
виджет встраивается просто отлично.
Предупреждение выдается на консоль: xcb_window window error: X server failure
Сначала я подумал, что это может быть потому, что я использую гном под Wayland, но это происходит на X
а также на wayland
,
Любая помощь приветствуется.
Обновление 1: добавлен пример полного кода. Когда я запускал его сегодня, в первый раз он действительно работал как ожидалось, но после этого снова возникла та же ошибка, что и описанная выше. Очень странно.
1 ответ
Как правильно отметили @mtz и @stovfl, проблема заключалась в том, что я начал воспроизведение видео (p.play()
) перед созданием окна (p.show_window()
).
Как предположил, я использовал GLib.idle_add(p.play)
чтобы позволить окну начать воспроизведение, как только оно будет готово. Модуль GLib можно импортировать с помощью from gi.repository import GLib
,