Serializing JSON Geometry Objects between Silverlight, WPF and ArcObjects

Richie Carmichael posted a great article about serialization of objects in JSON to send to the server. He walk us through to the best practices to do that.

I have been getting lots of questions lately in how to send Silverlight geometry to the server to send it to ArcObjects to store into a geospatial database.

I would like to say before that even the code below will work for doing that task, I would recommend to take this hack as it is, a hack until a solution to do that is put it into place, I do not know if this is the best way to do just that. The sample below will send a polygon from Silverlight to a Spatial database. Please do let me know if I can optimize the code or there is something else I can do better.

Given a ArcGIS.Geometry.Polygon convert it to a PointCollection then serialize it to JSON:

            ArcGIS.Geometry.PointCollection pointCollection = new ESRI.ArcGIS.Geometry.PointCollection();                        
            foreach(ArcGIS.Geometry.PointCollection ring in _geometry.Rings)
            {
                foreach (ESRI.ArcGIS.Geometry.MapPoint point in ring)
                {
                    pointCollection.Add(point);
                }                
            }

Convert it to Json

            MemoryStream memoryStream = new MemoryStream();
            DataContractJsonSerializer serializer = new DataContractJsonSerializer(obj.GetType());
            serializer.WriteObject(memoryStream, obj);
            memoryStream.Position = 0;
            StreamReader streamReader = new StreamReader(memoryStream);
            string JSON = streamReader.ReadToEnd();
            memoryStream.Close();
 
 

Send it using a Silverlight Service to the server and use the WPF binaries of those objects.

Server side Serialize it to a PointCollection

Byte[] bytes = Encoding.Unicode.GetBytes(polygon);
            MemoryStream memoryStream = new MemoryStream(bytes);
            DataContractJsonSerializer dataContractJsonSerializer = new DataContractJsonSerializer(gPolygon.GetType());
            gPolygon = dataContractJsonSerializer.ReadObject(memoryStream) as ESRI.ArcGIS.Geometry.PointCollection;
            memoryStream.Close();

Then create a double array to of those points, this will not bring attributes of you geometry, just the points.


double [] coor = new double[poly.Count*2];
            int t = 0;
            for (int i = 0; i < poly.Count; i++)
            {
                coor[t] = poly[i].X;
                t++;
                coor[t] = poly[i].Y;
                t++;
            }

So you can then convert it to a IPolygon from ArcObjects:



                    ESRI.ArcGIS.Geometry.IPointCollection pPointCol = _serverContext.CreateObject("esriGeometry.Polygon") as ESRI.ArcGIS.Geometry.IPointCollection;
                    for (int i = 0; i < Coordinates.Length; i += 2)
                    {
                        ESRI.ArcGIS.Geometry.IPoint pt = (ESRI.ArcGIS.Geometry.IPoint)_serverContext.CreateObject("esriGeometry.Point");
                        pt.PutCoords(Coordinates[i], Coordinates[i + 1]);
                        pPointCol.AddPoints(1, ref pt);
                    }

                    feature.Shape = pPointCol as ESRI.ArcGIS.Geometry.IPolygon;

Hope this opens a thread to accomplish this task faster and better.

Cheers

Al

1 Comment

Comments have been disabled for this content.