I'm trying to make a "Drawing Challenge": draw with the mouse for the Y-point and with the voice for the X-point. I tried this
import ddf.minim.*;
Minim minim;
AudioInput in;
float volume;
float moyenne=0;
int tampon=5;
void setup() {
size(640, 640, P2D);
minim = new Minim(this);
minim.debugOn();
background(255);
// get a line in from Minim, default bit depth is 16
in = minim.getLineIn(Minim.STEREO, 1024);
}
void draw() {
volume = in.mix.level()*10;
moyenne=((moyenne * tampon) + volume)/(tampon+3);
if ( volume > 1){
//line(15, 90, 95, 10);
line(moyenne, mouseY, moyenne, pmouseY);
if(keyPressed == true ){
stroke( random(255), random(255), random(255), random(255));
}
println(moyenne);
}
}
void stop() {
// always close Minim audio classes when you are done with them
in.close();
minim.stop();
super.stop();
This is not sensitive enough to receive the sound from the microphone or just trace some vertical lines without fluidity.
My question is : How can I make it more fluid while increasing the reception sensitivity of the microphone sound ?
Related
I’m trying to add a feature where you can click on different parts of the sketch and have an image randomly generated. It worked for the first time, but when I add another if mouse pressed function, it triggers all the mouse pressed code and all of the sets of images go off at the same time. I’m not sure how to isolate it so that just one goes off if it’s in the right spot.
Here is my code for the last attempt, I tried to isolate the mouse pressed function with a push and pop Matrix, which didn’t work.
PImage stage;
PImage model;
PImage [] hat = new PImage [5];
PImage [] pants = new PImage [4];
PImage [] shirt = new PImage [5];
int choice = 0;
int page = 0;
void setup() {
size (800, 800);
stage = loadImage("background.png");
background(255);
image(stage, 0, 0);
hat[0] = loadImage ("hat1.png");
hat[1] = loadImage ("hat2.png");
hat[2] = loadImage ("hat3.png");
hat[3] = loadImage ("hat4.png");
pants[0] = loadImage ("pant1.png");
pants[1] = loadImage ("pant2.png");
pants[2] = loadImage ("pant3.png");
pants[3] = loadImage ("pant4.png");
}
void draw() {
println(mouseX, mouseY); //398, 237 for hats.
image(stage, 0, 0);
pushMatrix();
if (dist(398, 237, mouseX, mouseY) <90 && mousePressed) choice = floor(random(4));
image(hat[choice], 349, 98);
popMatrix();
pushMatrix();
if (dist(404, 363, mouseX, mouseY) <90 && mousePressed) choice = floor(random(4));
image(pants[choice], 228, 263);
popMatrix();
}
The issue is that you're using the same variable for all the clothing items. So when you click on the hat button, it sets choice to a random number (let's say 2). Then you display hat[choice] and then you also display pants[choice]. One way around this is to have multiple different choice variables, hatChoice and pantsChoice. When you click on the hat button, it randomizes hatChoice, and when you click on the pants button, it randomizes pantsChoice. Something like this:
if (dist(398, 237, mouseX, mouseY) <90 && mousePressed) hatChoice = floor(random(4));
image(hat[hatChoice], 349, 98);
if (dist(404, 363, mouseX, mouseY) <90 && mousePressed) pantsChoice = floor(random(4));
image(pants[pantsChoice], 228, 263);
I also second #rjw1428's recommendation of using mouseClicked() instead of if (mousePressed). You can do something like this:
//your global variables...
int hatChoice = 0;
int pantsChoice = 0;
void setup() {
//your setup stuff...
}
void draw() {
image(stage, 0, 0);
image(hat[hatChoice], 349, 98);
image(pants[pantsChoice], 228, 263);
}
void mouseClicked() {
if (dist(mouseX, mouseY, 398, 237) < 90) {
hatChoice = floor(random(4));
}
if (dist(mouseX, mouseY, 404, 363) < 90) {
pantsChoice = floor(random(4));
}
}
This isn't a perfect solution, but to implement what you're trying to do, i might do this
PImage stage;
PImage model;
PImage [] hat = new PImage [5];
PImage [] pants = new PImage [4];
PImage [] shirt = new PImage [5];
int selectedHat = -1;
int selectedPants = -1;
int selectedShirt = -1;
int choice = 0;
int page = 0;
void setup(){
size (800,800);
stage = loadImage("background.png");
background(255);
image(stage,0,0);
initializeImages()
}
void draw(){
println(mouseX, mouseY); //398, 237 for hats.
image(stage,0,0);
if (selectedHat > 0) {
image(hat[selectedHat], 349,98);
}
if (selectedPants > 0) {
image(pants[choice], 228,263);
}
}
void mouseClicked() {
if(dist(404,363, mouseX, mouseY) <90 && mousePressed) {
selectedPants = floor(random(4));
}
if(dist(398,237, mouseX, mouseY) <90 && mousePressed) {
selectedHat = floor(random(4));
}
}
void initializeImages() {
hat[0] = loadImage ("hat1.png");
hat[1] = loadImage ("hat2.png");
hat[2] = loadImage ("hat3.png");
hat[3] = loadImage ("hat4.png");
pants[0] = loadImage ("pant1.png");
pants[1] = loadImage ("pant2.png");
pants[2] = loadImage ("pant3.png");
pants[3] = loadImage ("pant4.png");
}
Then if you wanted to clear, have an IF check for the location (button) that you want to select to clear, and your function could return all the 'selected' values back to -1
I'd like to rotate a cube in P3D and my code uses live sensor data to do that.
The problem is the previous orientations of the cube are always visible and overlap (as you can see in this image: http://i.stack.imgur.com/txXw6.jpg), which I don't want. I already tried the functions "hint(DISABLE_OPTIMIZED_STROKE)" and "hint(ENABLE_DEPTH_TEST)", which did nothing. Besides the hint functions I found nothing on a similar issue.
How can I render ONLY the current orientation?
import processing.serial.*;
import toxi.geom.*;
Serial myPort;
float qW;
float qX;
float qY;
float qZ;
float[] axis = new float[4];
Quaternion quat = new Quaternion(1, 0, 0, 0);
void setup()
{
size(600, 400, P3D);
myPort = new Serial(this, "COM3", 9600);
background(0);
lights();
}
void draw()
{
serialEvent();
quat.set(qW, qX, qY, qZ);
axis = quat.toAxisAngle();
pushMatrix();
translate(width/2, height/2, -100);
rotate(axis[0], axis[1], axis[2], axis[3]);
noFill();
stroke(255);
box(330, 200, 40);
popMatrix();
}
void serialEvent()
{
int newLine = 13; // new line character in ASCII
String message;
do
{
message = myPort.readStringUntil(newLine); // read from port until new line
if (message != null)
{
String[] list = split(trim(message), " ");
if (list.length >= 4)
{
qW = float(list[0]);
qX = float(list[1]);
qY = float(list[2]);
qZ = float(list[3]);
}
}
} while (message != null);
}
It looks like you're not clearing the frame buffer. Try adding background(0); as the first line in draw();:
void draw()
{
//clear background
background(0);
serialEvent();
quat.set(qW, qX, qY, qZ);
axis = quat.toAxisAngle();
pushMatrix();
translate(width/2, height/2, -100);
rotate(axis[0], axis[1], axis[2], axis[3]);
noFill();
stroke(255);
box(330, 200, 40);
popMatrix();
}
Off topic, it might worth checking out serialEvent().
You could do something like this in setup()
myPort = new Serial(this, "COM3", 9600);
myPort.bufferUntil('\n');
you shouldn't need to call serialEvent() in draw(), the serial library will do that, as it's buffering.
Then in serialEvent() hopefully you can get away with just:
String message = myPort.readString();
if(message !=null){
String[] list = split(trim(message), " ");
if (list.length >= 4)
{
qW = float(list[0]);
qX = float(list[1]);
qY = float(list[2]);
qZ = float(list[3]);
}
}
I'm trying to program an intro. I want the canvas to erase itself after it. I already have the trigger, but I do not know how to clear the canvas. Would just changing the background work? I still want to make stuff after it.
Here is the code:
void setup () {
frameRate(10);
stroke(255, 255, 255);
noFill();
rect(100,155,300,300);
size(500, 500);
}
void square () {
for (int x = 100; x <= 300; x += 100) {
for (int y = 155; y <= 355; y += 100) {
fill(random(0, 255), random(0, 255), random(0, 255));
rect(x, y,100,100);
}
}
};
void draw () {
int time = 0;
int logoLength = 100;
if (time < logoLength) {
fill(255, 255, 255);
background(0, 0, 0);
textFont(createFont("Lucida console", 19));
textAlign(CENTER,CENTER);
text("Ghost Cube Games presents",250,59);
time++;
print(time);
square();
} else if (time == logoLength) {
background(255, 255, 255);
}
}
You can simply call the background() function.
background(0); draws a black background.
background(255); draws a white background.
background(255, 0, 0); draws a red background.
More info can be found in the reference.
For a more specific example, if you want to show an intro screen, you can simply keep track of whether the intro screen is showing in a boolean variable. If that variable is true, then draw the intro screen. If not, then draw whatever else you want to draw. If you do this from the draw() function, then you don't really have to worry about clearing the screen, since calling the background() function will do that for you:
boolean showingIntro = true;
void draw() {
background(0);
if (showingIntro) {
text("INTRO", 20, 20);
} else {
ellipse(50, 50, 25, 25);
}
}
void mouseClicked() {
showingIntro = false;
}
I am tinkering with Processing and cannot figure out how to write text over an image I created using the image buffer (rotating squares)...when the square becomes smaller than the text, the changing digits wrote on top of each other. Cannot use resetting the bkg as a solution because that erases the overlapping images. Still having a hard time understanding this area...
Question: How to get the text to appear on top of the rotating squares without resetting the bkg and without the text writing over itself
Code below
Thank you!
float rotateAmount;
int boxColorR = 255;
int boxColorG = 255;
int boxColorB = 255;
int boxW = 480;
void setup () {
size(640,480);
rectMode(CENTER);
}
void drawText() {
//translate(width/2,height/2);
textAlign(LEFT, CENTER);
fill(255, 255, 255);
textSize(32);
text("RED: " + boxColorR,width/2,height/2);
text("GREEN: " + boxColorG,width/2,height/2+30);
text("BLUE: " + boxColorB,width/2,height/2+60);
text("Box Width: " + boxW,width/2,height/2+90);
}
void drawBox() {
translate(width/2,height/2);
rotateAmount += 12;
if (boxColorR <= 0) {
boxColorG--;
}
if (boxColorG <= 0) {
boxColorB--;
}
boxColorR--;
boxW--;
rotateAmount += .05;
rotate(rotateAmount);
fill(boxColorR,boxColorG,boxColorB);
rect(0,0,boxW,boxW);
resetMatrix();
}
void draw() {
//rect(width/2,height/2,640,480); //this solves the text overlapping but erases the cool effect
drawBox();
drawText();
}
Most Processing sketches use a call to the background() function as the first line in the draw() function. This clears out anything drawn in previous frames.
However, you want to keep the stuff drawn in previous frames, so you don't want to clear them out. The problem with this is that since your text isn't cleared out either, your text ends up looking garbled.
The solution to this is to use the PGraphics class to create an off-screen buffer. You draw the squares to the buffer instead of to the screen. Then you draw the buffer to the screen, and finally, you draw the text on top of the buffer.
Since you draw the buffer to the screen each frame, it clears away the old text, but the squares you've previously drawn are maintained in the buffer.
Code speaks louder than words:
float rotateAmount;
int boxColorR = 255;
int boxColorG = 255;
int boxColorB = 255;
int boxW = 480;
//create a buffer to draw boxes to
PGraphics buffer;
void setup () {
size(640, 480);
buffer = createGraphics(640, 480);
}
void drawText() {
//translate(width/2,height/2);
textAlign(LEFT, CENTER);
fill(255, 255, 255);
textSize(32);
text("RED: " + boxColorR, width/2, height/2);
text("GREEN: " + boxColorG, width/2, height/2+30);
text("BLUE: " + boxColorB, width/2, height/2+60);
text("Box Width: " + boxW, width/2, height/2+90);
}
//draw boxes to buffer
void drawBox() {
buffer.beginDraw();
buffer.rectMode(CENTER);
buffer.translate(width/2, height/2);
rotateAmount += 12;
if (boxColorR <= 0) {
boxColorG--;
}
if (boxColorG <= 0) {
boxColorB--;
}
boxColorR--;
boxW--;
rotateAmount += .05;
buffer.rotate(rotateAmount);
buffer.fill(boxColorR, boxColorG, boxColorB);
buffer.rect(0, 0, boxW, boxW);
buffer.resetMatrix();
buffer.endDraw();
}
void draw() {
//draw the boxes to the buffer
drawBox();
//draw the buffer to the screen
image(buffer, 0, 0);
//draw the text on top of the buffer
drawText();
}
I am trying to use processing to get the point cloud. But it turn out that it does not work
import SimpleOpenNI.*;
import processing.opengl.*;
SimpleOpenNI kinect;
void setup()
{
size( 1024, 768, OPENGL);
kinect = new SimpleOpenNI( this );
kinect.enableDepth();
}
void draw()
{
background( 0);
kinect.update();
translate( width/2, height/2, -1000);
rotateX( radians(180));
stroke(255);
PVector[] depthPoints = kinect.depthMapRealWorld();
//the program get stucked in the for loop it loops 307200 times and I don't have any points output
for( int i = 0; i < depthPoints.length ; i++)
{
PVector currentPoint = depthPoints[i];
point(currentPoint.x, currentPoint.y, currentPoint.z );
}
}
Your code if fine, just tested.
It loops 307200 times because it converts data from the depth image (640x480 = 307200) into 3D positions.
Are you sure you're not getting any errors ?
Also, drawing all the points in Processing is a bit slow, you might want to skip a few.
And as test, try to print out the 1st point and see if the value changes at all (it should)
or if the depth image has any data (isn't black/filled with zeroes):
import SimpleOpenNI.*;
import processing.opengl.*;
SimpleOpenNI kinect;
void setup()
{
size( 1024, 768, OPENGL);
kinect = new SimpleOpenNI( this );
kinect.enableDepth();
}
void draw()
{
background( 0);
kinect.update();
image(kinect.depthImage(),0,0,160,120);//check depth image
translate( width/2, height/2, -1000);
rotateX( radians(180));
stroke(255);
PVector[] depthPoints = kinect.depthMapRealWorld();
//the program get stucked in the for loop it loops 307200 times and I don't have any points output
for( int i = 0; i < depthPoints.length ; i+=4)//draw point for every 4th pixel
{
PVector currentPoint = depthPoints[i];
if(i == 0) println(currentPoint);
point(currentPoint.x, currentPoint.y, currentPoint.z );
}
}