Exemple #1
0
def plotBackground(areaPoly=None, ax=None, globalOrigin=None):
	"""
	plots the background from the tiff-file given. In the future, maybe data is taken from
	google maps or something similar?

	#local coordinates in areaPoly, with origin in origin
	origin is given in sweref99 coordinates, not local.
	"""	
	if not areaPoly: raise Exception('need area polygon in order to plot background')
	if not ax:
		fig=plt.figure()
		ax=fig.add_subplot(111, aspect='equal')
	figCorner=(595000, 6725000) #for this specific area, not general		
	if not globalOrigin:
		globalOrigin=figCorner
	#now, let our global origin be in the origin..
	w=5000 #for this specific image..
	h=5000
	figorigin=np.array(figCorner)-np.array(globalOrigin)
	limits=[figorigin[0], figorigin[0]+w, figorigin[1], figorigin[1]+h]
	folder=os.path.dirname(os.path.abspath(__file__))
	folder=os.path.join(folder, 'GIS')
	map=LinearSegmentedColormap.from_list('lightgray', ['#666666', '#C5C5C5']) #our own cmap
	bg=mpimg.imread(os.path.join(folder,'672_59_11.tif'))
	im = plt.imshow(bg, cmap=map,origin='lower', extent=limits)
	
	#now, adjust to our polygon..
	limits=list(fun.polygonLim(areaPoly))
	w=max(10, max(limits)/10.)
	limits[0]-=w #to get some space to polygon
	limits[1]+=w
	limits[2]-=w
	limits[3]+=w
	ax.axis(limits)
	return ax
Exemple #2
0
	def __init__(self, origin=None, globalOrigin=None,areaPoly=None, gridtype=None):
		if not areaPoly:
			raise Exception('areaPoly must be given.')
		if not origin:
			origin=(0,0)
		if not globalOrigin:
			globalOrigin=(596120, 6727530) #sweref99..located on map.. nice position.. use as default.
		self.areaPoly=areaPoly
		xmin,xmax,ymin,ymax=fun.polygonLim(areaPoly)
		side=10
		self.lim=np.array([xmin-0.5*side,xmax+0.5*side, ymin-0.5*side, ymax+0.5*side])
		self.A=fun.polygon_area(areaPoly)
		self.Ainv=1./self.A #used a lot.. faster to just compute this once.
		self.origin=origin
		self.globalOrigin=globalOrigin
		self.type=gridtype
		x,y,z=GIS.readTerrain(globalOrigin=globalOrigin , areaPoly=areaPoly)
		#get a list of how x and y varies.. strictly ascending
		xlist=x[:,0] #just the variations, not the 2D-matrix
		ylist=y[0,:]
		self.interpol=RectBivariateSpline(xlist, ylist, z) #used pretty much everytime we need the height of a specific point. Implemented in fortran and very fast

		nx.Graph.__init__(self)
		self.t_x=x
		self.t_y=y
		self.t_z=z
		self.roadWidth=4 #width of road
		self.overlap={} #will later be filled. A speedup thing
		self.weightFunction=normalizedPitchDist #reference to exter
		self.areaCover=go.roadAreaCoverage(self)
		self.moviefig=None #may be used for movies later
		self.cmdfolder=os.path.split(os.path.dirname(os.path.abspath(__file__)))[0]
Exemple #3
0
	def __init__(self,G=None, generate=False, dens=1, dbh_mean=0.5, dbh_std=0.1):
		if not G: raise Exception('by design, you need G for terrain to work. (globalVar(), see sim.tools.py)')
		self.G=G
		self.trees=[]
		self.stumps=[]
		self.roots=[]
		self.holes=[]
		self.piles=[]
		self.obstacles=[] #should hold all the above, except boulders.
		self.stumpFile='undefined'
		self.treeFile='undefined'
		self.stumpsPerH=0
		self.boulderFreq=0
		self.meanBoulderV=0
		#the following stuff are only used when the stand files are used. should maybe be separated.
		if not G.areaPoly: #create from A, square
			raise Exception('got too little information about the area, need areaPoly polygon. ')
		self.areaPoly=G.areaPoly
		self.area=polygon_area(G.areaPoly)
		lim=fun.polygonLim(self.areaPoly)
		self.xlim=list(lim[0:2])
		self.ylim=list(lim[2:4])
		if self.G and self.G.gridL:
			self._fixGrid(L=self.G.gridL)
		else:
			self._fixGrid()
		if not generate:
			self._fileini()
		else:
			self.generateTrees(dens, dbh_mean, dbh_std)
