Что происходит не так в моей реакции на столкновение? ⇐ C#
-
Гость
Что происходит не так в моей реакции на столкновение?
поэтому я работаю над системой реагирования на столкновения, основанной на алгоритме столкновения и скольжения...
только у меня возникла ошибка...
Это код с ошибкой
с использованием System.Collections; использование System.Collections.Generic; использование UnityEngine; [Система.Сериализуемый] Публичный класс CollisionRepsonse { общедоступное плавающее значение RemainingVelocity; общественный RaycastHit CollisonHit; общественный Vector3 CollisionHitLocation; общедоступный Vector3 OutputForce; } общедоступный класс NewBehaviourScript: MonoBehaviour { общественный Vector3 CurrentInputDir; общедоступное плавающее значение BaseVelocity = 5f; [SerializeField] List CollisionHits; RaycastHit InitialCollisonHit; bool FirstCollisionHit; общественный интервал я = 0; недействительное обновление() { if(Physics.CapsuleCast(transform.position, Transform.position, 0.5f, CurrentInputDir, out InitialCollisonHit, BaseVelocity)) { если (CollisionHits.Count == 0f) { FirstCollisionHit = правда; } если (FirstCollisionHit) { CollisionHits.Add(новый CollisionRepsonse{}); FirstCollisionHit = ложь; } если(CollisionHits.Count!= 0f) { Функция ответа на столкновение(); } void CollisionResponseFunction() { foreach (CollisionRepsonse CollisionRepsonse в CollisionHits) { если (я == 0) { CollisionHits.CollisionHitLocation = InitialCollisonHit.point; CollisionHits.RemainingVelocity = BaseVelocity - Vector3.Distance(transform.position, CollisionHits.CollisionHitLocation); CollisionHits.OutputForce = Vector3.ProjectOnPlane(CurrentInputDir, InitialCollisonHit.normal); } еще { //CollisionHits.CollisionHitLocation = CollisionHits.CollisonHit.point; //CollisionHits.RemainingVelocity = CollisionHits.RemainingVelocity - Vector3.Distance(CollisionHits.CollisionHitLocation, CollisionHits.CollisionHitLocation); //CollisionHits[i].OutputForce = Vector3.ProjectOnPlane(CollisionHits[i - 1].OutputForce, CollisionHits[i - 1].CollisonHit.normal); } if(CollisionHits[i].RemainingVelocity > 0f) { CollisionHits.Add(новый CollisionRepsonse{}); я++; } } } } } } Я получаю следующую ошибку.
InvalidOperationException: коллекция была изменена; операция перечисления может не выполниться. System.Collections.Generic.List1+Enumerator[T].MoveNextRare() (at :0) System.Collections.Generic.List1+Enumerator[T].MoveNext() ( в :0) NewBehaviourScript.g__CollisionResponseFunction|6_0 () (в Assets/Scripts/NewBehaviourScript.cs:46) NewBehaviourScript.Update () (в Assets/Scripts/NewBehaviourScript.cs:41)
но как только я изменю код на этот.
с использованием System.Collections; использование System.Collections.Generic; использование UnityEngine; [Система.Сериализуемый] Публичный класс CollisionRepsonse { общедоступное плавающее значение RemainingVelocity; общественный RaycastHit CollisonHit; общественный Vector3 CollisionHitLocation; общедоступный Vector3 OutputForce; } общедоступный класс NewBehaviourScript: MonoBehaviour { общественный Vector3 CurrentInputDir; общедоступное плавающее значение BaseVelocity = 5f; [SerializeField] List CollisionHits; RaycastHit InitialCollisonHit; bool FirstCollisionHit; общественный интервал я = 0; недействительное обновление() { if(Physics.CapsuleCast(transform.position, Transform.position, 0.5f, CurrentInputDir, out InitialCollisonHit, BaseVelocity)) { если (CollisionHits.Count == 0f) { FirstCollisionHit = правда; } если (FirstCollisionHit) { CollisionHits.Add(новый CollisionRepsonse{}); FirstCollisionHit = ложь; } если(CollisionHits.Count!= 0f) { Функция ответа на столкновение(); } void CollisionResponseFunction() { foreach (CollisionRepsonse CollisionRepsonse в CollisionHits) { if(CollisionHits[i].RemainingVelocity > 0f) { CollisionHits.Add(новый CollisionRepsonse{}); я++; } } } } } } все в порядке...
Итак, как только я добавлю эту строку.
if(i == 0) { CollisionHits[i].CollisionHitLocation = InitialCollisonHit.point; CollisionHits[i].RemainingVelocity = BaseVelocity - Vector3.Distance(transform.position, CollisionHits[i].CollisionHitLocation); CollisionHits[i].OutputForce = Vector3.ProjectOnPlane(CurrentInputDir, InitialCollisonHit.normal); } в цикле foreach выдается ошибка, говорящая, что коллекция была изменена... конечно, значение в классе изменено... но в том-то и дело, что я бы хранил там данные, но это не имеет ничего общего с в любом случае счетчик в цикле foreach... просто со значениями в нем... я обязательно увеличиваю целое число и число списков вместе, чтобы избежать этой проблемы... и я обязательно рассчитываю назад, а не вперед... так что Я перепробовал все, но смог найти проблему. Я ожидал, что все будет работать нормально, так как не могу найти ошибку в своих расчетах... но когда я удаляю вышеупомянутую часть кода (которая не должна мешать циклу foreach)... кажется, это работает.
поэтому я работаю над системой реагирования на столкновения, основанной на алгоритме столкновения и скольжения...
только у меня возникла ошибка...
Это код с ошибкой
с использованием System.Collections; использование System.Collections.Generic; использование UnityEngine; [Система.Сериализуемый] Публичный класс CollisionRepsonse { общедоступное плавающее значение RemainingVelocity; общественный RaycastHit CollisonHit; общественный Vector3 CollisionHitLocation; общедоступный Vector3 OutputForce; } общедоступный класс NewBehaviourScript: MonoBehaviour { общественный Vector3 CurrentInputDir; общедоступное плавающее значение BaseVelocity = 5f; [SerializeField] List CollisionHits; RaycastHit InitialCollisonHit; bool FirstCollisionHit; общественный интервал я = 0; недействительное обновление() { if(Physics.CapsuleCast(transform.position, Transform.position, 0.5f, CurrentInputDir, out InitialCollisonHit, BaseVelocity)) { если (CollisionHits.Count == 0f) { FirstCollisionHit = правда; } если (FirstCollisionHit) { CollisionHits.Add(новый CollisionRepsonse{}); FirstCollisionHit = ложь; } если(CollisionHits.Count!= 0f) { Функция ответа на столкновение(); } void CollisionResponseFunction() { foreach (CollisionRepsonse CollisionRepsonse в CollisionHits) { если (я == 0) { CollisionHits.CollisionHitLocation = InitialCollisonHit.point; CollisionHits.RemainingVelocity = BaseVelocity - Vector3.Distance(transform.position, CollisionHits.CollisionHitLocation); CollisionHits.OutputForce = Vector3.ProjectOnPlane(CurrentInputDir, InitialCollisonHit.normal); } еще { //CollisionHits.CollisionHitLocation = CollisionHits.CollisonHit.point; //CollisionHits.RemainingVelocity = CollisionHits.RemainingVelocity - Vector3.Distance(CollisionHits.CollisionHitLocation, CollisionHits.CollisionHitLocation); //CollisionHits[i].OutputForce = Vector3.ProjectOnPlane(CollisionHits[i - 1].OutputForce, CollisionHits[i - 1].CollisonHit.normal); } if(CollisionHits[i].RemainingVelocity > 0f) { CollisionHits.Add(новый CollisionRepsonse{}); я++; } } } } } } Я получаю следующую ошибку.
InvalidOperationException: коллекция была изменена; операция перечисления может не выполниться. System.Collections.Generic.List1+Enumerator[T].MoveNextRare() (at :0) System.Collections.Generic.List1+Enumerator[T].MoveNext() ( в :0) NewBehaviourScript.g__CollisionResponseFunction|6_0 () (в Assets/Scripts/NewBehaviourScript.cs:46) NewBehaviourScript.Update () (в Assets/Scripts/NewBehaviourScript.cs:41)
но как только я изменю код на этот.
с использованием System.Collections; использование System.Collections.Generic; использование UnityEngine; [Система.Сериализуемый] Публичный класс CollisionRepsonse { общедоступное плавающее значение RemainingVelocity; общественный RaycastHit CollisonHit; общественный Vector3 CollisionHitLocation; общедоступный Vector3 OutputForce; } общедоступный класс NewBehaviourScript: MonoBehaviour { общественный Vector3 CurrentInputDir; общедоступное плавающее значение BaseVelocity = 5f; [SerializeField] List CollisionHits; RaycastHit InitialCollisonHit; bool FirstCollisionHit; общественный интервал я = 0; недействительное обновление() { if(Physics.CapsuleCast(transform.position, Transform.position, 0.5f, CurrentInputDir, out InitialCollisonHit, BaseVelocity)) { если (CollisionHits.Count == 0f) { FirstCollisionHit = правда; } если (FirstCollisionHit) { CollisionHits.Add(новый CollisionRepsonse{}); FirstCollisionHit = ложь; } если(CollisionHits.Count!= 0f) { Функция ответа на столкновение(); } void CollisionResponseFunction() { foreach (CollisionRepsonse CollisionRepsonse в CollisionHits) { if(CollisionHits[i].RemainingVelocity > 0f) { CollisionHits.Add(новый CollisionRepsonse{}); я++; } } } } } } все в порядке...
Итак, как только я добавлю эту строку.
if(i == 0) { CollisionHits[i].CollisionHitLocation = InitialCollisonHit.point; CollisionHits[i].RemainingVelocity = BaseVelocity - Vector3.Distance(transform.position, CollisionHits[i].CollisionHitLocation); CollisionHits[i].OutputForce = Vector3.ProjectOnPlane(CurrentInputDir, InitialCollisonHit.normal); } в цикле foreach выдается ошибка, говорящая, что коллекция была изменена... конечно, значение в классе изменено... но в том-то и дело, что я бы хранил там данные, но это не имеет ничего общего с в любом случае счетчик в цикле foreach... просто со значениями в нем... я обязательно увеличиваю целое число и число списков вместе, чтобы избежать этой проблемы... и я обязательно рассчитываю назад, а не вперед... так что Я перепробовал все, но смог найти проблему. Я ожидал, что все будет работать нормально, так как не могу найти ошибку в своих расчетах... но когда я удаляю вышеупомянутую часть кода (которая не должна мешать циклу foreach)... кажется, это работает.
Мобильная версия