PandaGIS的SkyLine开发教程(4)__根据管线图层在三维场景中生成三维管线
SkyLine场景中的
三维管线同样可以根据管线矢量
图层自动生成。具体思路无非是获得矢量图层的
空间信息和相关属性,
然后在三维场景中进行渲染。下面提供相关样例代码,以供参考。
//生成3D管道
private void btnBulidPipe_Click(object sender, EventArgs e)
{
MapLayer lyrTemp = new MapLayer();
lyrTemp = (MapLayer)axMap1.Layers.Item(0);
TableDesc TabDesc = new TableDesc();
TabDesc = lyrTemp.Records.TableDesc;
Recordset recs = lyrTemp.Records;
Line lineTemp;
Points ptsTemp;
ESRI.MapObjects2.Core.Point ptTemp, ptBeg, ptEnd;
double douPipeGJ=0.0;//管径
string strPipeCZ=null;;//材质
//管线 数据的属性表中已有字段
//规格 材质 长度 上井管标高 下井管标高 标高位置 岔管类型
//需要传入数据
//起点坐标(x,y,h) 终点坐标(z,y,h) 管径 材质 纹理 名称 其它注释信息
ptBeg = new ESRI.MapObjects2.Core.Point();
ptEnd = new ESRI.MapObjects2.Core.Point();
int iGroupID = clsObjTree.IsExistGruop(DateTime.Now.Hour.ToString() + DateTime.Now.Minute.ToString() + DateTime.Now.Second.ToString(), "");
for (int i = 0; i < recs.Count; i++)
{
if (recs.Fields.Item("Shape").Value != System.DBNull.Value)
{
lineTemp = (Line)recs.Fields.Item("Shape").Value;
}
else
{
return;
}
if (recs.Fields.Item("上井管标高").Value != System.DBNull.Value)
{
ptBeg.Z = -(double)recs.Fields.Item("上井管标高").Value;
}
else
{
MessageBox.Show("上井管标高未赋值");
}
if (recs.Fields.Item("下井管标高").Value != System.DBNull.Value)
{
ptEnd.Z = -(double)recs.Fields.Item("下井管标高").Value;
}
else
{
MessageBox.Show("下井管标高未赋值");
}
if (recs.Fields.Item("材质").Value != System.DBNull.Value)
{
strPipeCZ = (string)recs.Fields.Item("材质").Value;
}
else
{
MessageBox.Show("材质字段未赋值");
}
if (lineTemp.Parts.Count > 1) MessageBox.Show("此线有"+lineTemp.Parts.Count.ToString()+"个部分。");
for (int j = 0; j < lineTemp.Parts.Count;j++ )
{
ptsTemp = (Points)lineTemp.Parts.Item(j);
if (ptsTemp.Count > 2) MessageBox.Show("此线有"+ptsTemp.Count.ToString()+"个端点。");
ptTemp = (ESRI.MapObjects2.Core.Point)ptsTemp.Item(0);
ptBeg.X = ptTemp.X;
ptBeg.Y = ptTemp.Y;
ptTemp = (ESRI.MapObjects2.Core.Point)ptsTemp.Item(1);
ptEnd.X = ptTemp.X;
ptEnd.Y = ptTemp.Y;
CreatePipe(ptBeg.X, ptBeg.Y, ptBeg.Z, ptEnd.X, ptEnd.Y, ptEnd.Z, strPipeCZ, douPipeGJ, i, iGroupID);
}
recs.MoveNext();
}
}
/// <summary>
/// 生成三维管线
/// </summary>
/// <param name="x1">起点X值</param>
/// <param name="y1">起点Y值</param>
/// <param name="z1">起点Z值</param>
/// <param name="x2">终点X值</param>
/// <param name="y2">终点Y值</param>
/// <param name="z2">终点Z值</param>
/// <param name="strPipeCZ">管线材质</param>
/// <param name="douPipeGJ">管线管径</param>
private void CreatePipe(double x1, double y1, double z1, double x2, double y2, double z2, string strPipeCZ, double douPipeGJ,int Fid,int iGroupID)
{
//关于传入参数的说明
//管线的边线的颜色和透明度 填充颜色和透明度(或者采用纹理) 管径为圆柱半径
//throw new Exception("The method or operation is not implemented.");
double douPipeLength = clsTE.CoordSys.GetDistanceEx(x1, y1, z1, x2, y2, z2); //管线长度
int iNumOfSegments = 20; //圆柱构成面数
int iLineColor=33023;
double douFillOpacity = 0.7;
int iFillColor = 255;
// string strDescription = "3D管道";
douPipeGJ =0.6;
object oYaw, oPitch;
double douYaw;
TerraExplorerX.ITerrain3DRegBase5 te3DEegBase5;
if (z1<z2)
{
clsTE.CoordSys.GetAimingAngles(x1, y1, z1, x2, y2, z2, out oYaw, out oPitch);
if ((double)oYaw < 180)
{
douYaw = (double)oYaw + 180;
}
else
{
douYaw = (double)oYaw - 180;
}
te3DEegBase5 = (TerraExplorerX.ITerrain3DRegBase5)clsTE.ObjectManager.CreateCylinder(x1, y1, z1, douPipeGJ, douPipeLength, iNumOfSegments, iLineColor, douFillOpacity, iFillColor, HeightStyleCode.HSC_TERRAIN_ABSOLUTE, iGroupID, Fid.ToString());
te3DEegBase5.SetPosition(x1, y1, z1, douYaw, 90 - (double)oPitch, 0.0, 7);
}
else
{
clsTE.CoordSys.GetAimingAngles(x2, y2, z2, x1, y1, z1, out oYaw, out oPitch);
if ((double)oYaw < 180)
{
douYaw = (double)oYaw + 180;
}
else
{
douYaw = (double)oYaw - 180;
}
te3DEegBase5 = (TerraExplorerX.ITerrain3DRegBase5)clsTE.ObjectManager.CreateCylinder(x2, y2, z2, douPipeGJ, douPipeLength, iNumOfSegments, iLineColor, douFillOpacity, iFillColor, HeightStyleCode.HSC_TERRAIN_ABSOLUTE, iGroupID, Fid.ToString());
te3DEegBase5.SetPosition(x2, y2, z2, douYaw, 90 - (double)oPitch, 0.0, 7);
}
te3DEegBase5.ToolTipText = Fid.ToString();
}
然后在三维场景中进行渲染。下面提供相关样例代码,以供参考。
//生成3D管道
private void btnBulidPipe_Click(object sender, EventArgs e)
{
MapLayer lyrTemp = new MapLayer();
lyrTemp = (MapLayer)axMap1.Layers.Item(0);
TableDesc TabDesc = new TableDesc();
TabDesc = lyrTemp.Records.TableDesc;
Recordset recs = lyrTemp.Records;
Line lineTemp;
Points ptsTemp;
ESRI.MapObjects2.Core.Point ptTemp, ptBeg, ptEnd;
double douPipeGJ=0.0;//管径
string strPipeCZ=null;;//材质
//管线 数据的属性表中已有字段
//规格 材质 长度 上井管标高 下井管标高 标高位置 岔管类型
//需要传入数据
//起点坐标(x,y,h) 终点坐标(z,y,h) 管径 材质 纹理 名称 其它注释信息
ptBeg = new ESRI.MapObjects2.Core.Point();
ptEnd = new ESRI.MapObjects2.Core.Point();
int iGroupID = clsObjTree.IsExistGruop(DateTime.Now.Hour.ToString() + DateTime.Now.Minute.ToString() + DateTime.Now.Second.ToString(), "");
for (int i = 0; i < recs.Count; i++)
{
if (recs.Fields.Item("Shape").Value != System.DBNull.Value)
{
lineTemp = (Line)recs.Fields.Item("Shape").Value;
}
else
{
return;
}
if (recs.Fields.Item("上井管标高").Value != System.DBNull.Value)
{
ptBeg.Z = -(double)recs.Fields.Item("上井管标高").Value;
}
else
{
MessageBox.Show("上井管标高未赋值");
}
if (recs.Fields.Item("下井管标高").Value != System.DBNull.Value)
{
ptEnd.Z = -(double)recs.Fields.Item("下井管标高").Value;
}
else
{
MessageBox.Show("下井管标高未赋值");
}
if (recs.Fields.Item("材质").Value != System.DBNull.Value)
{
strPipeCZ = (string)recs.Fields.Item("材质").Value;
}
else
{
MessageBox.Show("材质字段未赋值");
}
if (lineTemp.Parts.Count > 1) MessageBox.Show("此线有"+lineTemp.Parts.Count.ToString()+"个部分。");
for (int j = 0; j < lineTemp.Parts.Count;j++ )
{
ptsTemp = (Points)lineTemp.Parts.Item(j);
if (ptsTemp.Count > 2) MessageBox.Show("此线有"+ptsTemp.Count.ToString()+"个端点。");
ptTemp = (ESRI.MapObjects2.Core.Point)ptsTemp.Item(0);
ptBeg.X = ptTemp.X;
ptBeg.Y = ptTemp.Y;
ptTemp = (ESRI.MapObjects2.Core.Point)ptsTemp.Item(1);
ptEnd.X = ptTemp.X;
ptEnd.Y = ptTemp.Y;
CreatePipe(ptBeg.X, ptBeg.Y, ptBeg.Z, ptEnd.X, ptEnd.Y, ptEnd.Z, strPipeCZ, douPipeGJ, i, iGroupID);
}
recs.MoveNext();
}
}
/// <summary>
/// 生成三维管线
/// </summary>
/// <param name="x1">起点X值</param>
/// <param name="y1">起点Y值</param>
/// <param name="z1">起点Z值</param>
/// <param name="x2">终点X值</param>
/// <param name="y2">终点Y值</param>
/// <param name="z2">终点Z值</param>
/// <param name="strPipeCZ">管线材质</param>
/// <param name="douPipeGJ">管线管径</param>
private void CreatePipe(double x1, double y1, double z1, double x2, double y2, double z2, string strPipeCZ, double douPipeGJ,int Fid,int iGroupID)
{
//关于传入参数的说明
//管线的边线的颜色和透明度 填充颜色和透明度(或者采用纹理) 管径为圆柱半径
//throw new Exception("The method or operation is not implemented.");
double douPipeLength = clsTE.CoordSys.GetDistanceEx(x1, y1, z1, x2, y2, z2); //管线长度
int iNumOfSegments = 20; //圆柱构成面数
int iLineColor=33023;
double douFillOpacity = 0.7;
int iFillColor = 255;
// string strDescription = "3D管道";
douPipeGJ =0.6;
object oYaw, oPitch;
double douYaw;
TerraExplorerX.ITerrain3DRegBase5 te3DEegBase5;
if (z1<z2)
{
clsTE.CoordSys.GetAimingAngles(x1, y1, z1, x2, y2, z2, out oYaw, out oPitch);
if ((double)oYaw < 180)
{
douYaw = (double)oYaw + 180;
}
else
{
douYaw = (double)oYaw - 180;
}
te3DEegBase5 = (TerraExplorerX.ITerrain3DRegBase5)clsTE.ObjectManager.CreateCylinder(x1, y1, z1, douPipeGJ, douPipeLength, iNumOfSegments, iLineColor, douFillOpacity, iFillColor, HeightStyleCode.HSC_TERRAIN_ABSOLUTE, iGroupID, Fid.ToString());
te3DEegBase5.SetPosition(x1, y1, z1, douYaw, 90 - (double)oPitch, 0.0, 7);
}
else
{
clsTE.CoordSys.GetAimingAngles(x2, y2, z2, x1, y1, z1, out oYaw, out oPitch);
if ((double)oYaw < 180)
{
douYaw = (double)oYaw + 180;
}
else
{
douYaw = (double)oYaw - 180;
}
te3DEegBase5 = (TerraExplorerX.ITerrain3DRegBase5)clsTE.ObjectManager.CreateCylinder(x2, y2, z2, douPipeGJ, douPipeLength, iNumOfSegments, iLineColor, douFillOpacity, iFillColor, HeightStyleCode.HSC_TERRAIN_ABSOLUTE, iGroupID, Fid.ToString());
te3DEegBase5.SetPosition(x2, y2, z2, douYaw, 90 - (double)oPitch, 0.0, 7);
}
te3DEegBase5.ToolTipText = Fid.ToString();
}