Я работаю над графическим интерфейсом на основе Wt и борюсь с чем-то, что кажется очень простым:
Графический интерфейс отображает «события».В нашем проекте у нас есть модель (ActiveEventsModel
, основанная на WStandardItemModel
) и представление (ActiveEventsView
, основанное на WTableView
).В настоящее время представление просто показывает некоторый текст, соответствующий различным свойствам 'events'.Цель состоит в том, чтобы добавить в таблицу дополнительный столбец, содержащий кнопку (например, WPushButton
), которая позволяет пользователю «подтверждать» событие, отображаемое в этой строке (в контексте это, по сути, означает отклонение событие - т.е. каждое событие имеет кнопку, и нажатие кнопки удалит это событие из модели).
Я искал в Интернете и нашел это обсуждение на Wt-форуме, которое содержит некоторые рекомендации по вводу кнопки (производной от WAbstractItemDelegate
и использованию setItemDelegateForColumn
) и пример кодадля создания кнопки в делегате элемента.После некоторых незначительных изменений совместимости с Wt-4.0 у меня теперь есть кнопка в таблице.
Я определил очень простой класс EventDelegate
, полученный из WAbstractItemDelegate
:
header:
#include <Ui/WebToolkit.h> //convenience header containing all of the Wt elements we use
class EventDelegate : public Wt::WAbstractItemDelegate
{
public:
EventDelegate();
std::unique_ptr<Wt::WWidget> update(Wt::WWidget *widget, const Wt::WModelIndex &index,
Wt::WFlags<Wt::ViewItemRenderFlag> flags) override;
void acknowledge(Wt::WModelIndex &index);
};
source:
#include <Ui/EventDelegate.h>
EventDelegate::EventDelegate()
: WAbstractItemDelegate()
{
}
std::unique_ptr<Wt::WWidget> EventDelegate::update(Wt::WWidget *widget, const Wt::WModelIndex &index,
Wt::WFlags<Wt::ViewItemRenderFlag> flags)
{
std::unique_ptr<Wt::WWidget> w = std::make_unique<Wt::WPushButton>("acknowledge");
Wt::WPushButton *button = dynamic_cast<Wt::WPushButton*>(w.get());
button->clicked().connect(std::bind(&EventDelegate::acknowledge,this,index));
return w;
}
void EventDelegate::acknowledge(Wt::WModelIndex &index) {
//how do I interact with the model?
}
Поначалу это казалось многообещающим, но я просто не могу понять, как на самом деле заставить кнопку делать что-либо для модели.Я подумал, что, возможно, мне нужно переопределить WAbstractItemDelegate :: setModelData , но для этого мне нужна модель, о которой ItemDelegate, похоже, ничего не знает.
У меня есть есть ModelIndex, и ModelIndex знает, к какой модели он принадлежит, но выдаст мне его только как const
, который мне не нужен, потому что setModelData
нуженизменить это.
Должен ли я просто передать модель непосредственно делегату, например, в качестве параметра конструктора?Это кажется легким решением, но кажется очень не изящным.Или я просто лаю не на то дерево, когда пытаюсь это сделать?Я чрезвычайно новичок в Wt (и мои коллеги только немного меньше - это относительно новый проект и первый в нашей компании, который использовал Wt), так что это очень возможно.
(я не включил весь mcve, потому что я почти уверен, что мне здесь не хватает концептуально . Я могу добавить его позже, если люди считают, что действительно необходимо ответитьвопрос)