Calculate Image Moments of an EllipseΒΆ

Image moments can be used to determine the center of gravity or average pixel location of a binary object as well as the orientation of an object according to its axes of variation.

The interactive plot below demonstrates how to calculate the image moments of an ellipse-defined mask.

[1]:
import itk
import matplotlib.pyplot as plt
import numpy as np
from ipywidgets import interact
[2]:
output_size = [100, 100] # size of binary image containing the ellipse

@interact(tx=(0,output_size[0],1), ty=(0,output_size[1],1), a=(5,50,1), b=(5,50,1), theta=(0,2*np.pi,0.1))
def foo(tx=30, ty=50, a=5, b=10, theta=np.pi/4.0):
    '''
    Creates a binary image of an ellipse and calculates the image moments.  Major (purple) and minor (green)
    principal axes are displayed.

    Parameters
    ==========
    tx, ty : translation x and y
    a, b : ellipse horizontal and vertical widths before rotation
    theta : angle of rotation (radians)
    '''

    # ellipse starts as unit circle, use world transform to define final ellipse
    ellipse = itk.EllipseSpatialObject[2].New()
    ellipse_transform = itk.AffineTransform[itk.D, 2].New()
    ellipse_transform.Scale([a, b])
    ellipse_transform.Rotate2D(theta)
    ellipse_transform.Translate([tx, ty])
    ellipse.SetObjectToWorldTransform(ellipse_transform)

    ellipse_img = itk.spatial_object_to_image_filter(input=ellipse, inside_value=1, outside_value=0, size=output_size)

    momentor = itk.ImageMomentsCalculator.New(Image=ellipse_img)
    momentor.Compute()

    centroid = momentor.GetCenterOfGravity()
    prin_axes = itk.array_from_matrix(momentor.GetPrincipalAxes())
    minor_axes = prin_axes[0]
    major_axes = prin_axes[1]

    fig, ax = plt.subplots(figsize=[8,8])
    plt.imshow(ellipse_img, cmap='gray')
    plt.scatter(centroid[0], centroid[1])

    minor_pt = centroid + minor_axes*5
    plt.plot([centroid[0], minor_pt[0]], [centroid[1], minor_pt[1]], color='green')

    major_pt = centroid + major_axes*5
    plt.plot([centroid[0], major_pt[0]], [centroid[1], major_pt[1]], color='purple')

    print(momentor)

[ ]: