Здравствуйте,
ищу совет, как правильно готовить MDI на QT.
Т.к. до сих пор работал с голым WinAPI, MFC и WTL, то QT выглядит несколько диковато.
Для начала, как работать с меню (menuBar)? Есть ли возможность загрузить меню целиком? Или сборка из отдельных элементов в рантайме это нормальная практика?
Применительно к MDI, если имеем несколько документов разного типа (например текстовый редактор и графический), как переключать меню при смене активного документа? Убивать все содержимое menuBar'а и лепить заново? Или есть метод поизящнее?
Собственно, те же вопросы и по использованию QAction.
Принято делать так?
saveAct = new QAction(QIcon(":/images/save.png"), tr("&Save..."), this);
saveAct->setShortcuts(QKeySequence::Save);
saveAct->setStatusTip(tr("Save the current form letter"));
connect(saveAct, SIGNAL(triggered()), this, SLOT(save()));
printAct = new QAction(QIcon(":/images/print.png"), tr("&Print..."), this);
printAct->setShortcuts(QKeySequence::Print);
printAct->setStatusTip(tr("Print the current form letter"));
connect(printAct, SIGNAL(triggered()), this, SLOT(print()));
... еще много-много раз...
Или есть какие-то средства "автоматизации", не упомянутые в примерах? Типа карт сообщений в WTL/MFC? Пока, кроме изобретения собственного велосипеда, ничего не нашел.
Если разные документы должны обрабатывать одну и ту же команду, например "Печать", где принято создавать соответствующий QAction?
В MainWindow? А как тогда передать обработку активному документу (использовать грядку из qobject_cast'ов)?
Или же создавать в каждом документе свою копию QAction'а? Не будут ли они конфликтовать в этом случае?
_____________________
С уважением,
Stanislav V. Zudin
Здравствуйте, Stanislav V. Zudin, Вы писали:
SVZ>Для начала, как работать с меню (menuBar)? Есть ли возможность загрузить меню целиком? Или сборка из отдельных элементов в рантайме это нормальная практика?
Да, это нормальная практика. Что не устраивает?
SVZ>Применительно к MDI, если имеем несколько документов разного типа (например текстовый редактор и графический), как переключать меню при смене активного документа? Убивать все содержимое menuBar'а и лепить заново?
Нормальный вариант.
SVZ>Собственно, те же вопросы и по использованию QAction.
SVZ>Принято делать так?
Да.
SVZ>Или есть какие-то средства "автоматизации", не упомянутые в примерах? Типа карт сообщений в WTL/MFC?
Не в курсе, что это. Покажи, что хочется.
SVZ>Если разные документы должны обрабатывать одну и ту же команду, например "Печать", где принято создавать соответствующий QAction? SVZ>В MainWindow? А как тогда передать обработку активному документу (использовать грядку из qobject_cast'ов)? SVZ>Или же создавать в каждом документе свою копию QAction'а? Не будут ли они конфликтовать в этом случае?
Это не имеет отношения к Qt — это вопрос к дизайну. Пример:
MTD>Здравствуйте, Stanislav V. Zudin, Вы писали:
SVZ>>Для начала, как работать с меню (menuBar)? Есть ли возможность загрузить меню целиком? Или сборка из отдельных элементов в рантайме это нормальная практика?
MTD>Да, это нормальная практика. Что не устраивает?
Получается очень большой объем ручной работы. Ну и приходится создавать невероятную прорву QAction.
Кроме того, у меня сложилось впечатление, что в QT MDI не очень поощряется, особенно с разнотипными документами, что требуется мне.
SVZ>>Или есть какие-то средства "автоматизации", не упомянутые в примерах? Типа карт сообщений в WTL/MFC?
MTD>Не в курсе, что это. Покажи, что хочется.
В WinAPI/MFC/WTL команда от тулбара или меню идентифицируется числовым идентификатором, который передается в виндовом сообщении WM_COMMAND.
Поэтому все команды легко свести к массиву/мапу указателей на интерфейсы или функции. При этом легко гонять все команды от одного обработчика к другому.
Например, в MFC команду можно обработать во вьюшке, Документе, главном окне приложения — сообщение передается по цепочке, пока кто-нибудь его не обработает.
Если в определенный момент желающих обработать не найдется, то ничего криминального не произойдет — команда похерится.
SVZ>>Если разные документы должны обрабатывать одну и ту же команду, например "Печать", где принято создавать соответствующий QAction? SVZ>>В MainWindow? А как тогда передать обработку активному документу (использовать грядку из qobject_cast'ов)? SVZ>>Или же создавать в каждом документе свою копию QAction'а? Не будут ли они конфликтовать в этом случае?
MTD>Это не имеет отношения к Qt — это вопрос к дизайну. Пример:
MTD>
Да, я думал про такое. Потому и решил спросить тех, кто использует QT в боевых условиях, что есть в фреймворке для решения моей задачи.
Оказалось, готовых решений нет и надо городить свой велосипед.
Спасибо тебе за разъяснения.
_____________________
С уважением,
Stanislav V. Zudin
Здравствуйте, Stanislav V. Zudin, Вы писали:
MTD>>Да, это нормальная практика. Что не устраивает? SVZ>Получается очень большой объем ручной работы. Ну и приходится создавать невероятную прорву QAction.
Тут без вариантов — в любом фреймворке надо описать, что тебе надо. Как без этого? С QAction — это очень удобно, ведь его можно вставить не только в основное меню, но и например в меню показываемое по правой кнопке.
SVZ>В WinAPI/MFC/WTL команда от тулбара или меню идентифицируется числовым идентификатором, который передается в виндовом сообщении WM_COMMAND. SVZ>Поэтому все команды легко свести к массиву/мапу указателей на интерфейсы или функции. При этом легко гонять все команды от одного обработчика к другому. SVZ>Например, в MFC команду можно обработать во вьюшке, Документе, главном окне приложения — сообщение передается по цепочке, пока кто-нибудь его не обработает.
Вообще не понял нафига лезть под капот?
SVZ>Если в определенный момент желающих обработать не найдется, то ничего криминального не произойдет — команда похерится.
Это вообще печально.
Короче, вот пример в псевдокоде:
MainWindow()
{
CreateActions();
CurrentData_ = new TxtData();
setMenuBar(CreateMenu(CurrentData_));
}
CreateActions()
{
Open_ = new QAction();
Print_ = new QAction();
}
CreateMenu(TxtData&)
{
QMenuBar* menu = new QMenuBar();
menu->addAction(Open_);
menu->addAction(Print_);
return menu;
}
CreateMenu(BinData&)
{
QMenuBar* menu = new QMenuBar();
menu->addAction(Open_);
return menu;
}
Open()
{
CurrentData_->Open();
}
SVZ>Да, я думал про такое. Потому и решил спросить тех, кто использует QT в боевых условиях, что есть в фреймворке для решения моей задачи. SVZ>Оказалось, готовых решений нет и надо городить свой велосипед.
Здравствуйте, MTD, Вы писали:
SVZ>>В WinAPI/MFC/WTL команда от тулбара или меню идентифицируется числовым идентификатором, который передается в виндовом сообщении WM_COMMAND. SVZ>>Поэтому все команды легко свести к массиву/мапу указателей на интерфейсы или функции. При этом легко гонять все команды от одного обработчика к другому. SVZ>>Например, в MFC команду можно обработать во вьюшке, Документе, главном окне приложения — сообщение передается по цепочке, пока кто-нибудь его не обработает.
MTD>Вообще не понял нафига лезть под капот?
Ну я бы не назвал это лазаньем под капот
Есть команды разной породы:
Всякие Open, Exit, Settings etc. — они не зависят от текущего документа и могут обрабатываться в главном окошке, ни один документ о них и знать не знает.
Есть команды, специфичные для текущего документа, их обработчики находятся в соответствующих документах. Та же команда Print может поддерживаться всеми типами документов, но будет обработана только текущим документом.
А есть команды, которые относятся даже не к документу, а к его, активной в данный момент, вьюшке (масштабирование изображения, к примеру). Обработчики этих команд будут находиться, соответственно, во вьюхе.
Но ходить все команды будут по одному маршруту, их легко можно поймать и обработать. Или перехватить, что-то сделать свое, а потом дать команде долететь до цели.
Т.е. получается-то фактически то же, что ты нарисовал в примере, но на другом уровне.
MTD>Короче, вот пример в псевдокоде:
(пример скипнул) Примерно так же и стал делать, но были сомнения.
_____________________
С уважением,
Stanislav V. Zudin
SVZ>Получается очень большой объем ручной работы. Ну и приходится создавать невероятную прорву QAction.
Можно описать меню на подходящем DSL и генерировать по описанию. Заодно появляется возможность кастомизации меню юзером — мелочь, а приятно.
Re: MDI & QT best practices
От:
Аноним
Дата:
04.04.12 18:55
Оценка:
SVZ>Пока, кроме изобретения собственного велосипеда, ничего не нашел.
IMHO. КуТэ низкоуровневый фрэймворк заточенный не для написания сложных приложений, а для абстрагирования ГУИ. Все плюшки придется писать или дописывать вручную.