![]() |
Здравствуйте, гость ( Вход | Регистрация )
![]() ![]() |
![]() |
vo.borodin |
![]()
Сообщение
#1
|
Новичок Группа: Новичок Сообщений: 4 Регистрация: 26.3.2014 Пользователь №: 4088 Спасибо сказали: 0 раз(а) Репутация: ![]() ![]() ![]() |
В последнее время отошел от C++, но сейчас хочу возвратить навыки по нему. Реализация архитектуры Модель-Представление в Qt - тема интересная и сложная, хочу в ней разобраться. Есть много непонятных моментов и фундаментальных вопросов. Обо всём по порядку:
1) Класс QAbstractItemModel, как я понимаю, представляет собой самый общий интерфейс для модели, представляющей собой обертку над древовидной структурой данных. Есть корневой элемент данных, у корневого элемента есть потомки. Каждый из потомков является (или может являться) верхним левым элементом в некоей таблице элементов. Каждый из элементов в этой таблице сам может иметь потомков, и т. д. Так вот, я правильно понимаю, что модельный индекс QModelIndex - это некий объект, который ставится в соответствие каждому элементу данных в этой структуре и по которому можно этот элемент найти? 2) Лейтмотивом создания архитектуры MVC являлось отделение данных от способа их представления. Допустим, моё представление должно на основе данных в моей модели что-то нарисовать. Представление, я так понимаю, доступается до данных в модели через модельные индексы QModelIndex. Так вот, должно ли представление знать о способе организации данных в модели? Или смысл следующий: для одной модели мы можем создать несколько представлений, каждое из которых знает структуру данных в модели и отображает данные по-своему? 3) В чем суть делегатов? Должны ли они участвовать в отображении данных или только в обработке действий пользователя? 4) Допустим, в моей модели есть древовидная структура данных, в которой узлы дерева разных уровней представляются разными пользовательскими классами. Т. е. примерно так:
Возвращать QModelIndex должен метод index() в классе A. Но как в этом методе организовать генерацию индексов для объектов классов B, C, D, E и содержащихся в них данных? |
|
|
Анна |
![]()
Сообщение
#2
|
![]() Активный участник ![]() ![]() ![]() Группа: Участник Сообщений: 276 Регистрация: 22.5.2008 Из: Зеленоград Пользователь №: 181 Спасибо сказали: 30 раз(а) Репутация: ![]() ![]() ![]() |
1. Да, QModelIndex ставится в соответствие каждому элементу. Он кроме i и j ещё имеет третью координату parent. Этого достаточно, чтобы добраться до любого элемента.
2. Так вот, должно ли представление знать о способе организации данных в модели? Ну, если учесть, что есть несколько потомков от QAbstractItemView, легко предположить, что представление считает, что оно имеет представление о модели. Если вы предложите QTableView отобразить дерево, думаю ничего хорошего не получится, отобразится максимум один столбец, потому что QTableView не предназначено для отображения дерева 3) "В чем суть делегатов? Должны ли они участвовать в отображении данных или только в обработке действий пользователя?" Посмотрите на методы класса: он может отрисовывать данные элемента, и предоставляет виджет-редактор для редактирования данных элемента. 4. определите во всех классах метод index() + рекурсия, и будет вам счастье. Вот примеры древовидной модели: http://qt-project.org/doc/qt-5.0/qtwidgets...etreemodel.html http://qt-project.org/doc/qt-5.0/qtwidgets...etreemodel.html И ещё, читайте внимательно обзорную статью по MVC, там всё описано, просто не сразу осознаётся весь принцип. Но после разборки пары примеров и собственных опытов всё становится на свои места. Сообщение отредактировал Анна - 31.3.2014, 9:13 |
|
|
Litkevich Yuriy |
![]()
Сообщение
#3
|
![]() разработчик РЭА ![]() ![]() ![]() ![]() ![]() ![]() ![]() Группа: Сомодератор Сообщений: 9669 Регистрация: 9.1.2008 Из: Тюмень Пользователь №: 64 Спасибо сказали: 807 раз(а) Репутация: ![]() ![]() ![]() |
|
|
|
Litkevich Yuriy |
![]()
Сообщение
#4
|
![]() разработчик РЭА ![]() ![]() ![]() ![]() ![]() ![]() ![]() Группа: Сомодератор Сообщений: 9669 Регистрация: 9.1.2008 Из: Тюмень Пользователь №: 64 Спасибо сказали: 807 раз(а) Репутация: ![]() ![]() ![]() |
Также соит отметить что есть ещё одна вспомогательная модель - Модель выделения (SelectionModel), посмотри пример
%QTDIR%\examples\itemviews\chart Но как в этом методе организовать генерацию индексов для объектов классов B, C, D, E и содержащихся в них данных? Связать индекс с реальными данными можно с помощью метода:QModelIndex QAbstractItemModel::createIndex ( int row, int column, void * ptr = 0 ) const [protected] Посмотри пример "Simple Tree Model" |
|
|
vo.borodin |
![]()
Сообщение
#5
|
Новичок Группа: Новичок Сообщений: 4 Регистрация: 26.3.2014 Пользователь №: 4088 Спасибо сказали: 0 раз(а) Репутация: ![]() ![]() ![]() |
Всем спасибо за ответы. У меня в ходе разработки моего проекта появился ещё один вопрос относительно модели/представления в Qt. Допустим, мы находимся в рамках того кода, который я привёл выше. По определенному действию (например, нажатию на пункт главного меню) мне нужно добавить новый элемент в вектор vectorB (член данных класса A), а представление должно отреагировать на это добавление созданием нового виджета (скажем, созданием новой вкладки в объекте класса QTabWidget). Как это всё организовать? Начальные этапы понятны: при нажатии на пункт главного меню я вызываю у модели метод insertRow, передав ему такие параметры, чтобы добавился элемент в корневом классе иерархии, т.е. классе A; а что делать дальше?
|
|
|
![]() ![]() ![]() |
![]() |
Текстовая версия | Сейчас: 1.9.2024, 5:53 |