How to code Lines to polygon?

3761
15
Jump to solution
07-25-2016 04:31 PM
TieshengWu
Occasional Contributor

Hi all I want to convert lines feature that is directioned at random to polygons by python script, but my arcmap has no a license of 'feature to polygon'. How to realize it?

0 Kudos
15 Replies
DanPatterson_Retired
MVP Emeritus

You can try the minimum area bounding circle in Bounding containers with the cavaet that the crossed line pairs can be identified by an attribute in your table.  In other words, your 6 lines need to be grouped into 3 pairs, each pair being found in/crossing one circle.  If your data structure is different, you will still need to be able to associate the 2 lines or the 4 points that form each circle.

XanderBakker
Esri Esteemed Contributor

Could you post a sample of the data (some ball polygons and intersecting lines)? You could select for each ball the intersecting lines and split the polygon with the lines (if the intersecting lines are just 2 lines, not 4). This could work, but I should have a look at a small sample of the data.

0 Kudos
TieshengWu
Occasional Contributor

Thank you Dan and Xander so much. The file of sample data as attached.

0 Kudos
XanderBakker
Esri Esteemed Contributor

Juts did a little proof of concept with a single pie and 2 faults:

import arcpy
def main():
    fc_pie = r'D:\Temp\test\data.gdb\focal_sml_pie'  # single polygon
    fc_faults = r'D:\Temp\test\data.gdb\focal_sml_faults'  # 2 lines in single polygon
    fc_result = r'D:\Temp\test\data.gdb\test01'

    polygon = arcpy.da.SearchCursor(fc_pie, ('SHAPE@')).next()[0]

    lst_polygons = [polygon]
    with arcpy.da.SearchCursor(fc_faults, ('SHAPE@')) as curs:
        for row in curs:
            polyline = row[0]
            lst_polygons = splitPolygon(lst_polygons, polyline)

    arcpy.CopyFeatures_management(lst_polygons, fc_result)

def splitPolygon(lst_polygons, polyline):
    lst_pols = []
    for polygon in lst_polygons:
        try:
            lst_pols += polygon.cut(polyline)
        except Exception as e:
            print "Error:", e
            pass
    return lst_pols

if __name__ == '__main__':
    main()

and this resulted in:

The idea would be to loop through the pies, select the faults corresponding to the pie (select by location) and split the polygons.

XanderBakker
Esri Esteemed Contributor

And here is the code to cut all the pie polygons with the fault polylines:

import arcpy

def main():
    fc_pie = r'C:\GeoNet\SplitBalls\shp\focal_sml_pie.shp'
    fc_faults = r'C:\GeoNet\SplitBalls\shp\focal_sml_faults.shp'
    fc_result = r'C:\GeoNet\SplitBalls\shp\pie_pieces01.shp'

    arcpy.env.overwriteOutput = True

    # create dct with faults
    dct_faults = {r[0]: r[1] for r in arcpy.da.SearchCursor(fc_faults, ('OID@', 'SHAPE@'))}

    # loop through pie polygons
    lst_polygons = []
    with arcpy.da.SearchCursor(fc_pie, ('SHAPE@')) as curs_pie:
        for row_pie in curs_pie:
            polygon = row_pie[0]

            # get list of faults for current pie
            lst_faults_pie = getFaults(polygon, dct_faults.values())

            # cut pie based on faults
            lst_polygons_pie = [polygon]
            for fault in lst_faults_pie:
                lst_polygons_pie = splitPolygon(lst_polygons_pie, fault)

            # add polygons to list
            lst_polygons.extend(lst_polygons_pie)

    # write the pie pieces to a new featureclass
    arcpy.CopyFeatures_management(lst_polygons, fc_result)


def getFaults(polygon, lst_faults):
    '''Get list of fault polylines for pie polygon'''
    lst_faults_pie = []
    for fault in lst_faults:
        mid_pnt = fault.positionAlongLine(0.5, True)
        if polygon.contains(mid_pnt):
            lst_faults_pie.append(fault)
    return lst_faults_pie


def splitPolygon(lst_polygons, polyline):
    '''split pie polygon with fault polyline'''
    lst_pols = []
    for polygon in lst_polygons:
        try:
            lst_pols += polygon.cut(polyline)
        except Exception as e:
            print "Error:", e
            pass
    return lst_pols


if __name__ == '__main__':
    main()

Also find attached the resulting shapefile.

TieshengWu
Occasional Contributor

Thank you a lot.  It solve my problem. The only limitation is that it needs a 10.2 above version, but it's enough for me cause my platform is 10.3 Standard.

Thank you again.

0 Kudos