Alex is correct.
Cyrill, you're on the right track but seem to get confused between 3 ways at looking at your data:
- The images array is a 1D array (indices 0 to 15)
- The for loop is nested therefore you need to convert 2D indices to 1D. You are right:
x+y*width would give you the correct array index, but in this case width is not the full width of your sketch in pixels but the width of the grid (i.e. the number of columns in the 4x4 grid: 4)
- You are getting a null pointer pointer because you're trying to access elements in a 1D array as if it's 2D.
Something like this should work:
float pixelamount = 4;
float pixelsize;
PImage[] images = new PImage [16];
void setup() {
size(1080, 1080);
pixelsize = width/pixelamount;
for (int i = 0; i < images.length; i++) {
images[i] = loadImage(i + ".png");
}
//imageMode(CENTER);
}
void draw() {
background(0);
pushMatrix();
translate(pixelsize/2, pixelsize/2);
for (int x = 0; x < pixelamount; x++) {
for (int y = 0; y < pixelamount; y++) {
pushMatrix();
translate(pixelsize*x, pixelsize*y);
image(images[x + y * pixelamount], 0, 0, pixelsize, pixelsize);
popMatrix();
}
}
popMatrix();
}
If you want to loop with a single for loop (instead of a nested for loop) which would match how you store your data you can use this formula to go from 1D index to 2D indices:
x = index % gridColumns
y = index / gridColumns
(Bare in mind these are integers (so in other languages (like Python/JS/etc.) you'd pay attention to the division operation))
Here's a basic example to illustrate this:
size(1080, 1080);
textAlign(CENTER, CENTER);
textFont(createFont("Courier New Bold", 12));
int pixelAmount = 4;
int pixelSize = width/pixelAmount;
int gridColumns = 4;
// iterate once
for(int i = 0; i < 16; i++){
// calculate 2D grid indices
int xIndex = i % gridColumns;
int yIndex = i / gridColumns;
// convert from index to pixel size
int x = xIndex * pixelSize;
int y = yIndex * pixelSize;
// render debug data
String debugText = "1D index:" + i +
"\n2D indices:[" + xIndex + "][" + yIndex + "]" +
"\nx, y pixels::" + x + "," + y;
fill(255);
rect(x, y, pixelSize, pixelSize);
fill(0);
text(debugText, x + pixelSize / 2, y + pixelSize / 2);
}
Here's the same example as the above using a 2D array and nested loops:
size(1080, 1080);
textAlign(CENTER, CENTER);
textFont(createFont("Courier New Bold", 12));
int pixelAmount = 4;
int pixelSize = width/pixelAmount;
int[][] grid = new int[pixelAmount][pixelAmount];
// mimick image loading (storing 1D index)
int index = 0;
for(int y = 0; y < pixelAmount; y++)
for(int x = 0; x < pixelAmount; x++)
grid[x][y] = index++;
// mimick reading 2D array data
for(int y = 0; y < pixelAmount; y++){
for(int x = 0; x < pixelAmount; x++){
int xPixels = x * pixelSize;
int yPixels = y * pixelSize;
// manually copute index
// index = x + y * pixelAmount;
// or retrieve stored index
index = grid[x][y];
String debugText = "1D index:" + index + ".png" +
"\n2D indices:[" + x + "][" + y + "]" +
"\nx, y pixels::" + xPixels + "," + yPixels;
fill(255);
rect(xPixels, yPixels, pixelSize, pixelSize);
fill(0);
text(debugText, xPixels + pixelSize / 2, yPixels + pixelSize / 2);
}
}
My answer is more for the sake of completeness: displaying both 1D/2D ways at looking at the data.