Урок №12. Рисование в Qt5

  Дмитрий Бушуев  | 

  Обновл. 11 Янв 2020  | 

 231

В этой части туториала по Qt5/C++ мы немного поупражняемся в рисовании. Для этого в Qt5 есть очень мощный класс QPainter. Он может рисовать всё: от простых линий до сложных геометрических фигур по типу секторов, дуг окружностей, многоугольников и т.д.

Методика отрисовки объектов средствами Qt5 сводится к следующему:

   сначала нужно при помощи публичного наследования создать дочерний класс от класса QWidget.

   в созданном классе переопределить метод перерисовки paintEvent(QPaintEvent *).

Метод paintEvent(QPaintEvent *) всегда вызывается при создании виджета, а также всякий раз, когда нужно перерисовать его внешний вид (например, мы растянули/сжали окно, и вместе с этим изменили размеры нашего виджета).

Линии

А начнём мы с простого примера, в котором нарисуем в клиентской области окна шесть линий, которые будут отличаться друг от друга стилем.

Для этого мы создадим дочерний класс Lines, наследуя класс QWidget, и поместим код отрисовки линий внутри переопределённого метода paintEvent().

Заголовочный файл — lines.h:

Файл реализации — lines.cpp:

Т.к. метод paintEvent() вызывается каждый раз при обновлении виджета, то мы будем создавать объект класса QPainter и выполнять операцию рисования внутри данного метода. Поскольку сам объект QPaintEvent *e не используется, то желательно заранее сообщить об этом с помощью макроса Q_UNUSED, иначе компилятор выдаст предупреждение. Фактическая отрисовка линии делегируется методу drawLines():

При помощи класса QPen мы создаём объект pen со следующими параметрами:

   чёрный цвет;

   толщина 2 пикселя;

   сплошная заливка.

Объект pen используется для рисования линий и контуров фигур. Устанавливаем его с помощью метода setPen():

Метод drawLine() рисует линию, его четыре параметра — это координаты двух точек (начала и конца линии):

Метод setStyle() устанавливает стиль Qt::DashLine (пунктирная линия) для объекта pen:

Главный файл программы — main.cpp:

Результат:


Палитра цветов


Цвет — это объект, представляющий собой комбинацию значений интенсивности красного, зеленого и синего цветов («RGB» от «Red, Green, Blue»). Допустимые значения RGB находятся в диапазоне от 0 до 255. В следующем примере мы попробуем нарисовать девять прямоугольников с серым контуром, заполненных разными цветными заливками.

Заголовочный файл — colours.h:

Файл реализации — colours.cpp:

Класс кисти QBrush определяет шаблон заливки фигур, нарисованных с помощью объекта класса QPainter. Метод drawRect() рисует прямоугольник:

   первые два параметра метода — это координаты (x;y) верхнего левого угла прямоугольника;

   другие два параметра — это значения ширины прямоугольника и его высоты.

Для указания цвета мы будем использовать шестнадцатеричное представление:

Главный файл программы — main.cpp:

Результат:


Шаблоны узоров

Следующий пример аналогичен предыдущему, но в этот раз мы будем заполнять прямоугольники не сплошным цветом, а с помощью уже готовых шаблонов узоров кисти.

Заголовочный файл — patterns.h:

Файл реализации — patterns.cpp:

Создаём прямоугольник с определённым рисунком. Qt::HorPattern — это константа, используемая для создания шаблона горизонтальных линий:

Главный файл программы — main.cpp:

Результат:


Прозрачные прямоугольники


Прозрачность — это величина, характеризующая возможность объекта пропускать свет. Самый простой способ понять прозрачность — это представить себе кусок стекла или воды. Технически лучи света могут проходить сквозь стекло, и, таким образом, наблюдатель имеет возможность видеть объекты, находящиеся за ним.

В компьютерной графике мы можем добиться эффекта прозрачности, используя метод альфа-композитинга. Данный метод комбинирует изображение с фоном с целью создания эффекта частичной прозрачности. При этом в процессе композиции используется так называемый альфа-канал — это дополнительный канал, который может быть добавлен в рисунок и содержащий информацию о его прозрачности.

В следующем примере мы нарисуем 10 прямоугольников с разными уровнями прозрачности.

Заголовочный файл — transparent_rectangles.h:

Файл реализации — transparent_rectangles.cpp:

Метод setOpacity() устанавливает непрозрачность для объекта painter класса QPainter. Данное значение должно находиться в диапазоне от 0.0 до 1.0, где 0.0 — это абсолютная прозрачность, а 1.0 — абсолютная непрозрачность:

Главный файл программы — main.cpp:

Результат:


Пончик

А теперь попробуем создать форму пончика. «Пончик» — это более продвинутая геометрическая фигура, напоминающая одноименный вид пищи. Для этого нам понадобятся 72 вращаемых эллипса.

