How to automate selection and KML conversion?

2167
8
Jump to solution
01-12-2018 07:09 AM
ZacStanley3
New Contributor III

Hello Community-

First time poster, long time lurker. Hoping I can find some model builder or python help with an automation task.

I have about 300 lines I need to convert to KML based on attribute 'TrailName'.

Conceptually I understand what I need to do but am stuck executing with Model Builder.

I was thinking I could use the iterate row selection in model builder to select by 'TrailName' attribute and convert layer to kml. This process would need to be looped for every 'TrailName'.

Does anyone have experience or understanding on how to execute this?

Thanks in advance.

Zac

Tags (1)
0 Kudos
1 Solution

Accepted Solutions
XanderBakker
Esri Esteemed Contributor

Below some untested code that could work.

Explanation of the code:

  • lines 1, 22 and 23 can be "ignored". It is a way to be able to handle better the release of memory and stuff like this. So the code is actually the part from line 2 until 20 (without the additional indent this part would run too)
  • lines 2 and 3 import two modules: arcpy and os
  • line 4 makes the script overwrite any existing element (in this case for the layer in memory that will have the same name "lyr" for every train name)
  • lines 7 to 9 set some variables: input featureclass, the name of the field and the output folder
  • line 12 is a little more complex. In a single line it will create a cursor (see SearchCursor—Help | ArcGIS Desktop ) with a single field (your trailname) and return that value. This will create a list of all the trail names. In case the values are not unique I wrap this in list(set()) to make the list unique.
  • on line 15 the loop starts. It will extract each trail name from the list "lst_trails"
  • line 16 puts the quotes around the field name. it uses AddFieldDelimiters (AddFieldDelimiters—Help | ArcGIS Desktop ) to do that based on the workspace (this way it should work no matter if you work with a shapefile or a featureclass in a file, personal or enterprise geodatabase
  • line 17 creates the where clause. By using ".format" next to a string I can pass variables that will replace the {0} and {1} in the string.
  • line 18 creates a feature layer applying the where clause (so it only get's the feature(s) for the current trail name.
  • line 19 defines the output file name for the KMZ file. It uses os.path.join to join the path with the file name
  • line 20 finally converted the feature layer to the kmz file

def main():
    import arcpy
    import os
    arcpy.env.overwriteOutput = True

    # settings: edit these
    fc_in = r'path to your input featureclass'
    fld_trail = 'TrailName'
    out_folder = r'path to your output folder for KML files'

    # create list of unique trail names
    lst_trails = list(set([r[0] for r in arcpy.da.SearchCursor(fc_in, (fld_trail))]))

    # loop through trails
    for trail_name in lst_trails:
        fld = arcpy.AddFieldDelimiters(fc_in, fld_trail)
        where ="{0} = '{1}'".format(fld, trail_name)
        arcpy.MakeFeatureLayer_management(fc_in, "lyr", where)
        kmz_file = os.path.join(out_folder, "{0}.kmz".format(trail_name))
        arcpy.LayerToKML_conversion("lyr", kmz_file)

if __name__ == '__main__':
    main()
‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

View solution in original post

0 Kudos
8 Replies
XanderBakker
Esri Esteemed Contributor

Is the Trailname unique or can there be multiple features with the same train name? If values repeat the Iterate row would potentially overwrite kml files. In case of scripting this, you could generate a unique list of values from the field Trailname, and for each value set a definition query while creating a featurelayer and export that to KML using the trailname as output kml file name.

0 Kudos
ZacStanley3
New Contributor III

Yeah, TrailName is a unique values representing a single line feature.

0 Kudos
XanderBakker
Esri Esteemed Contributor

Below some untested code that could work.

Explanation of the code:

  • lines 1, 22 and 23 can be "ignored". It is a way to be able to handle better the release of memory and stuff like this. So the code is actually the part from line 2 until 20 (without the additional indent this part would run too)
  • lines 2 and 3 import two modules: arcpy and os
  • line 4 makes the script overwrite any existing element (in this case for the layer in memory that will have the same name "lyr" for every train name)
  • lines 7 to 9 set some variables: input featureclass, the name of the field and the output folder
  • line 12 is a little more complex. In a single line it will create a cursor (see SearchCursor—Help | ArcGIS Desktop ) with a single field (your trailname) and return that value. This will create a list of all the trail names. In case the values are not unique I wrap this in list(set()) to make the list unique.
  • on line 15 the loop starts. It will extract each trail name from the list "lst_trails"
  • line 16 puts the quotes around the field name. it uses AddFieldDelimiters (AddFieldDelimiters—Help | ArcGIS Desktop ) to do that based on the workspace (this way it should work no matter if you work with a shapefile or a featureclass in a file, personal or enterprise geodatabase
  • line 17 creates the where clause. By using ".format" next to a string I can pass variables that will replace the {0} and {1} in the string.
  • line 18 creates a feature layer applying the where clause (so it only get's the feature(s) for the current trail name.
  • line 19 defines the output file name for the KMZ file. It uses os.path.join to join the path with the file name
  • line 20 finally converted the feature layer to the kmz file

def main():
    import arcpy
    import os
    arcpy.env.overwriteOutput = True

    # settings: edit these
    fc_in = r'path to your input featureclass'
    fld_trail = 'TrailName'
    out_folder = r'path to your output folder for KML files'

    # create list of unique trail names
    lst_trails = list(set([r[0] for r in arcpy.da.SearchCursor(fc_in, (fld_trail))]))

    # loop through trails
    for trail_name in lst_trails:
        fld = arcpy.AddFieldDelimiters(fc_in, fld_trail)
        where ="{0} = '{1}'".format(fld, trail_name)
        arcpy.MakeFeatureLayer_management(fc_in, "lyr", where)
        kmz_file = os.path.join(out_folder, "{0}.kmz".format(trail_name))
        arcpy.LayerToKML_conversion("lyr", kmz_file)

if __name__ == '__main__':
    main()
‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍
0 Kudos
ZacStanley3
New Contributor III

This is fantastic - thank you. I will test and reply with questions.

0 Kudos
ZacStanley3
New Contributor III

Xander-

This script worked perfectly - now I need to study and understand what it did exactly - thanks again.

Zac

0 Kudos
XanderBakker
Esri Esteemed Contributor

Glad it worked! I don't mind to add some additional explanation to help you understand.

Can you mark the post and the correct answer with the "Mark Correct" button next to it?

ZacStanley3
New Contributor III

Would love an explanation!

0 Kudos
XanderBakker
Esri Esteemed Contributor

Done! If you have any questions, just let me know.

0 Kudos