<html><head><meta name="color-scheme" content="light dark"></head><body><pre style="word-wrap: break-word; white-space: pre-wrap;">package Basic.development;

import org.web3d.x3d.jsail.Core.*;
import org.web3d.x3d.jsail.EnvironmentalEffects.*;
import org.web3d.x3d.jsail.fields.*;
import org.web3d.x3d.jsail.Geometry3D.*;
import org.web3d.x3d.jsail.Grouping.*;
import org.web3d.x3d.jsail.Networking.*;
import org.web3d.x3d.jsail.Rendering.*;
import org.web3d.x3d.jsail.Scripting.*;
import org.web3d.x3d.jsail.Shape.*;
import org.web3d.x3d.jsail.Text.*;

// Javadoc metadata annotations follow, see below for X3DJSAIL Java source code.
/**
 * &lt;p&gt; X3D Geometry2D component nodes, implemented as prototypes for developmental use to provide backwards compatibility with VRML 97. Arc2D specifies a 2D linear circular arc. ArcClose2D specifies a portion of a circle. Circle2D specifies a 2D circular line. Disk2D specifies a 2D circular disk. Polyline2D specifies 2D line segments. Polypoint2D specifies 2D point array. Rectangle2D specifies a 2D rectangle. TriangleSet2D specifies 2D triangles. 2D nodes are considered particularly helpful for CADPart geometry and building user interfaces such as Heads-Up Displays (HUDs). &lt;/p&gt;
 &lt;p&gt; Related links: Catalog page &lt;a href="../../../development/Geometry2dComponentPrototypesIndex.html" target="_blank"&gt;Geometry2dComponentPrototypes&lt;/a&gt;,  source &lt;a href="../../../development/Geometry2dComponentPrototypes.java"&gt;Geometry2dComponentPrototypes.java&lt;/a&gt;, &lt;a href="https://www.web3d.org/x3d/content/examples/X3dResources.html" target="_blank"&gt;X3D Resources&lt;/a&gt;, &lt;a href="https://www.web3d.org/x3d/content/examples/X3dSceneAuthoringHints.html" target="_blank"&gt;X3D Scene Authoring Hints&lt;/a&gt;, and &lt;a href="https://www.web3d.org/x3d/content/X3dTooltips.html" target="_blank"&gt;X3D Tooltips&lt;/a&gt;. &lt;/p&gt;
	&lt;table style="color:black; border:0px solid; border-spacing:10px 0px;"&gt;
        &lt;caption&gt;Scene Meta Information&lt;/caption&gt;
		&lt;tr style="background-color:silver; border-color:silver;"&gt;
			&lt;td style="text-align:center; padding:10px 0px;"&gt;&lt;i&gt;meta tags&lt;/i&gt;&lt;/td&gt;
			&lt;td style="text-align:left;   padding:10px 0px;"&gt;&amp;nbsp; Document Metadata &lt;/td&gt;
		&lt;/tr&gt;

		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; title &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="../../../development/Geometry2dComponentPrototypes.x3d"&gt;Geometry2dComponentPrototypes.x3d&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; description &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; X3D Geometry2D component nodes, implemented as prototypes for developmental use to provide backwards compatibility with VRML 97. Arc2D specifies a 2D linear circular arc. ArcClose2D specifies a portion of a circle. Circle2D specifies a 2D circular line. Disk2D specifies a 2D circular disk. Polyline2D specifies 2D line segments. Polypoint2D specifies 2D point array. Rectangle2D specifies a 2D rectangle. TriangleSet2D specifies 2D triangles. 2D nodes are considered particularly helpful for CADPart geometry and building user interfaces such as Heads-Up Displays (HUDs). &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; creator &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; Christos Kalogrias, Don Brutzman, Ken Curtin, Duane Davis &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; created &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; 14 November 2003 &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; modified &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; 20 October 2019 &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr style="color:burntorange"&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; warning &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; These examples are complete but only used for developmental testing, not regular X3D authoring. &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; reference &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="../../../development/Geometry2dComponentExternProtos.x3d"&gt;Geometry2dComponentExternProtos.x3d&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; reference &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="../../../development/Geometry2dComponentExamples.x3d"&gt;Geometry2dComponentExamples.x3d&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; reference &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="https://www.web3d.org/specifications/X3Dv4/ISO-IEC19775-1v4-IS/Part01/components/geometry2D.html" target="_blank"&gt;https://www.web3d.org/specifications/X3Dv4/ISO-IEC19775-1v4-IS/Part01/components/geometry2D.html&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; subject &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; Geometry2D component nodes (Arc2D ArcClose2D Circle2D Disk2D Polyline2D Polypoint2D Rectangle2D TriangleSet2D) &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; identifier &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="https://www.web3d.org/x3d/content/examples/Basic/development/Geometry2dComponentPrototypes.x3d" target="_blank"&gt;https://www.web3d.org/x3d/content/examples/Basic/development/Geometry2dComponentPrototypes.x3d&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; generator &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; X3D-Edit 3.3, &lt;a href="https://savage.nps.edu/X3D-Edit" target="_blank"&gt;https://savage.nps.edu/X3D-Edit&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr&gt;
			&lt;td style="text-align:right; vertical-align: text-top;"&gt; &lt;i&gt; license &lt;/i&gt; &lt;/td&gt;
			&lt;td&gt; &lt;a href="../../../development/../license.html"&gt;../license.html&lt;/a&gt; &lt;/td&gt;
		&lt;/tr&gt;
		&lt;tr style="background-color:silver; border-color:silver;"&gt;
			&lt;td style="text-align:center;" colspan="2"&gt;  &amp;nbsp; &lt;/td&gt;
		&lt;/tr&gt;
	&lt;/table&gt;

	&lt;p&gt;
		This program uses the
		&lt;a href="https://www.web3d.org/specifications/java/X3DJSAIL.html" target="_blank"&gt;X3D Java Scene Access Interface Library (X3DJSAIL)&lt;/a&gt;.
		It has been produced using the 
		&lt;a href="https://www.web3d.org/x3d/stylesheets/X3dToJava.xslt" target="_blank"&gt;X3dToJava.xslt&lt;/a&gt;
		stylesheet
	       (&lt;a href="https://sourceforge.net/p/x3d/code/HEAD/tree/www.web3d.org/x3d/stylesheets/X3dToJava.xslt" target="_blank"&gt;version control&lt;/a&gt;)
                which is used to create Java source code from an original &lt;code&gt;.x3d&lt;/code&gt; model.
	&lt;/p&gt;

	* @author Christos Kalogrias, Don Brutzman, Ken Curtin, Duane Davis
 */

