Решили: панель интерфейса собирается из двух источников — материал приходит запечённой
процедурной текстурой (9-slice), форма и оправа рисуются вершинами (Painter2D). Фактуры печёт
редакторное окно Alebardium → UI → Bake Panel Textures, оправу рисует контрол PanelFrame.
Почему: плоская заливка читалась схемой, а не предметом («очень скучная форма», «нет рамки вокруг
какой-то»). Разведение по природе: фактура — это шум на площади, её дешевле посчитать один раз и
положить в атлас; кайма и накладки — это геометрия, которая обязана держать РАЗМЕР при любой ширине
панели, а растянутая картинка тянет её вместе с серединой. Отвергнуто: (1) рисовать всё картинкой —
9-slice плывёт на накладках; (2) рисовать всё вершинами — Painter2D не умеет текстурную заливку,
фактуры не будет; (3) filter: custom шейдером поверх — самый гибкий и самый дорогой путь, не нужен,
пока хватает двух первых.
Сказано: «Т.е. да, создавать для UI что-то процедурно - это правильный путь, который часто юзать будем, думаю» и «Да, давай как постоянный тул» (02.08.2026, сессия d2239d53). Выбор материала — «Самое нормальное то 2» (пергамент) и оправы — «Берем 3» (двойная кайма без накладок), 03.08.2026.
Грабли:
- Тема
.tssдержит СВОИ копии импортированных ярусов. После правкиtokens.*.ussобязателен переимпортtheme.ussИGuildmasterRuntimeTheme.tss, иначе часть переменных молча не резолвится: у меня отвалились разом стекло и сериф, при этом старые переменные работали — выглядело как «сломался шрифт», а не как устаревший кэш. Полчаса на диагностику. - Переимпорт UXML на живом play сносит построенное дерево.
UIDocumentпересобираетrootVisualElementиз ассета, а слои строит бутстрап вStart, который уже отработал — экран становится пустым. Ловится дважды за сессию; лечится перезапуском play, а не поиском бага. CustomStyleProperty<float>читает<number>, а не<length>:--gm-frame-width: 2pxмолча не резолвится, нужно2(та же конвенция, что у--gm-slant-width).- Оправа — оверлей, а не контейнер. Контейнер потребовал бы переписать структуру всех экранов; оверлей вешается одной строкой разметки и не трогает фон. Цена — он рисуется ПОВЕРХ содержимого, поэтому годится только для периметра.
- Текстуры импортируются кодом (
ApplyImportSettings): мип-уровни мылят кромку 9-slice, повтор рвёт край, сжатие съедает тонкое зерно. Забытый вручную пункт виден на панели сразу.
Владелец правды: Scripts/EditorTools/UI/PanelTextureBakerWindow.cs,
Scripts/UI/Components/PanelFrame.cs, UI/Theme/components.uss (секции --sheet и __frame),
дизайн-метафора — docs/wiki/gdd/10-vision/ui-visual-language.md.