diff --git a/Barcelona.osm.pbf b/Barcelona.osm.pbf new file mode 100644 index 000000000..d7f4ee3d6 Binary files /dev/null and b/Barcelona.osm.pbf differ diff --git a/profiles/foot.lua b/profiles/foot.lua index e8149f197..0b97712c4 100644 --- a/profiles/foot.lua +++ b/profiles/foot.lua @@ -8,43 +8,44 @@ Set = require('lib/set') Sequence = require('lib/sequence') Handlers = require("lib/way_handlers") find_access_tag = require("lib/access").find_access_tag +stations_data = nil -function fetch_pollution_data(location) - -- Convert location userdata to a string - local location_str = tostring(location) - -- Check if the location is "(undefined,undefined)" - if location_str == "(undefined,undefined)" then - print("Location is undefined. Skipping pollution data fetch.") - return 0 -- Return 0 for undefined locations - end - - -- Extract lat and lon from the location string - local lat, lon = location_str:match("%(([^,]+),([^%)]+)%)") - if lat and lon then - lat = tonumber(lat) - lon = tonumber(lon) - else - print("Invalid location format: " .. location_str) - return 0 -- Return 0 if the format is invalid - end - - -- Fetch pollution data - local url = string.format("http://localhost:8008/routes/api/pollution?lat=%f&lon=%f", lat, lon) +function fetch_pollution_data() + local url = "http://localhost:8008/routes/api/pollution" local response, status = http.request(url) - if status == 200 then - local data = json.decode(response) - return data.pollution -- Return the pollution weight from the backend + if status == 200 and response then + print("Raw response:", response) + local success, data = pcall(json.decode, response) -- Manejar errores de JSON + if success and data and data.stations then + print("Pollution data fetched successfully.") + print("Number of stations:", #data.stations) + return data + else + print("Failed to decode JSON or missing 'stations' key.") + end else - print("Failed to fetch pollution data. HTTP status: " .. tostring(status)) - return 0 -- Return 0 if the request fails + print("HTTP request failed. Status:", status) end + + -- Fallback a datos vacíos si hay un error + return { stations = {} } end + function setup() local walking_speed = 5 + stations_data = fetch_pollution_data() + + -- Check if data was successfully retrieved + if not stations_data or not stations_data.stations then + print("Warning: Pollution data could not be loaded. Defaulting to no pollution.") + stations_data = { stations = {} } -- Fallback to empty station data + else + print("Pollution data loaded successfully.") + end return { properties = { weight_name = 'duration', @@ -172,8 +173,47 @@ function setup() } end +function calculate_pollution(lat, lon) + -- Calcular contaminación + local pollution_value = 0 + local total_weight = 0 + local weight = 0 + local p = 1.8 + local max_distance = 3 + if stations_data and stations_data.stations then + for _, station in ipairs(stations_data.stations) do + local station_lat = tonumber(station.lat) + local station_lon = tonumber(station.lon) + local latest_reading = tonumber(station.pollution) + + if station_lat and station_lon and latest_reading then + -- Fórmula de distancia usando Haversine + local R = 6371 -- Radio de la Tierra en km + local dlat = math.rad(station_lat - lat) + local dlon = math.rad(station_lon - lon) + local a = math.sin(dlat / 2)^2 + + math.cos(math.rad(lat)) * math.cos(math.rad(station_lat)) * math.sin(dlon / 2)^2 + local c = 2 * math.atan2(math.sqrt(a), math.sqrt(1 - a)) + local distance = R * c + + -- Ponderación ajustada + weight = 1 / ((distance + 1)) + weight = tonumber(string.format("%.6f", weight)) + pollution_value = pollution_value + (latest_reading * weight) + --total_weight = total_weight + weight + + end + end + --print(pollution_value) + return pollution_value + else + print("No station data available.") + return 0 + end +end + function process_node(profile, node, result) - -- parse access and barrier tags + -- Parse access and barrier tags local access = find_access_tag(node, profile.access_tags_hierarchy) if access then if profile.access_tag_blacklist[access] then @@ -182,7 +222,7 @@ function process_node(profile, node, result) else local barrier = node:get_value_by_key("barrier") if barrier then - -- make an exception for rising bollard barriers + -- Make an exception for rising bollard barriers local bollard = node:get_value_by_key("bollard") local rising_bollard = bollard and "rising" == bollard @@ -191,20 +231,9 @@ function process_node(profile, node, result) end end end - local location = node:location() - local pollution = fetch_pollution_data(location) - print(pollution) - --result.weight = result.weight + pollution - - - -- check if node is a traffic light - local tag = node:get_value_by_key("highway") - if "traffic_signals" == tag then - -- Direction should only apply to vehicles - result.traffic_lights = true - end end + -- main entry point for processsing a way function process_way(profile, way, result) -- the intial filtering of ways based on presence of tags @@ -302,9 +331,29 @@ function process_turn (profile, turn) end end +function process_segment(profile, segment) + -- Extract coordinates of the start and end points + local source_lat, source_lon = segment.source.lat, segment.source.lon + local target_lat, target_lon = segment.target.lat, segment.target.lon + + -- Calculate pollution impact at source and target + local pollution_source = calculate_pollution(source_lat, source_lon) + local pollution_target = calculate_pollution(target_lat, target_lon) + + + -- Average pollution for the segment + local avg_pollution = (pollution_source + pollution_target) / 2 + --print(avg_pollution) + + -- Adjust weight and duration based on pollution level + segment.weight = segment.weight + (avg_pollution^1.4) +end + + return { setup = setup, process_way = process_way, process_node = process_node, - process_turn = process_turn + process_turn = process_turn, + process_segment = process_segment } \ No newline at end of file