Building a digital painting studio from scratch with Processing
A few weeks ago I met the German artist Arno Beck, whose work I find absolutely great. Arno is a painter and deals with the transfer of digital phenomena into the physical world. Inspired by his painting I developed a digital painting software with Processing in this session.
Thanks to johnny_ctrl for the editing!
paintingstudio.pde
PImage[] images;
PGraphics source;
PGraphics target;
PGraphics result;
PGraphics comp;
PGraphics artboard;
PImage buffer;
PImage currImage;
int POSTER_W = 580;
int POSTER_H = 810;
float TILES_X = POSTER_W / 5;
float TILES_Y = POSTER_H / 5;
int sx, sy, sw, sh, dx, dy, dw, dh;
float scalar = 1;
float offsetX = 0;
float offsetY = 0;
float coutoutW = 30;
float threshold = 150;
void setup() {
size(1740, 810);
source = createGraphics(POSTER_W, POSTER_H);
target = createGraphics(POSTER_W, POSTER_H);
result = createGraphics(POSTER_W, POSTER_H);
artboard = createGraphics(900, 900);
comp = createGraphics(POSTER_W, POSTER_H);
images = new PImage[9];
images[0] = loadImage("1.jpg");
images[1] = loadImage("2.jpg");
images[2] = loadImage("3.jpg");
images[3] = loadImage("4.jpg");
images[4] = loadImage("5.jpg");
images[5] = loadImage("6.jpg");
images[6] = loadImage("7.jpg");
images[7] = loadImage("8.jpg");
images[8] = loadImage("9.jpg");
currImage = images[int(random(images.length))];
}
void draw() {
background(#00ff00);
drawSource();
drawTarget();
drawResult();
image(source, 0, 0);
image(target, POSTER_W, 0);
image(result, POSTER_W + POSTER_W, 0);
noFill();
stroke(#00ff00);
strokeWeight(3);
drawArtboard();
rect(mouseX, mouseY, sw, sh);
rect(mouseX + POSTER_W, mouseY, sw, sh);
render();
}
artboard.pde
void drawArtboard() {
artboard.beginDraw();
artboard.background(0);
artboard.imageMode(CENTER);
PImage buffer = target.get();
artboard.image(buffer,artboard.width/2,artboard.height/2);
artboard.endDraw();
}
randomComposition.pde
void randomComposition() {
int padding = 50;
comp.beginDraw();
comp.background(255);
float diameter = random(300);
comp.fill(0);
comp.noStroke();
comp.ellipse(random(padding,POSTER_W-padding), random(padding,POSTER_H-padding), diameter, diameter);
comp.stroke(0);
comp.strokeWeight(8);
comp.strokeCap(RECT);
comp.line(random(padding,POSTER_W-padding), random(padding,POSTER_H-padding), random(padding,POSTER_W-padding), random(padding,POSTER_H-padding));
comp.endDraw();
}
render.pde
void render() {
if (frameCount % 10 == 0) {
artboard.save("out/" + nf(frameCount, 6) + ".png");
}
}
result.pde
void drawResult() {
float tileW = result.width / TILES_X;
float tileH = result.height / TILES_Y;
PImage buffer = target.get();
result.beginDraw();
result.background(#f1f1f1);
result.noStroke();
for (int x = 0; x < TILES_X; x++) {
for (int y = 0; y < TILES_Y; y++) {
int px = int(x*tileW);
int py = int(y*tileH);
color c = buffer.get(px, py);
float b = brightness(c);
if (b < threshold) {
result.fill(0);
} else {
result.fill(#f1f1f1);
}
result.push();
result.translate(x*tileW, y*tileH);
result.rect(0, 0, tileW, tileH);
result.pop();
}
}
result.endDraw();
}
source.pde
void drawSource(){
source.beginDraw();
source.background(0);
source.imageMode(CENTER);
source.push();
source.translate(source.width/2 + offsetX, source.height/2 + offsetY);
source.scale(scalar);
source.image(currImage,0,0);
source.pop();
source.endDraw();
}
target.pde
void drawTarget() {
target.beginDraw();
buffer = source.get();
if (frameCount == 1) {
target.background(#ffffff);
}
sx = mouseX;
sy = mouseY;
sw = int(coutoutW);
sh = int(coutoutW);
dx = mouseX;
dy = mouseY;
dw = int(coutoutW);
dh = int(coutoutW);
if (mousePressed) {
target.copy(buffer, sx, sy, sw, sh, dx, dy, dw, dh);
}
target.endDraw();
}
ui.pde
void keyReleased() {
if (key == '1') {
currImage=images[0];
}
if (key == '2') {
currImage=images[1];
}
if (key == '3') {
currImage=images[2];
}
if (key == '4') {
currImage=images[3];
}
if (key == '5') {
currImage=images[4];
}
if (key == '6') {
currImage=images[5];
}
if (key == '7') {
currImage=images[6];
}
if (key == '8') {
currImage=images[7];
}
if (key == '9') {
currImage=images[8];
}
if (key == 'r') {
scalar = random(1, 5);
offsetX = random(-800, 800);
offsetY = random(-800, 800);
}
if (key == 't') {
randomComposition();
currImage = comp.get();
}
if (key == 'e') {
scalar = 1;
offsetX = 0;
offsetY = 0;
}
}
void mouseWheel(MouseEvent event) {
float e = event.getCount();
coutoutW += e*10;
}
Related
Links
Enjoying the content?
I put a lot of love and effort into developing content on Creative Coding. Since 2018, I have published 219 interviews, case studies, and tutorials, along with over 280 lessons in 17 online courses – and there's more to come! If you'd like to support my work and help keep this platform evolving, please consider supporting me on Patreon. Thank you very much!
Related
The guiding principle in my teaching and in the development of this platform is “Demystify Technology”. The Problem When people […]
Two thousand and twenty-four. At the “Barceloneta” metro station, a few hundred meters from the beach, stands an old dot-matrix […]
In an age of increasing digital consumption, Hannah, a recent visual communication graduate, explored “Permacomputing”—a sustainable approach to technology inspired […]
Limitations have always been playing a major role in my creative work; I was only able to develop my best […]
In this interview, Copenhagen-based creative director Tameem Sankari shares his journey into Creative Coding, combining Processing, Blender, and Adobe CC. […]
In this post I’d like to introduce you to Sam Griffith, a talented graphic designer based in Detroit, to discuss […]
The next edition of the DEMO Festival is already approaching and I am currently developing a brand new talk for […]
20 = 1 21 = 222 = 323 = 824 = 1625 = 3226 = 6427 = 128 … »In […]
This is a call for coding designers. It aims to serve as a proposal and a provocation for creative work […]
Hi! In this post I’ll collect case studies and direct links to tools that people have built with p5.js and […]
Your 128kb journey starts here! This is a template you can use to start developing your idea within the 128kb […]
In 2022, I spontaneously posted a story on Instagram: If anyone out there is also in Rotterdam, I’d love to […]
One day in early 2024 I started to experiment with a new idea. I wrote down a set of rules […]
During OFFF Festival here in Barcelona, many interesting people come around! This interview with Talia Cotton came about almost by […]
Lena: This 10-minute visualiser for A. G. Cooks album teaser featuring my python archive generator, is one of my favourite […]
Hi Anna! It was super nice to meet you at the PCD CPH, I really liked your talk in which […]
When I held Martin Lorenz’s new book in my hands and turned it onto its back, I was a little […]
Hey folks, I hope you are doing great! You may have already read one or two of my essays that […]
Instagram, Twitter, TikTok… All the main platforms that technically have the required features to connect emerging communies for Creative Coding […]
In my teaching at universities and in workshops, I have met many very enthusiastic and highly talented people who have […]
I’ve been travelling a lot in the last few months. Still, it was only during a short stay in Copenhagen […]
For me, it’s by far the most inspiring project of the last few years: “Symphony in Acid”, a collaboration between […]
How does Creative Coding relate to the broad term “systems theory”? This question has been the subject of many conversations […]
One of the first exercises I assign to my students in my seminars is called “Random Compositions”. Basically, it’s quite […]
Click here to login or connect!To view this content, you must be a member of Tim's Patreon at €7 or […]
Click here to login or connect!To view this content, you must be a member of Tim's Patreon at €7 or […]
Click here to login or connect!To view this content, you must be a member of Tim's Patreon at €7 or […]
I am really excited to announce that I’ve finally released my brand new course Building Tools today! I just added […]