Использование виджета pyqt из линейно работающего консольного приложения - PullRequest
0 голосов
/ 04 июля 2011

Мой сценарий здесь следующий: я использую виджет pyqt для отображения сплошного полноэкранного режима на втором дисплее и наблюдаю за этим отображением с помощью камеры, которая непрерывно захватывает изображения. Я делаю некоторую обработку с изображениями, и это те данные, которые меня интересуют. Это прекрасно работает, когда используется интерактивно с ipython и matplotlib с использованием бэкэнда qt4agg, например,

% ipython -pylab
# ... import PatternDisplay, starting camera
pd = PatternDisplay(); pd.show(); pd.showColor(r=255,g=255,b=255)
imshow(cam.current_image)

Теперь мне нужно подобное поведение в консольном скрипте: он должен отображать виджет PatternDisplay, захватывать изображение, затем менять цвет в PatternDisplay, делать новое изображение и т. Д.

Проблема теперь в том, что PatternDisplay никогда не обновляется / перерисовывается в моем скрипте, вероятно потому, что PyQt никогда не получает шанс запустить свою очередь событий. Мне не повезло, пытаясь переместить линейную рабочую часть моего скрипта в QThread, потому что я больше не могу общаться с виджетом PatternDisplay из другого потока. Я пытался повторить реализацию ipython / matplotlib, но я не до конца понял, это довольно сложно - он избегает запуска основного цикла QApplication посредством исправлений обезьян и каким-то образом перемещает QT в свой собственный поток. Затем он периодически проверяет с помощью QTimer, была ли введена новая команда пользователем.

Разве нет простого способа достичь того, что я хочу сделать? Я с радостью предоставлю больше информации, если это необходимо. Спасибо за любую помощь!

Ответы [ 2 ]

2 голосов
/ 07 июля 2011

То, что вам нужно, проще, чем работа IPython - IPython делает приложение Qt и командную строку интерактивными одновременно.

I думаю, способ сделать это в Qt - это использовать таймер, который срабатывает через равные промежутки времени, и подключить сигнал к «слоту», представляющему вашу функцию, которая получает новое изображение и помещает его в виджет. Таким образом, вы извлекаете его из цикла событий, а не пытаетесь его подтолкнуть.

Я не очень много использовал Qt, поэтому не могу дать конкретику, но чем больше я об этом думаю, тем больше думаю, что это правильный способ сделать это.

1 голос
/ 13 июля 2011

Я решил ту же проблему (то есть интерактивную консоль ipython в терминале и поток GUI, работающий независимо) следующим образом с ipython 0.10 (код здесь ) 1. Создайте объект QApplication, но не вводитеявный цикл обработки событий 2. Запустите встроенный экземпляр IPython 3. Запустите необходимый код пользовательского интерфейса, создав для него окно и вызвав для него show() (например, здесь с yade.qt.Controller(), который я связал с F12. (Я не нашел способа попросить встроенную оболочку запустить команду в начале сеанса, как если бы пользователь ее набрал)

(Вы также можете show() ваше окносначала запустите встроенный ipython. Он предоставит цикл обработки событий для Qt.

(Кстати, я также пытался запустить Qt4 из фонового потока (используя модуль потоков python и Qt4.QThreads), но отказываетсябежать таким образом упрямо. не беспокоить идти так.)

1014 * недостаток заключается в том, что пользовательский интерфейс будет заблокирован, а IPython занят. Я надеюсь найти что-то лучше0.11, который должен иметь гораздо лучшие возможности для потоков (я спросил у пользователей ipython о том, как разблокировать пользовательский интерфейс).

HTH, v.

...