Les rasters sont très utiles pour représenter des couches de données. On considère que chaque pixel représente une surface et que les valeurs de ces pixels ont une signification (hauteur, température, chlorophylle...).
La solution la plus simple pour utiliser un raster comme support est d'utiliser une grille de même dimension que le raster et d'associer à chaque cellule un agent parcelle construit à partir de la valeur du pixel correspondant dans le raster. On peut alors positionner les agents à l'intérieur de ces agents parcelles.
Cependant plusieurs problèmes apparaissent rapidement:
Pour résoudre ces deux problèmes, nous allons combiner différents procédés.
G En revanche, il va falloir définir une classe de style pour faire correspondre à chaque valeur une couleur.
Attention: Il est important de toujours penser à faire correspondre les données des classes java avec le schéma défini dans le fichier model.score. Il faut donc ajouter la projection de type espace continu et le GridValueLayer dans les éléments du contexte défini dans model.score. Il faut également faire en sorte que les libellé se correspondent entre le nom donné dans le fichier model.score et la chaîne de caractères servant à repérer l'élément dans le code.
L'en tête de la classe Raster_manager aura donc cet aspect:
public class Grid_Manager implements Ground_Manager
{
private static Map<Integer,Color> map;
private double size_of_one_box = 3;
GridValueLayer grille = null;
ContinuousSpace space = null;
Field_Agent[][] matrice_terrain;
public Context create_ground(Context context,String url,String geographyname )
{
//we load the data in an integer matrix from the file at the specified URL
int[][] matrice = img_raster_loader(url);
//building of the projection's elements
.
.
.
return context;
}
}
Avant de construire la projection, on va récupérer les données qui nous intéressent dans une matrice :
private int[][]img_raster_loader(String url)
{
int[][] matrice = null ;
int[] pixel = new int[3];
try {
//we get back the bufferedImage which represent a raster
BufferedImage img = ImageIO.read(new File(url));
if (img == null)
{
System.out.println(" l'image est null");
}
//we can take the colormodel if we want to draw the raster with the same color //as the original image
IndexColorModel c =(IndexColorModel)img.getColorModel();
//we transform the colormodel in a map
Map<Integer,Color> colorMap =new HashMap<Integer,Color>();
for (int i = 0; i < c.getMapSize() ; i++)
{
colorMap.put(i, new Color(c.getRGB(i)));
}
map = colorMap;
//we read the raster from the bufferdImage
Raster r = img.getData();
//we make a matrix with the same Dimension than the raster
matrice = new int[r.getWidth()][r.getHeight()];
//for each cells of the matrix, we associate the value of the pixel
// here we know befor which data we were going to read, but it may // be recorded in another format
for (int i = 0 ; i < matrice.length; i++)
{
for (int j = 0 ; j < matrice[0].length; j++)
{
Object tab = null;
Object o = r.getDataElements(i,j,tab);
r.getSampleModel().getDataType();
if ( o != null && o instanceof byte[])
{
byte[] tab_byte = (byte[])o;
matrice[i][matrice[0].length -j -1] = (int)tab_byte[0];
}
}
}
} catch (IOException e) {
e.printStackTrace();
}
return matrice;
}
G Lors de la création, on lit l'image du coin supérieur gauche au coin inférieur droit. On doit donc adapter le parcours pour construire un tableau cohérent (puisque l'on parcourt les tableaux du coin inférieur gauche vers le coin supérieur droit).
Maintenant que nous avons récupéré nos données, nous pouvons compléter notre classe Create_Ground:
public Context create_ground(Context context,String url,String geographyname )
{
//we
load the grid in an array of integer
int[][]
matrice = img_raster_loader(url);
//we create a matrix which will contains the Field_Agent
matrice_terrain
=
new
Field_Agent[matrice.length][matrice[0].length];
Dimension dim =
new
Dimension(matrice.length,matrice[0].length);
//we
create the gridValueLayer
grille
=
new
GridValueLayer("ScalarField",
true,
new
repast.simphony.space.grid.WrapAroundBorders(),
dim.width,
dim.height);
context.addValueLayer(grille);
ContinuousSpaceFactory continousfactory = ContinuousSpaceFactoryFinder.createContinuousSpaceFactory(new
HashMap());
space
= continousfactory.createContinuousSpace("space",
context,
new
SimpleCartesianAdder(),new
WrapAroundBorders(),grille.getDimensions().getWidth(),grille.getDimensions().getHeight());
//on
parcourt tous les éléments de la grille pour les faire
//correspondre avec les valeurs enregistrées dans
la matrice que l'on a chargé.
for
(int
i = 0; i <grille.getDimensions().getWidth();i++)
{
for
(int
j = 0; j <grille.getDimensions().getHeight();j++)
{
grille.set(matrice[i][j],
i,j);
//on
créé un agent terrain avec la valeur correspondante
matrice_terrain[i][j]
=
new
Field_Agent(matrice[i][j]);
}
}
return
context;
}
Nous allons ensuite définir le style permettant de représenter notre « GridValueLayer ».
La plupart des méthodes sont des méthodes de Repast que l'on redéfinit.
§ On utilise le constructeur pour associer le style à notre valueLayer.
§ Puis on charge la table de correspondance que l'on a récupéré lorsque l'on a chargé le fichier pour associer une couleur à chaque valeur.
Public
class Style2d_terrain implements ValueLayerStyle
{
protected ValueLayer layer;
Map<Integer,Color> colorMap;
public Style2d_terrain()
{
//we get back the colorModel we have read during theinitialisation
colorMap = Grid_Manager.getmap();
}
@Override
public void addValueLayer(ValueLayer layer)
{
this.layer = layer;
}
@Override
public int getRed(double... coordinates)
{
return colorMap.get((int)layer.get(coordinates)).getRed();
}
@Override
public int getBlue(double... coordinates)
{
return colorMap.get((int)layer.get(coordinates)).getBlue();
}
@Override
public int getGreen(double... coordinates)
{
Return colorMap.get((int)layer.get(coordinates)).getGreen();
}
@Override
public float getCellSize()
{
return cell_size;
}
@Override
public Paint getPaint(double... coordinates)
{
return colorMap.get((int)layer.get(coordinates));
}
}
Une fois tous les éléments mis en place, il faut configurer l'affichage:
G l'affichage voulu est de type 2D.
G Normalement, si vous lancez la simulation, votre image doit apparaître en arrière plan.
retour aux mémos retour au modèle retour à la page d'accueil