Processing - three-line text editor and move to next line? - processing

I need to write a typing program to create a “three-line” text editor. If the length of the
input string is longer than the line (40 characters), it will be automatically move to
the next line.
This is my code so far:
String word = "";
void setup() {
size(1000, 600);
textSize(26);
fill(0);
}
void draw() {
background(255);
text(word, 0, 0, width, height);
}
void keyPressed() {
int lineBreak = word.length();
if(lineBreak > 39) {
word = word + "\n";
}
else {
word = word + key;
}
}
Whenever I run the problem, the string length stops at 40 characters but it doesn't move to the next line.

text() does not support line breaks.
You have to store each line to a separate string. For instance use StringList to store the lines of the text.
Create an array of strings, that stores the finished lines. The current line is still stored in word:
StringList lines = new StringList();
When the line limit is reached, then add the line to the list and start a new line:
if(lineBreak > 39) {
lines.append(word);
word = "";
}
Define a lineheight an draw the lines in a loop. The vertical position of a line is computed by lineheight * (i + 1), where i is the index of the line:
int lineheight = 30;
for (int i = 0; i < lines.size(); i++) {
String line = lines.get(i);
text(line, 0, lineheight * (i + 1));
}
text(word, 0, lineheight * (lines.size() + 1));
See the example:
StringList lines = new StringList();
String word = "";
void setup() {
size(1000, 600);
textSize(26);
fill(0);
}
void draw() {
background(255);
int lineheight = 30;
for (int i = 0; i < lines.size(); i++) {
String line = lines.get(i);
text(line, 0, lineheight * (i + 1));
}
text(word, 0, lineheight * (lines.size() + 1));
}
void keyPressed() {
int lineBreak = word.length();
if(lineBreak > 39) {
lines.append(word);
word = "";
}
else {
word += key;
}
}

Related

Processing String splitting and loops to form a facade

I have tried many methods, and can't seem to grasp the idea of extracting an index from my array of strings to help me generate my desired number of building with a desired height, please help, here is my example
edit: Hi, i saw your feedback and posted my code below, hopefully it helps with the idea overall, as much as it is just creating rects, its more complicated as i need to involve arrays and string splitting along with loops. i more or less got that covered but i as i said above, i cannot extract the values from my array of string and create my facades at my own desired number and height
String buffer = " ";
String bh = "9,4,6,8,12,2";
int[] b = int(split(bh, ","));
int buildingheight = b.length;
void setup () {
size(1200, 800);
background(0);
}
void draw () {
}
void Textbox() {
textSize(30);
text(buffer, 5, height-10);
}
void keyTyped() {
if (key == BACKSPACE) {
if (buffer.length() > 0) {
buffer = buffer.substring(0, buffer.length() - 1);
}
} else if (key == ENTER) {
background(0);
stroke(0);
GenerateFacade();
println(buffer);
}
else {
buffer = buffer + key;
Textbox();
}
}
void GenerateFacade() {
fill(128);
for (int i = 0; i < b.length; i++) {
for (int j = 0; j < b.length; j++) {
if (int(b[j]) > buildingheight) {
buildingheight = int(b[j]);
}
}
rect(i*width/b.length, height - (int(b[i])*height/buildingheight), width/b.length, int(b[i])*height/buildingheight);
}
}
For the next time it would be great if you provide us with some code so we know what you tried and maybe can point you to the problem you have.
You need just the keyPressed function and some variables
int x = 0;
int buildingWidth = 50;
int buildingHeight = height / 6;
void setup(){
size(1000, 500);
background(255);
}
void draw(){
}
void keyPressed(){
if(key >= '0' && key <= '9'){
int numberPressed = key - '0' ;
fill(0);
rect(x, height - buildingHeight * numberPressed,
buildingWidth, buildingHeight * numberPressed);
x += buildingWidth;
}
}
This is my result

Automation of selection in Processing

