Сегодня с помощью QtCreator и C++ мы реализуем простое «плавающее» окно – часы. Работать мы будем в Windows 10. Материал будет разбит на несколько частей.
Создавая программы, программист зачастую сталкивается с необходимостью вывода разнообразной информации на экран. Для этого обычно используются разнообразные всплывающие окна или окна диалог
Если же необходимо показывать пользователю достаточно часто изменяющуюся информацию, например, скорость загрузки/скачивания информации, вывод какого-либо графика – то тут лучше использовать «плавающее» окно.
Плавающие окна появились довольно давно, самые первые менеджеры закачки использовали их, чтобы отображать информацию о статусе соединения и скорости закачки. Как правило такие окошки были полупрозрачны, так что не перекрывали полностью полезную площадь экрана и могли быть размещены в любой части экрана. Такие окна часто использовались в старых программах для закачки файлов.
Яндекс.Браузер умеет откреплять любое видео в виде плавающего окна, что очень удобно.
Так же, «плавающее» окно использует программа Download Master.
Создание проекта
Откроем Qtcreator и создадим проект Qt Widgets Application
для декстопа.
Назовем его QtFloatWindow
.
В качестве «Build System
» выберем qmake
.
Класс окна оставим без изменений.
Пробный запуск
Сразу после создания, проект откроется в редакторе, нам нужно проверить собирается ли у нас проект в принципе.
Раскрываем папку с проектом и открываем файл mainwindow.cpp
Нажимаем Ctrl+R, будет запущена сборка проекта.
Возможно в процессе сборки вы получите сообщение об ошибке:

Жмем Yes.
Это ошибка:
C:\msys64\mingw64\share\qt5\mkspecs\common\windows-vulkan.conf:1: error: Cannot find feature windows_vulkan_sdk
Её можно спокойно игнорировать, если, конечно, вы не используете Vulkan API для разработки под windows.
Если более серьезных ошибок не возникло и среда сборки у вас настроена верно, то появится такое вот окно:
Вот и всё, текст прошел успешно можно закрывать окно.
Добавление формы для плавающего окошка
Пришло время заняться непосредственно плавающим окном.
Добавим новую форму в проект. Для этого щелкаем правой кнопкой на название проекта и выбираем Add new…
В новом выбираем Qt
и Qt Designer Form Class
и жмем Choose…

На следующей форме выбираем Widget
и жмем Next
Задаем имя новой формы в поле Class name
: FloatWindow

Жмем Next
и сразу Finish
Откроется наша, только что созданная, форма:
В свойствах формы в блоке geometry задаем новые размеры формы, пусть это будет:
Width: 200
Height: 70
Размеры окна, в редакторе, изменяться в соответствии с заданными размерами.
Тестирование новой формы
Если мы сейчас запустим сборку проекта, то после его запуска не увидим новую форму. Нам нужно вручную добавить код для его создания.
Откроем mainwindow.cpp
Добавим в начало файла:
[code]#include "floatwindow.h"[/code]
В конец MainWindow::MainWindow(QWidget *parent)
добавим:
[code]
FloatWindow *fwin = new FloatWindow();
fwin->show();
[/code]
У нас получится:
[code]
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "floatwindow.h"
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui(new Ui::MainWindow)
{
ui->setupUi(this);
FloatWindow *fwin = new FloatWindow();
fwin->show();
}
MainWindow::~MainWindow()
{
delete ui;
}
[/code]
Запускаем проект Ctrl+R
Откроется наше большое окно, если вы его свернем, то под ним окажется наша новая форма:

Добавление компонентов на форму
Займемся внешним видом нашей формы, откроем её в редакторе и перетащим новый компонент Widget
из области со списком компонентов.
Так же перетащим на Label
на только что созданный Widget
. Вы можете его перетащить и сбросить не только непосредственно на форму, но и на имя widget в списке компонентов формы.
В списке справа выбираем нашу форму – FloatWindow
Правой кнопкой вызываем меню и выбираем Lay Out -> Lay Out Horizontally
.
В списке справа выбираем нашу форму – Widget
Правой кнопкой вызываем меню и выбираем Lay Out -> Lay Out Horizontally
.
Выбираем widget
и в поле objectName
вводим новое значение для нее – centralwidget
Выбираем label
и в поле objectName
вводим новое значение для нее – clockLabel
Выбираем label
Обратите внимание, так как мы использовали Layout
, то изменять размер Label
мы не можем.
В окне свойств пролистайте вниз до свойств QLabel
В поле Text
вводим 00:00:00
В поле alignment
для Horizontal
выставляем AlignHCenter
Листаем вверх и выставляем размер шрифта равным 30
У нас получится следующее:

Теперь уберем ненужные отступы.
В списке справа выделяем FloatWindow
и пролистываем свойства до самого низа – Layout
Меняем все значения равные 9
или 6
на 0
. Таким образом мы убираем ненужные отступы.
Повторяем тоже самое для centralwidget
Делаем из формы «плавающее» окно
Открываем floatwindow.cpp
и добавляем код в FloatWindow::FloatWindow(QWidget *parent)
[code]
setStyleSheet("#centralwidget { background-color: rgba(255, 255, 255, 100); border:1px solid #eee; }");
setAttribute(Qt::WA_TranslucentBackground);
setWindowFlags(Qt::FramelessWindowHint|Qt::WindowStaysOnTopHint);
[/code]
Запускаем, чтобы проверить что получилось – Ctrl-R.
Вот у нас и получилось нечто похожее на «плавающее» окошко, правда сдвинуть его не получиться, так как заголовки и границы у формы мы скрыли.
Учим окно перемещаться по экрану
Давайте добавим код, позволяющий нам его перемещать по экрану.
Открываем floatwindow.cpp
и добавляем в конец файла:
[code]
void FloatWindow::mousePressEvent(QMouseEvent *evt)
{
oldPos = evt->globalPos();
}
void FloatWindow::mouseMoveEvent(QMouseEvent *evt)
{
const QPoint delta = evt->globalPos() - oldPos;
move(x()+delta.x(), y()+delta.y());
oldPos = evt->globalPos();
}
[/code]
Нажимаем F4 и добавляем
QPoint oldPos;
после
Ui::FloatWindow *ui;
Добавляем
[code]
protected:
void mousePressEvent(QMouseEvent *evt);
void mouseMoveEvent(QMouseEvent *evt);
[/code]
после
[code]
private:
Ui::FloatWindow *ui;
QPoint oldPos;
[/code]
Добавляем
#include <QMouseEvent>
В начало файла.
Запускаем сборку Ctrl-R.
Вот и наше полупрозрачное окошко:

Просто щелкаем на нем левой кнопкой мыши и не отпуская перетаскиваем в нужное место на экране.
Заключение
Подведем итоги, мы узнали:
- Как добавить еще одну форму к проекту;
- Как правильно добавить компоненты на форму и настроить отступы;
- Как превратить обычную форму в «плавающее» окно;
- Добавили функционал перемещения окна в любое место экрана.
Вот и всё на сегодня. В следующем материале мы добавим контекстное меню для плавающего окна и заставим часы идти.
Готовый проект вы можете найти на github по ссылке.