Daten I

Viele Variablen: Arrays, Arrays in 2D, Bilder (Bitmaps), Bilder: einzelne Pixel, Bilder als Arrays, Bilder (Vektoren)

Viele Variablen: Arrays

Statt:

size(410, 200);
background(255);

float py1 = 10+random(height-10);
float py2 = 10+random(height-10);
float py3 = 10+random(height-10);
float py4 = 10+random(height-10);
//usw...

line(10,10,10,py1);
line(20,10,20,py2);
line(30,10,30,py3);
line(40,10,40,py4);
// usw...

...eine Menge von Variablen (Feld/Array). Array deklarieren mit [].

float[] py;

Größe des Feldes festlegen mit new und [...].

py = new float[40];

Länge des Feldes abfragen mit length.

println(py.length);

Werte in das Feld speichern mit der Nummer einer Variable darin ([...], Zählen ab Null!)...

py[0] = 10+random(height-10);
py[1] = 10+random(height-10);
py[2] = 10+random(height-10);
py[3] = 10+random(height-10);
//  usw...

...meist in einer Schleife.

for (int i=0; i<py.length; i++) {
  py[i] = 10+random(height-10);
}

Verwenden der Variablen im Feld über ihre Nummer ([...], Zählen ab Null!).

for (int i=0; i<py.length; i++) {
  line(10*i+10,10,10*i+10,py[i]);
}

Zum Beispiel...Wall Drawing #118:

size(400, 400);
background(255);

float[] px;
float[] py;

px = new float[40];
py = new float[40];

for (int i=0; i<px.length; i++) {
  px[i] = random(width);
  py[i] = random(height);
}

for (int i=0; i<px.length; i++) {
  stroke(0, 128);
  strokeWeight(8);
  point(px[i], py[i]);
  for (int j=0; j<px.length; j++) {
    stroke(0, 24);
    strokeWeight(1);
    line(px[i],py[i],px[j],py[j]);
  }
}

Arrays in 2D

Arrays können auch in jedem Feld ein weiteres Array enthalten -- und damit Zeilen und Spalten bekommen. Z.B. für 10 Mal 10 zufällige Rotationen.

Anlegen mit [][]:

float[][] winkel;

winkel = new float[10][10];

Füllen mit Werten (jeder Winkel ist über zwei Zahlen markiert: Zeile und Spalte)...

for (int i=0; i<winkel.length; i++) {
  for (int j=0; j<winkel[i].length; j++) {
    winkel[i][j] = random(90);
  }
}

...und Zugriff auf die Koordinaten (wieder über zwei Zahlen):

for (int i=0; i<winkel.length; i++) {
  pushMatrix();
  for (int j=0; j<winkel[i].length; j++) {
    pushMatrix();
    rotate(radians(winkel[i][j]));
    rect(0,0,10,10);
    popMatrix();
    translate(0, 20);
  }
  popMatrix();
  translate(20, 0);
}

Jetzt z.B. Drehwinkel auf Tastendruck verändern.

float[][] winkel;

void setup() {
  size(400, 400);
  fill(255);
  noStroke();
  rectMode(CENTER);
  winkel = new float[10][10];
  for (int i=0; i<winkel.length; i++) {
    for (int j=0; j<winkel[i].length; j++) {
      winkel[i][j] = random(90);
    }
  }
}

void draw() {
  background(0);
  translate(110, 110);
  for (int i=0; i<winkel.length; i++) {
    pushMatrix();
    for (int j=0; j<winkel[i].length; j++) {
      pushMatrix();
      rotate(radians(winkel[i][j]));
      rect(0, 0, 10, 10);
      popMatrix();
      translate(0, 20);
    }
    popMatrix();
    translate(20, 0);
  }

  if (keyPressed) {
    for (int i=0; i<winkel.length; i++) {
      for (int j=0; j<winkel[i].length; j++) {
        winkel[i][j] = winkel[i][j] + 1;
      }
    }
  }
}

Bilder (Bitmaps)

Bilder laden, in Variable speichern und darstellen. (Achtung: "Sketch/Add File..." oder von Hand nach Sketch-Folder/data!)

size(400,400);

PImage bild;
bild = loadImage("Monitor.jpg");

imageMode(CENTER);
image(bild,width/2,height/2);

Bilder: einzelne Pixel

Alle Pixel eines Bildes können über PImage.get(...) abgefragt werden...

PImage bild;

void setup() {
  size(585,439);
  bild = loadImage("Monitor.jpg");
}

void draw() {
  image(bild,0,0);
  noStroke();
  fill(bild.get(mouseX,mouseY));
  rectMode(CENTER);
  rect(mouseX,mouseY,40,40);
}

