Различные статьи по Qt и c++

Что изменилось в Qt6: обзор ключевых отличий от Qt5 для практикующего разработчика

Qt6 — первое крупное обновление основной версии фреймворка за много лет. В отличие от перехода Qt4 → Qt5, который был довольно болезненным, Qt6 спроектирован так, чтобы упростить поддержку кода, работающего одновременно со старой и новой версией. Разберём ключевые изменения, которые реально влияют на повседневную разработку.

1. CMake как основная система сборки

qmake продолжает поддерживаться, но все новые возможности (модульность, генерация ресурсов, deployment-инструменты) появляются прежде всего в CMake-инфраструктуре. Пример минимального проекта:

cmake_minimum_required(VERSION 3.16)
project(HelloQt6 VERSION 1.0 LANGUAGES CXX)

set(CMAKE_CXX_STANDARD 17)
set(CMAKE_AUTOMOC ON)

find_package(Qt6 REQUIRED COMPONENTS Widgets)
qt_standard_project_setup()

qt_add_executable(HelloQt6 main.cpp)
target_link_libraries(HelloQt6 PRIVATE Qt6::Widgets)

Функция qt_standard_project_setup() — новинка Qt6, она автоматически настраивает AUTOMOC, AUTORCC, стандарт каталогов и др.

2. Изменение модели хранения QString

Внутри QString теперь хранятся данные в UTF-16, но добавлен полноценный класс QStringView для работы без копирования, а также улучшена поддержка UTF-8 через QUtf8StringView. Это особенно важно при работе с большими текстовыми данными:

void processLine(QStringView line) {
    if (line.startsWith(u"//"))
        return; // комментарий, пропускаем без копирования строки
    qDebug() << "Line:" << line;
}

QString text = "// comment\nreal data";
for (const auto &line : QStringView(text).split(u'\n'))
    processLine(line);

3. Новый рендеринг QML — RHI (Rendering Hardware Interface)

В Qt5 QtQuick жёстко завязан на OpenGL. В Qt6 добавлен слой абстракции RHI, который позволяет выбирать backend: Direct3D, Vulkan, Metal или OpenGL — в зависимости от платформы.

// main.qml — поведение не меняется, но под капотом
// рендерер может работать через Direct3D 11 на Windows
import QtQuick
import QtQuick.Window

Window {
    visible: true
    width: 640
    height: 480
    Rectangle {
        anchors.fill: parent
        color: "lightblue"
    }
}

Backend можно явно задать переменной окружения:

set QSG_RHI_BACKEND=d3d11

4. Удаление и реорганизация модулей

  • Qt Quick Controls 1 — полностью удалён, остался только Qt Quick Controls 2 (импортируется просто как QtQuick.Controls).
  • QtWebEngine теперь требует отдельного внимания к версиям Chromium.
  • Qt Multimedia переписан с нуля, API существенно отличается от Qt5-версии.
  • Появился Qt Quick 3D для декларативного 3D на QML.

5. Строгая типизация в QML

В Qt6 появилась возможность компилировать QML «статически» (qmlcachegen / qmltc), что требует более строгих типов в QML-коде:

import QtQuick

Item {
    // Явное указание типа свойства упрощает статическую компиляцию
    property int counter: 0
    property string label: "Count: " + counter

    Timer {
        interval: 1000; running: true; repeat: true
        onTriggered: counter++
    }
}

6. Изменение базовых типов

qreal стал везде типом double (на 32-битных платформах раньше это мог быть float), что устраняет ряд проблем с точностью на ARM-платформах.

7. Поддержка C++17 как минимум

Код, использующий Q_FOREACH, по-прежнему работает, но рекомендуется переходить на range-based for и структуры C++17:

// современный стиль с std::optional вместо проверки isValid()
std::optional<QString> findUser(int id) {
    if (id == 42)
        return QString("Alice");
    return std::nullopt;
}

if (auto user = findUser(42)) {
    qDebug() << "Found:" << *user;
}

Подводные камни

  • Старые скомпилированные .qmlc-кэши и плагины не совместимы между Qt5 и Qt6 — необходима полная пересборка.
  • Сторонние библиотеки (например, QZXing, qtkeychain) нужно проверять на поддержку Qt6 — не все обновились одновременно.
  • В новых дистрибутивах Linux часто присутствует только Qt6, без Qt5 — тестируйте deployment заранее.

Совет

Перед началом активной разработки на Qt6 проверьте, что все используемые сторонние библиотеки и плагины имеют актуальные релизы под Qt6. Это сэкономит время на этапе интеграции значительно больше, чем любые отличия в самом коде Qt-приложения.

================================================================================