Russian Qt Forum

Qt => Общие вопросы => Тема начата: Alp от Сентябрь 04, 2009, 15:37



Название: template + Q_OBJECT
Отправлено: Alp от Сентябрь 04, 2009, 15:37
Преамбула: я знаю, что в документации написано, что moc не умеет шаблоны... Наследование шаблона от Q_OBJECT-реализующего класса так же не работает

Есть задачка: приложение, в главном окне QTabWidget, на одном табе - таблица со списком студентов (5 полей), на другом  - таблица преподавателей (допустим, 7 полей). И там и там есть кнопки "Добавить" и "Удалить", изменение записей реализовано в слоте для itemChanged.

В целом виджеты (QStudentsWidget и QTeacherWidget) идентичны, разница только в том, что в одном хранится vector<Student>, в другом - vector<Teacher>, ну и пара методов реализующих взятие данных из таблицы и запись данных в неё.

Типы данных Student и Teacher по некоторым причинам не могут иметь общего предка. MVC использовать нельзя, типы данных должны быть чисто-STLными (орудовать внутри с MVC, а наружу выставлять STL-возвращающие геттеры тоже нельзя)

Вопрос: как без копипасты кода и MVC попроще реализовать такую вещь?


Название: Re: template + Q_OBJECT
Отправлено: BRE от Сентябрь 04, 2009, 15:51
Наследованием.


Название: Re: template + Q_OBJECT
Отправлено: Alp от Сентябрь 04, 2009, 16:35
Ага, а обновлять заголовки колонок таблицы вызовом виртуальной функции в конструкторе =)


Название: Re: template + Q_OBJECT
Отправлено: BRE от Сентябрь 04, 2009, 16:37
Ага, а обновлять заголовки колонок таблицы вызовом виртуальной функции в конструкторе =)
Не рекомендовал бы, но ... попробуй.  ;)
Думаю все эти проблемы, если подумать, решаются.


Название: Re: template + Q_OBJECT
Отправлено: Alp от Сентябрь 04, 2009, 19:22
Собственно, я потому и написал здесь, что думаю как эту задачу решить красиво уже третий день.


Название: Re: template + Q_OBJECT
Отправлено: BRE от Сентябрь 04, 2009, 19:40
Собственно, я потому и написал здесь, что думаю как эту задачу решить красиво уже третий день.
А что уже получилось, может наброски какие есть, покажи, посмотрим-покурим.  :)


Название: Re: template + Q_OBJECT
Отправлено: Igors от Сентябрь 04, 2009, 19:51
По моему, template и наследование с virtual'ами здесь мало подходят. Пусть таблица/форма - один класс но имеет member типа "MyDataModel" - а его уже делать с virtual'ами.


Название: Re: template + Q_OBJECT
Отправлено: BRE от Сентябрь 04, 2009, 20:47
По моему, template и наследование с virtual'ами здесь мало подходят. Пусть таблица/форма - один класс но имеет member типа "MyDataModel" - а его уже делать с virtual'ами.
Наследование - это механизм, он не может подходить в одном месте и не подходить в другом.  ;)


Название: Re: template + Q_OBJECT
Отправлено: Alp от Сентябрь 04, 2009, 22:44
Собственно, я потому и написал здесь, что думаю как эту задачу решить красиво уже третий день.
А что уже получилось, может наброски какие есть, покажи, посмотрим-покурим.  :)
Ок, завтра на работе посмотрю старые черновики, выложу.


Название: Re: template + Q_OBJECT
Отправлено: Djavdet от Октябрь 28, 2009, 17:59
а где ж продолжение7


Название: Re: template + Q_OBJECT
Отправлено: SASA от Ноябрь 03, 2009, 19:45
Если разного кода не много, и различия только в названиях типа, то можно попробывать использовать макросы.


Название: Re: template + Q_OBJECT
Отправлено: _govorilka от Ноябрь 14, 2009, 17:08
Назовите хоть одну реальную причину почему Teacher и Pupil не могут быть унаследованы от одного класса People... Нежелание или невозможность переписать уже имеющийся код - это конечно тоже причина (хотя и весьма сомнительная), но в этом случае я бы отказался от Q_Object и сделал шаблон. Проблема явно надуманная...


Название: Re: template + Q_OBJECT
Отправлено: Varan от Декабрь 20, 2011, 14:34
Если наследование не работает, то работает инкапсуляция.
Делаю такую прослойку:

Код
C++ (Qt)
class changes_emitter : public QObject
{
Q_OBJECT
public:
void send(unit const&)
{
emit unit_changed(u);
}
signals:
void unit_changed(unit const&);
};
 
И потом использую её в шаблоне вот так:
Код
C++ (Qt)
template<typename Unit>
class editor_impl : public editor
{
public:
// <...>
void send_changes(unit const& u)
{
changes_emitter_.send(u);
}
// <...>
private:
changes_emitter changes_emitter_;
};