public class Geometry2dComponentPrototypes
{
	/** Default constructor to create this object. */
	public Geometry2dComponentPrototypes ()
	{
	  initialize();
	}

	/** Create and initialize the X3D model for this object. */
	public final void initialize()
	{
            try { // catch-all
  x3dModel = new X3D().setProfile(X3D.PROFILE_IMMERSIVE).setVersion(X3D.VERSION_3_0)
  .setHead(new head()
    .addMeta(new meta().setName(meta.NAME_TITLE      ).setContent("Geometry2dComponentPrototypes.x3d"))
    .addMeta(new meta().setName(meta.NAME_DESCRIPTION).setContent("X3D Geometry2D component nodes, implemented as prototypes for developmental use to provide backwards compatibility with VRML 97. Arc2D specifies a 2D linear circular arc. ArcClose2D specifies a portion of a circle. Circle2D specifies a 2D circular line. Disk2D specifies a 2D circular disk. Polyline2D specifies 2D line segments. Polypoint2D specifies 2D point array. Rectangle2D specifies a 2D rectangle. TriangleSet2D specifies 2D triangles. 2D nodes are considered particularly helpful for CADPart geometry and building user interfaces such as Heads-Up Displays (HUDs)."))
    .addMeta(new meta().setName(meta.NAME_CREATOR    ).setContent("Christos Kalogrias, Don Brutzman, Ken Curtin, Duane Davis"))
    .addMeta(new meta().setName(meta.NAME_CREATED    ).setContent("14 November 2003"))
    .addMeta(new meta().setName(meta.NAME_MODIFIED   ).setContent("20 October 2019"))
    .addMeta(new meta().setName(meta.NAME_WARNING    ).setContent("These examples are complete but only used for developmental testing, not regular X3D authoring."))
    .addMeta(new meta().setName(meta.NAME_REFERENCE  ).setContent("Geometry2dComponentExternProtos.x3d"))
    .addMeta(new meta().setName(meta.NAME_REFERENCE  ).setContent("Geometry2dComponentExamples.x3d"))
    .addMeta(new meta().setName(meta.NAME_REFERENCE  ).setContent("https://www.web3d.org/specifications/X3Dv4/ISO-IEC19775-1v4-IS/Part01/components/geometry2D.html"))
    .addMeta(new meta().setName(meta.NAME_SUBJECT    ).setContent("Geometry2D component nodes (Arc2D ArcClose2D Circle2D Disk2D Polyline2D Polypoint2D Rectangle2D TriangleSet2D)"))
    .addMeta(new meta().setName(meta.NAME_IDENTIFIER ).setContent("https://www.web3d.org/x3d/content/examples/Basic/development/Geometry2dComponentPrototypes.x3d"))
    .addMeta(new meta().setName(meta.NAME_GENERATOR  ).setContent("X3D-Edit 3.3, https://savage.nps.edu/X3D-Edit"))
    .addMeta(new meta().setName(meta.NAME_LICENSE    ).setContent("../license.html")))
  .setScene(new Scene()
    .addComments(" ==================== ")
    .addChild(new WorldInfo().setTitle("Geometry2dComponentPrototypes.x3d"))
    .addChild(new ProtoDeclare("Arc2D").setName("Arc2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(0))
        .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1.5707963265))
        .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addComments(" Only the first node counts as the node type of a prototype. This node must be a geometry node. ")
        .addChild(new IndexedLineSet("ArcIndexPoints").setDEF("ArcIndexPoints")
          .setCoord(new Coordinate("Arc3DPoints")))
        .addComments(" Any nodes after initial node in a ProtoBody is not rendered. ")
        .addChild(new Group()
          .setIS(new IS()
            .addConnect(new connect().setNodeField("metadata").setProtoField("metadata")))
          .addChild(new Script("Arc2dToFaceSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   numOfPoints = 100;

   if (radius &lt; 0)
   {
      Browser.println ('[Arc2D] Warning:  invalid value, radius=' + value + ' must instead be &gt;= 0');
   }

   if ((startAngle &lt; 0) || (startAngle &gt;= 2 * Math.PI))
   {
	Browser.println ('[Arc2D] Warning: startAngle=' + startAngle + ' must be within range [0..2pi)'); // (]
   }

   if ((endAngle &lt; 0) || (endAngle &gt;= 2 * Math.PI))
   {
	Browser.println ('[Arc2D] Warning: endAngle=' + endAngle + ' must be within range [0..2pi)'); // (]
   }

   // equal startAngle, endAngle means draw full circle.
   // high out-of-range endAngle is OK for local computation.
   if (startAngle &gt;= endAngle)
      endAngle = endAngle + 2 * Math.PI;

   differAng = Math.abs((endAngle - startAngle)) / numOfPoints;

   for (i = 0; i &lt;= numOfPoints; i++)
   {
	arcSet3d[i] = new SFVec3f (radius * Math.cos(startAngle + i * differAng), radius * Math.sin(startAngle + i * differAng), 0.0);
        arcIndexSet3d[i] = i;
   }

} // initialize
""")
            .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("arcSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("arcIndexSet3d").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("startAngle").setProtoField("startAngle"))
              .addConnect(new connect().setNodeField("endAngle").setProtoField("endAngle"))
              .addConnect(new connect().setNodeField("radius").setProtoField("radius"))))
          .addChild(new ROUTE().setFromNode("Arc2dToFaceSet3d").setFromField("arcSet3d").setToNode("Arc3DPoints").setToField("point"))
          .addChild(new ROUTE().setFromNode("Arc2dToFaceSet3d").setFromField("arcIndexSet3d").setToNode("ArcIndexPoints").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("ArcClose2D").setName("ArcClose2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(0))
        .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1.5707963265))
        .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1))
        .addField(new field().setName("closureType").setType(field.TYPE_SFSTRING).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue("PIE"))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedFaceSet("ArcPointFaceIndex").setDEF("ArcPointFaceIndex")
          .setCoord(new Coordinate("ArcClose2DFaceCoordinate")))
        .addChild(new Group()
          .addChild(new Script("ArcClose2dToFaceSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   if (radius &lt; 0)
   {
      Browser.println ('[ArcClose2D] Warning:  invalid value, radius=' + value + ' must instead be &gt;= 0');
   }

   if ((startAngle &lt; 0) || (startAngle &gt;= 2 * Math.PI))
   {
	Browser.println ('[ArcClose2D] Warning: startAngle=' + startAngle + ' must be within range [0..2pi)'); //(]
   }

   if ((endAngle&lt; 0) || (endAngle&gt;= 2 * Math.PI))
   {
	Browser.println ('[ArcClose2D] Warning: endAngle=' + endAngle+ ' must be within range [0..2pi)'); // (]
    }

    // equal startAngle, endAngle means draw full circle.
    // high out-of-range endAngle is OK for local computation.
   if (startAngle &gt;= endAngle)
      endAngle = endAngle + 2*Math.PI;

   numOfPoints = 100;
   differAng = Math.abs((endAngle - startAngle))/numOfPoints;

   for ( i=0 ; i&lt;=numOfPoints ; i++)
   {
	if ( i == numOfPoints)
             arcSet3d[i] = new SFVec3f (0.0, 0.0, 0.0);
        else
             arcSet3d[i] = new SFVec3f ( radius*Math.cos(startAngle + i*differAng), radius*Math.sin(startAngle + i*differAng), 0.0 );
   }

   k=0;
   if (closureType =='PIE')
       for ( i=0 ; i&lt;numOfPoints ; i++)
       {
        	pointIndex[k]   = numOfPoints;
        	pointIndex[k+1] = i;
        	pointIndex[k+2] = i + 1;
        	pointIndex[k+3]   = numOfPoints;
        	pointIndex[k+4] = -1;
        k=k+5;
	}
   else
       for ( i=0 ; i&lt;numOfPoints-1 ; i++)
       {
              pointIndex[k]   = 0;
              pointIndex[k+1] = i;
              pointIndex[k+2] = i + 1;
              pointIndex[k+3]   = 0;
              pointIndex[k+4] = -1;
        k=k+5;
	}

} // initialize
""")
            .addField(new field().setName("closureType").setType(field.TYPE_SFSTRING).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("arcSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("pointIndex").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("closureType").setProtoField("closureType"))
              .addConnect(new connect().setNodeField("startAngle").setProtoField("startAngle"))
              .addConnect(new connect().setNodeField("endAngle").setProtoField("endAngle"))
              .addConnect(new connect().setNodeField("radius").setProtoField("radius"))))
          .addChild(new ROUTE().setFromNode("ArcClose2dToFaceSet3d").setFromField("arcSet3d").setToNode("ArcClose2DFaceCoordinate").setToField("point"))
          .addChild(new ROUTE().setFromNode("ArcClose2dToFaceSet3d").setFromField("pointIndex").setToNode("ArcPointFaceIndex").setToField("set_coordIndex")))))
    .addComments(" ArcClose2DUnfilled also provided since FillProperties not available in VRML 97 ")
    .addChild(new ProtoDeclare("ArcClose2DUnfilled").setName("ArcClose2DUnfilled")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(0))
        .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1.5707963265))
        .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1))
        .addField(new field().setName("closureType").setType(field.TYPE_SFSTRING).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue("PIE"))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedLineSet("ArcPointLineIndex").setDEF("ArcPointLineIndex")
          .setCoord(new Coordinate("ArcClose2DLineCoordinate")))
        .addChild(new Group()
          .addChild(new Script("ArcClose2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{

   if (radius &lt; 0)
   {
      Browser.println ('[ArcCloseUnfilled2D] Warning:  invalid value, radius=' + value + ' must instead be &gt;= 0');
   }

   if ((startAngle &lt; 0) || (startAngle &gt;= 2 * Math.PI))
   {
	Browser.println ('[ArcCloseUnfilled2D] Warning: startAngle=' + startAngle + ' must be within range [0..2pi)'); //(]
   }

   if ((endAngle&lt; 0) || (endAngle&gt;= 2 * Math.PI))
   {
	Browser.println ('[ArcCloseUnfilled2D] Warning: endAngle=' + endAngle+ ' must be within range [0..2pi)'); //(]
    }

    // equal startAngle, endAngle means draw full circle.
    // high out-of-range endAngle is OK for local computation.
   if (startAngle &gt;= endAngle)
      endAngle = endAngle + 2*Math.PI;

   numOfPoints = 100;
   differAng = Math.abs((endAngle - startAngle))/numOfPoints;

   for ( i=0 ; i&lt;=numOfPoints +1 ; i++)
   {
	if ( i == numOfPoints +1)
             arcSet3d[i] = new SFVec3f (0.0, 0.0, 0.0);
        else
             arcSet3d[i] = new SFVec3f ( radius*Math.cos(startAngle + i*differAng), radius*Math.sin(startAngle + i*differAng), 0.0 );
   }

   if (closureType =='CHORD')
   {
	for ( i=0 ; i&lt;=numOfPoints +1 ; i++)
	{
        	if ( i == numOfPoints +1)
             		pointIndex[i] = 0.0;
        	else
             		pointIndex[i] = i;
	}
   }
   else
   {
	for ( i=0 ; i&lt;=numOfPoints +1 ; i++)
	{
         pointIndex[i] = i;
	}
         pointIndex[i] = 0.0;
   }

} // initialize
""")
            .addField(new field().setName("closureType").setType(field.TYPE_SFSTRING).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("startAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("endAngle").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("arcSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("pointIndex").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("closureType").setProtoField("closureType"))
              .addConnect(new connect().setNodeField("startAngle").setProtoField("startAngle"))
              .addConnect(new connect().setNodeField("endAngle").setProtoField("endAngle"))
              .addConnect(new connect().setNodeField("radius").setProtoField("radius"))))
          .addChild(new ROUTE().setFromNode("ArcClose2dToLineSet3d").setFromField("arcSet3d").setToNode("ArcClose2DLineCoordinate").setToField("point"))
          .addChild(new ROUTE().setFromNode("ArcClose2dToLineSet3d").setFromField("pointIndex").setToNode("ArcPointLineIndex").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("Circle2D").setName("Circle2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedLineSet("Circ3DPointsIndex").setDEF("Circ3DPointsIndex")
          .setCoord(new Coordinate("Circ3DPoints")))
        .addChild(new Group()
          .addChild(new Script("Circ2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{
    if (radius &lt; 0)
   {
      Browser.println ('[Circle2D] Warning:  invalid value, radius=' + value + ' must instead be &gt;= 0');
   }


   numOfPoints = 100;
   differAng = 2*Math.PI/numOfPoints;

   for ( i=0 ; i&lt;=numOfPoints ; i++)
   {
	circSet3d[i] = new SFVec3f ( radius*Math.cos(i*differAng), radius*Math.sin(i*differAng), 0.0 );
        circIndexSet3d[i] = i;
   }

} // initialize
""")
            .addField(new field().setName("radius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("circSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("circIndexSet3d").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("radius").setProtoField("radius"))))
          .addChild(new ROUTE().setFromNode("Circ2dToLineSet3d").setFromField("circSet3d").setToNode("Circ3DPoints").setToField("point"))
          .addChild(new ROUTE().setFromNode("Circ2dToLineSet3d").setFromField("circIndexSet3d").setToNode("Circ3DPointsIndex").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("Disk2D").setName("Disk2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("innerRadius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(0))
        .addField(new field().setName("outerRadius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(1))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedFaceSet("DiskPointsIndex").setDEF("DiskPointsIndex")
          .setCoord(new Coordinate("Disk3DPoints")))
        .addChild(new Group()
          .addChild(new Script("Disk2dToFaceSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   if (innerRadius &lt; 0)
   {
      Browser.println ('[Disk2D] Warning:  invalid value, innerRadius=' + value + ' must instead be &gt;= 0');
   }

   if (outerRadius &lt; 0)
   {
      Browser.println ('[Disk2D] Warning:  invalid value, outerRadius=' + value + ' must instead be &gt;= 0');
   }



   numOfPoints    = 100.0;
   diskSet3d      = new MFVec3f();
   diskIndexSet3d = new MFInt32();
   differAng = 2 * Math.PI/numOfPoints;


   for ( i=0 ; i&lt;2*numOfPoints ; i++)
   {
        if ( i&lt;numOfPoints)
	     diskSet3d[i] = new SFVec3f ( innerRadius*Math.cos(i*differAng), innerRadius*Math.sin(i*differAng), 0.0 );
        else
             diskSet3d[i] = new SFVec3f ( outerRadius*Math.cos((i-numOfPoints-1.0)*differAng), outerRadius*Math.sin((i-numOfPoints-1.0)*differAng), 0.0 );
   }


   k=0;
   for (i=0 ; i&lt;numOfPoints ; i++)
   {
        diskIndexSet3d[k]   = i;
        diskIndexSet3d[k+1] = i + numOfPoints;
        diskIndexSet3d[k+2] = i + numOfPoints + 1;
        diskIndexSet3d[k+3]   = i;
        diskIndexSet3d[k+4] = -1;
        diskIndexSet3d[k+5] = i+1;
        diskIndexSet3d[k+6] = i ;
        diskIndexSet3d[k+7] = i + numOfPoints +1;
        diskIndexSet3d[k+8] = i +1;
        diskIndexSet3d[k+9] = -1;

        if (i == numOfPoints-1)
        {
        diskIndexSet3d[k]   = i;
        diskIndexSet3d[k+1] = i + numOfPoints;
        diskIndexSet3d[k+2] = numOfPoints;
        diskIndexSet3d[k+3]   = i;
        diskIndexSet3d[k+4] = -1;
        diskIndexSet3d[k+5] = 0;
        diskIndexSet3d[k+6] = i;
        diskIndexSet3d[k+7] = numOfPoints;
        diskIndexSet3d[k+8] = 0;
        diskIndexSet3d[k+9] = -1;
        }
   k=k+10;
   }

} // initialize
""")
            .addField(new field().setName("innerRadius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("outerRadius").setType(field.TYPE_SFFLOAT).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("diskSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("diskIndexSet3d").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("innerRadius").setProtoField("innerRadius"))
              .addConnect(new connect().setNodeField("outerRadius").setProtoField("outerRadius"))))
          .addChild(new ROUTE().setFromNode("Disk2dToFaceSet3d").setFromField("diskSet3d").setToNode("Disk3DPoints").setToField("point"))
          .addChild(new ROUTE().setFromNode("Disk2dToFaceSet3d").setFromField("diskIndexSet3d").setToNode("DiskPointsIndex").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("Polyline2D").setName("Polyline2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("lineSegments").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedLineSet("LinesSegmentsIndexPoints").setDEF("LinesSegmentsIndexPoints")
          .setCoord(new Coordinate("LineSegments3DPoints")))
        .addChild(new Group()
          .addChild(new Script("LineSegments2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   for ( i=0 ; i&lt;lineSegments.length ; i++)
   {
          lineSegments3D[i] = new SFVec3f ( lineSegments[i].x, lineSegments[i].y, 0.0 );
          lineSegmentsIndex[i] = i;
   }

     lineSegmentsIndex[i] = -1;

} // initialize
""")
            .addField(new field().setName("lineSegments").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("lineSegments3D").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("lineSegmentsIndex").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("lineSegments").setProtoField("lineSegments"))))
          .addChild(new ROUTE().setFromNode("LineSegments2dToLineSet3d").setFromField("lineSegments3D").setToNode("LineSegments3DPoints").setToField("point"))
          .addChild(new ROUTE().setFromNode("LineSegments2dToLineSet3d").setFromField("lineSegmentsIndex").setToNode("LinesSegmentsIndexPoints").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("Polypoint2D").setName("Polypoint2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("point").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new PointSet()
          .setCoord(new Coordinate("Points3D")))
        .addChild(new Group()
          .addChild(new Script("Points2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{

   for ( i=0 ; i&lt;point.length ; i++)
   {
          points3D[i] = new SFVec3f ( point[i].x, point[i].y, 0.0 );
   }

} // initialize
""")
            .addField(new field().setName("point").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("points3D").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("point").setProtoField("point"))))
          .addChild(new ROUTE().setFromNode("Points2dToLineSet3d").setFromField("points3D").setToNode("Points3D").setToField("point")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("Rectangle2D").setName("Rectangle2D").setAppinfo("Default filled matching default FillProperties filled=true.")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("size").setType(field.TYPE_SFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(new SFVec2f(2.0,2.0)))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedFaceSet().setSolid(false).setCoordIndex(new int[] {0,1,2,0,-1,2,3,0,2})
          .setCoord(new Coordinate("RectanglePoints")))
        .addChild(new Group()
          .addChild(new Script("Rect2dToFaceSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   xDim = size[0];
   yDim = size[1];

   pointSet3d[0] = new SFVec3f ( (-xDim / 2.0), (yDim / 2.0), 0.0 );
   pointSet3d[1] = new SFVec3f ( (-xDim / 2.0), (-yDim / 2.0), 0.0 );
   pointSet3d[2] = new SFVec3f ( (xDim / 2.0), (-yDim / 2.0), 0.0 );
   pointSet3d[3] = new SFVec3f ( (xDim / 2.0), (yDim / 2.0), 0.0 );

} // initialize
""")
            .addField(new field().setName("size").setType(field.TYPE_SFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("pointSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("fillNoFillSelection").setType(field.TYPE_SFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("size").setProtoField("size"))))
          .addChild(new ROUTE().setFromNode("Rect2dToFaceSet3d").setFromField("pointSet3d").setToNode("RectanglePoints").setToField("point")))))
    .addComments(" Rectangle2DUnfilled also provided since FillProperties not available in VRML 97 ")
    .addChild(new ProtoDeclare("Rectangle2DUnfilled").setName("Rectangle2DUnfilled")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("size").setType(field.TYPE_SFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(new SFVec2f(2.0,2.0)))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedLineSet().setCoordIndex(new int[] {0,1,2,3,0})
          .setCoord(new Coordinate("RectanglePointsLine")))
        .addChild(new Group()
          .addChild(new Script("Rect2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   xDim = size[0];
   yDim = size[1];

   pointSet3d[0] = new SFVec3f ( (-xDim / 2.0), (yDim / 2.0), 0.0 );
   pointSet3d[1] = new SFVec3f ( (-xDim / 2.0), (-yDim / 2.0), 0.0 );
   pointSet3d[2] = new SFVec3f ( (xDim / 2.0), (-yDim / 2.0), 0.0 );
   pointSet3d[3] = new SFVec3f ( (xDim / 2.0), (yDim / 2.0), 0.0 );

} // initialize
""")
            .addField(new field().setName("size").setType(field.TYPE_SFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("pointSet3d").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("fillNoFillSelection").setType(field.TYPE_SFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("size").setProtoField("size"))))
          .addChild(new ROUTE().setFromNode("Rect2dToLineSet3d").setFromField("pointSet3d").setToNode("RectanglePointsLine").setToField("point")))))
    .addComments(" ==================== ")
    .addChild(new ProtoDeclare("TriangleSet2D").setName("TriangleSet2D")
      .setProtoInterface(new ProtoInterface()
        .addField(new field().setName("vertices").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
        .addField(new field().setName("solid").setType(field.TYPE_SFBOOL).setAccessType(field.ACCESSTYPE_INITIALIZEONLY).setValue(false))
        .addField(new field().setName("metadata").setType(field.TYPE_SFNODE).setAccessType(field.ACCESSTYPE_INPUTOUTPUT).setAppinfo("Metadata node only")
          .addComments(" default NULL ")))
      .setProtoBody(new ProtoBody()
        .addChild(new IndexedFaceSet("TriangleSetIndexPoints").setDEF("TriangleSetIndexPoints").setSolid(false)
          .setCoord(new Coordinate("TriangleSet3DPoints")))
        .addChild(new Group()
          .addChild(new Script("TriangleSet2dToLineSet3d").setSourceCode("""
ecmascript:

function initialize()
{
   numbOfTriangles = Math.floor(vertices.length/3);

   for ( i=0 ; i&lt;3*numbOfTriangles ; i++)
   {
          triangleSet3D[i] = new SFVec3f ( vertices[i].x, vertices[i].y, 0.0 );
   }

   k=0;
   for (i=0; i&lt;numbOfTriangles; i++)
   {
        triangleSetIndex[k] = k - i ;
        triangleSetIndex[k+1] = k - i + 1 ;
        triangleSetIndex[k+2] = k - i + 2 ;
        triangleSetIndex[k+3] = -1 ;

        k=k+4;
    }

} // initialize
""")
            .addField(new field().setName("vertices").setType(field.TYPE_MFVEC2F).setAccessType(field.ACCESSTYPE_INITIALIZEONLY))
            .addField(new field().setName("triangleSet3D").setType(field.TYPE_MFVEC3F).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .addField(new field().setName("triangleSetIndex").setType(field.TYPE_MFINT32).setAccessType(field.ACCESSTYPE_OUTPUTONLY))
            .setIS(new IS()
              .addConnect(new connect().setNodeField("vertices").setProtoField("vertices"))))
          .addChild(new ROUTE().setFromNode("TriangleSet2dToLineSet3d").setFromField("triangleSet3D").setToNode("TriangleSet3DPoints").setToField("point"))
          .addChild(new ROUTE().setFromNode("TriangleSet2dToLineSet3d").setFromField("triangleSetIndex").setToNode("TriangleSetIndexPoints").setToField("set_coordIndex")))))
    .addComments(" ==================== ")
    .addChild(new Background().setGroundColor(new MFColor(new double[] {0.25,0.25,0.25})).setSkyColor(new MFColor(new double[] {0.25,0.25,0.25})))
    .addChild(new Anchor("LinkToExamples").setDescription("link to examples").setUrl(new String[] {"Geometry2dComponentExternProtos.x3d","https://www.web3d.org/x3d/content/examples/Basic/development/Geometry2dComponentExternProtos.x3d","Geometry2dComponentExamples.wrl","https://www.web3d.org/x3d/content/examples/Basic/development/Geometry2dComponentExamples.wrl"})
      .addChild(new Shape()
        .setAppearance(new Appearance()
          .setMaterial(new Material().setDiffuseColor(0.8,0.6,0.2)))
        .setGeometry(new Text().setString(new String[] {"Geometry2dComponentPrototypes","is a developmental file.","Click this text to view","Geometry2dComponentExamples"})
          .setFontStyle(new FontStyle().setJustify(FontStyle.JUSTIFY_MIDDLE_MIDDLE).setSize(0.75))))));
            }
            catch (Exception ex)
            {       
                System.err.println ("*** Further hints on X3DJSAIL errors and exceptions at");
                System.err.println ("*** https://www.web3d.org/specifications/java/X3DJSAIL.html");
                throw (ex);
            }
	}
	// end of initialize() method

	/** The initialized model object, created within initialize() method. */
	private X3D x3dModel;

	/** 
	 * Provide a 
	 * &lt;a href="https://dzone.com/articles/java-copy-shallow-vs-deep-in-which-you-will-swim" target="_blank"&gt;shallow copy&lt;/a&gt;
	 * of the X3D model.
	 * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/Core/X3D.html"&gt;X3D&lt;/a&gt;
	 * @return Geometry2dComponentPrototypes model
	 */
	public X3D getX3dModel()
	{	  
		return x3dModel;
	}
	   
    /** 
     * Default main() method provided for test purposes, uses CommandLine to set global ConfigurationProperties for this object.
     * @param args array of input parameters, provided as arguments
     * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/Core/X3D.html#handleArguments-java.lang.String:A-"&gt;X3D.handleArguments(args)&lt;/a&gt;
     * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/Core/X3D.html#validationReport--"&gt;X3D.validationReport()&lt;/a&gt;
     * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/CommandLine.html"&gt;CommandLine&lt;/a&gt;
     * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/CommandLine.html#USAGE"&gt;CommandLine.USAGE&lt;/a&gt;
     * @see &lt;a href="https://www.web3d.org/specifications/java/javadoc/org/web3d/x3d/jsail/ConfigurationProperties.html"&gt;ConfigurationProperties&lt;/a&gt;
     */
    public static void main(String args[])
    {
        System.out.println("Build this X3D model, showing validation diagnostics...");
        X3D thisExampleX3dModel = new Geometry2dComponentPrototypes().getX3dModel();
//      System.out.println("X3D model construction complete.");
	
        // next handle command line arguments
        boolean hasArguments = (args != null) &amp;&amp; (args.length &gt; 0);
        boolean validate = true; // default
        boolean argumentsLoadNewModel = false;
        String  fileName = new String();

        if (args != null)
        {
                for (String arg : args)
                {
                        if (arg.toLowerCase().startsWith("-v") || arg.toLowerCase().contains("validate"))
                        {
                                validate = true; // making sure
                        }
                        if (arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_X3D) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_CLASSICVRML) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_X3DB) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_VRML97) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_EXI) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_GZIP) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_ZIP) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_HTML) ||
                                arg.toLowerCase().endsWith(X3D.FILE_EXTENSION_XHTML))
                        {
                                argumentsLoadNewModel = true;
                                fileName = arg;
                        }
                }
        }
        if      (argumentsLoadNewModel)
                System.out.println("WARNING: \"Basic.development.Geometry2dComponentPrototypes\" model invocation is attempting to load file \"" + fileName + "\" instead of simply validating itself... file loading ignored.");
        else if (hasArguments) // if no arguments provided, this method produces usage warning
                thisExampleX3dModel.handleArguments(args);
	
        if (validate)
        {
            //  System.out.println("--- TODO fix duplicated outputs ---"); // omit when duplicated outputs problem is solved/refactored
		String validationResults = thisExampleX3dModel.validationReport();
            //  System.out.println("-----------------------------------"); // omit when duplicated outputs problem is solved/refactored
                System.out.print("Basic.development.Geometry2dComponentPrototypes self-validation test confirmation: ");
                if (!validationResults.equals("success"))
                    System.out.println();
                System.out.println(validationResults.trim());

                // experimental: test X3DJSAIL output files
                // development/Geometry2dComponentPrototypes_JavaExport.* file validation is checked when building X3D Example Archives
                String filenameX3D  = "development/Geometry2dComponentPrototypes_JavaExport.x3d"; 
                String filenameX3DV = "development/Geometry2dComponentPrototypes_JavaExport.x3dv"; 
                String filenameJSON = "development/Geometry2dComponentPrototypes_JavaExport.json";
                thisExampleX3dModel.toFileX3D        (filenameX3D);
                thisExampleX3dModel.toFileClassicVRML(filenameX3DV);
// TODO         thisExampleX3dModel.toFileJSON       (filenameJSON);
        }
    }
}
</pre></body></html>