Community Trekker

Joined:

May 19, 2017

## Creating Grid of Rectangles Using a For Loop

Hi,

I am trying to create an array of 24x2 rectangles in a new window. I can manually create these using the JSL commands for the graph box but I know that it can be done using a for loop which would be much quicker. I only need the rectangles to be two dimensions for now, and here is the following code that I was attempting to implement:

```y1 = 5;
y2 = 10;
win = New Window("Spine",
gb = Graph Box(
Frame Size(1000,1000),
)
);

For(i = 0, i<24, i++,
Rect(5,y1,10,y2);
y1 = y2+1;
y2 = y1+5;
gb<<reshow;
);```

but it doesn't seem to be working nor throwing me any errors. Thanks for any help.

1 ACCEPTED SOLUTION

Accepted Solutions

Super User

Joined:

Jun 22, 2012

Solution

## Re: Creating Grid of Rectangles Using a For Loop

The Graph Box() is dynamic and when coupled with your code, everytime it attemps to refresh the screen, your y values are increasing in size.  See the code below for a fix for the issue

``````Names Default To Here( 1 );
win = New Window( "Spine",
gb = Graph Box(
Frame Size( 1000, 1000 ),
Y Scale( 0, 500 ),
X Scale( 0, 500 ),
For( i = 1, i < 25, i++,
If( i == 1,
y1 = 5;
y2 = 0;
);
Rect( 45, y1, 50, y2 );
Rect( 50, y1, 55, y2 );
y2 = y1 + 1;
y1 = y1 + 6;

)
)
);``````
Jim
8 REPLIES

Super User

Joined:

Jun 22, 2012

## Re: Creating Grid of Rectangles Using a For Loop

There are a couple of issues.

1. The "rect" in your code are outside of the Graph Box() and so they do not know where to apply the rectangle.

2. Your X and Y  axis specifications go outside of the range of the Graph Box().

``````Names Default To Here( 1 );
y1 = 5;
y2 = 10;
win = New Window( "Spine",
gb = Graph Box(
Frame Size( 1000, 1000 ),
For( i = 0, i < 5, i++,
Rect( 5,y1, 10,y2);
y1 = y2 + 1;
y2 = y1 + 5;
);
)
);``````
Jim

Community Trekker

Joined:

May 19, 2017

## Re: Creating Grid of Rectangles Using a For Loop

Thanks! So far I have this, which somewhat works, but is placing the rectangles at position y~125 instead of y = 5 and y = 0. Any ideas as to why this may be?

```Names Default to Here(1);
y1 = 5;
y2 = 0;

win = New Window("Spine",
gb = Graph Box(
Frame Size(1000,1000),
Y Scale(0,500),
X Scale(0,500),
For(i=1,i<25,i++,
Rect(45,y1,50,y2);
Rect(50,y1,55,y2);
y2 = y1+1;
y1 = y1+6;

);
)
);```

Super User

Joined:

Jun 22, 2012

Solution

## Re: Creating Grid of Rectangles Using a For Loop

The Graph Box() is dynamic and when coupled with your code, everytime it attemps to refresh the screen, your y values are increasing in size.  See the code below for a fix for the issue

``````Names Default To Here( 1 );
win = New Window( "Spine",
gb = Graph Box(
Frame Size( 1000, 1000 ),
Y Scale( 0, 500 ),
X Scale( 0, 500 ),
For( i = 1, i < 25, i++,
If( i == 1,
y1 = 5;
y2 = 0;
);
Rect( 45, y1, 50, y2 );
Rect( 50, y1, 55, y2 );
y2 = y1 + 1;
y1 = y1 + 6;

)
)
);``````
Jim

Community Trekker

Joined:

May 19, 2017

## Re: Creating Grid of Rectangles Using a For Loop

thanks! works perfectly. is there any way to retrieve the points used to create the rectangles as a matrix? and is there a simple way to extend this idea to 3 dimensions using JSL's OpenGL implementation?

Super User

Joined:

Jun 22, 2012

## Re: Creating Grid of Rectangles Using a For Loop

I am not practiced with the OpenGL accessing of JMP, so I can not answer your question on how much of the graphical environment is available to it.

Concerning your other issue, I will point you to the Sample Scripts distributed with JMP, which will show you how using a 3D Scene opens up a whole world of 3D capabilities.  In particular, I will point you to the MatrixRotation and PatchEditor scripts, in which the code has feedback loops for detecting what has been drawn, and allow manipulation of those objects.

To access the samples, just go to

Help==>Sample Data

and then from the window that is opened, then select "Open the Sample Scripts Directory"

Jim
Highlighted

Staff

Joined:

Mar 21, 2013

## Re: Creating Grid of Rectangles Using a For Loop

Here's a way to make 3D cubes, without learning OpenGL, if you don't need too many. It is really plotting the outlines with points, so the number of points can get out of hand pretty quickly and make it too slow. This example uses 12K points and still performs well.

3D matrix of cubes

``````// make cube outlines using scatter plot points
dt = New Table( "cubes", New Column( "xx" ), New Column( "yy" ), New Column( "zz" ) );

make cube = function({dt,x0,x1,y0,y1,z0,z1},{x,y,z},
if(x1<x0, x=x0;x0=x1;x1=x;);
if(y1<y0, y=y0;y0=y1;y1=y;);
if(z1<z0, z=z0;z0=z1;z1=z;);
for(x=x0,x<=x1,x+=(x1-x0)/16,
);
for(y=y0,y<=y1,y+=(y1-y0)/16,
);
for(z=z0,z<=z1,z+=(z1-z0)/16,
);

);

For( xc = 20, xc <= 80, xc += 15,
For( yc = 20, yc <= 80, yc += 20,
For( zc = 20, zc <= 80, zc += 30,
make cube( dt, xc - 3, xc + 3, yc - 3, yc + 3, zc - 3, zc + 3 )
)
)
);

dt<<Scatterplot 3D(Y( :xx, :yy, :zz ));``````
Craige

Super User

Joined:

Jun 22, 2012

Cool

Jim

Staff

Joined:

Mar 21, 2013

## Re: Creating Grid of Rectangles Using a For Loop

In my example, I intended for the number of points to always be the same, but floating point round-off errors make this code

``for(y=y0,y<=y1,y+=(y1-y0)/16``

sometimes generate 16 vs 17 steps. A better way to write this would look something like this:

``````nsteps = 16;

for( iy = 0, iy <= nsteps, iy += 1,
y = y0 + iy * (y1 - y0) / nsteps;
``````

you could easily modify that loop to leave out the corner points rather than duplicating (triplicating?) them...for(iy=1, iy < nsteps, ...

Craige