/**
* Name: fieldofvision
* Author: Patrick Taillandier
* Description: This model illustrate how to use the masked_by operator to compute the field of vision of an agent (with obtsacles)
* Tags: perception, spatial_computation, masked_by
*/
model fieldofvision
global {
//number of obstacles
int nb_obstacles <- 20 parameter: true;
//perception distance
float perception_distance <- 40.0 parameter: true;
//precision used for the masked_by operator (default value: 120): the higher the most accurate the perception will be, but it will require more computation
int precision <- 600 parameter: true;
//space where the agent can move.
geometry free_space <- copy(shape);
init {
create obstacle number:nb_obstacles {
shape <- rectangle(2+rnd(20), 2+rnd(20));
free_space <- free_space - shape;
}
create people {
location <- any_location_in(free_space);
}
}
}
species obstacle {
aspect default {
draw shape color: #gray border: #black;
}
}
species people skills: [moving]{
//zone of perception
geometry perceived_area;
//the target it wants to reach
point target ;
reflex move {
if (target = nil ) {
if (perceived_area = nil) or (perceived_area.area < 2.0) {
//if the agent has no target and if the perceived area is empty (or too small), it moves randomly inside the free_space
do wander bounds: free_space;
} else {
//otherwise, it computes a new target inside the perceived_area .
target <- any_location_in(perceived_area);
}
} else {
//if it has a target, it moves towards this target
do goto target: target;
//if it reaches its target, it sets it to nil (to choose a new target)
if (location = target) {
target <- nil;
}
}
}
//computation of the perceived area
reflex update_perception {
//the agent perceived a cone (with an amplitude of 60°) at a distance of perception_distance (the intersection with the world shape is just to limit the perception to the world)
perceived_area <- (cone(heading-30,heading+30) intersection world.shape) intersection circle(perception_distance);
//if the perceived area is not nil, we use the masked_by operator to compute the visible area from the perceived area according to the obstacles
if (perceived_area != nil) {
perceived_area <- perceived_area masked_by (obstacle,precision);
}
}
aspect body {
draw triangle(2) rotate:90 + heading color: #red;
}
aspect perception {
if (perceived_area != nil) {
draw perceived_area color: #green;
draw circle(1) at: target color: #magenta;
}
}
}
experiment fieldofvision type: gui {
float minimum_cycle_duration <- 0.05;
output synchronized: true {
display view{
species obstacle;
species people aspect: perception transparency: 0.5;
species people aspect: body;
}
}
}