...auch nacheinander in einer doppelten Schleife (Zeilen und Spalten).

PImage bild;

void setup() {
  size(585, 439);
  bild = loadImage("Monitor.jpg");
}

void draw() {
  background(0);
  for (int i=0; i<bild.width; i++) {
    for (int j=0; j<bild.height; j++) {
      strokeWeight(20);
      if (brightness(bild.get(i,j)) > 200) {
        stroke(255,25);
        point(i,j);  
      }      
    }
  }
}

Wobei natürlich alle oder nur einige der Pixel angeschaut werden können. Z.B. Pixelate:

PImage bild;
int pixel = 10;

void setup() {
  size(585, 439);
  bild = loadImage("Monitor.jpg");
}

void draw() {
  background(255);
  noStroke();
  noSmooth();
  for (int i=0; i<bild.width; i = i+pixel) {
    for (int j=0; j<bild.height; j = j+pixel) {
      fill(bild.get(i,j));
      rect(i,j,pixel,pixel);
    }
  }
  
  pixel = mouseX/4+1;
}

Bilder als Arrays

Schneller als get(...) ist der Zugriff auf die Pixel als Array (pixels[]). Dazu muss das Array aller Pixel zunächst geladen werden: loadPixels().

Beim Zugriff auf das Array wird aus get(x, y) dann pixels[y*width+x].

PImage bild;

void setup() {
  size(585,439);
  bild = loadImage("Monitor.jpg");
}

void draw() {
  image(bild,0,0);
  noStroke();
  bild.loadPixels();
  fill(bild.pixels[mouseY*bild.width+mouseX]);
  rectMode(CENTER);
  rect(mouseX,mouseY,40,40);
}
...oder:
PImage bild;
int abstand = 8;

void setup() {
  size(585, 439);
  bild = loadImage("Monitor.jpg");
}

void draw() {
  background(255);
  stroke(0);
  bild.loadPixels();
  for (int i=0; i<bild.width; i=i+abstand) {
    for (int j=0; j<bild.height; j=j+abstand) {
      float helligkeit = brightness(bild.pixels[j*bild.width+i]);
      pushMatrix();
      translate(i, j);
      rotate(radians(helligkeit/255.0*360));
      line(0,-3,0,3);
      popMatrix();
    }
  }
}

Mit updatePixels() kann das Bild-Array selbst verändert werden.

PImage bild;

void setup() {
  size(585, 439);
  bild = loadImage("Monitor.jpg");
  
  bild.loadPixels();
    for (int i=0; i<bild.width; i++) {
      for (int j=0; j<bild.height; j++) {
        bild.pixels[j*bild.width+i] = color(255-brightness(bild.pixels[j*bild.width+i]));
      }
    }
    bild.updatePixels();
}

void draw() {
  image(bild,0,0);
}

Bilder (Vektoren)

Vektordaten (SVG, z.B. aus Illustrator) mit PShape statt PImage, ansonsten bleibt alles ähnlich (aber: Skalierbarkeit!).

size(600,600);

PShape svgbild;
svgbild = loadShape("fade.svg");

background(255);
shapeMode(CENTER);
shape(svgbild, width/2, height/2, 800, 800);
shape(svgbild, width/2, height/2, 400, 400);
shape(svgbild, width/2, height/2, 200, 200);
shape(svgbild, width/2, height/2);

Anders als bei Pixelbildern, lassen sich bei vektorbasierten Bildern die Processing-Styles (fill, stroke) benutzen. Z.B.

size(600,600);

PShape svgbild;
svgbild = loadShape("fade.svg");

svgbild.disableStyle();

background(255);
shapeMode(CENTER);
fill(0,0,64);
shape(svgbild, width/2, height/2, 800, 800);
fill(0,0,128);
shape(svgbild, width/2, height/2, 400, 400);
fill(0,0,192);
shape(svgbild, width/2, height/2, 200, 200);
fill(0,0,255);
shape(svgbild, width/2, height/2);

Oder in Abhängigket von der Maus (Schaltfläche):

PShape svgbild;

void setup() {
  size(800,400);
  svgbild = loadShape("fade.svg");
}

PShape svgbild;

void setup() {
  size(800, 400);
  svgbild = loadShape("fade.svg");
}

void draw() {
  background(0);
  shapeMode(CENTER);

  shape(svgbild, width/2, height/2, 200, 200);

  if (mouseX > width/2-100 && mouseX < width/2+100 &&
    mouseY > height/2-100 && mouseY < height/2+100) {
    svgbild.disableStyle();
  } else {
    svgbild.enableStyle();
  }
}