Exemple #4
0
	def __init__(self,L=24, xyRatio=1, origin=None, globalOrigin=None,angle=None, areaPoly=None):
		ExtendedGraph.__init__(self, origin=origin, globalOrigin=globalOrigin,areaPoly=areaPoly, gridtype='triGridGraph')
		
		digits=3 #used later..
		C=L/2. #preference questions, this does not span entirely all of space but is a good compromise
		self.L=L
		self.C=C
		dx=L
		dy=L*round(sqrt(3)/2., digits)
		cart=fun.getCartesian
		#xl=np.arange(0,Nx*dx, dx, dtype


		"""The strategy is to first cover an extra large area, and then take away the nodes that are outside.
		for a square area, the maximum "x-distance" is sqrt(2) times the side. This corresponds to angle pi/4 or
		5pi/4. The strategy is to always use this maximum length and then take away the ones outisde the area.
		This is an easy but inefficient algorithm, there is certainly room for speed up if required.
		But when coding this, most of the time is spent somewhere else so it doesn't matter really to optimize this part.
		"""
		xmin,xmax,ymin,ymax=fun.polygonLim(areaPoly)
		x1=np.arange(xmin,ceil(sqrt(xmax**2+ymax**2)), dx, dtype=np.float)
		x2=np.arange(xmin-dx/2., ceil(sqrt(xmax**2+ymax**2)), dx, dtype=np.float)
		yl=np.arange(ymin,ceil(sqrt(xmax**2+ymax**2)), dy, dtype=np.float) #hypothenuse in another way
		if not angle: angle=0
		#G=nx.Graph( L=L, type='sqGridGraph', C=C)
		self.lim=np.array([xmin-0.5*L,xmax+0.5*L, ymin-0.5*L, ymax+0.5*L])
		el=0
		direction=angle+pi/2.

		for yloc in yl:
			if (round(yloc/dy))%2==0:
				xl=x1
				xtype='x1'
			else:
				xl=x2
				xtype='x2'
			for index,xloc in enumerate(xl):
				if yloc==0 or angle==0: sl=[1]
				else: sl=[1,-1]
				for sign in sl:
					x,y=tuple(cart((xloc,sign*yloc), origin=(0,0), direction=direction, fromLocalCart=True))
					x,y=round(x,digits), round(y,digits)
					#x,y is now real coordinates, transformed through angle.
					if not inside((x,y),areaPoly): continue
					self.add_node((x, y))
					el+=1
					if y != 0:
						if index != 0:
							neig=tuple(cart([xloc-dx/2., round(yloc-dy,digits)], origin=(0,0), direction=direction, fromLocalCart=True))
							neig=round(neig[0],digits), round(neig[1],digits)
							if inside(neig, areaPoly): self.add_edge((x,y), neig, weight=L, visits=0, visited_from_node=[],c=0)
							neig=tuple(cart([xloc+dx/2., yloc-dy,digits], origin=(0,0), direction=direction, fromLocalCart=True))
							neig=round(neig[0],digits), round(neig[1],digits)
							if inside(neig, areaPoly): self.add_edge((x,y), neig, weight=L, visits=0, visited_from_node=[],c=0)
					if index != 0:
						self.add_edge(tuple([x,round(y,digits)]),tuple([x-dx, round(y,digits)]), weight=L, visits=0, visited_from_node=[],c=0)
		rem=True
		while rem:
			rem=False
			for n in self.nodes(): #pretty ugly, but a must..
				if self.degree(n)==1:
					rem=True
					self.remove_node(n)
					break
		self.overlap={} #will later be filled.
		self.roadWidth=4
		elements=el
		self.elements=el
		self.L=L
		self.density=elements/self.A