I am currently using a processing sketch to work through a large number of images I have in a folder. I have set an onClick command to advance to the next image in the string. It is quite time consuming and I would like to automate the action that once the sketch is completed the sketch would repeat it's self selecting the next image from the string. The onClick command also save the image the export folder but each time saves with the same file name, I've tried to set up sequential numbering but it hasn't worked so far. Any help would be greatly appreciated.
String[] imgNames = {"1.jpg", "2.jpg", "3.jpg"};
PImage img;
int imgIndex = 0;
void nextImage() {
background(255);
frameRate(10000);
loop();
frameCount = 0;
img = loadImage(imgNames[imgIndex]);
img.loadPixels();
imgIndex += 1;
if (imgIndex >= imgNames.length) {
imgIndex = 0;
}
}
void paintStroke(float strokeLength, color strokeColor, int strokeThickness) {
float stepLength = strokeLength/4.0;
// Determines if the stroke is curved. A straight line is 0.
float tangent1 = 0;
float tangent2 = 0;
float odds = random(1.0);
if (odds < 0.7) {
tangent1 = random(-strokeLength, strokeLength);
tangent2 = random(-strokeLength, strokeLength);
}
// Draw a big stroke
noFill();
stroke(strokeColor);
strokeWeight(strokeThickness);
curve(tangent1, -stepLength*2, 0, -stepLength, 0, stepLength, tangent2, stepLength*2);
int z = 1;
// Draw stroke's details
for (int num = strokeThickness; num > 0; num --) {
float offset = random(-50, 25);
color newColor = color(red(strokeColor)+offset, green(strokeColor)+offset, blue(strokeColor)+offset, random(100, 255));
stroke(newColor);
strokeWeight((int)random(0, 3));
curve(tangent1, -stepLength*2, z-strokeThickness/2, -stepLength*random(0.9, 1.1), z-strokeThickness/2, stepLength*random(0.9, 1.1), tangent2, stepLength*2);
z += 1;
}
}
void setup() {
size(1600, 700);
nextImage();
}
void draw() {
translate(width/2, height/2);
int index = 0;
for (int y = 0; y < img.height; y+=1) {
for (int x = 0; x < img.width; x+=1) {
int odds = (int)random(20000);
if (odds < 1) {
color pixelColor = img.pixels[index];
pixelColor = color(red(pixelColor), green(pixelColor), blue(pixelColor), 100);
pushMatrix();
translate(x-img.width/2, y-img.height/2);
rotate(radians(random(-90, 90)));
// Paint by layers from rough strokes to finer details
if (frameCount < 20) {
// Big rough strokes
paintStroke(random(150, 250), pixelColor, (int)random(20, 40));
} else if (frameCount < 1000) {
// Thick strokes
paintStroke(random(75, 125), pixelColor, (int)random(8, 12));
} else if (frameCount < 1500) {
// Small strokes
paintStroke(random(20, 30), pixelColor, (int)random(1, 4));
} else if (frameCount < 10000) {
// Big dots
paintStroke(random(5, 10), pixelColor, (int)random(5, 8));
} else if (frameCount < 10000) {
// Small dots
paintStroke(random(1, 2), pixelColor, (int)random(1, 3));
}
popMatrix();
}
index += 1;
}
}
if (frameCount > 10000) {
noLoop();
}
// if(key == 's'){
// println("Saving...");
// saveFrame("screen-####.jpg");
// println("Done saving.");
// }
}
void mousePressed() {
save("001.tif");
nextImage();
}
Can't you just call the nextImage() function from inside this if statement?
if (frameCount > 10000) {
noLoop();
}
Would be:
if (frameCount > 10000) {
nextImage();
}
As for using different filenames, just use an int that you increment whenever you save the file, and use that value in the save() function. Or you could use the frameCount variable:
save("img" + frameCount + ".tif");
If you have follow-up questions, please post a MCVE instead of your whole project. Try to isolate one problem at a time in a small example program that only does that one thing. Good luck.

Save image with Processing

