Я столкнулся с интересной проблемой с WT, я решил ее, но я не понимаю, ПОЧЕМУ мое решение решило проблему. Я перерыл документацию по WT для виджетов и дошел до сих пор с пустыми руками, так что, возможно, кто-то, кто знает больше о WT, может помочь мне здесь.
В любом случае, проблема в том, что виджет WComboBox в потоке поддержки не обновляет свои данные при нажатии и изменяет свой выбор.
Я создал тему повышения в классе
class MyConsole: public WApplication
{
private:
boost::shared_ptr<boost::thread> _thread;
WComboBox* _combo_box;
bool running;
//Thread function
void my_thread(Wt::WApplication *app);
}
Затем я заполняю поле со списком данными, в качестве двух записей будем использовать «foo» и «goya». Я сделал функцию для потока и поместил в нее цикл.
void MyConsole::my_thread(Wt::WApplication *app)
{
while(running)
{
std::string test;
Wt::WApplication::UpdateLock lock(app);
if(lock)
{
test = _combo_box->valueText().narrow();
}
if (strcmp("foo", test.c_str()) == 0)
{
cout << "we got foo" << endl;
}
else if (strcmp("goya", test.c_str()) == 0)
{
cout << "we got goya" << endl;
}
}
}
Без изменения первоначального выбора поля со списком, приведенный выше код всегда вводит оператор foo if, что ожидается. Тем не менее, когда я изменяю выбор _combo_box на «goya», приведенный выше код все равно входит в оператор «foo» if, что очень неожиданно. Дальнейшее изучение вопроса, например, распечатка текущего индекса поля со списком перед оператором if показало мне, что оно всегда равно 0 и никогда не увеличивается при изменении выбора.
Я исправил это, подключив комбинированный сигнал change () к функции «ничего не делать», которую я добавил в класс.
class MyConsole: public WApplication
{
private:
...
void WWidgetForceUpdate(void)
{
}
...
}
...
_combo_box->changed().connect(this, &MyConsole::WWidgetForceUpdate);
С добавлением этого вызова функции при изменении выбора операторы «foo» и «goya» if работали должным образом и распечатывали текущий индекс поля со списком перед оператором if, подтверждая, что индекс теперь меняется.
Почему подключение сигнала change () к функции «ничего не делать» исправило ситуацию? Я уверен, что есть большая проблема, которую я не вижу здесь 🙁
Любая помощь приветствуется.
Wt отправляет изменения из браузера на сервер, когда происходят события. Если ваша программа не заинтересована в событии, эта синхронизация не будет выполняться (в противном случае синхронизация будет выполняться для каждого символа текста, введенного в поле ввода, для каждого движения Моисея, … даже если ваше приложение не выполняет ничего с этим). Ничто, связанное с change (), не означает, что ничто не заинтересовано в этом конкретном событии, и браузер не уведомит сервер, когда это произойдет.
Любое событие, которое прослушивается, отправляет все изменения всех виджетов на сервер, так что полное дерево виджетов синхронизируется. Поэтому, если у вас есть кнопка с прослушивателем clicked () и комбинированный список без прослушивателя change (), состояние комбинированного блока все равно будет обновляться в дереве виджетов при нажатии кнопки.
Однако в вашем коде есть ошибка: вы не можете просто получить доступ к дереву виджетов из случайного потока, не захватывая блокировку обновления (WApplication :: UpdateLock).
Других решений пока нет …