Exemple #5
0
	def __init__(self,L=24, xyRatio=1,origin=None, globalOrigin=None,areaPoly=None, diagonals=False, angle=None):
		
		ExtendedGraph.__init__(self, origin=origin, globalOrigin=globalOrigin,areaPoly=areaPoly, gridtype='sqGridGraph')
		C=L/2.
		self.C=C
		self.L=L

		if angle ==None: #find the longest edge, and use its angle
			print "get the angle"
			angle=getAngleFromLongestEdge(areaPoly, origin)
			print "got the angle.", angle
			while angle>pi/2. or angle<0: #if it is.. most often does not enter loop
				if angle<0:
					angle+=pi/2.
				else:
					angle-=pi/2.
		dx=L
		dy=L
		cart=fun.getCartesian
		digits=3 #we round of to this in order to avoid numerical errors. 1mm is enough :)
		"""The strategy is to first cover an extra large area, and then take away the nodes that are outside.
		for a square area, the maximum "x-distance" is sqrt(2) times the side. This corresponds to angle pi/4 or
		5pi/4. The strategy is to always use this maximum length and then take away the ones outisde the area."""
		d=1/sqrt(2)+0.001
		direction=angle+pi/2.
		xmin,xmax,ymin,ymax=fun.polygonLim(areaPoly)
		xl=np.arange(xmin+C,ceil(sqrt(xmax**2+ymax**2)), dx, dtype=np.float) #hypothenuse
		yl=np.arange(ymin+C,ceil(sqrt(xmax**2+ymax**2)), dy, dtype=np.float) 
		el=0
		for xloc in xl:
			for yloc in yl:
				if yloc==0 or angle==0: sl=[1]
				else: sl=[1,-1]
				for sign in sl:
					x, y=tuple(cart((xloc,sign*yloc), origin=(0,0), direction=direction, fromLocalCart=True))
					x,y=round(x,digits), round(y,digits)
					if not inside((x,y),areaPoly): continue
					self.add_node((x, y))
					el+=1
					#neigbor 'backwards' in y-dir
					neig=tuple(cart((xloc,sign*(yloc)-dy), origin=(0,0), direction=direction, fromLocalCart=True))
					neig=round(neig[0],digits), round(neig[1],digits)
					if inside(neig, areaPoly): self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[], c=0)
					if diagonals and xloc != 0:
						neig=tuple(cart((xloc-dx,sign*(yloc-dy)), origin=(0,0), direction=direction, fromLocalCart=True))
						neig=round(neig[0],digits), round(neig[1],digits)
						if inside(neig, areaPoly): self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[],c=0)
						neig=tuple(cart((xloc+dx,sign*(yloc-dy)), origin=(0,0), direction=direction, fromLocalCart=True))
						neig=round(neig[0],digits), round(neig[1],digits)
						if inside(neig, areaPoly): self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig),visits=0, visited_from_node=[],c=0)
					if True or xloc != 0:
						neig=tuple(cart((xloc-dx,sign*yloc), origin=(0,0), direction=direction, fromLocalCart=True))
						neig=round(neig[0],digits), round(neig[1],digits)
						if inside(neig, areaPoly): self.add_edge((x,y),neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[],c=0)
		rem=True
		while rem:
			rem=False
			for n in self.nodes(): #pretty ugly, but a must..
				if self.degree(n)<=1:
					rem=True
					self.remove_node(n)
					break
		if not self.origin in self.nodes():
			shortest=None
			short_dist=1e10
			for n in self.nodes():
				d=fun.getDistance(n, self.origin)
				if d<short_dist:
					short_dist=d
					shortest=n
			self.origin=shortest
		elements=el
		self.elements=el			
		self.density=elements/self.A
Exemple #6
0
def readTerrain(globalOrigin=None, areaPoly=None):
	"""
	reads in data and returns local grid  x,y,z coordinates.

	Notes:
	-sweref coordinates are basically in [m], useful. We just need to normalize them to our new origin.
	-Problem with intersections between the files... how to handle?
	"""
	if not globalOrigin: globalOrigin=(596120, 6727530) #located on map.. nice position..
	if not areaPoly: areaPoly=[(0,0), (200,0), (200,200), (0,200)] #default..
	globalPoly=getGlobalCoordinate(globalOrigin, areaPoly=areaPoly)
	corn=(595000, 6725000)
	bordersPoly=[corn, (corn[0]+5000, corn[1]), (corn[0]+5000, corn[1]+5000), (corn[0], corn[1]+5000)]
	#check if polygon is inside polygon
	for node in globalPoly:
		if not col.pointInPolygon(node, globalPoly): raise Exception('areaPolygon is outside of the area that we have maps for.')

	#so, read in the data for our areaPolygon, or rather square containing it, and
	#normalize the cooordinates with respect to our origin.
	range=fun.polygonLim(globalPoly)
	xrange=range[0:2]
	yrange=range[2:4]
	xrange=[xrange[0]-2, xrange[1]+2]
	yrange=[yrange[0]-2, yrange[1]+2]
	#now, we should find out which files we need...
	fileList=getFileList(globalPoly)
	x, y, z=None, None, None #will later be created
	xlist, ylist, zlist=[], [], []
	m=1 #modulu, to reduce the grid resolution.. should be set from area of polygon..
	yold=None
	if len(fileList)>1: raise Exception('we do not support file overlaps right now..')
	folder=os.path.join(os.path.dirname(os.path.abspath(__file__)), 'tab')
	for fname in fileList:
		f=open(os.path.join(folder, fname+'.asc'))
		for index, line in enumerate(f):
			l=line.split()
			xtmp=int(l[0])
			ytmp=int(l[1])
			if ytmp>yrange[1]: break #because of how file is organized, we can do this.
			if xtmp<=xrange[1] and xtmp>=xrange[0] and ytmp>=yrange[0] and xtmp%m==0 and ytmp%m==0:
				if yold==None: yold=ytmp
				ztmp=float(l[2])
				if ytmp != yold: #new row..
					#identify if we're gonna need the next file in line..
					if x==None:
						x=np.array(xlist)
						y=np.array(ylist)
						z=np.array(zlist)
					else:
						x=np.vstack((x, xlist))
						y=np.vstack((y, ylist))
						z=np.vstack((z, zlist))
					xlist, ylist, zlist = [], [], []
				xlist.append(xtmp)
				ylist.append(ytmp)
				zlist.append(ztmp)
				yold=ytmp
		f.close()
	x-=globalOrigin[0]
	y-=globalOrigin[1]
	x=np.transpose(x) #we want it in the standard form that scipy understands.
	y=np.transpose(y) #this form corresponds to numpy.mgrid standard, but not numpy.meshgrid
	z=np.transpose(z)
	return x,y,z