I'm trying to save an image after certain time, the problem is that the image size is bigger than the display so when I use the save or saveFrame function it only saves the image that I can see in the display. There is any other way to save the whole image?
This is my code:
PImage picture, pictureFilter, img;
int total, cont, current;
ArrayList<ArrayList<Position>> columns;
String[] fontList;
public class Position {
public int x;
public int y;
}
void setup() {
fontList = PFont.list();
picture = loadImage("DSC05920b.JPG");
pictureFilter = loadImage("filtrePort2.jpg");
frame.setResizable(true);
size(picture.width, picture.height);
columns = new ArrayList<ArrayList<Position>>();
for(int i = 0; i < picture.width; i++) {
ArrayList<Position> row = new ArrayList<Position>();
for(int j = 0; j < picture.height; j++){
Position p = new Position();
p.x = i;
p.y = j;
row.add(p);
}
columns.add(row);
}
total = picture.width * picture.height;
cont = total;
current = 0;
img = createImage(picture.width, picture.height, RGB);
}
float randomLetter() {
float value = 23;
boolean found = false;
while(!found) {
value = random(48, 122);
if(value >48 && value <58) found = true;
if(value >65 && value <91) found = true;
if(value >97 && value <123) found = true;
}
return value;
}
void draw() {
int x = int(random(0, columns.size()));
ArrayList<Position> rows = columns.get(x);
int y = int(random(0, rows.size()));
Position p = rows.get(y);
color c = pictureFilter.get(p.x, p.y);
int r = (c >> 16) & 0xFF; // Faster way of getting red(argb)
if(r < 240) {
PFont f = createFont(fontList[int(random(0,fontList.length))],random(5, 24),true);
textFont(f);
fill(picture.get(p.x,p.y));
char letter = (char) int(randomLetter());
text(letter, p.x, p.y);
}
if(rows.size() == 1) {
if(columns.size() == 1) {
saveFrame("lol.jpg");
columns.remove(x);
} else {
columns.remove(x);
}
} else {
println(rows.size());
rows.remove(y);
}
--cont;
float percent = float(total-cont)/float(total)*100;
if(int(percent) != current) {
current = int(percent);
save("image_" + current + ".jpg");
}
println("DONE: " + (total-cont) + "/" + total + " Progress: " + percent + "%");
}
The code do a lot of stuff but the part that its not working well is at the final when I check if the percentage have been increased in order to save the image
You can write this into a PGraphics context - aka a graphics buffer.
The buffer can be as big as you need it to be, and you can choose whether to draw it on the screen or not..
// Create the buffer at the size you need, and choose the renderer
PGraphics pg = createGraphics(myImage.width, myImage.height, P2D);
// Wrap all your drawing functions in the pg context - e.g.
PFont f = createFont(fontList[int(random(0,fontList.length))],random(5, 24),true);
textFont(f);
pg.beginDraw();
pg.fill(picture.get(p.x,p.y));
char letter = (char) int(randomLetter());
pg.text(letter, p.x, p.y);
pg.endDraw();
// Draw your PG to the screen and resize the representation of it to the screen bounds
image(pg, 0, 0, width, height); // <-- this wont actually clip/resize the image
// Save it
pg.save("image_" + current + ".jpg");
The PImage class contains a save() function that exports to file. The API should be your first stop for questions like this.

Processing: Numbered Image squence

I am trying to create 100 frames where the numbers 0-100 are "printed" in the center of every frame. If I try the code below I get the error "It looks like you're mixing "active" and "static" modes".
size(1440,900);
font = loadFont("Arial-Black-96.vlw");
textFont(font,96);
int x = 0;
void draw() {
background(204);
y=0;
if (x < 100) {
text(y, 10, 50);
x = x + 1;
y=y+1;
} else {
noLoop();
}
// Saves each frame as screen-0001.tif, screen-0002.tif, etc.
saveFrame();
}
You need to wrap the first 3 lines in the setup() function.
Like:
void setup(){
size(1440,900);
font = loadFont("Arial-Black-96.vlw");
textFont(font,96);
}
I answered this without running the code, there were others issues, here a version of your code:
PFont font;
int x = 0;
int size = 96;
void setup() {
size(1440, 900);
font = createFont("Arial-Black", size);
textFont(font);
}
void draw() {
background(204);
if (x <= 100) {
String number = nf(x, 2);
text(number, width/2 - textWidth(number)/2, height/2);
x++;
saveFrame();
}
else {
exit();
}
}

