const Orientation = Object.freeze({ HAUT: Symbol("haut"), BAS: Symbol("bas"), GAUCHE: Symbol("gauche"), DROITE: Symbol("droite") }); class Noeud { coordX; coordY; chemins; constructor(coordX, coordY){ this.coordX = coordX; this.coordY = coordY; chemins = new Array(); } addCheminPossible(chemin){ this.chemins.push(chemin); } getCheminsPossibles(){ return this.chemins; } toString(){ log.console("node : (" + currentNode.getX + "; " + currentNode.getY + ")"); } toStringWithVoisins(){ log.console("node : (" + currentNode.getX + "; " + currentNode.getY + ")"); log.console("voisins connus : " + this.chemins.forEach((chemin) => chemin.toString())); } } class ModeAutomatique { cheminsPossibles = new Array(); // liste des listes de noeuds noeudsVisites = new Array(); // valeurs pour la première position posX=0; posY=0; rotation=HAUT; run(){ while(isObjectifTrouve()){ currentNode = getCaseAnalysee(); this.analyseEnvironnement(currentNode); // met à jour ses connaissances (à dessiner au fur et à mesure ?) this.deplacer(currentNode); // récupère un chemin non encore parcourus en fonction de ses connaissances } } isObjectifTrouve(){ return false; } //////////////////////////////////////// ANALYSE ENVIRONNEMENT analyseEnvironnement(currentNode){ currentNode.toString(); // SI case déjà visitée, alors on connait ses obstacles if (currentNode == null) { // pour les 4 directions possibles for (let i = 0; i < 4; i++) { if (!isObstacleDevant(currentNode, rotation)){ addCheminPossible(currentNode); } tourne(); // changement de l'angle de 90 degrés } this.noeudsVisites.push(currentNode); } } isObstacleDevant(){ // TODO return true; } tourne(){ if(this.rotation = Orientation.HAUT){ // TODO tourne this.rotation = Orientation.GAUCHE; } else if(this.rotation = Orientation.BAS){ // TODO tourne this.rotation = Orientation.GAUCHE; }else if(this.rotation = Orientation.BAS){ // TODO tourne this.rotation = Orientation.DROITE; }else if(this.rotation = Orientation.DROITE){ // TODO tourne this.rotation = Orientation.HAUT; } } addCheminPossible(){ chemin = new Array(); if(this.rotation = Orientation.HAUT){ chemin.push(new Noeud(posX+1, posY)); } else if(this.rotation = Orientation.BAS){ chemin.push(new Noeud(posX-1, posY)); }else if(this.rotation = Orientation.GAUCHE){ chemin.push(new Noeud(posX, posY-1)); }else if(this.rotation = Orientation.DROITE){ chemin.push(new Noeud(posX, posY+1)); } this.cheminsPossibles.push(chemin); } //////////////////////////////////////// MOVE deplacer(currentNode){ // on choisi le prochain noeud nextNode = getNextNode(); log.console("next node : "); nextNode.toString(); // on met à jour la liste des chemins en ajoutant le noeud courant dans les chemins non choisis updatePaths(nextNode); // on met à jour les coordonnées this.updateCoordonnees(currentNode, nextNode); // move this.move(); } // parcours en profondeur : il s'agit de LIFOs getNextNode(){ if (this.cheminsPossibles[this.cheminsPossibles.length - 1] > 0) { // on récupère la dernière liste cheminChoisi = this.cheminsPossibles[this.cheminsPossibles.length - 1]; // on récupère le dernier élément de cette liste nodeChoisi = cheminChoisi[cheminChoisi.length - 1]; log.console("noeud choisi :"); nodeChoisi.toString(); // on créé un nouveau noeud return new Noeud(nodeChoisi.posX, nodeChoisi.posY); } return null; } updatePaths(nextNode){ nextNode = this.getCaseAnalysee(); // on ajoute le noeud visité à toutes les listes sauf la dernière for (let i=0; i < this.cheminsPossibles -1; i++){ cheminPossible = this.cheminsPossibles[i]; if (nextNode == null){ // on ajoute le noeud en cours à la liste des noeuds visités cheminPossible.push(nextNode); } else { // on vire le noeud visité de toutes les listes s'il a déjà été visité avant (on fait demi tour) cheminPossible.pop(); } } // on supprime les listes vides cheminsPossibles = cheminsPossibles.filter(function (el) { return el.length > 0; }); log.console("nombre de chemins restants : " + this.cheminsPossibles.length) log.console("chemins possibles : " + this.cheminsPossibles) } updateCoordonnees(currentNode, nextNode) { log.console("coordonnees : (" + this.posX + "; " + this.posY + ")"); if (currentNode.getX > nextNode.getX){ this.rotation = Orientation.GAUCHE this.posY--; } else if (currentNode.getX < nextNode.getX){ this.rotation = Orientation.DROITE this.pos++; } else if (currentNode.getY > nextNode.getY){ this.rotation = Orientation.BAS this.posX--; } else { this.rotation = Orientation.HAUT this.posX++; } log.console("new coordonnees : (" + this.posX + "; " + this.posY + ")"); } move(currentNode, nextNode){ // déplacer robot (les coordonnées sont déjà à jour) } /////////////////////////////////////// GETTERS getCaseAnalysee(){ noeudsVisites.forEach((noeud) => { if (noeud.posX == this.posX && noeud.posY == this.posY){ return noeud; } }); return null; } }