Newer
Older
GHFX_REFACTOR / LineBuilder.cs
wxn on 2 Nov 2016 6 KB 提交
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using GeoScene.Globe;
using GeoScene.Engine;
using GeoScene.Data;
using System.Collections;
using System.Drawing;
namespace Cyberpipe
{
    public class LineBuilder:ModelBuilder
    {
        public LineBuilder(GSODataSource ds):base(ds)
        { 
        
        }

        public override bool validate(GSOLayer layer) {
            return true;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="updateMode">追加或修改</param>
        /// <param name="buildMode">高程入库或埋深入库</param>
        /// <param name="param"></param>
        public override bool doBuild(EnumUpdateMode updateMode,
                                     EnumBuildMode buildMode,
                                     BaseParam param) {
            
            LineParam lineParam = param as LineParam;
            GSOFeatureDataset newFeatureSet = ds.GetDatasetByName(lineParam.layerName) as GSOFeatureDataset;
            if(newFeatureSet==null){
                 newFeatureSet = base.CreateDBFeatureDataset(this.layer,lineParam.layerName);
            }
            newFeatureSet.Open();
            GSOFeatures features = this.layer.GetAllFeatures(true);
                for(int i=0;i<features.Length;i++){
                   GSOFeature f = features[i];
                   GSOGeoPolyline3D lineeee = f.Geometry as GSOGeoPolyline3D;
                   if (lineeee == null|| lineeee.GetSpaceLength(true, 6378137) == 0){
                            continue; //TODO LIST:判断是否会出现部署数据无法入库情况,Log2Net
                   }
               
               GSOFeature newFeature = newFeatureSet.CreateFeature();
               
               double radius = getRadius(lineParam,f);
               newFeature.Geometry = this.updateGemotry(f,lineParam,radius,buildMode) ; // f.Geometry;
               newFeature.Geometry.Style = getPipeLineStyle(lineParam,f,radius);
               newFeature.Name = f.GetFieldAsString(lineParam.uniqueIdFieldName);
               this.setFeatureValueByShapeFeature(f,newFeature);
              // newFeatureSet
               if (newFeatureSet.GetFeatureByName(newFeature.Name,true).Length>0) { //存在

                   if (updateMode.Equals(EnumUpdateMode.Append)){
                       continue;
                   }
                   else{
                       GSOFeature delFeature = newFeatureSet.GetFeatureByName(newFeature.Name, true)[0];
                       newFeatureSet.RemoveFeatureByID(delFeature.ID);
                   }
              }
               
               newFeatureSet.AddFeature(newFeature);
               
            }
               newFeatureSet.Save();  
               newFeatureSet.Close();
            return true;
        }


        private double getRadius(LineParam lineParam, GSOFeature f) {
            double radius = 0;
            GSOFieldDefn field = (GSOFieldDefn)(f.GetFieldDefn(lineParam.diameterFieldName));
            if (field.Type == EnumFieldType.Text)
            {
                string temp = f.GetFieldAsString(lineParam.diameterFieldName);
                double outNum = 0;
                bool num = double.TryParse(temp, out outNum);
                if (num)
                    radius = outNum / 2000;
            }
            else if (field.Type == EnumFieldType.Double || field.Type == EnumFieldType.INT32)
                radius = f.GetFieldAsDouble(lineParam.diameterFieldName) / 2000;  // 探测数据的单位一般是毫米,需换算为米; 管径一般是 直径, 这个需要半径, 所有除以2000 
            return radius;
        }

        /**
         * 获取管线style
         **/
        private GSOPipeLineStyle3D getPipeLineStyle(LineParam lineParam,GSOFeature f,double radius) {

            GSOPipeLineStyle3D style = new GSOPipeLineStyle3D();
            style.LineColor = Color.FromArgb(lineParam.transparency, lineParam.lineColor);
            style.Slice = lineParam.sliceNum;
            style.CornerSliceAngle = lineParam.cornerSliceAngle;
            style.Radius = radius;

            return style;
        }
       
        private GSOGeometry updateGemotry(GSOFeature f,LineParam lineParam,double radius, EnumBuildMode buildMode){

            f.Geometry.AltitudeMode = (buildMode.Equals(EnumBuildMode.Alititude)) ? EnumAltitudeMode.RelativeToGround : EnumAltitudeMode.Absolute;

            GSOGeoPolyline3D line = f.Geometry as GSOGeoPolyline3D;
            if (line == null) {
                return null; //log4net 记录错误处理
            }

            double deep1 = f.GetFieldAsDouble(lineParam.startDepthFieldName);
            double deep2 = f.GetFieldAsDouble(lineParam.endDepthFieldName);
            deep1 = lineParam.isRevert ? -deep1 : deep1;
            deep2 = lineParam.isRevert ? -deep2 : deep2;
            
            //根据相对模式进行深度修改
            deep1 = lineParam.relativeMode==1?deep1+radius*2:deep1-radius*2;
            deep2 = lineParam.relativeMode==1?deep2+radius*2:deep2-radius*2;

            GSOPoint3ds pt3ds = new GSOPoint3ds();
            for (int n = 0; n < line[0].Count; n++)
            {
                GSOPoint3d pt3d = line[0][n];
                int pointcount = line[0].Count;
                //TODO LIST:BUG 
                double totalLength = Math.Sqrt(Math.Pow(line[0][pointcount - 1].Y - line[0][0].Y, 2) + Math.Pow(line[0][pointcount - 1].X - line[0][0].X, 2));
                if (totalLength == 0)
                {
                    //TODOLIST:ERROR log4net
                    pt3d.Z = deep1;
                }
                else
                {
                    double radio = Math.Sqrt(Math.Pow(pt3d.Y - line[0][0].Y, 2) + Math.Pow(pt3d.X - line[0][0].X, 2)) / totalLength;
                    pt3d.Z = deep1 + (deep2 - deep1) * radio;
                }

                if (double.IsInfinity(pt3d.Z))
                {
                    //TODOLIST:ERROR log4net
                    pt3d.Z = deep2;
                    //MessageBox.Show("无穷!");
                }
                pt3ds.Add(pt3d);
            }
            line[0] = pt3ds;

            return line;
        }
    }
}