From ccd70f1b77f8cc779ab9bacc02b230eef42c64ca Mon Sep 17 00:00:00 2001 From: ptaillandier Date: Wed, 12 Jun 2024 16:58:18 +0700 Subject: [PATCH] Fixes issues with the tool to import geometries from GAMA --- .../Demo/Simple Player Game/DemoModelVR.gaml | 2 +- .../Utilities/SentGemetriesToUnity.gaml | 204 ++++++++++++------ .../unity/species/AbstractUnityLinker.java | 13 +- 3 files changed, 152 insertions(+), 67 deletions(-) diff --git a/gaml.extension.unity/models/LinkToUnity/Models/Demo/Simple Player Game/DemoModelVR.gaml b/gaml.extension.unity/models/LinkToUnity/Models/Demo/Simple Player Game/DemoModelVR.gaml index 8f5e120..6825828 100644 --- a/gaml.extension.unity/models/LinkToUnity/Models/Demo/Simple Player Game/DemoModelVR.gaml +++ b/gaml.extension.unity/models/LinkToUnity/Models/Demo/Simple Player Game/DemoModelVR.gaml @@ -63,7 +63,7 @@ species unity_linker parent: abstract_unity_linker { do add_geometries_to_send(simple_agentB,up_moto); } - action add_to_send_parameter(map map_to_send) { + action add_to_send_parameter(agent player, map map_to_send) { map_to_send["hotspots"] <- (block where (each.is_hotspot)) collect string(int(each)); } diff --git a/gaml.extension.unity/models/LinkToUnity/Models/Utilities/SentGemetriesToUnity.gaml b/gaml.extension.unity/models/LinkToUnity/Models/Utilities/SentGemetriesToUnity.gaml index e7882a9..82171fc 100644 --- a/gaml.extension.unity/models/LinkToUnity/Models/Utilities/SentGemetriesToUnity.gaml +++ b/gaml.extension.unity/models/LinkToUnity/Models/Utilities/SentGemetriesToUnity.gaml @@ -6,107 +6,183 @@ */ model sendGeometriesToUnity + global { + //unity properties that will be used for sending geometries/agents to Unity + unity_property up_road ; + unity_property up_building; - - //Shapefile of the bound - shape_file bounds_shape_file <- shape_file("../Includes/bounds.shp"); + + shape_file bounds_shape_file <- shape_file("../../includes/bounds.shp"); + + shape_file road_shape_file <- shape_file("../../includes/road.shp"); - //Shapefile of the buildings - file building_shapefile <- file("../includes/building.shp"); - //Shapefile of the roads - file road_shapefile <- file("../includes/road.shp") ; - //Shape of the environment + + shape_file building_shape_file <- shape_file("../../includes/building.shp"); + + geometry shape <- envelope(bounds_shape_file); + init { + create road from: road_shape_file; + + create building from: building_shape_file; + + + } - geometry shape <- envelope(bounds_shape_file) ; - - - - init { - //Initialization of the building using the shapefile of buildings - create building from: building_shapefile { - if (shape.area < 0.1) { - do die; - } - } - - //Initialization of the road using the shapefile of roads - create road from: road_shapefile { - float dist <- (building closest_to self) distance_to self; - width <- min(5.0, max(2.0, dist - 0.5)); - } - - } - - action after_sending_background { - do pause; - } } - //Species to represent the buildings -species building { +species road { aspect default { - draw shape color: darker(#darkgray).darker depth: rnd(10) + 2; + draw shape + 5.0 color: #black; } - } -//Species to represent the roads -species road { - float width; + +species building { aspect default { - draw (shape + width) color: #white; + draw shape color: #gray; } - } - - +//Species that will make the link between GAMA and Unity. It has to inherit from the built-in species asbtract_unity_linker species unity_linker parent: abstract_unity_linker { - list init_locations <- [{50.0, 50.0}]; - int port <- 8000; + //name of the species used to represent a Unity player string player_species <- string(unity_player); - int min_num_players <- 0; - int max_num_players <- 1; + + //in this model, no information will be automatically sent to the Player at every step, so we set do_info_world to false bool do_send_world <- false; - unity_property up_building; - unity_property up_road; + + + //initial location of the player + list init_locations <- [world.location]; init { + //define the unity properties do define_properties; - + + do add_background_geometries(road collect (each.shape + 3.0),up_road); do add_background_geometries(building,up_building); - do add_background_geometries(road collect (each.shape buffer each.width),up_road); } + + //action that defines the different unity properties action define_properties { - unity_aspect building_aspect <- geometry_aspect(10.0, #gray, precision); - up_building <- geometry_properties("building", "building", building_aspect, #no_interaction , false); - unity_properties << up_building; + unity_aspect road_aspect <- geometry_aspect(0.1, #black, precision); - unity_aspect road_aspect <- geometry_aspect(10.0, #gray, precision); - up_road <- geometry_properties("road", "road", road_aspect, #ray_interactable , false); + //define the up_tree unity property, with the name "tree", no specific layer, no interaction, and the agents location are not sent back + //to GAMA. + up_road<- geometry_properties("road", nil, road_aspect, #collider, false); + + // add the up_tree unity_property to the list of unity_properties unity_properties << up_road; + + + unity_aspect building_aspect <- geometry_aspect(10.0, #gray, precision); + + //define the up_geom unity property, with the name "polygon", no specific layer, no interaction, and the agents location are not sent back + //to GAMA. + up_building <- geometry_properties("building", nil, building_aspect, #collider, false); + + // add the up_geom unity_property to the list of unity_properties + unity_properties << up_building; } } -//Defaut species for the player -species unity_player parent: abstract_unity_player; +//species used to represent an unity player, with the default attributes. It has to inherit from the built-in species asbtract_unity_player +species unity_player parent: abstract_unity_player { + //size of the player in GAMA + float player_size <- 1.0; + //color of the player in GAMA + rgb color <- #red ; + + //vision cone distance in GAMA + float cone_distance <- 10.0 * player_size; + + //vision cone amplitude in GAMA + float cone_amplitude <- 90.0; -//Default xp with the possibility to move the player -experiment sendGeometriesToUnity autorun: true type: unity { - float minimum_cycle_duration <- 0.1; + //rotation to apply from the heading of Unity to GAMA + float player_rotation <- 90.0; + + //display the player + bool to_display <- true; + + + //default aspect to display the player as a circle with its cone of vision + aspect default { + if to_display { + if selected { + draw circle(player_size) at: location + {0, 0, 4.9} color: rgb(#blue, 0.5); + } + draw circle(player_size/2.0) at: location + {0, 0, 5} color: color ; + draw player_perception_cone() color: rgb(color, 0.5); + } + } +} + + +experiment main type: gui { + output { + display map { + species road; + species building; + } + } +} + +//default Unity (VR) experiment that inherit from the SimpleMessage experiment +//The unity type allows to create at the initialization one unity_linker agent +experiment vr_xp parent:main autorun: false type: unity { + //minimal time between two simulation step + float minimum_cycle_duration <- 0.05; + + //name of the species used for the unity_linker string unity_linker_species <- string(unity_linker); + //allow to hide the "map" display and to only display the displayVR display + list displays_to_hide <- ["map"]; + + + + //action called by the middleware when a player connects to the simulation + action create_player(string id) { + ask unity_linker { + do create_player(id); + } + } + + //action called by the middleware when a plyer is remove from the simulation + action remove_player(string id_input) { + if (not empty(unity_player)) { + ask first(unity_player where (each.name = id_input)) { + do die; + } + } + } + + //variable used to avoid to move too fast the player agent + float t_ref; + + output { - display carte type: 3d axes: false background: #black { - species road refresh: false; - species building refresh: false; + //In addition to the layers in the map display, display the unity_player and let the possibility to the user to move players by clicking on it. + display displayVR parent: map { + species unity_player; + event #mouse_down { + float t <- gama.machine_time; + if (t - t_ref) > 500 { + ask unity_linker { + move_player_event <- true; + } + t_ref <- t; + } + + } } } -} +} \ No newline at end of file diff --git a/gaml.extension.unity/src/gaml/extension/unity/species/AbstractUnityLinker.java b/gaml.extension.unity/src/gaml/extension/unity/species/AbstractUnityLinker.java index 5fb8b1d..ef39513 100644 --- a/gaml.extension.unity/src/gaml/extension/unity/species/AbstractUnityLinker.java +++ b/gaml.extension.unity/src/gaml/extension/unity/species/AbstractUnityLinker.java @@ -1071,7 +1071,7 @@ private void addToCurrentMessage(final IScope scope, final IList recipie * @throws GamaRuntimeException * the gama runtime exception */ - @action ( + @action ( name = "send_message", args = { @arg ( name = "players", @@ -1506,6 +1506,11 @@ public void primCreateInitPlayer(final IScope scope) throws GamaRuntimeException value = "Create a new unity player agent") }) public void primInitPlayer(final IScope scope) throws GamaRuntimeException { IMap players = getPlayers(getAgent()); + for(String id : new ArrayList(players.keySet())) { + if (players.get(id).dead()) { + players.remove(id); + } + } IAgent ag = getAgent(); String id = scope.getStringArg("id"); @@ -1939,6 +1944,10 @@ private void startSimulation(final IScope scope) { @action ( name = "add_to_send_parameter", args = { @arg ( + name = "player", + type = IType.AGENT, + doc = @doc ("Player to which send the information")), + @arg ( name = "map_to_send", type = IType.MAP, doc = @doc ("data already sent to the client")) }, @@ -1991,7 +2000,7 @@ public void primSendParameters(final IScope scope) throws GamaRuntimeException { toSend.put("world", worldT); - doAction1Arg(scope, "add_to_send_parameter", "map_to_send", toSend); + doAction2Arg(scope, "add_to_send_parameter", "player", player, "map_to_send", toSend); addToCurrentMessage(scope, buildPlayerListfor1Player(scope, player), toSend); }