org.clipsmonitor.monitor2015.RescueGenMap.java Source code

Java tutorial

Introduction

Here is the source code for org.clipsmonitor.monitor2015.RescueGenMap.java

Source

/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package org.clipsmonitor.monitor2015;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardOpenOption;
import org.clipsmonitor.core.MonitorGenMap;
import java.util.LinkedList;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.clipsmonitor.core.MonitorImages;
import org.clipsmonitor.monitor2015.RescueFacts;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.openide.util.Exceptions;

/*
 * Classe che definisce il concetto di scena all'interno del progetto e tutti i metodi per accedervi e
 * modificarla. Inoltre permette la possibilit di salvare e caricare le mappe per poter essere poi
 * successiviamente utilizzate dal simulatore
 *
 * @author Tobia Giani, Alessandro Basile, Marco Corona
 */
public class RescueGenMap extends MonitorGenMap {

    private static RescueGenMap instance;

    private String loaded; // stato iniziale del robot

    /*
     La classe viene definita singleton 
     */
    public static RescueGenMap getInstance() {
        if (instance == null) {
            instance = new RescueGenMap();
            instance.init();
        }
        return instance;
    }

    private RescueGenMap() {

    }

    @Override
    public void init() {
        this.img = MonitorImages.getInstance();
        this.log = "";
        log("Inizializzazione del Map generator in corso...");
        this.NumCellX = 0;
        this.NumCellY = 0;
        this.MapWidth = 0;
        this.MapHeight = 0;
        this.CellHeight = 0;
        this.CellWidth = 0;
        this.direction = "north";
        this.loaded = "unloaded";
        this.maxduration = 300;
        this.mode = "scene";
        this.personName = "person";
        this.defaulagentcondition = "gate+agent_north_unloaded";
        this.defaultagentposition = new int[2];
        this.defaultagentposition[0] = 3;
        this.defaultagentposition[1] = 2;
        this.agentposition = new int[2];
        this.agentposition[0] = this.defaultagentposition[0];
        this.agentposition[1] = this.defaultagentposition[1];
        this.NumPerson = 0;
        this.Persons = new LinkedList<Person>();
        this.setKeyMap = new String[] { "agent_north_unloaded", "agent_north_loaded", "agent_west_unloaded",
                "agent_west_loaded", "agent_east_unloaded", "agent_east_loaded", "agent_south_unloaded",
                "agent_south_loaded", "gate", "empty", "outdoor", "wall", "debris", "debris_injured" };
        this.setKeyColor = new String[] { "green", "blue", "red", "yellow", "black", "magenta", "orange" };

        this.MaxNumPerson = this.setKeyColor.length;
        log("Map generator inizializzato correttamente");
    }

    /**
     * Inizializzazione della scena eseguita mettendo nel perimetro della scena
     * l'outdoor e riempiendo il resto con le celle empty. Il metodo risulta
     * chiaramente adattato ai vincoli del progetto e a come si dovrebbe
     * presentare di default uno scenario
     *
     * @param scene matrice di stringe che dovr essere riempita
     */

    /**
     * Inizializzazione della scena eseguita mettendo nel perimetro della scena
     * l'outdoor e riempiendo il resto con le celle empty. Il metodo risulta
     * chiaramente adattato ai vincoli del progetto e a come si dovrebbe
     * presentare di default uno scenario
     *
     * @param scene matrice di stringe che dovr essere riempita
     */

    @Override
    public void initScene(String[][] scene) {

        for (int i = 0; i < scene.length; i++) {
            for (int j = 0; j < scene[i].length; j++) {
                if (i == 0 || i == scene.length - 1 || j == 0 || j == scene[0].length - 1) {
                    scene[i][j] = "outdoor";
                } else if (i == 1 || i == scene.length - 2 || j == 1 || j == scene[0].length - 2) {
                    scene[i][j] = "wall";
                } else {

                    scene[i][j] = "empty";
                }
            }
        }

        scene[this.agentposition[0]][this.agentposition[1]] = "gate" + "+" + "agent_" + direction + "_" + loaded;
        this.move = this.clone(scene);
    }

