[RESOLU][DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Pour les scripts écrits en C#
Règles du forum
Merci de respecter la NOMENCLATURE suivante pour vos TITRES de messages :

Commencez par le niveau de vos scripts
DB = Débutant
MY = Moyen
CF = Confirmé

Puis le domaine d'application
-RS = Réseau
-AL = Algorithmie

Exemple :

[DB-RS] Mouvement perso multijoueur
Darym
Messages : 5
Inscription : 31 Mai 2019 14:22

[RESOLU][DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Darym » 31 Mai 2019 14:34

Bonjour!

Nouveau sur ce forum je commence à écrire ici car j'ai un soucis qui me bloque...

J'essaye de faire un petit Tower Defense un peu différent: Mes IA sont des visiteurs de musée qui doivent visiter un musée et admirer les œuvres.
L'idée étant que le joueur va créer le tracé du musée (en créant des couloirs) et en plaçant des œuvres. Avant de voir arriver des vagues de touristes (mes IA) pour visiter ce musée.
Évidemment les œuvres sont des objectifs pour l'IA, qui doit aller vers l'objectif le plus proche puis se diriger vers la suivante.
Une fois toutes les œuvres visités, l'IA se dirige vers la sortie.
Mais tout ce petit GD est gêné par un souci,
Si mon IA recense bien tous les objets ayant le tag "Objectif" dans une liste, lorsque je veux supprimer l'objectif atteint de la liste, le script enlève TOUS les composant de la liste. Rendant mon IA immobile (ou se dirigeant vers un objectif qui n'est pas le plus proche avant de s’arrêter)

Pouvez-vous m'aider à comprendre quel est le problème?
Voici une image de ma scène:
Screen_MR.PNG
Screen_MR.PNG (232.99 Kio) Consulté 4977 fois
Et voici mon script à l'heure actuelle:

_________________________________________________________________________

Code : Tout sélectionner

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;

public class AI_Test_Interest_New : MonoBehaviour
{
    private Vector3 targetPosition; // Vector pour diriger l'IA vers le point le plus proche

    private NavMeshAgent directionNavAgent;

    public List<GameObject> Targets;//liste d'objectif

    public GameObject closest; //Censé être la cible la plus proche

    public GameObject Actual; //Censé être la cible atteinte par l'IA

    public bool TargetGet = false; // Pour savoir si l'IA a touché le trigger de l'objectif.

    public bool Atteint = false; // Bool secondaire sans doute inutile pour savoir si l'IA a atteint l'objectif et est prêt à repartir vers l'objectif suivant apres avoir retiré l'objectif attein précedemment.

    void Start()
    {
        FindTargets(); // charge toutes les entité avec le tag objectif dans la liste dés le départ
    }
    void Update()
    {
        MoveToClosest(); // placé dans le update pour le moment pour pousser un dplacement constant
        if (TargetGet == true)
        {
            ChangeTarget();
            //BUT : retirer l'objet actuel de la liste pour le remplacer par le secon plus proche.
            //QUESTION : desactiver le collider pour eviter qu'il prenne d'emblée le script ontriggerenter?

        }
        if (Atteint == true)
        {
            FindClosestTarget(); // une fois le changement fait, retrouve la cible la plus proche
            Debug.Log("change");
           
        }
    }
    void MoveToClosest() // Pour se deplacer vers la cible la plus proche
    {
        directionNavAgent = GetComponent<NavMeshAgent>();
        FindClosestTarget();
        directionNavAgent.destination = targetPosition;

    }
    void OnTriggerEnter(Collider other) // Active le bool TargetGet
    {
        if (other.tag == "Objectif")
        {
            Debug.Log("Pouti");
            TargetGet = true;

        }
    }
    void FindTargets() // Trouve les objets ayant le tag "Objectif"
    {
        Targets = new List<GameObject>();
        foreach (GameObject go in GameObject.FindGameObjectsWithTag("Objectif"))
        {
            Targets.Add(go);
        }
        //Targets.Add(GameObject.FindGameObjectWithTag("Objectif"));


    }
    void ChangeTarget() // Enleve la Target la plus proche pour la remplacer par la suivante.
    {
        float distance = Mathf.Infinity;
        Vector3 Position = transform.position;


        foreach (GameObject go in Targets) // reprend le code du FindTarget, car au moment ou le script est lancé le plus proche est forcemment celui à retirer de la liste
        {

            Vector3 diff = go.transform.position - Position;
            float curDistance = diff.sqrMagnitude;
            if (curDistance < distance)
            {
                Actual = go;
                Targets.Remove(Actual);
                //Targets.Remove(Actual);
                Atteint = true;
            }
            

        }

        
        Debug.Log("Removed");
       
    }
    void FindClosestTarget() // Trouve la cible la plus proche
    {
        float distance = Mathf.Infinity;
        Vector3 Position = transform.position;
        int i = (Targets.Count);
        Debug.Log(i);

        foreach (GameObject go in Targets)
        {

            Vector3 diff = go.transform.position - Position;
            float curDistance = diff.sqrMagnitude;
            if (curDistance < distance)
            {
                closest = go;
                distance = curDistance;
                targetPosition = closest.transform.position;
            }
           
        }

        return;
    }
    }
Dernière édition par Darym le 31 Mai 2019 21:41, édité 1 fois.

Avatar de l’utilisateur
Max
Messages : 8764
Inscription : 30 Juil 2011 13:57
Contact :

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Max » 31 Mai 2019 17:57

Hello,

Je ne comprends pas trop ta logique.
Tu as un Navmeshagent, auquel tu assignes un objectif ( MoveToClosest). Mais pour savoir si l'objectif est atteint, tu parcours l'ensemble des targets pour trouver la cible la plus proche. C'est volontaire ? Pourquoi ne pas faire une simple comparaison juste entre le Navmeshagent et le target courant ?
Image
Pas d'aide par MP, le forum est là pour ça.
En cas de doute sur les bonnes pratiques à adopter sur le forum, consulter la Charte et sa FAQ

Darym
Messages : 5
Inscription : 31 Mai 2019 14:22

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Darym » 31 Mai 2019 18:17

Ma logique n'est peut être pas bonne de base...

Comme le joueur pose lui même autant d'objectif que l'on veut, l'IA doit checker ce qu'il y a encore comme objectif:

IA check les objectifs existant et les place dans une liste
IA se dirige vers Objectif le plus proche (A)
IA Atteint Objectif A
IA Retire Objectif A de sa liste et se dirige vers le nouvel Objectif le plus proche (B)
IA Atteint Objectif B
IA Retire Objectif B de sa liste et se dirige vers le nouvel Objectif le plus proche (C)
...

Si le compteur de la liste atteint 0, l'IA se dirige vers un nouvel objectif "Sortie"

J'avoue que je ne connais pas enormément le navmesh agent =/ ni trop les listes...
Du coup c'est pour ça que je suis un peu perdu....

Avatar de l’utilisateur
Max
Messages : 8764
Inscription : 30 Juil 2011 13:57
Contact :

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Max » 31 Mai 2019 18:42

Darym a écrit :
31 Mai 2019 18:17
IA check les objectifs existant et les place dans une liste
IA se dirige vers Objectif le plus proche (A)
IA Atteint Objectif A
IA Retire Objectif A de sa liste et se dirige vers le nouvel Objectif le plus proche (B)
IA Atteint Objectif B
IA Retire Objectif B de sa liste et se dirige vers le nouvel Objectif le plus proche (C)
ça ok, là la logique est plutôt clair et classique.Le soucis je pense est dans la mise en œuvre niveau code.
Là où je tique un peu, c'est dans ta façon de chercher à savoir quand ton IA atteint un objectif.
Perso, pour tester si mon IA atteint le target désigné, je pars sur une simple comparaison de la position courante de l'IA et la position du target. Si cette distance les séparant descend sous une certaine valeur, alors on peut considérer le target atteint, on le supprime de la liste des objectifs, puis on assigne le target (objectif) suivant à l'IA.
Une autre technique pour détecter un but sur un target, est celle qui consiste à passer par des triggers sur chaque objectif. Quand l'IA rentre dedans, alors objectif est atteint, on passe au suivant.
Image
Pas d'aide par MP, le forum est là pour ça.
En cas de doute sur les bonnes pratiques à adopter sur le forum, consulter la Charte et sa FAQ

Darym
Messages : 5
Inscription : 31 Mai 2019 14:22

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Darym » 31 Mai 2019 18:48

La actuellement je fais fonctionner par un trigger, ce trigger declenche le retrait de l'objectif ("closest" dans mon code) sauf que....
Comme ma liste est publique je m'en rend compte trés rapidement, le retrait de closest retire TOUS les éléments de ma liste, et du coup mon ia n'avance plus...
L'idée est assez simple (enfin je pense) mais je pêche complètement dans son exécution...
Avez-vous une idée pour que ça ne retire qu'un seul élément de la liste?

Avatar de l’utilisateur
Max
Messages : 8764
Inscription : 30 Juil 2011 13:57
Contact :

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Max » 31 Mai 2019 19:05

Si on reprend ton code, dans la méthode ChangeTarget(), tu "Remove" les go dont la distance courante est inférieure à la valeur distance... qui est elle égale à l'infini. Donc forcément, tout tes targets sont supprimés...
Image
Pas d'aide par MP, le forum est là pour ça.
En cas de doute sur les bonnes pratiques à adopter sur le forum, consulter la Charte et sa FAQ

Darym
Messages : 5
Inscription : 31 Mai 2019 14:22

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Darym » 31 Mai 2019 21:01

Bon sang que je suis ***...
j'ai juste mis un float égal à 2.0 et ça a fonctionné XD
Mille merci! ça m'a vraiment aidé!
Merci pour ton aide et t patience!!!!

Avatar de l’utilisateur
Max
Messages : 8764
Inscription : 30 Juil 2011 13:57
Contact :

Re: [DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Max » 31 Mai 2019 21:10

Pas de soucis, passe ton sujet en [RESOLU] et se sera top ;)
Image
Pas d'aide par MP, le forum est là pour ça.
En cas de doute sur les bonnes pratiques à adopter sur le forum, consulter la Charte et sa FAQ

Darym
Messages : 5
Inscription : 31 Mai 2019 14:22

Re: [Résolu][DB - AL] Faire une IA qui va d'un point à un autre sans destruction

Message par Darym » 31 Mai 2019 21:42

Fait. ^^ Merci encore!

Répondre

Revenir vers « (C#) CSharp »