Для дальнейшей работы вам также необходимо знать, что же такое виджет, т.к. с этим словом вы часто будете сталкиваться в дальнейшем.
По терминологии Qt и Unix виджетом (widget) называется любой визуальный элемент графического интерфейса пользователя. Этот термин происходит от «window gadget» и соответствует элементу управления («control») и контейнеру («container») по терминологии Windows. Кнопки, меню, полосы прокрутки и фреймы являются примерами виджетов. Одни виджеты могут содержать в себе другие виджеты. Например, окно приложения обычно является виджетом, содержащим QMenuBar (панель меню), несколько QToolBar (панель инструментов), QStatusBar (строка состояния) и некоторые другие виджеты. Большинство приложений используют QMainWindow или QDialog в качестве окна приложения, однако Qt настолько гибок, что любой виджет может быть окном.
Виджеты всегда создаются сначала невидимыми, и поэтому до непосредственного вывода на экран вы можете настроить их и тем самым не допустить мерцание экрана.
По данному курсу рекомендованы к прочтению следующие книги:
1. Жасмин Бланшет, Марк Саммерфилд / Qt4: Программирование GUI на C++ = C++ GUI Programming with Qt 4. –Издание второе, дополненное. – Москва: КУДИЦ-ПРЕСС, 2008. – 718 с.
2. Макс Шлее / Qt 4.5. Профессиональное программирование на С++. –Санкт-Петербург: БХВ, 2010. – 896 с.
3. Куликов Г.Э. / Создание графических приложений на платформе Qt.
4. Земсков Ю.В. / Программирование на C++ с использованием библиотеки Qt4. – БХВ-Петербург, 2007.
1.1. Hello, World!
Начнем с простейшего приложения, известного всем «Hello, World!».
Последующее описание действий необычайно детализировано, впрочем, это только лишь для первого примера – в дальнейшем не будет приводиться столько экранных форм. Сейчас же они служат для большей наглядности и понимания программистом своих действий.
Также стоит заметить, что большинство из тех действий, что вы будете сейчас совершать, полностью автоматизированы, и их можно сделать всего за пару кликов воспользовавшись мастером, но в целях обучения мы будем их совещать последовательно вручную.
Для начала запустите Qt Creator.
1. Выберете Файл - Новый файл или проект…
Либо просто воспользуйтесь комбинацией Ctrl+N.
Рис. 1.1. Создание пустого проекта Qt
Выберите Другой проект и затем из списка Пустой проект Qt и нажмите Выбрать….
2. Введите имя проекта и путь к нему (избегайте символов кириллицы!!!), когда будете задавать путь, выделите для ваших проектов отдельную директорию, а также поставьте галочку Размещение проекта по умолчанию (теперь все ваши проекты по умолчанию будут размещаться в этом каталоге), нажмите Далее (2 раза). А потом – Завершить.
Рис. 1.2. Создание пустого проекта Qt
3. Теперь повторите пункты 1-2, только выберите: С++, а затем Файл исходных текстов С++.
Рис. 1.3. Добавление в проект файла исходных текстов С++
с помощью мастера
Это ОЧЕНЬ важно: начиная с версии Qt 5.0 в файл проекта стоит дописать:
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
или просто: QT += widgets
4. Введите следующий код:
#include <QApplication>
#include <QPushButton>
int main(int argc, char *argv[ ])
{
QApplication app(argc, argv);
QPushButton button("Hello, World!");
button.resize(200, 60);
button.show( );
return app.exec( );
}
5. Нажмите на кнопку Выполнить , либо Ctrl+R.
Если программа не запустилась – прочитайте, что пишет компилятор, проверьте путь к исполняемому файлу (он не должен содержать символов кириллицы), посмотрите, не запущена ли программа прямо сейчас…
Рис. 1.4. Результат работы программы
Пояснения к программе:
- (1-2) Подключили заголовочные файлы с определениями классов QApplication (приложение) и QPushButton (кнопка).
- (4) Обычный для C++ заголовок главной функции main с аргументами командной строки.
- (6) Объявили переменную типа QApplication (приложение), передав конструктору параметры командной строки, которые, возможно, указаны при запуске программы (argc - число параметров, argv - указатель на массив строковых значений).
- (8) Создали главное окно приложения, которое представляет собой обычную кнопку с текстом «Hello, World!» (пока мы избегаем использовать символы кириллицы, этому вопросу будет посвящены следующие примеры).
- (9) Определили размеры окна (ширину и высоту) в пикселях.
- (10) Вывели окно на экран.
- (12) Запустили цикл обработки событий, происходящих с элементами приложения. Пока в нашей программе никакие события не определены, кроме стандартных реакций на действия пользователя (изменение размеров и положения окна, нажатие кнопок в строке заголовка).
6. Прежде чем перейти к следующему примеру, позволим себе небольшое отступление, а именно заменим строки:
QPushButton button("Hello, World!");
button.resize(200, 60);
button.show( );
на строки:
QLabel *label = new QLabel ("<h2><i>Hello,</i> " "<font color = red > Qt! </font> </h2>");
label->show( );
заметьте, теперь мы используем указатели, а могли написать просто:
QLabel label("<h2><i>Hello,</i> " "<font color = red > Qt! </font></h2>");
label.show( );
вставьте тот вариант, который вам больше нравиться.
Также стоит добавить:
#include <QLabel>
и снова выполним построение приложения. При запуске окно будет выглядеть, как показано на рис. 1.5. Как иллюстрирует этот пример, совсем не трудно выделять элементы пользовательского интерфейса Qt-приложения с использованием некоторых простых средств форматирования документов HTML.
Рис. 1.5. Результат работы программы с HTML-форматированием
7. Продолжим модифицировать эту несложную программу и постепенно осваивать Qt. Откатим все изменения, сделанные нами в п.6, переделаем программу под указатели и допишем следующие строки:
Эти строки привязывают действие выхода из программы нашей кнопке, используя механизм сигналов и слотов.
Виджеты Qt (о том, что такое виджет см. стр. 6) генерируют сигналы в ответ на выполнение пользователем какого-то действия или изменение состояния. Например, QPushButton генерируют сигнал clicked( ) при нажатии пользователем кнопки. Сигнал может быть связан с функцией (называемой слотом в данном контексте) для автоматического ее выполнения при получении данного сигнала. В нашем примере мы связываем сигнал кнопки clicked( ) со слотом quit( ) объекта приложения QApplication. Макросы SIGNAL( ) и SLOT( ) являются частью синтаксиса.
8. Добавим «горячую клавишу». Если текст подписи содержит амперсанд “&”, то символ после амперсанда автоматически устанавливается в качестве «горячей клавиши», переопределяя ранее заданное значение. Вы можете определить собственный акселератор для кнопки с помощью метода setShortcut(const QKeySequence &), метод и свойство shortcut возвращают значение последовательности «горячих клавиш» для данной кнопки. Коды QKeySequence (советую посмотреть файл справки по этому классу) могут быть заданы как числовыми значениями символов, так и строками специального формата, которые могут восприниматься в Qt как допустимые. Например, “Ctrl+Q” является корректным сочетанием в качестве комбинации “горячих клавиш”. Но Qt не желает напрямую воспринимать текстовые константы – вам необходимо заключить их в функцию tr( ).
Впрочем, можно поступить и по-другому – использовать константные выражения, например: Qt::Key_Q – для клавиши Q.
Это странно: в Qt почему-то клавиши Enter соответствует константа Qt::Key_Return, а не Qt::Key_Enter.
Это важно: tr следует применять, в данном случае, следующим образом – QObject::tr(<Строковые символы в кавычках>).
9. Есть еще один интересный метод, связанный с кнопкой: animateClick( ). Сей метод анимирует щелчок на кнопке: она будет отрисована в “нажатом”, а через указанное время (в миллисекундах) — в “отжатом” состоянии. Такой эффект часто реализуется в демонстрационных целях, когда нужно эмулировать работу пользователя. Опробуйте этот метод в действии.
10. Специфика кнопок действия (QPushButton) состоит в следующем: одна из них может быть кнопкой по умолчанию, т.е. генерировать сигнал активизации во время нажатия клавиши <Enter> на форме. Обычно такое поведение используется в окнах диалога. Для установки/проверки свойства “кнопка по умолчанию” используются методы QPushButton::setDefault( ) и isDefault( ) соответственно.
В качестве практического задания реализуйте:
- анимацию трехсекундного нажатия на клавишу;
- выход из программы по нажатию Ctrl+Q и Enter.
Задания взаимоисключающие, посему реализуйте сначала одно, затем закомментируйте и приступайте к другому.
11. Давайте научим программу здороваться с нами.
До этого мы уже использовали QLabel и QPushButton в качестве главного виджета, обычно же используют QMainWindow или QDialog, однако на сей раз главным виджетом будет (как бы это странно не звучало) виджет.
#include <QApplication>
#include <QPushButton>
#include <QHBoxLayout>
#include <QSlider>
#include <QSpinbox>
#include <QLabel>
#include <QLineEdit>
int main(int argc, char *argv[ ])
{
QApplication app(argc, argv);
QWidget *window = new QWidget;
window->setWindowTitle("Enter Your Name and Age");
QLabel *label = new QLabel("<font color = red > Name </font>");
QLineEdit *lineEdit = new QLineEdit;
QLabel *label2 = new QLabel("<font color = yellow > Age </font>");
spinBox->setValue(35);
QLabel *label3 = new QLabel("<font color = red > Greetings, my Overlord! </font>");
+ В этом коде есть ошибка, Вам необходимо ее исправить.
В этом примере стоит обратить особое внимание на взаимодействие spinBox и slider, подумайте насколько это сложно реализовать с других средах.
Теперь вдумчиво разберите сей код, постарайтесь понять, что и как реализовано. Обратите внимание на то, как реализована компоновка виджетов в окне приложения, на названия подключаемых директивой #include модулей.
В качестве контрольного задания сделайте так, чтобы:
- приложение поздоровалось именно с вами, т.е. вывело на экран то, что вы напишите в поле lineedit (вывод стоит осуществить в заголовок окна и в label3);
- измените компоновку виджетов в окне, будьте готовы рассказать преподавателю, что такое слои (Layout) и как они работают.
Контрольные вопросы
1. Что собой представляет Qt?
2. Что такое «виджет»?
3. В чем состоит смысл понятия «кросс-платформенность»?
4. На каких ОС могут компилироваться программы написанные с помощью Qt?
5. Какие средства форматирования доступны в Qt?
6. Как работает механизм сигналов и слотов в Qt?
7. Как работает механизм компоновки виджетов в Qt?