    /**
     * Genera una stringa rappresentante la history da scrivere successivamante
     * su un file di testo Il testo prodotto contiene le informazioni
     * riguardanti l'agente nel suo stato iniziale, la durata massima messa a
     * disposizione dell'agente per eseguire le sue operazioni e l'elenco
     * completo di tutti i path che sono stati definiti per i vari agenti
     *
     * @return la stringa rappresentante la history
     */
    @Override
    public String exportHistory() {
        String history = "";
        history += "(maxduration " + this.maxduration + ") \n\n";
        int[] agentPos = GenMapToMap(this.agentposition);

        // posizione iniziale dell'agente
        history += "(initial_agentposition ( pos-r " + agentPos[0] + ")";
        history += "( pos-c " + agentPos[1] + ")";
        history += "(direction " + this.direction + ")) \n\n";

        for (Person elem : Persons) {
            String personName = elem.getColor();
            Path firstPath = getPathByName(personName + "_0");
            StepMove firstMove = firstPath.getMoves().getFirst();
            int[] firstMovePos = GenMapToMap(firstMove.getX(), firstMove.getY());
            int step = firstMove.getStep();
            int r = firstMovePos[0];
            int c = firstMovePos[1];
            history += RescueFacts.PersonStatus.getPersonStatus(personName, step, r, c);
        }
        history += "\n";

        Path[] paths = this.getPaths(-1);

        for (Path elem : paths) {
            String name = elem.getName();
            String person = name.substring(0, name.indexOf("_"));
            name = getNewPathName(name);
            int step = elem.getStartStep() + 1;
            history += RescueFacts.PersonMove.getPersonMove(step, person, name);
        }

        history += "\n";

        for (Path elem : paths) {
            String name = elem.getName();
            String person = name.substring(0, name.indexOf("_"));
            name = getNewPathName(name);
            int step = elem.getStartStep();
            LinkedList<StepMove> slist = elem.getMoves();
            for (StepMove s : slist) {
                int idstep = s.getStep() - step + 1;
                int[] stepPos = GenMapToMap(s.getX(), s.getY());
                history += "( move-path " + name + " " + idstep + " " + person + " " + stepPos[0] + " " + stepPos[1]
                        + " ) \n";

            }

        }

        return history;
    }

    /**
     * Genera il testo contenente i fatti che descrivono una possibile mappa. Il
     * metodo sfrutta un metodo ausiliario getEnvCell per costruire le stringhe
     * dei fatti che descrivono le varie celle
     *
     * @return la stringa con la descrizione di tutte le celle da salvare su un
     * file di testo
     */
    @Override
    public String exportScene() {

        //variabili per impostare la posizione delle componenti
        String s = "";

        for (int i = 0; i < scene.length; i++) {
            for (int j = 0; j < scene[i].length; j++) {
                int[] realCellPos = GenMapToMap(i, j);
                boolean testInjured = scene[i][j].contains("injured");
                s += RescueFacts.RealCell.getRealCell(realCellPos[0], realCellPos[1], scene[i][j], testInjured);
            }
        }
        return s;
    }

    /**
     * Verifica se la posizione dell'agente richiesta risulta essere compatibile
     * rispetto ai vincoli del progetto. Ritorna true se la condizione 
     * rispettata
     *
     * @param mapPos stringa da valutare come effettivamente valida
     * @return true se risulta una posizione valida per il robot, false
     * altrimenti
     */
    @Override
    public boolean RobotPositionIsValid(String mapPos) {

        return !mapPos.contains("debris") && !mapPos.contains("wall") && !mapPos.contains("outdoor");

    }

