forum.boolean.name

forum.boolean.name (http://forum.boolean.name/index.php)
-   Общие вопросы (http://forum.boolean.name/forumdisplay.php?f=166)
-   -   Поиск ближайшего объекта по тэгу. Вопрос. (http://forum.boolean.name/showthread.php?t=15097)

Fockerian 10.07.2011 17:29

Поиск ближайшего объекта по тэгу. Вопрос.
 
Нужна помощь.



Код:

using UnityEngine;
using System.Collections;

public class example : MonoBehaviour {
GameObject FindClosestEnemy() {
GameObject[] gos;
gos = GameObject.FindGameObjectsWithTag("Enemy");
GameObject closest;
float distance = Mathf.Infinity;
Vector3 position = transform.position;
foreach (GameObject go in gos) {
Vector3 diff = go.transform.position - position;
float curDistance = diff.sqrMagnitude;
if (curDistance < distance) {
closest = go;
distance = curDistance;
}
}
return closest;
}
void Awake() {
print(FindClosestEnemy().name);
}
}

Вот есть несколько объектов с тэгов врага, необходимо найти из этих объектов самый ближайший. На юнити.ком нашел в скриптах пример который помойму мне и нужен ( он как раз выше ) , но загрузив его себе юнитти стала ругаться. Ругается на return closest; ... Вот я не могу исправить и понять почему ругается. Если выносить GameObject closest за пределы GameObject FindClosestEnemy() { ...} юнити не ругается но опять же найдя единственный близкий больше не чего не ищет, как бы близко я не перемещался к другим объектам с тэгом враг. Как подлатать скрипт?

Lestar 10.07.2011 18:21

Ответ: Поиск ближайшего объекта по тэгу. Вопрос.
 
Скопируйте ошибку из консоли и покажите в коде,как вы применяете метод FindClosestEnemy.Чтобы искал постоянно ближайший,нужно в Update искать.И по хорошим делам переписать,чтобы в Update не искать обьекты по тэгу.

Например так

PHP код:

using UnityEngine;
using System.Collections;

public class 
example MonoBehaviour
{
    
GameObject[] gos;
    
GameObject closest;

    
void Start()
    {
        
gos GameObject.FindGameObjectsWithTag("Enemy");
    }

    
GameObject FindClosestEnemy()
    {            
        
float distance Mathf.Infinity;
        
Vector3 position transform.position;
        foreach (
GameObject go in gos)
        {
            
Vector3 diff go.transform.position position;
            
float curDistance diff.sqrMagnitude;
            if (
curDistance distance)
            {
                
closest go;
                
distance curDistance;
            }
        }
        return 
closest;
    }
    
void Update()
    {
        print(
FindClosestEnemy().name);
    }


Мой пример подходит,если у вас количество элеметнов массива gos неизменно.Вывод print в каждом фрейме существенно садит fps.Будте к этому готовы.

P.S. Ну и в добавок я предпочитаю использовать вместо
PHP код:

Vector3 diff go.transform.position position;
 
float curDistance diff.sqrMagnitude

в таком виде
PHP код:

float curDistance=Vector3.Distance(go.transform.position,position


Fockerian 10.07.2011 20:01

Ответ: Поиск ближайшего объекта по тэгу. Вопрос.
 
Спасибо большое за помощь и разъяснение, все работает на ура.
У меня пока колличество gos ограниченно, но в далеком будущем будет увеличиваться и уменьшаться. (враги будут респится). Чтобы это реализовать надо будет это все переписать в update?

И еще вопрос. Как сделать так чтобы команда Print обновлялась? а то скажем значение которое оно выводит ( в консоли) указывается только один раз. Грубо говоря у меня есть два объекта с именами, подъезжаю к одному имя пишется в консоли, подъезжаю ко второму пишится имя второго, возвращаясь к первому имя все также остается второго, но если я очищу консоль кнопкой "clear" то имя обновится на имя первого.

Lestar 10.07.2011 22:52

Ответ: Поиск ближайшего объекта по тэгу. Вопрос.
 
Цитата:

Сообщение от Fockerian (Сообщение 194983)
Чтобы это реализовать надо будет это все переписать в update?

Да,после каждого дестроя обьекта или его инстанса нужно будет очищать массив и искать все обьекты с тегом заново,но единоразово.То есть запускать например корутину,которая будет отвечать за очистку массива и его заполнение.Ну и в случае с непостоянным размером коллекции,использовать List<>,а не массив.
Цитата:

Сообщение от Fockerian (Сообщение 194983)
И еще вопрос. Как сделать так чтобы команда Print обновлялась? а то скажем значение которое оно выводит ( в консоли) указывается только один раз. Грубо говоря у меня есть два объекта с именами, подъезжаю к одному имя пишется в консоли, подъезжаю ко второму пишится имя второго, возвращаясь к первому имя все также остается второго, но если я очищу консоль кнопкой "clear" то имя обновится на имя первого.

Кнопка Collapse в консоли отвечает за отображение повторяющихся сообщений ,выводите через Debug.Log().

Fockerian 11.07.2011 13:38

Ответ: Поиск ближайшего объекта по тэгу. Вопрос.
 
Спасибо большое, вы мне очень помогли.
У меня созрел один вопрос давным давно, но найти ответа так до сих пор и не смог. Есть два значения, нужно чтобы одно значение переросло в другое.
Х=Х+10 или -10 не идет, по скольку у меня эти значение углы поворота башни, если так прописать то будет проскакиваться нужный угол, и башня будет поворачиватсья в обратку. Начнет дергаться. Если задать условие в котором будет сказано, если угол до цели меньше 5 градусов то угол башни равен углу цели то при поворое башни к цели она тоже дерганется и встанет как нужно, да и строк слишком много в скрипте, а как я понял надо экономить на всем. В общем есть же какаято команда которая с заданым шагом приращает значение из одного в другое независимо от того больше значение или меньше?

Fockerian 11.07.2011 21:25

Ответ: Поиск ближайшего объекта по тэгу. Вопрос.
 
Вопрос с поворотом башни решил через :
Код:

transform.rotation = Quaternion.Slerp (transform.rotation, Quaternion.LookRotation(direction), rotationSpeed * Time.deltaTime);
                transform.eulerAngles = new Vector3(0, transform.eulerAngles.y, 0);

вопрос собственно говоря снят.


Часовой пояс GMT +4, время: 13:42.

vBulletin® Version 3.6.5.
Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
Перевод: zCarot