Всем вечер добрый. При решении задачи по созданию области видимости для объекта и обнаружения самого близкого к объекту в поле зрения у меня возникли некие затруднения в оптимизации. Просьба, кто хорошо ладит с Unity в C# помогите пожалуйста.
Итак, вот описание задачи с моей точки зрения в Unity-C#: У нас объект, которым мы управляем и у него есть дочерний пустой объект, который имеет 4 компонента (Transform, Rigidbody, Sphere Collider и скрипт Detector) в Sphere Collider – Is Trigger = true. Далее в скрипте Detector в событии OnTriggerEnter я добавляю объект в список объектов при вхождении в поле коллайдера, в событии OnTriggerStay я нахожу среди всех объект, которые находятся в поле коллайдера самый ближайший к моему объекту и записываю имя, далее через метод Find класса GameObject я нахожу по имени этот самый объект и меняю цвет материала на зелёный, чтобы игрок знал на какой объект он нацелен, но вот дальше пока-что решить эту подзадачу, которая выделена мне не удалось (
когда мы поменяли цвет объекта на зелёный, то надо вернуть его первоначальный цвет если объект стал не самым ближайшим), а когда объект выходит из коллайдера, то я его удаляю из списка всех объектов.
Помогите мне решить эту подзадачу (когда мы поменяли цвет объекта на зелёный, то надо вернуть его первоначальный цвет если объект стал не самым ближайшим).
Если есть идеи по оптимизации этой всей задачи, то буду очень рад.
Спасибо, что уделили время.
Код скрипта Detector
/// <summary>
/// Список объектов в поле зрения
/// </summary>
private List<GameObject> visibleObject = new List<GameObject>();
/// <summary>
/// Старое и новое расстояние
/// </summary>
private float Next = 0, Old = 0;
/// <summary>
/// Имя объекта
/// </summary>
public static string nameObj = "";
/// <summary>
/// Вошёл в поле зрения
/// </summary>
/// <param name="other"></param>
private void OnTriggerEnter(Collider other)
{
if ((!other.name.Equals(Connect.NamePlayer)) && (!other.name.Equals("Terrain")) /*&& (!other.name.Contains("object"))*/) // если не равно нашему имени и имени объекта и поля
{
GameObject tempObject = other.gameObject; // инициализируем новый объект
if ((visibleObject.Find(n => !n.name.Equals(tempObject.name))) || (visibleObject.Count == 0)) // если такого объекта нет в списке или список пуст
{
visibleObject.Add(tempObject); // добавляем в список объект который находится в поле зрения
}
}
}
/// <summary>
/// Находится в поле зрения
/// </summary>
/// <param name="other"></param>
private void OnTriggerStay(Collider other)
{
if ((!other.name.Equals(Connect.NamePlayer)) && (!other.name.Equals("Terrain")) /*&& (!other.name.Contains("object"))*/) // если не равно нашему имени и имени объекта и поля
{
Old = (int)Math.Sqrt(Math.Pow((visibleObject[0].transform.position.x - transform.position.x), 2) + Math.Pow((visibleObject[0].transform.position.z - transform.position.z), 2)); // нахождение расстояния между указателем мыши и персонажем
foreach (GameObject obj in visibleObject)
{
Next = (int)Math.Sqrt(Math.Pow((obj.transform.position.x - transform.position.x), 2) + Math.Pow((obj.transform.position.z - transform.position.z), 2)); // нахождение расстояния между указателем мыши и персонажем
DebugConsole.Log(Next + " " + visibleObject.Count);
if (Next < Old || visibleObject.Count == 1) // если следующее расстояние меньше чем старое
{
Old = Next;
nameObj = obj.name;
}
}
GameObject.Find(nameObj).GetComponent<Renderer>().sharedMaterial.SetColor("_EmissionColor", Color.green);
}
}
/// <summary>
/// Вышел из поле зрения
/// </summary>
/// <param name="other"></param>
private void OnTriggerExit(Collider other)
{
visibleObject.Remove(visibleObject.Find(n => n.name == other.name)); // удаляем из списка объект который вышел из поля зрения
}