Заголовочный файл — donut.h:

Файл реализации — donut.cpp:

Включим сглаживание, чтобы рендеринг нашего пончика был более качественным:

При помощи данных линий, для облегчения процесса отрисовки нашей фигуры пончика, мы переместим начало системы координат в середину окна. По умолчанию оно расположено в верхнем левом углу окна (данная точка имеет координаты (0;0)):

В цикле for мы по очереди рисуем 72 вращаемых эллипса, при этом каждый последующий эллипс поворачивается на заданный угол относительно предыдущего:

Главный файл программы — main.cpp:

Результат:


Сложные геометрические фигуры


Фреймворк Qt5 позволяет создавать не только стандартные, но и более сложные геометрические фигуры. Вы можете убедиться в этом, взглянув на пример ниже, в котором мы нарисуем девять различных геометрических фигур.

Заголовочный файл — shapes.h:

Файл реализации — shapes.cpp:

QPainterPath — это класс, используемый для создания более сложных фигур при помощи заданной траектории рисования. С его помощью мы будем создавать так называемые «кривые Безье«:

Данные строчки кода рисуют сектор круга, хорду и прямоугольник с закругленными углами:

Далее, с помощью метода drawPolygon(), мы рисуем полигон, состоящий из пяти точек:

Возможности Qt5 позволяют создать траекторию рисования на основе символа, написанного с использованием определённого шрифта:

Так как окружность является частным случаем эллипса, то мы можем нарисовать обе эти фигуры при помощи одного и того же метода DrawEllipse(). Параметрами данного метода являются координаты начала (x;y) ограничивающего эллипс прямоугольника, а также ширина этого прямоугольника и его высота:

Главный файл программы — main.cpp:

Результат:


Линейные градиенты

В компьютерной графике градиент — это плавное смешение оттенков от светлого к темному или от одного цвета к другому. Данные градиенты используются для создания красочных фонов и спецэффектов имитации света и теней. В следующем примере показано создание простейших линейных градиентов.

Для этого нам понадобится нарисовать два прямоугольника, внутреннее пространство которых будет заполнено градиентами.

Заголовочный файл — linear_gradients.h:

Файл реализации — linear_gradients.cpp:

Объект класса QLinearGradient создаёт линейный градиент с областью интерполяции, лежащей между двумя точками, координаты которых передаются объекту в качестве соответствующих параметров:

Цвета в градиенте определяются с помощью стоп-точек. Метод setColorAt() создаёт точку остановки в заданной позиции с заданным цветом:

Заполняем прямоугольник градиентом:

Главный файл программы — main.cpp

Результат:


Радиальные градиенты


Радиальные градиенты — это сочетания цветов или оттенков цветов между двумя окружностями.

В примере ниже мы создадим радиальный градиент, который распространяется от центра окна к его краям.

Заголовочный файл — radial_gradient.h:

Файл реализации — radial_gradient.cpp:

Объект класса QRadialGradient создаёт радиальный градиент; он интерполирует цвета между фокусной точкой и конечными точками, лежащими внутри круга. Параметры — это координаты центральной точки круга и его радиус. Фокусная точка находится в центре круга:

Метод setColorAt() определяет цвета стоп-точек:

Заполняем всю область окна радиальным градиентом:

Главный файл программы — main.cpp:

Результат:


Эффект исчезновения

А сейчас мы попробуем создать эффект исчезновения текста. Пример показывает растущий центрированный текст, который, с некоторого момента, начинает постепенно исчезать.

В заголовочном файле определены два обработчика событий:

   обработчик событий отрисовки paintEvent();

   обработчик таймера timerEvent().

Заголовочный файл — puff.h:

Файл реализации — puff.cpp:

В конструкторе мы запускаем таймер. Каждые 15 мс генерируется событие таймера:

Внутри timerEvent() мы увеличиваем размер шрифта и перерисовываем виджет:

Если размер шрифта больше 10 точек, то мы постепенно уменьшаем непрозрачность и текст начинает исчезать:

Если текст полностью исчез, мы останавливаем таймер:

Главный файл программы — main.cpp:

Результат:


Заключение

Начав с основ рисования таких примитивов, как линии и простые фигуры, мы плавно перешли к созданию геометрических фигур с более сложной формой (многоугольники, фигуры с закругленными углами), к рисованию по заданной траектории, рассмотрели построения градиентов и даже нарисовали свой собственный пончик.

В следующем уроке мы научимся создавать свой собственный виджет.

Оценить статью:

Звёзд: 1Звёзд: 2Звёзд: 3Звёзд: 4Звёзд: 5 (7 оценок, среднее: 5,00 из 5)
Загрузка...

Добавить комментарий

Ваш E-mail не будет опубликован. Обязательные поля помечены *