Processing: I need counter inside draw function

I'm using controlP5 processing GUI, and I need counter inside draw() function.
I know that draw() function run continuously and every for loop is shown in its last step.
I need to see every step. I have two inputs, and I can input only once, because of draw(). I need draw() function to wait for input or something like that.
import controlP5.*;
Textarea myTextareaMI;
Textarea myTextareaVI;
Textarea my;
String textValueBODOVI = "";
String textValueZVANJE = "";
boolean mi=false, vi=false;
int i=1;
ControlP5 cp5;
int myColor = color(255);
int c1, c2;
float n, n1;
void setup() {
size(320, 480);
noStroke();
PFont font = createFont("arial", 20);
cp5 = new ControlP5(this);
cp5.addButton("NOVA PARTIJA")
.setValue(0)
.setPosition(0, 0)
.setSize(480, 19)
;
cp5.addButton("PONISTI ZADNJI UNOS")
.setValue(100)
.setPosition(0, 20)
.setSize(480, 19)
;
cp5.addBang("MI")
.setPosition(60, 80)
.setSize(60, 20)
.getCaptionLabel().align(ControlP5.CENTER, ControlP5.CENTER)
;
cp5.addBang("VI")
.setPosition(123, 80)
.setSize(60, 20)
.getCaptionLabel().align(ControlP5.CENTER, ControlP5.CENTER)
;
cp5.addTextfield("BODOVI")
.setPosition(60, 41)
.setSize(60, 20)
.setFont(font)
.setColor(color(255, 0, 0))
;
cp5.addTextfield("ZVANJE")
.setPosition(123, 41)
.setSize(60, 20)
.setFont(font)
.setColor(color(255, 0, 0))
;
;
int l=0;
for (int i=1;i<11;i++,l=l+22) {
my = cp5.addTextarea("MIVI"+i).setPosition(60, 101+l).setSize(123, 20).setFont(createFont("arial", 14))
.setLineHeight(14)
.setColor(color(128))
.setColorBackground(color(255, 100))
.setColorForeground(color(255, 100))
;
}
}
public void bang() {
}
void draw() {
delay(15);
background(myColor);
myColor = lerpColor(c1, c2, n);
n += (1-n)* 0.1;
funkcija();
}
void funkcija(){
int suma= 0;
for( i=1;i<=11;i++){
int brojmi=0;
textValueZVANJE = cp5.get(Textfield.class, "ZVANJE").getText();
textValueBODOVI = cp5.get(Textfield.class, "BODOVI").getText();
int bodovi = int(textValueBODOVI);
int zvanje = int(textValueZVANJE);
int mii, vii;
if(bodovi>0){
if (mi) {
println("mi"+brojmi+i);
int ukupno = 162 + zvanje;
vii = ukupno - bodovi;
cp5.get(Textarea.class, "MIVI"+i).setText(textValueBODOVI+" "+vii);
mi=false;
vi=false;
cp5.get(Textfield.class, "BODOVI").clear();
cp5.get(Textfield.class, "ZVANJE").clear();
loop();
}
if (vi) {
println("vi"+i);
int ukupno = 162 + zvanje;
mii = ukupno - bodovi;
cp5.get(Textarea.class, "MIVI"+i).setText(mii+" "+textValueBODOVI);
mi=false;
vi=false;
cp5.get(Textfield.class, "BODOVI").clear();
cp5.get(Textfield.class, "ZVANJE").clear();
}
}
brojmi++; }
}
public void controlEvent(ControlEvent theEvent) {
mi = theEvent.getController().getName().equals("MI");
vi = theEvent.getController().getName().equals("VI");
}
public void clear() {
cp5.get(Textfield.class, "BODOVI").clear();
cp5.get(Textfield.class, "ZVANJE").clear();
}
Mmmmm, I don't know if I got your question.
If your question is: "i need draw() function to wait for input or something like that.", then use a flag (boolean value) to decide if draw or not. When user input something, assign true to that value.
So your code should be:
void draw () {
// put the code you want to run anyways here...
// code
// code
if (hasUserInput) {
// here write the code you should wait to execute
}
}

Resources