LINUX.ORG.RU

Qt, QListWidget, перерисовка после добавления нового Item.


0

1
class Zzz : public QWidget
{
   Q_OBJECT
   public:
      Zzz()
      {
         qlw = new QListWidget(this); // this = parent
         connect(this, SIGNAL(signalLog), this, SLOT(slotLog()));
      }
      void log(const char *_str)
      {
         m_log_string = _str;
         signalLog();
      }
      QListWidget *qlw;
      std::string m_log_string;
   signals:
      void signalLog();
   public clots:
      void slotLog()
      {
         qlw->addItem(m_log_string.c_str());
      }
};

Писал по памяти, возможны ошибки. Кто шарит в Qt, тот суть понял: дёргаем log(), добавляется строка на экранный список.

Если дёргать log() очень быстро, то на экране строки появляются сразу пачками и только тогда, когда мы прекращаем его часто дёргать. То есть, если какой-то процесс вывалил гору строк с интервалом в 50 мс, то все эти строки появятся только целой горой.

Меня это чё-то мало устраивает. Хочу синхронности. То есть, чтобы слот завершал работу только тогда, когда экранное состояние списка будет перерисовано под новое содержимое.

Ниже приведены штукиъ, которые в разных комбинациях втыкались в slotLog(), но максимальный полученный эффект - это синхронное уменьшение размера ползунка скролл-бара, а строки по-прежнему появляются целой кучей за раз. Ну чё, вопрос традиционный - спасите-помогите (-;

Добавляемые в слот, но не помогающие ШтукиЪ:

qlw->viewport()->update();
qlw->viewport()->repaint();
qlw->update();
qlw->repaint();
QApplication::processEvents();

★☆

Последнее исправление: kiverattes (всего исправлений: 1)

Что мешает добавлять в listwidget строку сразу в log()? Сигналы-слоты небесплатны с точки зрения процессорного времени.

QListWidget имеет встроенную модель, в отличие от полноценных MVC-классов. Возможно, стоит использовать QListView.

Отрисовка происходит только тогда, когда модель пошлёт отображению сингал о том, что закончила добавлять. Несколько одинаковых сигналов подряд складываются в один, если не успевают выполняться.

И ещё, попробуй всё-таки пользоваться встроенным QString. Конверсии c-str/std::string/QString тоже немало времени отнимают.

schizoid ★★★
()

> Меня это чё-то мало устраивает. Хочу синхронности. То есть, чтобы слот завершал работу только тогда, когда экранное состояние списка будет перерисовано под новое содержимое.

модели для этого предназначены. негоже для хранения данных использовать виджеты - люди подумают что тебя делфи покусал

VladimirMalyk ★★★★★
()
Ответ на: комментарий от schizoid

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

kiverattes ★☆
() автор топика

Попробуй вызывать QApplication::processEvents() не в отдельном слоте, а сразу после emit signalLog();

m0rph ★★★★★
()
Ответ на: комментарий от kiverattes

долго трахаться сразу, как только к логу захочется прикрутить фильтр, отдать в два места сразу, добиться синхронности

VladimirMalyk ★★★★★
()
Ответ на: комментарий от VladimirMalyk

Такие сложные логи мы фигачим через log4cxx (-;

kiverattes ★☆
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.