Настройка выходных символов в скриптах

Свойство символов параметра инструмента-скрипта позволяет вам связать файл отдельного слоя (.lyr) с выходным параметром. При запуске инструмента-скрипта, результат добавляется для отображения на карту, с использованием символов, найденных в файле слоя. Вы можете также задать свойства символов в части кода скрипта символы (symbology).

В обоих случаях, вы можете связать один и только один файл слоя (.lyr) с выходным параметром. Наличие только одного файла слоя работает необходимым образом, если результат четко определен. Но что делать в том случае, когда результат не определен четко? Например, вы знаете только то, что результатом выполнения будет класс объектов, но не знаете, какой – точечный, линейный, или полигональный, пока не запустите инструмент. Файлы слоев зависят от типа геометрии, что означает, что вы не можете иметь один файл слоя, отображающий несколько типов объектов. В этом случае, вам необходимо иметь три файла слоев, по одному для каждого типа геометрии, и затем привязать правильный файл слоя, основываясь на типе геометрии результата. Следующий пример кода иллюстрирует это.

# Set the symbology of the output. 
    #   output    = the output value
    #   params[2] = the output parameter
    #
    params = arcpy.GetParameterInfo()
    desc = arcpy.Describe(output)
    if desc.shapeType == "Polygon":
        params[2].symbology = "c:/Tools/Extractor/ToolData/polygon.lyr"
    elif desc.shapeType == "Polyline":
        params[2].symbology = "c:/Tools/Extractor/ToolData/polyline.lyr"
    else:
        params[2].symbology = "c:/Tools/Extractor/ToolData/point.lyr"

Логика приведенного выше скрипта предельно проста: проверить тип геометрии (формы) и задать соответственно файл слоя. Даже если вы используете более сложную логику, схема остается той же:

Сравнение настройки символов через скрипт и через класс ToolValidator

Если вы хорошо знакомы с логикой проверки инструментов в программировании, через класс ToolValidator, вы можете увидеть, что пример кода выше может быть переписан для использования в методе updateParameters. На самом деле, если вам необходимо только привязать один файл слоя, вы можете сделать это в свойствах инструмента-скрипта, или через метод initializeParameters. Но если вам необходимо задать символы для одного любого слоя из нескольких слоев, то следует делать это в инструменте-скрипте. Добавление этой логики в класс ToolValidator перегружает ваш код логикой, которая не имеет никакого отношения к проверке инструмента, и в некоторых случаях вы даже не будете знать, какой файл слоя использовать, до запуска инструмента.

Пример скрипта

Скрипт, приведенный ниже, создает объекты на основании их расстояния от парков в городе Портленд. Задаются три параметра: входные объекты, расстояние, и выходные объекты. Выходные объекты должны иметь символы, позволяющие легко отличить их от других объектов на карте (то есть не похожие на символы по умолчанию, которые будет сложно различить). Поскольку входными параметрами могут быть как точки, так линии или полигоны, то необходимы три различных файла слоев.

Данный скрипт также демонстрирует несколько различных техник кодов, для портативности решения. Используются следующие техники портативности +++:

# ExtractData.py
# Description: Script that will extract features from an input layer within a specified
#              distance from a park.
# Parameters:
#  0 - input features
#  1 - distance from parks (linear units)
#  2 - output feature class

import arcpy
from arcpy import env
import os
import sys

env.overwriteOutput = True

try:
    # This tool makes use of a system folder with a Scripts and ToolData subfolder. 
    #  We can discover the pathname of this folder by examining the
    #  first argument to the script, which is the pathname to the script
    #  (example: "E:\examples\symbology\scripts\ExtractData.py".)  We
    #  then use this toolSharePath variable to create pathnames to our 
    #  shapefile data and layer files ("E:\examples\symbology\ToolData\points.lyr").
    #
    scriptPath      = sys.argv[0]
    toolSharePath   = os.path.dirname(os.path.dirname(scriptPath))
    dataPath        = os.path.join(toolSharePath, "ToolData")
    parkPath        = os.path.join(dataPath, "PortlandParks.shp")
    pointLyrPath    = os.path.join(dataPath, "point.lyr")
    polygonLyrPath  = os.path.join(dataPath, "polygon.lyr")
    polylineLyrPath = os.path.join(dataPath, "polyline.lyr")
    
    # Buffer the parks by the specified distance.  The output is a scratch
    #  feature class in the same workspace as the output feature class
    #
    arcpy.SetProgressorLabel("Buffering parks ...")
    scrname = arcpy.CreateScratchName("xxx", "", "featureclass", 
                                      os.path.dirname(arcpy.GetParameterAsText(2)))
    arcpy.Buffer_analysis(parkPath, scrname, arcpy.GetParameterAsText(1))

    # Clip the defined layer with the buffered parks
    #
    arcpy.SetProgressorLabel("Clipping " + arcpy.GetParameterAsText(0) + " ..." )
    output = arcpy.Clip_analysis(arcpy.GetParameterAsText(0), scrname, 
                                 arcpy.GetParameterAsText(2))

    # Delete intermediate dataset
    #
    try:
        arcpy.Delete_management(scrname)
    except:
        pass

    # Set the symbology of the output. 
    #
    params = arcpy.GetParameterInfo()
    desc = arcpy.Describe(output)
    if desc.shapeType == "Polygon":
        params[2].symbology = polygonLyrPath
    elif desc.shapeType == "Polyline":
        params[2].symbology = polylineLyrPath
    else:
        params[2].symbology = pointLyrPath

except:
    arcpy.AddError("An error occurred. " + arcpy.GetMessages(2))
9/10/2013