# Как контрибьютить в XiControl Спасибо, что хотите помочь! Краткие правила — подробности в [CLAUDE.md](CLAUDE.md) (да, это гайд и для людей: там философия проекта и принятые идиомы). ## Главное правило **Driver-free.** Никаких kernel-драйверов, WinRing0, прямого доступа к EC или записи MSR. Утилита работает только через штатный WMI-интерфейс прошивки (`MiCommonInterface`) и обычный Win32. PR, нарушающий этот принцип, не будет принят независимо от пользы фичи. ## Сборка и тесты ```powershell # приложение обычно уже запущено — сначала убить, иначе MSB3027 Stop-Process -Name XiControl -Force -ErrorAction SilentlyContinue dotnet build XiControl.sln -c Release # должно быть 0 ошибок / 0 предупреждений dotnet test XiControl.sln -c Release # все тесты зелёные ``` Сборка настроена строго: `TreatWarningsAsErrors=true`, анализаторы (.NET CA + Roslynator) включены. Осознанные исключения из правил задокументированы в [.editorconfig](.editorconfig) — не отключайте правила без обоснования. Exe после sln-сборки лежит в `src\bin\x64\Release\net8.0-windows\XiControl.exe`. Запуск показывает UAC (манифест `requireAdministrator`) — это норма. ## Стиль - Пишите как вокруг: плотный код, комментарии по-русски, объясняющие *почему*, а не *что*. - Любая строка для пользователя — через `Loc.T(...)` и сразу на трёх языках (RU/EN/ZH) в `src/Localization/lang/{ru,en,zh}.json`. Хардкод текста в UI не пройдёт ревью. - Деградируйте мягко: железо-зависимые вызовы — в try/catch с `Log.Ex`, приложение не падает на несовместимой модели. - UI-поток не блокируем: долгие WMI/PnP-вызовы — в `Task.Run`. - В таблице иконок `OsdForm` — намеренное колоночное выравнивание; `dotnet format` по этому файлу не гонять. ## Процесс 1. Синхронизируйте форк с `main` (кнопка «Sync fork») — `main` здесь часто уходит вперёд. 2. Фича — в отдельной ветке от свежего `main`, не в форк-`main`. 3. PR должен собираться чисто и проходить CI (build + tests — жёсткие гейты). 4. Проверка на железе приветствуется, но не обязательна: мейнтейнер проверяет на Xiaomi Book Pro 14 (TM2424). Укажите в PR, на какой модели тестировали вы. ## Переводы (добавить язык или поправить строки) Переводы — это **обычные JSON-файлы**, по одному на язык, в `src/Localization/lang/`. Кода трогать не нужно: список языков строится из этих файлов автоматически. **Добавить новый язык:** 1. Скопируйте `en.json` в `<код>.json`, где `<код>` — двухбуквенный код языка (`uk`, `de`, `fr`, `pl`…). Например `src/Localization/lang/uk.json`. 2. В начале файла поправьте мету: - `"_culture"` — тот же код, что в имени файла (`"uk"`); - `"_name"` — родное название языка, как оно должно выглядеть в списке (`"Українська"`); - `"_order"` — порядок в списке (существующие: ru=0, en=1, zh=2; новым дайте больше). 3. Переведите **значения** справа от `:`. **Ключи слева не трогайте** — это контракт с кодом. 4. Сохраните `{0}`, `{1}` и т.п. — это подстановки (числа, частоты); порядок можно менять под грамматику языка, но сам плейсхолдер должен остаться. 5. Всё. Язык появится в Настройки → Общие → Язык при следующем запуске. **Поправить существующий перевод:** отредактируйте значения в нужном `<код>.json`. **Проверка:** `dotnet test XiControl.sln -c Release` — тесты локализации ловят забытые/лишние ключи, пустые значения и рассинхрон плейсхолдеров между языками. Если тест красный — он прямо скажет, какой ключ и в каком языке не совпадает. Файлы в UTF-8, кириллица/иероглифы/диакритика пишутся как есть (не `\uXXXX`). ## Иконки SVG-иконки рисует мейнтейнер — в PR с новыми иконками сначала откройте issue. Технические требования: `docs/08` (спецификация), `docs/10-colors.md` (палитра), предпросмотр — `dotnet run --project tools/IconPreview -- user`.