# Better grid Performance

Hello there,

I createt a scaleable grid, that have no funktion at the Moment.
But it is Scaleable and you can move it.

Now my problem.

I want to generate a Grid with 1000*1000 rectangles (or more), but 1 000 000 rectangles are very much.
If i want to scale or transform the grid, I have only about five FPS
Is there a way to make that I reach 30 FPS?

Down there is the Code.
Thank you very much.

``````// Szize of one rectangle
int  size = 50,t;
float s,tr, tx, ty, tix, tiy;
//Grid size
int x = 1000, y = 1000;

class Gitter{

float numx, numy, size, col,mode,px,py,i;
//I need them later, but at the moment hey have no function
int n1, n2, n3, n4, n5, n6, n7, n8, i2;

Gitter(float id, float NUMX, float NUMY, float  SIZE){
numx = NUMX;
numy = NUMY;
size = SIZE;
i = id;

}

void Draw(){
rectMode(CENTER);
noStroke();fill(255);rect (numx * size +10,numy * size + 10, size-1 , size-1 );
}
}
Gitter[] gitter = new Gitter[x*y];

void setup(){
size(1600,800);

int  I = 0;
int ix,iy;
s = 1;
for (iy = 0;iy < y; iy = iy+1){
for(ix = 0;ix < x; ix = ix+1){
gitter[I] = new Gitter(I++,ix, iy, size);
}
}
tr = 0;

}
void draw(){

//scaling andtranslations
if (keyPressed){
if (keyCode == UP ){
s=s+0.05;
}
else if (keyCode == DOWN ){
s=s-0.05;
}
}

if ((mousePressed) && (mouseButton == LEFT)) {
if (tr == 0){
tr =  2;
tix = tx;
tiy = ty;
tix = tix - mouseX*(1/s);
tiy = tiy - mouseY*(1/s);
}
else{
tx = (1/s)*mouseX + tix;
ty = (1/s)*mouseY + tiy;

tr = 3;

}
}
if (tr > 0){
tr = tr - 1;
}

scale(s);
translate(tx,ty);
background(0);

int ix,iy;int I=0;
//draw grid
for (iy = 0;iy < y; iy = iy+1){
for(ix = 0;ix < x; ix = ix+1){
gitter[I++].Draw();

}
}

}
``````

If anyone have an idea, please let me here it

Maybe you ask yourself, why I want to create a grid like this.
That’s just training.
I have a lot of ideas for them I have to create more objects. Not rectangles, but different objects.
I hope, that I learn to understand, how I can create them without a large framedrop and without a loop, which have to run every time it called one million times

