How to resolve the algorithm Sutherland-Hodgman polygon clipping step by step in the Ruby programming language

Published on 12 May 2024 09:40 PM

How to resolve the algorithm Sutherland-Hodgman polygon clipping step by step in the Ruby programming language

Table of Contents

Problem Statement

The   Sutherland-Hodgman clipping algorithm   finds the polygon that is the intersection between an arbitrary polygon (the “subject polygon”) and a convex polygon (the “clip polygon”). It is used in computer graphics (especially 2D graphics) to reduce the complexity of a scene being displayed by eliminating parts of a polygon that do not need to be displayed.

Take the closed polygon defined by the points: and clip it by the rectangle defined by the points: Print the sequence of points that define the resulting clipped polygon.

Display all three polygons on a graphical surface, using a different color for each polygon and filling the resulting polygon. (When displaying you may use either a north-west or a south-west origin, whichever is more convenient for your display mechanism.)

Let's start with the solution:

Step by Step solution about How to resolve the algorithm Sutherland-Hodgman polygon clipping step by step in the Ruby programming language

This Ruby code implements the Sutherland-Hodgman algorithm, which is used to clip a polygon (the "subject polygon") against another polygon (the "clip polygon"). Polygon clipping is used in computer graphics to determine which parts of a shape are visible within a given viewing area or window.

Here's a detailed explanation of the code:

  1. Point Struct:

    • The code defines a Point struct using Struct.new to represent points in the polygons. Each point has two fields: x and y.
    • The to_s method is defined within the struct to provide a string representation of the point as "(x, y)".
  2. sutherland_hodgman Function:

    • This function takes two parameters: subjectPolygon and clipPolygon, which are arrays of Point objects representing the polygons to be clipped.

    • Inside the function, there are a few inner functions defined as procs to reduce the argument passing to "inside" and "intersection":

      • inside: This proc takes a point p as an argument and returns true if the point is inside the current clip edge defined by cp1 and cp2. It uses a cross-product calculation to determine if the point is on the left side of the edge.
      • intersection: This proc takes no arguments and returns the intersection point between the current subject edge defined by s and e and the current clip edge defined by cp1 and cp2. It uses a line-line intersection calculation to find the intersection point.
    • The function initializes outputList with the subjectPolygon and iterates over the clipPolygon vertices.

    • For each cp2 in the clipPolygon, it initializes inputList with the current outputList.

    • It then initializes outputList as an empty array and s with the last point in inputList.

    • It iterates over each e in inputList and checks if e is inside the current clip edge using the inside proc.

    • If e is inside, it adds the intersection point between the current subject edge and the current clip edge to outputList unless s is also inside the current clip edge. It then adds e to outputList.

    • If s is inside the current clip edge, it adds the intersection point between the current subject edge and the current clip edge to outputList.

    • It updates s to e.

    • Finally, it updates cp1 to cp2.

    • The function returns the outputList, which contains the clipped polygon.

  3. Sample Polygons and Clipping:

    • The code defines subjectPolygon as an array of points representing a subject polygon with 9 vertices.
    • It defines clipPolygon as an array of points representing a clip polygon with 4 vertices.
    • It calls the sutherland_hodgman function with subjectPolygon and clipPolygon and prints the result, which is an array of Point objects representing the clipped polygon.

Source code in the ruby programming language

Point = Struct.new(:x,:y) do
  def to_s; "(#{x}, #{y})" end
end

def sutherland_hodgman(subjectPolygon, clipPolygon)
  # These inner functions reduce the argument passing to
  # "inside" and "intersection".
  cp1, cp2, s, e = nil
  inside = proc do |p|
    (cp2.x-cp1.x)*(p.y-cp1.y) > (cp2.y-cp1.y)*(p.x-cp1.x)
  end
  intersection = proc do
    dcx, dcy = cp1.x-cp2.x, cp1.y-cp2.y
    dpx, dpy = s.x-e.x, s.y-e.y
    n1 = cp1.x*cp2.y - cp1.y*cp2.x
    n2 = s.x*e.y - s.y*e.x
    n3 = 1.0 / (dcx*dpy - dcy*dpx)
    Point[(n1*dpx - n2*dcx) * n3, (n1*dpy - n2*dcy) * n3]
  end
  
  outputList = subjectPolygon
  cp1 = clipPolygon.last
  for cp2 in clipPolygon
    inputList = outputList
    outputList = []
    s = inputList.last
    for e in inputList
      if inside[e]
        outputList << intersection[] unless inside[s]
        outputList << e
      elsif inside[s]
        outputList << intersection[]
      end
      s = e
    end
    cp1 = cp2
  end
  outputList
end

subjectPolygon = [[50, 150], [200, 50], [350, 150], [350, 300],
                  [250, 300], [200, 250], [150, 350], [100, 250],
                  [100, 200]].collect{|pnt| Point[*pnt]}
 
clipPolygon = [[100, 100], [300, 100], [300, 300], [100, 300]].collect{|pnt| Point[*pnt]}
 
puts sutherland_hodgman(subjectPolygon, clipPolygon)


  

You may also check:How to resolve the algorithm Archimedean spiral step by step in the Python programming language
You may also check:How to resolve the algorithm A+B step by step in the M2000 Interpreter programming language
You may also check:How to resolve the algorithm Zeckendorf number representation step by step in the Klingphix programming language
You may also check:How to resolve the algorithm Multifactorial step by step in the Swift programming language
You may also check:How to resolve the algorithm Floyd-Warshall algorithm step by step in the SequenceL programming language