How to set layer elevation on-the-ground in python script?

1379
6
03-23-2020 12:57 AM
AndresMaremäe1
New Contributor II

Hi

I'm creating 3D scenes and updating them from geodatabase using python script in ArcGIS Pro. I have automated entire process except one little step. Features in a building footprints layer have to be on-the-ground for extrusion but if I add the data from geodatabase then the features in layer are at-an-absolute height. How to set layer elevation setting "on-the-ground" with python script in ArcGIS PRO?

Thank you in advance

Andres

Tags (1)
6 Replies
DanPatterson_Retired
MVP Emeritus

there are not 3d methods or classes exposed directly in the arcpy module, You will have to continue to call/use the tools from within the existing toolset providing defaults if applicable or even possible.

ArcGIS Pro Python reference—ArcGIS Pro | Documentation 

0 Kudos
AndresMaremäe1
New Contributor II

Thank you, Dan

I will stop spending time on this issue at the moment then. Maybe in the future there will be some other or new solution for this.

0 Kudos
KoryKramer
Esri Community Moderator

You might be (should be?) able to achieve this using Python CIM access.  Read this carefully: Python CIM access—ArcPy | Documentation 

In the tips section of that documentation it basically says that if you're not sure what property you need to be modifying in the cim, change it in the UI and compare with changes in the output json.  So I did a quick experiment (though looking back, I'm doing this in a Map rather than a Scene - hopefully the process would work for you).

When my layer's Elevation is set to "On the ground"

I export a layer file to get the .json and open that in Notepad++.

I see

And I can see that the Ground surface for the map uses the same.  So it’s tying the layer’s elevation to the map’s ground elevation surface.

Maybe you could do the same with the layers in your Scene to understand how the Ground setting is structured in the json and then use Python CIM access to get the definition, make modifications, and set the definition.  Again, heed the caution noted in the documentation:)

Also, here are some examples for common requests using the CIM access through Python: https://www.arcgis.com/home/item.html?id=8772f61319584882bb697ba003030636 

AndresMaremäe1
New Contributor II

Kory, I did not notice your answer before. Your suggested solution sounds really interesting and I will try it next week. Thank you and I will report about my experiment.

0 Kudos
AndresMaremäe1
New Contributor II

Well, CIM did the trick. So many thanks, Kory!

At first I did look it like a year ago also but I did not understand that it is possible to add new properties with setDefiniton method. Anyhow works now like a charm.

I will add the code over here if anyone will need a hint or smthng.

import json
import arcpy

def OnTheGround(in_lyr😞
  
  proj = arcpy.mp.ArcGISProject('Current')
  scene = proj.listMaps('Scene')[0]
  lyr = scene.listLayers(in_lyr)[0]

  json_string = r'''[
      {
        "type" : "CIMMapElevationSurface",
        "baseSources" : [
          {
            "type" : "CIMElevationSource",
            "dataConnection" : {
              "type" : "CIMStandardDataConnection",
              "workspaceConnectionString" : "DATABASE=D:\\ArcGis\\Projects\\DTM2019\\DTM2019.gdb",
              "workspaceFactory" : "FileGDB",
              "dataset" : "DEM2019",
              "datasetType" : "esriDTRasterDataset"
            },
            "verticalUnit" : {
              "uwkid" : 9001
            },
            "visibility" : true,
            "name" : "DEM2019",
            "elevationSourceID" : "a4638e171e3ba60ab47074c9ee3fa4950"
          }
        ],
        "elevationMode" : "BaseGlobeSurface",
        "name" : "Ground",
        "verticalExaggeration" : 1,
        "mapElevationID" : "{EC00A89B-0733-41CB-AECB-14F58E16E64C}",
        "color" : {
          "type" : "CIMRGBColor",
          "values" : [
            255,
            255,
            255,
            100
          ]
        },
        "surfaceTINShadingMode" : "Smooth",
        "visibility" : true,
        "expanded" : true
      }
    ]'''

  cim = lyr.getDefinition('V2')

  cim_elev = json.loads(json_string)
  cim.elevationSurfaces = cim_elev
  cim.layerElevation.mapElevationID = "{EC00A89B-0733-41CB-AECB-14F58E16E64C}"
  cim.featureElevationExpression = ''
  lyr.setDefinition(cim)

def AtAnAbsoluteHeight(in_lyr😞
  
  proj = arcpy.mp.ArcGISProject('Current')
  scene = proj.listMaps('Scene')[0]
  lyr = scene.listLayers(in_lyr)[0]

  cim = lyr.getDefinition('V2')
  
  cim.elevationSurfaces= ""
  cim.layerElevation.mapElevationID = ''
  cim.featureElevationExpression = "Shape.Z"
  lyr.setDefinition(cim)
0 Kudos
nahardito
New Contributor

where the code is added? how to add the code in python for the purposes?

0 Kudos