Как получить доступ к виджетам используя поток qt? - PullRequest
2 голосов
/ 05 сентября 2011

В моей программе у меня есть класс виджетов с текстовым полем и указателем qthread. Используя указатель qthread, я хочу постоянно обновлять текстовое поле путем выделения текста, не затрагивая приложение. Но я не могу получить доступ к текстовому полю. Даже если я получаю доступ к текстовому полю, передавая параметр в qthread. Я могу получить доступ к текстовому полю и выполнить обновление выделенного текста несколько раз, после чего мое приложение автоматически завершает работу и выдает ошибку

list_thread: ../../src/XlibInt.c:596: _XPrivSyncFunction: сбой утверждения `(dpy-> flags & (1L << 3))! = 0 '. </p>

1 Ответ

3 голосов
/ 05 сентября 2011

В Qt вы не можете (или не должны) вызывать любые функции графического интерфейса в другом потоке, отличном от основного потока. Что вы можете сделать, это отправить сигнал в рабочий поток и получить его в основном потоке.

Например, если вы после создания цепочки просто позвоните

connect(thread, SIGNAL(newText(QString)), lineEdit, SLOT(setText(QString)));

По умолчанию будет установлено соединение типа Qt::AutoConnection. Всякий раз, когда вы излучаете сигнал в том же потоке, где живет приемник, это эквивалентно простому вызову функции. Но когда вы посылаете этот сигнал в другой поток (например, в ваш новый поток), он ставится в очередь, а затем доставляется, когда основной поток снова запланирован, и продолжает свой цикл обработки событий, и поэтому функция слота всегда будет вызываться в потоке, где Ресивер живет. Но убедитесь, что вы объявляете сигнал с параметром значения (без указателя или ссылки), так что вы действительно получаете копию QString, а не указатель / ссылку на строку потока (которая, возможно, уже была перезаписана потоком ). * +1008 *

...
signals:
    void newText(QString);
...

Вы также можете настроить соединение так, чтобы поток ожидал (блокирует) после излучения, пока приемник не завершит обработку сигнала (вернувшегося из функции слота), используя Qt::BlockingQueuedConnection в качестве типа соединения. Но в вашем случае это не должно быть необходимым.

Дополнительную информацию смотрите в превосходной документации Qt .

...