loop through an ArrayList which displays as a grid, – completed
randomly select a few of the cells, – completed
subdivide the selected into 4 smaller cells, – completed
add the new cells to the ArrayList – problem area
display the new grid that has the larger and smaller GridCells – problem area
I guess the main problem is I’m not clear on how to access and then integrate the smaller cells into the main ArrayList.
Any guidance is greatly appreciated!
//////////////////////////////////////////////////////////////////////////////////////////
Current version of code as follows:
import java.util.List;
List<GridCell>cell = new ArrayList<GridCell>();
void setup() {
size (600, 600);
background(255);
noLoop();
for (int x = 0; x < width; x+= 100) {
for (int y = 0; y < height; y+= 100) {
cell.add(new GridCell(x, y, 100, 100));
}
}
}
void draw() {
for (GridCell c : cell) {
c.display();
}
subdivideCells();
}
void subdivideCells() {
List<GridCell>fourCells = new ArrayList<GridCell>();
for (int i = 0; i < cell.size(); i++) {
if (random(1)<0.5)
cell.get(i).subdivide();
cell.add(fourCells); //***this is wrong but I don't know why
}
}
/////////////////////////////////////////////////////////////////////
class GridCell {
int x, y, w, h;
GridCell(int x_, int y_, int w_, int h_) {
x = x_;
y = y_;
w = w_;
h = h_;
}
void display() {
stroke(0);
strokeWeight(2);
rect(x, y, w, h);
}
List<GridCell>subdivide() {
List<GridCell> newCells = new ArrayList();
newCells.add(new GridCell(x, y, w/2, h/2));
newCells.add(new GridCell(x+w/2, y, w/2, h/2));
newCells.add(new GridCell(x, y+h/2, w/2, h/2));
newCells.add(new GridCell(x+w/2, y+h/2, w/2, h/2));
return newCells;
}
}
Firstly, here a block with {…} should start because you already have TWO lines that are dependent upon the if clause not only one.
Second: the function returns a new arraylist. You need to receive this arraylist from the function (like List<GridCell> newCells = ...subdivide...). This is where you call the function. Then for loop over the new small arraylist and add the items to the main arraylist. This is all inside said {…}
Hello @Chrisir !
Thank you for the quick reply!
I made 2 changes based on your response, but
See below:
void subdivideCells() {
for (int i = 0; i < cell.size(); i++) {
List<GridCell>fourCells = new ArrayList<GridCell>(); // move the List to here?
if (random(1)<0.5) { //added the missing {...}
cell.get(i).subdivide();
cell.add(fourCells);
}
}
}
This is the part where I’m most confused. I can’t figure out what I’m supposed to be connecting and in what order…but will look at this some more…
I think this is getting closer?
But consistent error message on the last line…
void subdivideCells() {
for (int i = 0; i < cell.size(); i++) {
if (random(1)<0.5) {
List<GridCell> newCells = cell.get(i).subdivide(); // Yes?? no error message here now
//for (int i = 0; i < newCells.size(); i++) { //replaced regular for loop with for each to eliminate duplicate i variable
for (GridCell g : newCells) {
cell.add(newCells); //keep getting error message on this line
}
}
}
Thank you!!! That cleared the last error message.
Now the program hangs when I try to run it. Got some time out error messages so not sure what is happening. I’ll try again tomorrow.
Thank you again!!!
I greatly appreciate the help.
Yes, I had thought of trying that.
Right now, am trying to get a better handle on manipulating arrayLists so probably won’t attempt removing old cells at this time (or maybe ever…
I looked into this, it’s more complicate than I thought it was
ArrayList<GridCell> cells = new ArrayList<GridCell>();
void setup() {
size (600, 600);
background(255);
noLoop();
// make grid
for (int x = 0; x < width; x+= 100) {
for (int y = 0; y < height; y+= 100) {
cells.add(new GridCell(x, y, 100, 100));
}
}
// divide cells
for (int i = 0; i < 16; i++) {
subdivideCells();
}
}
void draw() {
// display grid
for (GridCell c : cells) {
c.display();
}
}
//-----------------------------------------------------------------------------------------------------
// Other function
void subdivideCells() {
// It is necessary to have a controlCounter and use this is in the for-loop since we change the size() of the ArrayList
int controlCounter=0;
// It is necessary to store upperBound and use this is in the for-loop since we change the size() of the ArrayList
int upperBound = cells.size();
// println(cells.size() +"\n--------------------" );
for (int i = 0; i < upperBound; i++) {
if (random(1)<0.5) {
// get this cell from the ArrayList
GridCell parentCell = cells.get(i);
// mark this parent cell as dead
parentCell.isDead=true;
// get 4 sub rectangles "newCells" and add them to the main list "cells"
ArrayList<GridCell> newCells = parentCell.subdivide();
// replaced regular for loop with for each
for (GridCell currentNewCell : newCells) {
cells.add(currentNewCell);
}//for
}//if
controlCounter++;
if (controlCounter>1784) {
println("abort "+controlCounter);
return;
}//if
}//for
// remove dead cells (backward)
for (int i = cells.size()-1; i > 0; i--) {
if (cells.get(i).isDead) {
cells.remove(i);
}
}
}//func
/////////////////////////////////////////////////////////////////////
class GridCell {
int x, y,
w, h;
color colGridCell = color(random(255), random(255), random(255));
boolean isDead=false;
GridCell(int x_, int y_, int w_, int h_) {
x = x_;
y = y_;
w = w_;
h = h_;
}
void display() {
stroke(0);
// noStroke();
// strokeWeight(2);
fill(colGridCell);
rect(x, y, w, h);
}
ArrayList<GridCell>subdivide() {
ArrayList<GridCell> newCells = new ArrayList();
newCells.add(new GridCell(x, y, w/2, h/2));
newCells.add(new GridCell(x+w/2, y, w/2, h/2));
newCells.add(new GridCell(x, y+h/2, w/2, h/2));
newCells.add(new GridCell(x+w/2, y+h/2, w/2, h/2));
return newCells;
}//method
//
}//class
//
@Chrisir Thank you so very much!!! This is greatly helpful!!
I understand all of the code and logic.
But one small question about the control counter.
Code runs the same with the controlCounters commented out. Is this supposed to be linked to the cells.size()?
I’m probably overlooking something…
I had the controlCounter to end the for loop early.
In my tests the image looked best when it was around 1700; when it was 17000 the image had to many black areas, probably due to the black outline stroke color of the rectangles