Делаю сейчас программу, в которой второе окно должно мигать морзянкой сменяя черный фон белым. Я уже и через таймер попробовал в самом коде окна и в отдельный поток выкладывал.
Сейчас у меня такой вариант(тестовый) и он не работает. Появляется белое окно, потом проходит время равное сумме всех интервалов таймера и потом окно становится черным, хотя задумка теста - окно должно мигать несколько раз с интервалом, заданным в таймере
for(int j = 0; j < 3; j++)
{
this->setPalette(QPalette(Qt::white));
this->show();
m_timer->start(2000);
}
коннект для приема сигнала от таймера
QObject::connect(m_timer, SIGNAL(timeout()), this, SLOT(BlackWindow()));
и сам слот
void morzewindow::BlackWindow()
{
this->setPalette(QPalette(Qt::black));
this->show();
m_timer->stop();
}
Может у кого-то была подобная задача реализованная средствами Qt? помогите. Мне как новичку уже ни одной идеи в голову не приходит. Все что знал, о чем подозревал, все перепробовал.
UPDATE:
запуск потока и функции в нем:
MorzeBlinkTimer.moveToThread(&MorzeBlinkThread);
QObject::connect(&MorzeBlinkTimer, SIGNAL(latency(bool)), SLOT(Blink(bool)));
MorzeBlinkThread.start();
MorzeBlinkTimer.startBlink(etalon2.GetReadyCodeMorzeForBlink());
функцию запускаю вручную, потому что она принимает указатель на массив с морзянкой.
//слот для смены цвета окна морзянки черный/белый
void morzewindow::Blink(bool BlackWhite)
{
if(BlackWhite)
{
this->setPalette(QPalette(Qt::white));
this->show();
}
else
{
this->setPalette(QPalette(Qt::black));
this->show();
}
}
и сама функция потока, которая вводит задержку(фрагмент):
void startBlink(int* morze)
{
for(int i = 0; i < 50; i++)
{
switch(morze[i])
{
case 0:
emit latency(true);
QThread::msleep(iDot);
emit latency(false);
QThread::msleep(iPauseSymbol);
break;
}
}
}
Ответ
Все правильно, пока все функции не отработают и не "встанут" в ожидании событий в графическом интерфейсе - он не обновится.
Делать надо отдельным потоком, но там есть тонкости, тоже долго получалось как у вас - что не реагировало окно ни на что, пока не отработают все события.
Вот рабочий пример обновления графического интерфейса в отдельном потоке.
В основной функции у вас должно быть примерено так:
//Starting process in the new thread
Worker * pWorker = new Worker;
QThread * pThread = new QThread();
pWorker->moveToThread(pThread);
connect(pThread, SIGNAL(started()), pWorker, SLOT(slotDummyUpdatingRequest()));
// сигнал старта потока соединяем с функцией имеющей задержки
connect(pWorker, SIGNAL(sigDummyNextRequestStage()), this, SLOT(slotStageRequestPrint()));
// сигнал от объекта осуществляющего задержки на обновление окна соединяем со слотом обновления окна текущего оъекта
pThread->start();
И сам слот обновления графики, срабатывающий асинхронно:
void UpdatingRequestState::slotStageRequestPrint() {
//здесь идет установка внешнего вида элементов, в моем случае используется QML
QObject * pList = m_pQmlObject->findChild
Ну и собственно функция, выполняемая в отдельном потоке, по сигналам которой интерфейс обновляется
void Worker::slotDummyUpdatingRequest() {
//dummy imitation of the work
for (int i = 0; i < 5; i++) {
QThread::msleep(500); // задержка
emit sigDummyNextRequestStage();
qDebug() << "Updating Request...";
}
}
Комментариев нет:
Отправить комментарий