# ProgressPanel

## Обзор компонента

`Minecraft_launcher` — десктопный лаунчер Minecraft на Qt Quick. Почти каждое действие в нём
долгое: скачивание версии игры, установка Java, распаковка и архивация папки `.minecraft` при
смене сборки, загрузка сезонной сборки. Лаунчер не блокирует окно на это время, поэтому ход
операции нужно показывать неотрывно от остального интерфейса.

`ProgressPanel` — та самая плашка прогресса. Она размещается в левом нижнем углу главного окна,
где не перекрывает кнопку запуска, сообщение по центру и кнопки папки и настроек. Компонент
только отображает переданное состояние; сам он ничего не считает и ни за чем не следит.

## Место в проекте и зависимости

Импортирует `QtQuick` и `QtQuick.Controls 2.15`; C++-типы напрямую не использует.

Объявлен в `QML_FILES` модуля `Minecraft_launcher` (`CMakeLists.txt`), поэтому доступен по имени
внутри модуля без импорта. Инстанцируется в [Main](Main.md) — по одной плашке на вид долгой
операции.

## Иерархия и роль

Корневой тип — `Rectangle` фиксированного размера 320×72 px со скруглением 8 px, тёмной заливкой,
акцентной рамкой и лёгкой полупрозрачностью, чтобы плашка читалась поверх фонового изображения
окна.

Внутри — пять элементов без внешних зависимостей: заголовок слева сверху, проценты справа сверху,
полоса прогресса (дорожка и заполнение с плавной анимацией ширины на 120 мс), строка подробностей
снизу и крестик отмены в правом нижнем углу с увеличенной областью нажатия.

## Свойства

| Свойство | Тип | По умолчанию | Обязательное | Описание |
|----------|-----|--------------|--------------|----------|
| `title` | `string` | `""` | Нет | Заголовок операции в левом верхнем углу, полужирным. Длинный текст обрезается справа многоточием. |
| `status` | `string` | `""` | Нет | Строка состояния внизу плашки. Показывается только когда `detail` пуст. |
| `fraction` | `double` | `-1` | Нет | Доля выполнения от `0` до `1`. Значение `-1` означает «итог ещё неизвестен»: вместо процентов выводится многоточие, а полоса остаётся пустой. |
| `detail` | `string` | `""` | Нет | Необязательная вторая строка подробностей — мегабайты у загрузки, путь у архивации. Если задана, вытесняет `status`. Длинный текст обрезается посередине, чтобы у пути были видны и начало, и конец. |
| `cancellable` | `bool` | `true` | Нет | Показывать ли крестик отмены. Ставится в `false` для операций, которые прерывать нельзя. |

## Сигналы

#### cancelRequested()

Пользователь нажал крестик в правом нижнем углу. Сигнал сообщает только о намерении: плашка не
скрывает себя и не меняет своё состояние.

Обработчик должен сам остановить операцию в бэкенде и убрать плашку с экрана — как правило, вызвав
соответствующий метод отмены у `LauncherBackend`; видимость плашки при этом снимется сама, потому
что она привязана к свойству занятости бэкенда.

Сигнал не испускается при `cancellable: false` — в этом случае крестик скрыт.

## Методы

Собственных функций нет.

## Взаимодействие с другими компонентами

Все пять свойств плашки — точки внешней привязки. В [Main](Main.md) они связаны со свойствами
`LauncherBackend`: у загрузки версии это группа `downloading` / `downloadProgress` /
`downloadVersion` / `downloadStatus` / `downloadBytesDone` / `downloadBytesTotal`, у смены сборки —
`switching` / `switchProgress` / `switchStage` / `switchStatus`. Байты в мегабайты переводит
функция `formatMb()` главного окна, а не сама плашка.

Видимостью плашки управляет родитель, обычно привязывая её к тому же признаку занятости, который
питает `fraction`. Сигнал `cancelRequested` родитель замыкает на метод отмены бэкенда.

## Пример использования

```qml
ProgressPanel {
    anchors.left: parent.left
    anchors.bottom: parent.bottom
    anchors.margins: 16
    visible: backend.downloading

    title: qsTr("Загрузка Minecraft %1").arg(backend.downloadVersion)
    status: backend.downloadStatus
    fraction: backend.downloadProgress
    detail: formatMb(backend.downloadBytesDone) + " / " + formatMb(backend.downloadBytesTotal)

    onCancelRequested: backend.cancelDownload()
}
```

---

При создании этого документа использовался ИИ.
