Beispiel #1
0
//---------------------------------------------------------
double CExercise_14::Vectorise(int x, int y, CSG_Shape *pSegment)
{
	int		Dir, ix, iy;
	double	Length;

	Length	= 0.0;

	pSegment->Add_Point(Get_XMin() + x * Get_Cellsize(), Get_YMin() + y * Get_Cellsize());

	if( (Dir = m_pDir->asInt(x, y)) >= 0 )
	{
		Length	= Get_Length(Dir);

		ix		= Get_xTo(Dir, x);
		iy		= Get_yTo(Dir, y);

		switch( m_pChnl->asInt(ix, iy) )
		{
		case CHANNEL:
			Length	+= Vectorise(ix, iy, pSegment);	// recursive function call...
			break;

		case MOUTH:
			Length	+= Get_Length(Dir);
			pSegment->Add_Point(Get_XMin() + ix * Get_Cellsize(), Get_YMin() + iy * Get_Cellsize());
			break;
		}
	}

	return( Length );
}
Beispiel #2
0
//---------------------------------------------------------
double CErosion_LS_Fields::Get_Flow(int x, int y, double dz[8])
{
	if( m_Fields.is_NoData(x, y) )
	{
		return( 0.0 );
	}

	double	d, z = m_pDEM->asDouble(x, y), dzSum = 0.0;

	int		ID	= m_Fields.asInt(x, y);

	for(int i=0; i<8; i++)
	{
		dz[i]	= 0.0;

		int	ix	= Get_xTo(i, x);
		int	iy	= Get_yTo(i, y);

		if(	m_pDEM->is_InGrid(ix, iy) && (d = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
		{
			if( ID == m_Fields.asInt(ix, iy) )
			{
				dzSum	+= (dz[i] = pow(d / Get_Length(i), 1.1));
			}
			else if( m_bStopAtEdge )
			{
				dzSum	+= pow(d / Get_Length(i), 1.1);
			}
		}
	}

	return( dzSum );
}
//---------------------------------------------------------
void CChannelNetwork_Distance::Initialize_MFD(int x, int y)
{
	const double	MFD_Convergence	= 1.1;

	double	Flow[8], dz, zSum = 0.0, z = m_pDEM->asDouble(x, y);

	if( m_pRoute )
	{
		for(int i=0, ix, iy; i<8; i++)
		{
			if( m_pDEM->is_InGrid(ix=Get_xTo(i, x), iy=Get_yTo(i, y)) && !m_pRoute->is_NoData(ix, iy) && (dz = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
			{
				zSum	+= (Flow[i]	= pow(dz / Get_Length(i), MFD_Convergence));
			}
			else
			{
				Flow[i]	= 0.0;
			}
		}
	}

	if( zSum == 0.0 )
	{
		for(int i=0, ix, iy; i<8; i++)
		{
			if( m_pDEM->is_InGrid(ix=Get_xTo(i, x), iy=Get_yTo(i, y)) && (dz = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
			{
				zSum	+= (Flow[i]	= pow(dz / Get_Length(i), MFD_Convergence));
			}
			else
			{
				Flow[i]	= 0.0;
			}
		}
	}

	if( zSum > 0.0 )
	{
		m_Flow[8].Set_Value(x, y, zSum);

		for(int i=0; i<8; i++)
		{
			if( Flow[i] > 0.0 )
			{
				m_Flow[i].Set_Value(x, y, Flow[i] / zSum);
			}
		}
	}
}
Beispiel #4
0
//---------------------------------------------------------
void CChannelNetwork::Set_Route_Standard(int x, int y)
{
	int		i, ix, iy, iMin;

	double	z, dz, dzMin;

	z		= pDTM->asDouble(x,y);
	iMin	= 0;

	for(i=1; i<=8; i++)
	{
		ix		= Get_xTo(i,x);
		iy		= Get_yTo(i,y);

		if( !pDTM->is_InGrid(ix,iy) )
		{
			iMin	= i;
			break;
		}
		else
		{
			dz		= (z - pDTM->asDouble(ix,iy)) / Get_Length(i);

			if( iMin <= 0 || dzMin < dz )
			{
				iMin	= i;
				dzMin	= dz;
			}
		}
	}

	pChannels->Set_Value(x,y, iMin );
}
//---------------------------------------------------------
bool CChannelNetwork_Distance::Set_D8(int x, int y)
{
	int	Direction;

	if( !Get_D8(x, y, Direction) )
	{
		return( false );
	}

	int	ix = Get_xTo(Direction, x), iy = Get_yTo(Direction, y);

	double	dz	= m_pDEM->asDouble(x, y) - m_pDEM->asDouble(ix, iy);
	double	dx	= Get_Length(Direction);

	m_pDistance->Set_Value(x, y, m_pDistance->asDouble(ix, iy) + sqrt(dz*dz + dx*dx));
	m_pDistVert->Set_Value(x, y, m_pDistVert->asDouble(ix, iy) + dz);
	m_pDistHorz->Set_Value(x, y, m_pDistHorz->asDouble(ix, iy) + dx);

	if( m_pTime )
	{
		double	dt	= Get_Travel_Time(x, y, Direction);

		m_pTime->Set_Value(x, y, m_pTime->asDouble(ix, iy) + dt);
	}

	if( m_pFields )
	{
		int	Crossed	= m_pFields->asDouble(ix, iy) == m_pFields->asDouble(x, y) ? 0 : 1;

		m_pPasses->Set_Value(x, y, m_pPasses->asInt(ix, iy) + Crossed);
	}

	return( true );
}
//---------------------------------------------------------
inline double CChannelNetwork_Distance::Get_Travel_Time(int x, int y, int Direction)
{
	int	ix = Get_xTo(Direction, x), iy = Get_yTo(Direction, y);

	double	v, k, R, dz, dx;

	dz	= m_pDEM->is_InGrid(ix, iy) ? m_pDEM->asDouble(x, y) - m_pDEM->asDouble(ix, iy) : 0.1;
	dx	= Get_Length(Direction);

//	k	= m_pFlow_K && !m_pFlow_K->is_NoData(x, y) ? m_pFlow_K->asDouble(x, y) : m_Flow_K;
	k	= !m_pFlow_K || (m_pFlow_K->is_NoData(x, y) && m_pFlow_K->is_NoData(ix, iy)) ? m_Flow_K
		: m_pFlow_K->is_NoData( x,  y) ? m_pFlow_K->asDouble(ix, iy)
		: m_pFlow_K->is_NoData(ix, iy) ? m_pFlow_K->asDouble( x,  y)
		: (m_pFlow_K->asDouble(x, y) + m_pFlow_K->asDouble(ix, iy)) / 2.0;

//	R	= m_pFlow_R && !m_pFlow_R->is_NoData(x, y) ? m_pFlow_R->asDouble(x, y) : m_Flow_R;
	R	= !m_pFlow_R || (m_pFlow_R->is_NoData(x, y) && m_pFlow_R->is_NoData(ix, iy)) ? m_Flow_R
		: m_pFlow_R->is_NoData( x,  y) ? m_pFlow_R->asDouble(ix, iy)
		: m_pFlow_R->is_NoData(ix, iy) ? m_pFlow_R->asDouble( x,  y)
		: (m_pFlow_R->asDouble(x, y) + m_pFlow_R->asDouble(ix, iy)) / 2.0;

	v	= k * pow(R, 2.0 / 3.0) * sqrt(dz / dx);	// [m / s], simplified Manning equation

	return( dx / (v * 3600.0) );	// return travel time in hours
}
//---------------------------------------------------------
void CChannelNetwork_Distance::Execute_D8(int x, int y)
{
	int		nPasses	= m_pFields ? m_pPasses->asInt   (x, y) : 0;
	double	Field	= m_pFields ? m_pFields->asDouble(x, y) : 0;

	double	sz	= m_pDistVert->asDouble(x, y);
	double	sx	= m_pDistHorz->asDouble(x, y);
	double	sd	= m_pDistance->asDouble(x, y);

	for(int i=0; i<8; i++)
	{
		int	ix	= Get_xFrom(i, x);
		int	iy	= Get_yFrom(i, y);

		if( m_pDEM->is_InGrid(ix, iy) && m_Dir.asInt(ix, iy) == i )
		{
			double	dz	= m_pDEM->asDouble(ix, iy) - m_pDEM->asDouble(x, y);
			double	dx	= Get_Length(i);

			if( m_pDistVert )	m_pDistVert->Set_Value(ix, iy, sz + dz);
			if( m_pDistHorz )	m_pDistHorz->Set_Value(ix, iy, sx + dx);
			if( m_pDistance )	m_pDistance->Set_Value(ix, iy, sd + sqrt(dz*dz + dx*dx));
			if( m_pTime     )	m_pTime    ->Set_Value(ix, iy, m_pTime->asDouble(x, y) + Get_Travel_Time(x, y, i));
			if( m_pSDR      )	m_pSDR     ->Set_Value(ix, iy, m_pSDR ->asDouble(x, y) + Get_Travel_Time(x, y, i));
			if( m_pFields   )	m_pPasses  ->Set_Value(ix, iy, Field != m_pFields->asDouble(ix, iy) ? nPasses + 1 : nPasses);
		}
	}

	if( m_pSDR )
	{
		m_pSDR->Set_Value(x, y, exp(-m_Flow_B * m_pSDR->asDouble(x, y)));
	}
}
Beispiel #8
0
//---------------------------------------------------------
void CFlow_by_Slope::Set_Area(int x, int y)
{
	double	Decay;

	if( Get_Decay(x, y, Decay) )
	{
		int		i, ix, iy;
		double	z, dzSum, dz[8];

		for(i=0, dzSum=0.0, z=m_pDEM->asDouble(x, y); i<8; i++)
		{
			if( m_pDEM->is_InGrid(ix = Get_xTo(i, x), iy = Get_yTo(i, y)) && (dz[i] = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
			{
				dzSum	+= (dz[i] = pow(dz[i] / Get_Length(i), 1.1));
			}
			else
			{
				dz[i]	= 0.0;
			}
		}

		if( dzSum > 0.0 )
		{
			Decay	*= m_pFlow->asDouble(x, y) / dzSum;

			for(i=0; i<8; i++)
			{
				if( dz[i] > 0.0 )
				{
					m_pFlow->Add_Value(Get_xTo(i, x), Get_yTo(i, y), Decay * dz[i]);
				}
			}
		}
	}
}
//---------------------------------------------------------
void CChannelNetwork_Distance::Initialize_D8(int x, int y)
{
	int		i, iMax, iRoute;
	double	z, dz, dzMax, dzRoute;

	for(i=0, iMax=-1, dzMax=0.0, iRoute=-1, dzRoute=0.0, z=m_pDEM->asDouble(x, y); i<8; i++)
	{
		int	ix	= Get_xTo(i, x);
		int	iy	= Get_yTo(i, y);

		if( is_InGrid(ix, iy) && (dz = (z - m_pDEM->asDouble(ix, iy)) / Get_Length(i)) > 0.0 )
		{
			if( dz > dzMax )
			{
				iMax	= i;
				dzMax	= dz;
			}

			if( m_pRoute && !m_pRoute->is_NoData(ix, iy) && dz > dzRoute )
			{
				iRoute	= i;
				dzRoute	= dz;
			}
		}
	}

	m_Dir.Set_Value(x, y, iRoute >= 0 ? iRoute : iMax);
}
//---------------------------------------------------------
void CFlow_RecursiveUp::Set_MFD(int x, int y)
{
	int		i, ix, iy;

	double	z, d, *dz, dzSum;

	z		= pDTM->asDouble(x,y);
	dz		= Flow[y][x];
	dzSum	= 0;

	for(i=0; i<8; i++)
	{
		ix	= Get_xTo(i,x);
		iy	= Get_yTo(i,y);

		if( is_InGrid(ix,iy) )
		{
			d	= z - pDTM->asDouble(ix,iy);

			if( d > 0 )
				dzSum	+= dz[i]	= pow(d / Get_Length(i), MFD_Converge);
		}
	}

	if( dzSum )
	{
		for(i=0; i<8; i++)
			if( dz[i] > 0 )
				dz[i]	/= dzSum;
	}
}
//---------------------------------------------------------
double CConvergence::Get_2x2(int x, int y, bool bGradient)
{
	int		i, n;
	double	Height, Slope, Aspect, iSlope, iAspect, d, dSum;

	for(i=0, n=0, dSum=0.0, iAspect=-M_PI_135; i<4; i++, iAspect+=M_PI_090)
	{
		if( Get_2x2_Gradient(x, y, i, Slope, Aspect, Height) )
		{
			d		= Aspect - iAspect;

			if( bGradient )
			{
				iSlope	= atan((Height - m_pDTM->asDouble(x, y)) / Get_Length(1));
				d		= acos(sin(Slope) * sin(iSlope) + cos(Slope) * cos(iSlope) * cos(d));	// Nach dem Seiten-Kosinus-Satz...
			}

			d		= fmod(d, M_PI_360);

			if( d < -M_PI_180 )
			{
				d	+= M_PI_360;
			}
			else if( d > M_PI_180 )
			{
				d	-= M_PI_360;
			}

			dSum	+= fabs(d);
			n++;
		}
	}

	return( n > 0 ? (dSum / (double)n - M_PI_090) * 100.0 / M_PI_090 : 0.0 );
}
Beispiel #12
0
//---------------------------------------------------------
double CSG_Vector::Get_Angle(const CSG_Vector &Vector) const
{
	if( Get_N() > Vector.Get_N() )
	{
		return( Vector.Get_Angle(*this) );
	}

	int		i;
	double	A, B, z, *Z	= Get_Data();

	if( (A = Get_Length()) > 0.0 && (B = Vector.Get_Length()) > 0.0 )
	{
		for(i=0, z=0.0; i<Get_N(); i++)
		{
			z	+= Vector[i] * Z[i];
		}

		for(i=Get_N(); i<Vector.Get_N(); i++)
		{
			z	+= Vector[i];
		}

		return( acos(z / (A * B)) );
	}

	return( 0.0 );
}
Beispiel #13
0
//---------------------------------------------------------
void CFlow_Distance::Set_Length_MFD(int x, int y)
{
	int		i, ix, iy;
	double	z, d, dzSum, dz[8];

	if( m_pDTM->is_InGrid(x, y) )
	{
		z		= m_pDTM->asDouble(x, y);
		dzSum	= 0.0;

		for(i=0; i<8; i++)
		{
			ix		= Get_xTo(i, x);
			iy		= Get_yTo(i, y);

			if( m_pDTM->is_InGrid(ix, iy) && (d = z - m_pDTM->asDouble(ix, iy)) > 0.0 )
			{
				dz[i]	= pow(d / Get_Length(i), m_Converge);
				dzSum	+= dz[i];
			}
			else
			{
				dz[i]	= 0.0;
			}
		}

		if( dzSum > 0.0 )
		{
			d	 = m_pLength->asDouble(x, y);

			for(i=0; i<8; i++)
			{
				if( dz[i] > 0.0 )
				{
					ix		= Get_xTo(i, x);
					iy		= Get_yTo(i, y);

					dz[i]	/= dzSum;

					m_pLength->Add_Value(ix, iy, dz[i] * (d + Get_Length(i)));
					m_pWeight->Add_Value(ix, iy, dz[i]);
				}
			}
		}
	}
}
//---------------------------------------------------------
bool CChannelNetwork_Distance::Get_MFD(int x, int y, CSG_Vector &Flow)
{
	const double	MFD_Convergence	= 1.1;

	double	dz, Sum = 0.0, z = m_pDEM->asDouble(x, y);

	if( m_pRoute )
	{
		for(int i=0; i<8; i++)
		{
			int	ix = Get_xTo(i, x), iy = Get_yTo(i, y);

			if( m_pDEM->is_InGrid(ix, iy) && !m_pRoute->is_NoData(ix, iy) && (dz = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
			{
				Sum	+= (Flow[i]	= pow(dz / Get_Length(i), MFD_Convergence));
			}
		}

		if( Sum > 0.0 )
		{
			Flow	*= 1. / Sum;

			return( true );
		}
	}

	for(int i=0; i<8; i++)
	{
		int	ix = Get_xTo(i, x), iy = Get_yTo(i, y);

		if( m_pDEM->is_InGrid(ix, iy) && !m_pDistance->is_NoData(ix, iy) && (dz = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
		{
			Sum	+= (Flow[i]	= pow(dz / Get_Length(i), MFD_Convergence));
		}
	}

	if( Sum > 0.0 )
	{
		Flow	*= 1. / Sum;

		return( true );
	}

	return( false );
}
//---------------------------------------------------------
void CChannelNetwork_Distance::Execute_MFD(int x, int y)
{
	double	df	= m_Flow[8].asDouble(x, y);

	if( df > 0.0 )
	{
		if( m_pDistance )	m_pDistance->Mul_Value(x, y, 1.0 / df);
		if( m_pDistVert )	m_pDistVert->Mul_Value(x, y, 1.0 / df);
		if( m_pDistHorz )	m_pDistHorz->Mul_Value(x, y, 1.0 / df);
		if( m_pTime     )	m_pTime    ->Mul_Value(x, y, 1.0 / df);
		if( m_pSDR      )	m_pSDR     ->Mul_Value(x, y, 1.0 / df);
	}

	double	sz	= m_pDistVert->asDouble(x, y);
	double	sx	= m_pDistHorz->asDouble(x, y);
	double	sd	= m_pDistance->asDouble(x, y);

	for(int i=0; i<8; i++)
	{
		int	ix	= Get_xTo(i, x);
		int	iy	= Get_yTo(i, y);

		if( m_pDEM->is_InGrid(ix, iy) && (df = m_Flow[(i + 4) % 8].asDouble(ix, iy)) > 0.0 )
		{
			double	dz	= m_pDEM->asDouble(ix, iy) - m_pDEM->asDouble(x, y);
			double	dx	= Get_Length(i);
			double	dt	= m_pTime || m_pSDR ? Get_Travel_Time(x, y, i) : 1.0;

			if( m_pDistance->is_NoData(ix, iy) )
			{
				m_Flow[8].Set_Value(ix, iy, df);

				if( m_pDistVert )	m_pDistVert->Set_Value(ix, iy, df * (sz + dz));
				if( m_pDistHorz )	m_pDistHorz->Set_Value(ix, iy, df * (sx + dx));
				if( m_pDistance )	m_pDistance->Set_Value(ix, iy, df * (sd + sqrt(dz*dz + dx*dx)));
				if( m_pTime     )	m_pTime    ->Set_Value(ix, iy, df * (m_pTime->asDouble(x, y) + dt));
				if( m_pSDR      )	m_pSDR     ->Set_Value(ix, iy, df * (m_pSDR ->asDouble(x, y) + dt));
			}
			else
			{
				m_Flow[8].Add_Value(ix, iy, df);

				if( m_pDistVert )	m_pDistVert->Add_Value(ix, iy, df * (sz + dz));
				if( m_pDistHorz )	m_pDistHorz->Add_Value(ix, iy, df * (sx + dx));
				if( m_pDistance )	m_pDistance->Add_Value(ix, iy, df * (sd + sqrt(dz*dz + dx*dx)));
				if( m_pTime     )	m_pTime    ->Add_Value(ix, iy, df * (m_pTime->asDouble(x, y) + dt));
				if( m_pSDR      )	m_pSDR     ->Add_Value(ix, iy, df * (m_pSDR ->asDouble(x, y) + dt));
			}
		}
	}

	if( m_pSDR )
	{
		m_pSDR->Set_Value(x, y, exp(-m_Flow_B * m_pSDR->asDouble(x, y)));
	}
}
//---------------------------------------------------------
inline double CChannelNetwork_Distance::Get_Travel_Time(int x, int y, int i)
{
	double	dz	= m_pDEM->asDouble(Get_xTo(i, x), Get_yTo(i, y)) - m_pDEM->asDouble(x, y);
	double	dx	= Get_Length(i);
	double	k	= m_pFlow_K && !m_pFlow_K->is_NoData(x, y) ? m_pFlow_K->asDouble(x, y) : m_Flow_K;
	double	R	= m_pFlow_R && !m_pFlow_R->is_NoData(x, y) ? m_pFlow_R->asDouble(x, y) : m_Flow_R;

	double	v	= k * pow(R, 2.0 / 3.0) * sqrt(dz / dx);	// [m / s], simplified Manning equation

	return( dx / (v * 3600.0) );	// return travel time in hours
}
//---------------------------------------------------------
double CSG_Shape_Line::Get_Length(void)
{
	int		iPart;
	double	Length;

	for(iPart=0, Length=0.0; iPart<m_nParts; iPart++)
	{
		Length	+= Get_Length(iPart);
	}

	return( Length );
}
Beispiel #18
0
//---------------------------------------------------------
bool CKinWav_D8::Initialize(double Roughness)
{
	m_Flow_Last	.Create(*Get_System(), SG_DATATYPE_Float);
	m_Alpha		.Create(*Get_System(), SG_DATATYPE_Float);
	m_Direction	.Create(*Get_System(), SG_DATATYPE_Char);
	m_Direction	.Set_NoData_Value(-1);

	m_pFlow->Assign(0.0);
	DataObject_Set_Colors(m_pFlow, 100, SG_COLORS_WHITE_BLUE);
	DataObject_Update(m_pFlow, 0.0, 100.0, SG_UI_DATAOBJECT_SHOW);

	//-----------------------------------------------------
	for(int y=0; y<Get_NY() && Set_Progress(y); y++)
	{
		for(int x=0; x<Get_NX(); x++)
		{
			if( !m_pDEM->is_NoData(x, y) )
			{
				int		i, ix, iy, iMax;
				double	z, d, dMax;

				for(i=0, iMax=-1, dMax=0.0, z=m_pDEM->asDouble(x, y); i<8; i++)
				{
					ix	= Get_xTo(i, x);
					iy	= Get_yTo(i, y);

					if( is_InGrid(ix, iy) && (d = (z - m_pDEM->asDouble(ix, iy)) / Get_Length(i)) > dMax )
					{
						dMax	= d;
						iMax	= i;
					}
				}

				if( iMax < 0 )
				{
					m_Direction	 .Set_NoData(x, y);
				}
				else
				{
					m_Direction	.Set_Value(x, y, iMax);

					m_Alpha		.Set_Value(x, y, pow(Roughness / sqrt(dMax), Beta_0));

					if( m_Alpha.asDouble(x, y) > 10 )
						m_Alpha.Set_Value(x, y, 10);
				}
			}
		}
	}

	return( true );
}
Beispiel #19
0
//---------------------------------------------------------
bool CSlopeLength::On_Execute(void)
{
	int		x, y;

	//-----------------------------------------------------
	m_pDEM		= Parameters("DEM"   )->asGrid();
	m_pLength	= Parameters("LENGTH")->asGrid();

	if( !m_pDEM->Set_Index() )
	{
		Error_Set(_TL("index creation failed"));

		return( false );
	}

	//-----------------------------------------------------
	m_Slope.Create(*Get_System());

	for(y=0; y<Get_NY() && Set_Progress(y); y++)
	{
		#pragma omp parallel for private(x)
		for(x=0; x<Get_NX(); x++)
		{
			double	Slope, Aspect;

			if( m_pDEM->Get_Gradient(x, y, Slope, Aspect) )
			{
				m_Slope   .Set_Value(x, y, Slope);
				m_pLength->Set_Value(x, y, 0.0);
			}
			else
			{
				m_Slope   .Set_NoData(x, y);
				m_pLength->Set_NoData(x, y);
			}
		}
	}

	//-----------------------------------------------------
	for(sLong n=0; n<Get_NCells() && Set_Progress_NCells(n); n++)
	{
		if( m_pDEM->Get_Sorted(n, x, y) )
		{
			Get_Length(x, y);
		}
	}

	//-----------------------------------------------------
	m_Slope.Destroy();

	return( true );
}
//---------------------------------------------------------
void CFlow_Parallel::Set_MFD(int x, int y)
{
	int		i, ix, iy;
	double	z, d, dzSum, dz[8];

	//-----------------------------------------------------
	for(i=0, dzSum=0.0, z=m_pDTM->asDouble(x, y); i<8; i++)
	{
		ix	= Get_xTo(i, x);
		iy	= Get_yTo(i, y);

		if( m_pDTM->is_InGrid(ix, iy) )
		{
			d	= z - m_pDTM->asDouble(ix, iy);
		}
		else
		{
			ix	= Get_xTo(i + 4, x);
			iy	= Get_yTo(i + 4, y);

			if( m_pDTM->is_InGrid(ix, iy) )
			{
				d	= m_pDTM->asDouble(ix, iy) - z;
			}
			else
			{
				d	= 0.0;
			}
		}

		if( d > 0.0 )
		{
			dzSum	+= (dz[i] = pow(d / Get_Length(i), m_Converge));
		}
		else
		{
			dz[i]	= 0.0;
		}
	}

	//-----------------------------------------------------
	if( dzSum > 0.0 )
	{
		for(i=0; i<8; i++)
		{
			if( dz[i] > 0.0 )
			{
				Add_Fraction(x, y, i, dz[i] / dzSum);
			}
		}
	}
}
//---------------------------------------------------------
bool CChannelNetwork_Distance::Set_MFD(int x, int y)
{
	CSG_Vector	Flow(8);

	if( !Get_MFD(x, y, Flow) )
	{
		return( false );
	}

	double	Distance = 0.0, DistVert = 0.0, DistHorz = 0.0, Time = 0.0, SDR = 0.0;

	double	z = m_pDEM->asDouble(x, y);

	for(int i=0; i<8; i++)
	{
		if( Flow[i] > 0.0 )
		{
			int	ix = Get_xTo(i, x), iy = Get_yTo(i, y);

			double	dz	= z - m_pDEM->asDouble(ix, iy);
			double	dx	= Get_Length(i);

			Distance += Flow[i] * (m_pDistance->asDouble(ix, iy) + sqrt(dz*dz + dx*dx));
			DistVert += Flow[i] * (m_pDistVert->asDouble(ix, iy) + dz);
			DistHorz += Flow[i] * (m_pDistHorz->asDouble(ix, iy) + dx);

			if( m_pTime )
			{
				double	dt	= Get_Travel_Time(x, y, i);

				Time += Flow[i] * (m_pTime->asDouble(ix, iy) + dt);
			}
		}
	}

	if( Distance > 0.0 )
	{
		m_pDistance->Set_Value(x, y, Distance);
		m_pDistVert->Set_Value(x, y, DistVert);
		m_pDistHorz->Set_Value(x, y, DistHorz);

		if( m_pTime )
		{
			m_pTime->Set_Value(x, y, Time);
		}
	}

	return( true );
}
Beispiel #22
0
//---------------------------------------------------------
void CConvergence::Do_Gradient(void)
{
    int		x, y, i, ix, iy, n;
    double	z, Slope, Aspect, iSlope, iAspect, d, dSum;

    for(y=0; y<Get_NY() && Set_Progress(y); y++)
    {
        for(x=0; x<Get_NX(); x++)
        {
            if( pDTM->is_InGrid(x, y) )
            {
                z	= pDTM->asDouble(x, y);

                for(i=0, n=0, dSum=0.0, iAspect=-M_PI_180; i<8; i++, iAspect+=M_PI_045)
                {
                    ix	= Get_xTo(i, x);
                    iy	= Get_yTo(i, y);

                    if( pDTM->is_InGrid(ix, iy) && pDTM->Get_Gradient(ix, iy, Slope, Aspect) && Aspect >= 0.0 )
                    {
                        iSlope	= atan((pDTM->asDouble(ix, iy) - z) / Get_Length(i));

                        // Nach dem Seiten-Kosinus-Satz...
                        d		= acos(sin(Slope) * sin(iSlope) + cos(Slope) * cos(iSlope) * cos(iAspect - Aspect));

                        //---------------------------------
                        d		= fmod(d, M_PI_360);

                        if( d < -M_PI_180 )
                        {
                            d	+= M_PI_360;
                        }
                        else if( d > M_PI_180 )
                        {
                            d	-= M_PI_360;
                        }

                        //---------------------------------
                        dSum	+= fabs(d);
                        n++;
                    }
                }

                pConvergence->Set_Value(x, y, n > 0 ? (dSum / (double)n - M_PI_090) * 100.0 / M_PI_090 : 0.0);
            }
        }
    }
}
Beispiel #23
0
//---------------------------------------------------------
bool CSG_Vector::Set_Unity(void)
{
	double	Length;

	if( (Length = Get_Length()) > 0.0 )
	{
		for(int i=0; i<Get_N(); i++)
		{
			Get_Data()[i]	/= Length;
		}

		return( true );
	}

	return( false );
}
Beispiel #24
0
//---------------------------------------------------------
void CFlow_Distance::Set_Length_D8(int x, int y)
{
	int		i, ix, iy;

	if( m_pDTM->is_InGrid(x, y) && (i = m_pDTM->Get_Gradient_NeighborDir(x, y, true)) >= 0 )
	{
		ix	= Get_xTo(i, x);
		iy	= Get_yTo(i, y);

		if( m_pDTM->is_InGrid(ix, iy) )
		{
			m_pLength->Add_Value(ix, iy, m_pLength->asDouble(x, y) + Get_Length(i));
			m_pWeight->Add_Value(ix, iy, 1.0);
		}
	}
}
Beispiel #25
0
//---------------------------------------------------------
void CCellBalance::Set_MFD(int x, int y, double Weight)
{
	const double	MFD_Converge	= 1.1;

	int		i, ix, iy;
	double	z, d, dzSum, dz[8];

	z		= m_pDEM->asDouble(x, y);
	dzSum	= 0.0;

	for(i=0; i<8; i++)
	{
		ix		= Get_xTo(i, x);
		iy		= Get_yTo(i, y);

		if( m_pDEM->is_InGrid(ix, iy) && (d = z - m_pDEM->asDouble(ix, iy)) > 0.0 )
		{
			dz[i]	= pow(d / Get_Length(i), MFD_Converge);
			dzSum	+= dz[i];
		}
		else
		{
			dz[i]	= 0.0;
		}
	}

	if( dzSum > 0.0 )
	{
		d		= Weight / dzSum;

		for(i=0; i<8; i++)
		{
			if( dz[i] > 0.0 )
			{
				ix		= Get_xTo(i, x);
				iy		= Get_yTo(i, y);

				m_pBalance->Add_Value(ix, iy, dz[i] * d);
			}
		}
	}
}
Beispiel #26
0
//---------------------------------------------------------
void CFlow::Add_Fraction(int x, int y, int Direction, double Fraction)
{
	int		ix, iy;

	if( is_InGrid(x, y) )
	{
		ix	= Get_xTo(Direction, x);
		iy	= Get_yTo(Direction, y);

		if( is_InGrid(ix, iy) )
		{
			if( pCatch )
			{
				pCatch			->Add_Value(ix, iy, Fraction * pCatch			->asDouble(x, y));
			}

			if( pCatch_Height )
			{
				pCatch_Height	->Add_Value(ix, iy, Fraction * pCatch_Height	->asDouble(x, y));
			}

			if( pCatch_Slope )
			{
				pCatch_Slope	->Add_Value(ix, iy, Fraction * pCatch_Slope		->asDouble(x, y));
			}

			if( pFlowPath )
			{
				pFlowPath		->Add_Value(ix, iy, Fraction * (pFlowPath		->asDouble(x, y) + Get_Length(Direction)));
			}

			if( pCatch_Aspect && pCatch_AspectY )
			{
				pCatch_Aspect	->Add_Value(ix, iy, Fraction * pCatch_Aspect	->asDouble(x, y));
				pCatch_AspectY	->Add_Value(ix, iy, Fraction * pCatch_AspectY	->asDouble(x, y));
			}
		}
	}
}
//---------------------------------------------------------
double CConvergence::Get_9x9(int x, int y, bool bGradient)
{
	int		i, ix, iy, n;
	double	Slope, Aspect, iSlope, iAspect, d, dSum;

	for(i=0, n=0, dSum=0.0, iAspect=-M_PI_180; i<8; i++, iAspect+=M_PI_045)
	{
		ix	= Get_xTo(i, x);
		iy	= Get_yTo(i, y);

		if( m_pDTM->is_InGrid(ix, iy) && m_pDTM->Get_Gradient(ix, iy, Slope, Aspect) && Aspect >= 0.0 )
		{
			d		= Aspect - iAspect;

			if( bGradient )
			{
				iSlope	= atan((m_pDTM->asDouble(ix, iy) - m_pDTM->asDouble(x, y)) / Get_Length(i));
				d		= acos(sin(Slope) * sin(iSlope) + cos(Slope) * cos(iSlope) * cos(d));	// Nach dem Seiten-Kosinus-Satz...
			}

			d		= fmod(d, M_PI_360);

			if( d < -M_PI_180 )
			{
				d	+= M_PI_360;
			}
			else if( d > M_PI_180 )
			{
				d	-= M_PI_360;
			}

			dSum	+= fabs(d);
			n++;
		}
	}

	return( n > 0 ? (dSum / (double)n - M_PI_090) * 100.0 / M_PI_090 : 0.0 );
}
Beispiel #28
0
//---------------------------------------------------------
bool CDiffuse_Pollution_Risk::Get_Flow_Proportions(int x, int y, double Proportion[8])
{
	if( m_pDEM->is_InGrid(x, y) )
	{
		double Sum = 0.0;

		for(int i=0; i<8; i++)
		{
			int	ix	= Get_xTo(i, x);
			int	iy	= Get_yTo(i, y);

			if( m_pDEM->is_InGrid(ix, iy) && m_pDEM->asDouble(x, y) > m_pDEM->asDouble(ix, iy) )
			{
				Sum	+= (Proportion[i]	= ((m_pDEM->asDouble(x, y) - m_pDEM->asDouble(ix, iy)) / Get_Length(i)));
			}
			else
			{
				Proportion[i]	= 0.0;
			}
		}

		if( Sum > 0.0 )
		{
			for(int i=0; i<8; i++)
			{
				if( Proportion[i] > 0.0 )
				{
					Proportion[i]	/= Sum;
				}
			}

			return( true );
		}
	}

	return( false );
}
Beispiel #29
0
//---------------------------------------------------------
void CChannelNetwork::Set_Vector(int x, int y, int ID)
{
	bool	bContinue;

	int		i, ix, iy, j, Order;

	double	xMin, yMin, Length;

	CSG_Shape	*pShape;

	//-----------------------------------------------------
	if( (Order = pChannels->asInt(x,y)) > 0 )
	{
		bContinue	= true;

		for(i=0, j=4; i<8 && bContinue; i++, j=(j+1)%8)
		{
			ix	= Get_xTo(i,x);
			iy	= Get_yTo(i,y);

			if(	pDTM->is_InGrid(ix,iy)
			&&	pChannels->asInt(ix,iy) == Order
			&&	pChannelRoute->asChar(ix,iy) && j == pChannelRoute->asChar(ix,iy) % 8 )
			{
				bContinue	= false;
			}
		}

		//-------------------------------------------------
		if( bContinue )	// Startpunkt gefunden...
		{
			xMin	= pDTM->Get_XMin(),
			yMin	= pDTM->Get_YMin();
			ID		= 1;

			pShape	= pShapes->Add_Shape();

			do
			{
				bContinue	= false;
				Length		= 0;

				Lock_Set(x,y);

				pShape->Add_Point(xMin + x * Get_Cellsize(), yMin + y * Get_Cellsize());

				i	= pChannelRoute->asChar(x,y);

				if( i > 0 )
				{
					ix		= Get_xTo(i,x);
					iy		= Get_yTo(i,y);

					Length	+= Get_Length(i);

					if( pDTM->is_InGrid(ix,iy) )
					{
						if(	!is_Locked(ix,iy)
						&&	(	pChannels->asInt(ix,iy) == Order
							||	pChannels->asInt(ix,iy) < 0) )
						{
							x			= ix;
							y			= iy;
							bContinue	= true;
						}
						else
						{
							pShape->Add_Point(xMin + ix * Get_Cellsize(), yMin + iy * Get_Cellsize());
						}
					}
				}
			}
			while( bContinue );

			pShape->Set_Value(0, ID );
			pShape->Set_Value(1, Order );
			pShape->Set_Value(2, Length );
		}
	}
}
Beispiel #30
0
//---------------------------------------------------------
void CChannelNetwork::Set_Channel_Route(int x, int y)
{
	const int	BUFFER_GROWSIZE	= 256;

	int		xStart, yStart, i, ix, iy, goDir, m, n, nDiv;

	double	z, dz, dzMin, Length;

	//-----------------------------------------------------
	if( pStart->asChar(x,y) && !pChannelRoute->asChar(x,y) )
	{
		Lock_Create();

		n		= 0;
		nDiv	= 0;
		Length	= 0;
		xStart	= x;
		yStart	= y;

		do
		{
			//---------------------------------------------
			// 1. Divergence ?!...

			if( pConvergence )
			{
				if( pConvergence->asDouble(x,y) > -1.0 )
				{
					nDiv++;
				}
				else
				{
					nDiv	= 0;
				}
			}

			if( pConvergence && nDiv > maxDivCells )
			{
				goDir	= -1;
			}
			else
			{
				//-----------------------------------------
				// 2. Is there any channel around ?!...

				goDir	= 0;
				z		= pDTM->asDouble(x,y);

				for(i=1; i<=8; i++)
				{
					ix		= Get_xTo(i,x);
					iy		= Get_yTo(i,y);

					if( pDTM->is_InGrid(ix,iy) && !is_Locked(ix,iy) && pChannelRoute->asChar(ix,iy) )
					{
						dz		= (z - pDTM->asDouble(ix,iy)) / Get_Length(i);

						if( goDir <= 0 || dzMin < dz )
						{
							goDir	= i;
							dzMin	= dz;
						}
					}
				}

				if( goDir <= 0 )	// ...if not then go as usual...
				{
					goDir	= pChannels->asInt(x,y);
				}


				//-----------------------------------------
				// 3. Go to Drainage Direction !...

				if(	goDir > 0 )
				{
					Lock_Set(x,y);

					x		= Get_xTo(goDir,x);
					y		= Get_yTo(goDir,y);

					Length	+= Get_UnitLength(goDir);

					if( n >= Direction_Buffer )
					{
						Direction_Buffer	+= BUFFER_GROWSIZE;
						Direction			= (int *)SG_Realloc(Direction, Direction_Buffer * sizeof(int));
					}

					Direction[n++]	= goDir;
				}
			}
		}
		while( goDir > 0 && pDTM->is_InGrid(x,y) && !is_Locked(x,y) && !pChannelRoute->asChar(x,y) );


		//-------------------------------------------------
		if( Length >= minLength )
		{
			x	= xStart;
			y	= yStart;

			if( goDir < 0 )
			{
				n	-= nDiv;
			}

			for(m=0; m<n; m++)
			{
				goDir	= Direction[m];

				pChannelRoute->Set_Value(x,y,goDir);

				for(i=0; i<8; i++)	// Don't start new channels beside existing ones...
				{
					ix		= Get_xTo(i,x);
					iy		= Get_yTo(i,y);

					if( pDTM->is_InGrid(ix,iy) )
					{
						pStart->Set_Value(ix,iy,0);
					}
				}

				x	= Get_xTo(goDir,x);
				y	= Get_yTo(goDir,y);
			}
		}
	}
}