why not play and make a benchmark list FPS ( print like

``````  void draw() {
background(0);
fill(255);
text(nf(frameRate,1,1),10,10);
``````
• grid 100 500 1000
• your program has the loop structure and the JOB: draw rect()

i see that when i disable the rect() in the class draw, FPS only get 80% ( 45 of 60FPS)…

• change the canvas size has what effect…

a small thing can help, its a

``````void setup() {
noSmooth();

``````

i encourage you to test the limits of your hardware / OS and Processing,
but soon you might see that that Gigantomania
like your size(3000,2000) and grid 1000*1000
not really teach you coding, and that is what it is about here.

Thank you very much, I will try it out

@kll
An other idea, is it possible, that I just generate the rectangles, which I display at the moment?
I mean, that the program generates new rectangles, if I zoom out?

now you do translate and scale ( move and zoom )
what is a killer if you want use like the color change click on rectangle
( i give you that code already but actually you go backward )

instead you can change x,y,w,h ( or even grid ) and regenerate the grid
after keypress

as i play with that i see already a problem,
a regeneration of the class array deletes also the knowledge of which one was clicked …
so for both ways need to separate the size and the clicked array

@kll
And it teaches me coating in the point that I will learn, to work with much objects.
My later goal is, to create an small ai.
And for this I want to lern, how I generate a large number of objects like neurons, ais or anything like this, and how I can manage every object that uses the ai sepperately if I create more than one at the same time

I saw your code and I understood how it worked, but my goal is not to create a large grid with one million rectangles, my goal is to learn, how I can work with one million objects how fast how possible.
I want to learn, If I should use sub programs and if yes why. The how is the other question, but why I should do this or something other and for what can I use something like a class and what not.

now actually i doubt that you run my
example from

need to click on the

example

to see the code

Use renderer FX2D for size(): Processing.org/reference/size_.html

@GoToLoop thank you, I will try it out.

@kll I ran your code and I found it great that the size of the rectangles scales with the size of the rows and the size of the screen.
But I am a beginner and I have to learn, that scaling isn’t the best idea.

And that is a very good idea and I want to try it out.
I think, that this is the solution for my grid.

this version has changed moving and sizing

``````// https://discourse.processing.org/t/scalable-grid-with-rectangles/7256
// https://discourse.processing.org/t/better-grid-performance/7314
// test FPS on RPI
// grid 8     FPS 59
// grid 100   FPS 6.7  ( disable rect get FPS 45 )  ( noSmooth FPS 9 )
// grid 100   FPS 5.4  ( size(1200,1200) )
// grid 500   FPS go down slowly ?
// test FX2D not run on RPI

int x = 12, y = x, w = 5, h = w, grid = 100, many = grid*grid;
boolean auto = false;//true;
boolean shownum = false;    // key [n]
boolean showstroke = true;
boolean showFPS = true;
// color setup:
color bg  = color(200, 200, 0);
color stk = color(0, 0, 200);
color fillsel = color(0, 200, 0);
color fillnsel= color(200, 0, 200);

Myrect[] myrects= new Myrect[many];

void setup() {
size(800, 520);
noSmooth();
set_grid();
println("use: mouse LEFT to select, mouse RIGHT to deselect");
println("key UP DOWN RIGTH LEFT for position");
println("key +  -  for grid size");
println("key n toggle shownumber");
}

void draw() {
background(bg);
fill(0);
if (showFPS ) text(nf(frameRate, 1, 1), 10, 10);
for (int i = 0; i < many; i++) myrects[i].drawit();               // draw each rect ( and check on mouse over + click )
}

class Myrect {
int x, y, id;//, w, h; from global
boolean selected=false;
Myrect (int x, int y, int id) {
this.x = x;
this.y = y;
this.id = id;
}
void drawit() {
if ( showstroke ) stroke(stk);
else noStroke();
if ( selected ) fill(fillsel);
else            fill(fillnsel);
rect(x, y, w, h);
fill(0);   // black text
if (shownum) text(id, x+w/4, y+h/3);
sel();
}
boolean over() {
return( x < mouseX && mouseX < x+w && y < mouseY && mouseY < y+h );
}
void sel() {
if ( over() ) {
if (  selected && mousePressed && mouseButton == RIGHT) selected=false;
if ( !selected && mousePressed && mouseButton == LEFT)  selected=true;
}
}
}

void set_wh() {
// use x,y,grid as master and auto adjust rectangles (w,h) to window:
println(" width= "+width+", height= "+height+", grid= "+grid);
w = ( width  - 2 * x ) / grid;
println(" w= "+w+", x= "+x+", ( grid * w + 2 * x )= "+(grid*w+2*x));
h = ( height - 2 * y ) / grid;
println(" h= "+h+", y= "+y+", ( grid * h + 2 * y )= "+(grid*h+2*y));
}

void set_grid() {
if ( auto ) set_wh();
for (int i = 0; i < many; i++)  myrects[i]=new Myrect(x+(i%grid)*w, y+(floor(i/grid))*h, i);
}

void keyPressed() {
if ( keyCode == UP )         y--;
else if ( keyCode == DOWN )  y++;
else if ( keyCode == LEFT )  x--;
else if ( keyCode == RIGHT ) x++;
else if ( key     == '+' )   w++;
else if ( key     == '-' )   w--;
h=w;
set_grid();

if ( key == 'n' ) shownum = !shownum;
}

``````
1 Like

Wow, I did not thought, that the scale and translation would effect the fps so massive. At home I will try it instantly.

Thank you very much

i wait to see your test list,
this on top of the code relates to a 40euro computer with 1GB RAM ( for cpu gpu and ramdisk )

try with backup memory class just hold one boolean.

``````// https://discourse.processing.org/t/scalable-grid-with-rectangles/7256
// https://discourse.processing.org/t/better-grid-performance/7314
// test FPS on RPI
// grid 8     FPS 59
// grid 100   FPS 6.7  ( disable rect get FPS 45 )  ( noSmooth FPS 9 )
// grid 100   FPS 5.4  ( size(1200,1200) )
// grid 500   FPS go down slowly ?
// test FX2D not run on RPI

// use backup memory array for resize/reinit grid but remember selected rects

int x = 12, y = x, w = 10, h = w, grid = 50, many = grid*grid;
boolean auto = false;//true;
boolean shownum = false;    // key [n]
boolean showstroke = true;
boolean showFPS = true;
// color setup:
color bg  = color(200, 200, 0);
color stk = color(0, 0, 200);
color fillsel = color(0, 200, 0);
color fillnsel= color(200, 0, 200);

Myrect[]   myrects   = new Myrect[many];
Mybackup[] myselects = new Mybackup[many];  // temporary memory

void setup() {
size(800, 520);
noSmooth();
set_grid(true);     // init
println("use: mouse LEFT to select, mouse RIGHT to deselect");
println("key UP DOWN RIGHT LEFT for position");
println("key +  -  for grid size");
println("key n toggle shownumber");
}

void draw() {
background(bg);
fill(0);
if (showFPS ) text(nf(frameRate, 1, 1), 10, 10);
for (int i = 0; i < many; i++) myrects[i].drawit();               // draw each rect ( and check on mouse over + click )
}

class Mybackup {
boolean selected=false;
}

class Myrect {
int x, y, id;//, w, h; from global
boolean selected=false;
Myrect (int x, int y, int id) {
this.x = x;
this.y = y;
this.id = id;
}
void drawit() {
if ( showstroke ) stroke(stk);
else noStroke();
if ( selected ) fill(fillsel);
else            fill(fillnsel);
rect(x, y, w, h);
fill(0);   // black text
if (shownum) text(id, x+w/4, y+h/3);
sel();
}
boolean over() {
return( x < mouseX && mouseX < x+w && y < mouseY && mouseY < y+h );
}
void sel() {
if ( over() ) {
if (  selected && mousePressed && mouseButton == RIGHT) selected=false;
if ( !selected && mousePressed && mouseButton == LEFT)  selected=true;
}
}
}

void set_wh() {
// use x,y,grid as master and auto adjust rectangles (w,h) to window:
println(" width= "+width+", height= "+height+", grid= "+grid);
w = ( width  - 2 * x ) / grid;
println(" w= "+w+", x= "+x+", ( grid * w + 2 * x )= "+(grid*w+2*x));
h = ( height - 2 * y ) / grid;
println(" h= "+h+", y= "+y+", ( grid * h + 2 * y )= "+(grid*h+2*y));
}

void set_grid(boolean init) {
if ( auto ) set_wh();
if ( init )  for (int i = 0; i < many; i++)  myselects[i]=new Mybackup();                     // init backup memory
else         for (int i = 0; i < many; i++)  myselects[i].selected = myrects[i].selected;     // backup
for (int i = 0; i < many; i++)  myrects[i]=new Myrect(x+(i%grid)*w, y+(floor(i/grid))*h, i);  // resize
if ( !init ) for (int i = 0; i < many; i++)  myrects[i].selected = myselects[i].selected;     // restore
}

void keyPressed() {
if ( keyCode == UP )         y--;
else if ( keyCode == DOWN )  y++;
else if ( keyCode == LEFT )  x--;
else if ( keyCode == RIGHT ) x++;
else if ( key     == '+' )   w++;
else if ( key     == '-' )   w--;
h=w;
auto = false;  // confirm
set_grid(false);

if ( key == 'n' ) shownum = !shownum;
}

``````
2 Likes

The results of my test ``````//resolutions with scaling and transformation
//grid 10 * 10 = 60 fps
//grid 100 * 100 = 60 fps
//grid 200 * 200 = 56 fps
//grid 300 * 300 = 36 fps
//grid 400 * 400 = 21 fps
//grid 500 * 500 = 14 fps

//resolutions with scaling and transformation
//grid 10 * 10 = 60 fps
//grid 100 * 100 = 60 fps
//grid 200 * 200 = 58 fps
//grid 300 * 300 = 38 fps
//grid 400 * 400 = 24 fps
//grid 500 * 500 = 16 fps

//computer states 4k monitor, 2.6 Ghz CPU, 16 GB ram.

int  size = 3,t;
float rd, s,tr, tx, ty, tix, tiy;
//Grid size
int x = 500, y = 500;
boolean showFPS = true;
int ac;

class Gitter{

float numx, numy, size, col,mode,px,py,i,ac;
//I need them later, but at the moment hey have no function
int n1, n2, n3, n4, n5, n6, n7, n8, i2;

Gitter(float id, float NUMX, float NUMY, float  SIZE, float acc){
numx = NUMX;
numy = NUMY;
size = SIZE;
i = id;
i2 = (int)id;
ac = (int)acc;

}

void Draw(){

rectMode(CENTER);

tr = 0;
if (gitter[i2].ac == 2) {fill(200);rect (numx * size +10,numy * size + 10, size-1 , size-1 );}
}

}
Gitter[] gitter = new Gitter[x*y];

void setup(){
size(3000,2000);
noSmooth();

int  I = 0;
int ix,iy;
s = 1;

for (iy = 0;iy < y; iy = iy+1){
for(ix = 0;ix < x; ix = ix+1){
rd = random(1,11);
gitter[I] = new Gitter(I++,ix, iy, size,rd);
}
}

}
void draw(){
background(0);

//scaling andtranslations

if (showFPS ) text(nf(frameRate, 1, 1), 10, 10);
int ix,iy;int I=0;
//draw grid
for (iy = 0;iy < y; iy = iy+1){
for(ix = 0;ix < x; ix = ix+1){
gitter[I++].Draw();

}
}
fill(255);
textSize(20);
text(nf(frameRate,1,1),40,40);

}
``````

There is a small different, but it isn’t large. The test was without stroke. The stroke have a massive influence on the Performance.
With stroke I got only 9 fps in a 500*500 Grid.
The biggest problem are the rectangles. If I only create them (as object) but do not Draw them, the results was 60 FPS up to 2000 *2000 and about 40 FPS for 5000, by 5000.
I tryed a little bit out and createt randomly only about 10 % of the rectangles and of cours, the Framerate was much higher.

So here is my resolution.
drawing rectangles needs much performance, the scale and the transform a little bit, the Stroke and the Window size needs much performance too.
If I want to create a net of rectangles which is scaleable and transormeable, I can create the whole net, but draw only the rectangles, which are in my field of fiew. That would garant the best Performance, because I wont see every time the whoole field and so I have not to draw oll rectangles.

and
noSmooth();

but anyhow you understand already the difference
for computation / logic / program flow
and the drawing of lines… incl internal pixel mapping / coloring

what you now need to get a feeling for might be a
CALC JOB
like not drawing 1000 rectangles but doing 1000 add ( like matrix ) calculations instead…

Yes, my next goal is, to create a AI, which find speciel designs in a small grid, to learn, how they (AIs) work.