how to get geometry type of layer using IMapServer3 and IMapLayerInfo? (C#)
http://forums.arcgis.com/threads/11481-how-to-get-geometry-type-of-layer-using-IMapServer3-and-IMapLayerInfo-(C-)
I need to create a REST extension that will return JSON looking like that:
"layers" : [ { "MaxScale" : 0, "MinScale" : 0, "defaultVisibility" : true, "geometryType" : null, "id" : 0, "name" : "Name", "parentLayerId" : -1, "subLayerIds" : [ 1, 2 ] }, { "MaxScale" : 0, "MinScale" : 0, "defaultVisibility" : false, "geometryType" : "esriGeometryPoint", "id" : 1, "name" : "NAME Offices", "parentLayerId" : 0, "subLayerIds" : null } ... As I'm able to get almost all informations that I want, I have only issue getting geometryType anddefaultVisibility. I was trying to find a way by looking into DOCS, I'm sure If I will be able to get IGeometry interface I should be able to get geometry type, but how to get IGeometry interface starting from IMapServer3? Or there is other way to do it? Here is a code that is creating list of layers in JSON format: private XxxLayerInfo[] GetLayerInfos() { IMapServer3 mapServer = _serverObjectHelper.ServerObject as IMapServer3; if (mapServer == null) throw new Exception("Unable to access XXX map server."); IMapServerInfo msInfo = mapServer.GetServerInfo(mapServer.DefaultMapName); IMapLayerInfos layerInfos = msInfo.MapLayerInfos; int length = layerInfos.Count; XxxLayerInfo[] xxxLayerInfos = new XxxLayerInfo[c][/c]; for(int i = 0; i < length; i++) { IMapLayerInfo layerInfo = layerInfos.get_Element(i); xxxLayerInfos[i] = XxxLayerInfo.CreateXxxLayerInfo(layerInfo); } return xxxLayerInfos; } public static XxxLayerInfo CreateXxxLayerInfo(IMapLayerInfo mapLayerInfo) { var layer = new XxxLayerInfo(); layer.Id = mapLayerInfo.ID; layer.Name = mapLayerInfo.Name; layer.GeometryType = null; //mapLayerInfo.GeometryType - HOW TO GET this?; layer.DefaultVisibility = false; //mapLayerInfo.DefaultVisibility - HOW TO GET this?; layer.MinScale = mapLayerInfo.MinScale; layer.MaxScale = mapLayerInfo.MaxScale; layer.ParentLayerId = mapLayerInfo.ParentLayerID; layer.SubLayers = mapLayerInfo.SubLayers; return layer; } Ok, there is a way to do it with multiply casts and few extra loops (esri why?) As what surprising is that after 2 (?) months question staid without answer - the only place for Q reg ESRI. The full desc how to do it can be found here - text in PL. If you are interested only in code, here it is: // get map info public static MapInfo ConstructFrom(IMapServer3 mapServer3) { // IMapServerInfo3 contains CopyrightText prop, 1 & 2 does not var mapServerInfo = (IMapServerInfo3)mapServer3.GetServerInfo(mapServer3.DefaultMapName); var mapInfo = new MapInfo { Description = mapServerInfo.Description, MapName = mapServerInfo.Name, CopyrightText = mapServerInfo.CopyrightText }; IMapLayerInfos layerInfos = mapServerInfo.MapLayerInfos; for (int i = 0; i < layerInfos.Count; i++) { var layerInfo = layerInfos.Element[i]; mapInfo.Layers.Add( LayerInfo.ConstructFrom( layerInfo, LayerInfo.IsLayerVisible(mapServerInfo, layerInfo.ID) )); } return mapInfo; } // get layer info private static readonly int[] AvaliableReports = new[] {17,18,19,20}; public static LayerInfo ConstructFrom(IMapLayerInfo mapLayerInfo, bool visible) { var layerInfo = new LayerInfo { Id = mapLayerInfo.ID, DisplayField = mapLayerInfo.DisplayField, ScaleUpper = (int)mapLayerInfo.MaxScale, ScaleLower = (int)mapLayerInfo.MinScale, Name = mapLayerInfo.Name, Description = mapLayerInfo.Description, DefaultVisibility = visible, ParentLayerId = mapLayerInfo.ParentLayerID, }; IFields fields = mapLayerInfo.Fields; bool addFields = false; if (fields != null) { for (int j = 0; j < fields.FieldCount; j++) { IField field = fields.Field[j]; if (field.Type == esriFieldType.esriFieldTypeString) { layerInfo.DictFields[field.Name] = field.AliasName; continue; } if(field.Type != esriFieldType.esriFieldTypeGeometry) { continue; } IGeometryDef geometryDef = field.GeometryDef; layerInfo.GeometryType = Enum.GetName(typeof(esriGeometryType), geometryDef.GeometryType); switch (geometryDef.GeometryType) { case esriGeometryType.esriGeometryNull: layerInfo.GeometryType = null; break; case esriGeometryType.esriGeometryPoint: addFields = true; break; } } } // hack: this should be done in a proper way... but for now is enough layerInfo.ContainsReport = AvaliableReports.Contains(layerInfo.Id); if(!addFields) { layerInfo.DictFields = new Dictionary<string, string>(); } if (mapLayerInfo.SubLayers == null) { return layerInfo; } for (int i = 0; i < mapLayerInfo.SubLayers.Count; i++) { layerInfo.SubLayerIds.Add(mapLayerInfo.SubLayers.Element[i]); } return layerInfo; } // get default visibility public static bool IsLayerVisible(IMapServerInfo3 mapServerInfo, int layerId) { ILayerDescriptions layerDescs = mapServerInfo.DefaultMapDescription.LayerDescriptions; long c = layerDescs.Count; for (long i = 0; i < c; i++) { var layerDesc = (ILayerDescription3)layerDescs.Element[i]; if (layerDesc.ID == layerId) { return layerDesc.Visible; } } return false; }