    /*
     *  Verifica se la posizione dell'agente richiesta risulta essere compatibile
     *  rispetto ai vincoli del progetto. Ritorna true se la condizione  rispettata
     */
    @Override
    public boolean PersonPositionIsValid(String mapPos) {

        return !mapPos.contains("debris") && !mapPos.contains("wall");

    }

    /**
     * Setta tutti i paramentri del modello relativi al robot, la sua posizione
     * e eventualmente se risulta essere carico o scarico
     *
     * @param state stringa rappresentante il robot
     * @param x riga della cella
     * @param y colonna della cella
     */
    @Override
    public void SetRobotParams(String state, int x, int y) {

        this.agentposition[0] = x;
        this.agentposition[1] = y;

        String[] params = state.split("_");
        String AgentDirection = params[1];
        String AgentLoaded = params[2];

        this.direction = AgentDirection;
        this.loaded = AgentLoaded;

    }

    /**
     * Metodo per la creazione della matrice di icone da disegnare sulla mappa
     * del generatore quando questo  impostato in modalit scene.Il metodo si occupa 
     * di creare le icone con l'overlap.
     *
     * @return la matrice di icone da disegnare sul pannello
     */

    public boolean getEmptyPerson() {

        return this.Persons.isEmpty();
    }

    public void error(String message) {
        this.AppendLogMessage(message, "error");
    }

    public void log(String message) {
        this.AppendLogMessage(message, "log");
    }

    public void clear() {
        instance = null;
    }

    public int[] GetJsonMapDimension(File jsonMap) {

        try {
            //converto il file in un oggetto JSON
            FileReader jsonreader = new FileReader(jsonMap);
            char[] chars = new char[(int) jsonMap.length()];
            jsonreader.read(chars);
            String jsonstring = new String(chars);
            jsonreader.close();
            JSONObject json = new JSONObject(jsonstring);
            //leggo il numero di celle dalla radice del JSON

            int NumCellX = Integer.parseInt(json.get("cell_x").toString());
            int NumCellY = Integer.parseInt(json.get("cell_y").toString());

            return new int[] { NumCellX, NumCellY };
        } catch (JSONException ex) {

            AppendLogMessage(ex.getMessage(), "error");
        } catch (IOException ex) {
            AppendLogMessage(ex.getMessage(), "error");
        } catch (NumberFormatException ex) {
            AppendLogMessage(ex.getMessage(), "error");
        }

        return null;
    }

    /**
     * Genera un file Json corrispondente ad uno scenario definito nel file map
     * @param map 
     */

    public void createJsonScene(File map) {
        try {
            BufferedReader mapread = new BufferedReader(new FileReader(map));
            String l = "";
            log(map.getName());
            String regex = "\\s*(\\(real_cell\\s*(\\(pos-r (\\d+)\\))\\s*(\\(pos-c (\\d+)\\))\\s*(\\(contains ([a-z]+)\\))\\s*(\\(injured (yes|no)\\))\\)\\s*)";
            Pattern p = Pattern.compile(regex);
            int maxR = 0;
            int maxC = 0;
            String posR = "";
            String posC = "";
            String contains = "";
            String injured = "";
            String state = "";
            JSONObject Info = new JSONObject();

            while ((l = mapread.readLine()) != null) {
                Matcher m = p.matcher(l);
                boolean match = m.find();
                if (match) {
                    posR = m.group(3);
                    posC = m.group(5);
                    int r = Integer.parseInt(posR);
                    int c = Integer.parseInt(posC);
                    if (maxR < r) {
                        maxR = r;
                    }
                    if (maxC < c) {
                        maxC = c;
                    }

                }
            }

            mapread = new BufferedReader(new FileReader(map));
            Info.put("cell_x", maxC);
            Info.put("cell_y", maxR);
            JSONArray ArrayCells = new JSONArray();

            while ((l = mapread.readLine()) != null) {
                Matcher m = p.matcher(l);
                boolean match = m.find();
                if (match) {
                    posR = m.group(3);
                    posC = m.group(5);
                    contains = m.group(7);
                    injured = m.group(9);
                    int r = Integer.parseInt(posR);
                    int c = Integer.parseInt(posC);
                    JSONObject cell = new JSONObject();
                    int[] GenToMap = this.MapToGenMap(r, c, maxR);

                    cell.put("x", GenToMap[0]);
                    cell.put("y", GenToMap[1]);
                    state = contains;
                    if (contains.contains("debris")) {
                        if (injured.contains("yes")) {
                            state = "debris_injured";
                        } else {
                            state = "debris";
                        }
                    }
                    cell.put("state", state);
                    //salvo solo l'intero dello stato che viene
                    //scenepato internamente;
                    ArrayCells.put(cell);
                }
            }
            Info.put("cells", ArrayCells);
            File jsonfile = new File(map.getParent() + File.separator + "infoMap.json");
            Files.write(Paths.get(jsonfile.getAbsolutePath()), Info.toString(2).getBytes());
        } catch (FileNotFoundException ex) {
            Exceptions.printStackTrace(ex);
        } catch (IOException ex) {
            Exceptions.printStackTrace(ex);
        } catch (JSONException ex) {
            Exceptions.printStackTrace(ex);
        }
    }