Exemple #7
0
	def __init__(self,L=None, xyRatio=1, origin=None, globalOrigin=None,angle=None, areaPoly=None,  weightFunction=weightFromLength):
		"""The strategy is to first cover an extra large area, and then take away the nodes that are outside.
		for a square area, the maximum "x-distance" is sqrt(2) times the side. This corresponds to angle pi/4 or
		5pi/4. The strategy is to always use this maximum length and then take away the ones outisde the area.
		This is an easy but inefficient algorithm, there is certainly room for speed up if required.
		But when coding this, most of the time is spent somewhere else so it doesn't matter really to optimize this part.

		The square grid has been updated with a better algorithm for this. It might be a good idea to copy this algorithm to this part, but it is not done now.

		Another improvement could be to optimize the inside() function. It currently does unnecessary many point in polygon tests, which is time consuming for polygons with many nodes.
		"""
		C=12
		digits=3 #used later..
		if L==None:
			L=C/(sin(1/3.0*pi)*0.5)
		ExtendedGraph.__init__(self, origin=origin, globalOrigin=globalOrigin,areaPoly=areaPoly, L=L, C=C,gridtype='triGridGraph', weightFunction=weightFunction)
		#C=L/2. #preference questions, this does not span entirely all of space but is a good compromise
		self.L=L
		self.C=C
		dx=L
		dy=L*round(sqrt(3)/2., digits)
		cart=fun.getCartesian

		xmin,xmax,ymin,ymax=fun.polygonLim(areaPoly)
		x1=np.arange(xmin,ceil(sqrt(xmax**2+ymax**2)), dx, dtype=np.float)
		x2=np.arange(xmin-dx/2., ceil(sqrt(xmax**2+ymax**2)), dx, dtype=np.float)
		yl=np.arange(ymin,ceil(sqrt(xmax**2+ymax**2)), dy, dtype=np.float) #hypothenuse in another way
		if not angle: angle=0
		self.lim=np.array([xmin-0.5*L,xmax+0.5*L, ymin-0.5*L, ymax+0.5*L])
		direction=angle+pi/2.

		for yloc in yl:
			if (round(yloc/dy))%2==0:
				xl=x1
			else:
				xl=x2
			for index,xloc in enumerate(xl):
				x,y=tuple(cart((xloc,yloc), origin=(0,0), direction=direction, fromLocalCart=True))
				x,y=round(x,digits), round(y,digits)
				self.add_node((x, y))
				if y != 0:
					neig=tuple(cart([xloc-dx/2., round(yloc-dy,digits)], origin=(0,0), direction=direction, fromLocalCart=True))
					neig=round(neig[0],digits), round(neig[1],digits)
					self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y),neig), visits=0, visited_from_node=[],c=0)
					neig=tuple(cart([xloc+dx/2., yloc-dy,digits], origin=(0,0), direction=direction, fromLocalCart=True))
					neig=round(neig[0],digits), round(neig[1],digits)
					self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y),neig), visits=0, visited_from_node=[],c=0)
				self.add_edge((x,y),tuple([round(x-dx,digits), round(y,digits)]), weight=self.edgeWeightCalc((x,y),tuple([round(x-dx,digits), round(y,digits)])), visits=0, visited_from_node=[],c=0)
		rem=True
		for n in self.nodes():
			if not self.inside(n):
				self.remove_node(n)
		while rem:
			rem=False
			for n in self.nodes(): #pretty ugly, but a must..
				if self.degree(n)<=1:
					rem=True
					self.remove_node(n)
					break
		self.overlap={} #will later be filled.
		self.roadWidth=4
		self.L=L
		if not self.origin in self.nodes():
			shortest=None
			short_dist=1e10
			for n in self.nodes():
				d=fun.getDistance(n, self.origin)
				if d<short_dist:
					short_dist=d
					shortest=n
			self.origin=shortest
		elements=len(self.nodes())
		self.elements=elements
		self.density=elements/self.A
		self.density=elements/self.A
