Quantcast
Channel: Question and Answer » arcpy
Viewing all articles
Browse latest Browse all 767

Polygon scaling using arcpy

$
0
0

Is it possible to scale each polygon by a numeric value in an attribute table field using arcpy. I have updated the code from some previous excellent work done by Evil Genius

import arcpy
import math

def scale_geom(geom, scale, reference=None):
   """Returns geom scaled to scale %"""
   if geom is None: return None
   if reference is None:
    # we'll use the centroid if no reference point is given
    reference = geom.centroid

refgeom = arcpy.PointGeometry(reference)
newparts = []
for pind in range(geom.partCount):
    part = geom.getPart(pind)
    newpart = []
    for ptind in range(part.count):
        apnt = part.getObject(ptind)
        if apnt is None:
            # polygon boundaries and holes are all returned in the same part.
            # A null point separates each ring, so just pass it on to
            # preserve the holes.
            newpart.append(apnt)
            continue
        bdist = refgeom.distanceTo(apnt)

        bpnt = arcpy.Point(reference.X + bdist, reference.Y)
        adist = refgeom.distanceTo(bpnt)
        cdist = arcpy.PointGeometry(apnt).distanceTo(bpnt)

        # Law of Cosines, angle of C given lengths of a, b and c
        angle = math.acos((adist**2 + bdist**2 - cdist**2) / (2 * adist * bdist))

        scaledist = bdist * scale

        # If the point is below the reference point then our angle
        # is actually negative
        if apnt.Y < reference.Y: angle = angle * -1

        # Create a new point that is scaledist from the origin
        # along the x axis. Rotate that point the same amount
        # as the original then translate it to the reference point
        scalex = scaledist * math.cos(angle) + reference.X
        scaley = scaledist * math.sin(angle) + reference.Y

        newpart.append(arcpy.Point(scalex, scaley))
    newparts.append(newpart)

return arcpy.Geometry(geom.type, arcpy.Array(newparts), geom.spatialReference)

incur = arcpy.da.SearchCursor(r'D:ZOCPOLYPGDIS_MASTER.shp', ['OID@','SHAPE@'])
outcur = arcpy.da.InsertCursor(r'D:ZOCPOLYPGDIS_MASTER_1.shp', ['SHAPE@'])

for row in incur:
    # Scale each feature by 0.5 and insert into dest_fc
    outcur.insertRow([scale_geom(row[1], arcpy.da.SearchCursor(r'D:ZOCPOLYPGDIS_MASTER.shp', ['Scale_Fact']))])
del incur
del outcur

Viewing all articles
Browse latest Browse all 767

Trending Articles