3 votos

En ArcGIS, ¿cómo crear una polilínea localmente?

Utilizando el más reciente SDK .net core de ESRI ArcGis en una aplicación local (no web).

Trato de crear una clase envolvente basada en ArcGis:IFeatureSet que tomará una colección de objetos que implementan IGeoCoordinate (Proporcionar un GeoCoordinate) y generará automáticamente todas las características y sus propiedades.

Todo parece posible y casi funciona pero no encuentro la forma de crear una Característica dando su polilínea y un conjunto de atributos.

¿Alguien sabe cómo crear una característica de forma programada?

using Esri.ArcGISRuntime.Data;
using Esri.ArcGISRuntime.Geometry;
using Esri.ArcGISRuntime.Symbology;
using Esri.ArcGISRuntime.UI;
using EsriUtil;
using GeoCoordinatePortable;
using GeoGraphicalCore;
using HQ.Util.General.Reflection;
using System;
using System.CodeDom;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Text;

namespace ElectricalNetworkMapArcgis.Util
{
    public class FeatureSetWrapper<T> : IFeatureSet where T : IGeoCoordinateContainer // EO: It should already exists... 
    {
        public IEnumerable<T> Objects { get; private set; }
        public List<Feature> Features { get; private set; }
        public List<Field> _fields { get; private set; }

        public GeometryType GeometryType { get; private set; }
        public SpatialReference SpatialReference { get; private set; }

        public FeatureSetWrapper(IEnumerable<T> objects, GeometryType geometryType, SpatialReference spatialReference)
        {
            Objects = objects;
            GeometryType = geometryType;
            SpatialReference = spatialReference;

            FillFieldsThroughReflection();
            FillFeatures();
        }

        public void FillFieldsThroughReflection()
        {
            foreach(var prop in typeof(T).GetProperties())
            {
                if (prop.CanRead)
                {
                    Field field = new Field(prop.PropertyType.GetEsriAssociatedFieldType(), prop.Name, prop.DisplayName(), GetEvaluatedFieldLenght(prop), null, prop.CanWrite, false);
                    _fields.Add(field);
                }
            }
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="pi"></param>
        /// <returns>The proper maxLenght if the count of items if less than "maxIteration" otherwise return a very rough estimate</returns>
        int GetEvaluatedFieldLenght(PropertyInfo pi)
        {
            int stringLenghtMax = 0;

            if (pi.PropertyType == typeof(string))
            {
                const int maxIteration = 60; // EO: ~random choice. IF there is millions of record, it would take too much time to verify all, considering also that is from reflection.
                int iterCount = 0;
                foreach(T obj in Objects)
                {
                    stringLenghtMax = Math.Max(stringLenghtMax, pi.GetValue(obj).ToString().Length);

                    iterCount++;
                    if (iterCount == maxIteration) // Prevent potential super long delay
                    {
                        return stringLenghtMax * 2; // We reach maxIteration and estimate (hope we are right) to keep the double in order to give room for not evaluated values. 
                    }
                }
            }

            return stringLenghtMax;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <returns>Return the count of feature</returns>
        int FillFeatures()
        {
            int countOfObject = 0;

            var polyLineBuilder = new PolylineBuilder(SpatialReferences.Wgs84);

            foreach (T obj in Objects)
            {
                IEnumerable<GeoCoordinate> geoCoordinates = obj.GetGeoCoordinates();

                foreach (var geoCoordinate in geoCoordinates)
                {
                    // EO: check is coordinates are into Quebec limits
                    Debug.Assert(geoCoordinate.Longitude > -80 && geoCoordinate.Longitude < -57);
                    Debug.Assert(geoCoordinate.Latitude > 44 && geoCoordinate.Latitude < 62);

                    MapPoint pointIter = new MapPoint(geoCoordinate.Longitude, geoCoordinate.Latitude, SpatialReferences.Wgs84);
                    polyLineBuilder.AddPoint(pointIter);
                }

                var polyline = polyLineBuilder.ToGeometry();

                // For GraphicOverlay
                // var graphic = new Graphic(polyline, _simpleLineSymbol);

                // BUG HERE

                var feature = new Feature(polyline); // DOES NOT EXISTS

                // Add Attributes here

                Features.Add(feature);

                countOfObject++;
                polyLineBuilder.Parts.Clear();
            }

            return countOfObject;
        }

        private static readonly SimpleLineSymbol _simpleLineSymbol = new SimpleLineSymbol(SimpleLineSymbolStyle.Solid, System.Drawing.Color.FromArgb(128, 255, 0, 0), 2);

        public IReadOnlyList<Field> Fields => _fields;

        public IEnumerator<Feature> GetEnumerator()
        {
            return Features.GetEnumerator();
        }

        IEnumerator IEnumerable.GetEnumerator()
        {
            return Features.GetEnumerator();
        }
    }
}

1voto

Dr I Puntos 521

Las características se crean a partir de FeatureTables utilizando el método "CreateFeature": https://developers.arcgis.com/net/latest/wpf/api-reference/html/M_Esri_ArcGISRuntime_Data_FeatureTable_CreateFeature.htm

Las características no pueden ser independientes sin una tabla a la que pertenezcan. En su lugar, podría devolver una FeatureCollectionTable con las características pobladas en ella.

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X