Exemple #8
0
	def __init__(self,L=24, xyRatio=1,origin=None, globalOrigin=None,areaPoly=None, diagonals=False, angle=None, shift=(0,0), weightFunction=weightFromLength):
		C=L/2.0
		ExtendedGraph.__init__(self, origin=origin, globalOrigin=globalOrigin,areaPoly=areaPoly, L=L, C=C, gridtype='sqGridGraph', weightFunction=weightFunction)
		xmin,xmax,ymin,ymax=fun.polygonLim(areaPoly)
		origin=self.origin
		
		if angle ==None: #find the longest edge, and use its angle
			angle, shift=self.getAngleFromLongestEdge()
			print "got the angle.", angle*360/(2*3.14), shift
			while angle>pi/2. or angle<0: #if it is.. most often does not enter loop
				if angle<0:
					angle+=pi/2.
				else:
					angle-=pi/2.
		dx=L
		dy=L
		cart=fun.getCartesian
		digits=3 #we round of to this in order to avoid numerical errors. 1mm is enough :)
		"""The strategy is to first cover an extra large area, and then take away the nodes that are outside.
		for a square area, the maximum "x-distance" is sqrt(2) times the side. This corresponds to angle pi/4 or
		5pi/4. The strategy is to always use this maximum length and then take away the ones outisde the area."""
		d=1/sqrt(2)+0.001
		#direction is by definition not bigger that 90 degrees:
		ym=sqrt((xmax-xmin)**2+(ymax-ymin)**2)
		xlmin=-ceil(sin(pi/2.-angle)*(ymax-ymin)/L)*L
		xlmax=ceil(sin(angle)*(xmax-xmin)/L)*L
		xl=np.arange(shift[0]+xlmin,xlmax, dx, dtype=np.float)
		yl=np.arange(shift[1],ym, dy, dtype=np.float)
		for xloc in xl:
			for yloc in yl:
				if yloc==0 or angle==0: sl=[1]
				x, y=tuple(cart((xloc,yloc), origin=origin, direction=angle, fromLocalCart=True))
				x,y=round(x,digits), round(y,digits)
				self.add_node((x, y))
				#neigbor 'backwards' in y-dir
				neig=tuple(cart((xloc,(yloc)-dy), origin=origin, direction=angle, fromLocalCart=True))
				neig=round(neig[0],digits), round(neig[1],digits)
				self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[], c=0)
				if diagonals and xloc != 0:
					neig=tuple(cart((xloc-dx,(yloc-dy)), origin=origin, direction=angle,fromLocalCart=True))
					neig=round(neig[0],digits), round(neig[1],digits)
					self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[],c=0)
					neig=tuple(cart((xloc+dx,(yloc-dy)), origin=origin, direction=angle, fromLocalCart=True))
					neig=round(neig[0],digits), round(neig[1],digits)
					self.add_edge((x,y), neig, weight=self.edgeWeightCalc((x,y), neig),visits=0, visited_from_node=[],c=0)
				neig=tuple(cart((xloc-dx,yloc), origin=origin, direction=angle, fromLocalCart=True))
				neig=round(neig[0],digits), round(neig[1],digits)
				self.add_edge((x,y),neig, weight=self.edgeWeightCalc((x,y), neig), visits=0, visited_from_node=[],c=0)
		for node in self.nodes():
			if not self.inside(node):
				self.remove_node(node)
		rem=True
		while rem:
			rem=False
			for n in self.nodes(): #pretty ugly, but a must..
				if self.degree(n)<=1:
					rem=True
					self.remove_node(n)
					break
		if not self.origin in self.nodes():
			shortest=None
			short_dist=1e10
			for n in self.nodes():
				d=fun.getDistance(n, self.origin)
				if d<short_dist:
					short_dist=d
					shortest=n
			self.origin=shortest
		elements=len(self.nodes())
		self.elements=elements
		self.density=elements/self.A