    /**
     *  Esegue il parsing di un file history e ne costruisce il json corrispondente
     * @param history
     * @param jsonMap 
     */

    public void createJsonHistory(File history, File jsonMap) {
        try {
            JSONObject Info = new JSONObject();
            BufferedReader mapread = new BufferedReader(new FileReader(history));
            String l = "";
            String timeRegex = "\\s*(\\(maxduration\\s*(\\d+)\\s*\\)\\s*)";
            String agentPosRegex = "\\s*(\\(initial_agentposition\\s*" + "(\\(pos-r (\\d+)\\))\\s*"
                    + "(\\(pos-c (\\d+)\\))\\s*" + "(\\(direction ([a-z]+)\\))\\s*\\))";

            String perStatusRegex = "\\s*(\\(\\s*personstatus\\s*" + "(\\(step (\\d+)\\))"
                    + "\\s*(\\(time (\\d+)\\))\\s*" + "(\\(ident [A-Za-z0-9]+\\))\\s*" + "(\\(pos-r (\\d+)\\))\\s*"
                    + "(\\(pos-c (\\d+)\\))\\s*" + "(\\(activity out\\))\\s*\\))";

            String perMoveRegex = "\\s*(\\(\\s*personmove\\s*" + "(\\(step (\\d+)\\))\\s*"
                    + "(\\(ident ([A-Za-z0-9]+)\\))\\s*" + "(\\(path-id ([A-Za-z0-9]+)\\))\\s*\\))";

            String movePathRegex = "\\s*(\\(\\s*move\\-path\\s+" + "([A-Za-z0-9]+)\\s+" + "(\\d+)\\s+"
                    + "([A-Za-z0-9]+)\\s+" + "(\\d+)\\s+(\\d+)\\s*\\))";

            // recupero dal json della mappa la dimensione in celle della mappa
            // per eseguire le operazioni di trasformazione delle coordinate 
            // anche sulle move degli agenti

            int[] mapDimension = GetJsonMapDimension(jsonMap);

            Pattern timeDuration = Pattern.compile(timeRegex);
            Pattern agent = Pattern.compile(agentPosRegex);
            Pattern personStatus = Pattern.compile(perStatusRegex);
            Pattern personMove = Pattern.compile(perMoveRegex);
            Pattern moves = Pattern.compile(movePathRegex);

            while ((l = mapread.readLine()) != null) {
                Matcher tdm = timeDuration.matcher(l);
                Matcher agm = agent.matcher(l);
                Matcher psm = personStatus.matcher(l);
                Matcher pmm = personMove.matcher(l);
                Matcher mm = moves.matcher(l);

                // inserisco la maxduration 
                if (tdm.find()) {
                    String timeDur = tdm.group(2);
                    int t = Integer.parseInt(timeDur);
                    Info.put("time", t);
                }
                // inserisco le informazioni sull'agent
                if (agm.find()) {
                    String posR = agm.group(3);
                    String posC = agm.group(5);
                    String direction = agm.group(7);
                    int r = Integer.parseInt(posR);
                    int c = Integer.parseInt(posC);
                    int[] InitAgentPos = MapToGenMap(r, c, mapDimension[1]);
                    Info.put("robot_x", InitAgentPos[0]);
                    Info.put("robot_y", InitAgentPos[1]);
                    Info.put("robot_x_default", InitAgentPos[0]);
                    Info.put("robot_y_default", InitAgentPos[1]);
                    Info.put("robot_direction", direction);
                    Info.put("robot_loaded", "unloaded");
                }
                if (psm.find()) {

                }
                if (pmm.find()) {

                }
                if (mm.find()) {

                }
            }
            JSONArray PersonsArray = new JSONArray();
            Info.put("personList", PersonsArray);
            File jsonfile = new File(history.getParent() + File.separator + "infoMove.json");
            Files.write(Paths.get(jsonfile.getAbsolutePath()), Info.toString(2).getBytes());

        } catch (FileNotFoundException ex) {
            Exceptions.printStackTrace(ex);
        } catch (IOException ex) {
            Exceptions.printStackTrace(ex);
        } catch (JSONException ex) {
            Exceptions.printStackTrace(ex);
        }
    }

