16

I'm attempting to split around 4000 polygons at their midpoint, perpendicular to their longest axis (ie across the width at the midpoint), as in the diagram below.

enter image description here

Ideally, I'd like to do this automatically and avoid manually splitting each polygon. I have extracted the midpoint of polygons by converting the longest lines that can be drawn in each, I just need to determine a method to draw a width line across this point automatically.

Polygons vary in their width, and hence tools which split polygons by defining width lines of a certain length isn't really what I'm looking for.

Any ideas?

4
  • are all the polygons convex?
    – AnserGIS
    Mar 14, 2017 at 13:33
  • Yes, they are more or less shaped similar to that shown in the above diagram.
    – Matt
    Mar 14, 2017 at 14:20
  • Create perpendicular as described gis.stackexchange.com/questions/201867/… Use use them and original as inputs for feature to polygon. It will help to do near on points to boundaries
    – FelixIP
    Mar 14, 2017 at 18:42
  • @Matt did my answer solve your problem? If so could you mark it as answered with the checkbox?
    – BERA
    Mar 23, 2017 at 10:11

1 Answer 1

26

Script below will output a new feature class of split polygons and the lines used for splitting them. Advanced license is required.

The polygons will be split like this: enter image description here

enter image description here

Using Centroid of Minimum Bounding Geometry rectangle as midpoint and split across the rectangle.

import arcpy
print 'Running'
arcpy.env.workspace = r'C:\TEST.gdb'    #Change to match your data
infc = r'polygons123'                   #Change to match your data
outfc_splitlines = r'splitlines'        
outfc_splitpolygons=r'splitpolygons'    

spatial_ref = arcpy.Describe(infc).spatialReference
arcpy.CreateFeatureclass_management(out_path=arcpy.env.workspace, out_name=outfc_splitlines, geometry_type='POLYLINE',spatial_reference=spatial_ref) #Creates a new feature class to hold the split lines

with arcpy.da.SearchCursor(infc,['SHAPE@','SHAPE@X','SHAPE@Y']) as cursor: #For each input polygon create a minimum bounding rectangle
    for row in cursor:
        arcpy.MinimumBoundingGeometry_management(row[0],r'in_memory\bounding','RECTANGLE_BY_WIDTH')
        arcpy.SplitLine_management(r'in_memory\bounding', r'in_memory\splitline') #Split the rectangle into four lines, one for each side
        linelist=[]
        with arcpy.da.SearchCursor(r'in_memory\splitline',['SHAPE@LENGTH','SHAPE@']) as cursor2:
            for row2 in cursor2:
                linelist.append(row2) #Store the lines lenghts and geometries in a list
            linelist=sorted(linelist,key=lambda x: x[0]) #Sort shortest to longest (the two shortest sides of the rectangles come first and second in list)
        arcpy.CopyFeatures_management(in_features=linelist[0][1], out_feature_class=r'in_memory\templine') #Copy the first line to memory
        with arcpy.da.UpdateCursor(r'in_memory\templine',['SHAPE@X','SHAPE@Y']) as cursor3:
            for row3 in cursor3:
                newcentroidx=row[1] #Find x coord of bounding rectangle centroid
                newcentroidy=row[2] #Find y..
                row3[0]=newcentroidx #Assign this to the shortest line
                row3[1]=newcentroidy #Assign this to the shortest line
                cursor3.updateRow(row3) #Move the line to the centroid of bounding rectangle
        arcpy.Append_management(inputs=r'in_memory\templine', target=outfc_splitlines) #Save this line in splitline feature class
#After all split lines are created convert input polygons to lines, merge with split lines and create new polygons from lines.

arcpy.FeatureToLine_management(in_features=infc, out_feature_class=r'in_memory\polytemp')
arcpy.Merge_management(inputs=[r'in_memory\polytemp',outfc_splitlines], output=r'in_memory\templines')
arcpy.FeatureToPolygon_management(in_features=r'in_memory\templines', out_feature_class=outfc_splitpolygons)
print 'Done'

enter image description here

Attributes will get lost but you can use Spatial Join to add them again.

6
  • 8
    Great solution. I think it should be noted that the Advanced license is required to perform this operation (splitline, featureToLine and featureToPolygon). Further, I think adding some comments throughout your code will help new python users understand what each line is doing.
    – Fezter
    Mar 14, 2017 at 22:42
  • Hi @BERA, sorry for the slow reply. Script doesn't seem to work, outputting the following error: ERROR 000466: in_memory\templine does not match the schema of target splitlines Failed to execute (Append).
    – Matt
    Apr 5, 2017 at 9:17
  • 1
    Try to change the append line to: arcpy.Append_management(inputs=r'in_memory\templine', target=outfc_splitlines, schema_type='NO_TEST')
    – BERA
    Apr 5, 2017 at 9:20
  • 1
    Seem to get another error, this time: Parsing error IndentationError: unindent does not match any outer indentation level (line 28)
    – Matt
    Apr 5, 2017 at 10:21
  • You need to have 8 spaces before the arcpy.Append_manag...
    – BERA
    Apr 5, 2017 at 18:45

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.