НАЧАЛО РАБОТЫРЕШЕНИЕ ПРОБЛЕМ
Решение проблем
Для каждой проблемы ниже приведены причина и решение. Если плагин пишет строку в лог, блок показывает строку формата из исходного кода: %s — путь к объекту, %d — число. Предупреждения и ошибки появляются в Output Log под LogCrushform или LogCrushformWheel. Строки Crushform.Stats — это то, что выводит одноимённая команда.
Вмятины
Заголовок раздела «Вмятины»Вмятины не появляются
Заголовок раздела «Вмятины не появляются»Причина. UCFDeformComponent без профиля Crushform (UCFProfile) ничего не делает. Он не строит решётку, пока профиль не задан, и в этом случае не пишет строку в лог. Адаптер автомобиля без заданного Deform Profile использует профиль проекта по умолчанию.
Если профиль задан, но у владельца нет ни одного компонента меша, который может гнуться, компонент остаётся выключенным и пишет:
%s has a profile but no deformable mesh components; Crushform stays offРешение. Создайте Data Asset UCFProfile и задайте его компоненту: в настройках класса по умолчанию или между SpawnActorDeferred и FinishSpawning. О мешах см. разделы ниже.
Меш не получает вмятин, потому что его материал не подключён
Заголовок раздела «Меш не получает вмятин, потому что его материал не подключён»Причина. Меш показывает вмятины только через материал. MF_CF_Deform двигает вершины и поворачивает их нормали, и его нужно подключить к World Position Offset и Normal. Без этого меш не двигается.
Решение. Подключите каждый материал меша, который должен гнуться: MF_CF_Deform — к World Position Offset и Normal, MF_CF_Paint — между вашей краской и входами Base Color, Roughness и Metallic, а Wear Depth и Scratch — от MF_CF_Deform. Из Python unreal.CFContentLibrary.wire_material(material, deform, paint, max_displacement + fold_amplitude) делает всё это сразу.
Некоторые меши не получают вмятин
Заголовок раздела «Некоторые меши не получают вмятин»Причина. Гнутся только Static Mesh и скинированные меши. Instanced Static Mesh не гнутся никогда, потому что все их экземпляры делят один примитив. Дальше работают фильтры профиля Include Tags и Exclude Tags: если Include Tags не пуст, у меша должен быть один из его тегов, а меш с любым тегом из Exclude Tags пропускается.
Решение. Поставьте меш в обычный компонент Static Mesh, а не в Instanced Static Mesh. Сверьте теги компонента меша с Include Tags и Exclude Tags профиля, уберите тег или поменяйте списки. Деталь, которая двигается относительно кузова, нужно исключить; см. раздел «Подвижные детали гнутся неправильно».
Удар слишком слабый для вмятины
Заголовок раздела «Удар слишком слабый для вмятины»Причина. Удар, у которого дельта-v не больше Min Delta V, вмятины не оставляет. По умолчанию это 0,5 м/с. Такой удар всё же может считаться царапиной.
Решение. Уменьшите Min Delta V в профиле, если мелкие удары должны оставлять вмятины. Чтобы проверить более сильным ударом, выполните Crushform.DebugImpact [DeltaV] [Name]: команда бьёт эктор под прицелом со скоростью 10 м/с по умолчанию. Это чит; он есть во всех сборках, кроме Shipping.
У автомобиля нет ни вмятин, ни грязи
Заголовок раздела «У автомобиля нет ни вмятин, ни грязи»Причина. Адаптер автомобиля создаёт свой компонент деформации, только если включён Dirt and Dents. Стеклянные панели и грязь на колёсах тоже ему нужны.
Решение. Включите Dirt and Dents на адаптере.
Вмятины перестают появляться на некоторых повреждённых автомобилях
Заголовок раздела «Вмятины перестают появляться на некоторых повреждённых автомобилях»Причина. У атласа фиксированное число слотов, по умолчанию 128, каждый размером 256x8 текселей. Когда все слоты заняты, повреждённый эктор ждёт свободного слота, а самые дальние от камер своих игроков повреждённые экторы рисуются без вмятин, пока слот не освободится. Crushform.Stats выводит число слотов:
Crushform atlas: %d of %d slots used, %d waiting, %d evictions, %d uploads.Решение. Укажите Atlas (Project Settings › Plugins › Crushform › Atlas) на собственный Render Target в RGBA8 большего размера, до 4096 текселей по стороне. Число слотов равно его размеру, делённому на Slot Width и на Slot Height.
Подвижные детали гнутся неправильно
Заголовок раздела «Подвижные детали гнутся неправильно»Причина. Решётка привязывается к корню в BeginPlay. Меш, который начинает двигаться позже, гнётся в позе, которую имел в BeginPlay. Типичные примеры — двери и рулевое колесо.
Решение. Исключите деталь по тегу, как описано в разделе «Некоторые меши не получают вмятин».
Материалы
Заголовок раздела «Материалы»Материал перестаёт компилироваться после подключения: он уже читает две коллекции параметров
Заголовок раздела «Материал перестаёт компилироваться после подключения: он уже читает две коллекции параметров»Причина. Материал может ссылаться не больше чем на две коллекции параметров материала. Подключение MF_CF_Paint или MF_CF_WheelDirt добавляет коллекцию грязи, поэтому мастер-материал, который уже читает две коллекции, перестаёт компилироваться.
Решение. Освободите место для коллекции грязи до подключения: мастер-материал может ссылаться не больше чем на одну другую коллекцию. Например, перенесите параметры второй коллекции в первую и подключите заново.
Подключение отклонено: материал использует нормаль в мировом пространстве
Заголовок раздела «Подключение отклонено: материал использует нормаль в мировом пространстве»Причина. MF_CF_Deform работает в касательном пространстве. Материал с нормалью в мировом пространстве отклоняется, и подключение оставляет его как был:
WireMaterial: %s takes a world-space normal; MF_CF_Deform works in tangent spaceРешение. Включите у материала тангентную нормаль (опция Tangent Space Normal) и подключите его заново.
Вмятины мерцают у края экрана на Nanite
Заголовок раздела «Вмятины мерцают у края экрана на Nanite»Причина. Nanite отсекает по границам World Position Offset. Если Max World Position Offset Displacement меньше самой глубокой вмятины плюс Fold Amplitude, вмятина у края экрана мерцает. Max Displacement профиля — это максимальное смещение любого узла, и материалы кузова должны использовать именно его.
Решение. Подключите материал заново: при подключении граница увеличивается, если она слишком мала. Или задайте Max World Position Offset Displacement вручную: Max Displacement профиля плюс Fold Amplitude материала.
Skeletal Mesh не получает вмятин
Заголовок раздела «Skeletal Mesh не получает вмятин»Причина. Шейдеры для Skeletal Mesh компилируются, только если материал помечен Used with Skeletal Mesh. Мастер-материалы автомобилей самого плагина помечены этой опцией.
Решение. В Details материала, в разделе Usage, включите Used with Skeletal Mesh.
Грязь и колёса
Заголовок раздела «Грязь и колёса»На кузове нет грязи
Заголовок раздела «На кузове нет грязи»Причина. Кузов покрывается грязью, только если в Project Settings > Plugins > Crushform задан ассет Surfaces. Без него не покрывается ни один кузов. Если ассет задан, но не загружается, лог пишет:
Crushform surfaces %s do not load; bodies stay cleanГрязи также нужен host-объект, который отвечает на вопросы о колёсах: кузов, которому не сообщено ни одного колеса, грязи не получает, а таймер грязи ничего не делает.
Решение. Задайте Surfaces как /Crushform/Surfaces/DA_CF_Surfaces или свою таблицу. Добавьте адаптер автомобиля (или host-объект, который отвечает на вопросы о колёсах). Затем проверьте, что Dirt and Dents включён.
На выделенном сервере нет грязи
Заголовок раздела «На выделенном сервере нет грязи»Причина. Выделенный сервер грязь не рисует, поэтому её там не увидеть. Crushform.Stats сообщает об этом на сервере:
Crushform atlas: none in this process (a dedicated server draws nothing).События грязи OnDirtChanged, OnWashed и OnWheelSurfaceChanged на выделенном сервере никогда не срабатывают.
Решение. Смотрите грязь на клиенте. AddDirt и WashAt меняют грязь только на локальном инстансе, поэтому вызывайте их на каждом инстансе, где результат должен быть виден. Wash — сетевая мойка всего кузова: её вызывают только на авторити, и она моет кузов на каждом инстансе.
Поверхность земли не оставляет грязи
Заголовок раздела «Поверхность земли не оставляет грязи»Причина. Колесо читает строку для физического материала своей поверхности в таблице Surfaces. Материалу без строки достаётся строка Default. Значения Dirt в строке задают, сколько грязи поверхность передаёт кузову, поэтому строка Default с нулевым Dirt не оставляет грязи на любой поверхности, у которой нет собственной строки.
Решение. Назначьте земле один из физических материалов плагина, например /Crushform/Surfaces/PM_CF_Asphalt, или свой. Добавьте для него строку в таблице Surfaces с заданными значениями Dirt.
Колесо не получает грязи, потому что это только кость
Заголовок раздела «Колесо не получает грязи, потому что это только кость»Причина. У колеса, которое есть только кость, нет меша, который можно загрязнить или деформировать, поэтому на нём нет ни грязи, ни деформации шины. Адаптер Chaos берёт имя кости колеса из компонента движения.
Решение. Добавьте колесу меш, чтобы на нём было что загрязнять.
Колёса остаются чистыми
Заголовок раздела «Колёса остаются чистыми»Причина. Материал колеса не проходит через MF_CF_WheelDirt. Материал колеса плагина собран так: Base Color, Roughness и Metallic проходят через MF_CF_WheelDirt.
Решение. Используйте /Crushform/Materials/M_CF_Wheel. Или подключите MF_CF_WheelDirt к Base Color, Roughness и Metallic колеса самостоятельно.
На колесе нет ни вмятин, ни грязи, хотя в его материале есть MF_CF_Deform или MF_CF_Paint
Заголовок раздела «На колесе нет ни вмятин, ни грязи, хотя в его материале есть MF_CF_Deform или MF_CF_Paint»Причина. Адаптер автомобиля никогда не деформирует меш колеса или всё, что прикреплено под ним, потому что колесо поворачивается под решёткой кузова. Поэтому материал кузова (MF_CF_Deform или MF_CF_Paint) на колесе никогда не получает вмятин, а грязь на колесе рисует только MF_CF_WheelDirt.
Решение. Уберите MF_CF_Deform и MF_CF_Paint из материала колеса. Оставьте MF_CF_WheelDirt, а MF_CF_TireDeform — под переключателем Tire Deform. На ободе оставьте Tire Deform выключенным.
Звук и эффекты
Заголовок раздела «Звук и эффекты»Нет звука качения
Заголовок раздела «Нет звука качения»Причина. Звук качения молчит в четырёх случаях:
-
Переключатель Rolling Sound в Project Settings > Plugins > Crushform Wheels выключен.
-
Attenuation пуст. Звук остаётся выключенным, и лог пишет:
%s: no Attenuation in Project Settings > Plugins > Crushform Wheels; the rolling sound stays off -
В строке поверхности нет Rolling Sound. Пустое поле означает тишину, и строка не берёт звук у строки
Default. -
Рядом нет слушателя. Звук играет, только пока слушатель находится в радиусе действия затухания.
Решение. Включите Rolling Sound. Задайте Attenuation как /Crushform/Sounds/SA_CF_TireRolling. Укажите в строке поверхности Rolling Sound, например /Crushform/Sounds/SW_CF_Tire_Asphalt_Loop. Затем встаньте в зоне слышимости.
Мультиплеер
Заголовок раздела «Мультиплеер»Вмятины у игроков отличаются
Заголовок раздела «Вмятины у игроков отличаются»Причина. Для каждого кузова источник удара — один инстанс. По умолчанию это авторити. Инстанс, который не является ни авторити, ни источником удара, собственное столкновение не применяет. Источником удара становится инстанс, который симулирует кузов: именно его отчёт несёт вмятину. Кроме того, сервер отклоняет любой отчёт с ударом сильнее Max Plausible Delta V, по умолчанию 40 м/с.
Решение. В вашем ICFDeformHost сделайте так, чтобы IsCrushformImpactSourceHere отвечал Yes на инстансе, который симулирует кузов. Если ваши удары сильнее Max Plausible Delta V, поднимите лимит, иначе сервер отклонит эти отчёты. Сравните счётчики сети и ударов, которые выводит Crushform.Stats, на сервере и на клиенте.
Консоль и сборки
Заголовок раздела «Консоль и сборки»Консольные команды ничего не делают в собранной игре
Заголовок раздела «Консольные команды ничего не делают в собранной игре»Причина. Все консольные команды Crushform вырезаны из сборок Shipping. Crushform.Debug, Crushform.ShowZones, Crushform.ShowCollision, Crushform.RepairAll и Crushform.DebugImpact — это читы: они есть во всех сборках, кроме Shipping, и в редакторе.
Решение. Проверяйте эти команды в редакторе или в сборке, которая не Shipping. Не опирайтесь на CrushformDebug в коде, который попадает в релиз (см. Установка).
Host-объекты
Заголовок раздела «Host-объекты»Ответ Blueprint-host-объекта не виден в превью
Заголовок раздела «Ответ Blueprint-host-объекта не виден в превью»Причина. Превью в редакторе не выполняет ответы Blueprint-host-объектов. AActor::ProcessEvent пропускает скрипт на экторе, если экторы в его мире не инициализированы, а в превью это как раз так. Поэтому панель Details и редактор зон не видят ответ Blueprint.
Решение. Проверяйте ответ в Play In Editor, где экторы инициализированы.
Второй host-объект заменяет первый
Заголовок раздела «Второй host-объект заменяет первый»Причина. Host-объект хранится отдельно для каждого эктора и каждого интерфейса. Второй host-объект для того же эктора и того же интерфейса заменяет первый, и выводится предупреждение:
Host %s replaces host %s for %s under %sРешение. Оставьте один host-объект на пару «эктор и интерфейс», а ненужную регистрацию удалите.
Host-объект не принимается
Заголовок раздела «Host-объект не принимается»Причина. Объект, который не реализует интерфейс, не принимается. В C++ реестр пишет в лог:
Host %s does not implement %s, so it cannot answer for %sHost, заданный через SetCrushformHost после BeginPlay, тоже не принимается:
%s: SetCrushformHost after BeginPlay is refused; the host is read once, in BeginPlayРешение. В Blueprint откройте Class Settings, нажмите Add в разделе Implemented Interfaces, затем реализуйте функции интерфейса. Вызывайте SetCrushformHost до BeginPlay.
Проверка работы
Заголовок раздела «Проверка работы»- Запустите уровень заново в Play In Editor и воспроизведите проблему.
- Откройте консоль и выполните
Crushform.Stats. Команда выводит занятые слоты атласа, слоты в ожидании и счётчики каждого повреждаемого эктора. Если есть слоты в ожидании, см. раздел «Вмятины перестают появляться на некоторых повреждённых автомобилях». - Выполните
Crushform.Debug 1. Команда рисует повреждённые узлы решётки и недавние удары, так что вы видите, где на кузове появилась вмятина. - Проверьте Output Log на новые строки
LogCrushformиLogCrushformWheel.