    /**
     * Legge da un file Json e imposta gli attributi del robot  
     * @param jsonFile 
     */

    public void LoadJsonRobotParams(File jsonFile) {
        try {
            //converto il file in un oggetto JSON
            FileReader jsonreader = new FileReader(jsonFile);
            char[] chars = new char[(int) jsonFile.length()];
            jsonreader.read(chars);
            String jsonstring = new String(chars);
            jsonreader.close();
            JSONObject json = new JSONObject(jsonstring);
            agentposition = new int[] { json.getInt("robot_x"), json.getInt("robot_y") };
            defaultagentposition = new int[] { json.getInt("robot_x_default"), json.getInt("robot_y_default") };

            direction = json.getString("robot_direction");
            loaded = json.getString("robot_loaded");
            scene[agentposition[0]][agentposition[1]] += "+" + "agent_" + direction + "_" + loaded;
            defaulagentcondition = scene[agentposition[0]][agentposition[1]];
            move = clone(scene);
            CopyToActive(scene);
        }

        catch (JSONException ex) {
            AppendLogMessage(ex.getMessage(), "error");
        } catch (IOException ex) {
            AppendLogMessage(ex.getMessage(), "error");
        } catch (NumberFormatException ex) {
            AppendLogMessage(ex.getMessage(), "error");
        }
    }

    /**
     * Salva sul json passato in input le informazioni relative all'agente 
     * da utilizzare per ricaricare la scena
     * @param json 
     */

    public boolean SaveJsonRobotParams(File json) {
        try {
            JSONObject Info = new JSONObject();
            Info.put("robot_x", agentposition[0]);
            Info.put("robot_y", agentposition[1]);
            Info.put("robot_x_default", agentposition[0]);
            Info.put("robot_y_default", agentposition[1]);
            Info.put("robot_direction", direction);
            Info.put("robot_loaded", loaded);
            Files.write(Paths.get(json.getAbsolutePath()), Info.toString(2).getBytes(), StandardOpenOption.APPEND);
            return true;
        } catch (JSONException ex) {
            AppendLogMessage(ex.getMessage(), "error");
            return false;

        } catch (NumberFormatException ex) {
            AppendLogMessage(ex.getMessage(), "error");
            return false;
        } catch (IOException ex) {
            Exceptions.printStackTrace(ex);
            return false;
        }
    }
}