1# Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.org/sumo 2# Copyright (C) 2016-2019 German Aerospace Center (DLR) and others. 3# SUMOPy module 4# Copyright (C) 2012-2017 University of Bologna - DICAM 5# This program and the accompanying materials 6# are made available under the terms of the Eclipse Public License v2.0 7# which accompanies this distribution, and is available at 8# http://www.eclipse.org/legal/epl-v20.html 9# SPDX-License-Identifier: EPL-2.0 10 11# @file networkxtools.py 12# @author Joerg Schweizer 13# @date 14# @version $Id$ 15 16import sys 17reload(sys) 18sys.setdefaultencoding('utf8') 19 20import os 21import pickle 22from copy import deepcopy 23try: 24 import networkx as nx 25 IS_NX = True 26except: 27 IS_NX = False 28 29import numpy as np 30 31import agilepy.lib_base.classman as cm 32import agilepy.lib_base.arrayman as am 33import agilepy.lib_base.xmlman as xm 34from agilepy.lib_base.processes import Process 35from agilepy.lib_base.misc import filepathstring_to_filepathlist, filepathlist_to_filepathstring 36from agilepy.lib_base.geometry import get_length_polypoints, get_dist_point_to_segs, get_diff_angle_clockwise 37 38from coremodules.network.network import MODES, ID_MODE_PED, ID_MODE_BIKE, ID_MODE_CAR 39from coremodules.network.netconvert import * 40from coremodules.misc.shapeformat import guess_utm_from_coord 41 42import json 43 44try: 45 import pyproj 46except: 47 from mpl_toolkits.basemap import pyproj 48 49 50LANEATTRS_DEFAULT = {'is_rightside': False, 'is_leftside': False, 'n_lane': 0, 51 'ids_modes_disallow': [], 'ids_modes_allow': []} 52 53LANEATTRS = ('lane', 'track') 54 55 56def load_objfile(filepath): 57 f = open(filepath, 'rb') 58 try: 59 f = open(filepath, 'rb') 60 except: 61 print 'WARNING in load_obj: could not open', filepath 62 return None 63 64 # try: 65 # print ' pickle.load...' 66 obj = pickle.load(f) 67 f.close() 68 return obj 69 70 71def print_attrs(attrs): 72 for key, val in attrs.iteritems(): 73 print ' %s=\t%s' % (key, val) 74 print 75 76 77class Road: 78 def __init__(self, element, parent): 79 # edges_osm[id_way]= {}#{'nodes':(element['nodes'][0],element['nodes'][1])}# not needed {'nodes': element['nodes']} 80 81 self.parent = parent 82 83 self._osmattrs = element.get('tags', {}) 84 85 self.highway = self._osmattrs.get('highway', 'road') 86 # if element.has_key('tags'): 87 # self._attrs.update(element['tags']) 88 89 # is_one is a scpecial one way detection 90 #self._is_oneway = self.is_oneway_osm() 91 # self.is_oneway_osm() 92 93 #self._id_osm = id_osm 94 #osmattrs = self._osmattrs 95 # if not self._is_oneway: 96 # self._id_osm_opp = -id_osm 97 # else: 98 # self._id_osm_opp = -1 99 100 self._lanes = [] 101 self._lanes_opp = [] 102 self.make_oneway() 103 self.config() 104 self.make_lanestructure() 105 self.make_sumoattrs() 106 self.make_road() 107 # get from parent 108 # self._width_bikelane = 1.5 #m 109 # self.parent.width_sidewalk = 1.0 #m 110 #self._modes_reserved_lane = ['bus', 'taxi','emergency'] 111 112 def config(self): 113 """ 114 Make defaults to be overridden 115 """ 116 print 'config' 117 # pass here either road type specific defaults 118 # or global defaults from parent process 119 120 self.n_lane = self.parent.n_lane 121 self.id_mode = ID_MODE_CAR 122 self.lanewidth = self.parent.lanewidth 123 self.lanewidth_bike = self.parent.lanewidth_bike 124 self.lanewidth_bus = self.parent.lanewidth_bus 125 self.width_sidewalk = self.parent.width_sidewalk 126 #self.width_footpath = self.parent.width_footpath 127 128 self.ids_modes_pt_shared = self.parent.ids_modes_pt_shared 129 self.ids_modes_bike = self.parent.ids_modes_bike 130 self.ids_modes_allow = [] 131 self.ids_modes_disallow = [] 132 133 self.make_speed(self.parent.speed_max) 134 self.speed_max_bus = self.parent.speed_max_bus 135 self.speed_max_bike = self.parent.speed_max_bike 136 self.speed_max_ped = self.parent.speed_max_ped 137 138 def make_laneattrs_main(self): 139 self._laneattrs_main = {'speed_max': self.speed_max, 140 'width': self.lanewidth, 141 'ids_modes_allow': self.ids_modes_allow, 142 'ids_modes_disallow': self.ids_modes_disallow, 143 # 'ids_mode': MODES["passenger"], 144 'is_rightside': True, 145 'is_leftside': False, 146 'width_rightside': self.lanewidth, 147 } 148 149 def get_osmattr(self, key, is_int=False, is_float=False, default=None): 150 valstr = self._osmattrs.get(key, '') 151 if valstr.find(',') > -1: 152 v = valstr.split(',')[0] 153 elif valstr.find(';') > -1: 154 v = valstr.split(';')[0] 155 else: 156 v = valstr 157 if is_int: 158 try: 159 return int(v) 160 except: 161 return default 162 if is_float: 163 try: 164 return float(v) 165 except: 166 return default 167 168 else: 169 return v 170 171 def make_sumoattrs(self): 172 173 osmattrs = self._osmattrs 174 print 'make_sumoattrs' 175 print_attrs(osmattrs) 176 #self._highway = osmattrs.get('highway','road') 177 178 self.make_laneattrs_main() 179 self.make_sidewalkattrs() 180 self.make_buswayattrs() 181 self.make_bikewayattrs() 182 183 def make_lanestructure(self): 184 osmattrs = self._osmattrs 185 is_oneway_osm = osmattrs.get('oneway', 'no') == 'yes' 186 187 n_lane_forward_osm = -1 188 n_lane_backward_osm = -1 189 is_lanes_forward_rigid = False 190 is_lanes_backward_rigid = False 191 if osmattrs.has_key('lanes'): 192 # total number of lanes provided 193 n_lane_osm_str = osmattrs['lanes'] 194 # if type(n_lane_osm_str) in cm.STRINGTYPES: 195 if n_lane_osm_str.count(';') > 0: 196 n_lane_osm = 1 197 for n_lane_osm_elem in n_lane_osm_str.split(';'): 198 if int(n_lane_osm_elem) > n_lane_osm: 199 n_lane_osm = int(n_lane_osm_elem) 200 elif n_lane_osm_str.count(',') > 0: 201 n_lane_osm = 1 202 for n_lane_osm_elem in n_lane_osm_str.split(','): 203 if int(n_lane_osm_elem) > n_lane_osm: 204 n_lane_osm = int(n_lane_osm_elem) 205 else: 206 n_lane_osm = int(osmattrs['lanes']) 207 208 if is_oneway_osm: 209 # in cas of oneway 210 n_lane_backward_osm = 0 211 n_lane_forward_osm = n_lane_osm 212 is_lanes_forward_rigid = True 213 214 else: 215 # in case of bidir 216 if osmattrs.has_key('lanes:forward'): 217 n_lane_forward_osm = int(osmattrs['lanes:forward']) 218 is_lanes_forward_rigid = True 219 if osmattrs.has_key('lanes:backward'): 220 n_lane_backward_osm = int(osmattrs['lanes:backward']) 221 is_lanes_backward_rigid = True 222 else: 223 n_lane_backward_osm = n_lane_osm-n_lane_forward_osm 224 # correct if necessary 225 if n_lane_backward_osm <= 0: 226 n_lane_backward_osm = 1 227 n_lane_osm = n_lane_forward_osm+n_lane_backward_osm 228 229 elif osmattrs.has_key('lanes:backward'): 230 n_lane_backward_osm = int(osmattrs['lanes:backward']) 231 n_lane_forward_osm = n_lane_osm-n_lane_backward_osm 232 is_lanes_backward_rigid = True 233 234 # correct if necessary 235 if n_lane_forward_osm <= 0: 236 n_lane_forward_osm = 1 237 n_lane_osm = n_lane_forward_osm+n_lane_backward_osm 238 239 else: 240 # symmetric dist 241 if n_lane_osm < 2: 242 n_lane_osm = 2 243 244 n_lane_forward_osm = int(0.5*n_lane_osm+0.5) 245 n_lane_backward_osm = n_lane_forward_osm 246 else: 247 # no information on total of lanes 248 if is_oneway_osm: 249 # in cas of oneway 250 n_lane_backward_osm = 0 251 if osmattrs.has_key('lanes:forward'): 252 n_lane_forward_osm = int(osmattrs['lanes:forward']) 253 is_lanes_forward_rigid = True 254 else: 255 n_lane_forward_osm = self.n_lane # default 256 else: 257 # bidir 258 if osmattrs.has_key('lanes:forward'): 259 n_lane_forward_osm = int(osmattrs['lanes:forward']) 260 is_lanes_forward_rigid = True 261 if osmattrs.has_key('lanes:backward'): 262 n_lane_backward_osm = int(osmattrs['lanes:backward']) 263 is_lanes_backward_rigid = True 264 else: 265 n_lane_backward_osm = self.n_lane # default 266 267 elif osmattrs.has_key('lanes:backward'): 268 n_lane_backward_osm = int(osmattrs['lanes:backward']) 269 is_lanes_backward_rigid = True 270 n_lane_forward_osm = self.n_lane # default 271 272 else: 273 # no lane information 274 n_lane_forward_osm = self.n_lane # default 275 n_lane_backward_osm = self.n_lane # default 276 277 n_lane_osm = n_lane_forward_osm+n_lane_backward_osm 278 279 self._is_lanes_backward_rigid = is_lanes_backward_rigid 280 self._is_lanes_forward_rigid = is_lanes_forward_rigid 281 282 self._n_lane_forward_osm = n_lane_forward_osm 283 self._n_lane_backward_osm = n_lane_backward_osm 284 self._n_lane_osm = n_lane_osm 285 print ' lane numbers: n_lane_forward_osm=%d, n_lane_backward_osm=%d n_default=%d' % ( 286 n_lane_forward_osm, n_lane_backward_osm, self.n_lane) 287 288 def _get_access(self, access_str): 289 access_data = np.array(access_str.split('|'), dtype=np.object)[::-1] 290 return access_data == 'designated', access_data == 'no' 291 292 def get_laneaccess(self, vname, is_opp=False): 293 if is_opp: 294 if self._is_lanes_backward_rigid: 295 osmattrs = self._osmattrs 296 access_str = osmattrs.get(vname+':lanes', '') 297 if access_str != '': 298 allowed, disallowed = self._get_access(access_str) 299 return allowed[:self._n_lane_backward_osm], disallowed[:self._n_lane_backward_osm] 300 301 else: 302 access_str = osmattrs.get(vname+':lanes:backward', '') 303 if access_str != '': 304 allowed, disallowed = self._get_access(access_str) 305 return allowed, disallowed 306 307 else: 308 return [], [] 309 310 else: 311 return [], [] 312 313 else: 314 if self._is_lanes_forward_rigid: 315 osmattrs = self._osmattrs 316 access_str = osmattrs.get(vname+':lanes', '') 317 if access_str != '': 318 allowed, disallowed = self._get_access(access_str) 319 return allowed[self._n_lane_backward_osm:], disallowed[self._n_lane_backward_osm:] 320 321 else: 322 access_str = osmattrs.get(vname+':lanes:forward', '') 323 if access_str != '': 324 allowed, disallowed = self._get_access(access_str) 325 return allowed, disallowed 326 327 else: 328 return [], [] 329 330 else: 331 return [], [] 332 333 def make_road(self): 334 """ 335 Makes road lanes in both directions 336 """ 337 338 #lanes = [] 339 #lanes_opp = [] 340 print ' realoneway', self.is_oneway() 341 342 #self._lanes = [] 343 #self._lanes_opp = [] 344 345 print ' Main Dir ^^^^^^^^^^^' 346 if self._is_lanes_forward_rigid: 347 self.make_lanes_rigid(is_opp=False, n_lane_osm=self._n_lane_forward_osm) 348 else: 349 self.make_lanes(is_opp=False, n_lane_osm=self._n_lane_forward_osm) 350 351 if not self.is_oneway(): 352 353 print ' Opp Dir vvvvvvvvvvv' 354 if self._is_lanes_backward_rigid: 355 self.make_lanes_rigid(is_opp=True, n_lane_osm=self._n_lane_backward_osm) 356 else: 357 self.make_lanes(is_opp=True, n_lane_osm=self._n_lane_backward_osm) 358 359 print ' id', id(self) 360 print ' len(self._lanes)', len(self._lanes) 361 print ' len(self._lanes_opp)', len(self._lanes_opp) 362 363 def _get_speedinfo(self, speed_max_str): 364 speed_max_data = speed_max_str.split(' ') 365 if len(speed_max_data) == 1: 366 #speed_max_data = speed_max_data[0].split(';') 367 # TODO: here we could do a per lane assignment 368 return float(speed_max_data[0])/3.6 369 else: 370 371 # todo 372 # maxspeed=60 373 # maxspeed=50 mph 374 # maxspeed=10 knots 375 unit = speed_max_data[1] 376 if unit == 'mph': 377 return float(speed_max_data[0])/3.6*1.609344 378 379 elif unit == 'knots': 380 return float(speed_max_data[0])/3.6*1.852 381 382 def make_speed(self, speed_max_default): 383 # estimate speed max in m/s 384 if self._osmattrs.has_key('maxspeed'): 385 speed_max_str = self._osmattrs['maxspeed'] 386 if speed_max_str.count(';') > 0: 387 speed_max = np.inf 388 for v_str in speed_max_str.split(';'): 389 v = self._get_speedinfo(v_str) 390 if v < speed_max: 391 speed_max = v 392 393 else: 394 speed_max = self._get_speedinfo(speed_max_str) 395 else: 396 speed_max = speed_max_default 397 398 self.speed_max = speed_max 399 400 def _is_opposite(self, osmattrs, tag): 401 if osmattrs.has_key(tag): 402 elems = osmattrs[tag].split('_') 403 return elems[0] == 'opposite' 404 else: 405 return False 406 407 def is_oneway(self): 408 return self._is_oneway 409 410 def make_oneway(self): 411 # print 'make_oneway' 412 osmattrs = self._osmattrs 413 414 if osmattrs.get('junction', '') == 'roundabout': 415 self._is_oneway = True 416 417 elif osmattrs.has_key('oneway'): 418 if osmattrs['oneway'] == 'no': 419 self._is_oneway = False 420 421 else: 422 if self._is_opposite(osmattrs, 'busway'): 423 self._is_oneway = False 424 425 elif self._is_opposite(osmattrs, 'busway:right'): 426 self._is_oneway = False 427 428 elif osmattrs.has_key('lanes:bus:backward'): 429 self._is_oneway = False 430 431 elif osmattrs.has_key('trolley_wire:both'): 432 self._is_oneway = False 433 434 elif osmattrs.has_key('lanes:psv:backward'): 435 self._is_oneway = False 436 437 elif self._is_opposite(osmattrs, 'cycleway'): 438 self._is_oneway = False 439 440 elif self._is_opposite(osmattrs, 'busway'): 441 self._is_oneway = False 442 443 elif osmattrs.get('cycleway', '') == 'both': 444 self._is_oneway = False 445 446 # elif osmattrs.get('busway','') == 'both': 447 # self._is_oneway = False 448 449 # sidewalks on both sides go in the same direction 450 # elif osmattrs.get('sidewalk','') == 'both': 451 # self._is_oneway = False 452 453 elif osmattrs.has_key('oneway:bicycle'): 454 if osmattrs['oneway:bicycle'] == 'no': 455 self._is_oneway = False 456 457 else: 458 self._is_oneway = True 459 460 else: 461 self._is_oneway = True 462 463 else: 464 self._is_oneway = False 465 466 def add_sidewalk(self, road, is_opp=False): 467 """ 468 Method to explicitely add sidewalks with the given road attributes 469 """ 470 osmattrs = self._osmattrs 471 472 if is_opp: 473 ind = 0 474 else: 475 ind = 1 476 477 print 'add_sidewalk', is_opp, self._sidewalkattrs[ind]['n_lane'], self._sidewalkattrs[ind]['n_lane'] == 0 478 if self._sidewalkattrs[ind]['n_lane'] == 0: 479 self.make_sidewalk(is_opp=is_opp, is_rightside=True, width=road.lanewidth) 480 self.make_road() 481 482 # if self._is_oneway: 483 # # generate sidewalks in both directions 484 # ind = 1 485 # if self._sidewalkattrs[ind]['n_lane'] == 1: 486 # self.make_sidewalk(is_opp = False, is_rightside = False, width = road.lanewidth) 487 488 def make_sidewalk(self, is_opp=False, is_rightside=True, 489 ids_modes_allow=[], width=1.0, n_lane=1): 490 491 if is_opp: 492 ind = 0 493 else: 494 ind = 1 495 # !!!!foot=use_sidepath may be applied on the street 496 # to mark that sidewalks are mapped separately. 497 # Also, sidewalk=separate 498 499 print 'make_sidewalk', ind, is_rightside 500 # needed to merge access? 501 self._sidewalkattrs[ind]['is_share'] = len(ids_modes_allow) > 0 502 503 ids_allowed_set = [ID_MODE_PED] 504 for id_mode in ids_modes_allow: 505 if id_mode not in ids_allowed_set: 506 ids_allowed_set.append(id_mode) 507 508 self._sidewalkattrs[ind]['ids_modes_allow'] = list(ids_allowed_set) 509 self._sidewalkattrs[ind]['ids_modes_disallow'] = [] 510 if is_rightside: 511 self._sidewalkattrs[ind]['is_rightside'] = True 512 self._sidewalkattrs[ind]['width_rightside'] = width 513 self._sidewalkattrs[ind]['n_lane'] += n_lane 514 else: 515 self._sidewalkattrs[ind]['is_leftside'] = True 516 self._sidewalkattrs[ind]['width_leftside'] = width 517 self._sidewalkattrs[ind]['n_lane'] += n_lane 518 519 self._sidewalkattrs[ind]['speed_max'] = self.speed_max_ped 520 # print ' sidewalkattr=',self._sidewalkattrs[ind] 521 print_attrs(self._sidewalkattrs[ind]) 522 523 def make_sidewalkattrs(self): 524 print 'make_sidewalkattrs' 525 osmattrs = self._osmattrs 526 self._sidewalkattrs = (deepcopy(LANEATTRS_DEFAULT), 527 deepcopy(LANEATTRS_DEFAULT)) 528 529 sidewalk = osmattrs.get('sidewalk', 'auto') 530 531 if sidewalk not in ['no', 'none', 'auto']: 532 # there is a sidewalk, make sure there is at least one 533 534 if osmattrs.has_key('sidewalk:width'): 535 width_left = float(osmattrs['sidewalk:width']) 536 width_right = width_left 537 538 elif osmattrs.has_key('sidewalk:both:width'): 539 width_left = float(osmattrs['sidewalk:both:width']) 540 width_right = width_left 541 else: 542 width_left = float(osmattrs.get('sidewalk:left:width', self.width_sidewalk)) 543 width_right = float(osmattrs.get('sidewalk:right:width', self.width_sidewalk)) 544 545 if osmattrs.get('oneway', 'no') == 'no': 546 # bidirecional 547 548 if sidewalk == 'both': 549 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 550 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 551 552 elif sidewalk == 'left': 553 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 554 555 elif sidewalk == 'right': 556 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 557 558 else: 559 # no indication means both 560 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 561 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 562 563 else: 564 # oneway 565 if sidewalk == 'both': 566 # both sidewalks go in the same direction 567 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 568 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 569 570 elif sidewalk == 'left': 571 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 572 573 elif sidewalk == 'right': 574 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 575 576 else: 577 # no indication means both 578 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 579 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 580 581 # if no siedewalk width_sidewalk = -1 582 #self.width_sidewalk = max(widths) 583 # print ' sidewalkattr='#,self._sidewalkattrs 584 # for attrs in self._sidewalkattrs: 585 # if attrs['n_lane']>0: 586 # print_attrs(attrs) 587 588 def make_bikelane(self, is_opp=False, is_rightside=True, 589 ids_modes_allow=[], width=1.5, n_lane=1): 590 print 'make_bikelane', is_opp, is_rightside, ids_modes_allow 591 if is_opp: 592 ind = 0 593 else: 594 ind = 1 595 596 # needed to merge access? 597 self._bikewayattrs[ind]['is_share'] = len(ids_modes_allow) > 0 598 599 ids_allowed_set = deepcopy(self.ids_modes_bike) 600 for id_mode in ids_modes_allow: 601 if id_mode not in ids_allowed_set: 602 ids_allowed_set.append(id_mode) 603 604 self._bikewayattrs[ind]['ids_modes_allow'] = list(ids_allowed_set) 605 self._bikewayattrs[ind]['ids_modes_disallow'] = [] 606 if is_rightside: 607 self._bikewayattrs[ind]['is_rightside'] = True 608 self._bikewayattrs[ind]['width_rightside'] = width 609 self._bikewayattrs[ind]['n_lane'] += n_lane 610 else: 611 self._bikewayattrs[ind]['is_leftside'] = True 612 self._bikewayattrs[ind]['width_leftside'] = width 613 self._bikewayattrs[ind]['n_lane'] += n_lane 614 615 self._bikewayattrs[ind]['speed_max'] = self.speed_max_bike 616 617 print_attrs(self._bikewayattrs[ind]) 618 619 def make_bikewayattrs(self): 620 """ Returns a tuple with attribute dictionaries for bikeways 621 on left and right side of the road. 622 Dictionary with the following keys: 623 widths: is a tuple with sidewalk widths of left and right sidewalk. 624 if values are less than 0 means no sidewalk. 625 """ 626 print 'make_bikewayattrs' 627 self._bikewayattrs = (deepcopy(LANEATTRS_DEFAULT), 628 deepcopy(LANEATTRS_DEFAULT)) 629 630 osmattrs = self._osmattrs 631 cycleway = osmattrs.get('cycleway', '') 632 cycleway_left = osmattrs.get('cycleway:left', '') 633 cycleway_right = osmattrs.get('cycleway:right', '') 634 635 if osmattrs.has_key('cycleway:width'): 636 width_left = float(osmattrs['cycleway:width']) 637 width_right = width_left 638 639 elif osmattrs.has_key('cycleway:both:width'): 640 width_left = float(osmattrs['cycleway:both:width']) 641 width_right = width_left 642 643 else: 644 width_left = float(osmattrs.get('cycleway:left:width', self.lanewidth_bike)) 645 width_right = float(osmattrs.get('cycleway:right:width', self.lanewidth_bike)) 646 647 if osmattrs.get('oneway', 'no') == 'no': 648 # cycle lanes on bidir road 649 650 if cycleway in LANEATTRS: 651 self.make_bikelane(is_opp=False, width=width_right) 652 self.make_bikelane(is_opp=True, width=width_left) 653 return 654 655 elif cycleway in OSMKEYS_SHARED: 656 self.make_bikelane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 657 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 658 return 659 660 elif cycleway in OSMKEYS_SHARED_OPP: 661 self.make_bikelane(is_opp=False, width=width_right) 662 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 663 return 664 665 cycleway = osmattrs.get('cycleway:both', '') 666 if cycleway in LANEATTRS: 667 self.make_bikelane(is_opp=False, width=width_right) 668 self.make_bikelane(is_opp=True, width=width_left) 669 return 670 671 elif cycleway in OSMKEYS_SHARED: 672 self.make_bikelane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 673 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 674 return 675 676 #cycleway = osmattrs.get('cycleway:left','') 677 if (cycleway_left != '') & (cycleway_right != ''): 678 # also both sides 679 if cycleway_left in LANEATTRS: 680 self.make_bikelane(is_opp=True, is_rightside=False, width=width_left) 681 elif cycleway_left in OSMKEYS_SHARED: 682 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared) 683 684 if cycleway_right in LANEATTRS: 685 self.make_bikelane(is_opp=False, is_rightside=False, width=width_left) 686 elif cycleway_right in OSMKEYS_SHARED: 687 self.make_bikelane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared) 688 689 # check left only 690 elif cycleway_left in LANEATTRS: 691 self.make_bikelane(is_opp=True, is_rightside=False, width=width_left) 692 return 693 694 elif cycleway_left in OSMKEYS_SHARED: 695 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared) 696 # if osmattrs.get('bicycle','no') == 'yes': 697 # self.make_bikelane(is_opp = False, is_rightside = True,width = width_right) 698 699 # check right only 700 elif cycleway_right in LANEATTRS: 701 self.make_bikelane(is_opp=False, is_rightside=True) 702 703 elif cycleway_right == 'opposite_share_busway': 704 self.make_bikelane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 705 # if osmattrs.get('bicycle','no') == 'yes': 706 # self.make_bikelane(is_opp = False, is_rightside = True,width = width_right) 707 708 # general bicycle tag if all from abive fails but share with pedestrians 709 elif osmattrs.get('bicycle', 'no') == 'yes': 710 # check if there are cycle lanes already 711 if (self._bikewayattrs[0]['n_lane'] == 0) & (self._bikewayattrs[1]['n_lane'] == 0): 712 self.make_bikelane(is_opp=False, is_rightside=True, 713 width=width_right, ids_modes_allow=[ID_MODE_PED, ]) 714 self.make_bikelane(is_opp=True, is_rightside=True, width=width_left, 715 ids_modes_allow=[ID_MODE_PED, ]) 716 717 else: 718 # cycle lanes on oneway road 719 720 if cycleway in LANEATTRS: 721 722 self.make_bikelane(is_opp=False) 723 724 if osmattrs.get('oneway:bicycle', 'yes') == 'no': 725 self.make_bikelane(is_opp=True, width=width_left) 726 # else: 727 # self.make_bikelane(is_opp = False, width = width_right) 728 return 729 730 elif cycleway == 'opposite': 731 self.make_bikelane(is_opp=True, is_rightside=True, width=width_left) 732 # if osmattrs.get('bicycle','no') == 'yes': 733 # self.make_bikelane(is_opp = False, is_rightside = True, width = width_right) 734 return 735 736 elif cycleway == 'opposite_share_busway': 737 self.make_bikelane(is_opp=True, is_rightside=True, 738 ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 739 # if osmattrs.get('bicycle','no') == 'yes': 740 # self.make_bikelane(is_opp = False, is_rightside = True,width = width_right) 741 return 742 743 if cycleway == 'both': 744 # attention with this key a cycle lane in the opposite direction 745 # will be created as it makes no sense to have bikelanes 746 # in the smae direction on both sides 747 self.make_bikelane(is_opp=False, is_rightside=True, width=width_right) 748 self.make_bikelane(is_opp=True, is_rightside=True, width=width_left) 749 750 elif cycleway_right in LANEATTRS: 751 self.make_bikelane(is_opp=False, width=width_right) 752 753 elif cycleway_left in LANEATTRS: 754 self.make_bikelane(is_opp=False, is_rightside=False, width=width_right) 755 756 elif cycleway_left == 'opposite_lane': 757 self.make_bikelane(is_opp=True, is_rightside=True, width=width_left) 758 # if osmattrs.get('bicycle','no') == 'yes': 759 # self.make_bikelane(is_opp = False, is_rightside = True,width = width_right) 760 761 elif osmattrs.get('oneway:bicycle', '') == 'no': 762 self.make_bikelane(is_opp=True, is_rightside=False, width=width_right) 763 # if (osmattrs.get('bicycle','no') == 'yes'): 764 # # check if there are cycle lanes already 765 # if (self._bikewayattrs[1]['n_lane'] == 0): 766 # self.make_bikelane(is_opp = False, is_rightside = True, width = width_right) 767 768 # if (osmattrs.get('bicycle','no') == 'yes'): 769 # # check if there are cycle lanes already 770 # if (self._bikewayattrs[1]['n_lane'] == 0): 771 # self.make_bikelane(is_opp = False, is_rightside = True, width = width_right) 772 773 # print ' bikewayattrs='#,self._bikewayattrs 774 # for attrs in self._bikewayattrs: 775 # if attrs['n_lane']>0: 776 # print_attrs(attrs) 777 778 def make_buslane(self, is_opp=False, is_rightside=True, 779 ids_modes_allow=[], width=3.5, n_lane=1): 780 print 'make_buslane', is_opp, is_rightside, width 781 if is_opp: 782 ind = 0 783 else: 784 ind = 1 785 786 #self._buswayattrs[ind]['is_share'] = len(ids_modes_allow)>0 787 788 ids_allowed_set = deepcopy(self.ids_modes_pt_shared) 789 for id_mode in ids_modes_allow: 790 if id_mode not in ids_allowed_set: 791 ids_allowed_set.append(id_mode) 792 793 self._buswayattrs[ind]['ids_modes_allow'] = list(ids_allowed_set) 794 self._buswayattrs[ind]['ids_modes_disallow'] = [] 795 796 if is_rightside: 797 self._buswayattrs[ind]['is_rightside'] = True 798 self._buswayattrs[ind]['width_rightside'] = width 799 self._buswayattrs[ind]['n_lane'] += n_lane 800 else: 801 self._buswayattrs[ind]['is_leftside'] = True 802 self._buswayattrs[ind]['width_leftside'] = width 803 self._buswayattrs[ind]['n_lane'] += n_lane 804 # print ' buswayattr',self._buswayattrs[ind] 805 self._buswayattrs[ind]['speed_max'] = self.speed_max_bus 806 print_attrs(self._buswayattrs[ind]) 807 808 def make_buswayattrs(self): 809 print 'make_buswayattrs' 810 self._buswayattrs = (deepcopy(LANEATTRS_DEFAULT), 811 deepcopy(LANEATTRS_DEFAULT)) 812 813 osmattrs = self._osmattrs 814 815 if osmattrs.has_key('busway:width'): 816 width_left = float(osmattrs['busway:width']) 817 width_right = width_left 818 819 elif osmattrs.has_key('busway:both:width'): 820 width_left = float(osmattrs['busway:both:width']) 821 width_right = width_left 822 else: 823 width_left = float(osmattrs.get('busway:left:width', self.lanewidth_bus)) 824 width_right = float(osmattrs.get('busway:right:width', self.lanewidth_bus)) 825 826 busway = osmattrs.get('busway', '') 827 828 if busway is not "": 829 # busway scheme 830 if osmattrs.get('oneway', 'no') == 'no': 831 # bidir 832 print ' buslane bidir', busway 833 if busway == 'lane': 834 self.make_buslane(is_opp=False) 835 self.make_buslane(is_opp=True) 836 return 837 838 elif busway in OSMKEYS_SHARED: 839 self.make_buslane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 840 self.make_buslane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 841 return 842 843 busway = osmattrs.get('busway:both', '') 844 if busway == 'lane': 845 self.make_buslane(is_opp=False) 846 self.make_buslane(is_opp=True) 847 return 848 849 elif busway in OSMKEYS_SHARED: 850 self.make_buslane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 851 self.make_buslane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 852 853 # elif busway in OSMKEYS_SHARED_OPP : 854 # self.make_buslane(is_opp = True, ids_modes_allow = self.ids_modes_pt_shared) 855 856 busway = osmattrs.get('busway:left', '') 857 if busway == 'lane': 858 self.make_buslane(is_opp=True, is_rightside=False, width=width_left) 859 860 elif busway in OSMKEYS_SHARED: 861 self.make_buslane(is_opp=True, is_rightside=False, 862 ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 863 864 elif busway in OSMKEYS_SHARED_OPP: 865 self.make_buslane(is_opp=True, is_rightside=False, 866 ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 867 868 busway = osmattrs.get('busway:right', '') 869 if busway == 'lane': 870 self.make_buslane(is_opp=False) 871 872 elif busway in OSMKEYS_SHARED: 873 self.make_buslane(is_opp=False, ids_modes_allow=self.ids_modes_pt_shared, width=width_right) 874 875 elif busway in OSMKEYS_SHARED_OPP: 876 self.make_buslane(is_opp=True, ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 877 878 return 879 880 else: 881 # cycle lanes on oneway road 882 print ' buslane oneway', busway, busway in ('opposite', 'opposite_lane') 883 if busway == 'lane': 884 self.make_buslane(is_opp=False, width=width_right) 885 886 if osmattrs.get('oneway:bus', 'yes') == 'no': 887 self.make_buslane(is_opp=True, width=width_left) 888 return 889 890 elif busway in ('opposite', 'opposite_lane'): 891 self.make_buslane(is_opp=True, is_rightside=False, width=width_left) 892 893 elif busway == 'opposite_share_busway': 894 self.make_buslane(is_opp=True, is_rightside=False, 895 ids_modes_allow=self.ids_modes_pt_shared, width=width_left) 896 897 elif self._osmattrs.get('busway:right', '') == 'lane': 898 self.make_buslane(is_opp=False, width=width_right) 899 900 elif self._osmattrs.get('busway:left', '') == 'lane': 901 self.make_buslane(is_opp=False, is_rightside=False, width=width_right) 902 903 elif self._osmattrs.get('busway:left', '') == 'opposite_lane': 904 self.make_buslane(is_opp=True, width=width_left) 905 906 return 907 908 elif osmattrs.has_key('lanes:psv'): 909 # lanes:psv=* scheme 910 if osmattrs.get('oneway', 'no') == 'no': 911 # bidir 912 pvs = int(osmattrs.get('lanes:psv', '1')) 913 if pvs/2 > 1: 914 self.make_buslane(is_opp=True, n_lane=pvs/2, width=width_right) 915 self.make_buslane(is_opp=False, n_lane=pvs/2, width=width_left) 916 else: 917 self.make_buslane(is_opp=False, n_lane=1, width=width_right) 918 else: 919 # oneway 920 pvs = int(osmattrs.get('lanes:psv', '1')) 921 self.make_buslane(is_opp=False, n_lane=pvs, width=width_right) 922 return 923 924 elif osmattrs.has_key('lanes:bus'): 925 # lanes:psv=* scheme 926 if osmattrs.get('oneway', 'no') == 'no': 927 # bidir 928 pvs = int(osmattrs.get('lanes:bus', '1')) 929 if pvs/2 > 1: 930 self.make_buslane(is_opp=True, n_lane=pvs/2, width=width_right) 931 self.make_buslane(is_opp=False, n_lane=pvs/2, width=width_left) 932 else: 933 self.make_buslane(is_opp=False, n_lane=1, width=width_right) 934 else: 935 # oneway 936 pvs = int(osmattrs.get('lanes:bus', '1')) 937 self.make_buslane(is_opp=False, n_lane=pvs, width=width_right) 938 return 939 940 if osmattrs.has_key('lanes:psv:forward'): 941 self.make_buslane(is_opp=False, n_lane=int(osmattrs['lanes:psv:forward']), width=width_right) 942 943 if osmattrs.has_key('lanes:psv:backward'): 944 self.make_buslane(is_opp=True, n_lane=int(osmattrs['lanes:psv:backward']), width=width_left) 945 946 if osmattrs.has_key('lanes:bus:forward'): 947 self.make_buslane(is_opp=False, n_lane=int(osmattrs['lanes:bus:forward']), width=width_right) 948 949 if osmattrs.has_key('lanes:bus:backward'): 950 self.make_buslane(is_opp=True, n_lane=int(osmattrs['lanes:bus:backward']), width=width_left) 951 952 if osmattrs.get('oneway', 'no') == 'yes': 953 # special check of opposite bus lane 954 if osmattrs.has_key('trolley_wire:both') | osmattrs.has_key('trolley_wire:backward'): 955 # if way is oneway withot reserved access, 956 # but there are wires in both ways, 957 # then there is probably a reserved bus lane in opposite 958 # direction 959 if self._buswayattrs[0]['n_lane'] == 0: 960 self.make_buslane(is_opp=True, width=width_right) 961 962 # print ' buswayattrs=',self._buswayattrs 963 # for attrs in self._buswayattrs: 964 # if attrs['n_lane']>0: 965 # print_attrs(attrs) 966 967 def get_priority(self, is_opp=False): 968 """ 969 Returns priority of road. 970 971 To be overridden. 972 """ 973 if is_opp: 974 lanes = self._lanes_opp 975 else: 976 lanes = self._lanes 977 978 speed_max = self.get_speed_max() 979 n_lane = len(lanes) 980 # is_residential =... 981 if n_lane == 0: 982 return 0 983 984 if n_lane == 1: 985 if speed_max < 11.0/3.6: 986 return 1 987 elif speed_max <= 31.0/3.6: 988 return 2 989 elif speed_max <= 51.0/3.6: 990 return 3 991 else: 992 return 4 993 994 elif n_lane == 2: 995 if speed_max < 11.0/3.6: 996 return 4 997 elif speed_max <= 31.0/3.6: 998 return 5 999 elif speed_max <= 51.0/3.6: 1000 return 6 1001 else: 1002 return 7 1003 1004 elif n_lane == 3: 1005 if speed_max < 11.0/3.6: 1006 return 5 1007 elif speed_max <= 31.0/3.6: 1008 return 6 1009 elif speed_max <= 51.0/3.6: 1010 return 7 1011 elif speed_max <= 111.0/3.6: 1012 return 8 1013 else: 1014 return 9 1015 1016 elif n_lane > 3: 1017 if speed_max < 11.0/3.6: 1018 return 6 1019 elif speed_max <= 51.0/3.6: 1020 return 7 1021 elif speed_max <= 91.0/3.6: 1022 return 8 1023 elif speed_max <= 111.0/3.6: 1024 return 9 1025 else: 1026 return 10 1027 1028 def merge_laneattrs(self, laneattrs_dest, laneattrs_merge, is_rightside=False, is_leftside=False): 1029 print 'merge_laneattrs' 1030 # print ' laneattrs_dest',laneattrs_dest 1031 # print ' laneattrs_merge',laneattrs_merge 1032 #self._buswayattrs[ind]['ids_modes_allow'] = ids_allowed 1033 #self._buswayattrs[ind]['width'] = width 1034 #self._buswayattrs[ind]['is_rightside'] = is_rightside 1035 # if laneattrs_merge['width']>laneattrs_dest['width']: 1036 width_dest = 0.0 1037 if laneattrs_dest.has_key('width'): 1038 width_dest = laneattrs_dest['width'] 1039 else: 1040 if is_rightside: 1041 width_dest = laneattrs_dest['width_rightside'] 1042 else: 1043 width_dest = laneattrs_dest['width_leftside'] 1044 1045 if laneattrs_merge.has_key('width'): 1046 width_merge = laneattrs_merge['width'] 1047 else: 1048 if is_rightside: 1049 width_merge = laneattrs_merge['width_rightside'] 1050 else: 1051 width_merge = laneattrs_merge['width_leftside'] 1052 1053 # if width_dest<width_merge: 1054 # laneattrs_dest['width'] = width_merge 1055 # else: 1056 laneattrs_dest['width'] = width_dest 1057 1058 if laneattrs_dest['speed_max'] > laneattrs_merge['speed_max']: 1059 laneattrs_dest['speed_max'] = laneattrs_merge['speed_max'] 1060 1061 self.disallow_on_lane(laneattrs_dest, laneattrs_merge['ids_modes_disallow']) 1062 self.allow_on_lane(laneattrs_dest, laneattrs_merge['ids_modes_allow']) 1063 1064 def append_lane(self, lanes, laneattrs, is_rightside=False, is_leftside=False): 1065 if is_rightside: 1066 lanes.insert(0, deepcopy(laneattrs)) 1067 lanes[0]['width'] = laneattrs['width_rightside'] 1068 1069 elif is_leftside: 1070 lanes.append(deepcopy(laneattrs)) 1071 lanes[-1]['width'] = laneattrs['width_leftside'] 1072 1073 def set_lane(self, lanes, laneattrs, ind): 1074 lanes[ind] = deepcopy(laneattrs) 1075 if not laneattrs.has_key('width'): 1076 if laneattrs.has_key('width_rightside'): 1077 lanes[ind]['width'] = laneattrs['width_rightside'] 1078 else: 1079 lanes[ind]['width'] = laneattrs['width_rightside'] 1080 1081 def disallow_on_lane(self, laneattrs, ids_disallow): 1082 # print 'disallow_on_lane ids_disallow',ids_disallow 1083 for id_disallow in ids_disallow: 1084 if id_disallow in laneattrs['ids_modes_allow']: 1085 laneattrs['ids_modes_allow'].remove(id_disallow) 1086 1087 if len(laneattrs['ids_modes_allow']) == 0: 1088 for id_disallow in ids_disallow: 1089 if id_disallow not in laneattrs['ids_modes_disallow']: 1090 laneattrs['ids_modes_disallow'].append(id_disallow) 1091 else: 1092 laneattrs['ids_modes_disallow'] = [] 1093 1094 def allow_on_lane(self, laneattrs, ids_allow): 1095 laneattrs['ids_modes_disallow'] = [] 1096 1097 for id_allow in ids_allow: 1098 if id_allow not in laneattrs['ids_modes_allow']: 1099 laneattrs['ids_modes_allow'].append(id_allow) 1100 1101 def make_lanes_rigid(self, is_opp=False, n_lane_osm=0): 1102 print 'make_lanes_rigid', is_opp, n_lane_osm 1103 osmattrs = self._osmattrs 1104 1105 if is_opp: 1106 ind = 0 1107 if self._is_oneway: 1108 self._lanes_opp = [] 1109 return False 1110 else: 1111 ind = 1 1112 1113 lanes = [] 1114 for i in range(n_lane_osm): 1115 lanes.append(deepcopy(self._laneattrs_main)) 1116 1117 # if is_lanes_rigid: 1118 # # respect given lane numbers for main modes, except footpath 1119 # pass 1120 # else: 1121 1122 # do busways 1123 attrs = self._buswayattrs[ind] 1124 1125 if attrs['n_lane'] > 0: 1126 print ' busways n_lane', attrs['n_lane'] 1127 1128 n_lane = len(lanes) 1129 1130 allowed, disallowed = self.get_laneaccess('bus', is_opp=is_opp) 1131 if len(allowed) == 0: 1132 allowed, disallowed = self.get_laneaccess('psv', is_opp=is_opp) 1133 1134 n_allow = len(allowed) 1135 if n_allow > 0: 1136 for i, a, d in zip(xrange(n_allow), allowed, disallowed): 1137 if ind < n_lane: 1138 if a & (i < n_lane): 1139 self.set_lane(lanes, attrs, i) 1140 if d: 1141 self.disallow_on_lane(lanes[i], attrs['ids_modes_disallow']) 1142 1143 else: 1144 n_lane_assig = attrs['n_lane'] 1145 for i in range(n_lane): 1146 if n_lane_assig > 0: 1147 if attrs['is_rightside']: 1148 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1149 n_lane_assig -= 1 1150 1151 if attrs['is_leftside']: 1152 self.merge_laneattrs(lanes[n_lane-i-1], attrs, is_leftside=True) 1153 n_lane_assig -= 1 1154 1155 # do bikeways 1156 attrs = self._bikewayattrs[ind] 1157 if attrs['n_lane'] > 0: 1158 print ' bikeways n_lane', attrs['n_lane'] 1159 1160 n_lane = len(lanes) 1161 1162 allowed, disallowed = self.get_laneaccess('bicycle', is_opp=is_opp) 1163 1164 n_allow = len(allowed) 1165 if n_allow > 0: 1166 for i, a, d in zip(xrange(n_allow), allowed, disallowed): 1167 if i < n_lane: 1168 if a & i < n_lane: 1169 self.set_lane(lanes, attrs, i) 1170 if d: 1171 self.disallow_on_lane(lanes[i], attrs['ids_modes_disallow']) 1172 1173 else: 1174 n_lane_assig = attrs['n_lane'] 1175 for i in range(n_lane): 1176 if n_lane_assig > 0: 1177 if attrs['is_rightside']: 1178 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1179 n_lane_assig -= 1 1180 1181 if attrs['is_leftside']: 1182 self.merge_laneattrs(lanes[n_lane-i-1], attrs, is_leftside=True) 1183 n_lane_assig -= 1 1184 1185 # do sidewalks 1186 attrs = self._sidewalkattrs[ind] 1187 if attrs['n_lane'] > 0: 1188 print ' sidewalks n_lane', attrs['n_lane'] 1189 n_lane_assig = attrs['n_lane'] 1190 n_lane = len(lanes) 1191 # sidewalks are not considered lanes in osm 1192 # so we append/prepend them 1193 while n_lane_assig > 0: 1194 if attrs['is_rightside']: 1195 if attrs['is_share'] & (len(lanes) > 0): 1196 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1197 else: 1198 self.append_lane(lanes, attrs, is_rightside=True) 1199 n_lane_assig -= 1 1200 if attrs['is_leftside']: 1201 if attrs['is_share'] & (len(lanes) > 0): 1202 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1203 else: 1204 self.append_lane(lanes, attrs, is_leftside=True) 1205 n_lane_assig -= 1 1206 1207 # disallow pedestrians on other lanes 1208 # 1209 for laneattrs in lanes: 1210 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 1211 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 1212 1213 if is_opp: 1214 self._lanes_opp = lanes 1215 else: 1216 self._lanes = lanes 1217 print ' created %d lanes' % len(lanes) 1218 # print ' lanes', lanes 1219 for laneattrs in lanes: 1220 print_attrs(laneattrs) 1221 return True 1222 1223 def make_lanes(self, is_opp=False, n_lane_osm=0): 1224 print 'make_lanes', is_opp, n_lane_osm 1225 osmattrs = self._osmattrs 1226 is_lanes_rigid = False 1227 1228 if is_opp: 1229 ind = 0 1230 if self._is_oneway: 1231 self._lanes_opp = [] 1232 return False 1233 else: 1234 ind = 1 1235 1236 lanes = [] 1237 for i in range(n_lane_osm): 1238 lanes.append(deepcopy(self._laneattrs_main)) 1239 1240 # do busways 1241 attrs = self._buswayattrs[ind] 1242 if attrs['n_lane'] > 0: 1243 print ' busways n_lane', attrs['n_lane'] 1244 n_lane_assig = attrs['n_lane'] 1245 n_lane = len(lanes) 1246 1247 while n_lane_assig > 0: 1248 if attrs['is_rightside']: 1249 self.append_lane(lanes, attrs, is_rightside=True) 1250 n_lane_assig -= 1 1251 if attrs['is_leftside']: 1252 self.append_lane(lanes, attrs, is_leftside=True) 1253 n_lane_assig -= 1 1254 1255 # do bikeways 1256 attrs = self._bikewayattrs[ind] 1257 if attrs['n_lane'] > 0: 1258 print ' bikeways n_lane', attrs['n_lane'] 1259 n_lane_assig = attrs['n_lane'] 1260 n_lane = len(lanes) 1261 1262 while n_lane_assig > 0: 1263 if attrs['is_rightside']: 1264 if attrs['is_share'] & (len(lanes) > 0): 1265 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1266 else: 1267 self.append_lane(lanes, attrs, is_rightside=True) 1268 n_lane_assig -= 1 1269 1270 if attrs['is_leftside']: 1271 if attrs['is_share'] & (len(lanes) > 0): 1272 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1273 else: 1274 self.append_lane(lanes, attrs, is_leftside=True) 1275 n_lane_assig -= 1 1276 1277 # do sidewalks 1278 attrs = self._sidewalkattrs[ind] 1279 if attrs['n_lane'] > 0: 1280 print ' sidewalks n_lane', attrs['n_lane'] 1281 n_lane_assig = attrs['n_lane'] 1282 n_lane = len(lanes) 1283 # sidewalks are not considered lanes in osm 1284 # so we append/prepend them 1285 while n_lane_assig > 0: 1286 if attrs['is_rightside']: 1287 if attrs['is_share'] & (len(lanes) > 0): 1288 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1289 else: 1290 self.append_lane(lanes, attrs, is_rightside=True) 1291 n_lane_assig -= 1 1292 if attrs['is_leftside']: 1293 if attrs['is_share'] & (len(lanes) > 0): 1294 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1295 else: 1296 self.append_lane(lanes, attrs, is_leftside=True) 1297 n_lane_assig -= 1 1298 1299 # disallow pedestrians on other lanes 1300 # 1301 for laneattrs in lanes: 1302 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 1303 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 1304 1305 if is_opp: 1306 self._lanes_opp = lanes 1307 else: 1308 self._lanes = lanes 1309 print ' created %d lanes' % len(lanes) 1310 # print ' lanes', lanes 1311 for laneattrs in lanes: 1312 print_attrs(laneattrs) 1313 return True 1314 1315 def get_speed_max(self, is_opp=False): 1316 # TODO: go through lanes and get speed max 1317 return self.speed_max 1318 1319 def is_roundabout(self): 1320 return self._osmattrs.get('junction', '') == 'roundabout' 1321 1322 def configure_edge(self, id_edge, net, is_opp=False): 1323 print 'configure_edge', id_edge, net.edges.ids_sumo[id_edge], is_opp 1324 # print ' id',id(self) 1325 # print ' len(self._lanes)',len(self._lanes) 1326 # print ' len(self._lanes_opp)',len(self._lanes_opp) 1327 1328 osmattrs = self._osmattrs 1329 edges = net.edges 1330 if is_opp: 1331 ind = 0 1332 lanes = self._lanes_opp 1333 else: 1334 ind = 1 1335 lanes = self._lanes 1336 1337 if self._is_oneway: # & (not self.is_roundabout()): 1338 type_spread = 1 # centered 1339 else: 1340 type_spread = 0 # right spread 1341 1342 wayattrs = self._sidewalkattrs[ind] 1343 if wayattrs['n_lane'] > 0: 1344 width_sidewalk = max(wayattrs.get('width_leftside', -1), wayattrs.get('width_rightside', -1)) 1345 else: 1346 width_sidewalk = -1.0 1347 1348 # get max lane width 1349 lanewidth = 0.0 1350 for laneattrs in lanes: 1351 if laneattrs['width'] > lanewidth: 1352 lanewidth = laneattrs['width'] 1353 1354 edges.types[id_edge] = self.highway 1355 edges.nums_lanes[id_edge] = len(lanes) 1356 edges.types_spread[id_edge] = type_spread 1357 edges.speeds_max[id_edge] = self.get_speed_max(is_opp) 1358 edges.priorities[id_edge] = self.get_priority(is_opp) 1359 edges.names[id_edge] = osmattrs.get('name', '') 1360 edges.widths_lanes_default[id_edge] = lanewidth 1361 edges.widths_sidewalk[id_edge] = width_sidewalk 1362 # edges.[id_edge] = 1363 1364 # net.edges.set_row( id_edge, 1365 # types_spread = type_spread, 1366 # speeds_max = self.get_speed_max(is_opp), 1367 # priorities = self.get_priority(is_opp), 1368 # #'widths'=# will be done during update 1369 # names = osmattrs.get('name',''), 1370 # widths_lanes_default = lanewidth, 1371 # widths_sidewalk = width_sidewalk, 1372 # ) 1373 1374 # add lanes 1375 n_lane = len(lanes) 1376 if n_lane == 0: 1377 print 'WARNING: no lane for this direction!!' 1378 ids_lane = net.lanes.add_rows(n_lane) 1379 1380 for id_lane, ind_lane, laneattrs in zip(ids_lane, xrange(n_lane), lanes): 1381 if len(laneattrs['ids_modes_allow']) == 0: 1382 id_mode_main = self.id_mode 1383 else: 1384 id_mode_main = laneattrs['ids_modes_allow'][0] 1385 net.lanes.set_row(id_lane, 1386 indexes=ind_lane, 1387 widths=laneattrs['width'], 1388 speeds_max=laneattrs['speed_max'], 1389 #offsets_end = kwargs['offsets_end'], 1390 #ids_modes_allow = laneattrs['ids_modes_allow'], 1391 #ids_modes_disallow = laneattrs['ids_modes_disallow'], 1392 ids_mode=id_mode_main, 1393 ids_edge=id_edge, 1394 ) 1395 # must be done seperately!! 1396 net.lanes.ids_modes_allow[id_lane] = laneattrs['ids_modes_allow'] 1397 net.lanes.ids_modes_disallow[id_lane] = laneattrs['ids_modes_disallow'] 1398 1399 edges.ids_lanes[id_edge] = list(ids_lane) 1400 1401 1402class Primary(Road): 1403 1404 def config(self): 1405 """ 1406 Make defaults to be overridden 1407 """ 1408 Road.config(self) 1409 self.highway = self._osmattrs.get('highway', 'primary') 1410 # put 50km/h default speed limit 1411 self.make_speed(50.0/3.6) 1412 1413 self.n_lane = 2 1414 self.id_mode = ID_MODE_CAR 1415 self.lanewidth = 3.5 1416 1417 def get_priority(self, is_opp=False): 1418 """ 1419 Returns priority of road. 1420 1421 To be overridden. 1422 """ 1423 if is_opp: 1424 lanes = self._lanes_opp 1425 else: 1426 lanes = self._lanes 1427 1428 speed_max = self.get_speed_max() 1429 n_lane = len(lanes) 1430 # is_residential =... 1431 if n_lane == 0: 1432 return 0 1433 1434 elif n_lane <= 2: 1435 if speed_max <= 51.0/3.6: 1436 return 7 1437 elif speed_max <= 111.0/3.6: 1438 return 8 1439 else: 1440 return 9 1441 1442 elif n_lane == 3: 1443 if speed_max <= 51.0/3.6: 1444 return 7 1445 elif speed_max <= 91.0/3.6: 1446 return 8 1447 elif speed_max <= 111.0/3.6: 1448 return 9 1449 else: 1450 return 10 1451 1452 elif n_lane > 3: 1453 return 10 1454 1455 def make_lanes_rigid(self, is_opp=False, n_lane_osm=0): 1456 print 'make_lanes_rigid', is_opp, n_lane_osm 1457 osmattrs = self._osmattrs 1458 1459 if is_opp: 1460 ind = 0 1461 if self._is_oneway: 1462 self._lanes_opp = [] 1463 return False 1464 else: 1465 ind = 1 1466 1467 lanes = [] 1468 for i in range(n_lane_osm): 1469 lanes.append(deepcopy(self._laneattrs_main)) 1470 1471 # if is_lanes_rigid: 1472 # # respect given lane numbers for main modes, except footpath 1473 # pass 1474 # else: 1475 1476 # do busways 1477 attrs = self._buswayattrs[ind] 1478 1479 if attrs['n_lane'] > 0: 1480 print ' busways n_lane', attrs['n_lane'] 1481 1482 n_lane = len(lanes) 1483 1484 allowed, disallowed = self.get_laneaccess('bus', is_opp=is_opp) 1485 if len(allowed) == 0: 1486 allowed, disallowed = self.get_laneaccess('psv', is_opp=is_opp) 1487 1488 n_allow = len(allowed) 1489 if n_allow > 0: 1490 for i, a, d in zip(xrange(n_allow), allowed, disallowed): 1491 if ind < n_lane: 1492 if a & (i < n_lane): 1493 self.set_lane(lanes, attrs, i) 1494 if d: 1495 self.disallow_on_lane(lanes[i], attrs['ids_modes_disallow']) 1496 1497 else: 1498 n_lane_assig = attrs['n_lane'] 1499 for i in range(n_lane): 1500 if n_lane_assig > 0: 1501 if attrs['is_rightside']: 1502 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1503 n_lane_assig -= 1 1504 1505 if attrs['is_leftside']: 1506 self.merge_laneattrs(lanes[n_lane-i-1], attrs, is_leftside=True) 1507 n_lane_assig -= 1 1508 1509 # do bikeways 1510 attrs = self._bikewayattrs[ind] 1511 if attrs['n_lane'] > 0: 1512 print ' bikeways n_lane', attrs['n_lane'] 1513 1514 n_lane = len(lanes) 1515 1516 allowed, disallowed = self.get_laneaccess('bicycle', is_opp=is_opp) 1517 1518 n_allow = len(allowed) 1519 if n_allow > 0: 1520 for i, a, d in zip(xrange(n_allow), allowed, disallowed): 1521 if i < n_lane: 1522 if a & i < n_lane: 1523 self.set_lane(lanes, attrs, i) 1524 if d: 1525 self.disallow_on_lane(lanes[i], attrs['ids_modes_disallow']) 1526 1527 else: 1528 n_lane_assig = attrs['n_lane'] 1529 for i in range(n_lane): 1530 if n_lane_assig > 0: 1531 if attrs['is_rightside']: 1532 if is_opp: 1533 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1534 else: 1535 # in a primary link require 2 lanes for cars 1536 if n_lane_osm > 2: 1537 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1538 else: 1539 self.append_lane(lanes, attrs, is_rightside=True) 1540 n_lane_assig -= 1 1541 1542 if attrs['is_leftside']: 1543 self.merge_laneattrs(lanes[n_lane-i-1], attrs, is_leftside=True) 1544 n_lane_assig -= 1 1545 1546 # do sidewalks 1547 attrs = self._sidewalkattrs[ind] 1548 if attrs['n_lane'] > 0: 1549 print ' sidewalks n_lane', attrs['n_lane'] 1550 n_lane_assig = attrs['n_lane'] 1551 n_lane = len(lanes) 1552 # sidewalks are not considered lanes in osm 1553 # so we append/prepend them 1554 while n_lane_assig > 0: 1555 if attrs['is_rightside']: 1556 if attrs['is_share'] & (len(lanes) > 0): 1557 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1558 else: 1559 self.append_lane(lanes, attrs, is_rightside=True) 1560 n_lane_assig -= 1 1561 1562 if attrs['is_leftside']: 1563 if attrs['is_share'] & (len(lanes) > 0): 1564 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1565 else: 1566 self.append_lane(lanes, attrs, is_leftside=True) 1567 n_lane_assig -= 1 1568 1569 # disallow pedestrians on other lanes 1570 # 1571 for laneattrs in lanes: 1572 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 1573 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 1574 1575 if is_opp: 1576 self._lanes_opp = lanes 1577 else: 1578 self._lanes = lanes 1579 print ' created %d lanes' % len(lanes) 1580 # print ' lanes', lanes 1581 for laneattrs in lanes: 1582 print_attrs(laneattrs) 1583 return True 1584 1585 def make_lanes(self, is_opp=False, n_lane_osm=0): 1586 print 'make_lanes primary', is_opp, n_lane_osm 1587 osmattrs = self._osmattrs 1588 #is_lanes_rigid = False 1589 1590 if is_opp: 1591 ind = 0 1592 if self._is_oneway: 1593 self._lanes_opp = [] 1594 return False 1595 else: 1596 ind = 1 1597 1598 lanes = [] 1599 for i in range(n_lane_osm): 1600 lanes.append(deepcopy(self._laneattrs_main)) 1601 1602 # do busways 1603 attrs = self._buswayattrs[ind] 1604 if attrs['n_lane'] > 0: 1605 print ' busways n_lane', attrs['n_lane'] 1606 n_lane_assig = attrs['n_lane'] 1607 n_lane = len(lanes) 1608 1609 while n_lane_assig > 0: 1610 if attrs['is_rightside']: 1611 self.append_lane(lanes, attrs, is_rightside=True) 1612 n_lane_assig -= 1 1613 if attrs['is_leftside']: 1614 self.append_lane(lanes, attrs, is_leftside=True) 1615 n_lane_assig -= 1 1616 1617 # do bikeways 1618 attrs = self._bikewayattrs[ind] 1619 if attrs['n_lane'] > 0: 1620 print ' bikeways n_lane', attrs['n_lane'] 1621 n_lane_assig = attrs['n_lane'] 1622 n_lane = len(lanes) 1623 1624 while n_lane_assig > 0: 1625 if attrs['is_rightside']: 1626 if is_opp: 1627 if attrs['is_share'] & (len(lanes) > 0): 1628 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1629 else: 1630 self.append_lane(lanes, attrs, is_rightside=True) 1631 else: 1632 # primary link specific: only merge if more than 2 lanes 1633 if attrs['is_share'] & (len(lanes) > 2): 1634 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1635 else: 1636 self.append_lane(lanes, attrs, is_rightside=True) 1637 n_lane_assig -= 1 1638 1639 if attrs['is_leftside']: 1640 # primary link specific: only merge if more than 2 lanes 1641 if attrs['is_share'] & (len(lanes) > 0): 1642 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1643 else: 1644 self.append_lane(lanes, attrs, is_leftside=True) 1645 n_lane_assig -= 1 1646 1647 # do sidewalks 1648 attrs = self._sidewalkattrs[ind] 1649 if attrs['n_lane'] > 0: 1650 print ' sidewalks n_lane', attrs['n_lane'] 1651 n_lane_assig = attrs['n_lane'] 1652 n_lane = len(lanes) 1653 # sidewalks are not considered lanes in osm 1654 # so we append/prepend them 1655 while n_lane_assig > 0: 1656 if attrs['is_rightside']: 1657 if attrs['is_share'] & (len(lanes) > 0): 1658 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1659 else: 1660 self.append_lane(lanes, attrs, is_rightside=True) 1661 n_lane_assig -= 1 1662 if attrs['is_leftside']: 1663 if attrs['is_share'] & (len(lanes) > 0): 1664 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1665 else: 1666 self.append_lane(lanes, attrs, is_leftside=True) 1667 n_lane_assig -= 1 1668 1669 # disallow pedestrians on other lanes 1670 # 1671 for laneattrs in lanes: 1672 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 1673 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 1674 1675 if is_opp: 1676 self._lanes_opp = lanes 1677 else: 1678 self._lanes = lanes 1679 print ' created %d lanes' % len(lanes) 1680 # print ' lanes', lanes 1681 for laneattrs in lanes: 1682 print_attrs(laneattrs) 1683 return True 1684 1685 1686class Residential(Road): 1687 1688 def config(self): 1689 """ 1690 Make defaults to be overridden 1691 """ 1692 Road.config(self) 1693 # put 30km/h default speed limit 1694 self.make_speed(30.0/3.6) 1695 1696 def get_priority(self, is_opp=False): 1697 """ 1698 Returns priority of road. 1699 1700 To be overridden. 1701 """ 1702 if is_opp: 1703 lanes = self._lanes_opp 1704 else: 1705 lanes = self._lanes 1706 1707 speed_max = self.get_speed_max() 1708 n_lane = len(lanes) 1709 return 3 1710 1711 def make_sidewalkattrs(self): 1712 print 'make_sidewalkattrs' 1713 osmattrs = self._osmattrs 1714 self._sidewalkattrs = (deepcopy(LANEATTRS_DEFAULT), 1715 deepcopy(LANEATTRS_DEFAULT)) 1716 1717 sidewalk = osmattrs.get('sidewalk', 'auto') 1718 1719 if sidewalk not in ['no', 'none', 'auto']: 1720 # there is a sidewalk, make sure there is at least one 1721 1722 if osmattrs.has_key('sidewalk:width'): 1723 width_left = float(osmattrs['sidewalk:width']) 1724 width_right = width_left 1725 1726 elif osmattrs.has_key('sidewalk:both:width'): 1727 width_left = float(osmattrs['sidewalk:both:width']) 1728 width_right = width_left 1729 else: 1730 width_left = float(osmattrs.get('sidewalk:left:width', self.width_sidewalk)) 1731 width_right = float(osmattrs.get('sidewalk:right:width', self.width_sidewalk)) 1732 1733 if osmattrs.get('oneway', 'no') == 'no': 1734 # bidirecional 1735 1736 if sidewalk == 'both': 1737 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1738 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 1739 1740 elif sidewalk == 'left': 1741 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 1742 1743 elif sidewalk == 'right': 1744 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1745 1746 else: 1747 # no indication means both 1748 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1749 self.make_sidewalk(is_opp=True, is_rightside=True, width=width_left) 1750 1751 else: 1752 # oneway 1753 if sidewalk == 'both': 1754 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1755 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 1756 1757 elif sidewalk == 'left': 1758 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 1759 1760 elif sidewalk == 'right': 1761 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1762 1763 else: 1764 # no indication means both 1765 self.make_sidewalk(is_opp=False, is_rightside=True, width=width_right) 1766 self.make_sidewalk(is_opp=False, is_rightside=False, width=width_left) 1767 1768 elif sidewalk == 'auto': 1769 # automatic sidewalk generation for residential roads 1770 if self.is_oneway(): 1771 # put a sidewalk on both sides of the oneway 1772 self.make_sidewalk(is_opp=False, is_rightside=True, width=self.width_sidewalk) 1773 self.make_sidewalk(is_opp=False, is_rightside=False, width=self.width_sidewalk) 1774 else: 1775 # put a sidewalk on both sides of the road 1776 self.make_sidewalk(is_opp=False, is_rightside=True, width=self.width_sidewalk) 1777 self.make_sidewalk(is_opp=True, is_rightside=True, width=self.width_sidewalk) 1778 1779 1780class Footpath(Road): 1781 def config(self): 1782 """ 1783 Make defaults to be overridden 1784 """ 1785 print 'config' 1786 # pass here either road type specific defaults 1787 # or global defaults from parent process 1788 self.id_mode = ID_MODE_PED 1789 # highway=footway|path 1790 self.highway = self._osmattrs.get('highway', 'footway') 1791 1792 # Use footway=crossing for places where the footway crosses a street. 1793 # Use footway=sidewalk 1794 1795 self.footway = self._osmattrs.get('footway', '') 1796 self.n_lane = 1 1797 1798 if self.footway == 'sidewalk': 1799 lanewidth = self.parent.width_sidewalk 1800 else: 1801 lanewidth = self.parent.width_footpath 1802 1803 # half lanewidth if segregated 1804 if self._osmattrs.get('segregated', '') == 'yes': 1805 lanewidth /= 2 1806 1807 self.lanewidth = lanewidth 1808 self.lanewidth_bike = lanewidth 1809 #self.lanewidth_bus = self.parent.lanewidth_bus 1810 #self.width_sidewalk = self.parent.width_sidewalk 1811 #self.width_footpath = self.parent.width_footpath 1812 1813 #self.ids_modes_pt_shared = self.parent.ids_modes_pt_shared 1814 self.ids_modes_bike = self.parent.ids_modes_bike 1815 self.ids_modes_allow = [ID_MODE_PED] 1816 self.ids_modes_disallow = [] 1817 self.make_speed(self.parent.speed_max_ped) 1818 1819 #self.speed_max_bus = self.parent.speed_max_bus 1820 self.speed_max_bike = self.parent.speed_max_bike 1821 #self.speed_max_ped = self.parent.speed_max_ped 1822 1823 def get_priority(self, is_opp=False): 1824 """ 1825 Returns priority of road. 1826 1827 To be overridden. 1828 """ 1829 if is_opp: 1830 lanes = self._lanes_opp 1831 else: 1832 lanes = self._lanes 1833 1834 speed_max = self.get_speed_max() 1835 n_lane = len(lanes) 1836 return 1 1837 1838 def make_oneway(self): 1839 # print 'make_oneway' 1840 osmattrs = self._osmattrs 1841 1842 # default for footpath is oneway = yes 1843 if osmattrs.get('oneway', 'yes') == 'no': 1844 self._is_oneway = False 1845 1846 else: 1847 # check if really oneway 1848 # we make oneway if only pedestrians use this edge 1849 if (osmattrs.get('bicycle', '') in ('yes', 'designated')) | (osmattrs.get('route', '') == 'bicycle'): 1850 self._is_oneway = False 1851 else: 1852 self._is_oneway = True 1853 1854 def make_buswayattrs(self): 1855 # print 'make_buswayattrs' 1856 # self._buswayattrs = (LANEATTRS_DEFAULT.copy(), 1857 # LANEATTRS_DEFAULT.copy()) 1858 pass 1859 1860 def make_sidewalkattrs(self): 1861 self._sidewalkattrs = (deepcopy(LANEATTRS_DEFAULT), 1862 deepcopy(LANEATTRS_DEFAULT)) 1863 # pass 1864 1865 def make_bikewayattrs(self): 1866 print 'make_bikewayattrs' 1867 osmattrs = self._osmattrs 1868 self._bikewayattrs = (deepcopy(LANEATTRS_DEFAULT), 1869 deepcopy(LANEATTRS_DEFAULT)) 1870 1871 width_left = self.lanewidth_bike 1872 width_right = self.lanewidth_bike 1873 1874 # if osmattrs.get('oneway','no')=='no': 1875 # cycle lanes on bidir road 1876 if (osmattrs.get('bicycle', '') in ('yes', 'designated')) | (osmattrs.get('route', '') == 'bicycle'): 1877 if osmattrs.get('segregated', '') == 'yes': 1878 # bike lanes to the left of the footpath 1879 self.make_bikelane(is_opp=False, is_rightside=False, width=width_right) 1880 self.make_bikelane(is_opp=True, is_rightside=False, width=width_left) 1881 else: 1882 # bike lanes will be merged with the footpath 1883 self.make_bikelane(is_opp=False, width=width_right, ids_modes_allow=[ID_MODE_PED]) 1884 self.make_bikelane(is_opp=True, width=width_left, ids_modes_allow=[ID_MODE_PED]) 1885 1886 def make_lanes_rigid(self, is_opp=False, n_lane_osm=0): 1887 print 'make_lanes_rigid ped', is_opp, n_lane_osm 1888 osmattrs = self._osmattrs 1889 1890 if is_opp: 1891 ind = 0 1892 if self._is_oneway: 1893 self._lanes_opp = [] 1894 return False 1895 else: 1896 ind = 1 1897 1898 lanes = [] 1899 for i in range(n_lane_osm): 1900 lanes.append(deepcopy(self._laneattrs_main)) 1901 1902 # if is_lanes_rigid: 1903 # # respect given lane numbers for main modes, except footpath 1904 # pass 1905 # else: 1906 1907 # do bikeways 1908 attrs = self._bikewayattrs[ind] 1909 if attrs['n_lane'] > 0: 1910 print ' bikeways n_lane', attrs['n_lane'] 1911 1912 n_lane = len(lanes) 1913 1914 allowed, disallowed = self.get_laneaccess('bicycle', is_opp=is_opp) 1915 1916 n_allow = len(allowed) 1917 if n_allow > 0: 1918 for i, a, d in zip(xrange(n_allow), allowed, disallowed): 1919 if i < n_lane: 1920 if a & i < n_lane: 1921 self.set_lane(lanes, attrs, i) 1922 if d: 1923 self.disallow_on_lane(lanes[i], attrs['ids_modes_disallow']) 1924 1925 else: 1926 n_lane_assig = attrs['n_lane'] 1927 for i in range(n_lane): 1928 if n_lane_assig > 0: 1929 if attrs['is_rightside']: 1930 self.merge_laneattrs(lanes[i], attrs, is_rightside=True) 1931 n_lane_assig -= 1 1932 1933 if attrs['is_leftside']: 1934 self.merge_laneattrs(lanes[n_lane-i-1], attrs, is_leftside=True) 1935 n_lane_assig -= 1 1936 1937 def make_lanes(self, is_opp=False, n_lane_osm=0): 1938 print 'make_lanes ped', is_opp, n_lane_osm 1939 osmattrs = self._osmattrs 1940 1941 print ' main lane attrs' 1942 print_attrs(self._laneattrs_main) 1943 1944 if is_opp: 1945 ind = 0 1946 if self._is_oneway: 1947 self._lanes_opp = [] 1948 return False 1949 else: 1950 ind = 1 1951 1952 lanes = [] 1953 for i in range(n_lane_osm): 1954 lanes.append(deepcopy(self._laneattrs_main)) 1955 1956 # do bikeways 1957 attrs = self._bikewayattrs[ind] 1958 if attrs['n_lane'] > 0: 1959 print ' bikeways n_lane', attrs['n_lane'] 1960 n_lane_assig = attrs['n_lane'] 1961 n_lane = len(lanes) 1962 1963 while n_lane_assig > 0: 1964 if attrs['is_rightside']: 1965 if attrs['is_share'] & (len(lanes) > 0): 1966 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 1967 else: 1968 self.append_lane(lanes, attrs, is_rightside=True) 1969 n_lane_assig -= 1 1970 1971 if attrs['is_leftside']: 1972 if attrs['is_share'] & (len(lanes) > 0): 1973 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 1974 else: 1975 self.append_lane(lanes, attrs, is_leftside=True) 1976 n_lane_assig -= 1 1977 1978 if is_opp: 1979 self._lanes_opp = lanes 1980 else: 1981 self._lanes = lanes 1982 1983 print ' created %d lanes' % len(lanes) 1984 # print ' lanes', lanes 1985 for laneattrs in lanes: 1986 print_attrs(laneattrs) 1987 return True 1988 1989 1990class Cycleway(Road): 1991 1992 def config(self): 1993 """ 1994 Make defaults to be overridden 1995 """ 1996 print 'config cycleway' 1997 # pass here either road type specific defaults 1998 # or global defaults from parent process 1999 2000 self.highway = self._osmattrs.get('highway', 'cycleway') 2001 2002 self.id_mode = ID_MODE_BIKE 2003 self.n_lane = 1 2004 2005 # print ' width',self._osmattrs.get('width',self.parent.lanewidth_bike) 2006 if self.is_oneway(): 2007 width_default = self.parent.lanewidth_bike 2008 else: 2009 width_default = 2*self.parent.lanewidth_bike 2010 2011 self.lanewidth = self.get_osmattr('width', is_float=True, default=width_default) 2012 2013 # half lane width if bidir 2014 if not self.is_oneway(): 2015 self.lanewidth *= 0.5 2016 2017 #self.lanewidth_bike = self.parent.lanewidth_bike 2018 #self.lanewidth_bus = self.parent.lanewidth_bus 2019 self.width_sidewalk = self.parent.width_sidewalk 2020 self.width_footpath = self.parent.width_footpath 2021 2022 #self.ids_modes_pt_shared = self.parent.ids_modes_pt_shared 2023 #self.ids_modes_bike = self.parent.ids_modes_bike 2024 self.ids_modes_allow = self.parent.ids_modes_bike 2025 self.ids_modes_disallow = [] 2026 self.make_speed(self.parent.speed_max_bike) 2027 2028 print ' ids_modes_allow', self.ids_modes_allow 2029 #self.speed_max_bus = self.parent.speed_max_bus 2030 #self.speed_max_bike = self.parent.speed_max_bike 2031 self.speed_max_ped = self.parent.speed_max_ped 2032 2033 def make_oneway(self): 2034 # print 'make_oneway' 2035 osmattrs = self._osmattrs 2036 2037 # default for bikeway is oneway = no 2038 if osmattrs.get('oneway', 'no') == 'no': 2039 self._is_oneway = False 2040 2041 else: 2042 self._is_oneway = True 2043 2044 def make_buswayattrs(self): 2045 # print 'make_buswayattrs' 2046 # self._buswayattrs = (LANEATTRS_DEFAULT.copy(), 2047 # LANEATTRS_DEFAULT.copy()) 2048 pass 2049 2050 # def make_sidewalkattrs(self): 2051 # self._sidewalkattrs = (deepcopy(LANEATTRS_DEFAULT), 2052 # deepcopy(LANEATTRS_DEFAULT)) 2053 # #pass 2054 2055 def make_bikewayattrs(self): 2056 pass 2057 2058 def make_lanes_rigid(self, is_opp=False, n_lane_osm=0): 2059 print 'make_lanes_rigid cycle', is_opp, n_lane_osm 2060 osmattrs = self._osmattrs 2061 2062 if is_opp: 2063 ind = 0 2064 if self._is_oneway: 2065 self._lanes_opp = [] 2066 return False 2067 else: 2068 ind = 1 2069 2070 lanes = [] 2071 for i in range(n_lane_osm): 2072 lanes.append(deepcopy(self._laneattrs_main)) 2073 2074 # do sidewalks 2075 attrs = self._sidewalkattrs[ind] 2076 if attrs['n_lane'] > 0: 2077 print ' sidewalks n_lane', attrs['n_lane'] 2078 n_lane_assig = attrs['n_lane'] 2079 n_lane = len(lanes) 2080 # sidewalks are not considered lanes in osm 2081 # so we append/prepend them 2082 while n_lane_assig > 0: 2083 if attrs['is_rightside']: 2084 if attrs['is_share'] & (len(lanes) > 0): 2085 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 2086 else: 2087 self.append_lane(lanes, attrs, is_rightside=True) 2088 n_lane_assig -= 1 2089 if attrs['is_leftside']: 2090 if attrs['is_share'] & (len(lanes) > 0): 2091 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 2092 else: 2093 self.append_lane(lanes, attrs, is_leftside=True) 2094 n_lane_assig -= 1 2095 2096 # disallow pedestrians on other lanes 2097 # 2098 for laneattrs in lanes: 2099 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 2100 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 2101 2102 if is_opp: 2103 self._lanes_opp = lanes 2104 else: 2105 self._lanes = lanes 2106 print ' created %d lanes' % len(lanes) 2107 # print ' lanes', lanes 2108 for laneattrs in lanes: 2109 print_attrs(laneattrs) 2110 return True 2111 2112 def make_lanes(self, is_opp=False, n_lane_osm=0): 2113 print 'make_lanes cycle', is_opp, n_lane_osm 2114 osmattrs = self._osmattrs 2115 is_lanes_rigid = False 2116 2117 if is_opp: 2118 ind = 0 2119 if self._is_oneway: 2120 self._lanes_opp = [] 2121 return False 2122 else: 2123 ind = 1 2124 2125 lanes = [] 2126 for i in range(n_lane_osm): 2127 lanes.append(deepcopy(self._laneattrs_main)) 2128 2129 # do sidewalks 2130 attrs = self._sidewalkattrs[ind] 2131 if attrs['n_lane'] > 0: 2132 print ' sidewalks n_lane', attrs['n_lane'] 2133 n_lane_assig = attrs['n_lane'] 2134 n_lane = len(lanes) 2135 # sidewalks are not considered lanes in osm 2136 # so we append/prepend them 2137 while n_lane_assig > 0: 2138 if attrs['is_rightside']: 2139 if attrs['is_share'] & (len(lanes) > 0): 2140 self.merge_laneattrs(lanes[0], attrs, is_rightside=True) 2141 else: 2142 self.append_lane(lanes, attrs, is_rightside=True) 2143 n_lane_assig -= 1 2144 if attrs['is_leftside']: 2145 if attrs['is_share'] & (len(lanes) > 0): 2146 self.merge_laneattrs(lanes[-1], attrs, is_leftside=True) 2147 else: 2148 self.append_lane(lanes, attrs, is_leftside=True) 2149 n_lane_assig -= 1 2150 2151 # disallow pedestrians on other lanes 2152 # 2153 for laneattrs in lanes: 2154 if ID_MODE_PED not in laneattrs['ids_modes_allow']: 2155 self.disallow_on_lane(laneattrs, [ID_MODE_PED]) 2156 2157 if is_opp: 2158 self._lanes_opp = lanes 2159 else: 2160 self._lanes = lanes 2161 print ' created %d lanes' % len(lanes) 2162 # print ' lanes', lanes 2163 for laneattrs in lanes: 2164 print_attrs(laneattrs) 2165 return True 2166 2167 def get_priority(self, is_opp=False): 2168 """ 2169 Returns priority of road. 2170 2171 To be overridden. 2172 """ 2173 if is_opp: 2174 lanes = self._lanes_opp 2175 else: 2176 lanes = self._lanes 2177 2178 speed_max = self.get_speed_max() 2179 n_lane = len(lanes) 2180 return 2 2181 2182 2183ROADCLASSES = {'road': Road, 2184 'path': Footpath, 2185 'pedestrian': Footpath, 2186 'footway': Footpath, 2187 'stairs': Footpath, 2188 'steps': Footpath, 2189 'platform': Footpath, 2190 'cycleway': Cycleway, 2191 'residential': Residential, 2192 'living_street': Residential, 2193 'primary': Primary, 2194 'primary_link': Primary, 2195 'motorway': Primary, 2196 'trunk': Primary, 2197 'motorway_link': Primary, 2198 'trunk_link': Primary, 2199 'primary_link': Primary, 2200 } 2201OSMKEYS_SHARED = ('shared', 'share_lane', 'share_busway', 'share_cycleway') 2202OSMKEYS_SHARED_OPP = ('opposite_shared', 'opposite_share_lane', 'opposite_share_busway', 'opposite_share_cycleway') 2203 2204 2205class OxImporter(Process): 2206 def __init__(self, scenario, 2207 ident='oximporter', 2208 name='OSMnx importer', 2209 info='Import of network imported with the help of osmnx.', 2210 logger=None, **kwargs): 2211 2212 print 'OxImporter.__init__' 2213 2214 self._init_common(ident, 2215 parent=scenario, 2216 name=name, 2217 logger=logger, 2218 info=info, 2219 ) 2220 2221 attrsman = self.set_attrsman(cm.Attrsman(self)) 2222 2223 # self.id_mode = attrsman.add(am.AttrConf('id_mode', modechoices['bicycle'], 2224 # groupnames = ['options'], 2225 # choices = modechoices, 2226 # name = 'Mode', 2227 # info = 'Transport mode to be matched.', 2228 # )) 2229 2230 self.osmdatafilepaths = attrsman.add( 2231 cm.AttrConf('osmdatafilepaths', kwargs.get('osmdatafilepaths', scenario.get_rootfilepath()), 2232 groupnames=['options'], 2233 perm='rw', 2234 name='OSM data file(s)', 2235 wildcards='Jason file (*.json)|*.json', 2236 metatype='filepaths', 2237 info="""One or several jason filepaths holding OSM related information.""", 2238 )) 2239 2240 self.nxnetworkpaths = attrsman.add( 2241 cm.AttrConf('nxnetworkpaths', kwargs.get('nxnetworkpaths', scenario.get_rootfilepath()), 2242 groupnames=['options'], 2243 perm='rw', 2244 name='Networkx file(s)', 2245 wildcards='NetworkX file (*.obj)|*.obj', 2246 metatype='filepaths', 2247 info="""One or several network X filepaths containing topological information of simplified network.""", 2248 )) 2249 2250 self.n_lane = attrsman.add(cm.AttrConf('n_lane', 1, 2251 groupnames=['options', 'osm'], 2252 name='Default lane number', 2253 info="Default lane number.", 2254 )) 2255 2256 self.speed_max = attrsman.add(cm.AttrConf('speed_max', 50.0/3.6, 2257 groupnames=['options', 'osm'], 2258 name='Default Max. speed', 2259 info="General default maximum speed.", 2260 unit='m/s', 2261 )) 2262 2263 self.speed_max_bus = attrsman.add(cm.AttrConf('speed_max_bus', 50.0/3.6, 2264 groupnames=['options', 'osm'], 2265 name='Default Max. bus speed', 2266 info="Default maximum speed on busways.", 2267 unit='m/s', 2268 )) 2269 2270 self.speed_max_bike = attrsman.add(cm.AttrConf('speed_max_bike', 20.0/3.6, 2271 groupnames=['options', 'osm'], 2272 name='Default Max. bike speed', 2273 info="Default maximum speed on bikeways.", 2274 unit='m/s', 2275 )) 2276 2277 self.speed_max_ped = attrsman.add(cm.AttrConf('speed_max_ped', 3.0/3.6, 2278 groupnames=['options', 'osm'], 2279 name='Default Max. ped. speed', 2280 info="Default maximum speed on footpath or sidewalks.", 2281 unit='m/s', 2282 )) 2283 2284 self.lanewidth = attrsman.add(cm.AttrConf('lanewidth', 3.25, 2285 groupnames=['options', 'osm'], 2286 name='Default lane', 2287 info="Default lane width for standard lane.", 2288 unit='m', 2289 )) 2290 2291 self.lanewidth_bike = attrsman.add(cm.AttrConf('lanewidth_bike', 1.5, 2292 groupnames=['options', 'osm'], 2293 name='Default bikeway width', 2294 info="Default bikeway width.", 2295 unit='m', 2296 )) 2297 2298 self.lanewidth_bus = attrsman.add(cm.AttrConf('lanewidth_bus', 3.5, 2299 groupnames=['options', 'osm'], 2300 name='Default busway width', 2301 info="Default busway width.", 2302 unit='m', 2303 )) 2304 2305 self.width_footpath = attrsman.add(cm.AttrConf('width_footpath', 1.5, 2306 groupnames=['options', 'osm'], 2307 name='Default footpath width', 2308 info="Default footpath width.", 2309 unit='m', 2310 )) 2311 2312 self.width_sidewalk = attrsman.add(cm.AttrConf('width_sidewalk', 1.0, 2313 groupnames=['options', 'osm'], 2314 name='Default sidewalk width', 2315 info="Default sidewalk width.", 2316 unit='m', 2317 )) 2318 2319 self.modes_pt_shared = attrsman.add(cm.AttrConf('modes_pt_shared', ['bus', 'taxi', 'emergency', 'bicycle'], 2320 groupnames=['options', 'osm'], 2321 name='Modes on PT reserved lanes', 2322 info="Modes that are allowed on reserved lanes for public transport.", 2323 perm='r', 2324 )) 2325 2326 self.modes_bike = attrsman.add(cm.AttrConf('modes_bike', ['bicycle', ], 2327 groupnames=['options', 'osm'], 2328 name='Modes on dedicated bike lanes', 2329 info="Modes that are allowed on dedicated bike lanes.", 2330 perm='r', 2331 )) 2332 2333 self.ids_modes_bike = [] 2334 for mode in self.modes_bike: 2335 self.ids_modes_bike.append(MODES[mode]) 2336 2337 self.ids_modes_pt_shared = [] 2338 for mode in self.modes_pt_shared: 2339 self.ids_modes_pt_shared.append(MODES[mode]) 2340 2341 # def import_xnet(net, nodeshapefilepath, edgeshapefilepath, polyshapefilepath): 2342 #import_nodeshapes(net, nodeshapefilepath) 2343 2344 def get_scenario(self): 2345 return self.parent 2346 2347 def do(self): 2348 print self.ident+'.do' 2349 2350 print ' osmdatafilepaths', self.osmdatafilepaths 2351 print ' nxnetworkpaths', self.nxnetworkpaths 2352 net = self.get_scenario().net 2353 self._net = net 2354 self._map_id_edge_sumo_to_doubles = {} 2355 self.edges_osm = {} 2356 self.nodes_osm = {} 2357 2358 projparams_target = net.get_projparams() 2359 if projparams_target in ("", "!"): 2360 projparams_target = None 2361 2362 for filepath in self.osmdatafilepaths.split(','): 2363 self.import_osmdata(json.loads(open(filepath).read())) 2364 2365 for filepath in self.nxnetworkpaths.split(','): # filepathstring_to_filepathlist(self.nxnetworkpaths): 2366 graphx = load_objfile(filepath.strip()) 2367 self.import_nx(graphx, projparams=projparams_target) 2368 2369 net.edges.update(is_update_lanes=True) 2370 2371 return True 2372 2373 def import_osmdata(self, osmdata): 2374 edges_osm = self.edges_osm 2375 nodes_osm = self.nodes_osm 2376 for element in osmdata['elements']: 2377 # {u'nodes': [5340543333L, 5340543332L], u'type': u'way', u'id': 553233159, u'tags': {u'highway': u'service', u'oneway': u'no', u'service': u'driveway', u'surface': u'asphalt', u'incline': u'up'}} 2378 # {u'lat': 47.6038005, u'type': u'node', u'lon': 7.6006465, u'id': 453208, u'tags': {u'ref': u'69', u'name': u'Weil am Rhein / H\xfcningen', u'highway': u'motorway_junction'}} 2379 # print ' parse element',element['id'],element['type'] 2380 if element['type'] == 'way': 2381 if element.has_key('tags'): 2382 highway = element['tags'].get('highway', 'road') 2383 else: 2384 highway = 'road' 2385 print ' '+70*'-' 2386 print ' way', element['id'], type(element['id']), highway 2387 edges_osm[str(element['id'])] = ROADCLASSES.get(highway, Road)(element, self) 2388 print ' done with way', element['id'], id(self.edges_osm[str(element['id'])]) 2389 2390 if element['type'] == 'node': 2391 nodes_osm[element['id']] = element.get('tags', {}) 2392 2393 print ' import_osmdata:done' 2394 2395 # def get_id_edge_sumo(self, osmid): 2396 # idmap = self._map_id_edge_sumo_to_doubles 2397 # if idmap.has_key(osmid): 2398 # idmap[osmid] +=1 2399 # else: 2400 # idmap[osmid] = 0 2401 # return (osmid, idmap[osmid]) 2402 # #return str(osmid)+'#'+str(idmap[osmid]) 2403 2404 def get_edgenumber(self, osmid_dir): 2405 idmap = self._map_id_edge_sumo_to_doubles 2406 if idmap.has_key(osmid_dir): 2407 idmap[osmid_dir] += 1 2408 else: 2409 idmap[osmid_dir] = 0 2410 return idmap[osmid_dir] 2411 2412 def get_id_edge_sumo(self, osmid_dir): 2413 edgenumber = self.get_edgenumber(osmid_dir) 2414 return osmid_dir+'#'+str(edgenumber) 2415 2416 def get_id_edge_osm_from_id_sumo(self, id_sumo): 2417 """ 2418 Returns from id_sumo: 2419 (id_osm, is_opp, num) 2420 """ 2421 data = id_sumo.split('#') 2422 if data[0][0] == '-': 2423 return data[0][1:], True, int(data[1]) 2424 else: 2425 return data[0], False, int(data[1]) 2426 2427 def is_edge_eligible(self, id_osm, id_fromnode_sumo, id_tonode_sumo): 2428 2429 print 'is_edge_eligible', id_osm, type(id_osm), id_fromnode_sumo, id_tonode_sumo, self.edges_osm.has_key( 2430 id_osm), self._edgelookup.has_key(id_osm) 2431 if not self.edges_osm.has_key(id_osm): 2432 # foe some reason, nx network has edges that are not in jason 2433 return False 2434 2435 edgelookup = self._edgelookup 2436 2437 if edgelookup.has_key(id_osm): 2438 # is reverse already in database 2439 # print ' check',edgelookup[id_osm], (id_tonode_sumo, id_fromnode_sumo) in edgelookup[id_osm] 2440 edgelookup[id_osm].add((id_fromnode_sumo, id_tonode_sumo)) 2441 if (id_tonode_sumo, id_fromnode_sumo) in edgelookup[id_osm]: 2442 return False 2443 else: 2444 return True 2445 2446 else: 2447 edgelookup[id_osm] = set([(id_fromnode_sumo, id_tonode_sumo)]) 2448 return True 2449 2450 def make_segment_edge_map(self): 2451 """ 2452 Generates a vertex matrix with line segments of all edges 2453 and a map that maps each line segment to edge index. 2454 """ 2455 polylines = self._edgeshapes 2456 n_edges = len(polylines) 2457 inds = np.arange(n_edges) 2458 #ids = inds+1 2459 print 'make_linevertices', n_edges 2460 2461 linevertices = np.zeros((0, 2, 3), np.float32) 2462 vertexinds = np.zeros((0, 2), np.int32) 2463 polyinds = [] 2464 2465 lineinds = [] 2466 linebeginstyles = [] 2467 lineendstyles = [] 2468 2469 i = 0 2470 ind_line = 0 2471 2472 for ind in inds: 2473 2474 # if is_laneshapes: 2475 # polyline = laneshapes[ids_lanes[ind][0]] 2476 # else: 2477 polyline = polylines[ind] 2478 2479 n_seg = len(polyline) 2480 # print ' =======',n_seg#,polyline 2481 2482 if n_seg > 1: 2483 polyvinds = range(n_seg) 2484 # print ' polyvinds\n',polyvinds 2485 vi = np.zeros((2*n_seg-2), np.int32) 2486 vi[0] = polyvinds[0] 2487 vi[-1] = polyvinds[-1] 2488 2489 # Important type conversion!! 2490 v = np.zeros((2*n_seg-2, 3), np.float32) 2491 v[0] = polyline[0] 2492 v[-1] = polyline[-1] 2493 if len(v) > 2: 2494 2495 v[1:-1] = np.repeat(polyline[1:-1], 2, 0) 2496 vi[1:-1] = np.repeat(polyvinds[1:-1], 2) 2497 2498 n_lines = len(v)/2 2499 # print ' v\n',v 2500 polyinds += n_lines*[ind] 2501 lineinds.append(np.arange(ind_line, ind_line+n_lines)) 2502 ind_line += n_lines 2503 2504 else: 2505 # empty polygon treatment 2506 v = np.zeros((0, 3), np.float32) 2507 vi = np.zeros((0), np.int32) 2508 2509 linevertices = np.concatenate((linevertices, v.reshape((-1, 2, 3)))) 2510 vertexinds = np.concatenate((vertexinds, vi.reshape((-1, 2)))) 2511 # print ' linevertex\n',linevertices 2512 i += 1 2513 2514 #self._segvertices = linevertices 2515 self._edgeinds = np.array(polyinds, np.int32) 2516 self._seginds = lineinds 2517 self._segvertexinds = np.array(vertexinds, np.int32) 2518 2519 self._x1 = linevertices[:, 0, 0] 2520 self._y1 = linevertices[:, 0, 1] 2521 2522 self._x2 = linevertices[:, 1, 0] 2523 self._y2 = linevertices[:, 1, 1] 2524 2525 def get_closest_edge_dist(self, p, ind_shape, n_best=0, d_min=0.5, alpha_min=1.0*np.pi/180, d_max=None): 2526 """ 2527 Returns edge id which is closest to point p. 2528 Requires execution of make_segment_edge_map 2529 """ 2530 # print ' x1', x1 2531 # print ' x2', x2 2532 #halfwidths = 0.5*self.get_widths_array()[self._polyinds] 2533 x1, y1, x2, y2 = self._x1, self._y1, self._x2, self._y2 2534 d2 = get_dist_point_to_segs(p[0:2], x1, y1, x2, y2, is_ending=True) 2535 # print ' min(d2)=',np.min(d2),'argmin=',np.argmin(d2),self.get_ids(self._edgeinds[np.argmin(d2)]) 2536 2537 d2[self._seginds[ind_shape]] = np.inf 2538 #d2[d2<0.5] = np.inf 2539 2540 # check side 2541 v1 = np.concatenate(((x2-x1).reshape(1, -1), (y2-y1).reshape(1, -1)), 0) 2542 v2 = np.concatenate(((p[0]-x1).reshape(1, -1), (p[1]-y1).reshape(1, -1)), 0) 2543 angles = get_diff_angle_clockwise(v1, v2) 2544 #d2[angles<alpha_min] = np.inf 2545 2546 if n_best == 0: 2547 ind = np.argmin(d2) 2548 return self._edgeinds[ind], np.sqrt(d2[ind]) 2549 2550 elif d_max is None: 2551 dists2_min = np.zeros(n_best, dtype=np.float32) 2552 inds_min = np.zeros(n_best, dtype=np.int) 2553 for i in xrange(n_best): 2554 ind = np.argmin(d2) 2555 inds_min[i] = ind 2556 dists2_min[i] = d2[ind] 2557 d2[ind] = np.inf 2558 2559 return self._edgeinds[inds_min], np.sqrt(dists2_min), angles[inds_min] 2560 2561 else: 2562 ind = np.argmin(d2) 2563 dist2_min = d2[ind] 2564 dists2_min = [dist2_min] 2565 inds_min = [ind] 2566 while (dist2_min < d_max**2) & (len(dists2_min) < n_best): 2567 d2[ind] = np.inf 2568 ind = np.argmin(d2) 2569 dist2_min = d2[ind] 2570 dists2_min.append(dist2_min) 2571 inds_min.append(ind) 2572 2573 return self._edgeinds[inds_min], np.sqrt(dists2_min), angles[inds_min] 2574 2575 def configure_roundabouts(self): 2576 print 'configure_roundabouts' 2577 nodes = self._net.nodes 2578 roundabouts = [] 2579 edges_osm = self.edges_osm 2580 ids_edge_osm = self._ids_edge_osm 2581 ids_edge_sumo = self._ids_edge_sumo 2582 ids_tonode = self._ids_tonode 2583 ids_fromnode = self._ids_fromnode 2584 shapes = self._edgeshapes 2585 2586 alpha_crit = 90.0*np.pi/180.0 2587 2588 graph = nx.Graph() 2589 digraph = nx.DiGraph() 2590 #junctionnet = {} 2591 for ind, id_edge_osm, shape, id_fromnode, id_tonode in zip(np.arange(len(ids_edge_osm)), ids_edge_osm, self._edgeshapes, ids_fromnode, ids_tonode): 2592 road = edges_osm[id_edge_osm] 2593 if road.is_roundabout(): # & (len(shape)>2): 2594 graph.add_edge(id_fromnode, id_tonode, ind=ind) 2595 digraph.add_edge(id_fromnode, id_tonode, ind=ind) 2596 2597 # print ' graph.nodes()',graph.nodes() 2598 #ids_node_junctions = [[]] 2599 2600 for ids_node_junction_list in nx.cycle_basis(graph): 2601 if len(ids_node_junction_list) > 2: 2602 # print ' ids_node_junction_list',ids_node_junction_list 2603 ids_node_junction = np.array(ids_node_junction_list, dtype=np.int32) 2604 2605 coords = nodes.coords[ids_node_junction] 2606 center = np.mean(coords, 0) 2607 deltas = coords-center 2608 angles = np.arctan2(deltas[:, 0], deltas[:, 1]) 2609 inds = np.argsort(angles, axis=0)[::-1] # reverse order 2610 # print ' inds',inds 2611 # print ' angels',angles[inds] 2612 # print ' ids_node_junction',ids_node_junction[inds] 2613 # print ' len(graph)',len(graph) 2614 ids_node_ok = list(ids_node_junction[inds]) 2615 ids_node_ok.append(ids_node_ok[0]) 2616 #n_node = len(ids_node_ok) 2617 # for ind in xrange(len(ids_node_ok)): 2618 # if digraph.has_edge() 2619 2620 ids_rbsedges_sumo = [] 2621 for id_fromnode, id_tonode in zip(ids_node_ok[:-1], ids_node_ok[1:]): 2622 2623 ind = graph[id_tonode][id_fromnode]['ind'] 2624 if not digraph.has_edge(id_fromnode, id_tonode): 2625 # print ' flip',ids_edge_sumo[ind] 2626 # print ' shapes',shapes[ind] 2627 # print ' shapes',shapes[ind][::-1] 2628 ids_tonode[ind] = id_tonode 2629 ids_fromnode[ind] = id_fromnode 2630 shapes[ind][:] = shapes[ind][::-1] 2631 2632 ids_rbsedges_sumo.append(ids_edge_sumo[ind]) 2633 2634 roundabouts.append((ids_rbsedges_sumo, ids_node_ok)) 2635 2636 #data = np.concatenate((angles.reshape(-1,1), ids_node_junction).reshape(-1,1),0) 2637 # graph.remove_nodes_from(ids_node_junction) 2638 self._roundabouts = roundabouts 2639 2640 def get_id_osm_maindir(self, id_osm): 2641 if id_osm[0] == '-': 2642 return id_osm[1:] 2643 else: 2644 return id_osm 2645 2646 def check_consistency(self): 2647 print 'check_consistency' 2648 nodelookup = {} 2649 2650 for ind, id_fromnode, id_tonode, id_edge_sumo in zip(np.arange(len(self._ids_edge_sumo)), self._ids_fromnode, self._ids_tonode, self._ids_edge_sumo): 2651 ids_fromtonode = (id_fromnode, id_tonode) 2652 if nodelookup.has_key(ids_fromtonode): 2653 print ' WARNING: %s double edge to %s detected' % ( 2654 id_edge_sumo, nodelookup[ids_fromtonode]), 'from', id_fromnode, 'to', id_tonode 2655 self._are_edge_valid[ind] = False 2656 2657 nodelookup[ids_fromtonode] = id_edge_sumo 2658 2659 def configure_footpath(self): 2660 2661 are_edge_valid = self._are_edge_valid 2662 edges_osm = self.edges_osm 2663 ids_edge_osm = self._ids_edge_osm 2664 ids_edge_sumo = self._ids_edge_sumo 2665 footpath_condig = ('footway', 'path', 'pedestrian') 2666 footpath_nomerge = ('footway', 'path', 'pedestrian', 'stairs', 'steps', 2667 'platform', 'primary_link', 'secondary_link') 2668 footpath_merge_cross = ('cycleway',) 2669 prio_max = 7 2670 dist_min_detect = 15.0 2671 dist_min_detect_cross = 3.0 2672 dist_min_remove = 0.0 2673 2674 n_best = 10 2675 2676 length_max_cross = 30.0 2677 2678 alpha_crit = 30.0*np.pi/180.0 2679 alpha_crit_cross = 30.0*np.pi/180.0 2680 print 'configure_footpath alpha_crit', alpha_crit 2681 #self.id_mode = ID_MODE_PED 2682 # highway=footway|path 2683 #self.highway = self._osmattrs.get('highway','footway') 2684 2685 # Use footway=crossing for places where the footway crosses a street. 2686 # Use footway=sidewalk 2687 for ind, id_edge_osm, shape, length in zip(np.arange(len(ids_edge_osm)), ids_edge_osm, self._edgeshapes, self._length): 2688 road = edges_osm[id_edge_osm] 2689 2690 if road.highway in footpath_condig: 2691 print ' check edge', ids_edge_sumo[ind], road.footway, (road.get_osmattr( 2692 'tunnel') != 'yes'), (length > dist_min_remove), length 2693 #(road.footway != 'crossing') (road.footway != 'sidewalk') 2694 ids_osm_main = set() 2695 is_remove = True 2696 ip = 0 2697 2698 if (road.footway == 'sidewalk'): 2699 # spacial sidewal merge. Sidewalks must be merged 2700 # to a main road 2701 for i in range(0, len(shape)): 2702 point = shape[i] 2703 is_foundmatch = False 2704 inds_edge_main, dists, angles = self.get_closest_edge_dist( 2705 point, ind, n_best=20, d_max=dist_min_detect) 2706 #matchdata = {} 2707 print ' check sidewalk point (%d/%d)' % (i+1, len(shape)) 2708 for ind_edge_main, dist, angle in zip(inds_edge_main, dists, angles): 2709 id_edge_osm_main, is_opp, nr = self.get_id_edge_osm_from_id_sumo( 2710 ids_edge_sumo[ind_edge_main]) 2711 road_main = edges_osm[id_edge_osm_main] 2712 prio = road_main.get_priority(is_opp) 2713 print ' check medge %s d=%.1fm al=%.1f' % (ids_edge_sumo[ind_edge_main], dist, angle/np.pi*180), prio, road_main.highway, ( 2714 angle < alpha_crit), (dist < 2*dist_min_detect), (road_main.highway not in footpath_nomerge) 2715 # print ' p1',shape[i-1],'pc',point,'p2',shape[i] 2716 if (angle < 2*alpha_crit) & (dist < dist_min_detect) & (road_main.highway not in footpath_nomerge): 2717 print ' add edge main edge %s' % ids_edge_sumo[ind_edge_main], ( 2718 id_edge_osm_main, is_opp) 2719 ids_osm_main.add((id_edge_osm_main, is_opp)) 2720 is_foundmatch = True 2721 break 2722 2723 is_remove = len(ids_osm_main) > 0 2724 2725 elif (road.footway != 'crossing') | (length > length_max_cross): 2726 # normal footpath merge 2727 2728 if (road.get_osmattr('tunnel') != 'yes') & (length > dist_min_remove): 2729 2730 for i in range(1, len(shape)): 2731 point = shape[i-1]+0.5*(shape[i]-shape[i-1]) 2732 is_foundmatch = False 2733 inds_edge_main, dists, angles = self.get_closest_edge_dist( 2734 point, ind, n_best=20, d_max=dist_min_detect) 2735 print ' check footpath point (%d/%d)' % (i+1, len(shape)) 2736 for ind_edge_main, dist, angle in zip(inds_edge_main, dists, angles): 2737 id_edge_osm_main, is_opp, nr = self.get_id_edge_osm_from_id_sumo( 2738 ids_edge_sumo[ind_edge_main]) 2739 road_main = edges_osm[id_edge_osm_main] 2740 prio = road_main.get_priority(is_opp) 2741 print ' check medge %s d=%.1fm al=%.1f,%.2f' % (ids_edge_sumo[ind_edge_main], dist, angle/np.pi*180, angle), prio, road_main.highway, ( 2742 angle < alpha_crit), (dist < dist_min_detect), (road_main.highway not in footpath_nomerge) 2743 # print ' p1',shape[i-1],'pc',point,'p2',shape[i] 2744 if (prio <= prio_max) & (angle < alpha_crit) & (dist < dist_min_detect) & (road_main.highway not in footpath_nomerge): 2745 print ' add edge main edge %s' % ids_edge_sumo[ind_edge_main], ( 2746 id_edge_osm_main, is_opp) 2747 ids_osm_main.add((id_edge_osm_main, is_opp)) 2748 is_foundmatch = True 2749 break 2750 2751 if not is_foundmatch: 2752 ids_osm_main = set() 2753 is_remove = False 2754 break 2755 else: 2756 is_remove = False 2757 2758 else: 2759 # special merge at crossings 2760 if (road.get_osmattr('tunnel') != 'yes'): 2761 2762 for i in range(1, len(shape)): 2763 point = shape[i-1]+0.5*(shape[i]-shape[i-1]) 2764 is_foundmatch = False 2765 inds_edge_main, dists, angles = self.get_closest_edge_dist( 2766 point, ind, n_best=20, d_max=dist_min_detect_cross) 2767 print ' check crossing point (%d/%d)' % (i+1, len(shape)) 2768 for ind_edge_main, dist, angle in zip(inds_edge_main, dists, angles): 2769 id_edge_osm_main, is_opp, nr = self.get_id_edge_osm_from_id_sumo( 2770 ids_edge_sumo[ind_edge_main]) 2771 road_main = edges_osm[id_edge_osm_main] 2772 prio = road_main.get_priority(is_opp) 2773 print ' check medge %s d=%.1fm al=%.1f' % (ids_edge_sumo[ind_edge_main], dist, angle/np.pi*180), prio, road_main.highway, ( 2774 angle < alpha_crit_cross), (dist < dist_min_detect_cross), (road_main.highway in footpath_merge_cross) 2775 # print ' p1',shape[i-1],'pc',point,'p2',shape[i] 2776 # if (prio<=prio_max)&(((angle<alpha_crit_cross)&(dist < dist_min_detect))|(dist < dist_min_detect_cross))& (road_main.highway in footpath_merge_cross): 2777 if (prio <= prio_max) & (angle < alpha_crit_cross) & (dist < dist_min_detect_cross) & (road_main.highway in footpath_merge_cross): 2778 print ' add edge main edge %s' % ids_edge_sumo[ind_edge_main], ( 2779 id_edge_osm_main, is_opp) 2780 ids_osm_main.add((id_edge_osm_main, is_opp)) 2781 is_foundmatch = True 2782 break 2783 2784 if not is_foundmatch: 2785 ids_osm_main = set() 2786 is_remove = False 2787 break 2788 2789 else: 2790 is_remove = False 2791 2792 if is_remove: 2793 # footpath can be matched to main roads 2794 2795 for id_osm_main, is_opp in ids_osm_main: 2796 print ' found', id_edge_osm, 'match with', id_osm_main, 'is_opp', is_opp 2797 edges_osm[id_osm_main].add_sidewalk(road, is_opp=is_opp) 2798 2799 # make sure footpath is invalid 2800 print ' eliminate edge', ids_edge_sumo[ind] 2801 are_edge_valid[ind] = False 2802 2803 def _get_osmid_from_attr(self, attrs): 2804 id_osm_str = attrs['osmid'] 2805 2806 if type(id_osm_str) in cm.STRINGTYPES: 2807 if id_osm_str.count(';') > 0: 2808 return int(id_osm_str.split(';')[0]) 2809 else: 2810 return int(id_osm_str) 2811 else: 2812 return id_osm_str 2813 2814 def _get_osmid_from_nxattr(self, attrs): 2815 id_osm_data = attrs['osmid'] 2816 2817 if hasattr(id_osm_data, '__iter__'): 2818 return str(id_osm_data[0]) 2819 else: 2820 return str(id_osm_data) 2821 2822 def import_nx(self, graphx, projparams=None, offset=None, highway_bidir=['rail', ]): 2823 """ 2824 Import an networkx graph into net 2825 """ 2826 print 'import_nx' 2827 net = self._net 2828 edges_osm = self.edges_osm 2829 nodes_osm = self.nodes_osm 2830 idmap = self._map_id_edge_sumo_to_doubles 2831 get_id_mode = net.modes.get_id_mode 2832 2833 if not hasattr(graphx, 'adj'): 2834 graphx.adj = graphx._adj 2835 2836 if not hasattr(graphx, 'node'): 2837 graphx.node = graphx._node 2838 2839 # initialize main vectors 2840 #n_nodes = len(graphx.adj) 2841 #ids_nodes_sumo = np.zeros(n_nodes, dtype = np.object) 2842 #ids_nodes_sumo = np.array(graphx.adj.keys(), dtype = np.int32) 2843 gxnodes = graphx.node 2844 nodes = net.nodes 2845 edges = net.edges 2846 n_node = len(graphx.adj) 2847 ids_node = net.nodes.add_rows(n_node) 2848 2849 id_sumonodetypes = nodes.types.choices 2850 id_nodetype_default = id_sumonodetypes['priority'] 2851 id_nodetype_tl = id_sumonodetypes['traffic_light'] 2852 nodetypemap = {'motorway_junction': id_sumonodetypes['zipper'], 2853 'traffic_signals': id_sumonodetypes['traffic_light'], 2854 'crossing': id_sumonodetypes['priority'], 2855 'turning_circle': id_sumonodetypes['dead_end'], 2856 'turning_loop': id_sumonodetypes['dead_end'], 2857 'miniroundabout': id_sumonodetypes['priority'], 2858 'stop': id_sumonodetypes['allway_stop'], 2859 } 2860 2861 lonlats_node = np.zeros((n_node, 2), dtype=np.float32) 2862 ids_node_sumo = np.zeros(n_node, dtype=np.object) 2863 nodetypes = np.zeros(n_node, dtype=np.int32) 2864 elevation = np.zeros(n_node, dtype=np.float32) 2865 #nodetype = np.zeros(n_node, dtype = np.object) 2866 2867 # for id_sumo, nodedict in zip(nodes.ids_sumo[ids_node],: 2868 2869 #ids_node_sumo = np.zeros(n_node, dtype = np.int32) 2870 2871 i_node = -1 2872 for id_fromnode, id_fromnode_sumo, outgoingdicts in zip(ids_node, graphx.adj.keys(), graphx.adj.values()): 2873 i_node += 1 2874 #ids_node_sumo[i_node] = id_fromnode_sumo 2875 print ' ', id_fromnode, id_fromnode_sumo, gxnodes[id_fromnode_sumo] # nodes.ids_sumo[id_fromnode] 2876 lonlats_node[i_node] = [gxnodes[id_fromnode_sumo]['x'], gxnodes[id_fromnode_sumo]['y']] 2877 ids_node_sumo[i_node] = str(id_fromnode_sumo) 2878 elevation[i_node] = float(gxnodes[id_fromnode_sumo].get('elevation', 0.0)) 2879 nxnodetype = gxnodes[id_fromnode_sumo].get('highway', 'default') 2880 # if nxnodetype == 'crossing':... 2881 # if nxnodetype = 'bus_stop' 2882 nodetypes[i_node] = nodetypemap.get(nxnodetype, id_nodetype_default) 2883 2884 nodes.ids_sumo[ids_node] = ids_node_sumo 2885 nodes.types[ids_node] = nodetypes 2886 nodes.types_tl[ids_node[nodetypes == id_nodetype_tl]] = nodes.types_tl.choices['static'] 2887 2888 if projparams is None: 2889 print ' take first node to estimate projection', (lonlats_node[0][0], lonlats_node[0][1]) 2890 projparams = guess_utm_from_coord([lonlats_node[0][0], lonlats_node[0][1]]) 2891 print ' projparams', projparams 2892 proj = pyproj.Proj(projparams) 2893 net.set_projparams(projparams) 2894 2895 xx, yy = proj(lonlats_node[:, 0], lonlats_node[:, 1]) 2896 zz = elevation 2897 if offset == None: 2898 offset = np.array([-np.min(xx), -np.min(yy)], dtype=np.float32) 2899 offset3d = np.array([-np.min(xx), -np.min(yy), 0.0], dtype=np.float32) 2900 net.set_offset(offset) 2901 2902 # Format of Boundary box [MinX, MinY ,MaxX, MaxY ] 2903 net.set_boundaries([0, 0, np.max(xx)+offset[0], np.max(yy)+offset[1]], 2904 [np.min(lonlats_node[:, 0]), np.min(lonlats_node[:, 1]), np.max(lonlats_node[:, 0]), np.max(lonlats_node[:, 1])]) 2905 2906 # print ' nodes.coords[ids_node].shape', nodes.coords[ids_node].shape 2907 # print ' (xx+offset[0]).shape', (xx+offset[0]).shape 2908 2909 #nodes.coords[ids_node][:,0] = xx+offset[0] 2910 #nodes.coords[ids_node][:,1] = yy+offset[1] 2911 2912 # print ' xx',np.array(xx, dtype = np.float32).reshape(-1,1).shape 2913 # print ' yy',np.array(yy, dtype = np.float32).reshape(-1,1).shape 2914 # print ' zz.reshape(-1,1)',zz.reshape(-1,1).shape 2915 nodes.coords[ids_node] = np.concatenate((np.array(xx, dtype=np.float32).reshape(-1, 1), 2916 np.array(yy, dtype=np.float32).reshape(-1, 1), 2917 zz.reshape(-1, 1)), 1) + offset3d 2918 2919 ids_edge_sumo = [] # np.zeros(n_edge, dtype = np.object) 2920 ids_edge_osm = [] # np.zeros(n_edge, dtype = np.int32) 2921 inds_edge_opp = [] # -1*np.ones(n_edge, dtype = np.int32) 2922 2923 ids_fromnode = [] # np.zeros(n_edge, dtype = np.int32) 2924 ids_tonode = [] # np.zeros(n_edge, dtype = np.int32) 2925 #lengths = np.zeros(n_edge, dtype = np.float32) 2926 shapes = [] # np.zeros(n_edge, dtype = np.object) 2927 #names = np.zeros(n_edge, dtype = np.object) 2928 # types_spread = np.zeros(n_edge, dtype = np.object) # 0=center, 1 = right 2929 get_id_node = nodes.ids_sumo.get_id_from_index 2930 i_edge = -1 2931 i_node = -1 2932 2933 # dictionary with id_osm as key and (id_fromnode,id_tonode) as value 2934 # this is to prevent, that a return way with the same id_osm 2935 # is being created 2936 self._edgelookup = {} 2937 2938 # debug 2939 self._nodelookup = {} 2940 2941 for id_fromnode, id_fromnode_sumo, outgoingdicts in zip(ids_node, graphx.adj.keys(), graphx.adj.values()): 2942 i_node += 1 2943 # print ' id_fromnode_sumo',i_node, id_fromnode, id_fromnode_sumo 2944 for id_tonode_sumo, edgedatalist in outgoingdicts.iteritems(): 2945 2946 edgeattrs = edgedatalist[0] 2947 2948 id_osm = self._get_osmid_from_nxattr(edgeattrs) 2949 2950 if self.is_edge_eligible(id_osm, id_fromnode_sumo, id_tonode_sumo): 2951 2952 id_tonode = get_id_node(str(id_tonode_sumo)) 2953 2954 if edgeattrs.has_key('geometry'): 2955 # print ' geometry',edgeattrs['geometry'] 2956 lonlats = edgeattrs['geometry'].xy 2957 xx, yy = proj(lonlats[0], lonlats[1]) 2958 zz = np.zeros((len(xx), 1), dtype=np.float32) 2959 # print ' xx',xx 2960 # print ' yy',yy 2961 # print ' zz',zz 2962 shape1 = np.concatenate((np.array(xx, dtype=np.float32).reshape(-1, 1), 2963 np.array(yy, dtype=np.float32).reshape(-1, 1), 2964 zz), 1) + offset3d 2965 2966 # elevation interpolation 2967 # print ' shape1',shape1 2968 # print ' dists',np.sqrt(np.sum((shape1[1:,:]-shape1[:-1,:])**2,1)) 2969 cumlength = np.cumsum(np.sqrt(np.sum((shape1[1:, :]-shape1[:-1, :])**2, 1))) 2970 # print ' cumlength',cumlength 2971 length = cumlength[-1] 2972 vfrom, vto = nodes.coords[[id_fromnode, id_tonode]] 2973 height_delta = vto[2]-vfrom[2] 2974 height_offset = vfrom[2] 2975 height = height_offset+cumlength/length*height_delta 2976 2977 # print ' cumlength.shape',cumlength.shape 2978 # print ' height_offset',height_offset 2979 # print ' height_delta',height_delta 2980 2981 # print ' height',height.shape,height 2982 shape1[0, 2] = height_offset 2983 shape1[1:, 2] = height 2984 2985 else: 2986 shape1 = nodes.coords[[id_fromnode, id_tonode]] 2987 2988 # 2989 # make foreward edge 2990 2991 # print ' shape=\n',list(shape) 2992 i_edge += 1 2993 shapes.append(list(shape1)) 2994 ids_fromnode.append(id_fromnode) 2995 ids_tonode.append(id_tonode) 2996 2997 ids_edge_osm.append(id_osm) 2998 #edgenum = get_edgenumber(id_osm) 2999 ids_edge_sumo.append(self.get_id_edge_sumo(id_osm)) 3000 3001 road = edges_osm[id_osm] 3002 print ' created edge %s from' % ids_edge_sumo[-1], id_fromnode_sumo, 'to', id_tonode_sumo 3003 # print ' id_osm,id(road)', id_osm, id(road), ids_edge_osm[i_edge] 3004 3005 if not road.is_oneway(): 3006 # set edge for opposite direction 3007 inds_edge_opp.append(i_edge + 1) # index of opposite edge 3008 i_edge += 1 3009 shapes.append(list(shape1)[::-1]) 3010 ids_fromnode.append(id_tonode) 3011 ids_tonode.append(id_fromnode) 3012 ids_edge_sumo.append(self.get_id_edge_sumo('-'+id_osm)) 3013 ids_edge_osm.append(id_osm) 3014 inds_edge_opp.append(-2) # mark that this is the opposite edge 3015 print ' created reverse ids_edge_sumo', ids_edge_sumo[i_edge] 3016 3017 else: 3018 inds_edge_opp.append(-1) 3019 3020 self._are_edge_valid = np.ones(len(ids_edge_sumo), dtype=np.bool) 3021 3022 # print ' inds_valid before',inds_valid 3023 self._edgeshapes = np.array(shapes, dtype=np.object) 3024 self._ids_edge_osm = np.array(ids_edge_osm, dtype=np.object) 3025 self._ids_edge_sumo = np.array(ids_edge_sumo, dtype=np.object) 3026 self._length = get_length_polypoints(self._edgeshapes) 3027 3028 self._ids_fromnode = np.array(ids_fromnode, dtype=np.int32) 3029 self._ids_tonode = np.array(ids_tonode, dtype=np.int32) 3030 self.make_segment_edge_map() 3031 3032 self.check_consistency() 3033 self.configure_roundabouts() 3034 self.configure_footpath() 3035 3036 inds_valid = np.flatnonzero(self._are_edge_valid) 3037 n_edge = len(inds_valid) 3038 # print ' n_edge',n_edge,'of',len(ids_edge_sumo) 3039 # print ' inds_valid',inds_valid 3040 # print ' shapes', shapes 3041 ids_edges = edges.multimake(self._ids_edge_sumo[inds_valid], 3042 ids_fromnode=self._ids_fromnode[inds_valid], 3043 ids_tonode=self._ids_tonode[inds_valid], 3044 #lengths = lengths, 3045 shapes=self._edgeshapes[inds_valid], 3046 #names = names, 3047 ) 3048 3049 roundabouts = net.roundabouts 3050 for ids_rbedge_sumo, ids_rbnode in self._roundabouts: 3051 # print ' ', 3052 roundabouts.make(ids_edge=edges.ids_sumo.get_ids_from_indices(ids_rbedge_sumo), 3053 ids_node=ids_rbnode, 3054 ) 3055 3056 # print ' shapes[0:9]',shapes[0:9] 3057 # print ' edges.shapes[1:10]',edges.shapes[1:10] 3058 # print ' edges.shapes.get_value()[0:9]',edges.shapes.get_value()[0:9] 3059 #net.edges.update(is_update_lanes = False) 3060 # enrich edges with osmattributes 3061 # print ' ids_edge_osm',ids_edge_osm 3062 for id_edge, id_edge_osm, ind_edge_opp in zip(ids_edges, self._ids_edge_osm[inds_valid], np.array(inds_edge_opp, dtype=np.int32)[inds_valid]): 3063 id_sumo = edges.ids_sumo[id_edge] 3064 3065 if id_sumo[0] > '-': # it is not an opposite edge 3066 road = edges_osm[id_edge_osm] 3067 # print ' configure way',id_edge_osm,id(self.edges_osm[id_edge_osm]),id(road) 3068 road.configure_edge(id_edge, net) 3069 #id_edge_opp = self.get_id_edge_opp 3070 id_sumo_opp = '-'+id_sumo 3071 if edges.ids_sumo.has_index(id_sumo_opp): # there is an opposite edge 3072 road.configure_edge(edges.ids_sumo.get_id_from_index(id_sumo_opp), net, is_opp=True) 3073 3074 # make roundabouts 3075