List of layers TOC preserving nesting

500
2
08-15-2022 01:21 PM
Vidar
by
Occasional Contributor II

Is there a way to loop through the TOC and preserve the nested hierarchy i.e. NOT the GetLayersAsFlattenedList() method. I also need to examine whether they are group layers or feature/raster layers as I go round.

Can't find anything obvious. I did try:

MapView.Active.Map.Layers

but that just returned me the project node, an item count of 1 - when I had numerous layers loaded in, that made no sense to me.

If anyone can help that would be great.

Tags (2)
0 Kudos
2 Replies
UmaHarano
Esri Regular Contributor

Hi

You can iterate through the layers in the TOC and determine if a layer is a Group layer or not using the "GroupLayer" type.

var map = MapView.Active.Map;
if (map == null)
  return;
//Get the group layers first
IReadOnlyList<GroupLayer> groupLayers = map.Layers.OfType<GroupLayer>().ToList();
//Iterate 
foreach (var groupLayer in groupLayers)
{
//Do something with groupLayer
}

 

There is a snippet in the ProSDK wiki that iterates through the TOC. In this snippet, unchecked layers are removed from the TOC.  Removes all layers that are unchecked 

0 Kudos
Wolf
by Esri Regular Contributor
Esri Regular Contributor

Uma's suggestion works only for group layers, if you want a more general way to traverse the layer hierarchy you have to use the Layers collection of the Map class, as suggest by Uma.  But when you iterate through the layers you need to look at the real type of the layer object (in essence each class that derives from the Layer class) and if the derived type has a Layers collection you then iterate into that sub layer collection.  Below is a sample implementation, however, the implementation is incomplete because it only looks at AnnotationLayers and CompositeLayers as 2nd level entries in the TOC (there are more classes the derive from the Layer class and that have a Layers collection).

Wolf_0-1661218372195.png

 

protected override void OnClick()
{
  try
  {
    var mva = MapView.Active;
    if (mva == null) return;
    var layers = mva.Map.Layers;
    StringBuilder sb = new();
    GetLayers(layers, sb, "");
    MessageBox.Show(sb.ToString());
  }
  catch (Exception ex)
  {
    MessageBox.Show(ex.Message);
  }
}

private static bool GetLayers(ReadOnlyObservableCollection<Layer> layers, StringBuilder sb, string indent)
{
  foreach (var layer in layers)
  {
    var lyrName = layer.Name.Substring(0, Math.Min(40, layer.Name.Length));
    sb.AppendLine($@"{indent}{lyrName} {layer.GetType().Name}");
    if (layer is AnnotationLayer annoLyr)
    {
      GetLayers(annoLyr.Layers, sb, indent + "  ");
      continue;
    }
    if (layer is CompositeLayer compositeLyr)
    {
      GetLayers(compositeLyr.Layers, sb, indent + "  ");
      continue;
    }
  }
  return true;
}